From b6c01fcabd0c9bf680c7a0d2ea1b5ec75f92fb04 Mon Sep 17 00:00:00 2001 From: raster Date: Sat, 29 Jan 2011 03:36:15 +0000 Subject: [PATCH] move elementary to trunk base. out of TMP/st. git-svn-id: svn+ssh://svn.enlightenment.org/var/svn/e/trunk/elementary@56356 7cbeb6ba-43b4-40fd-8cce-4c39aea84d33 --- .gitignore | 43 + AUTHORS | 36 + COPYING | 491 + ChangeLog | 0 INSTALL | 14 + Makefile.am | 45 + NEWS | 0 README | 3 + autogen.sh | 16 + config/Makefile.am | 18 + config/default/Makefile.am | 23 + config/default/base.src | 37 + config/default/icon.png | Bin 0 -> 9183 bytes config/default/profile.desktop | 21 + config/illume/Makefile.am | 22 + config/illume/base.src | 37 + config/illume/icon.png | Bin 0 -> 7555 bytes config/illume/profile.desktop | 16 + config/profile.src | 1 + config/standard/Makefile.am | 23 + config/standard/base.src | 37 + config/standard/icon.png | Bin 0 -> 12068 bytes config/standard/profile.desktop | 19 + configure.ac | 542 + data/.cvsignore | 3 + data/Makefile.am | 3 + data/desktop/Makefile.am | 10 + data/desktop/elementary.png | Bin 0 -> 7313 bytes data/desktop/elementary_config.desktop | 13 + data/desktop/elementary_test.desktop | 13 + data/edje_externals/Makefile.am | 42 + data/edje_externals/ico_anchorblock.png | Bin 0 -> 306 bytes data/edje_externals/ico_anchorview.png | Bin 0 -> 403 bytes data/edje_externals/ico_bubble.png | Bin 0 -> 1311 bytes data/edje_externals/ico_button.png | Bin 0 -> 181 bytes data/edje_externals/ico_check.png | Bin 0 -> 179 bytes data/edje_externals/ico_clock.png | Bin 0 -> 7958 bytes data/edje_externals/ico_fileselector.png | Bin 0 -> 265 bytes data/edje_externals/ico_fileselector_button.png | Bin 0 -> 198 bytes data/edje_externals/ico_genlist.png | Bin 0 -> 158 bytes data/edje_externals/ico_hoversel.png | Bin 0 -> 4670 bytes data/edje_externals/ico_list.png | Bin 0 -> 2167 bytes data/edje_externals/ico_map.png | Bin 0 -> 2232 bytes data/edje_externals/ico_notepad.png | Bin 0 -> 148 bytes data/edje_externals/ico_photocam.png | Bin 0 -> 11838 bytes data/edje_externals/ico_progressbar.png | Bin 0 -> 138 bytes data/edje_externals/ico_radio.png | Bin 0 -> 257 bytes data/edje_externals/ico_scrolled_entry.png | Bin 0 -> 125 bytes data/edje_externals/ico_slider.png | Bin 0 -> 172 bytes data/edje_externals/ico_slideshow.png | Bin 0 -> 1059 bytes data/edje_externals/ico_spinner.png | Bin 0 -> 215 bytes data/edje_externals/ico_thumb.png | Bin 0 -> 147 bytes data/edje_externals/ico_toggle.png | Bin 0 -> 200 bytes data/edje_externals/ico_toolbar.png | Bin 0 -> 6075 bytes data/edje_externals/icons.edc | 37 + data/images/Makefile.am | 47 + data/images/bubble.png | Bin 0 -> 4878 bytes data/images/bubble_sh.png | Bin 0 -> 1600 bytes data/images/icon_00.png | Bin 0 -> 9793 bytes data/images/icon_01.png | Bin 0 -> 11371 bytes data/images/icon_02.png | Bin 0 -> 12432 bytes data/images/icon_03.png | Bin 0 -> 15014 bytes data/images/icon_04.png | Bin 0 -> 7912 bytes data/images/icon_05.png | Bin 0 -> 1483 bytes data/images/icon_06.png | Bin 0 -> 4977 bytes data/images/icon_07.png | Bin 0 -> 2548 bytes data/images/icon_08.png | Bin 0 -> 4861 bytes data/images/icon_09.png | Bin 0 -> 7774 bytes data/images/icon_10.png | Bin 0 -> 4745 bytes data/images/icon_11.png | Bin 0 -> 8684 bytes data/images/icon_12.png | Bin 0 -> 3018 bytes data/images/icon_13.png | Bin 0 -> 5051 bytes data/images/icon_14.png | Bin 0 -> 8448 bytes data/images/icon_15.png | Bin 0 -> 8706 bytes data/images/icon_16.png | Bin 0 -> 11758 bytes data/images/icon_17.png | Bin 0 -> 13769 bytes data/images/icon_18.png | Bin 0 -> 6079 bytes data/images/icon_19.png | Bin 0 -> 11785 bytes data/images/icon_20.png | Bin 0 -> 8278 bytes data/images/icon_21.png | Bin 0 -> 14661 bytes data/images/icon_22.png | Bin 0 -> 12215 bytes data/images/icon_23.png | Bin 0 -> 10078 bytes data/images/logo.png | Bin 0 -> 81162 bytes data/images/logo_small.png | Bin 0 -> 5655 bytes data/images/mystrale.jpg | Bin 0 -> 74115 bytes data/images/mystrale_2.jpg | Bin 0 -> 355595 bytes data/images/panel_01.jpg | Bin 0 -> 63544 bytes data/images/parking.png | Bin 0 -> 3166 bytes data/images/plant_01.jpg | Bin 0 -> 165867 bytes data/images/rock_01.jpg | Bin 0 -> 330094 bytes data/images/rock_02.jpg | Bin 0 -> 285555 bytes data/images/sky_01.jpg | Bin 0 -> 134813 bytes data/images/sky_02.jpg | Bin 0 -> 31413 bytes data/images/sky_03.jpg | Bin 0 -> 73364 bytes data/images/sky_04.jpg | Bin 0 -> 25078 bytes data/images/wood_01.jpg | Bin 0 -> 96136 bytes data/objects/Makefile.am | 50 + data/objects/clo.png | Bin 0 -> 120231 bytes data/objects/colorpreview.edc | 22 + data/objects/cross.png | Bin 0 -> 18620 bytes data/objects/cursors.edc | 80 + data/objects/font_preview.edc | 40 + data/objects/grid_bg.png | Bin 0 -> 1146 bytes data/objects/multip.edc | 17 + data/objects/over.png | Bin 0 -> 73621 bytes data/objects/sky.jpg | Bin 0 -> 69378 bytes data/objects/test.edc | 698 + data/objects/under.png | Bin 0 -> 36742 bytes data/themes/Makefile.am | 233 + data/themes/arrow_down.png | Bin 0 -> 1577 bytes data/themes/arrow_down.xcf.gz | Bin 0 -> 4262 bytes data/themes/arrow_left.png | Bin 0 -> 1637 bytes data/themes/arrow_right.png | Bin 0 -> 1605 bytes data/themes/arrow_up.png | Bin 0 -> 1584 bytes data/themes/arrow_up.xcf.gz | Bin 0 -> 3261 bytes data/themes/bar_shine.png | Bin 0 -> 3045 bytes data/themes/black.png | Bin 0 -> 124 bytes data/themes/bt_base1.png | Bin 0 -> 952 bytes data/themes/bt_base2.png | Bin 0 -> 981 bytes data/themes/bt_bases.png | Bin 0 -> 769 bytes data/themes/bt_basew.png | Bin 0 -> 1527 bytes data/themes/bt_dis_base.png | Bin 0 -> 1101 bytes data/themes/bt_dis_hilight.png | Bin 0 -> 230 bytes data/themes/bt_dis_shine.png | Bin 0 -> 1153 bytes data/themes/bt_glow.png | Bin 0 -> 1028 bytes data/themes/bt_hilight.png | Bin 0 -> 343 bytes data/themes/bt_hilightw.png | Bin 0 -> 279 bytes data/themes/bt_shine.png | Bin 0 -> 305 bytes data/themes/bt_sm_base1.png | Bin 0 -> 477 bytes data/themes/bt_sm_base2.png | Bin 0 -> 482 bytes data/themes/bt_sm_hilight.png | Bin 0 -> 285 bytes data/themes/bt_sm_shine.png | Bin 0 -> 275 bytes data/themes/bt_spinner_down.png | Bin 0 -> 687 bytes data/themes/bt_spinner_hilight.png | Bin 0 -> 344 bytes data/themes/bt_spinner_up.png | Bin 0 -> 511 bytes data/themes/bubble.png | Bin 0 -> 1230 bytes data/themes/bubble_1.png | Bin 0 -> 1335 bytes data/themes/bubble_2.png | Bin 0 -> 1339 bytes data/themes/bubble_3.png | Bin 0 -> 1308 bytes data/themes/bubble_4.png | Bin 0 -> 1307 bytes data/themes/bubble_shine.png | Bin 0 -> 251 bytes data/themes/bubble_shine3.png | Bin 0 -> 336 bytes data/themes/bubble_shine4.png | Bin 0 -> 327 bytes data/themes/busy-1.png | Bin 0 -> 2124 bytes data/themes/busy-2.png | Bin 0 -> 2339 bytes data/themes/busy-3.png | Bin 0 -> 2395 bytes data/themes/busy-4.png | Bin 0 -> 2395 bytes data/themes/busy-5.png | Bin 0 -> 2299 bytes data/themes/busy-6.png | Bin 0 -> 2216 bytes data/themes/busy-7.png | Bin 0 -> 2286 bytes data/themes/busy-8.png | Bin 0 -> 2293 bytes data/themes/busy-9.png | Bin 0 -> 2249 bytes data/themes/check.png | Bin 0 -> 3058 bytes data/themes/check2.png | Bin 0 -> 2561 bytes data/themes/check_base.png | Bin 0 -> 320 bytes data/themes/color_picker_alpha.png | Bin 0 -> 3156 bytes data/themes/color_picker_alpha_bg.png | Bin 0 -> 974 bytes data/themes/color_picker_brightness.png | Bin 0 -> 657 bytes data/themes/color_picker_color.png | Bin 0 -> 4480 bytes data/themes/color_picker_opacity.png | Bin 0 -> 3886 bytes data/themes/cur_box.png | Bin 0 -> 187 bytes data/themes/cur_glow.png | Bin 0 -> 391 bytes data/themes/cur_hi.png | Bin 0 -> 188 bytes data/themes/cur_shad.png | Bin 0 -> 252 bytes data/themes/cur_shine.png | Bin 0 -> 200 bytes data/themes/default-desktop.edc | 1351 + data/themes/default.edc | 36110 ++++++++++++++++++++++ data/themes/dia_botshad.png | Bin 0 -> 209 bytes data/themes/dia_grad.png | Bin 0 -> 5155 bytes data/themes/dia_topshad.png | Bin 0 -> 249 bytes data/themes/down.png | Bin 0 -> 841 bytes data/themes/emo-angry-shout.png | Bin 0 -> 8717 bytes data/themes/emo-angry.png | Bin 0 -> 8959 bytes data/themes/emo-crazy-laugh.png | Bin 0 -> 9225 bytes data/themes/emo-evil-laugh.png | Bin 0 -> 9092 bytes data/themes/emo-evil.png | Bin 0 -> 8991 bytes data/themes/emo-goggle-smile.png | Bin 0 -> 9670 bytes data/themes/emo-grumpy-smile.png | Bin 0 -> 8587 bytes data/themes/emo-grumpy.png | Bin 0 -> 8574 bytes data/themes/emo-guilty-smile.png | Bin 0 -> 9298 bytes data/themes/emo-guilty.png | Bin 0 -> 9151 bytes data/themes/emo-haha.png | Bin 0 -> 8993 bytes data/themes/emo-half-smile.png | Bin 0 -> 8667 bytes data/themes/emo-happy-panting.png | Bin 0 -> 9206 bytes data/themes/emo-happy.png | Bin 0 -> 8571 bytes data/themes/emo-indifferent.png | Bin 0 -> 8526 bytes data/themes/emo-kiss.png | Bin 0 -> 9214 bytes data/themes/emo-knowing-grin.png | Bin 0 -> 8481 bytes data/themes/emo-laugh.png | Bin 0 -> 9139 bytes data/themes/emo-little-bit-sorry.png | Bin 0 -> 8288 bytes data/themes/emo-love-lots.png | Bin 0 -> 9671 bytes data/themes/emo-love.png | Bin 0 -> 8981 bytes data/themes/emo-minimal-smile.png | Bin 0 -> 8896 bytes data/themes/emo-not-happy.png | Bin 0 -> 8885 bytes data/themes/emo-not-impressed.png | Bin 0 -> 8300 bytes data/themes/emo-omg.png | Bin 0 -> 8727 bytes data/themes/emo-opensmile.png | Bin 0 -> 9580 bytes data/themes/emo-smile.png | Bin 0 -> 9590 bytes data/themes/emo-sorry.png | Bin 0 -> 8638 bytes data/themes/emo-squint-laugh.png | Bin 0 -> 9103 bytes data/themes/emo-surprised.png | Bin 0 -> 8431 bytes data/themes/emo-suspicious.png | Bin 0 -> 8543 bytes data/themes/emo-tongue-dangling.png | Bin 0 -> 9005 bytes data/themes/emo-tongue-poke.png | Bin 0 -> 8974 bytes data/themes/emo-uh.png | Bin 0 -> 8641 bytes data/themes/emo-unhappy.png | Bin 0 -> 8686 bytes data/themes/emo-very-sorry.png | Bin 0 -> 9009 bytes data/themes/emo-what.png | Bin 0 -> 8410 bytes data/themes/emo-wink.png | Bin 0 -> 8749 bytes data/themes/emo-worried.png | Bin 0 -> 9116 bytes data/themes/emo-wtf.png | Bin 0 -> 8946 bytes data/themes/flip.xcf.gz | Bin 0 -> 10985 bytes data/themes/flip_0b.png | Bin 0 -> 1540 bytes data/themes/flip_0t.png | Bin 0 -> 1547 bytes data/themes/flip_1b.png | Bin 0 -> 451 bytes data/themes/flip_1t.png | Bin 0 -> 666 bytes data/themes/flip_2b.png | Bin 0 -> 1074 bytes data/themes/flip_2t.png | Bin 0 -> 1495 bytes data/themes/flip_3b.png | Bin 0 -> 1408 bytes data/themes/flip_3t.png | Bin 0 -> 1444 bytes data/themes/flip_4b.png | Bin 0 -> 705 bytes data/themes/flip_4t.png | Bin 0 -> 1137 bytes data/themes/flip_5b.png | Bin 0 -> 1490 bytes data/themes/flip_5t.png | Bin 0 -> 824 bytes data/themes/flip_6b.png | Bin 0 -> 1651 bytes data/themes/flip_6t.png | Bin 0 -> 1569 bytes data/themes/flip_7b.png | Bin 0 -> 1110 bytes data/themes/flip_7t.png | Bin 0 -> 996 bytes data/themes/flip_8b.png | Bin 0 -> 1660 bytes data/themes/flip_8t.png | Bin 0 -> 1719 bytes data/themes/flip_9b.png | Bin 0 -> 1512 bytes data/themes/flip_9t.png | Bin 0 -> 1659 bytes data/themes/flip_amb.png | Bin 0 -> 963 bytes data/themes/flip_amt.png | Bin 0 -> 1075 bytes data/themes/flip_b.png | Bin 0 -> 384 bytes data/themes/flip_base.png | Bin 0 -> 598 bytes data/themes/flip_base_shad.png | Bin 0 -> 826 bytes data/themes/flip_pmb.png | Bin 0 -> 709 bytes data/themes/flip_pmt.png | Bin 0 -> 1052 bytes data/themes/flip_shad.png | Bin 0 -> 918 bytes data/themes/flip_t.png | Bin 0 -> 442 bytes data/themes/frame_1.png | Bin 0 -> 431 bytes data/themes/frame_2.png | Bin 0 -> 676 bytes data/themes/group_index.png | Bin 0 -> 217 bytes data/themes/head.png | Bin 0 -> 10083 bytes data/themes/hoversel_entry_bg.png | Bin 0 -> 782 bytes data/themes/icon_apps.png | Bin 0 -> 872 bytes data/themes/icon_arrow_down.png | Bin 0 -> 866 bytes data/themes/icon_arrow_down_left.png | Bin 0 -> 1992 bytes data/themes/icon_arrow_down_right.png | Bin 0 -> 1649 bytes data/themes/icon_arrow_left.png | Bin 0 -> 893 bytes data/themes/icon_arrow_right.png | Bin 0 -> 942 bytes data/themes/icon_arrow_up.png | Bin 0 -> 776 bytes data/themes/icon_arrow_up_left.png | Bin 0 -> 1695 bytes data/themes/icon_arrow_up_right.png | Bin 0 -> 2028 bytes data/themes/icon_chat.png | Bin 0 -> 3221 bytes data/themes/icon_clock.png | Bin 0 -> 4190 bytes data/themes/icon_close.png | Bin 0 -> 3221 bytes data/themes/icon_delete.png | Bin 0 -> 1628 bytes data/themes/icon_edit.png | Bin 0 -> 1138 bytes data/themes/icon_file.png | Bin 0 -> 2753 bytes data/themes/icon_folder.png | Bin 0 -> 6124 bytes data/themes/icon_home.png | Bin 0 -> 1534 bytes data/themes/icon_left_arrow.png | Bin 0 -> 1887 bytes data/themes/icon_refresh.png | Bin 0 -> 5123 bytes data/themes/icon_right_arrow.png | Bin 0 -> 1832 bytes data/themes/ilist_1.png | Bin 0 -> 1281 bytes data/themes/ilist_1_h.png | Bin 0 -> 1222 bytes data/themes/ilist_2.png | Bin 0 -> 1381 bytes data/themes/ilist_2_h.png | Bin 0 -> 1384 bytes data/themes/ilist_item_shadow.png | Bin 0 -> 322 bytes data/themes/ilist_item_shadow_h.png | Bin 0 -> 350 bytes data/themes/leftright.png | Bin 0 -> 1367 bytes data/themes/map_item.png | Bin 0 -> 3041 bytes data/themes/map_item_1.png | Bin 0 -> 2669 bytes data/themes/map_item_2.png | Bin 0 -> 2578 bytes data/themes/outdent-bottom.png | Bin 0 -> 1826 bytes data/themes/outdent-top.png | Bin 0 -> 1913 bytes data/themes/radio.png | Bin 0 -> 4684 bytes data/themes/radio2.png | Bin 0 -> 4406 bytes data/themes/radio_base.png | Bin 0 -> 3125 bytes data/themes/sb_runnerh.png | Bin 0 -> 160 bytes data/themes/sb_runnerv.png | Bin 0 -> 166 bytes data/themes/separator_h.png | Bin 0 -> 151 bytes data/themes/separator_v.png | Bin 0 -> 96 bytes data/themes/shad_circ.png | Bin 0 -> 1521 bytes data/themes/shadow.png | Bin 0 -> 1030 bytes data/themes/shelf_inset.png | Bin 0 -> 509 bytes data/themes/sl_bg.png | Bin 0 -> 479 bytes data/themes/sl_bg_over.png | Bin 0 -> 302 bytes data/themes/sl_bt2_0_0.png | Bin 0 -> 413 bytes data/themes/sl_bt2_0_1.png | Bin 0 -> 466 bytes data/themes/sl_bt2_0_2.png | Bin 0 -> 446 bytes data/themes/sl_bt2_1.png | Bin 0 -> 350 bytes data/themes/sl_bt2_2.png | Bin 0 -> 286 bytes data/themes/sl_bt_0.png | Bin 0 -> 571 bytes data/themes/sl_bt_1.png | Bin 0 -> 249 bytes data/themes/sl_bt_2.png | Bin 0 -> 246 bytes data/themes/sl_bt_3.png | Bin 0 -> 570 bytes data/themes/sl_units.png | Bin 0 -> 893 bytes data/themes/slv_bg.png | Bin 0 -> 555 bytes data/themes/slv_bg_over.png | Bin 0 -> 300 bytes data/themes/slv_units.png | Bin 0 -> 812 bytes data/themes/sp_bt_l.png | Bin 0 -> 440 bytes data/themes/sp_bt_r.png | Bin 0 -> 369 bytes data/themes/thumb_shadow.png | Bin 0 -> 1087 bytes data/themes/tog_base.png | Bin 0 -> 868 bytes data/themes/tog_dis_base.png | Bin 0 -> 2148 bytes data/themes/toolbar_sel.png | Bin 0 -> 2107 bytes data/themes/toolbar_separator_v.png | Bin 0 -> 166 bytes data/themes/tooltip-base.png | Bin 0 -> 1656 bytes data/themes/tooltip-corner-bottom-left-tip.png | Bin 0 -> 440 bytes data/themes/tooltip-corner-bottom-right-tip.png | Bin 0 -> 441 bytes data/themes/tooltip-corner-top-left-tip.png | Bin 0 -> 452 bytes data/themes/tooltip-corner-top-right-tip.png | Bin 0 -> 453 bytes data/themes/tooltip-edge-bottom-tip.png | Bin 0 -> 471 bytes data/themes/tooltip-edge-left-tip.png | Bin 0 -> 466 bytes data/themes/tooltip-edge-right-tip.png | Bin 0 -> 494 bytes data/themes/tooltip-edge-top-tip.png | Bin 0 -> 475 bytes data/themes/up.png | Bin 0 -> 788 bytes data/themes/updown.png | Bin 0 -> 1416 bytes doc/.cvsignore | 3 + doc/Doxyfile | 139 + doc/Makefile.am | 32 + doc/e.css | 273 + doc/elementary.dox.in | 62 + doc/foot.html | 18 + doc/head.html | 68 + doc/img/edoxy.css | 486 + doc/img/elementary.png | Bin 0 -> 7313 bytes doc/img/foot_bg.png | Bin 0 -> 173 bytes doc/img/head_bg.png | Bin 0 -> 214 bytes doc/img/header_menu_background.png | Bin 0 -> 192 bytes doc/img/header_menu_background_last.png | Bin 0 -> 637 bytes doc/img/header_menu_current_background.png | Bin 0 -> 1200 bytes doc/img/header_menu_unselected_background.png | Bin 0 -> 1596 bytes doc/img/logo.png | Bin 0 -> 3825 bytes elementary.pc.in | 12 + elementary.spec.in | 102 + m4/ac_attribute.m4 | 47 + m4/efl_binary.m4 | 71 + m4/efl_doxygen.m4 | 99 + m4/efl_threads.m4 | 206 + src/.cvsignore | 2 + src/Makefile.am | 4 + src/bin/.cvsignore | 7 + src/bin/Makefile.am | 133 + src/bin/config.c | 3019 ++ src/bin/quicklaunch.c | 297 + src/bin/run.c | 160 + src/bin/test.c | 419 + src/bin/test_actionslider.c | 131 + src/bin/test_anchorblock.c | 243 + src/bin/test_anchorview.c | 108 + src/bin/test_anim.c | 113 + src/bin/test_bg.c | 211 + src/bin/test_box.c | 280 + src/bin/test_bubble.c | 81 + src/bin/test_button.c | 174 + src/bin/test_calendar.c | 181 + src/bin/test_check.c | 83 + src/bin/test_clock.c | 146 + src/bin/test_colorselector.c | 97 + src/bin/test_conform.c | 205 + src/bin/test_ctxpopup.c | 178 + src/bin/test_cursor.c | 397 + src/bin/test_diskselector.c | 131 + src/bin/test_entry.c | 1644 + src/bin/test_fileselector.c | 210 + src/bin/test_fileselector_button.c | 147 + src/bin/test_fileselector_entry.c | 159 + src/bin/test_flip.c | 494 + src/bin/test_flipselector.c | 115 + src/bin/test_floating.c | 109 + src/bin/test_focus.c | 376 + src/bin/test_focus2.c | 151 + src/bin/test_gengrid.c | 357 + src/bin/test_genlist.c | 1631 + src/bin/test_hover.c | 172 + src/bin/test_hoversel.c | 109 + src/bin/test_icon.c | 37 + src/bin/test_icon_desktops.c | 128 + src/bin/test_index.c | 255 + src/bin/test_inwin.c | 71 + src/bin/test_label.c | 78 + src/bin/test_launcher.c | 922 + src/bin/test_layout.c | 83 + src/bin/test_list.c | 758 + src/bin/test_map.c | 604 + src/bin/test_menu.c | 115 + src/bin/test_multi.c | 135 + src/bin/test_notify.c | 307 + src/bin/test_pager.c | 330 + src/bin/test_panel.c | 264 + src/bin/test_panes.c | 118 + src/bin/test_photo.c | 104 + src/bin/test_photocam.c | 342 + src/bin/test_progressbar.c | 205 + src/bin/test_radio.c | 102 + src/bin/test_scaling.c | 126 + src/bin/test_scroller.c | 266 + src/bin/test_separator.c | 74 + src/bin/test_slider.c | 199 + src/bin/test_slideshow.c | 215 + src/bin/test_spinner.c | 89 + src/bin/test_store.c | 268 + src/bin/test_table.c | 69 + src/bin/test_thumb.c | 70 + src/bin/test_toggle.c | 87 + src/bin/test_toolbar.c | 618 + src/bin/test_tooltip.c | 550 + src/bin/test_transit.c | 524 + src/bin/test_weather.c | 176 + src/bin/test_win_state.c | 369 + src/edje_externals/Makefile.am | 61 + src/edje_externals/elm.c | 300 + src/edje_externals/elm_anchorblock.c | 104 + src/edje_externals/elm_anchorview.c | 104 + src/edje_externals/elm_bubble.c | 165 + src/edje_externals/elm_button.c | 125 + src/edje_externals/elm_check.c | 148 + src/edje_externals/elm_clock.c | 241 + src/edje_externals/elm_fileselector.c | 185 + src/edje_externals/elm_fileselector_button.c | 252 + src/edje_externals/elm_fileselector_entry.c | 252 + src/edje_externals/elm_genlist.c | 333 + src/edje_externals/elm_hoversel.c | 148 + src/edje_externals/elm_icon.c | 116 + src/edje_externals/elm_label.c | 87 + src/edje_externals/elm_list.c | 305 + src/edje_externals/elm_map.c | 207 + src/edje_externals/elm_notify.c | 199 + src/edje_externals/elm_panes.c | 171 + src/edje_externals/elm_photocam.c | 208 + src/edje_externals/elm_progressbar.c | 251 + src/edje_externals/elm_radio.c | 176 + src/edje_externals/elm_scrolled_entry.c | 184 + src/edje_externals/elm_scroller.c | 104 + src/edje_externals/elm_slider.c | 339 + src/edje_externals/elm_slideshow.c | 182 + src/edje_externals/elm_spinner.c | 244 + src/edje_externals/elm_thumb.c | 146 + src/edje_externals/elm_toggle.c | 212 + src/edje_externals/elm_toolbar.c | 129 + src/edje_externals/modules.inc | 28 + src/edje_externals/private.h | 118 + src/lib/Elementary.h.in | 2647 ++ src/lib/Elementary_Cursor.h | 88 + src/lib/Makefile.am | 137 + src/lib/elc_anchorblock.c | 461 + src/lib/elc_anchorview.c | 494 + src/lib/elc_ctxpopup.c | 1563 + src/lib/elc_fileselector.c | 1052 + src/lib/elc_fileselector_button.c | 683 + src/lib/elc_fileselector_entry.c | 655 + src/lib/elc_hoversel.c | 721 + src/lib/elc_scrolled_entry.c | 1611 + src/lib/elm_actionslider.c | 546 + src/lib/elm_animator.c | 446 + src/lib/elm_bg.c | 398 + src/lib/elm_box.c | 894 + src/lib/elm_bubble.c | 476 + src/lib/elm_button.c | 564 + src/lib/elm_calendar.c | 1280 + src/lib/elm_check.c | 471 + src/lib/elm_clock.c | 837 + src/lib/elm_cnp_helper.c | 1779 ++ src/lib/elm_colorselector.c | 878 + src/lib/elm_config.c | 1740 ++ src/lib/elm_conform.c | 346 + src/lib/elm_diskselector.c | 1543 + src/lib/elm_entry.c | 2791 ++ src/lib/elm_flip.c | 700 + src/lib/elm_flipselector.c | 1158 + src/lib/elm_font.c | 128 + src/lib/elm_frame.c | 251 + src/lib/elm_gengrid.c | 2904 ++ src/lib/elm_genlist.c | 4873 +++ src/lib/elm_hover.c | 957 + src/lib/elm_icon.c | 651 + src/lib/elm_image.c | 487 + src/lib/elm_index.c | 959 + src/lib/elm_label.c | 1064 + src/lib/elm_layout.c | 1274 + src/lib/elm_list.c | 2497 ++ src/lib/elm_main.c | 3430 ++ src/lib/elm_map.c | 3627 +++ src/lib/elm_mapbuf.c | 395 + src/lib/elm_menu.c | 928 + src/lib/elm_module.c | 216 + src/lib/elm_notify.c | 625 + src/lib/elm_pager.c | 442 + src/lib/elm_panel.c | 469 + src/lib/elm_panes.c | 429 + src/lib/elm_photo.c | 342 + src/lib/elm_photocam.c | 1780 ++ src/lib/elm_priv.h | 204 + src/lib/elm_progressbar.c | 635 + src/lib/elm_radio.c | 587 + src/lib/elm_scroller.c | 919 + src/lib/elm_separator.c | 130 + src/lib/elm_slider.c | 1142 + src/lib/elm_slideshow.c | 798 + src/lib/elm_spinner.c | 924 + src/lib/elm_store.c | 754 + src/lib/elm_table.c | 279 + src/lib/elm_theme.c | 866 + src/lib/elm_thumb.c | 755 + src/lib/elm_toggle.c | 480 + src/lib/elm_toolbar.c | 2250 ++ src/lib/elm_transit.c | 2664 ++ src/lib/elm_util.c | 197 + src/lib/elm_widget.c | 2758 ++ src/lib/elm_widget.h | 545 + src/lib/elm_win.c | 2505 ++ src/lib/els_box.c | 220 + src/lib/els_box.h | 1 + src/lib/els_cursor.c | 617 + src/lib/els_icon.c | 726 + src/lib/els_icon.h | 23 + src/lib/els_pan.c | 285 + src/lib/els_pan.h | 8 + src/lib/els_scroller.c | 2606 ++ src/lib/els_scroller.h | 39 + src/lib/els_tooltip.c | 787 + src/modules/Makefile.am | 6 + src/modules/test_entry/Makefile.am | 32 + src/modules/test_entry/mod.c | 36 + src/modules/test_map/Makefile.am | 32 + src/modules/test_map/mod.c | 50 + tests/test_decl.sh | 102 + tests/test_eapi.sh | 40 + tests/test_getter.sh | 27 + tests/test_setter.sh | 55 + tests/test_setter_blacklist.txt | 18 + 535 files changed, 149576 insertions(+) create mode 100644 .gitignore create mode 100644 AUTHORS create mode 100644 COPYING create mode 100644 ChangeLog create mode 100644 INSTALL create mode 100644 Makefile.am create mode 100644 NEWS create mode 100644 README create mode 100755 autogen.sh create mode 100644 config/Makefile.am create mode 100644 config/default/Makefile.am create mode 100644 config/default/base.src create mode 100644 config/default/icon.png create mode 100644 config/default/profile.desktop create mode 100644 config/illume/Makefile.am create mode 100644 config/illume/base.src create mode 100644 config/illume/icon.png create mode 100644 config/illume/profile.desktop create mode 100644 config/profile.src create mode 100644 config/standard/Makefile.am create mode 100644 config/standard/base.src create mode 100644 config/standard/icon.png create mode 100644 config/standard/profile.desktop create mode 100644 configure.ac create mode 100644 data/.cvsignore create mode 100644 data/Makefile.am create mode 100644 data/desktop/Makefile.am create mode 100644 data/desktop/elementary.png create mode 100644 data/desktop/elementary_config.desktop create mode 100644 data/desktop/elementary_test.desktop create mode 100644 data/edje_externals/Makefile.am create mode 100644 data/edje_externals/ico_anchorblock.png create mode 100644 data/edje_externals/ico_anchorview.png create mode 100644 data/edje_externals/ico_bubble.png create mode 100644 data/edje_externals/ico_button.png create mode 100644 data/edje_externals/ico_check.png create mode 100644 data/edje_externals/ico_clock.png create mode 100644 data/edje_externals/ico_fileselector.png create mode 100644 data/edje_externals/ico_fileselector_button.png create mode 100644 data/edje_externals/ico_genlist.png create mode 100644 data/edje_externals/ico_hoversel.png create mode 100755 data/edje_externals/ico_list.png create mode 100644 data/edje_externals/ico_map.png create mode 100644 data/edje_externals/ico_notepad.png create mode 100644 data/edje_externals/ico_photocam.png create mode 100644 data/edje_externals/ico_progressbar.png create mode 100644 data/edje_externals/ico_radio.png create mode 100644 data/edje_externals/ico_scrolled_entry.png create mode 100644 data/edje_externals/ico_slider.png create mode 100644 data/edje_externals/ico_slideshow.png create mode 100644 data/edje_externals/ico_spinner.png create mode 100644 data/edje_externals/ico_thumb.png create mode 100644 data/edje_externals/ico_toggle.png create mode 100644 data/edje_externals/ico_toolbar.png create mode 100644 data/edje_externals/icons.edc create mode 100644 data/images/Makefile.am create mode 100644 data/images/bubble.png create mode 100644 data/images/bubble_sh.png create mode 100644 data/images/icon_00.png create mode 100644 data/images/icon_01.png create mode 100644 data/images/icon_02.png create mode 100644 data/images/icon_03.png create mode 100644 data/images/icon_04.png create mode 100644 data/images/icon_05.png create mode 100644 data/images/icon_06.png create mode 100644 data/images/icon_07.png create mode 100644 data/images/icon_08.png create mode 100644 data/images/icon_09.png create mode 100644 data/images/icon_10.png create mode 100644 data/images/icon_11.png create mode 100644 data/images/icon_12.png create mode 100644 data/images/icon_13.png create mode 100644 data/images/icon_14.png create mode 100644 data/images/icon_15.png create mode 100644 data/images/icon_16.png create mode 100644 data/images/icon_17.png create mode 100644 data/images/icon_18.png create mode 100644 data/images/icon_19.png create mode 100644 data/images/icon_20.png create mode 100644 data/images/icon_21.png create mode 100644 data/images/icon_22.png create mode 100644 data/images/icon_23.png create mode 100644 data/images/logo.png create mode 100644 data/images/logo_small.png create mode 100644 data/images/mystrale.jpg create mode 100644 data/images/mystrale_2.jpg create mode 100644 data/images/panel_01.jpg create mode 100644 data/images/parking.png create mode 100644 data/images/plant_01.jpg create mode 100644 data/images/rock_01.jpg create mode 100644 data/images/rock_02.jpg create mode 100644 data/images/sky_01.jpg create mode 100644 data/images/sky_02.jpg create mode 100644 data/images/sky_03.jpg create mode 100644 data/images/sky_04.jpg create mode 100644 data/images/wood_01.jpg create mode 100644 data/objects/Makefile.am create mode 100644 data/objects/clo.png create mode 100644 data/objects/colorpreview.edc create mode 100644 data/objects/cross.png create mode 100644 data/objects/cursors.edc create mode 100644 data/objects/font_preview.edc create mode 100644 data/objects/grid_bg.png create mode 100644 data/objects/multip.edc create mode 100644 data/objects/over.png create mode 100644 data/objects/sky.jpg create mode 100644 data/objects/test.edc create mode 100644 data/objects/under.png create mode 100644 data/themes/Makefile.am create mode 100644 data/themes/arrow_down.png create mode 100644 data/themes/arrow_down.xcf.gz create mode 100644 data/themes/arrow_left.png create mode 100644 data/themes/arrow_right.png create mode 100644 data/themes/arrow_up.png create mode 100644 data/themes/arrow_up.xcf.gz create mode 100644 data/themes/bar_shine.png create mode 100644 data/themes/black.png create mode 100644 data/themes/bt_base1.png create mode 100644 data/themes/bt_base2.png create mode 100644 data/themes/bt_bases.png create mode 100644 data/themes/bt_basew.png create mode 100644 data/themes/bt_dis_base.png create mode 100644 data/themes/bt_dis_hilight.png create mode 100644 data/themes/bt_dis_shine.png create mode 100644 data/themes/bt_glow.png create mode 100644 data/themes/bt_hilight.png create mode 100644 data/themes/bt_hilightw.png create mode 100644 data/themes/bt_shine.png create mode 100644 data/themes/bt_sm_base1.png create mode 100644 data/themes/bt_sm_base2.png create mode 100644 data/themes/bt_sm_hilight.png create mode 100644 data/themes/bt_sm_shine.png create mode 100644 data/themes/bt_spinner_down.png create mode 100644 data/themes/bt_spinner_hilight.png create mode 100644 data/themes/bt_spinner_up.png create mode 100644 data/themes/bubble.png create mode 100644 data/themes/bubble_1.png create mode 100644 data/themes/bubble_2.png create mode 100644 data/themes/bubble_3.png create mode 100644 data/themes/bubble_4.png create mode 100644 data/themes/bubble_shine.png create mode 100644 data/themes/bubble_shine3.png create mode 100644 data/themes/bubble_shine4.png create mode 100644 data/themes/busy-1.png create mode 100644 data/themes/busy-2.png create mode 100644 data/themes/busy-3.png create mode 100644 data/themes/busy-4.png create mode 100644 data/themes/busy-5.png create mode 100644 data/themes/busy-6.png create mode 100644 data/themes/busy-7.png create mode 100644 data/themes/busy-8.png create mode 100644 data/themes/busy-9.png create mode 100644 data/themes/check.png create mode 100644 data/themes/check2.png create mode 100644 data/themes/check_base.png create mode 100644 data/themes/color_picker_alpha.png create mode 100644 data/themes/color_picker_alpha_bg.png create mode 100644 data/themes/color_picker_brightness.png create mode 100644 data/themes/color_picker_color.png create mode 100644 data/themes/color_picker_opacity.png create mode 100644 data/themes/cur_box.png create mode 100644 data/themes/cur_glow.png create mode 100644 data/themes/cur_hi.png create mode 100644 data/themes/cur_shad.png create mode 100644 data/themes/cur_shine.png create mode 100644 data/themes/default-desktop.edc create mode 100644 data/themes/default.edc create mode 100644 data/themes/dia_botshad.png create mode 100644 data/themes/dia_grad.png create mode 100644 data/themes/dia_topshad.png create mode 100644 data/themes/down.png create mode 100644 data/themes/emo-angry-shout.png create mode 100644 data/themes/emo-angry.png create mode 100644 data/themes/emo-crazy-laugh.png create mode 100644 data/themes/emo-evil-laugh.png create mode 100644 data/themes/emo-evil.png create mode 100644 data/themes/emo-goggle-smile.png create mode 100644 data/themes/emo-grumpy-smile.png create mode 100644 data/themes/emo-grumpy.png create mode 100644 data/themes/emo-guilty-smile.png create mode 100644 data/themes/emo-guilty.png create mode 100644 data/themes/emo-haha.png create mode 100644 data/themes/emo-half-smile.png create mode 100644 data/themes/emo-happy-panting.png create mode 100644 data/themes/emo-happy.png create mode 100644 data/themes/emo-indifferent.png create mode 100644 data/themes/emo-kiss.png create mode 100644 data/themes/emo-knowing-grin.png create mode 100644 data/themes/emo-laugh.png create mode 100644 data/themes/emo-little-bit-sorry.png create mode 100644 data/themes/emo-love-lots.png create mode 100644 data/themes/emo-love.png create mode 100644 data/themes/emo-minimal-smile.png create mode 100644 data/themes/emo-not-happy.png create mode 100644 data/themes/emo-not-impressed.png create mode 100644 data/themes/emo-omg.png create mode 100644 data/themes/emo-opensmile.png create mode 100644 data/themes/emo-smile.png create mode 100644 data/themes/emo-sorry.png create mode 100644 data/themes/emo-squint-laugh.png create mode 100644 data/themes/emo-surprised.png create mode 100644 data/themes/emo-suspicious.png create mode 100644 data/themes/emo-tongue-dangling.png create mode 100644 data/themes/emo-tongue-poke.png create mode 100644 data/themes/emo-uh.png create mode 100644 data/themes/emo-unhappy.png create mode 100644 data/themes/emo-very-sorry.png create mode 100644 data/themes/emo-what.png create mode 100644 data/themes/emo-wink.png create mode 100644 data/themes/emo-worried.png create mode 100644 data/themes/emo-wtf.png create mode 100644 data/themes/flip.xcf.gz create mode 100644 data/themes/flip_0b.png create mode 100644 data/themes/flip_0t.png create mode 100644 data/themes/flip_1b.png create mode 100644 data/themes/flip_1t.png create mode 100644 data/themes/flip_2b.png create mode 100644 data/themes/flip_2t.png create mode 100644 data/themes/flip_3b.png create mode 100644 data/themes/flip_3t.png create mode 100644 data/themes/flip_4b.png create mode 100644 data/themes/flip_4t.png create mode 100644 data/themes/flip_5b.png create mode 100644 data/themes/flip_5t.png create mode 100644 data/themes/flip_6b.png create mode 100644 data/themes/flip_6t.png create mode 100644 data/themes/flip_7b.png create mode 100644 data/themes/flip_7t.png create mode 100644 data/themes/flip_8b.png create mode 100644 data/themes/flip_8t.png create mode 100644 data/themes/flip_9b.png create mode 100644 data/themes/flip_9t.png create mode 100644 data/themes/flip_amb.png create mode 100644 data/themes/flip_amt.png create mode 100644 data/themes/flip_b.png create mode 100644 data/themes/flip_base.png create mode 100644 data/themes/flip_base_shad.png create mode 100644 data/themes/flip_pmb.png create mode 100644 data/themes/flip_pmt.png create mode 100644 data/themes/flip_shad.png create mode 100644 data/themes/flip_t.png create mode 100644 data/themes/frame_1.png create mode 100644 data/themes/frame_2.png create mode 100644 data/themes/group_index.png create mode 100644 data/themes/head.png create mode 100644 data/themes/hoversel_entry_bg.png create mode 100644 data/themes/icon_apps.png create mode 100644 data/themes/icon_arrow_down.png create mode 100644 data/themes/icon_arrow_down_left.png create mode 100644 data/themes/icon_arrow_down_right.png create mode 100644 data/themes/icon_arrow_left.png create mode 100644 data/themes/icon_arrow_right.png create mode 100644 data/themes/icon_arrow_up.png create mode 100644 data/themes/icon_arrow_up_left.png create mode 100644 data/themes/icon_arrow_up_right.png create mode 100644 data/themes/icon_chat.png create mode 100644 data/themes/icon_clock.png create mode 100644 data/themes/icon_close.png create mode 100644 data/themes/icon_delete.png create mode 100644 data/themes/icon_edit.png create mode 100644 data/themes/icon_file.png create mode 100644 data/themes/icon_folder.png create mode 100644 data/themes/icon_home.png create mode 100644 data/themes/icon_left_arrow.png create mode 100644 data/themes/icon_refresh.png create mode 100644 data/themes/icon_right_arrow.png create mode 100644 data/themes/ilist_1.png create mode 100644 data/themes/ilist_1_h.png create mode 100644 data/themes/ilist_2.png create mode 100644 data/themes/ilist_2_h.png create mode 100644 data/themes/ilist_item_shadow.png create mode 100644 data/themes/ilist_item_shadow_h.png create mode 100644 data/themes/leftright.png create mode 100644 data/themes/map_item.png create mode 100644 data/themes/map_item_1.png create mode 100644 data/themes/map_item_2.png create mode 100644 data/themes/outdent-bottom.png create mode 100644 data/themes/outdent-top.png create mode 100644 data/themes/radio.png create mode 100644 data/themes/radio2.png create mode 100644 data/themes/radio_base.png create mode 100644 data/themes/sb_runnerh.png create mode 100644 data/themes/sb_runnerv.png create mode 100644 data/themes/separator_h.png create mode 100644 data/themes/separator_v.png create mode 100644 data/themes/shad_circ.png create mode 100644 data/themes/shadow.png create mode 100644 data/themes/shelf_inset.png create mode 100644 data/themes/sl_bg.png create mode 100644 data/themes/sl_bg_over.png create mode 100644 data/themes/sl_bt2_0_0.png create mode 100644 data/themes/sl_bt2_0_1.png create mode 100644 data/themes/sl_bt2_0_2.png create mode 100644 data/themes/sl_bt2_1.png create mode 100644 data/themes/sl_bt2_2.png create mode 100644 data/themes/sl_bt_0.png create mode 100644 data/themes/sl_bt_1.png create mode 100644 data/themes/sl_bt_2.png create mode 100644 data/themes/sl_bt_3.png create mode 100644 data/themes/sl_units.png create mode 100644 data/themes/slv_bg.png create mode 100644 data/themes/slv_bg_over.png create mode 100644 data/themes/slv_units.png create mode 100644 data/themes/sp_bt_l.png create mode 100644 data/themes/sp_bt_r.png create mode 100644 data/themes/thumb_shadow.png create mode 100644 data/themes/tog_base.png create mode 100644 data/themes/tog_dis_base.png create mode 100644 data/themes/toolbar_sel.png create mode 100644 data/themes/toolbar_separator_v.png create mode 100644 data/themes/tooltip-base.png create mode 100644 data/themes/tooltip-corner-bottom-left-tip.png create mode 100644 data/themes/tooltip-corner-bottom-right-tip.png create mode 100644 data/themes/tooltip-corner-top-left-tip.png create mode 100644 data/themes/tooltip-corner-top-right-tip.png create mode 100644 data/themes/tooltip-edge-bottom-tip.png create mode 100644 data/themes/tooltip-edge-left-tip.png create mode 100644 data/themes/tooltip-edge-right-tip.png create mode 100644 data/themes/tooltip-edge-top-tip.png create mode 100644 data/themes/up.png create mode 100644 data/themes/updown.png create mode 100644 doc/.cvsignore create mode 100644 doc/Doxyfile create mode 100644 doc/Makefile.am create mode 100644 doc/e.css create mode 100644 doc/elementary.dox.in create mode 100644 doc/foot.html create mode 100644 doc/head.html create mode 100644 doc/img/edoxy.css create mode 100644 doc/img/elementary.png create mode 100644 doc/img/foot_bg.png create mode 100644 doc/img/head_bg.png create mode 100644 doc/img/header_menu_background.png create mode 100644 doc/img/header_menu_background_last.png create mode 100644 doc/img/header_menu_current_background.png create mode 100644 doc/img/header_menu_unselected_background.png create mode 100644 doc/img/logo.png create mode 100644 elementary.pc.in create mode 100644 elementary.spec.in create mode 100644 m4/ac_attribute.m4 create mode 100644 m4/efl_binary.m4 create mode 100644 m4/efl_doxygen.m4 create mode 100644 m4/efl_threads.m4 create mode 100644 src/.cvsignore create mode 100644 src/Makefile.am create mode 100644 src/bin/.cvsignore create mode 100644 src/bin/Makefile.am create mode 100644 src/bin/config.c create mode 100644 src/bin/quicklaunch.c create mode 100644 src/bin/run.c create mode 100644 src/bin/test.c create mode 100644 src/bin/test_actionslider.c create mode 100644 src/bin/test_anchorblock.c create mode 100644 src/bin/test_anchorview.c create mode 100644 src/bin/test_anim.c create mode 100644 src/bin/test_bg.c create mode 100644 src/bin/test_box.c create mode 100644 src/bin/test_bubble.c create mode 100644 src/bin/test_button.c create mode 100644 src/bin/test_calendar.c create mode 100644 src/bin/test_check.c create mode 100644 src/bin/test_clock.c create mode 100644 src/bin/test_colorselector.c create mode 100644 src/bin/test_conform.c create mode 100644 src/bin/test_ctxpopup.c create mode 100644 src/bin/test_cursor.c create mode 100644 src/bin/test_diskselector.c create mode 100644 src/bin/test_entry.c create mode 100644 src/bin/test_fileselector.c create mode 100644 src/bin/test_fileselector_button.c create mode 100644 src/bin/test_fileselector_entry.c create mode 100644 src/bin/test_flip.c create mode 100644 src/bin/test_flipselector.c create mode 100644 src/bin/test_floating.c create mode 100644 src/bin/test_focus.c create mode 100644 src/bin/test_focus2.c create mode 100644 src/bin/test_gengrid.c create mode 100644 src/bin/test_genlist.c create mode 100644 src/bin/test_hover.c create mode 100644 src/bin/test_hoversel.c create mode 100644 src/bin/test_icon.c create mode 100644 src/bin/test_icon_desktops.c create mode 100644 src/bin/test_index.c create mode 100644 src/bin/test_inwin.c create mode 100644 src/bin/test_label.c create mode 100644 src/bin/test_launcher.c create mode 100644 src/bin/test_layout.c create mode 100644 src/bin/test_list.c create mode 100644 src/bin/test_map.c create mode 100644 src/bin/test_menu.c create mode 100644 src/bin/test_multi.c create mode 100644 src/bin/test_notify.c create mode 100644 src/bin/test_pager.c create mode 100644 src/bin/test_panel.c create mode 100644 src/bin/test_panes.c create mode 100644 src/bin/test_photo.c create mode 100644 src/bin/test_photocam.c create mode 100644 src/bin/test_progressbar.c create mode 100644 src/bin/test_radio.c create mode 100644 src/bin/test_scaling.c create mode 100644 src/bin/test_scroller.c create mode 100644 src/bin/test_separator.c create mode 100644 src/bin/test_slider.c create mode 100644 src/bin/test_slideshow.c create mode 100644 src/bin/test_spinner.c create mode 100644 src/bin/test_store.c create mode 100644 src/bin/test_table.c create mode 100644 src/bin/test_thumb.c create mode 100644 src/bin/test_toggle.c create mode 100644 src/bin/test_toolbar.c create mode 100644 src/bin/test_tooltip.c create mode 100644 src/bin/test_transit.c create mode 100644 src/bin/test_weather.c create mode 100644 src/bin/test_win_state.c create mode 100644 src/edje_externals/Makefile.am create mode 100644 src/edje_externals/elm.c create mode 100644 src/edje_externals/elm_anchorblock.c create mode 100644 src/edje_externals/elm_anchorview.c create mode 100644 src/edje_externals/elm_bubble.c create mode 100644 src/edje_externals/elm_button.c create mode 100644 src/edje_externals/elm_check.c create mode 100644 src/edje_externals/elm_clock.c create mode 100644 src/edje_externals/elm_fileselector.c create mode 100644 src/edje_externals/elm_fileselector_button.c create mode 100644 src/edje_externals/elm_fileselector_entry.c create mode 100644 src/edje_externals/elm_genlist.c create mode 100644 src/edje_externals/elm_hoversel.c create mode 100644 src/edje_externals/elm_icon.c create mode 100644 src/edje_externals/elm_label.c create mode 100644 src/edje_externals/elm_list.c create mode 100644 src/edje_externals/elm_map.c create mode 100644 src/edje_externals/elm_notify.c create mode 100644 src/edje_externals/elm_panes.c create mode 100644 src/edje_externals/elm_photocam.c create mode 100644 src/edje_externals/elm_progressbar.c create mode 100644 src/edje_externals/elm_radio.c create mode 100644 src/edje_externals/elm_scrolled_entry.c create mode 100644 src/edje_externals/elm_scroller.c create mode 100644 src/edje_externals/elm_slider.c create mode 100644 src/edje_externals/elm_slideshow.c create mode 100644 src/edje_externals/elm_spinner.c create mode 100644 src/edje_externals/elm_thumb.c create mode 100644 src/edje_externals/elm_toggle.c create mode 100644 src/edje_externals/elm_toolbar.c create mode 100644 src/edje_externals/modules.inc create mode 100644 src/edje_externals/private.h create mode 100644 src/lib/Elementary.h.in create mode 100644 src/lib/Elementary_Cursor.h create mode 100644 src/lib/Makefile.am create mode 100644 src/lib/elc_anchorblock.c create mode 100644 src/lib/elc_anchorview.c create mode 100644 src/lib/elc_ctxpopup.c create mode 100644 src/lib/elc_fileselector.c create mode 100644 src/lib/elc_fileselector_button.c create mode 100644 src/lib/elc_fileselector_entry.c create mode 100644 src/lib/elc_hoversel.c create mode 100644 src/lib/elc_scrolled_entry.c create mode 100644 src/lib/elm_actionslider.c create mode 100644 src/lib/elm_animator.c create mode 100644 src/lib/elm_bg.c create mode 100644 src/lib/elm_box.c create mode 100644 src/lib/elm_bubble.c create mode 100644 src/lib/elm_button.c create mode 100644 src/lib/elm_calendar.c create mode 100644 src/lib/elm_check.c create mode 100644 src/lib/elm_clock.c create mode 100644 src/lib/elm_cnp_helper.c create mode 100644 src/lib/elm_colorselector.c create mode 100644 src/lib/elm_config.c create mode 100644 src/lib/elm_conform.c create mode 100644 src/lib/elm_diskselector.c create mode 100644 src/lib/elm_entry.c create mode 100644 src/lib/elm_flip.c create mode 100644 src/lib/elm_flipselector.c create mode 100644 src/lib/elm_font.c create mode 100644 src/lib/elm_frame.c create mode 100644 src/lib/elm_gengrid.c create mode 100644 src/lib/elm_genlist.c create mode 100644 src/lib/elm_hover.c create mode 100644 src/lib/elm_icon.c create mode 100644 src/lib/elm_image.c create mode 100644 src/lib/elm_index.c create mode 100644 src/lib/elm_label.c create mode 100644 src/lib/elm_layout.c create mode 100644 src/lib/elm_list.c create mode 100644 src/lib/elm_main.c create mode 100644 src/lib/elm_map.c create mode 100644 src/lib/elm_mapbuf.c create mode 100644 src/lib/elm_menu.c create mode 100644 src/lib/elm_module.c create mode 100644 src/lib/elm_notify.c create mode 100644 src/lib/elm_pager.c create mode 100644 src/lib/elm_panel.c create mode 100644 src/lib/elm_panes.c create mode 100644 src/lib/elm_photo.c create mode 100644 src/lib/elm_photocam.c create mode 100644 src/lib/elm_priv.h create mode 100644 src/lib/elm_progressbar.c create mode 100644 src/lib/elm_radio.c create mode 100644 src/lib/elm_scroller.c create mode 100644 src/lib/elm_separator.c create mode 100644 src/lib/elm_slider.c create mode 100644 src/lib/elm_slideshow.c create mode 100644 src/lib/elm_spinner.c create mode 100644 src/lib/elm_store.c create mode 100644 src/lib/elm_table.c create mode 100644 src/lib/elm_theme.c create mode 100644 src/lib/elm_thumb.c create mode 100644 src/lib/elm_toggle.c create mode 100644 src/lib/elm_toolbar.c create mode 100644 src/lib/elm_transit.c create mode 100644 src/lib/elm_util.c create mode 100644 src/lib/elm_widget.c create mode 100644 src/lib/elm_widget.h create mode 100644 src/lib/elm_win.c create mode 100644 src/lib/els_box.c create mode 100644 src/lib/els_box.h create mode 100644 src/lib/els_cursor.c create mode 100644 src/lib/els_icon.c create mode 100644 src/lib/els_icon.h create mode 100644 src/lib/els_pan.c create mode 100644 src/lib/els_pan.h create mode 100644 src/lib/els_scroller.c create mode 100644 src/lib/els_scroller.h create mode 100644 src/lib/els_tooltip.c create mode 100644 src/modules/Makefile.am create mode 100644 src/modules/test_entry/Makefile.am create mode 100644 src/modules/test_entry/mod.c create mode 100644 src/modules/test_map/Makefile.am create mode 100644 src/modules/test_map/mod.c create mode 100755 tests/test_decl.sh create mode 100755 tests/test_eapi.sh create mode 100755 tests/test_getter.sh create mode 100755 tests/test_setter.sh create mode 100644 tests/test_setter_blacklist.txt diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..dcdce19 --- /dev/null +++ b/.gitignore @@ -0,0 +1,43 @@ +*.lo +*.o +*.la +.libs +.deps +.*.swp +*.pc +Makefile +Makefile.in +*.so +*.edj +elementary_config +elementary_quicklaunch +elementary_run +elementary_test +elementary_testql +/aclocal.m4 +/autom4te.cache/ +/config.guess +/config.log +/config.status +/config.sub +/configure +/depcomp +/elementary.spec +/elementary_config.h +/elementary_config.h.in +/install-sh +/libtool +/ltmain.sh +/missing +/stamp-h1 +core +cscope.out +doc/elementary.dox +elementary.spec +m4/libtool.m4 +m4/ltoptions.m4 +m4/ltsugar.m4 +m4/ltversion.m4 +m4/lt~obsolete.m4 +src/lib/Elementary.h +tags diff --git a/AUTHORS b/AUTHORS new file mode 100644 index 0000000..52c3367 --- /dev/null +++ b/AUTHORS @@ -0,0 +1,36 @@ +The Rasterman (Carsten Haitzler) +Gustavo Sverzut Barbieri +Cedric Bail +Vincent Torri +Daniel Kolesa +Jaime Thomas +Swisscom - http://www.swisscom.ch/ +Christopher Michael +Marco Trevisan (Treviño) +Michael Bouchaud +Jonathan Atton (Watchwolf) +Brian Wang +Mike Blumenkrantz (zmike) +Samsung Electronics +Samsung SAIT +Brett Nash +Bruno Dilly +Rafael Fonseca +Hermet (Chuneon Park) +Woohyun Jung +Jaehwan Kim +Wonguk Jeong +Leandro A. F. Pereira +Helen Fornazier +Gustavo Lima Chaves +Fabiano Fidêncio +Tiago Falcão +Otavio Pontes +Viktor Kojouharov +Daniel Juyung Seo (SeoZ) +Sangho Park +Rajeev Ranjan (Rajeev) +Seunggyun Kim +Sohyun Kim +Jihoon Kim +Jeonghyun Yun (arosis) diff --git a/COPYING b/COPYING new file mode 100644 index 0000000..ba77514 --- /dev/null +++ b/COPYING @@ -0,0 +1,491 @@ +Copyright notice for Elementary: + +Copyright (C) 2008-2010 Carsten Haitzler and various contributors (see AUTHORS) + +This library is free software; you can redistribute it and/or modify it +under the terms of the GNU Lesser General Public License as published by the +Free Software Foundation; either version 2.1 of the License. + +This library is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS +FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more +details. + +Below is a copy of the GNU Lesser General Public License that is distributed +along with this library. If you do not have a copy below, write to the Free +Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA +02110-1301 USA + + GNU LESSER GENERAL PUBLIC LICENSE + Version 2.1, February 1999 + + Copyright (C) 1991, 1999 Free Software Foundation, Inc. + 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + +[This is the first released version of the Lesser GPL. It also counts + as the successor of the GNU Library Public License, version 2, hence + the version number 2.1.] + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +Licenses are intended to guarantee your freedom to share and change +free software--to make sure the software is free for all its users. + + This license, the Lesser General Public License, applies to some +specially designated software packages--typically libraries--of the +Free Software Foundation and other authors who decide to use it. You +can use it too, but we suggest you first think carefully about whether +this license or the ordinary General Public License is the better +strategy to use in any particular case, based on the explanations below. + + When we speak of free software, we are referring to freedom of use, +not price. Our General Public Licenses are designed to make sure that +you have the freedom to distribute copies of free software (and charge +for this service if you wish); that you receive source code or can get +it if you want it; that you can change the software and use pieces of +it in new free programs; and that you are informed that you can do +these things. + + To protect your rights, we need to make restrictions that forbid +distributors to deny you these rights or to ask you to surrender these +rights. These restrictions translate to certain responsibilities for +you if you distribute copies of the library or if you modify it. + + For example, if you distribute copies of the library, whether gratis +or for a fee, you must give the recipients all the rights that we gave +you. You must make sure that they, too, receive or can get the source +code. If you link other code with the library, you must provide +complete object files to the recipients, so that they can relink them +with the library after making changes to the library and recompiling +it. And you must show them these terms so they know their rights. + + We protect your rights with a two-step method: (1) we copyright the +library, and (2) we offer you this license, which gives you legal +permission to copy, distribute and/or modify the library. + + To protect each distributor, we want to make it very clear that +there is no warranty for the free library. Also, if the library is +modified by someone else and passed on, the recipients should know +that what they have is not the original version, so that the original +author's reputation will not be affected by problems that might be +introduced by others. + + Finally, software patents pose a constant threat to the existence of +any free program. We wish to make sure that a company cannot +effectively restrict the users of a free program by obtaining a +restrictive license from a patent holder. Therefore, we insist that +any patent license obtained for a version of the library must be +consistent with the full freedom of use specified in this license. + + Most GNU software, including some libraries, is covered by the +ordinary GNU General Public License. This license, the GNU Lesser +General Public License, applies to certain designated libraries, and +is quite different from the ordinary General Public License. We use +this license for certain libraries in order to permit linking those +libraries into non-free programs. + + When a program is linked with a library, whether statically or using +a shared library, the combination of the two is legally speaking a +combined work, a derivative of the original library. The ordinary +General Public License therefore permits such linking only if the +entire combination fits its criteria of freedom. The Lesser General +Public License permits more lax criteria for linking other code with +the library. + + We call this license the "Lesser" General Public License because it +does Less to protect the user's freedom than the ordinary General +Public License. It also provides other free software developers Less +of an advantage over competing non-free programs. These disadvantages +are the reason we use the ordinary General Public License for many +libraries. However, the Lesser license provides advantages in certain +special circumstances. + + For example, on rare occasions, there may be a special need to +encourage the widest possible use of a certain library, so that it becomes +a de-facto standard. To achieve this, non-free programs must be +allowed to use the library. A more frequent case is that a free +library does the same job as widely used non-free libraries. In this +case, there is little to gain by limiting the free library to free +software only, so we use the Lesser General Public License. + + In other cases, permission to use a particular library in non-free +programs enables a greater number of people to use a large body of +free software. For example, permission to use the GNU C Library in +non-free programs enables many more people to use the whole GNU +operating system, as well as its variant, the GNU/Linux operating +system. + + Although the Lesser General Public License is Less protective of the +users' freedom, it does ensure that the user of a program that is +linked with the Library has the freedom and the wherewithal to run +that program using a modified version of the Library. + + The precise terms and conditions for copying, distribution and +modification follow. Pay close attention to the difference between a +"work based on the library" and a "work that uses the library". The +former contains code derived from the library, whereas the latter must +be combined with the library in order to run. + + GNU LESSER GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License Agreement applies to any software library or other +program which contains a notice placed by the copyright holder or +other authorized party saying it may be distributed under the terms of +this Lesser General Public License (also called "this License"). +Each licensee is addressed as "you". + + A "library" means a collection of software functions and/or data +prepared so as to be conveniently linked with application programs +(which use some of those functions and data) to form executables. + + The "Library", below, refers to any such software library or work +which has been distributed under these terms. A "work based on the +Library" means either the Library or any derivative work under +copyright law: that is to say, a work containing the Library or a +portion of it, either verbatim or with modifications and/or translated +straightforwardly into another language. (Hereinafter, translation is +included without limitation in the term "modification".) + + "Source code" for a work means the preferred form of the work for +making modifications to it. For a library, complete source code means +all the source code for all modules it contains, plus any associated +interface definition files, plus the scripts used to control compilation +and installation of the library. + + Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running a program using the Library is not restricted, and output from +such a program is covered only if its contents constitute a work based +on the Library (independent of the use of the Library in a tool for +writing it). Whether that is true depends on what the Library does +and what the program that uses the Library does. + + 1. You may copy and distribute verbatim copies of the Library's +complete source code as you receive it, in any medium, provided that +you conspicuously and appropriately publish on each copy an +appropriate copyright notice and disclaimer of warranty; keep intact +all the notices that refer to this License and to the absence of any +warranty; and distribute a copy of this License along with the +Library. + + You may charge a fee for the physical act of transferring a copy, +and you may at your option offer warranty protection in exchange for a +fee. + + 2. You may modify your copy or copies of the Library or any portion +of it, thus forming a work based on the Library, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) The modified work must itself be a software library. + + b) You must cause the files modified to carry prominent notices + stating that you changed the files and the date of any change. + + c) You must cause the whole of the work to be licensed at no + charge to all third parties under the terms of this License. + + d) If a facility in the modified Library refers to a function or a + table of data to be supplied by an application program that uses + the facility, other than as an argument passed when the facility + is invoked, then you must make a good faith effort to ensure that, + in the event an application does not supply such function or + table, the facility still operates, and performs whatever part of + its purpose remains meaningful. + + (For example, a function in a library to compute square roots has + a purpose that is entirely well-defined independent of the + application. Therefore, Subsection 2d requires that any + application-supplied function or table used by this function must + be optional: if the application does not supply it, the square + root function must still compute square roots.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Library, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Library, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote +it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Library. + +In addition, mere aggregation of another work not based on the Library +with the Library (or with a work based on the Library) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + +Linking this library statically or dynamically with other modules is +making a combined work based on this library. Thus, the terms and +conditions of the GNU General Public License cover the whole combination. + +As a special exception, the copyright holders of this library give you +permission to link this library with independent modules to produce an +executable, regardless of the license terms of these independent modules, +and to copy and distribute the resulting executable under terms of your +choice, provided that you also meet, for each linked independent module, +the terms and conditions of the license of that module. An independent +module is a module which is not derived from or based on this library. +If you modify this library, you may extend this exception to your version +of the library, but you are not obliged to do so. If you do not wish to +do so, delete this exception statement from your version. + + 3. You may opt to apply the terms of the ordinary GNU General Public +License instead of this License to a given copy of the Library. To do +this, you must alter all the notices that refer to this License, so +that they refer to the ordinary GNU General Public License, version 2, +instead of to this License. (If a newer version than version 2 of the +ordinary GNU General Public License has appeared, then you can specify +that version instead if you wish.) Do not make any other change in +these notices. + + Once this change is made in a given copy, it is irreversible for +that copy, so the ordinary GNU General Public License applies to all +subsequent copies and derivative works made from that copy. + + This option is useful when you wish to copy part of the code of +the Library into a program that is not a library. + + 4. You may copy and distribute the Library (or a portion or +derivative of it, under Section 2) in object code or executable form +under the terms of Sections 1 and 2 above provided that you accompany +it with the complete corresponding machine-readable source code, which +must be distributed under the terms of Sections 1 and 2 above on a +medium customarily used for software interchange. + + If distribution of object code is made by offering access to copy +from a designated place, then offering equivalent access to copy the +source code from the same place satisfies the requirement to +distribute the source code, even though third parties are not +compelled to copy the source along with the object code. + + 5. A program that contains no derivative of any portion of the +Library, but is designed to work with the Library by being compiled or +linked with it, is called a "work that uses the Library". Such a +work, in isolation, is not a derivative work of the Library, and +therefore falls outside the scope of this License. + + However, linking a "work that uses the Library" with the Library +creates an executable that is a derivative of the Library (because it +contains portions of the Library), rather than a "work that uses the +library". The executable is therefore covered by this License. +Section 6 states terms for distribution of such executables. + + When a "work that uses the Library" uses material from a header file +that is part of the Library, the object code for the work may be a +derivative work of the Library even though the source code is not. +Whether this is true is especially significant if the work can be +linked without the Library, or if the work is itself a library. The +threshold for this to be true is not precisely defined by law. + + If such an object file uses only numerical parameters, data +structure layouts and accessors, and small macros and small inline +functions (ten lines or less in length), then the use of the object +file is unrestricted, regardless of whether it is legally a derivative +work. (Executables containing this object code plus portions of the +Library will still fall under Section 6.) + + Otherwise, if the work is a derivative of the Library, you may +distribute the object code for the work under the terms of Section 6. +Any executables containing that work also fall under Section 6, +whether or not they are linked directly with the Library itself. + + 6. As an exception to the Sections above, you may also combine or +link a "work that uses the Library" with the Library to produce a +work containing portions of the Library, and distribute that work +under terms of your choice, provided that the terms permit +modification of the work for the customer's own use and reverse +engineering for debugging such modifications. + + You must give prominent notice with each copy of the work that the +Library is used in it and that the Library and its use are covered by +this License. You must supply a copy of this License. If the work +during execution displays copyright notices, you must include the +copyright notice for the Library among them, as well as a reference +directing the user to the copy of this License. Also, you must do one +of these things: + + a) Accompany the work with the complete corresponding + machine-readable source code for the Library including whatever + changes were used in the work (which must be distributed under + Sections 1 and 2 above); and, if the work is an executable linked + with the Library, with the complete machine-readable "work that + uses the Library", as object code and/or source code, so that the + user can modify the Library and then relink to produce a modified + executable containing the modified Library. (It is understood + that the user who changes the contents of definitions files in the + Library will not necessarily be able to recompile the application + to use the modified definitions.) + + b) Use a suitable shared library mechanism for linking with the + Library. A suitable mechanism is one that (1) uses at run time a + copy of the library already present on the user's computer system, + rather than copying library functions into the executable, and (2) + will operate properly with a modified version of the library, if + the user installs one, as long as the modified version is + interface-compatible with the version that the work was made with. + + c) Accompany the work with a written offer, valid for at + least three years, to give the same user the materials + specified in Subsection 6a, above, for a charge no more + than the cost of performing this distribution. + + d) If distribution of the work is made by offering access to copy + from a designated place, offer equivalent access to copy the above + specified materials from the same place. + + e) Verify that the user has already received a copy of these + materials or that you have already sent this user a copy. + + For an executable, the required form of the "work that uses the +Library" must include any data and utility programs needed for +reproducing the executable from it. However, as a special exception, +the materials to be distributed need not include anything that is +normally distributed (in either source or binary form) with the major +components (compiler, kernel, and so on) of the operating system on +which the executable runs, unless that component itself accompanies +the executable. + + It may happen that this requirement contradicts the license +restrictions of other proprietary libraries that do not normally +accompany the operating system. Such a contradiction means you cannot +use both them and the Library together in an executable that you +distribute. + + 7. You may place library facilities that are a work based on the +Library side-by-side in a single library together with other library +facilities not covered by this License, and distribute such a combined +library, provided that the separate distribution of the work based on +the Library and of the other library facilities is otherwise +permitted, and provided that you do these two things: + + a) Accompany the combined library with a copy of the same work + based on the Library, uncombined with any other library + facilities. This must be distributed under the terms of the + Sections above. + + b) Give prominent notice with the combined library of the fact + that part of it is a work based on the Library, and explaining + where to find the accompanying uncombined form of the same work. + + 8. You may not copy, modify, sublicense, link with, or distribute +the Library except as expressly provided under this License. Any +attempt otherwise to copy, modify, sublicense, link with, or +distribute the Library is void, and will automatically terminate your +rights under this License. However, parties who have received copies, +or rights, from you under this License will not have their licenses +terminated so long as such parties remain in full compliance. + + 9. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Library or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Library (or any work based on the +Library), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Library or works based on it. + + 10. Each time you redistribute the Library (or any work based on the +Library), the recipient automatically receives a license from the +original licensor to copy, distribute, link with or modify the Library +subject to these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties with +this License. + + 11. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Library at all. For example, if a patent +license would not permit royalty-free redistribution of the Library by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Library. + +If any portion of this section is held invalid or unenforceable under any +particular circumstance, the balance of the section is intended to apply, +and the section as a whole is intended to apply in other circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 12. If the distribution and/or use of the Library is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Library under this License may add +an explicit geographical distribution limitation excluding those countries, +so that distribution is permitted only in or among countries not thus +excluded. In such case, this License incorporates the limitation as if +written in the body of this License. + + 13. The Free Software Foundation may publish revised and/or new +versions of the Lesser General Public License from time to time. +Such new versions will be similar in spirit to the present version, +but may differ in detail to address new problems or concerns. + +Each version is given a distinguishing version number. If the Library +specifies a version number of this License which applies to it and +"any later version", you have the option of following the terms and +conditions either of that version or of any later version published by +the Free Software Foundation. If the Library does not specify a +license version number, you may choose any version ever published by +the Free Software Foundation. + + 14. If you wish to incorporate parts of the Library into other free +programs whose distribution conditions are incompatible with these, +write to the author to ask for permission. For software which is +copyrighted by the Free Software Foundation, write to the Free +Software Foundation; we sometimes make exceptions for this. Our +decision will be guided by the two goals of preserving the free status +of all derivatives of our free software and of promoting the sharing +and reuse of software generally. + + NO WARRANTY + + 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO +WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. +EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR +OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY +KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR +PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE +LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME +THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. + + 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN +WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY +AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU +FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR +CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE +LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING +RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A +FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF +SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH +DAMAGES. + + END OF TERMS AND CONDITIONS diff --git a/ChangeLog b/ChangeLog new file mode 100644 index 0000000..e69de29 diff --git a/INSTALL b/INSTALL new file mode 100644 index 0000000..7c9d317 --- /dev/null +++ b/INSTALL @@ -0,0 +1,14 @@ +COMPILING and INSTALLING: + +If you got a official release tar archive do: + ./configure + +( otherwise if you got this from enlightenment cvs do: ./autogen.sh ) + +Then to compile: + make + +To install (run this as root, or the user who handles installs): + make install + +NOTE: You MUST make install Elementary for it to run properly. diff --git a/Makefile.am b/Makefile.am new file mode 100644 index 0000000..f41c83e --- /dev/null +++ b/Makefile.am @@ -0,0 +1,45 @@ +SUBDIRS = src data config doc + +ACLOCAL_AMFLAGS = -I m4 + +MAINTAINERCLEANFILES = \ +Makefile.in \ +aclocal.m4 \ +config.guess \ +elementary_config.h.in \ +config.sub \ +configure \ +depcomp \ +install-sh \ +ltmain.sh \ +missing \ +$(PACKAGE_TARNAME)-$(PACKAGE_VERSION).tar.gz \ +$(PACKAGE_TARNAME)-$(PACKAGE_VERSION).tar.bz2 \ +$(PACKAGE_TARNAME)-$(PACKAGE_VERSION)-doc.tar.bz2 \ +m4/libtool.m4 \ +m4/lt~obsolete.m4 \ +m4/ltoptions.m4 \ +m4/ltsugar.m4 \ +m4/ltversion.m4 + + +EXTRA_DIST = \ +README \ +AUTHORS \ +COPYING \ +autogen.sh \ +elementary.pc.in \ +elementary.spec \ +elementary.spec.in \ +m4/ac_attribute.m4 \ +m4/efl_binary.m4 \ +m4/efl_doxygen.m4 + +pkgconfigdir = $(libdir)/pkgconfig +pkgconfig_DATA = elementary.pc + +.PHONY: doc + +doc: + @echo "entering doc/" + $(MAKE) -C doc doc diff --git a/NEWS b/NEWS new file mode 100644 index 0000000..e69de29 diff --git a/README b/README new file mode 100644 index 0000000..3de8538 --- /dev/null +++ b/README @@ -0,0 +1,3 @@ +Elementary - a basic widget set that is easy to use based on EFL for mobile +touch-screen devices. + diff --git a/autogen.sh b/autogen.sh new file mode 100755 index 0000000..995ff2f --- /dev/null +++ b/autogen.sh @@ -0,0 +1,16 @@ +#!/bin/sh + +rm -rf autom4te.cache +rm -f aclocal.m4 ltmain.sh + +touch README + +echo "Running aclocal..." ; aclocal $ACLOCAL_FLAGS -I m4 || exit 1 +echo "Running autoheader..." ; autoheader || exit 1 +echo "Running autoconf..." ; autoconf || exit 1 +echo "Running libtoolize..." ; (libtoolize --copy --automake || glibtoolize --automake) || exit 1 +echo "Running automake..." ; automake --add-missing --copy --gnu || exit 1 + +if [ -z "$NOCONFIGURE" ]; then + ./configure "$@" +fi diff --git a/config/Makefile.am b/config/Makefile.am new file mode 100644 index 0000000..2fb26b1 --- /dev/null +++ b/config/Makefile.am @@ -0,0 +1,18 @@ +MAINTAINERCLEANFILES = Makefile.in +SUBDIRS = default standard illume + +EET_EET = @eet_eet@ + +EXTRA_DIST = profile.src + +filesdir = $(datadir)/elementary/config + +files_DATA = profile.cfg + +%.cfg: %.src + $(EET_EET) -i \ + $(top_builddir)/config/$@ config \ + $< 0 + +clean-local: + rm -rf *.cfg *~ diff --git a/config/default/Makefile.am b/config/default/Makefile.am new file mode 100644 index 0000000..ba2bc96 --- /dev/null +++ b/config/default/Makefile.am @@ -0,0 +1,23 @@ +MAINTAINERCLEANFILES = Makefile.in + +EET_EET = @eet_eet@ + +EXTRA_DIST = \ + profile.desktop \ + icon.png \ + base.src + +filesdir = $(datadir)/elementary/config/default +files_DATA = \ + profile.desktop \ + icon.png \ + base.cfg + +%.cfg: %.src + $(EET_EET) -e \ + $(top_builddir)/config/default/$@ config \ + $< 1 + +clean-local: + rm -rf *.cfg *~ + diff --git a/config/default/base.src b/config/default/base.src new file mode 100644 index 0000000..5bc2be3 --- /dev/null +++ b/config/default/base.src @@ -0,0 +1,37 @@ +group "Elm_Config" struct { + value "config_version" int: 65539; + value "engine" string: "software_x11"; + value "thumbscroll_enable" uchar: 1; + value "thumbscroll_threshold" int: 24; + value "thumbscroll_momentum_threshold" double: 100.0; + value "thumbscroll_friction" double: 1.0; + value "thumbscroll_bounce_friction" double: 0.5; + value "thumbscroll_bounce_enable" uchar: 1; + value "page_scroll_friction" double: 0.5; + value "bring_in_scroll_friction" double: 0.5; + value "zoom_friction" double: 0.5; + value "thumbscroll_border_friction" double: 0.5; + value "scale" double: 1.0; + value "bgpixmap" int: 0; + value "compositing" int: 1; + value "font_hinting" int: 2; + value "cache_flush_poll_interval" int: 512; + value "cache_flush_enable" uchar: 1; + value "image_cache" int: 4096; + value "font_cache" int: 512; + value "edje_cache" int: 32; + value "edje_collection_cache" int: 64; + value "finger_size" int: 40; + value "fps" double: 60.0; + value "theme" string: "default"; + value "modules" string: ""; + value "tooltip_delay" double: 1.0; + value "cursor_engine_only" uchar: 1; + value "focus_highlight_enable" uchar: 0; + value "focus_highlight_animate" uchar: 0; + value "toolbar_shrink_mode" int: 3; + value "fileselector_expand_enable" uchar: 0; + value "inwin_dialogs_enable" uchar: 1; + value "icon_size" int: 32; + value "longpress_timeout" double: 1.0; +} diff --git a/config/default/icon.png b/config/default/icon.png new file mode 100644 index 0000000000000000000000000000000000000000..9c08ee2a58b98727f32b2524ce4c3272e9b7ff7f GIT binary patch literal 9183 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 literal 0 HcmV?d00001 diff --git a/config/default/profile.desktop b/config/default/profile.desktop new file mode 100644 index 0000000..3cdfb82 --- /dev/null +++ b/config/default/profile.desktop @@ -0,0 +1,21 @@ +[Desktop Entry] +Type=Link +Name=Default +Name[cs]=Výchozí +Name[it]=Predefinito +Name[hu]=Alapértelmezett +Name[fr]=Prédéfini +Name[el]=Προκαθορισμένο +Name[eo]=Pravaloroj +Name[zh_CN]=默认 +Namr[pt]=Omissões +Icon=icon.png +Comment=Select this to begin
the initial setup again. +Comment[cs]=Vyberte pro znovuspuštění
tohoto průvodce. +Comment[it]=Selezionare questo per riprendere
la configurazione iniziale. +Comment[hu]=Válaszd ezt az alap
beállítáok megismétléséhez. +Comment[fr]=Sélectionnez ceci pour retrouver la
configuration par défaut et
reprendre le paramétrage
initial. +Comment[el]=Επέλεξε αυτό για να
ξεκινήσεις την αρχική ρύθμιση ξανά. +Comment[eo]=Elektu tion por restartigi
la pravalorizan agordon. +Comment[zh_CN]=点击这里重新进行初始化设置主题。 +Comment[pt]=Selecione isto para executar novamente a configuração inicial diff --git a/config/illume/Makefile.am b/config/illume/Makefile.am new file mode 100644 index 0000000..9aa769d --- /dev/null +++ b/config/illume/Makefile.am @@ -0,0 +1,22 @@ +MAINTAINERCLEANFILES = Makefile.in + +EET_EET = @eet_eet@ + +EXTRA_DIST = \ + profile.desktop \ + icon.png \ + base.src + +filesdir = $(datadir)/elementary/config/illume +files_DATA = \ + profile.desktop \ + icon.png \ + base.cfg + +%.cfg: %.src + $(EET_EET) -e \ + $(top_builddir)/config/illume/$@ config \ + $< 1 + +clean-local: + rm -rf *.cfg *~ diff --git a/config/illume/base.src b/config/illume/base.src new file mode 100644 index 0000000..5bc2be3 --- /dev/null +++ b/config/illume/base.src @@ -0,0 +1,37 @@ +group "Elm_Config" struct { + value "config_version" int: 65539; + value "engine" string: "software_x11"; + value "thumbscroll_enable" uchar: 1; + value "thumbscroll_threshold" int: 24; + value "thumbscroll_momentum_threshold" double: 100.0; + value "thumbscroll_friction" double: 1.0; + value "thumbscroll_bounce_friction" double: 0.5; + value "thumbscroll_bounce_enable" uchar: 1; + value "page_scroll_friction" double: 0.5; + value "bring_in_scroll_friction" double: 0.5; + value "zoom_friction" double: 0.5; + value "thumbscroll_border_friction" double: 0.5; + value "scale" double: 1.0; + value "bgpixmap" int: 0; + value "compositing" int: 1; + value "font_hinting" int: 2; + value "cache_flush_poll_interval" int: 512; + value "cache_flush_enable" uchar: 1; + value "image_cache" int: 4096; + value "font_cache" int: 512; + value "edje_cache" int: 32; + value "edje_collection_cache" int: 64; + value "finger_size" int: 40; + value "fps" double: 60.0; + value "theme" string: "default"; + value "modules" string: ""; + value "tooltip_delay" double: 1.0; + value "cursor_engine_only" uchar: 1; + value "focus_highlight_enable" uchar: 0; + value "focus_highlight_animate" uchar: 0; + value "toolbar_shrink_mode" int: 3; + value "fileselector_expand_enable" uchar: 0; + value "inwin_dialogs_enable" uchar: 1; + value "icon_size" int: 32; + value "longpress_timeout" double: 1.0; +} diff --git a/config/illume/icon.png b/config/illume/icon.png new file mode 100644 index 0000000000000000000000000000000000000000..9e0ed3dac82f0499c92c86775018cf5d0c0a5517 GIT binary patch literal 7555 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 systems like
phones and web
tablets with tiny
touchscreen displays.
Only use this if
you really have
such a device. +Comment[cs]=Illume profil pro
přenosná zařízení
jako telefony
a webové tablety
s malými dotykovými displeji.
Použijte jen pokud
opravdu máte
takové zařízení. +Comment[it]=Profilo Illume per sistemi embedded come
cellulari e webpad con piccoli display
touchscreen. Usatelo solo se
avete realmente un dispositivo simile. +Comment[hu]=Illume profil
telefonokhoz, érintőképernyőkhöz.
Csak akkor használd ezt,
ha valóban ilyen eszközöd van. +Comment[fr]=Profil Illume pour les systèmes embarqués
comme les téléphones et les tablettes
Internet pourvus d'un petit écran
tactile. À n'utiliser que si vous
disposez d'un tel matériel. +Comment[el]=Το προφίλ Illume είναι
για μικροσυσκευές όπως
κινητά τηλέφωνα ή internet
tablets με μικρές οθόνες αφής.
Επιλέξτε μόνο αν έχετε τέτοια
συσκευή. +Comment[eo]=Profilo Illume por la
enkorpigitaj sistemoj
kiel la telefonoj kaj
ttt-tabletoj kun etaj
tuŝekranoj. Nur uzu
tiun se vi vere havas
tian aparaton. +Comment[zh_CN]=为带有小型触屏的嵌入式系统如手机和上网本设计的 Illume 设置主题。 +Comment[pt]=Perfil para telemóveis e web tablets com pequenos ecrãs tácteis.
Só deve ser utilizado para dispositivos deste tipo diff --git a/config/profile.src b/config/profile.src new file mode 100644 index 0000000..331d858 --- /dev/null +++ b/config/profile.src @@ -0,0 +1 @@ +default \ No newline at end of file diff --git a/config/standard/Makefile.am b/config/standard/Makefile.am new file mode 100644 index 0000000..88cae80 --- /dev/null +++ b/config/standard/Makefile.am @@ -0,0 +1,23 @@ +MAINTAINERCLEANFILES = Makefile.in + +EET_EET = @eet_eet@ + +EXTRA_DIST = \ + profile.desktop \ + icon.png \ + base.src + +filesdir = $(datadir)/elementary/config/standard +files_DATA = \ + profile.desktop \ + icon.png \ + base.cfg + +%.cfg: %.src + $(EET_EET) -e \ + $(top_builddir)/config/standard/$@ config \ + $< 1 + +clean-local: + rm -rf *.cfg *~ + diff --git a/config/standard/base.src b/config/standard/base.src new file mode 100644 index 0000000..142e0e7 --- /dev/null +++ b/config/standard/base.src @@ -0,0 +1,37 @@ +group "Elm_Config" struct { + value "config_version" int: 65539; + value "engine" string: "software_x11"; + value "thumbscroll_enable" uchar: 0; + value "thumbscroll_threshold" int: 4; + value "thumbscroll_momentum_threshold" double: 100.0; + value "thumbscroll_friction" double: 1.0; + value "thumbscroll_bounce_friction" double: 0.5; + value "thumbscroll_bounce_enable" uchar: 0; + value "page_scroll_friction" double: 0.5; + value "bring_in_scroll_friction" double: 0.5; + value "zoom_friction" double: 0.5; + value "thumbscroll_border_friction" double: 0.5; + value "scale" double: 1.0; + value "bgpixmap" int: 0; + value "compositing" int: 1; + value "font_hinting" int: 2; + value "cache_flush_poll_interval" int: 512; + value "cache_flush_enable" uchar: 1; + value "image_cache" int: 4096; + value "font_cache" int: 512; + value "edje_cache" int: 32; + value "edje_collection_cache" int: 64; + value "finger_size" int: 5; + value "fps" double: 60.0; + value "theme" string: "default-desktop"; + value "modules" string: ""; + value "tooltip_delay" double: 1.0; + value "cursor_engine_only" uchar: 1; + value "focus_highlight_enable" uchar: 0; + value "focus_highlight_animate" uchar: 0; + value "toolbar_shrink_mode" int: 3; + value "fileselector_expand_enable" uchar: 1; + value "inwin_dialogs_enable" uchar: 0; + value "icon_size" int: 32; + value "longpress_timeout" double: 1.0; +} diff --git a/config/standard/icon.png b/config/standard/icon.png new file mode 100644 index 0000000000000000000000000000000000000000..90b57af47dd12d33c8bbf686931853865a4b1ce1 GIT binary patch literal 12068 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 racgprofile that is
universal for most
desktop and laptop
systems. Choose this
if you are not
sure what to choose. +Comment[cs]=Toto je standartní
univerzální
profil pro většinu
stolních a přenosných
počítačů. Vyberte pokud
si nejste jisti
co vybrat. +Comment[it]=Questo è il profilo standard, universale per la
maggior parte dei sistemi desktop e portatili.
Scegliete questo se non siete sicuri di cosa scegliere. +Comment[hu]=Ez az általános,
alap beállítás,
amely megfelelő a
legtöbb laptop és
asztali gép számára. +Comment[fr]=Le profil standard adapté à la quasi totalité
des systèmes de bureau et ordinateurs
portables. Choisissez ce profil si
vous êtes indécis. +Comment[el]=Αυτό είναι το κανονικό
προφίλ που είναι κοινό
για τα περισσότερα συστήματα. Επιλέξτε αυτό
αν δεν είστε σίγουροι για
την επιλογή σας. +Comment[eo]=Tio estas la kutima profilo
taŭga por preskaŭ ĉiuj
oficejaj sistemoj kaj
porteblaj sistemoj.
Elektu ĝin se vi ne certas. +Comment[zh_CN]=适用于大多数台式机和笔记本的设置主题,如果您不清楚如何选择则请使用这个。 +Comment[pt]=O perfil de configuração padrãoo utilizado para a maioria dos computadores e portáteis.
Escolha-o se não souber o que escolher diff --git a/configure.ac b/configure.ac new file mode 100644 index 0000000..086d53b --- /dev/null +++ b/configure.ac @@ -0,0 +1,542 @@ +=-------##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--## +##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--## +m4_define([v_maj], [0]) +m4_define([v_min], [7]) +m4_define([v_mic], [0]) +m4_define([v_rev], m4_esyscmd([(svnversion "${SVN_REPO_PATH:-.}" | grep -v export || echo 0) | awk -F : '{printf("%s\n", $1);}' | tr -d ' :MSP\n'])) +m4_if(v_rev, [0], [m4_define([v_rev], m4_esyscmd([git log 2> /dev/null | (grep -m1 git-svn-id || echo 0) | sed -e 's/.*@\([0-9]*\).*/\1/' | tr -d '\n']))]) +##-- When released, remove the dnl on the below line +dnl m4_undefine([v_rev]) +##-- When doing snapshots - change soname. remove dnl on below line +m4_define([relname], [ver-pre-svn-09]) +m4_define([v_rel], [-release relname]) +##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--## +m4_ifdef([v_rev], [m4_define([v_ver], [v_maj.v_min.v_mic.v_rev])], +[m4_define([v_ver], [v_maj.v_min.v_mic])]) +m4_define([lt_rev], m4_eval(v_maj + v_min)) +m4_define([lt_cur], v_mic) +m4_define([lt_age], v_min) +##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--## +##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--## + +AC_INIT([elementary], [v_ver], [enlightenment-devel@lists.sourceforge.net]) +AC_PREREQ(2.52) +AC_CONFIG_SRCDIR([configure.ac]) +AC_CONFIG_MACRO_DIR([m4]) +AC_CANONICAL_BUILD +AC_CANONICAL_HOST + +AC_CONFIG_HEADERS([elementary_config.h]) +AH_TOP([ +#ifndef EFL_CONFIG_H__ +#define EFL_CONFIG_H__ +]) +AH_BOTTOM([ +#endif /* EFL_CONFIG_H__ */ +]) + +AM_INIT_AUTOMAKE([1.6 dist-bzip2]) +m4_ifdef([AM_SILENT_RULES], [AM_SILENT_RULES([yes])]) + +AC_GNU_SOURCE + +AC_C_BIGENDIAN +AC_ISC_POSIX +AC_PROG_CC +AM_PROG_CC_STDC +AC_HEADER_STDC +AC_C_CONST +AC_C___ATTRIBUTE__ +AC_FUNC_ALLOCA + +AC_LIBTOOL_WIN32_DLL +define([AC_LIBTOOL_LANG_CXX_CONFIG], [:])dnl +define([AC_LIBTOOL_LANG_F77_CONFIG], [:])dnl +AC_PROG_LIBTOOL + +##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--## +##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--## +m4_ifdef([v_rev], , [m4_define([v_rev], [0])]) +m4_ifdef([v_rel], , [m4_define([v_rel], [])]) +AC_DEFINE_UNQUOTED(VMAJ, [v_maj], [Major version]) +AC_DEFINE_UNQUOTED(VMIN, [v_min], [Minor version]) +AC_DEFINE_UNQUOTED(VMIC, [v_mic], [Micro version]) +AC_DEFINE_UNQUOTED(VREV, [v_rev], [Revison]) +version_info="lt_rev:lt_cur:lt_age" +release_info="v_rel" +AC_SUBST(version_info) +AC_SUBST(release_info) +##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--## +##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--##--## +VMAJ=v_maj +VMIN=v_min +AC_SUBST(VMAJ) +AC_SUBST(VMIN) + +EDJE_VERSION="1.0.0" + +case "$host_os" in + mingw32ce* | cegcc*) + MODULE_ARCH="$host_os-$host_cpu" + MODULE_EDJE="$host_os-$host_cpu" + ;; + *) + MODULE_ARCH="$host_os-$host_cpu-v_maj.v_min.v_mic" + MODULE_EDJE="$host_os-$host_cpu-${EDJE_VERSION}" + ;; +esac +AC_SUBST(release_info) +AC_SUBST(MODULE_ARCH) +AC_DEFINE_UNQUOTED(MODULE_ARCH, "$MODULE_ARCH", "Module architecture") +AC_SUBST(MODULE_EDJE) +AC_DEFINE_UNQUOTED(MODULE_EDJE, "$MODULE_EDJE", "Edje module architecture") + +EFL_SHARED_EXTENSION="${shrext_cmds}" +AC_DEFINE_UNQUOTED(EFL_SHARED_EXTENSION, "${EFL_SHARED_EXTENSION}", "Shared extension") + +requirement_elm="" + +PKG_PROG_PKG_CONFIG + +# Check whether pkg-config supports Requires.private +if $PKG_CONFIG --atleast-pkgconfig-version 0.22; then + pkgconfig_requires_private="Requires.private" +else + pkgconfig_requires_private="Requires" +fi +AC_SUBST(pkgconfig_requires_private) + +lt_enable_auto_import="" +ELM_UNIX_DEF="#undef" +ELM_WIN32_DEF="#undef" +ELM_WINCE_DEF="#undef" +have_windows="no" +case "$host_os" in + mingw32ce* | cegcc*) + PKG_CHECK_MODULES([EVIL], [evil]) + AC_DEFINE(HAVE_EVIL, 1, [Set to 1 if evil package is installed.]) + lt_enable_auto_import="-Wl,--enable-auto-import" + ELM_WINCE_DEF="#define" + have_windows="yes" +dnl managed by evil + AC_DEFINE(HAVE_DLADDR) + dlopen_libs=-ldl + requirement_elm="evil" + have_socket="no" + ;; + mingw*) + PKG_CHECK_MODULES([EVIL], [evil]) + AC_DEFINE(HAVE_EVIL, 1, [Set to 1 if evil package is installed.]) + lt_enable_auto_import="-Wl,--enable-auto-import" + ELM_WIN32_DEF="#define" + have_windows="yes" +dnl managed by evil + AC_DEFINE(HAVE_DLADDR) + dlopen_libs=-ldl + requirement_elm="evil" + have_socket="no" + ;; + *solaris*) + ELM_UNIX_DEF="#define" + have_socket="yes" + AC_CHECK_LIB([socket], [connect], [], [have_socket="no"]) + ;; + darwin*) + ELM_UNIX_DEF="#define" + have_socket="yes" + AC_CHECK_HEADERS([crt_externs.h]) + AC_DEFINE([environ], [(*_NSGetEnviron())], ["apple doesn't follow POSIX in this case."]) + ;; + *) + ELM_UNIX_DEF="#define" + AC_CHECK_FUNCS(dlopen, res=yes, res=no) + if test "x$res" = "xyes"; then + AC_CHECK_FUNCS(dladdr, AC_DEFINE(HAVE_DLADDR)) + else + AC_CHECK_LIB(dl, dlopen, res=yes, res=no) + if test "x$res" = "xyes"; then + AC_CHECK_LIB(dl, dladdr, AC_DEFINE(HAVE_DLADDR)) + dlopen_libs=-ldl + else + AC_MSG_ERROR(Cannot find dlopen) + fi + fi + have_socket="yes" + ;; +esac +AM_CONDITIONAL([BUILD_RUN], [test "x$have_socket" = "xyes"]) + +have_fork="no" +want_quicklaunch="auto" +AC_ARG_ENABLE([quick-launch], + [AC_HELP_STRING([--disable-quick-launch], [disable quick-launch support, @<:@default=detect@:>@])], + [want_quicklaunch=$enableval], []) + +if test "x$want_quicklaunch" != "xno"; then + AC_CHECK_FUNCS(fork, [ + have_fork="yes" + AC_DEFINE(HAVE_FORK) + ]) +fi +AM_CONDITIONAL([BUILD_QUICKLAUNCH], [test "x$have_fork" = "xyes"]) + +AC_SUBST(dlopen_libs) +AC_SUBST(lt_enable_auto_import) +AC_SUBST(ELM_UNIX_DEF) +AC_SUBST(ELM_WIN32_DEF) +AC_SUBST(ELM_WINCE_DEF) + +AM_CONDITIONAL([ELEMENTARY_WINDOWS_BUILD], [test "x${have_windows}" = "xyes"]) + +PKG_CHECK_MODULES([ELEMENTARY], + [ + eina >= 1.0.0 + eet >= 1.4.0 + evas >= 1.0.0 + ecore >= 1.0.0 + ecore-evas >= 1.0.0 + ecore-file >= 1.0.0 + ecore-imf >= 1.0.0 + edje >= ${EDJE_VERSION} + ] +) + +requirement_elm="edje >= ${EDJE_VERSION} ecore-file >= 1.0.0 ecore-evas >= 1.0.0 ecore >= 1.0.0 evas >= 1.0.0 eet >= 1.4.0 eina >= 1.0.0 ${requirement_elm}" + +have_elementary_x="no" +want_elementary_x="auto" +AC_ARG_ENABLE([ecore-x], + [AC_HELP_STRING([--disable-ecore-x], [disable ecore-x support. @<:@default=detect@:>@])], + [want_elementary_x=$enableval], []) + +if test "x$want_elementary_x" != "xno"; then + PKG_CHECK_MODULES([ELEMENTARY_X], + [ecore-x >= 1.0.0], + [ + AC_DEFINE(HAVE_ELEMENTARY_X, 1, [X11 support for Elementary]) + have_elementary_x="yes" + requirement_elm="ecore-x >= 1.0.0 ${requirement_elm}" + ], + [have_elementary_x="no"] + ) +else + have_elementary_x="no" +fi +if test "x$want_elementary_x" = "xyes" -a "x$have_elementary_x" = "xno"; then + AC_MSG_ERROR([ecore-x support requested, but not found by pkg-config.]) +fi + + +have_elementary_fb="no" +want_elementary_fb="auto" +AC_ARG_ENABLE([ecore-fb], + [AC_HELP_STRING([--disable-ecore-fb], [disable ecore-fb support. @<:@default=detect@:>@])], + [want_elementary_fb=$enableval], []) + +if test "x$want_elementary_fb" != "xno"; then + PKG_CHECK_MODULES([ELEMENTARY_FB], + [ecore-fb >= 1.0.0], + [ + AC_DEFINE(HAVE_ELEMENTARY_FB, 1, [FB support for Elementary]) + have_elementary_fb="yes" + requirement_elm="ecore-fb >= 1.0.0 ${requirement_elm}" + ], + [have_elementary_fb="no"] + ) +else + have_elementary_fb="no" +fi +if test "x$want_elementary_fb" = "xyes" -a "x$have_elementary_fb" = "xno"; then + AC_MSG_ERROR([ecore-fb support requested, but not found by pkg-config.]) +fi + +have_elementary_sdl="no" +want_elementary_sdl="auto" +AC_ARG_ENABLE([ecore-sdl], + [AC_HELP_STRING([--disable-ecore-sdl], [disable ecore-sdl support. @<:@default=detect@:>@])], + [want_elementary_sdl=$enableval], []) + +if test "x$want_elementary_sdl" != "xno"; then + PKG_CHECK_MODULES([ELEMENTARY_SDL], + [ecore-sdl >= 1.0.0], + [ + AC_DEFINE(HAVE_ELEMENTARY_SDL, 1, [SDL support for Elementary]) + have_elementary_sdl="yes" + requirement_elm="ecore-sdl >= 1.0.0 ${requirement_elm}" + ], + [have_elementary_sdl="no"] + ) +else + have_elementary_sdl="no" +fi +if test "x$want_elementary_sdl" = "xyes" -a "x$have_elementary_sdl" = "xno"; then + AC_MSG_ERROR([ecore-sdl support requested, but not found by pkg-config.]) +fi + +have_elementary_win32="no" +want_elementary_win32="auto" +AC_ARG_ENABLE([ecore-win32], + [AC_HELP_STRING([--disable-ecore-win32], [disable ecore-win32 support. @<:@default=detect@:>@])], + [want_elementary_win32=$enableval], []) + +if test "x$want_elementary_win32" != "xno"; then + PKG_CHECK_MODULES([ELEMENTARY_WIN32], + [ecore-win32 >= 1.0.0], + [ + AC_DEFINE(HAVE_ELEMENTARY_WIN32, 1, [Windows XP support for Elementary]) + have_elementary_win32="yes" + requirement_elm="ecore-win32 >= 1.0.0 ${requirement_elm}" + ], + [have_elementary_win32="no"] + ) +else + have_elementary_win32="no" +fi +if test "x$want_elementary_win32" = "xyes" -a "x$have_elementary_win32" = "xno"; then + AC_MSG_ERROR([ecore-win32 support requested, but not found by pkg-config.]) +fi + +have_elementary_wince="no" +want_elementary_wince="auto" +AC_ARG_ENABLE([ecore-wince], + [AC_HELP_STRING([--disable-ecore-wince], [disable ecore-wince support. @<:@default=detect@:>@])], + [want_elementary_wince=$enableval], []) + +if test "x$want_elementary_wince" != "xno"; then + PKG_CHECK_MODULES([ELEMENTARY_WINCE], + [ecore-wince >= 1.0.0], + [ + AC_DEFINE(HAVE_ELEMENTARY_WINCE, 1, [Windows CE support for Elementary]) + have_elementary_wince="yes" + requirement_elm="ecore-wince >= 1.0.0 ${requirement_elm}" + ], + [have_elementary_wince="no"] + ) +else + have_elementary_wince="no" +fi +if test "x$want_elementary_wince" = "xyes" -a "x$have_elementary_wince" = "xno"; then + AC_MSG_ERROR([ecore-wince support requested, but not found by pkg-config.]) +fi + +ELM_EDBUS_DEF="#undef" +have_elementary_edbus="no" +want_elementary_edbus="auto" +AC_ARG_ENABLE([edbus], + [AC_HELP_STRING([--disable-edbus], [disable edbus support. @<:@default=detect@:>@])], + [want_elementary_edbus=$enableval], []) + +if test "x$want_elementary_edbus" != "xno"; then + PKG_CHECK_MODULES([ELEMENTARY_EDBUS], + [ + edbus >= 1.0.0 + ], + [ + AC_DEFINE(HAVE_ELEMENTARY_EDBUS, 1, [EDBus support for Elementary]) + have_elementary_edbus="yes" + ELM_EDBUS_DEF="#define" + requirement_elm="edbus >= 1.0.0 ${requirement_elm}" + ], + [have_elementary_edbus="no"] + ) +else + have_elementary_edbus="no" +fi +if test "x$want_elementary_edbus" = "xyes" -a "x$have_elementary_edbus" = "xno"; then + AC_MSG_ERROR([E_DBus support requested, but no e_dbus found by pkg-config.]) +fi +AC_SUBST(ELM_EDBUS_DEF) + +ELM_EFREET_DEF="#undef" +have_elementary_efreet="no" +want_elementary_efreet="auto" +AC_ARG_ENABLE([efreet], + [AC_HELP_STRING([--disable-efreet], [disable efreet support. @<:@default=detect@:>@])], + [want_elementary_efreet=$enableval], []) + +if test "x$want_elementary_efreet" != "xno"; then + PKG_CHECK_MODULES([ELEMENTARY_EFREET], + [ + efreet >= 1.0.0 + efreet-mime >= 1.0.0 + efreet-trash >= 1.0.0 + ], + [ + AC_DEFINE(HAVE_ELEMENTARY_EFREET, 1, [Efreet support for Elementary]) + have_elementary_efreet="yes" + ELM_EFREET_DEF="#define" + requirement_elm="efreet >= 1.0.0 efreet-mime >= 1.0.0 efreet-trash >= 1.0.0 ${requirement_elm}" + ], + [have_elementary_efreet="no"] + ) +else + have_elementary_efreet="no" +fi +if test "x$want_elementary_efreet" = "xyes" -a "x$have_elementary_efreet" = "xno"; then + AC_MSG_ERROR([Efreet support requested, but no efreet/efreet-mime/efreet-trash found by pkg-config.]) +fi +AC_SUBST(ELM_EFREET_DEF) + +ELM_EWEATHER_DEF="#undef" +have_elementary_eweather="no" +want_elementary_eweather="auto" +AC_ARG_ENABLE([eweather], + [AC_HELP_STRING([--disable-eweather], [disable eweather support. @<:@default=detect@:>@])], + [want_elementary_eweather=$enableval], []) + +if test "x$want_elementary_eweather" != "xno"; then + PKG_CHECK_MODULES([ELEMENTARY_EWEATHER], + [ + eweather + ], + [ + AC_DEFINE(HAVE_ELEMENTARY_EWEATHER, 1, [EWeather support for Elementary]) + have_elementary_eweather="yes" + ELM_EWEATHER_DEF="#define" + requirement_elm="eweather ${requirement_elm}" + ], + [have_elementary_eweather="no"] + ) +else + have_elementary_eweather="no" +fi +if test "x$want_elementary_eweather" = "xyes" -a "x$have_elementary_eweather" = "xno"; then + AC_MSG_ERROR([Eweather support requested, but no eweather found by pkg-config.]) +fi +AC_SUBST(ELM_EWEATHER_DEF) + +ELM_ETHUMB_DEF="#undef" +have_elementary_ethumb="no" +want_elementary_ethumb="auto" +AC_ARG_ENABLE([ethumb], + [AC_HELP_STRING([--disable-ethumb], [disable ethumb support. @<:@default=detect@:>@])], + [want_elementary_ethumb=$enableval], []) + +if test "x$want_elementary_ethumb" != "xno"; then + PKG_CHECK_MODULES([ELEMENTARY_ETHUMB], + [ + ethumb_client + ], + [ + AC_DEFINE(HAVE_ELEMENTARY_ETHUMB, 1, [Ethumb support for Elementary]) + have_elementary_ethumb="yes" + ELM_ETHUMB_DEF="#define" + requirement_elm="ethumb_client ${requirement_elm}" + ], + [have_elementary_ethumb="no"] + ) +else + have_elementary_ethumb="no" +fi +if test "x$want_elementary_ethumb" = "xyes" -a "x$have_elementary_ethumb" = "xno"; then + AC_MSG_ERROR([Ethumb support requested, but no ethumb found by pkg-config.]) +fi +AC_SUBST(ELM_ETHUMB_DEF) + +ELM_DEBUG_DEF="#undef" +want_elementary_debug="no" +AC_ARG_ENABLE([debug], + [AC_HELP_STRING([--enable-debug], [enable elementary debug support. @<:@default=disabled@:>@])], + [want_elementary_debug=$enableval], []) + +if test "x$want_elementary_debug" = "xyes"; then + AC_DEFINE(HAVE_ELEMENTARY_DEBUG, 1, [Elementary debug.]) + ELM_DEBUG_DEF="#define" +fi +AC_SUBST(ELM_DEBUG_DEF) + +ELM_ALLOCA_H_DEF="#undef" +AC_CHECK_HEADER(alloca.h, [ELM_ALLOCA_H_DEF="#define"]) +AC_SUBST(ELM_ALLOCA_H_DEF) + +ELM_LIBINTL_H_DEF="#undef" +AC_CHECK_HEADER(libintl.h, [ELM_LIBINTL_H_DEF="#define"]) +AC_SUBST(ELM_LIBINTL_H_DEF) + +EFL_CHECK_THREADS([ + TH=1 +] , [ + AC_MSG_ERROR(no thread support found. required.) + exit 1 +]) +AC_SUBST(EFL_PTHREAD_CFLAGS) +AC_SUBST(EFL_PTHREAD_LIBS) + +my_libs="-lm" +AC_SUBST(my_libs) +AC_SUBST(requirement_elm) + +EFL_WITH_BIN([eet], [eet-eet], [eet]) +EFL_WITH_BIN([edje], [edje-cc], [edje_cc]) + +EFL_CHECK_DOXYGEN([build_doc="yes"], [build_doc="no"]) + +EFL_ENABLE_BIN([elementary-test]) +EFL_ENABLE_BIN([elementary-config]) + +AC_OUTPUT([ +Makefile +elementary.spec +elementary.pc +doc/elementary.dox +doc/Makefile +src/Makefile +src/lib/Makefile +src/lib/Elementary.h +src/bin/Makefile +src/modules/Makefile +src/modules/test_entry/Makefile +src/modules/test_map/Makefile +src/edje_externals/Makefile +data/Makefile +data/themes/Makefile +data/images/Makefile +data/objects/Makefile +data/desktop/Makefile +data/edje_externals/Makefile +config/Makefile +config/default/Makefile +config/standard/Makefile +config/illume/Makefile +]) + +##################################################################### +## Info + +echo +echo +echo +echo "------------------------------------------------------------------------" +echo "$PACKAGE $VERSION" +echo "------------------------------------------------------------------------" +echo +echo "Configuration Options Summary:" +echo +echo " Engines:" +echo " X11....................: ${have_elementary_x}" +echo " Framebuffer............: ${have_elementary_fb}" +echo " SDL....................: ${have_elementary_sdl}" +echo " Windows XP.............: ${have_elementary_win32}" +echo " Windows CE.............: ${have_elementary_wince}" +echo +echo " Features:" +echo " EDBus..................: ${have_elementary_edbus}" +echo " EFreet.................: ${have_elementary_efreet}" +echo " EWeather...............: ${have_elementary_eweather}" +echo " Ethumb.................: ${have_elementary_ethumb}" +echo " Quick Launch...........: ${have_fork}" +echo +echo " eet......................: ${eet_eet}" +echo " edje_cc..................: ${edje_cc}" +echo +echo " Build elementary_test....: ${have_elementary_test}" +echo " Build elementary_config..: ${have_elementary_config}" +echo +echo "Compilation................: make (or gmake)" +echo " CPPFLAGS.................: $CPPFLAGS" +echo " CFLAGS...................: $CFLAGS" +echo " LDFLAGS..................: $LDFLAGS" +echo +echo "Installation...............: make install (as root if needed, with 'su' or 'sudo')" +echo " prefix...................: $prefix" +echo diff --git a/data/.cvsignore b/data/.cvsignore new file mode 100644 index 0000000..d880450 --- /dev/null +++ b/data/.cvsignore @@ -0,0 +1,3 @@ +Makefile +Makefile.in +default.edj diff --git a/data/Makefile.am b/data/Makefile.am new file mode 100644 index 0000000..17807ed --- /dev/null +++ b/data/Makefile.am @@ -0,0 +1,3 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in +SUBDIRS = themes images objects desktop edje_externals diff --git a/data/desktop/Makefile.am b/data/desktop/Makefile.am new file mode 100644 index 0000000..14e5d0f --- /dev/null +++ b/data/desktop/Makefile.am @@ -0,0 +1,10 @@ +4AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +desktopdir = $(datadir)/applications +desktop_DATA = elementary_test.desktop elementary_config.desktop + +icondir = $(datadir)/icons +icon_DATA = elementary.png + +EXTRA_DIST = $(desktop_DATA) $(icon_DATA) diff --git a/data/desktop/elementary.png b/data/desktop/elementary.png new file mode 100644 index 0000000000000000000000000000000000000000..79754891f19704929cf6198da9c17f7f12a7601b GIT binary patch literal 7313 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 literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_anchorview.png b/data/edje_externals/ico_anchorview.png new file mode 100644 index 0000000000000000000000000000000000000000..7615015d53caff4c337dc282647275fe43af9583 GIT binary patch literal 403 zcmeAS@N?(olHy`uVBq!ia0vp^Vj#@H1|*Mc$*~4fjKx9jP7LeL$-D$|*pj^6T^Rm@ z;DWu&Cj&(|3p^r=85p>QL70(Y)*K0-AbW|YuPgg4W;sC(VIP5)%Ydc`d%8G=Se(8( z)!y%@0nf4em#0H#2pB6RCZ#5SWR03J;epzQMxk{d*!UWbOxRQ`t&$<3<@Nc>{{Y2( zC%5T5@BVAqICX)`6PX?VpY9Ux@Q`ulP-GJ9P;9waBiMO!%Hy?L=YA6?3BOQ1|HnB? z206Zb#X}cgGhSV`>ivROa~?gNWplord%N%?i%R>We;JSM_IbW&dZGMf)eNrbshwN5 zy?h=c;_Ar3nCv4fFww=&`{K049WHyd72n&Yo2$=Vvn||zaqi}8N=mN{&oT5Ewg}YO zY$)rW{ZKM_1%I5H_47O5A3W1Lp|tbwe%6_%etdZ+@psuuGx-yd)bx)LyW=G)z4*}Q$iB}yRW1r literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_bubble.png b/data/edje_externals/ico_bubble.png new file mode 100644 index 0000000000000000000000000000000000000000..e2df401f2fa891bcf64a0152c40cb13a96f6145c GIT binary patch literal 1311 zcmV+)1>pLLP)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L00!&;00!&<9(6c100007bV*G`2igN2 z4j&aTyQc&I00f^&L_t(&-tAh?OCx6(e&(AmGs(u)w5;g1T2CHI53(S%muN*0x<%-r z?B1)#Tq^VrSbFSYFJ2b4XSYX9EhyA#PTdMcq^J0!V8m>KMDt@aGtM_(4}OzQ#>s9H zwrnQmg_j8-GxI**`+V>FPUex&oJo!&7oRy=)TAcQA;N8t9DwEc+)_rG1W2>l?34Zd z{jUIo0H^>00AvSv--8UCo}T8ryStyCpPz4RZf<@7;I06yv?|y}7DWNj17Ps@`1mrH z%W+-Tc_x#2vA(|k2*5o7I0%6H5v(L=*$rSQ9*=*YN~Jhsj5Ef#rfEE#PQQr90pBAb{T9 z-qFd)$(6ISvtQTN)*b@r@~Fn-4fmDmh^ww)KyoaA`vT6REVA)Ffcwd0a;d++e^`>d z?0q1i;Lae-QB0t)6>5J(8Z!z4Ga^`Ny|Bq+?c-P8hua}RW#_~s>?$F z?)3EZyoyGn<254^+2x!=Q51y3;SYv}hQ5x)ViVD5^n7Jy<)z4~;&G2!u825ky_u{u zdI0Lu($XhWQ&Zn{b#;9j2n6oG?R`Qit;(!vnoV8j>gwvOSSz6jLZjv!4Rbsgw#J6X`0qhz&6-M?%_1cvS6AfG)*h-?d{Et zjg37APzGRJ6Nq!?{*wXRnV+A3Ff%i=9u9{?oO2k40n4&lx1SLLMNuG05=x~~d3kyH z;oRKZUjSYKV1+`#k{o+e0nn37CYJ^W2fvhM8Rc@>H=|f66ar%mCnqPr3=a>_0=NWV z*IbyFG8>y?h5*whOfjS2n&Uw{XSNXCHGFdg|ks2%ETl0#a)>;ie zg7u2qP1m-~B&qj@eg)`BSIe?|O;>k+_oQn(8mVXV`nmAD>FG1FBOG)AcX#&s_iNrHa)422hS3kIASn@4~{uqlt-$Z&X!%uf~HN#R>NN_f}IiR*I#F zwJh8gD^;qiJ7}kfp5msiywyP3K$!q$SJf(wUb6ziRsrb*TT?*zx}g0ilJ}fq{skG- VtYMYjn4kav002ovPDHLkV1m0fa6JG3 literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_button.png b/data/edje_externals/ico_button.png new file mode 100644 index 0000000000000000000000000000000000000000..842a43283b4d7e918e80bba63d2bc822d25aa16d GIT binary patch literal 181 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 KGUYJyFaHB?Fhzd= literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_fileselector.png b/data/edje_externals/ico_fileselector.png new file mode 100644 index 0000000000000000000000000000000000000000..fbf06dcbcf42a85e9dc3f90b2ec698607c7cb31a GIT binary patch literal 265 zcmV+k0rvihP)7w1cM*IXZYxg>p{7cq;OX*P5K?JR4Xh{a~ZGmudIb2?V zM3a@e*a%P;6MDt8B?0QHs*0MnZQG6jU>rvb!w?0U=lMg0*7}yhF#$l+G*O{-T|=a5 z1-%~nzK8dI6-X%sDdl&t_a4TWRbXpv7_5|nwRUylpb9DF+pGWOI9NAk1~bP|F(2m~ zm>JGF0KnOvKJFaMaXEONI0RV)ex{6~;wO5XYzbwhE_MQRiTpL~Qw7Ey+>1sz=_xq* P00000NkvXXu0mjfg-UM6 literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_fileselector_button.png b/data/edje_externals/ico_fileselector_button.png new file mode 100644 index 0000000000000000000000000000000000000000..6b5c7734d820320a2c586fc8cc51add4862ee8ba GIT binary patch literal 198 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 HtC0Tz_%V@w literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_list.png b/data/edje_externals/ico_list.png new file mode 100755 index 0000000000000000000000000000000000000000..9a1dc647dbe62f7c4325d6ebe398973deabafc2a GIT binary patch literal 2167 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 literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_photocam.png b/data/edje_externals/ico_photocam.png new file mode 100644 index 0000000000000000000000000000000000000000..c789dbbf003f9318e7f034afefebaa95c5a74940 GIT binary patch literal 11838 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 literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_slider.png b/data/edje_externals/ico_slider.png new file mode 100644 index 0000000000000000000000000000000000000000..307f45cddbaa7516927b39098db9a7b7020494f2 GIT binary patch literal 172 zcmeAS@N?(olHy`uVBq!ia0vp^Vj#@H1|*Mc$*~4f#hxyXAr`0KPTnneK!L~EwNLga z%Skq#gKR*;`Jhn98watDvr83R&#k}e`RymO#IbY>PlcV#7V7_$pV#bN|yZElL(SY;7{}-+&DgnFB(B8KKPU) zI^fNI46e`&Tam-%3^&)#S6wZ8SO zb@l;DD4~QB{%5fB6Iqre05=$8S8V@hAR+)bbsUEm5zsX4RU&$yG3NU>2@ugCW6Us3 z^Q%08(a}*hJ3IR&fM;Y`h9pTuM2s<(A5oyzbwL22v9a-Cdwct?q9{C-NveZ1cv(hNkQKU0v5R!C>&mbUOWJO-)TElgYdx#$Yg*357zLP$-nC zt*tFG@h%h!{j{*KFu^&0nTTE@q8Ev%HIYcXTUS^2gRbitUDxlfuC8hTAOV2a>y=ei zg=@UBvT{q7W%&L6O-YjA_xm@+dymHhP1B0Zkj?V`H~%+x8I=rl+UdPESv}Mn*t`Fy?yQ&UqP1prW&A2m}K5;^N|5S6A0P09-g@jPdgF@;^Kt `aIa!wTCP|V>M7A&h zHUOK>MRp%A%){aEFY$Q%!|Lj4JFkFS>q^GhbG^O2@2sq>Gy|Z4fq`#kW@bLWH086i zm&tKqZF_q=*xA`RczAeNUR71~WNmHjy@rN{uO&%(T(p^Ut}(_M06gt7|CNY-cK-!e zk+^n^hI-=bBrM8w?SGS14ByC$I$N+{vK d$DbtJYmi@eBr5;_002ovPDHLkV1h9)H8n6E`3?X8 literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_spinner.png b/data/edje_externals/ico_spinner.png new file mode 100644 index 0000000000000000000000000000000000000000..0ab2af63bcbb4f1b8f9d995750524a5006a3f5fe GIT binary patch literal 215 zcmeAS@N?(olHy`uVBq!ia0vp^Vj#@H1|*Mc$*~4fjKx9jP7LeL$-D$|*pj^6T^Rm@ z;DWu&Cj&(|3p^r=85p>QL70(Y)*K0-AbW|YuPgg4W_eLn(G&IgA6y$9*$jMalG+Lyhdmy@H$=9CevT1xf)~()kM&RqQ z8@UCy|$Iel??f@sB(_ifK}e?EJz`ag(qN@((QQK9`UKr0wLUHx3vIVCg! E02h-;TL1t6 literal 0 HcmV?d00001 diff --git a/data/edje_externals/ico_thumb.png b/data/edje_externals/ico_thumb.png new file mode 100644 index 0000000000000000000000000000000000000000..e98ed3dc0954aaa43898b20bf24035b95cd08c17 GIT binary patch literal 147 zcmeAS@N?(olHy`uVBq!ia0vp^Vj#@H1|*Mc$*~4fQJyZ2Ar`0KUfsys5WwMjvAyv4 zah6*Ke7({eRLji5)F%88&hsqf;u4s|-oU+euENZ#6VLGaZawH^Wc@&vLFtj?3avYT vg_F|sllRK<+k7~%-@-|BZDq@n*E8>ZpOJAeX@>wS&=v+yS3j3^P6*}Kk56o9GC^4rzu7I_tq)^00009Tq?P^R>Q9`Y(PwuJds3J?DJJ>-~B?-zUOAPmAds=Q%1WDkeBg-3T0C{(GIJ1Ap6< zt^2`&+RI2wm8#?`*E0Br&gOxZI@RgF-}jAq3E&+DcbJ(M71epxe=lmP^h^kNlO7G% z)u8`H!+n{7(d;0z61>HM)_8Z{?QD5{QD{eAEx4|M=__V-Dk^q1 zxcYr#zhA2v%Wl~D%BA4-&x^ekPZeTTX-Q?Xqs$zR55-WdXA!Tmj2`22Ocr@PyzioN zg9?RT8Sl8|e_dry)Ml?aBMiHgHz0jcb>_|JC{%C7Z!|01&rLtz+T?W5Xh8EQJhS!H z!{y%x8nF#e*L~M_l%15EiXD_FNhQd7dlO@0t8@Xf3=YK)XF1i8)>T6w(8z8HCTE$e zb+{a%zTi?`90Mlth=I4?3Q|ixk>!Q6oIig)Kk}m$q)YZ06$WYzp(_{3p~&~zvQ(3F zCDYUq2+BHhc)LHj`gu-WNe+rrCL{XiPlUM`dzf_`!QP|R9GU=Eymp~3ONuswV9&84 zt0WkzaWS?VeBziMhC|huiy0MMW)7!;W8$C;X34TQ+BHYUoi_`>P16@-Ju5I!vuxG~ zbpyl|4a2jcs)42H#~45FMZE^CU5XkaLHmwHihf`!8KBkNvKUvAnEb8WJk-t^;wV|wf> z-bF_nK7QOcKF)jjh^l7kUJ_GRJm@kk=iaKTo@7cnOc+(k)V8faMWIL`A2! zkJ8f8_&B4?ntkicm(n#w*l2juv@bD-3W?pE{&lRV+?+l0k^fzQG!+~J!x`Omn?+0B zzJ1@r<2JY{a>S#40t_|rC!%~zq}LYXE~gU^pb!tEB}#7|1p3MfhCRoYmj=h5mWuFc zccBvRcHAUy$Jcz1f?^ncRJtB@4N8s#_7IXR_eat4gn#UvATHJRJ?k0CnUMBSt8l5@-QI!O>bTK~`4QR2Amb8rJRQhrg$AdU<(K zspnimPqa{WE}jdG=$`##bQ7p-@uehlICnMaX(&E7SA#$PERjh3@#DvPytW>8VRh}a zE0EaHa6c;bJwF^$=Ru@xm5BD{Io|Q6oYL1`sjsPlNkBf;)}|E{+{EEp?nazn+{#a0uc6b;T z$WnU%-M~q9*?36h9cA3$TtMF7{$TKSdfHk*K%mBR{#;!N@z*bHCnw5CL>3AIgF?8u z=Vv;jI%Yirm3b~G{kbTX5)~7}Y>a4JS9KVVOtG^ylc<80l*LHu-Pex@C+&d>*_{V&VG}QJ~(*p9}tj+#df+@6NiRWA3QjZKp?>Rlg4GT$eJ!JhqFM!eZq|i*}Cx8 zq+8B#8A*I4d42E5%*<^1&oXh;Ste+|oo8rxSW^NrH(u+d&VLE`V`XLKm+I<=4Ah^ZZ9mKdzne>zoB;7JyT3ge^K(m4lQ9di9t=&Aq15;D)=l!o} zd?+c2xgH+7(J`yP(RcbH6s(%^$)AU7_3KTUB71T4{)*SiA17}w4oa!03}z_>$oc;f z0tHf1A_j~*%o>uIl>B{i^6OI-|921b^fo&~#owy)UuI_~Hq~=Kr4hH)mhJMDQVF*I zTM6x#g=pVz?mI8uu%U${j+{uQsNWD07Usw5m6j<=We=ncQ(kYT3h3zSZv8GSWnm7# z3+}Z?4pwn%IuJPB?^a38&i?0E?s5Y?J!ezIEpcUK@x#L=U{x7HRe|a3u9AEQpBTY0 zsaWiMM+7V5g$vs`JST6#-p25#d`+h?v;W;QsP}(09r>XWr8iN(d5c0difP-@10vRx+Z5l6lvQE`_MUdvWSlr4zXA6W3?O zDYdiKoX{BtIy(BZbRm9?7UN>F&4=@)`<>!Jt;wQKU;+ss5{oj9VbHd%Ar=}M8t1X{ zP#^(dPC%h;9pi7fYHfY}{8E<-ZVFdBx3Ztz=wQ|VHa`9i3LjP#8qk{F0bCG5LnD3X zPTA+r_aq?Dh8oA(RT8t3Zx=||zQycdSC_#T)GBGtbjXqK+nVoRN8pyBEDQ}6;@4us zVba>C^Zj3{s%AF*zDb`{DZEzaZ*6Iz(#vBtO9mLAc(|1FV|aLLH~56zLHTsN&-J_} z@N}>vpQKP=1=Q5k-o?f~=_4C+-^29$<^+j}*YCl<9$B1^&(T6TI!;xNSj^7#CcIJQ zJC|gD9D(N=6>0L64KYf-OI zCwO`2MkX_TC8=sY(lb>6XFaud#KFNa|F51mT4+of<&(5uym%~FY}i!WbnlbUIS?+H zD#2NR2fjG7T@S7^F|_zP7_=*uo}Ru>BLD3QSZ{PFHfWbvT3;80FwVHkSa!0eJAR;>7a3!KcM09R*~=cF$ff8f(R^c)V0n6I3c|g}DK9Ut zNZ7{E@RD*iJ92Q+U}2(XqbFQ6g%n+#e-=4%H(*y}dwU!0 z_M+8B0FTY&K@e-GXV3W4bXXYas3BZjwg6ng)I8_ThF{?MTDn5&H;NmX_nbz{-)0Os z&n_l$_iisp>a()MFF+9wRTW0-$h2>4NE8;{HT9ipq5gY9 z{;OolAYD6OGXbrca23cCSYBUW1T}O#MX&O{CLf|ED{=uREUcUz3*=&6)+r6fPW!$x zH`J0xA#7xJEOG066lnASIeB*GIVYcPPKESDV){q7HD}QB1w}=lDl3yjpHxZ6NyPQ5 zY~@nGX_~s;-c9+z6vNR|K^6~yzq6a)CW!xr1yV3i=wgrfW12Wmx{DE-_xiXYqul=z z4xo1A1KWzhxEx@aEi{GXdlyi?v73vEgUt4;HfrIqq4s zrdm~#3QE2rT7FX~+YWygM49ekplCI%WV^Nxi=*8#;6_c`*!7ENX+cAFu)2v2)i6uGDSERt5z4t< ze?fmTp_s`5lekWwnwi<~LA207p($f7udpx*-~j=h0&i?Q7R|P`f^;%dRX~Rh2Y@u(_`{!1ZlM?Z>tar2W_JJOb3I!ygWda z5sMemfO&_O|AdX4{M~C_EXWJewj`SdZuJVTjFyF1{@pS)84HkFyp)iTz@-wDd3fmm zZ-MqEd;vqkFzQZDw?L=>6aqb8NJvO3t~W}&38tk*-)a@dZW$P#eR{mer5rdH#ywUX zvsE0DekaW1L`)CyGm{#mAKA;&LWFI0HdX~!SNBVJ(W2J#hUqyA3%;zkPgKDK8Z0j8 z>JpCEe4A(gbz2)P)S#QC(u(0Kg|3WFK|@3kz42cPr&sgWMsa6PzwhhLz$}?qaGx% zx$${4T+1LNOTDy`cnj^VR%T9ieW9JHBT&p%`T0|YrA+{z<8=g_ zI_r@2KJnVQj;OI-V0>eZ^;os=Yvtu5s;!Pvkg$jnrw$tr<)amlH=GB5h!1kTEzJlG3_775kryNOaAu+ogT^xZB!^^XG@0?(~nTwIb{x{xVIw;1Abo9m!ApVIzR2wU zmyk87ztK%cU~oDo8tVGQEV&jWyn@e)mA^k{HOa-LxUa7dG!C?9s44bM(GIld2LJ0R z*8xON*}>@L!37c$lapB@)Pbad2tEptVOm238?O(8ZLZa*eGjN2tVCu&}bz+vQ>cD~S$j2LwjqQNj%Lq7i5$(Qmyx8-H7>z4WVF|Zp6 z`FK&^u2K}xNqHLMZeYXUPocRT{R>x2HtEJry9kX#BM+YRy@<3XIq<~d5F zx-dgVpF$0K%n3X}k0P>?XtZHQUmIag{xP}_%O@-T-p>k5jT=x+-c|Orq2Nh5Zw-vajy( j0?+^dKeV29AFIeIO8D&9eYpf4qf@~(^wdjKtzQ2RZ`IKZ literal 0 HcmV?d00001 diff --git a/data/edje_externals/icons.edc b/data/edje_externals/icons.edc new file mode 100644 index 0000000..e36ccea --- /dev/null +++ b/data/edje_externals/icons.edc @@ -0,0 +1,37 @@ +#define ICON(_name) \ +images { image: "ico_"_name".png" COMP; } \ +collections { group { name: "ico_"_name; \ + parts { part { name: "icon"; \ + type: IMAGE; mouse_events: 0; \ + description { state: "default" 0.0; \ + align: 0.5 0.5; \ + aspect: 1.0 1.0; \ + aspect_preference: VERTICAL; \ + image.normal: "ico_"_name".png"; \ +}}}}} + +ICON("anchorblock") +ICON("anchorview") +ICON("bubble") +ICON("button") +ICON("check") +ICON("clock") +ICON("fileselector") +ICON("fileselector_button") +ICON("genlist") +ICON("hoversel") +ICON("list") +ICON("map") +ICON("notepad") +ICON("photocam") +ICON("progressbar") +ICON("radio") +ICON("scrolled_entry") +ICON("slider") +ICON("slideshow") +ICON("spinner") +ICON("thumb") +ICON("toggle") +ICON("toolbar") +ICON("slideshow") + diff --git a/data/images/Makefile.am b/data/images/Makefile.am new file mode 100644 index 0000000..baf9ed5 --- /dev/null +++ b/data/images/Makefile.am @@ -0,0 +1,47 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +filesdir = $(datadir)/elementary/images +files_DATA = \ +panel_01.jpg \ +plant_01.jpg \ +rock_01.jpg \ +rock_02.jpg \ +sky_01.jpg \ +sky_02.jpg \ +sky_03.jpg \ +sky_04.jpg \ +wood_01.jpg \ +logo.png \ +logo_small.png \ +parking.png \ +icon_00.png \ +icon_01.png \ +icon_02.png \ +icon_03.png \ +icon_04.png \ +icon_05.png \ +icon_06.png \ +icon_07.png \ +icon_08.png \ +icon_09.png \ +icon_10.png \ +icon_11.png \ +icon_12.png \ +icon_13.png \ +icon_14.png \ +icon_15.png \ +icon_16.png \ +icon_17.png \ +icon_18.png \ +icon_19.png \ +icon_20.png \ +icon_21.png \ +icon_22.png \ +icon_23.png \ +bubble.png \ +bubble_sh.png \ +mystrale.jpg \ +mystrale_2.jpg + +EXTRA_DIST = $(files_DATA) diff --git a/data/images/bubble.png b/data/images/bubble.png new file mode 100644 index 0000000000000000000000000000000000000000..dfb71b7e78a4c067cae32a3116cc2e7701a04729 GIT binary patch literal 4878 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 AcmMzZ literal 0 HcmV?d00001 diff --git a/data/images/bubble_sh.png b/data/images/bubble_sh.png new file mode 100644 index 0000000000000000000000000000000000000000..b66c1e624de5793ac420af492a755a015bd30208 GIT binary patch literal 1600 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 literal 0 HcmV?d00001 diff --git a/data/images/icon_02.png b/data/images/icon_02.png new file mode 100644 index 0000000000000000000000000000000000000000..592cb5ace4b61f1c8e673b73d764be455e1e0842 GIT binary patch literal 12432 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 literal 0 HcmV?d00001 diff --git a/data/images/icon_03.png b/data/images/icon_03.png new file mode 100644 index 0000000000000000000000000000000000000000..3d3063b1a91cc6ff78f6c4125368aaa5ce646d7f GIT binary patch literal 15014 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 literal 0 HcmV?d00001 diff --git a/data/images/icon_04.png b/data/images/icon_04.png new file mode 100644 index 0000000000000000000000000000000000000000..454bd62d8fbfae092b3f843a21b65f74949e8364 GIT binary patch literal 7912 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 literal 0 HcmV?d00001 diff --git a/data/images/icon_05.png b/data/images/icon_05.png new file mode 100644 index 0000000000000000000000000000000000000000..bb817921ff0e324ea992b363348e7e94030413e4 GIT binary patch literal 1483 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 literal 0 HcmV?d00001 diff --git a/data/images/icon_07.png b/data/images/icon_07.png new file mode 100644 index 0000000000000000000000000000000000000000..1c76beba0cc84ea28da33a782d623107a142a9c8 GIT binary patch literal 2548 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 T`2>#UIsj+CIq&v?qxF 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 Nh^Nn$O5heD{{!&)Df0jT literal 0 HcmV?d00001 diff --git a/data/images/icon_11.png b/data/images/icon_11.png new file mode 100644 index 0000000000000000000000000000000000000000..cdb212ec16776ef62c1b0388f79c117d851526f2 GIT binary patch literal 8684 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 NGmN#-Q?zINe*omOo6rCN literal 0 HcmV?d00001 diff --git a/data/images/icon_13.png b/data/images/icon_13.png new file mode 100644 index 0000000000000000000000000000000000000000..27d964e8e33e5a3f581ddbf41f9c925d00c08b33 GIT binary patch literal 5051 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 literal 0 HcmV?d00001 diff --git a/data/images/icon_15.png b/data/images/icon_15.png new file mode 100644 index 0000000000000000000000000000000000000000..8ab20cedeaa492b7e30d6b3538de6e57f17ab72a GIT binary patch literal 8706 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 aoUKKiTwi2u%Q6Eufe>oCsujx5LjDJZ(5r<2 literal 0 HcmV?d00001 diff --git a/data/images/icon_16.png b/data/images/icon_16.png new file mode 100644 index 0000000000000000000000000000000000000000..7f5ad1e624d03efb5133035ac31f29194fcf8a85 GIT binary patch literal 11758 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 dylk!A?Zn(XpJ#06 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 aXLr}&|HnbK5}k^305nzgRO*%Nqy7ihJA|tM literal 0 HcmV?d00001 diff --git a/data/images/icon_19.png b/data/images/icon_19.png new file mode 100644 index 0000000000000000000000000000000000000000..d8784e0bfc9798cea976e1a30a53018b514b1ad5 GIT binary patch literal 11785 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 Ola>4`Q6Xj+^#1^suN4;n literal 0 HcmV?d00001 diff --git a/data/images/icon_20.png b/data/images/icon_20.png new file mode 100644 index 0000000000000000000000000000000000000000..69a9dca92f22acfa15f3c4644b26f8c003bb633a GIT binary patch literal 8278 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 K$}mOq@c#fdB=qnA literal 0 HcmV?d00001 diff --git a/data/images/icon_21.png b/data/images/icon_21.png new file mode 100644 index 0000000000000000000000000000000000000000..6561e5fb7827cba951e2e39436748d745ac3edd3 GIT binary patch literal 14661 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 Br9uDz literal 0 HcmV?d00001 diff --git a/data/images/icon_22.png b/data/images/icon_22.png new file mode 100644 index 0000000000000000000000000000000000000000..d6130e82fe4b0f4b663c76ebe930a02fe9db58b5 GIT binary patch literal 12215 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 Avj6}9 literal 0 HcmV?d00001 diff --git a/data/images/icon_23.png b/data/images/icon_23.png new file mode 100644 index 0000000000000000000000000000000000000000..27f5457e584e0691054d2a2f31b3d2560da84457 GIT binary patch literal 10078 zcmaiacQl)C+?= zGFm}MHI?_ppx%5`$ANkK4?)#!YueAT9Kw<4sWi0iEf|VT4aL%9YxgLCbA*z#8(VU-WC7~5#ZQ+bQRBOlU$MvqYXB)KP%8Z-wU%g&9y7ix% zzGjqdhxt(14=t11UAO8PPYez7;~&2S4M}CsjLjZz7x6S8$!~`lPgtqWm*~Qk7Xl}z z%!{vU_)~*Hc9_DL)DsG)57ljuXVa@yoN*hH+`h4;ti5%bQfZ+i-oWX?5phWciWY_0 z>cR{Rk(ZnZjS%avp1B6QPQi3?$OF&6Q=XT-=!_`&$CJIiRA;R=g3Ng|A5oLqT)o|G zo12MC0XI{Y-(mkeCj~u%{a0Sgj&uEb$&hYHKE+!PJn~>-)b_9Ol_q;FslVO*=Pyw^ zZ8mDiRZUnwG1IGgE`RIPvVs&Oms0ee7yK5FT|&NB?P$P?Cwc$WQP&b(S`xO)ExpfYRt7J7OasT)2-a!U?hz|D@PO+g{K4 zD%ax@TVsE!08rGd(xZbZCeJAg)XQp%G5d4P8U-G>1Q_f&+MvwRgjJH zOwp?{xTTm>zQIO*S|NlH1QFq#@+sk(FrE(|gJl7AK%%8zhzXeS%w>#4e5a;_B%r1>g?I-#hq?xt6qN2Bwu=U&9doh76)p$PYY*-0k2}@U z5DeEIR8J|a2hO|UcLgG-`C`O~Dx4S4Oi@XfJ^GOm62w$ZrbsxQN$KSPeA;8@8; z(&pqxQAR8Zibfz;Z_HHQlS$dhUTdhBsSAxpW%p@wxBNArB2(SP3)GspejIV&a<6Y? z-3vN3g3!iCcN73|6i+H)inv93sNzVS>z!{@FKBs@YLIo#4ujvOc5r=N`#a((@@=?~ zsT2mz8xsMi>u2%cqQ|*XMMx2Aptk;^{Xs=QoUE|V7Br>=zksC0=5ih$(42OUEnBd) zkg|!M>ry#iD>E`OPE{cavre_zbu;s-uw@&r-uuK%>a=%J5JXVKfeJ@LErpN^>B#() zC4wJojT*hCejPeCx4n=I7hB1v!a+W|UPpiCKi?&)Z)lMZxOYOs!`al9OmZSyGIsC3 z#k%2eN())EzJ+USP4hN$baVpar#54G30iH^@^KhWszNr5t_P77w!{VdM2B`6tlRh( zHuN<3$m;Snx8YBXKb%#Mrk}J+oOMiX-r6EU58H;`2wyX|uqb$MSX$s%KQr_|w}!ma zl3+qG_cNP#gH2OdIZ=vk%*e10KQL+3%5!)_F>%MG&sVFeI$uD-WbE_$@K|3ZX=URQ z33viL^&2lp7@?U2ud_5JWuPi|w>vsI)^N7tFueHbv?%{ze4(csVjE9kzHE-vA_r3P zT5C-<*4j1;E_Zt<^Vv{GfV&~irOuX^LL-sL9k<0`Wye0t15;Ui7R?6op>-$S6rZiO zggh%YO?H7RWvQ#~ju=ti{wa5m9mXVQUh_F**k|NUu#H-P&r#}PAmxOyZ>S_K5*`<874Z4swBmuTq&664TVafg{bG3`If#Z}$C}aE z$-R(}p{J9rIut!rmRr*CSli^UfZ&CERedA^cCn+Q?oLBFgrkaG)5-yNO@#T)*j*WBFoKq@UR=D5PiJ^+Bcw8JO2g zFs>`FZD$wMd-Zzi+)YiRA->`dL2b=E3Qv zef~RWExZm*fAAkhx514HKME48HShuT^{g=YZ ze|Ql7YddJ&{2oj`<~|xaKY4-@$yl*CTecYG*GPd7Gw-Ke`Q*uj(Cpn#>bWUHc~@>Q zQYIa-4XTj>A`J-OlxRff1rXaqL7P(FEWE4W?biGF3PF~qB9}TmxoT!yC37ytSb^}8 zD#BQJYGq7XpIwbMmoR#G)y5eV2XO#h=Cj1&hqW})YDnNH2ocmxf{6Ab0ZG zDi?y^$jI4UTx)Ti;eevOSMJWYOx!#!>D=EWzi9tk+Wv+zRPc7(DZ_JcW9;n{p1jP= zLli?EoG6T!6emKFupw15|!K5R4Gd;M$}lHhVrD0Wdqta z<{3}9mpW(k6dwCQxH2r)8;BNKs!<8%7>KaW%C|20G&Qgh`}g9G>SQ<_0>;EA=Cc!H zPrj;l#e~5AY(lN^nRdHHv;%@o7x&W62xj0`Ka<|JseDt^lju9kGg%kPpBHg5-HqD{ zWXPj|#6UD)22Qmmv26!eh?%dkX~Ky&(T}7!^BQtr$uK=sIzidAu6PqC-D@Stgh=b&3w`gP%pf{>dYPg>?qQ8=HZVp<-6(E1TJ?WShO!q z)+yG6pP$|DeZg~XjT69Mx5B{rXz!;5sDM?27kx$^V~yCS!1?O@wosaYwuzB%XD^Li z(;{zDK&)D+s9U&K>Y}{GdhL8M5q1}IYz4K)tK?q9LM*3ta_{RfRH>25YvZtUsbh7n zlXZDq1%uQvHEzY1bdhkp0X$`ilYF2|c92w})GBJh2yo&w7UiqFWk|=Z!l`16l=awM z8R?FWj_!Wnww&}#AFK*;K)&x=pj4vu6D-D*9zdT z){H)I?5QD@qnvIgz8R7-{kr7I#Vky~xy-n+A|5Fp4lFXpq>A$u0~DVt#McUBt2gi3%k&Z;fdRmG%l4<_YQ^eR}S5 zE7sphjQVplh3nb#AD(u9a2F=(bgM)mgu>!ahS9)EwnZZV$Pk5KK2d1#YkZVGi-_s< z;SYKiNTK*^Xa-_ts466PJM_HLui4dQCZ7ZG;B?^vC<%hH#$1A;k)@@j#2tmeg^tL) z9_tZX+0aK+tbDYESSKXx3L;fuS0Mlq%xDMXW1TBMQ`hAPrY0@n=urXAB3Yr#_<6ku zG?$w6MT;9VQA?A66e?eOy&?k@X4myI1A{!-RNvnjIvdPli@VY#{OA%MJZQ}91GA-W zch|l3>Ju!fK681WSJr^;Cy*@PZ{Avxx})Z*D3Ef&1-4PlFr znHCdYQ_S3&PLiLhL`7m==X!TSmr%&Eii+dz?(Uu&@_za<6h&M?r}iDP4)P)z1DQ5e z=)XVIef3#~@0?_fL@ILc+YgD3gdfBC?ainM-UdVS)eDqML?g=a1c@}_AgKcGTv-9r z(a}NF`QFIDO##WNcjNHrt>oLlI_Um@hYLmRo4F zHNKU2Gq!keL4uf#fhT#JTVkeSAi=h_w##poPgloBMn)FfLXU54FEsJ-@(I9Y(^n+H zpMM5D5|Y!rFPl1uFioNZGH`pAXkT%0G-pSu<^i~q6D?XB^8L6i4fQLUp80o;YtCC-o@va=7bd<> z#Z@YQ*Ou}wj@hMi`Q*YQgj3|NUBkbXvt>$g^+)#i#n>})6>B)vrKLamz}2f-X+(`? zt2McF`}XavQ_wRHOmd2~hX=%p?It*?yv#?MAFrQJ2~>qZI3Hfos2p>uTVGzb4ceSn z1iZ%&jv92Iu0+!_#70R=O76Cc_A^}Mvm~FN9l#|d&|%x@1uDp?N`*mLEsi%?kgl6C zI^+X144<8w%jL<{`^(>B6({I=YiBEgysr3gI|as*CTMjteof9YS2ahVB&7)IT9GV< zQ31~ zkkn<%5>E7~9$^X{ibs7(?$WF=xl>nHr%ob~hP8*jwG?{|!j+U#tSeVeM|e(0&ck*` zG@_As>izog;(gmtehmDJtUU(aDa#Q90jf+-E{*lcO7w7* z=)A9=;)pu#&wke?4Y~TgjUH04Qh`rPbERoP^nFGL2!#yDr?1%HOSFEV3zTQAy)QG6 z*ipdNU+oyz)(pxjo?fA)f}-E)i$HmJdWVO3Ye)`KIp87)N{h9(@=vJ6g)qx5-fvo- zgGMIK+_Y4VQaKK_CePnEj3Kmfj~V&IfTutdE}Wi{&ri<-H);>@Aw*5(V z&s07gQyy>j+elkmTPs9;d5ZjxY7&cjg>vFVmnA1(qHHhsOUK8>CHAJ=nCXTV1!gw# zF93@XCN&xe2M&$Ige?rKrsA>Nw;&b2$;I4wgidnl6e~gd7v93#w33xbleu! z{wmZ0H&Yz!jnufszQn#tqmyHCzzZa*#mRBQ6}#ZsmSJ`;s3w$;7T zTiM#s@NdQKFUwWU!3V!@VBok{iK427@1-BzxT2Ew-~64zwKh>5q02H!h1JNFA3tbC zt@u&|L&*1YNedaI*4CI9KO}P&{~dP5Jnd?kl<)LPCrvNJ7?QE0pLAWKc*PvAVr#Q6 zRRLMJS8MP{`!PCb;?Yoc6=YG#*45=gKFA|gpft^&8Efg}#9(py>*?3}_EXo;yD=T4n+t2WfTOoDcxwIi#e(;ZRC*?S8pFq9oEEQx?A3eLc$dl zT`%(}m4%XD0jX|9Ff3AqJQrhXBu!H<2;&i`{Pu3!aPFRcmflqakYg<6 zYad)T({98?QcgT89vNYycH2yJGm!Aa zsmh~PU&PAC=bHne6^OdI;GM71Ls~F3r$2viBdxA8Kfk@#lk+uV=@SW>f%3l*_NpO0 zgW0O-+8C4?_$`0QnCk5898F*qvP0t2=EA3!FQnG zof*k@BWuKQ$MN@p|Mi?8A<62)*;Th1((|Rs2Uf)yDABFZX}9{1ZEf1_d8nlNTZJ#iQZADKE6)1-X0^F+# zGtl@gf;~2;Q3JyP9XB>M7DR3f^<=;4M96~2J<$DBOS+kO^G)q7Y4`bJEXrx7P9|V$ zA;#8N(tYD7=n`K{Nh@3=kv{{cqt&)lPyVvARZG%Q=ltNvGIRU=MR4*P%~&hVH)1wl z4b$Dqo>tb>JU^N;o^1`LH*e1SY%Jwz>fp;0Qyi6f%VvrJ=y3qW1@S?$dQsTMbZrmM z*;YKqKXQ9kYFN5P%#@3ei@4Qf=CG}JPpMk8pGzSCVg>yrlY+;JZ-hzyCJadgV!CipiF*Y`%9<}uTbn?Nu`Fz;` z=3(OmZa)zKQwQY7`<3=h7*2d_XowikxLQ_GZr$3HFUl!0&gwbK98kYs@b?z7BW9(H z>=*3Ca$B0X;@3Ra6twqiL&AQrC3Js%%HM6S$yYjM=~h~PPEga3+(=XbBey1r>jk&s zhp|-QeT92E$SW|xSExk&um&tj6V|uf|B8~>^XB*y>l3coO0N+mSa(s z7(u=mU1W6(&_LwFe|tYBWd%VZ-|HZC$veYt^;)h)i2y)}-n&z1SX!88m!9Bj&w@+G zwv-hc&KcYEefWU&W$?t=9{3dEIU7GrtP!TBrk1@agRQ5FN%z`h<>i}Kj>G1l>Au;v z9~FHnx)VX~3K;Vt)&SGU25h}9pICDW43te=g6gu32q!w2l-hwZu`K=l{XYh>Brx8C z`61hV(fs`U_<^*#U#@SlC_p{!`*8JE>g!;{kxRmcCe9F~L+J>%5|d?^D4p||po7P17QU(vg7jvl1AM^m1%}#dsXmJh)NIjS4pNU7f{W`at)7;Sr}zXAq^^CXTa@{2)R zpc<3)Tc0dmk}({5v`_U0%Q92dxOwCi=7t;mIyf49fcsci6*WF?@Tn4Llt-j7^q@TZ z!PVEZ1Wx(PdgtB0!VZ0?#TTA|Wm1xmjhGutOPTrkBtUxg!U7(d(_|>UBm^|h=;H4e$_?FQgV4@y=>mv8i(9Y8n{=YgIw*IxSLw7 zET7KSF04kFS1DZR+6nO()E#ysP2@}bx@$B1JMpS*4nAghc2ocj!No?RE&}Gw%+3Au z<41A1{ujWcZGHe?#O_drER@5~PWF0wdJJH;?Y8ya9l-(@B9y{T8k7RJ1+?=O5|qz( zl%-=jy` z)?U`stgQ0MOEMeFz~DJu(WnRLB4BB{)_LdQ!-xG=P^tQeJotKa{H!ApLPfr+;L z|Gc+WImRhBbsI`v`bO~^I zcCI+!@=9z~AV5fXz&~?Ar+X9bX6<38gMa`2HDOZ=v|pv{bFN?B0({=TTotxIW&f3; zbRes6cDVGjFrItb>u8fEl9G!Ce&A=8eg24vbBzh%op}W-ZzGo;Qfutdt83`bi;HiL zUYsAks0SeKbUfLZ;)}QzQmNGdzcPt?8{yEwR3ZEDT*i1X=eZtnMT( z8Zaa#CB@R(i)Ac5y-8n$?m95sTmBHc#!H`4%!4;-*WBAr_gg4|S-C$11*7v;{m)Qb zp(lr)J1a#mvY&+h(mR}8eCQ<04I6UuU)i?rS&`7RlH4)zADW$t|=zqfn* z)ox$vJ_g{}%7{dw7`&2oEL{)Ed1E9dm6UgM)N_8e>Cawa)+`nNPn7@>xvXBKD?$8m zzf)AMuV1U}hUvy!^F*#f;AqHEzlGEbg>CTu#>~WO?TKawP2UBY;Qe)YJTni8GMJa{ zSf*V|l6+j1Ny^6Wu?7J@7z*Zf!6-x~dbZ{Vpp*r88Mwi>Vt zxC{M$X%I0UmXhJ>q){aPrn-hY99}sFSX5+&C9KuFB463xZS~i9sXtJoOUWxMw?8W# zmr@uiJ?I=<^B;OF6axvev3Ve$f^OT2y_fm6AZ$A1mtH{^(6Rb1Gk7dLYeA;~V!Cwc zpQVO3TXs?cSMjfS@l2z!E@?RSOn4k1mz(EGfG5bg0eDGYTSe{&n>F~2l2oSqq+DkJ?L^!fhWMqtKm$UM37e=3p&dUuI?7m^sJQp6 z$!B%{YmPJrJ3G7KlFVRNJHgU@)EyLLXGhGH@kA)^ebdX#%oKZ~xW@*d!d_%UsIWAH zoW}y_Y>WAP_^_>_Z6|LNLO$TfW9>2DO`KnTc_BvJ5@T9@68?8=rl_c>$GXzt>%aih z$gG#{=;gsqT6#Tdguts=#(rwX=Hz!--J|jn+`$7}ia~5Z zTe6+4n)yNtgjyqotFz+#Z$%EECEnrjc$rwuvERlB@D)%4Jg%&~yo$p-;QIzpI)tu1 zw2%WTYx6;b7D98hiLdN|lj!Z2oc&QtP4D#S;0g+u&Q6Asl3Q>oxj3&t6;I-c3Bj=4 zXLau%Ob*Srg$Dlt;;p~dgm8^kRRVbBLuT+Bx)c)^AHTP?^-&gp%)npo-)>C}g^{?F zLK>=7&iYfBH%LY}+wXsRd3ra2_|5?u_Wvm>GYhyx7-)16d#`8PwaoghGaZkyJm%{dEeqbMmI#%H}3sja9 zU-Vk9@1jg%3&6q3$NMt}|1eJ;AdfXhMxd>+wsu_=BH1nGavfb4HOE7@Z{%NT^bMe4 zi6=@&#epY(dMoXRxc?CfU~ePbUeej_#)Tnh_wTvpKeOILSwNJnys`*0#w#m@yKCJ( zb^8^_9lSUG)SV+qO-WoFHCt^zv@%d`_Q7QC9l24$A`dVg(Bzn21QPJ6p`qai|IK-` zq$Qc??D*Ua%i~SyVb(0rFwi3Uxw|?R1k~+A3OksXRPmXt6EY3EJ?!ql|cbBVaUzP>*F>z5P3gy2>) zvr$KqV{YKtH?*>3-U8TR$GLsq`DY^~znk@mf>mPAO~2o>M{O+m%)udS^~&oQpui3} zKPLCqx9!~t`rdVcySMVfYtUa_8)9 zZlmuS&cxU_LC+(wRR|_}4$yis@Z?!+mS={7N8c3FU%K>@HH>I<>RfXGQqM;BrexiZ zznn!W2?u?M1c2qqzWaGyAmEL!jQ3hn=X`oKHqBCR3T(J4#Bvl( zyxD>KpP9pNOs;a@zkmPlb@Cxy3b&%uzt?W4_c4GH*!bDv7$Pd|tK{_qeD>4*Or4Q$ z%i?^`Vsxivom71*mcqCC@y*J7u587`(acr5eur$x8^9b12?-ay*C*jSdllhxMz~mD zi@rhMmESL+soag(we#d++Ygi4hmo+B!^Nc0gV5KE^BRjTTE81*>W6w~7$O3HH&O<6 zcWabF|4RP58&FRJ0|PG7LkG%rzt+y)Ns$l!{3@+jTzy+m0&}2Ox!A$mH0URD+8i@W z7O8r*q_&92OxjOOlpP zIqvzoDOLe605DOOeL<+<`R~oMyFi70OGrppm`w?r-RGD5;)X(M$2kCIasR5y!&l)) z96>;uJeDpy`tr0bYGg$BG^hP22dKuy;^N}OfF^6(-NF+C=nOTtrd!YQu@X>w!~-Jk zafR~Hk8~&$x>CG(t`}jCp6ReJ3clmK`O)<_oNN7L(r@eE0j_hx%Ktl~^}ols&Y3Tj zw`{pMf;54nXM#RzMm}gSTPq*iJ2t=vNL&mqc1H|;NBlp10I%V2IWg(mVzP2#V*LYN zqyM+S)!oL?F7W@e02@mC6Ij6c?;rHs?R@;Lylg@K{{D9z-JHGARvxx@-M#E{ek)u9 PZUSkkX+J1OSVsL13g5Bf literal 0 HcmV?d00001 diff --git a/data/images/logo.png b/data/images/logo.png new file mode 100644 index 0000000000000000000000000000000000000000..7dbae67a5341801bf7d64949a6874276e1859008 GIT binary patch literal 81162 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 z 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 literal 0 HcmV?d00001 diff --git a/data/images/mystrale.jpg b/data/images/mystrale.jpg new file mode 100644 index 0000000000000000000000000000000000000000..31edf4aeb6c043d680ed7eaa3377e925252691eb GIT binary patch literal 74115 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 literal 0 HcmV?d00001 diff --git a/data/images/mystrale_2.jpg b/data/images/mystrale_2.jpg new file mode 100644 index 0000000000000000000000000000000000000000..88d86d6bcf2d54425e970e4f68bb82bd183411b0 GIT binary patch literal 355595 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�B%#ylfrot8N)3vktrC5&3jGVd}E` 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⋘$6B*tO{ptL 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

    u%ZTJIJk=1EW^>?dCwd| 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ξ<$|=w+4=fhCudTU%kW1>T#amVGMi&vZG;<*3C`| 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 F|JlqT{Wt&s literal 0 HcmV?d00001 diff --git a/data/images/panel_01.jpg b/data/images/panel_01.jpg new file mode 100644 index 0000000000000000000000000000000000000000..46fbdb92a75835bbbb8cd1fbfb03966f2f7daba1 GIT binary patch literal 63544 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

    A<1YwXBmXJ995K>JZC|Os-R5NJ^`>q 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

    _{|1j;h+<=Sn=Eoco*lY2+2Tuj&#=uypw^988ZL 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%0Ao2BC;M}P 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

    ICtNzgoEM`iP8pu@e5Rfy@J7YNKw?YsF7rb4z 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 z�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


    ~1ceRn{j(m2kU>C4m^h?zrG` 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 AZvX%Q literal 0 HcmV?d00001 diff --git a/data/images/sky_01.jpg b/data/images/sky_01.jpg new file mode 100644 index 0000000000000000000000000000000000000000..22f30508ddfdbd84f11da4bb78d584fc70c3cc88 GIT binary patch literal 134813 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
    Dx<2(h39&@mg(L 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 literal 0 HcmV?d00001 diff --git a/data/images/sky_02.jpg b/data/images/sky_02.jpg new file mode 100644 index 0000000000000000000000000000000000000000..d0d74488e7de20a849f6716db816b3282fc60100 GIT binary patch literal 31413 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 literal 0 HcmV?d00001 diff --git a/data/images/sky_04.jpg b/data/images/sky_04.jpg new file mode 100644 index 0000000000000000000000000000000000000000..c5cbc18650aeaab99081747afb748a5f00921d1a GIT binary patch literal 25078 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

    `M%CDJtkgc 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 Qyi7S&PG9OlTH1gA*=;;{ga7~l literal 0 HcmV?d00001 diff --git a/data/objects/Makefile.am b/data/objects/Makefile.am new file mode 100644 index 0000000..0f80b6c --- /dev/null +++ b/data/objects/Makefile.am @@ -0,0 +1,50 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +EDJE_CC = @edje_cc@ +EDJE_FLAGS = -v -id $(top_srcdir)/data/objects -fd $(top_srcdir)/data/objects + +filesdir = $(datadir)/elementary/objects + +files_DATA = test.edj multip.edj colorpreview.edj cursors.edj font_preview.edj + +EXTRA_DIST = \ +test.edc \ +multip.edc \ +colorpreview.edc \ +cursors.edc \ +font_preview.edc \ +grid_bg.png \ +over.png \ +under.png \ +sky.jpg \ +clo.png \ +cross.png + +test.edj: Makefile $(EXTRA_DIST) + $(EDJE_CC) $(EDJE_FLAGS) \ + $(top_srcdir)/data/objects/test.edc \ + $(top_builddir)/data/objects/test.edj + +multip.edj: Makefile $(EXTRA_DIST) + $(EDJE_CC) $(EDJE_FLAGS) \ + $(top_srcdir)/data/objects/multip.edc \ + $(top_builddir)/data/objects/multip.edj + +colorpreview.edj: Makefile $(EXTRA_DIST) + $(EDJE_CC) $(EDJE_FLAGS) \ + $(top_srcdir)/data/objects/colorpreview.edc \ + $(top_builddir)/data/objects/colorpreview.edj + +cursors.edj: Makefile $(EXTRA_DIST) + $(EDJE_CC) $(EDJE_FLAGS) \ + $(top_srcdir)/data/objects/cursors.edc \ + $(top_builddir)/data/objects/cursors.edj + +font_preview.edj: Makefile $(EXTRA_DIST) + $(EDJE_CC) $(EDJE_FLAGS) \ + $(top_srcdir)/data/objects/font_preview.edc \ + $(top_builddir)/data/objects/font_preview.edj + +clean-local: + rm -f *.edj diff --git a/data/objects/clo.png b/data/objects/clo.png new file mode 100644 index 0000000000000000000000000000000000000000..dedfc519a74c84475876ecabf2a54a7ec4e02e38 GIT binary patch literal 120231 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

    QJVg1ny_wBDw+CXBvGJEtB%WdY` z^$e7SpkEJns?bkJJzxx8fR)0OIjlsjJ#;$n&gsQRy~r|7@Nah2`<}fUyALi*Myt%f z&tB!b42WZmVaxRzthEb@eTF0V^OI-*IT;~ZA;qrs-Eae z9+AT)L31~;c1=o}BZKP^W^&%mORYNZrjn06c=x>V6So(Y^HgDd%2D%L>BLKYL-WJe zHBD4(Qg9lh0~XY&c9(n?6%n$Kb$L$XN>TTvTPvcQ?!-H?DSP7Gd$scrNgvwqSr>EO zSrovBKNYXV8M@s)aR5N_)bWE+tX^GPBrhId4L!m&Ya_g<4+-qhcNSi8=N#{=M}FVS z=}gh9%w1}5iL6HuN~yeb=Gubh6UxJyDgVC3HtL916!>spH*at=zTPDlf7!e6$&-lR zyAv~sz}1om@~6$8H`mkYLq8VJC+2_S`906sT#=UJ`@h_Iz7^keu_DV=F(9D-So9~^ zAgac}$l;_=`k34@9kgssJr|2bqbc27*5MXQ3BEBwLY-*g`K#VUief>W{3kUYLU78E z8C_X?A&|!gf*Wd>`%GBBjo=`J7-fSxaqJA|ZFbB+CNtbxe;USB#VVJ}8<{7rk?w&lLQ6bdH31S~9a*Sv*Dp>-9WX zO@DyHilmMoiRA(2RAIUb^cpeCu4cTWi2*;Cw4-7z0GG@lh)cO@&s4~p)nMs^H0eO} zr`JzBk`FBjU9icTF)6ial0=&d*Q?h)eEjGPL1wqLPR{7q+Q;ni;o`bg85z2wfcBWq z>7d%NV~>KM`*PI2CSHF5ue(VVtj*w7+QUbMlW*-`&x6>A-)|)r7(s1?Uky%GDoQm5 zEq*+S)iQd5kVW5G863idZSH2}socqb1wbTz8M|sRWN6WN&g|8JqdqPX%$D~L)Rps~ zisJxAHVy!tA4K{8WFSM~%So?o+&OlLwCa|kpiIY(vIgeEF#WMU46sbI#oB`uX{Db+ zoqgB2*(#=6t#RW_m)$(hjIp;#NJmHNqOo%0+(&b<7E)VKi%eGf>NlL+PSNxpBskXN z!Mzwvpq+nI)BayBzl{S-$hB!Nu4dFcxN^<2wbOkBED7L>CkM$!Pij zc+}sgYL9luU7gkBJqfeg%SUuuejQ+uIc%rEeBxx{X3FJaGa@?nMq3k4?zx_F-ld72 z5v8k79=fclm~+S6D=y||^iL=c=o#WWUZq<;>X*wMS2&CmMPl~6Q+l9roEC9|^ZKmB z&MU=|NKAN&!up6-xG%@4eI-=kIl7}i@VqkzwskF^vFX2hp?)7+QYP?j7Yi+u_}(We zV$P1TI-$G_Su_cIg{{#Dkyr>CVtG9z9E3i}SHHbqwWq^<_EvohBIxWRB6w;~7d9zD zUZrP@xiHUs9E)Y!|Gaw7Cs$ixG{U*a&$cms^l`MKPn(`$N8>Z;1f4VcN-j0 zQ7xy4{HdB*r=*FjX(5|K2TE$sIoZC99SU%>zarN=DzdhR!$2?tf}l|bb^t`$x21o* zrTz>Wesg!;@ZZy3gY@dWzuhViNMhnfw`sq3{jH#Ln6yyOj(TaC@0r}kG}sDB8dcHy(%sF|VcL~U+Vk%T030<@5NLJvUD%?A zCBY=WHZkO#0qqhiFVD{UQ&BsnI-FK8d$|hnpyKhWW$|(?4CKYh+2eT4D;?TBWDT8n zGOJx!m*w!hXi5>`7hP>TxnYY{?Xo#&le1Bul$5N&=wfsD#1;W$Y6!9O}zg^EE<*0 zv#r)wmp=x-J0h^mNW%PlNG0?cK7fELEZmLxCuWH#|E^FNg#jkY|h2P>)w9Q)UXCx%*~?xUjjI z3Ja*VJS{O*d9n|cn-f&$#Ig@Qvv)J#`gQje97G5DtHJwje=3WczB^&_;Yc!k4>V)H z4&fNQpptIZD|vy8@=uk{D$Wr#%g~UVBf8)s&n&}h{J>caGSuXJzv^6-h+T2vAisGt zB(|UWFtZeh6QbF>1eOm~RD<9zvELK-z5NGfqAjO_Nfa=^(d?{+acMCG@KU=H$pvA6i>RHyIAcKAft~3L!I%JcdFk+2Q67N_4M+u zJ6~X_p>!QD#$Zb;lom&wq1uaNm*rygr6OLcs-ix<1lki5T%%)?c12g1GWf>+w`bQU z{~By*@6gy@<|zF-6Jgo#!F>-@>iAIR`9sp_AH?_G@9OQ#AQIYIwHB^f`Kc`o$)qbE z@bTU#1?SgF`&4E6jz=+(FMlrR>p+ev+etyJH6Hu%KxvBmlA+E$T-z`{ZGAX-!$B;o z;tojNcqRR$i=%HAopb=a8&I=qU32A?!t~Oreg`ZM2=%emSs3RV;awulqBdop@O`KP zoLR1Pyu6dz?0o$Na@a2vQ}Skp10&*rDIAJ54xdtq&gjp#%>n?LKig<1rX~N zX4MhFLozd!g>tg^-wgwWDVW=R(+aocJbUw17KiW3%Ql0lHnm90zBk#gy6^40q;^Gj zVIjfek?1+h0UzH(k{OlD+V&F;2;~E1U=2IebV{b@+cl?F3}Nh~p1l0!#w+Ld=!Si& z=Q)H)yT|6ZHt{6pRu0Wwfv%sHt!?XcaiaUWMXvR(DNFCre04e5dd0BZ=Byr>pkpDov;6^#`VR#m2$JbM=3Dgk3*c z3$s)^l{>KNTQC`Jez~@0*iA5Q6p^2Fnkx9#s{N1qxc~-_BhC%}-f}b8p#IX=GR*8! z5u%pIx&V9L#((+sxEXuy>gZrM#YSg;I5qJd&}(T}hW5~sCMhR~% z0aoW?5QJ-~G%@jJyX52jeZ_q`_ugTtbac`)`lI|>^Gn5%Hj9NNv;sHD2bba5I}tao zpur+!uM-QL~*=G=8#d{A2Zcbpat&dfxLM#{rxIzVSQhoB6_R z|IZsLaUC4P%VJM#gwj1?hiyG~J=QCa33>vuriw)W^SSv_H>)8K2EUb+16(G>_o1pY zC2E;&Y1ot}ZmI*f7x&4iWZdd_SU&jT4ysyS4Xj(=bbQv`UG*Xu6R{>PaYD~foNNi4Fn#b4-VK}%* zmh>xqIoWX2gGxa21ig~bAPVteByZ?e>&ysdNa@zV7+-!gNTKUnkb?$(S8&oS=3V9* zUK?w_j4psg0B2-0v6|4)YS>46NOv8@1`^B`gkI<0@k@>T!nmHi>G3N+K;Y_;`1hpV z)?7VZ-{OD5lh#HP>z}z{WFH~T!;poZsIyskw`0-=O zMZ}HJ!(m@9zvr;0;^s%Mbc?s#d)}6USPE6bjNzk9NNQ9VF4fC}7sAR~<@B=p{0qh~ zen~gIoAs*|(Kn?XabcKvJXv-41%YXY76*G0o+};6uOZ9tmx1${dVM{i- zdfUE1YGxm&@V9N*;Dd@ub$YR9UH6)2>xS2`(kS_D0fCVQidmbNH}9{|z=HL8Z}y*g zp(*{G|3ZTQa`BJGBfn^w`_Sb|Hphr|z3G;N zs8K8W-Mm%PO&$I4KcS)oi5Bk-z8Mt?3@YnIsWaJ?u$lxi`wCq^Kzbrqj{m}{$Ab#i zIcuMtES`8*ceC4o85nP?w?9)OhpUl0>P2p9ExEP9GL*xUWsw+)f||ovE>&v&R?$-A z^VuSN3xj}-_i7x`?u*#v<|}=>MDU=e!WUg`dGM2Ik6lrXV@OfNO>?oDcNyAdkZ#*p zufpe#kZGhVIKp!nwUf{qtBb_GlnJ^Ujyw~bKO$#cdqE^Ba<%fG9xk{`DO z_&B`LA%^u+Bwbr>^wb`4ujff{h4&We56OuT@Lxh^!iz$&t%;*~zybooRBpCwF)S6^ z)Cju_an=QuPI2pdP?yxE`}cUrQk^P)j+|b$s68o<;&ME4bM~cVGpprgBC^rSVV%F zd0VD%39m^=UQ2>`vzSYtt;WLZI7zo8JL`azU%9RYD$goMk|pH(9$J;PP9SGZ@2gg> zv+BFKnr|uX>nv}#VTxM~kAFyz2kb@JEa1!5*Q;r>_#VkLSlm-=XX*?-`E2o32sWM+ zAun&XDGTQ|rH1R8=+}|)7#NYac?R+dtEaQSY`~~5#M=bE$ft!O-qgL~656aFtE3Fg zJ;>bqm30$c{D+r;rSdOh^Z88{16n!^W2EsO4meR5gduRrBAyYode!*UM7DTvVNKkL zy-@Il=XK*>9Tv~3j=)Aw#5;&ZxX+}I_8KTwzPkz@kS=R~dT1SMWR^7$>9)vjy1P<> z47P2!R#x|cnR&$1VZHPpJq5@m=L$p>w2xgGu<4ceV@D5)<^sODH_qO;HA=;s1@P*K>WdcSPU5A{sZTl;0t_&qGc9%x}p>2|z#vKLEfzy|y3 zI?Fc5OhNil1vEqJvHF6@q40X|L1t&_V1>g{n z9nlKAga3GG#o&aE>bY5aT>GhPbyhX?K zX!R?iyn#OF58t<@@Z{G%4uJ);UNI{v(@eA*>nv(`eMKzGeSg=XxvT7nK`wmj;t}y+ z4@wycA()VEKtO?^q<5zWW0cfv`iOQL zQ+%LzZqkIoDVW~wUQbC4=o!ztrdaF&!!R%vS)%o+2Nk$TkV%ZQjY%CnC31vf?4$T# z*pO-TTIQbrV{N3Nm+|+ZYevC(9ZrW~n%!Uf@;~n3oPPG?%k?vrO+gxZK||>ON7Grj zHTnMUTYY07N(x8|h_on3$CR3YfPi#NrCV~;KoOK2k^>|pMu)&Cfz6_0fOJji9xxbe zW7}_^-*J5ZgFSUW_paA`r3=aaLv{J-ur*77iTkvqs7-Ce_|1Cdv-`FO2(-mvLGD?ecVROhIdkLV zBq}PXNLjU+#{Z53BGrL|o;?s_?Xp{;R*sxC6Kc}L(tE(N^`{=mYF?FcdMnn@A#RBE zH@}DuD-e`hpy_yx3tt^5{=$I!;?8na%}hM)2r`h%Y{!d>gWwZla@?~Jy3htJx`&P@ zCjRb6bdyVA^k~Px-?xaYqcGgSL)qeibbmMyRCduBzfj=ASGzZ?EbdNctX&;E(5LUX z>gTktIN6$hveq~FpneqAw5MgbG&uM4A9KX#9Z9?FK+aw{skq+%arYnhmeJ^Ym({O6 z!#YdX_n#<|WK$<-+u#vm6ZGLZ59L`5#cVy~3_I?Z$4k`ulYVr6)&zk4c?v%O-(B&8 zotG*GU%#9ZJOQUWU%pBbo`Ybb`pR1C){<6@EuU&1>;g4q3E8d>XhUG z0Mz;;2Vj@=ILtz&!UkeJ4`?0~T)`5^w~L4rvMWOrzdA*#<+dHYU=c3*S5Jy5bEh=-uCj@f8RIU zN4{+4k}=6@DgcS9v69qgJDl{EOhJu|^l-q``9!gdI!t`Y`DVq|AT#lg)`AJG0AHf( zX*+il5^DCw>1VlI_;(maov4!8K7_jhhI^Yo@< z(1Q1l9l^Xps<%K6sp)Iq696MX%gqX%5iDo<)S@>2x0SMn{F7QTIC#n|@xPE@>I4)u z=`i(WHoIVcF8uOZ-?vKdj?92({>MCjmx$v;Uqb^si1lZT{9bWKsLCY%pDMxSlyjE8(=bG zf9!0)2mE+15$aE;11pm8Eu|enB=q~cmUjxvQ!Q@KctswjUWL_99y%?K*b~73z3wRg zRd?t!?3!xxzjOIsg4TgRa{eS$pOD=NBm(Id-K1i4O;3aE-bf9d^x-pkStm|DJt4V&c zc>Hq3v*l*!SBIA9@5kETY|Lmo}1_|DE@kL7QV?}Dqmhf_kSt{PS3j8j3|IU$U~Gh?8NyRaze-U2`r4a zdFvn1bbJC}gY({m(Q*_~&|mwWav*1`uH=$AsAU4vz~o76Y%!)?i;DkUi>%RiVZgy8 zK6+^xr#+*T6Ku<0Rs1%Af9FymN0B%my*}d;F?!s}&E#?Hd(*O}o?+5y2U2sE9?yu3 z$mw#tb45M(t9e{rrmz&PI}VPZ6_yGX#~lPW?A`LEWwkz;2}~?W(f$OV54C&aHUDiB z;^PcxEU3Ytku{+QIQKE+%>{%T^HxVQ+hbZips-FxUiA63jn#>rF<6uE&pKL5$Y`h_ zZb)>~pgK|tvek8b6%y+Bzq9_ASIc>EN}5Yx@RJu*_V{}F?peObqvj|{a{fkRN>-x* zr=-20Y-{wJth~qL(jVoB)grvhKUZpX0nuqMCV`$)BH1nrw%SeW--(1=L+8bZc& zMfjHA4pY27*?LIYJAeXGQ|GaO`YS95z&+$;LddYjG2l9;nckT~Ab~y}A;HxAC@S(r zA^%3T6RKuKQ~HvQ|1y8d6zV5c+cokkLClC_4wr2!XPzO0C2C7#U_(|t3s;_RN68d9 z;CvX5G9-BvOcFjU@S>@eqFeV~RP({@)L%_!6^){r8kpwlcI%JK#98yn-*T?V*dI7gYE4>;T)wO;^PK}`C6T4=K zFE2ydk4Uw30`+xKgGM&MJGEwXQ|A=i?u${8hcO4f<;bC)Y>IPD3X%^mEb!=s9!OvG zis_F!Z&6wwL@hi@4R1cWvIXXY2pn5!Y#!KUH#PpEtQ$cH_94AaZXa?9GAbwV!0}c4 zSyXeV=*J_G`Yhzsv2);YcUsf^TXV&eV<3I4OrB%s_$V+@oqfQ0Yw*S94k-#1v~4gP zyvjpM$_eCK5CXeW*p06$Q$C+IPG{eUg>oLbeq8dsoZ5sIA(Sd)(Pg@VA3SOq+|BP? zvK6g&$vm2l0QoXj7NDOhJ_{2{ay_P%b^a5BSn}IZBF1L;$D+mxFHCzH=oy3^J3n9l zJxgo^3wF_?Llf*1bi-kk{0!al(sy-JusL2H&YCFq8+BDF(h$E71$Te;@X7f>LVFz0 z#wc~5+(<>#PRnFY|ES~I856rBz%nvwur^I_ljXmLrYH}`S59PyBID)nhtA5kEUd5P zLpuHOr>otAU@(LUM=E!v^c7LEeFwqQk&!zQQPRE6k>Af$){9%mF-d*SAuY&>^(@u1 zt1h6HrfB3>|5N;ClhR|?4}T4APBtOq*obH^NND09LX9N{-2dbq^LtSS6Zf>HND%8o zX`|t#K9t4M2frnsB_yfjg?NUHYh&J9lJKgnGs!CPlL_I5rCu<|ma}@*ZCpY0QMrqu z!0oNyh`gNUUX)GjG0k~0=d4>YP?$+Yno^xg$Qt&be|<5u91u%zl;f>_y$jre;!MZ+Rd^hO_Y!4+Nds!UZV>-6sucyH{`v4&$I z#*el?YRAS~4T?_wkcjWD&0ok_s}Fi%%`#imKo0kjX1d(K!Cur(J;e^3){ETaF0925 zC)~M6hR!ao>}Pvvuxq~+m5@`JGqBAV@!)B@9J3si)ZCLrkMbcU6PX}`uDgy?K0_dTJ10E!Chp>3T!2uubSCW zreU;N*MP2z+(ovm~oKci4c|*@%{>=PfipToXrhwT8f#Aiqrl zMDO?UdQQi3FVtF2wrv!W;Q?C(F> z$Vl1wQJ{%1nV6Pax=p^5K3!emx(=rO@rhTs`=;MQj~T-l-%fX9-3+zoyV0#0)Wz8k z^WAGq?+ax3KoK&g$fljvz(C+2_|$_paq5gp8{wpdfg{ziGJGa;dFe*EkC2|ekuWHp zy4rHiO4MG+bfo6dGD&A!o0yQaCf^=XSLP|90bqNE3noC8a$6sy8muTvFi5*Uf$LD4 z@0QarqT#R94yWVfwErSOAW*Dd19hLeZ}s;0{)5ieo-m>P7EQiY=AVF(L(74|OeS(U zVuc!XhLoBJFf1HBde67xV>UM(u&`9k)Odh{XL$dv{oYkfStO7xRk?!cG}Q>{pw4EyYRd1v`}W^mK<;8_?9t_~05sLO$Ou}=R{Fy8^EmMJE3&OktM`+X zTlkqMJyJoDjP#BA8|yoKJn}t%)z(I`+~PZx=yWoBTm#s^*xT0TO&-7TUisD#_^Pt z1bkxjhxyjM6x@TLno2eCK;1l!5!!ajcp%l_WNrEjEa~5DE7G2D-gZWc{fNRW7Dj!z zmPVJ4uXEK=TUZ>+(OOL2BNQLGzqVrIwRI&W_Z8U$1b}yWQR=PHr%<$H&&OaySx@Rr zS{(U|Um3BMituL+_0PaBF=DM3bevyF(0e@wJg07ACQr~cfx5!$s3qP>WjpYz&t+r& zpM3L17?PNzjnC2O!nn!tO2HHgZ-dEx4yl&#trVy`bJ<%sI0LEn3sAcCtP)x>>IyA? z>#_aB|KMb^Zu4tA4PfX+T6LFP|Em3aGYg zR=mNlqh;_}ueby+d)t?)#((1G-C>+Cka5(u{z2sr5!gT09($C^S^u)tpLbH~adSkA zaIA|vOR2JoWlQ1ae_yCyBx?=U>UIH5dD*U=pt|gx#^?AZ1pHJsos5FS0?b%=Qxd~d z@GT?pV?{D4M$3@)nmENuvd5!sYiNbsxfc8uohiBZ3()Pu0a(9u+-B{pH{9BWac?Yt z_G^5}wu*}P0-Wd{sJ+go^Xm_I$S-CbFv6-iMdv`A?I-~U{hl>vEL!>99_uMwTiS1? zV!@|H$bM6IYaqAnjHOr_%gip=K|L+tt%oB&=V{{hS#n5Ny`PsVv+l-)_UA~Sq;rUZ zE3CX+e&LhdKn89$%WR`eZ!nZYdKx~C0l(08K`(?l>)+{DHXR2LiVt5AIQ>82s><#N z{HZrIlov|QQuH5DVZZerJ25|RjkJ)?x{3h#QYZ7er*z}s52Yd21Gd)wS6sDtraCv+ ziKdc+Ys9pYwQDrKHKltB5>s~C7t67bNbMGWg#WU4MA`y!vGX zlN**cbL>hF+Hq?g$6=USnZ}r#+J7Le6a=p=H^Eb^H5WP@)pulBQbs$sXM~6sHUSSb zK_dx$yg}NnlSut7y%8IMEF)}&f1m?grmKAr&LDs@^35vV@HlZEB-s*=&cO3^owf&j z(lFBtAp>P6i!8)aQD!*M_2U8f&ig=3I3jEIs)UtE`?zj9p4#qr!)aqK%!%v)9T+?j z0S=-ES%Nb^g?;IT<+zfc!Dgb2OK4d<}Z>|{~<8@ zkkMw^LNE_D_eF#m-dcF~$JCy05TL-vpeIDx2WnuWaFy&9nhY7+_A5hX7zyg3I%rk# zo4a{gZ692(Pa15&4euo{{eukkA}`OU67EMJPrI704SKn4SbuArX2F;im|#+G<~#FUmGO@JA4v(e z(0-lBf8x<9H#NgQ99jiAGri$zFypD9V!Gv;I~spF6iJy}W8g%Avd<$c$A1L0{CfF< zq~9Sns~lO1w#8tF4@LQ&C>!=NeDEDKJMoy87C{04!hgC5mp%uG`!?zk` z1^-3GP*S;LF^AT)QQKZal)xZobkwwlVM~9#JzzLih06LnuQCZpv_%7cR}Ct1QOt`9?+IAX@O zw5x;mt&5A-`;s;~6kZ)kH-A1($`yXx1&q-ryTC(B0w;cPm&^BR-Ywc{W*B3JOXGzl z7}~w!zB2Dt%tsuxG3G1uvw4rPUA{EE^)Uo@I*7nla_{*N$8kRLqM9Rh^G$<)RIX<7 z@{NsVkE7hjV5S;D)lf$r60c0g@v0ikR3P){P1xT2p;!~VFopAUa_WSgz|eflc$@{d zI~v>DP{6p8?lu#Xb?c(?*|>uqs=EE_qrwUPlJ)yoVrUhabe-aKQo`}V!Zo{@*~$ zX-*Wu5aV$S%Nl%Y5R+2k2Gz)~WwJyU#Ua(oBWX?(b)2=h5boJLd#0b`RyMnLrl<@; z0kCl$!WHeiviSMxgX>|U65KY4eNxJg9o+`qXR9S`@0)7`lnhlnH)+WM%W1xpe3Q}a zB2ADD*6$n&(U@|o(UDhIUU5Sq`0;fQZ4vM?nU9+(^?wa40L3L}*(Gf!2gwYUT%5K` zAR|Sx+hth0aX?e=TajNk4+L(YUo5zwpYD8(IMN|fT-q}II}6`I9)mj0|2{bNOQcz$ zVvlOyi_gS&*b>|CAx(>naP;_+Ze&QxM(GvR=l)JM3|Y)`X_>x1IQ6Vl7;~7s*SVtL z59J3;Zt+FSadKEKb-xd){&r8pG9OSFY5i~UM4TmOC*vQKI4(pVFoPy}iMG@SvwoS> zd-DN_7%zQl;@#VhXracw1g$!rpqwTGZUwsDLNo*(2eCbh3F0}mc&H$6h+;pk1D7B- zGOUBoHMqYGs!*i2NT#-)EIC;|3s*z#mfxIDdT4*WW=50H_f6E*#aBYUKKZ&TsbcNL zsoH$NY)bG>s3Pb?5#QS3v_nSRP&kaKXQHrWXPpZmxp2SDpKKetY2o0cHf1#KSpqzBrC$teBs_SW5 z(n>n7_hv?+b$TqapJmrQS%0=d_e`}L?$Lz{MK+DycP*O^`6it5zh3P16I>ufT)C#s zO<>OjqdF_q>Y3uM1FwPBW`s{fiNs zLbSLFFLIws!#u*U4-QHh$B*HYW#ffT8Lf);MhXaXM5B+YKo$+4lt(B%3n{BP5U<@if=<2J~H@A{$)ssCZ@4eq)DbMod0U5zV zr!aYM#&V0{OV)|V%82r{bpT$K<61_u6y=oG zhaCxUf(E@Ok8v2h9BR+9KwUyI_^1ZRB8TN7JzBd9=?VmvT%h(&SQN*TJku_-3G z)^1w_DeYA1s+1q8a!e7ERL)W;qFP1c#6IY^gFIqf6o|&GOKU-AioJTlY}#X+cD2pQ zvYxTutsRR39YYNE;rt{S`gT^^ZX9q`vf0NrPwF@qh=4?p+lz7 zXK0ZRQ?+YL;0dTfp*+%qmPxmkpI~e>0?;Ao5BW3Py%BF{UMHlgYOf;`_73o?{#Lw) zf_3N4MkTFR7P2YzzT@bo&xPu1_IswVg+szDoBiH!nB_IY;oJ3yr!}+c$E%$XO`n~yJd zJeP7(qhqSVk*=TNiz!`r$;$r}E;}V@A5;V6?(yV$JG;76-iH&!Z|4FBQp$(B`9FSn zft}jxvjDlxdQJKN@`MgKa;c9z6JH#vNTj$Bz_jCQp`;CP=g*n`k!n_c>`6)}FK~6! z_l3BXhrf2DHqM2IU`W@UQ;v7lgyqo)=oO?YN|ILD%E8(!i%6Yyq8F3;i(6?**b_@L zfb>dRJK#BvQ0N~66gP%oc)g4F`e^$L zKJVWC&cNfcz*}mZzlWDL1yX`hOxUQTnsD|3{$H4mA?z2-Bk+PBAd7_3A}E2y%T2HQ zzwnYk{GpIQmoHYV`ALyKkEi0I-bWtydV)+p{kh;){Id~2r6<h1NG#1!t z;tibZj=>HIL-V8TscgFmpn_Kr8K0F^d%?z3nf&PfkrVev$7}WZU6|+s+vnlP7ax6f zs(t=p)9-H`ES&zs_QK;~m^(@y29=zR#gl3mubYS&JPM3gKzWX=OK*lg ztBu+&4>}#gEegS$RK{wx%sP7pmANbPF;kMw%Oz4r#zDw zkAUZO5lwBk#+cuCS&xPv&yWbWcjr$vE9U77-BDePd}!VlE~xAt{--stCIAQt36?Y1 zTj>fyuHMRk7WO_LF}87(ODn1K;Ny~XsQJQ&sqB~jeD%acG7Vl%y}V{$tMh6%BBco- zS)OoVs-d=)MQ6z{Z}K=K86v489u`FF>PW$BxgILk*2uWFy85`y+vHacW0%-Eroy## zz*dg7gL`|6Pg9}r@aA=o9a;!eW2pDYG1;3>@pRK*@?J!2K$=N?!TWuB=shgfQuR{2 zaQGgviB%!I7YPi3Zepsh4UG}F9Njw1eE?&=KSt6w+MDepEj|4YOs&-zuS*uM&Wm}n z^4?chz9s^EX`l@QkDo4RRIfc4U()H|YrGqhlFH6a;;n%5*+>eFu$i=_eV>SF={0I8 z$V%PTW`n`;wUfS6N-euidoE}<@7eI3^*<-wivcfwcJ0VSeJ8oMinPvwjKAgBKtdNf zPaW=+Y#I16ZdD(zDSV;2&kg+n$>o=6ZuKGxD$YS^USN>hC;)KV0{F0YBP^?h zQMw?9(A>7QsWWo8sMbdtV%aoxLs{IS2`Ro^Uq1>kY37x#XQ|=^2nau_ZyWZ#TtwK~ z!x&tL5Xgvb=V9n}{3ey@I2l>nEJ%pP z-!7u>BFZXuMkVXgBD7|fmNeSOa0J}H<5FPK-Or;KS`<*W<;j`{zN7lE-}^G)Ind*i z>qO~ed2&;rxVabNqn{v&R$16;wATC2;~Od{@}QJbdB{XDN7koHgs(T`8K?9eM^YR9 zgCx8^`@^>;EG(-||3&?0rHdd<>+D|qJYf@ON4FXpWjybb@LZC-#42n-S{sR6_oLvC zu{Gyp3+9w1z97AqdnpckY|Fky(#0+Jtb+s3Q-8bYx$%<>Z^gVe%qYB7#GTpQV-i>! zajZy3YC}yK*V1kNutqHj2N#sAHDd(w69=afV@BF)N`izbTQtRQC{6ggy(8lpu(N%X z;-DqK2Uv=GR#}jSQ|*ElPZ3XizVcDMeIh7gklFdDG!y}vK+KufcUZ+IpC|Jvt2{jAIV@m+dMJKD9|7EHwydBPDTt#tUHA!{`(f02 z?OMawsNnDQ3DxiHkP7+N9_wR2xK7wbHR@ebeb#>77{P?=_$LZ$4&H1NcRsPZC%iai zt#Z$v*pbT@AiXg%)(%#So>b-U!c}i%r(^=E5T8D6ADWM8NCy|KxgFd@nBT7CiKdHMRRL{7gw9%R92(6Gxe$ygj z=iW=G49j)54Vv4vH|G?S!-xm@uksbzvpz`Mi-`4i7--u896rCdcSdR$X}L}^8NeX+ z1_(5sPs#8J>dm^X+x&}7ko#$X+&0-tV=rF~%YWUwkQR4{X5bP-Suq=!72#{e0WuY4 zPeKG_=#^Sh*-hRI6*(=!lv&*-pg@9@{@|HB$rqvMf{NBV)_~<1AVvRE>%5Vy1tM$3A zRHnocGFBqf^c5LDg16NHP1OJl@aBzvwqMPvGmNUq=cj<^|5n?^ax$BJIMy*CqX2$j znSu<>W^>(HI=P`l;}i70EzH_ur#g+CzS}eS@PBt4HyRL04IYgg8v~r~wWC(WIJX~2 z2Hm<0v~_3eL}=*$!>-I6K7c|ilch*hg-EJIhA*h6^`M=69%P5@4E9X-{lQ{AkX+q7 z?cfWyZ(HH97F5%&7tUjc27y~C# zICgadhp5yj>M6hU>F$(g=0g>0kK|8!n!;hiOe6l|`2>Qfj(d+D8W9{}(do5b=cIMk zipUW~C9ZC|?}2QbUVGk8orQc`+jQf7X?CRNxbUsE9#J8+xLeD&mlcEd6Z9Lxz@>@6 zwKIkUX-RrxX{MJ7yDwjGOy}~8NoxZ6y!RKChV#)UyjZNE7$!Y(d7HOnX>-|{IIg0b zC5qg5MwXNCpo1vaFFJlCHxwM|h1!K5!&mz%`auqC!?OW_%HSm297EFbm&4SnGcg>b zI&Y4QKzq+m38miSPq2F8dBu*rwj~}xr3HSfJ!9fn_FzN%CH8E($N%*FM7}ROBsj)aH6g=nKy^&C$h1lJE0AHP zAa+wsP=1G|V(B&=bbc{cT&Exy=AyZ@ zU)}uA)2nB6y-#uy!h!UC!S5}7{h=zSy)>s(>EA(k-_n#|eL{t@R zP{T+mF^eR<JZ{$+G|~%4la(HVo-DQD*F~8={Mm;er#v6EXy#m)@G655M+e*SsRilD zex6$rSm!i{o7KY|ML(}l)vypNPs(w>^jY!NDP%6ZxKuUFZMqh}sY2fK!~hiyQPV@>8Bd-|24BT?n_!#1z}wFj9tDT;6Q zS9_YOX54t=fB%tzYIm)&U8$?B&;aX_15k5V=;uy_yCGsPK39s*e3ro;oA*U$AyXTU zP~r;Z9rf2JyF=52u}BtB0v4p}asb6RLi1kz*2R>7+8+17U6fw7WtfmrZG+v8n`$`a z!0yU)m5l8=h5O^nnh5lma)C4?8fm9h7(PWS)X1uMO-&Ms_le{BdUt2NQji&@7NIh~ z7@}R`XrWVHjs8a1NKAZiq_U0t4 z$hqZ?FYCrjft&mNf?L*9w|6c;YH~2bPCo^~rSjmzH#W;G4QZXX9*!H*$3WlhV#v3u zv@Fb(In2xqpcCfT;#CT^$D7HqTwTGn`@fmEj!^pY+STYcEwa~&{q(J5l*?SBHd3ua zuPNs2Ps&wy)fo8^VRxZ~Xq+%l^rWXNf)}iOCdA#dc2Kr68X%LjG+z&hLkQUUnNTe%Q?W3x4Fz85`p5Y@lsXO{Mks zq=7HD5sL71WjKvx9_4HfJMg*#Qy6%^jF2MdpF(e@q)Wv3BXzwCROZflm$*Zr+-XoHIAOhJ>riYuOxPKr8~7?f_Yr!p?MuR5kXr6jeakorxi>qn5$;r zL?EOrfGR?+RE>|Ge9e;A^y;ro2j2+i+qUeYPGSlriLQxXzuprv{_S#YZBZ^|lz5%! zQ#1)Kr62iRg9%40Bs@OeecGbLD&@ECjhTvc_;yX4OVd6Vqd98KnvoZced+sY^#HtD zt_UogX5nSTg1$-V*-q%el1u*@XVmE=@@|OxQjh0EB_+(}S2wrPl{by3PHvyF@aRl@ zsEbEFx4pRXO_!a)8mTKTn<#D|2&)Sq9)&@+tUa_NMWaik9S7Eo{YlcDqGueF*HDxALv~_iu^B&g@F+`VaAu)R7t;9 z*f1)l{Mv)V5eQu8*v`v&!jdB#K)0{+WY}*jYh}|0*;R7qaA|HnHwmJOFt{GXIafLm zucX48YQhpNjsWu7kUJ3JWCf1vBB|ypo2^Hh`zgAaY3(TqZm?o_Eq+#I?{JrmQ@oEw zOd5Eq*>+FJEZ_{kImqo=*7AMR8)dEh)N@>w=5`s+DrmoNsX-ObJ%0wNRL*Kvu63a- z-YPdA{B~La_c(IO@@X;t5p~_El6`kcR zhp$cw9Wypt{zNU=p2g4WFHV@K$((+8AY6&)lM-(|u zm4evkZV2%ux2xE(EIaG^UcS?=J4rW#rqXsX!oN#?MH(=8ONK@$a9F4Z2fWbkX`t~E z`LphljSVj=;`cq3O*ez?dNAZL2bMbrXV`aKd!EpvrfZiKyrDjFm=)_i_!FbAXEKj2 zaV)afiQ{=ySRdEN>weY7NBUH$*>=~;3z5==JDgRyOw$|m(nJoKSI_#1Y+U5>C@T@9lzQg ze@__z9PSX`tc+Po5Gb3->IE+{o^)QOCA`~(S%2okFAb*)DDrrN10TSMUaURf=e$uR zimbHxV}%vq(R_FP0|lT_Dq{+>}B+ig&w&l>dqT7Bt(j^6;}s<;}(wvJF%tiv3%|icO`U^5NodFn zr&#B}P&ataWqW`RXr5HaJu-Q|!qWhRlvt9vO;!|#s*8gb2S;ImLI~gbjP%*jOP>VC z{to2y+?M@lS9mhPK06&mTU07tei1?>gP6BPIT2ea6#WiaohR@4=hfJkd@-mL7}*I< zX)am8B*^(;D@aR_=@f+svI8dbe#beXBZ?6nMo+XJAp6uZnTeHKE0x*K#ArMpco*I& zb=-!WX(e=g>F~TCK!ht@K7Gei|Eq)2xgxVh7@yM}=bKx9;@)+OX(w@bbh()9mfWY7 zp1WB(i^1$v*mXsQ^EwOr*n5kE`Ok(#TQJvv?&#W58>*Z1V8!A@E(Nf2>9VhOl_>D} zjuEXv{pZ^?w>3&(On2L9V^-}0L0{S}a3^heA)23Hl`f1}y)&=U`$W9nQ-L?w)W@Ko zP_j1qC(l1^FTN*w=#S;2jl$ORtR{o1&%1$-tc{?%XNwiKl9oKDn}Zvh>5?0;ka1Uy zAjtCop>iir&k`Y^o4vP>&m^jg*my!#BaVNjJSLGW!sS(8cWnrnFws;|rGjf((!)4g zG2h!R!5Kw;FN5udMSasf<%&3f;@ec~sLy&QFwT$>N+dh=>j`#L zW=GgL%ta&`a^6ggSpA)M2yP?U-F|Y&5WBA46zxB7DLPS2PF+2*! zU;Q)EaY-XP@JaYD3dUVJ@%P{ea%4AUP^xNISz)@oF%o>q5a!+aEwcJ+sKNL3S0e*= zzI!o$DG3bWrk|LAv?p{m{h$w@VyWT3)ahdL+?wZa4!Lh+?p?$s^=dT}?w1e#R=#Uh zsK)!7`*B5Wa9xo8{jO?8uG7Zxt< zhYQt52F351%;4%yNHxd9naawo%Y!Hz&-VYmpnj!NCvD&F=O&Qq5~LLggd1al95d(a z|HXsV-!E?LN)!ht=lcs`FKJ56D|ZL&B0|1;NP%1Gt_`T(nN@iAJ7;6iW*u8~_M-OZ zjYkiJMz&lf@?GTJK5U7q*mB!`p6d=M*xGr~cwpoTyjrUdy3%i64 z())|KVsvE#9Br;0B@ctUQRa^Zs0sBJ3+O0UDy4i8<5S*ixzx+GfCKlyz~)XrnO{NU zI+jVdkZOO|f|ufD7RmPAFh2QE&JQx?mn!s2n-vR^!E8CTn`ks5!STP3L+OXcmqCnn z#<{NO{w=oFOHjJ)_aj!5Yq`uR5j}tYesvk);xRfFvT}SKd26aeR_!Cp7f-nBFM`LA z`|{sv_8i+teEpOSMfLZ0>bCYO4UQ1D+P|PVIkbkUZ9WJ8x2AW&?gYnmN2LQ`^#MDi z-Mx*gym31qMrV!CgE!TUF~8t<*P{xZeerXG?uPx7<&p5h2ATZ;msgp>uQblp)pJYPV`N^%rbxYHy~i`fPj=gi!)PB?p#T6 zz8%1Ez#m?ybU}_0ynUudCl-!0elL@Mlj|S1jTL8kll5UdV?BxwM9Gwpl@#fv^1NH` zcsI}?X$oE{e3xC_g9l$41J|STH~wB9byKthi{M&F$d%Qg)@7R)@@X^ExaFnFC4oN= zI#q^thA2z@*_LG#iLasSMBb-57p`SiE8-bmaPeEwN%8*x{%CD&Zc zvMi=LnER@mb#sNmTx}Hg^5?31Cn`5f_|!{O(e9a}glgt|c2)}b?;wh}qwhRwO~?T= z2f03619b`Est?LNyqzxkG&`oe_a5}LwLv30A*{HVz2gZYA1f~i+1o-W99M= zGV~7YX7;}b@ic#CDQ*DG*Q9j)%v3~EmxT$GX+*R?lU@8BB|G}+DnasE9_qj65sJ*p zpBvP|yE3nL0*YR*)*A(OB*ZtpTb?}05q-RtgM+lhHWI_t{d|lVf?JFCB+h>EpeOm# zcO@UQ^~75q`&OZCF4}&v2%3ma3FcaELjPfjFuw!h@@h(_t2BzNVHLVV7hlyD)JT^Z zw7Z-mCjI?(#s0PW`X~)wr9$ji4D|;roU(yUkXb}}M2+&Rq$iOv_YL1P3$-Tj?BDx& z8@T|%b{wotzS5e67V3WvoV=RHcYNZL7h3+v6fTtBOfbqT-1*M>yFS z515h zCbnBQR_EaC(nV*K*@Dn(qr*!9U1jfQj9WCw8`!|jEb0)zrBL9>>37!#vfK~#w2gE_ zMfC(cdH1yGZ)!do{I|FIY|pqCwn%5VqKLs*ej2tsSTjFY_H7G}l_~U%3?2cfC!RI3 zG!|1`BIutm_q+Ub*<)`-M@hxy#@e{@I!gGKG4b?XRCrdJJDtt((SORL>;+*PQV4nIr2US^4Ne zqG1zGiH-E*>pfP|<%Y=pa~IO4Rl%ZxS<^q<_c6!N`rE=4Vm@vc|DK*3Z&qtwya6 ziui458Q*-fgCKBD3oy$;hE5K&z0NpUIrI~lB}Wzg(h_qHUNKN)vD`i;( zxBEK$Q}k_|dqrLE^4so+zj2oQTdz8e(AsHJd?F^U_eJvCu?JdPmii7f-}><%5BKrQ z-;#@3>^#^iMalE;za4-VZAH!PZpR-$?c}K69Wvc6hfB7@+ak%)i&Zm|8GSV#FKX-a z6AFWmMnUX>l=OEqg_r0s@Q0z9*8_aDPT1$&M%X zf;;Qm7nO0_F;h0z7hZURsuH6X&SzqTX zvt8m{V}dSg>?kb$`!#}~12v0F;b@$%E^w`(gF`JpiI4}h% zt3bYqMxh7*l7!SAv;415(u*fdY{>O<=*Y>}|t-Wgsw{CYeoEtnTmX zJ~?B58~F6gv(gAK!HLR(Gh%tQ>G3>t6F@l8e|3LO3Mc~MzTtmiZ1_&#dd5HP5nIW@P3W zn|=mgR`KnbdyUdWY!G4QpOtjc>+1#;U9%3Gs4_eV**+hz)43n_^I6x zc!v!;Qo}GibdvTC{zG-QFx(dt>0{Hr4ue-17L8c;8TRYzy^f1#uo(`ZL06NW;fGXZ zW}1k8z*l#5vN@|4+BX8xU9j?>)}VWV?wLUJceNfmEt0B64mS7iyY`@~h*cTwE7#{_ zBRW~fZVZ?b06r@U?4|<0qwV0%eR`&HiGhFD{^SS;1P6F!-?BY$H&8z_OiVrNJ1a7G zrXIT?L7Ce^G~W)v+1mJXbYj-6YN{_E!;^Rs1nc;Kzu}^}G$TzO4{ctZSCp ztWJPobqK^j-ddCer1QiXWQ5>Z$%DJ_OE270MF!~yfs3y2p=3Tat5w5#LCXf$v+Sz{{``YCr!Iw@pu${Dv zZG#7J@nuJ$;u5-I{Fl~pc9R1%TLQsAf>vXLdn;W#a1-pS2Vn&}aIKz`uw3FgtS;_xOAh z&~!xR4vE#1J;d-01Fj?NeW$I&-oGV2s-o|jJ)e=-nT{Hfd8R97{r{)2>vs(stNy+N zzh|XA{(~=n&+~aVzPu9X-hnT_a(&u~=ld=qRVBHH!GTKJ<9Fc8X5ywSIn~~$Q~PtIwEO+QetD0cpD;#@(~&U;UCc3H)^9rjbz zA3Qb|${CIdi2jdQ`}=@!!~N}nceReOjI3)(eYeKa)#q~*KjU2)^~#j(E1#(<(&ml( z=j^_Hw+1S3T_-bwL)W&m(^|iC4@{$nRT5T-%&3FY#k0wXC?w!x1|sYoZ9jk>fH$F& zE+7PG1~Q-cJRz|XM88^z*QtiFEJ*y!IJs2V- z!>3N8dfu?Uvq1bz`0hkjDY$m!41z1%d2P_$5$o_7Cb^USnQ1T1H`%5}u4fYBPIaWL z`?tz(s8}Gb?O2`-1o64<*^bY|@s53HWG`m>V4#-htKct--5v$Pq+PfO7T`7PmEJnW z_U{bT=5M~vcMnV1{r)7x1(QE`_w&C4h%1ejc@m(Vy}rsMI(6=L{(l!_xnT|OkVd%c zb#^bFox1z3Y3s3F)(u-ZbG~NL22{^y*7oze);=TUApVRMnemysS5}ev1Rq2L0rGe4 z#$A4?l2plbiYER$Bkh7Q*ZMdUzzKtsvh`dE#Q6JTA?@0R|7xfuF?Qrg&IGzRN%Gu@ z52gu7@2ZIZ55D~C-2dG~=H2-6-RtY{<)5&>6uzwbmEVOgU3F6zc>0cxnau9(%86aU zmz4z36>RX_j4zbt-XyqackfQKhwgm2VLek2h7Eiu(hS%mCbs)Y8<0sZbQ8}i>=I-A zceIwn#05&bd>VVZGt6cXT&U&6l&uisI`{^yvpGp z=KBq~4#PlA0G0vPftp6mQ6z`h%V})AtK2z${yQu3s%^yT`pyEOhk3qiZ&a#iIzDIY zu1wX+_IEee-U|2Uf=~xe?*c+ffLRR+*>w&K$Ytkr6ddO6z!-MEGaL3Dxd8UlII~V1 z;1uUO8$9x(cz({F&;LVg^Aw<5B|Um@q)%fD4nmy0Dg>Vi@zw>|<1(7je;kI;`XJA7 z5c|MDK5O@#%RPSJ^T3^_uqT7;ujfL1{@~CK>e^Tkx;UAFt1+6$rLC zxabJ$I+wq{0-1ICVn*VssgV!k5C0*~=j;3re6EZg3BkF(M_=AQ{(g3*#?P~Ui2cL% z_`qk`f!8zpKt6b=5&IXls1EXd=0{X@i>elJ{*zTRXF6X9*Pm&XDy*x9C44o$+zE8w zfzJ+He<^(Vfot6#?)%@(vpw_tcJSp6QJ9^D<4yRoN(3Cm{m(FZhM(7<^h1z_mE_AB zM`nq+4nMiQ@=VyX`(DJDtU~S|#O`L(sxv$KVektKzI>W{?Hl%s?O))th zdrtl0{>+|H7bJDm6n`YY$KnYD{M7;c)7Zyv$mfx$_$NNcNK&pCv5}ZIp0BmD>6u`- z^($7(js=6Rxb6u*jOGWyEeP*@g!lgV`RBJJc3~~;Gg<#1f^-}O`{4MEY~5lkfN)+{ zviiVhJ^dJ;s`%qyKi}h#tljwe|Ie_8dP0`QVWfSz|3P96R|KPYpI`iUg~W8NIZkZ2 z2@v2wn<7(oh&;vQ|L%&D9ia1fepRYGlq0INfSefy!=}8k>^vKm!+>fPNWJSd3uoub z{%1O6Fwdd-nRm9Py`yzu=lNG!t9KI>JHOwcvyHp9aCa!r)q8u_`nlFPRngGF+oO?y zp$hr!Cedbr(134ss|>SHBJfiL!VxTvViKZSky+hC4ok4?`$0f-w%6nOstKYosjD=u zcB?aCa9Gwl*P#b%#r1Ytt-}P471^MjVLchXtdJ6_BJ4l-^6Njp-TWC>WvR~M%W9#) zyYQvM$n%T#(k$4mRyg0g`(&8sF#qr~Q>hB94#RyHzH~a7Q~1eUTi8xqo6?Bh)d;Krn;jEGk_p zYr-JvTz-gs8@sFKN&GR*{&3e0_|Bl16k(EIvxsMZc~vGxxz{M%6fGJ>*!SIjgK zRxo-FMmV?ws+;gm&h)-;FOTw$>4t z4nr{#udE1#<<$f^8THp&g6mrn zA2=;u=0B$+GFvg2WyWb197SZ{hgsaH)etvPHDi8R}|2p_|8KIX6xo0g~ZhB!PCp!tSqoz(5z=2Ks?829; zATt9sjPPxneuY)zRT4$n)a|G_H4T8AhDhBZ_69x=>v3nOf_JigknOi|(sx9>mtneg z!hgC9J;Rr57(*|<@BbEj`8)CBm5v$r{fY)+l_=Z6msb;c@4%OL6ESKkx2t%&gIr|y z#-yF^%p0Lh3%27=ocJ#(Ozo%*V4P}7}vK;@OGp}Xz0?;@W&_@IZV zMU&mbfYzLjL`!VDR?jojO^RQKIU7@uX;~Xn95@t7!-yBMjQ9#vj>373L0N}x?b!)@ zs~XZh0L%lQD-bgK-%T)mfNN~UdsY>lXNd|&WJb&}L_jzRfzXn(lxcLjmU1^3OeNkN zVI70NOyl==;LE=|k$Hs#yn;L0#`(B{FL#L2cjHTUe`o!ps=}VaPOSgW3RdRk`t0tT z_62+NDn6O0Nw=~20`J6^JA)Y`0oM}zlbugD@U>!B)f8`#7+VovyPXSX_U}rxvvr@) zEyYv(j3PB#0be5Emu#P}MCh?_PHVN~Ot9rh@WDu~DI@Be!NjVinRN-CwF|vqcNF%H z8kkMk*_q(1fm)%+BtJW$HH^>L&PY`5$VjC8M5VQSCnMN|A%!stJ3+_JL!1Uk&!Q9A zZArN^klvZn`=M7L<1%PLeV3F3svRv^Vt zATTF%C1?D1=Fj72x;;0Gf!sj?Z4m)-0ZX*IEt|RPA&eyaQjp+Xr23eg54f=9$*=9elA9sGh-> zE|9y5FXzSeKlA)!qDB#!OpmXs<2Z`fvTHjau=p;C>1+`;){tqWPO>lFjV~3BWmqZm zyXt(ZD%8sPjol`L;7mtOX7~8K@%*S*kaZNe{k(ROWOyO-byE;XUHG{{&cD*hR`M4! z!JABSDRvhDy5oXf!w~0IRj;!3bFK5vMs;wq{e@2}RhjNgukujp{5pKOt8JTU`Dgw~ z;>{f*(;dXQ=|HQFuu|H)3z!^`hB2mhw*H(6)PIL|-aE+xfDcQ!TO;!fk$Ls|j2u+M z3cjkf+)YjWII%vJ=Q9n_IXCxCJGnQH3n2IIK(101cQ=u_OJY`n?VTW;o#lbQMr*m# zbm{`Eu;g4ru0feS;~_}oj?Yu$WA>Z@7dGrC%eW5_cvjkjE834)l;3|qdRbyUBA=hY|zuqv#Gdu`1eD6jvMB52FINxB3!GKBQ5@_`0}gp z+g*YD-PotH{&x|rth)CKk$4qfPD6yeqfjA}kzhpT2d-5ty4J%k2#GTtMR$;yS6a)P zh#Ru?cS*}Th)k6vsuF?mZ2#?gbn*1zwLbeG^=s0m;v0 zxOByrkASV73jzFGh&YhArzIG#743qHQzQAB?SYtx83F5b;m3fy<0aFF&q%wd$(h~5 zL*TATY!uJHz~_!9Cw-LRX4Sp7KKrA%&)LwZ|Eb7yM%n=ZkWF8io_7W4>=-fyHg}1( z-w8JVBm(nJpsX~;u7V7wMR|4Yt3-y%NbflPuO>3v#r1KH)=g=?s+;6q5AZDC?;tW6 zIQ`w{)?Lfh)}`N75qrgcHFGAML`sENs@N+v#OH$mO;x$6GR}(RZH6rB@bUx-h)3Vg zvhvl;u*xnE@RY+43|kLzZU%Dg{A|yy!>XP|8@VI5!n$Cmz?Ui>iO;c_ zpHZ_H<{HGiprjc`xsHJEVFNw!?~EIuwG>!j@&kU7=|s*3R|Zf#ke9W-e(qcNehf$| z84=|SGvcU|gP09KIwMwH4UD6scN#&N!`zw5=)`b$Nh+3ozB(Nd;{M`#K9lu!#;~C_ zY+-fC9rgCmoywD|6@edStyT7@CH5n}&#J+9B>Uq7T3CJ<`xEzHRflRUj;6AHthM^P z0TR>v=>joE7!Bywi5Mt3XT+ZW6I@d(o`a~j(-XgvRi7!qIH0Tkdm$jmh@mO=*9iXY zKt44*p6}HMtv)xa0{i&+^+cY5@2FLz90DI8T-$+P#pTr$Zh*^$G-wUFx!9G%`0qjN z@9XtF;D)Hf6g7%sHvKil{9nsic>H|d$Is{gdfp$)dvxSN_JAJb6oK%AtYfSk_z1q} zb$)&n>`NohTD3|s-;=ef?O=m=eg6!fwccC%xh_oCYy$YNWi7f1<{UU5_^f4m82g+} zeIH?chp=nk43R&DZ*2mL-_=syH}GYJs8(%wJNTqhyiviIhk3uJ!S^WKze1oiZ$~2J$MQZ|oAL+ouWhmUng5CvU7gs713EGH zVfObVxN5Z@%KmrM<)*UNBf01G-v{)>^C2*8HF@5lhaqNb^16nHSU(8dihxNYnb!jb zaPhe+gi-eY8LlPn@Bd2n?CO8I!O?4_<%*eJU;hO@EOD*SWJ7~Gcv5{DUS$^IKQ~OL ziM^jyOU4S)f0EB@i~Tzm?EJCd#Mk+GVYeS49ymh$^a#A$z`r|+9ACzY8onER-2%pp z!$Y4*Y`)sO591#?c%nQdGAl%ms?xf9l2>-F%=QOZbi^w##WLG2XY^#l$qFsF!)v3i-_hLmus+w`Fy#FMAjGcv^5I?cy#I5-h zD7wHp;I5PpJsKS~dHX z_!7l{`;PbsH@vUYK;J0y;5c&R6eV7aKmJY{cBev6btq;LCSai&y7w zIE=G%-)=b0&SzAl!PJ`X+7I=44$C{~h0Nv;vp3X$z}QNj;pK=gS+UaD`6v~eU)%JuVnR2F{(K zcLq8Gx?ODGA>Ox%hp(Kp`o5aVHBlEPu88dau1S`65QBFCw>!n)+llw7Rt&iIxF(E+ z`twYCy#fPg9l^W4@7CFg>8lFwED&!7usKl2DsHdr@3Vm#BWm1Kai?!NPp+HOP<3md z04&pa>4e;=0GbJ3p;Q_6;9CE(3Wv2Kp%(zL0w5}juUfO$ij$ZyYzvTKI#Uenp4DMI z6C63Qan&X@!~JJ=hfR!)6`S$dJQs|`fIK^ggIvcD_n}&mlvw_cLg1cN8)OqiulV;} zzv=AcF1|dV+jQ4^T`K}yW!)L_hgGHw@CubGah6rO|H&BhofFN!0$+Awe|Jes*M5H1 zf3smLZ3AC2Jo{A|^jE*nl8dY&uaRKB8t1Kh1Nov7bsVzy4$ur;NO8A!ZnYj9fJ)h6q&r^g{i?WR z9WULGttEU}Au>C(W|EsO=kzvR7WyH8`OZ{I7ocVpE)97FOe4=nRZb}5wNt9U>!{zI zRd0p0zDji6DYShzky+9Bsshb3&#yyQ5LZdFcLBv-+@I=vv?7s-B+BD!n3^~3 zZ&z6{3uGKy^9iq|gaWv$uJ0^97u7O)Ht19Oj+JDU^Ajk5Q8ihSeX+K32J}bpNz(xK z%qOk)xV8=+_}q^8#OD_KfxHdmjIY@p(4?lqPw461+1d=`ogWz?81*jKs=h}8;0Hdp z)O37q(V2#Lp5PrCDj~6E)MsKJ*ZYr^iH9H*S;gd;*V6}4^yc=Kc4ohm#t*(uH{w$E0Sr9DlJm&)(%&OcE2vXaOGv<9ED`*VYM zbojf1F;zvTOI$Za;%+AZ03ZNKL_t)tzuf(~N;hJK?;|VUMm=T$3m?cEqthyOzz`866 zGs5pgsj7p-QB`TZGLh+kST_N4+ca?5!ZLEBq1GB+1w`Et3+u)j_}uz8L>8kJodvKr z@Zxt9neN`+QIWX|l$5g>H{SnQpm|5Nfvdm(-ZQnmUwn2uT8`PDM`EX{8RJ>BKTgBv z>fTX7?=%6X1A^75xMu^{Gelh5(-5!Q?=e+B{ESA5M0HK+WQRr zcCzmwfDIB-?~c~;X@DiOwTe_@fDQO}#&|vF9XbIU&wdYJGb0MKs@7&m=LWBJnAxd# zjT1fzvtHW+ziJ$1KJ%{Da!0f|yWR?WN7=X|S(ibuZ&lLBwGhUN1epC0pZ^p4!@*c! zA2qgj1IOQuFW>Rr?S^Y(8f?4xm~~Mwn*>KM+ z84RU5gt870=2tp&7i%V~bSJ(*z()>8t3*TOgfjmcV~#FjACNus`n?|snK{9A{WB6% z`R_<5$3*Y?Ge5wk1sEB6z|Xw-lGbuoj-7!pw~-u!?uHIk9IPwn&4Qq8fI?5$_ZR>T z5p26*8xY3nPkmi&jozIwx(jCAu%dp`{a*!|?9a-uB&WA?B^ao-*5C2_Y<-+w=Fadi zKvyYNbk5H1-<>n0KFa-*o2zJ?8Rs9Q`)6tsZ8r}XL&~1`zYUCh3W(b^<-S3OYj2Z8b zV8^1s|5MzC)ifo&>i8Z$cbJgiz-@~3{%J8 zr$U@Cn^dvQtjp<7#+P>z=~p{e6hU>i+dx&pxfb0j{%!^%x$0u4`TRTaWu>EOhsex^ z6)O9!l2P5@GuFC!wY6NuXASjXxjVMO;Y;@ZyF}&yPuiayNV&sXFcOdr_;UP!leTh1 z=25_Y>>ejM*Q_E{4ccUSkqvnzpu&Xnq@iNYy-wR-lI^%#N=T3hcSuCI&Omd&e) zIB*F6!|o$XkY^n^bAz{9$;?~u#XB@Is~})*9O&u-sul;89j^qwu8K1r)GCSThKF2r zeQb3ZO>WA2n>^P7PZ% zK&3i(##M5`5Tq0Pi3q0=SpiIy`<>7eYgPMRWmu0Q#VhtrRf|pJ)!z&lPC>xMFPF9M zg+Qwrzy}g2WEIPIRAkPL_i`GUnSW(firF;Tj}X+p1ngg52l7n&`m-;fdf;}S{Y!(*$dmu0TbFKF?Jl7RhuhIod3hGuO(`AyIG1_N0 zpvx3gr}VwZ{?QSItG(rgv2(urK!f)Qm9*uYg}#(RvUT!$aR z$aEL07;$$WSGqsknRFAs-H^$cIPL^@e1Nx#XZUt!;Abm5(-AP~di_euiD~_^t}=zy zOGM_%_-5tL|3a?uv%N2mMGMX4F87 zpOXp9u9=e$@Y38>H{kVNYml=pVCD$phIEAMBtS&HhB=tK&V{x9W^JIcb@DEt5}E!A z(ZxuG19_X`2-m+W#*N~-J;^#g1<>q8#{&4)y$@W|5Uo@MD<|+Bxpqf~9^|uTm@*xY z*kUrm|Gj?pBYCbJyfuu05>~~-_K#{AXu&3B=gVbGvp~hQp1_bQ+4&wKFwf52bNO?f zx_2O-z^Amu*4FD|@ikfNw$mwMU&GjzD)3=J;79=HdKSLpbDQu8`(u#(-IDcZVNqm1VtosD;O$7G9zo&+)fEfaa{Q%cModEt{e4a|ZRx5s6p2>3oj<5UtKR^Hf zM<6zTEZ6|}T&?X`;lPGDg5)Akbt-j75r76(+9baUc{G2 z62xc2%m#Snvcgck;C~gq9K`Q4{n<>~NmWfh@M{7n#(Dq3=OG;H^Zk}Q9}p7c48A;! zUwstg&8kLfT!ROA60VV0dWS^n0t<~`{~zSKW3}39!?Sx{fBuPlSYA(v!j-h@3I0Q3 zL;i)jhG0CC@hoOZy6*``@xnJhmi5b?QN!no&ls=%AlJY0L|IJB@KL<}Z%NWX4SkGj z`3-tl(OQuh?RF3LGsA*eC)5b`_2cK)WBLCd%U28d^<_66_;)h>K;DtqllWr2zSVwZ zT-6b9#7Oq}kL8@b;<)vmX5tGzkZXHpHegN4ufveWN@O0!>CM8wXVK^ZdgOd7Y+U8A zt1a!5u*z)u(}30i&F-(`oSwtZw6&|5qC3IgSAM?woJu=&1^{=6xOZQ>(&u2;@lHYf zJMOPCY(^1Qk(?W5kFoYERpGMRmZjFxRdKg3KCkZi<2RgB=W|#)b{x9)JMB*8S*t`! z6TxZrvkkh6Ci^{RA2J}JWMZP`XGN^r4Ktf2V97Mh26EwXwujVtQ*tg1|4x)50NNP> zrD@K((`M`m*lh(n2ST=0h>Yxfslb{2epR6p8O7}{Yqtmad z4&Y;Lz7b*=gDM)23 zgru^MPk}Krf;T?f59s*_ZW!qh_$|Y*jEl-_9t3t73kkUX?m<3dB+qCTYzniPP8LBG zrMNw}gI68LHI1)qjL39=E*|hqZ>kw4yd{8AWi+O^p`D5$;B)KPGYKdfcokG52O$DX zrf1X)FpBRr$ojM|au!#`(A}%wc#W-i%{zkC)zb2-&X%p`C=!`~*Z6t&{(vDA6xakl zS5E_Z1bIaf%m>VBVZe*V83P^wAr6`_77Q&L&euL^8k%a40L-2{Fe zdXjzB#&qbZf^MKsGen(QJ61WV@WvFxuB$FPkXJ}4jiB}Cet>7ZUzuffo|_@0ulT`= z3_+F<9))M8$heG1Q%PO*H4Pb&ReG-P|1@W^BTt&IxO2c)T06`&Ng&3i)@M4XJ-Hud z2Qng=5h@k3$Kj~2A|?Mse5tOrid z-ykwuVK1nGS!V~9T)~&ExaNNw+@}Uzo*%^hM;@R)uot+sD8PM9MgFH_) zbS$%hv#{r~J*apr^?V$TXXp2qxZnZa>Z1+|60oU=I7TpKq+ugODGO%ZMhCn;R4*Jf z*2X!&D`r^hGlZj7_Zi9Cim`l$uF9Pm^Q)~()r{&DfPRI{+!>Zt36h+~VK&wFPav`? zI=f0YROzm;>a2{ws2E$|d{&uFooAqAK#N(o8_(|VuF7O&nzGjixYml&tHKxEV`UHn z`<>`tGNNe^kP%zS9q?uCb#3GPA_4l{0LiL-cP;rbdC3IQ<8wHSO>u(*Kk#c?PY?I~ zEZBUO!G|D_GqS%j2%=&?RF*!|3Y}yx4eVE8GU)~wz`FYxaoTqmM53z}Z6Zh>gc#0R z4_VPb#EXNRzpQ$iB@LXWrmEQf>Waue8DFaF1U|R!?vk-zktnbDFGnmgeCf1|2Wl0W zfbZ&4nBL*bPOw2YM0#a_SHv^(=JRm{Urs`hy>oy4E^Ha?7B(pNi(+uHlPQj98GBP2?I0 zsTU8B3y?D+^blky+gPJO95915H-G+2Yu39!=2wWV?|%Os8U3r-)C$mM+3htDn(&jA zcc!J{i`LJPgqhykEZCz=v$6^l7}0WO?>NxXOpwD`Tka0z&Q6`Ydw;lAkN6C}f$KT~ z|E&c$1&E(td6IdDJ4y+K^>?)i#DAj_C%*;@x7E4s2T zjUxtRXSz$yHmJSjT5WcNDF!w(JywR9VxaTYt%Xh4*GlCG1cn$18M6B9 zryyljRc8-G59$by_|XV!uOd*BT%clQuuD? z{$T?B$}kib%&WLby?-y-XVzMpNuzuxfxPsWiG8!h?1g|R17+O= zODZ5ANpQgg)|F=0I{fEAULm7^%n#y3W)Vmzq8U@m-)< zsfxK8giS;4G2#Dq5=?$ousOk#1WIF10o?4&xpvt#@IK6*8Yj<7MI3zv8jX+!?>OHL zU$4c*25OMTv)ai{_SOTxCfuGU{ksZA zhuFK#oXKo&sX(@o0C=rb$y&po#0O=GcBY}2RhA5M-yM1~DZ`dPt+o6rKD*jle)aRO z{{Dcj%DbwM2N6Vm1(D0}hm!kYWZ^7g&}{$j%0gvT)06l~mHY>Eg0Z5do1MjVSg5L) zemB0nQ@_z+$?SX2-wTVcrg1= zoqts|2-K#sv-gR1Wf-EpI>#mYSw%LoY3)cB|+af6)cz z8iLna|1T!W)4lw_uT#BxvXQ%SzM005)A3SO2JA3*e6GaGrVvLW^8u~3^a7?2{5qk@ zfy39|KcFjtc7jJX6Mm$lmHIJqw!$ZW;)&xo9_UY~dGkw`A~BB_#9%rOnvudYVM$w1Bp z0vTDxvi`#mnI8twkHS8wh}%26sRn8(yX=7GfzR4j5eu+Z7S{oSKw^F*1o;7-$$lpO zyu(*5YNzb()916+unRmdKwb$zhmA&#i1R2e9Y_aOqCY~WZ% zd}hDXpfxVz_v5pS6St548){S2 zv!a|R|;L+ z0G*0mSJFlCyhIGylY3md53-pl@tF>D?`()?b(k|tNV+NIvw&w=MPS4o9iLnGBew41 zdBp12kL3Scmtuwuvi<1_1F{5a1z$!C7V+MWj%apWhaum8Au^dzF`&z{RW;a5h=%Ne zI^lU&>RfSHY{RcaW(OZE0_Z7)3Us@6P8UeIjM`TW`>1CBey5|W>Pud6DpLfK?*Iad ztm&v#1^kI(-EN;Vf%Ikw61Q(vJ3Bj9&lC5?fVQf*dKd9r0Xx47a8_PF5{IkW4St8+ zsSF=-gEpM)Vac*i&WX|vRg)T>t*^A$z+i?dDXNHJS0$yivZ|yR2-*7r^#i=()A^1L zEi<4<-(B)XiPfu$QYCrudcJEie4tkKsq7`-+a;^SU3`Xa7>V1@YG_s@6xlFKHS8)I zrjikrjC6I~3-74%e>cAT3Jv(X2-h>x4jE2;7Zz~Oz8BAdyFTaN*s!k(d06oq4SMjH zYkh7Tq@&Z|cO3y|)@uh}?wo%kIsN*5#UN*3E>=^lZR7aKT)#f=02f5h z7ABVI{@2fE5VPcCx%QrX&g-7P;n%X@Q2<+w1W9UYH4E4r(c)Sc9`O1RCEifWCnJby(BL=B_N$c?b~SDA!L#!-PX zCx-5bfl+u?>-}UyCf5IpRW0g#tQm3UG^&%cnGV^*JfE>)z%$Y3!vx#TJ}8^3vYb&Y zJnlIl7X{BM(qg;Ay1qTJ-K#G_vZovP5SsWLz7^Mpy}sjfYt2eF{D96FA0%*FH7=Qd z?EwCdv0ty}wdy^t&-)2ok@A3-UQz4&k7P|_2DK4j*cN-s_Gea!$69zF(3+1U*;@?j zAlTEM5LX?*zleQSQa$U}K)owv^}{M-o+W-i@N4T*tk}&4F0Om&z~`Yf+5UQl&-#b3 zyB)u3;7)rR@U;=8*3jDU#G<0%qH%6~Sq?-1~1yYS~ESa!uPjrb`yB`0O`Hf3iR1a8>N z)oZI(MRe3!PqLuxOp8~$_?&mw%NaiabobK3B*QhrzHynF_vaA|_P$5~wFqVpU@{j5;P7*92Fb zJf0=02f@ej^Q&>PYmKkYpkVe$;Z&9o$ZW1kv^Ie+vqFGhh9y0UK%go>on2%%K%fpF+00K!ZRr~);Q5U|Jh zbb;HG08S@H&Puf3MQXd})k&aQ(MYO*>a#@VM}e?bg4wQZeirtwA~CDOxS9y`tIx=t zZ|2yVA=;JwtvJ1}cxOw{Yxf8sK6XvS>U*WdQ_*P4?8BAUli0}JmiE}DJW)$L zj)eS00+d$}zb20zf$y|Cr@>-v!}clr-iaUm0p2Z?Rirl(Ohh}j0`grlb6vmVB2jS_ zUtXPRyi+mhItpM2rpo=dBv6l1CKL4`Ez|fsM})Y5_O3)Zt9WNscpbH2HM{t#@@KVU ztI|Q_3N{9b30(DTE8hPoT=*zW{UfAzz^~2;+`wmznX;0aFF9& zs`14HuO#pA3E>7VH&f|ITk%uYYOV0)lh~nt0$(Z;G+R%VI0t@Bl&|*iNcg6#Q@d4f%6&HfFdc{`U4lc@{kz50xTY%mrntnGCQJLJQ4u3{ws!8iR8GwmgY{=1rU%;K7L6Bf+el5IHeWU_@p{ z{s4KKrwh!lRNnutpLh6jw?j)26thSmDl#Fi_qSxtV|%Ld@1yXU72I_vdFlMJ((8BC zsb}`bnR{=^8erp@&J*wNhOsi-ufUe#<60T$5bE4VBf2tTm;mhpjGaX5X8JHb-npkoNcQVYa zh)h;UrRKmydtA{2uGs$U>~?|ATJrp|^--}58>R(8_I`Rj2;=JBOc~;eCLSYNoJL~? zULJ-u?}pHLBp|aR*H%#gZN0aCBN1?Q7)UiE>Vk7-%o{#WjLjxlHPkdXSwOA=2__z{ zG+bPT*zRQVs{vJIeL4YPY#QnrqJ%ji2Q=C5SKBpqO3o_+?XD7H=lo3Mt-F8@{> z>+0rQ&lCGCo8bN~!S)KU1R*Dtw&E-j+XuWTdMoV7ZitXd^*K=QZh-Kk(f;)WV5;Fi z>-`__t=rQ8&g#1E2JAqtAqo;KDKbxKc(L`F223gYwkBFD8kkk0CENeA08A^sOA-57 zYt$etH67&JbLL{Qf8Qf)1t z8@}L-ue^#cv3dRR8DH^(%y)P2N?j15vO!B_oSjI1C6T_1FDD6?_ETwnnA&S);+&F$;=8iVHKAymfOYuM=@5+ ze9(lSVK8r6Ustg5K(1f!;=?HI2XY>PnuHpQ5i0gF`}-h7T}HI2Sd{T(2Y9k*f@_3= z#6Z<*aD@|rT49N*nr+2%=6C}3Y(_$qMjhe*`P~P6m5!QlI>m-%6_s%j4?`x!105?W z9;j)nu>X&(?@@@jkqx&7DjCSU%RqnC)N-a_QYD&^0Et!ra*8}*geE&ES!R8bJ(z)z zOhmt`K~j+*IP*H7he-gu()cdNR%zR2`-cUwT^Q~iA|1v3Qwh*_96c68>zrq`ViX1l zfH>M}@Y)PHzC%Ku0ho*cY6a3bR+YW}e42aj#Xystn7Domb0RV?jP-ei(FnGbFRcXR@@ zBRSIyahl<aYlYPEOLZB#q3Gt`JQPluMpYF z=T7933cJz(XZKMBU#dj2>z06s9V5xfjtc)S5a^kXdK|JwkuJw(|YSF>?XM% z*0SxMf5n-ct(a(nJj(P`T#{fKGD!ioD}l%kk?EdSmc3D^{i%U?;nXMtFD6^-%v ze+%!AfGcOfH4$U}fFAZUH|*~a$pVJcoNSvbY|6U5)HAIlkyU332tnMEm^@1`rkzfY zA^=oVhn+)XLbIc|;0IZlsw115Mwtn4kFfbNU>&Dj-2nu5OL*^cew9GfX%e|A3=}}K zBMcQOtu!U4A>XSNQ!bN#$FL`rF=rLS86mV2XjI#{0bLQf2H4F!H+HV)#`Raew?pKy z{j@Wcu&U8m(G1N1z?sU)R=B=*fy`F0JI!1xLU35k1XmIft*|fW#y!Vt7^rL5Dy`^v zmSz%QA0iM1@?l&%Q_C}Qc8KRy1z%Mn^8ubw#sYpj^6dE!0`%kcGqL(AA)c}GQ`N`lT!`wC+3l+M2M?}G&FRU))P)?JM+D#YEHO2ZxO#tIo)fe5ea z67I%P&c?g=V~5D7N;BPk7SG_f3Pxf!@7+UyR0U$i_B27C6M!pNq2eJsxh2KYzv`$*XQBkZ@a7{S*b`Uw9w!&*n< zx~p*$|NRK01#^a-tp5msHY3?P35eD`-^6_>;Pq_woa}^{*SJ z?y|@;ob$T^1`wjgP0nLPy3;Xa0RJ$*caZ(Tvbs!qpc??fBupORXJ$g&09>=@fxJTT zFhN9SYgga&@&zA>easSeWBI)Y{+$7KWXwT`!Y;s1hp!}#;E551jwpE&5-k#?4ZiJ@ zfv=eT&j^GbaKXA~9>&kPsozoSajnvOkaP1i2?`bn0lal9dwmc1WQ4sn!#T(X_Qclb zxPGyN?q##U8&UzxLiGte{MX>2|eq=72#xS z`A_hwec*GVwG;f!T9Ai{iP!e%6_<|SkK7pm$v`&0bzL--M6JV@V`E=OeAyRU$AAOyzx9zXz3om2XA^`YNa^r8n0HnxxJ)wOGnVb*`D>f&z0*2h zt%SU?AJs&=v*i6>;dK>=R*3hrZC#lS->Hgm?f+8*2WoGu-^*Huvx*p30miPOlXEmp za5hoX{Bi3si$K0&OV4Qho*fnk0W=Sb5<5ut zT})y;asB1+rL!5+>@^lxRs8o5`z)(G$&x&kjs}JynRZxKF%tKtnigEa(syEbHMDf% zTI+f%*!Ot>A6}`r-oeM&K5i%O`R{};8To^a=TnvDn!-lB>v=0(%~tq57n3{PP8fV} zh-;bfovIN2^z3u34$8{n+Z}9(V8hQ;+&jD0%~}p<86Gt(uL*n^*M(Isx+)i1t+F;!P7C=vWQklyMt^v@@Ms-tt zd$RFX&|Yo*Q3F+2(0>=`aRS)bFv7sEtb0~TPzAb9#|s4`K9V46S8)AqaCwF(I2({T zapz1-d1v}!MHl8yP#y__Y&h3fwB%eNdhP_8&OTio7N%@E8>$tFoGZ`gtQOwtsF}U3 z+8{<=#f)Qhn3yA~+6Dluiq-FGxK__lGyX|UbzVCP)X*M)Co0#BZML2dL4svd+ZoBs zD&iE-%v!l)rIRBv=Y?}QgpZ$w_+a=b{#=Ki4E$K^02^}ENN_Q4ATqo83^pJN$#aYY zcT}5k#g@BdM`jCN`0}{f|F~gjyTemlOIn2lVC$Ueo@F{)Ohb96T|27=S@+2yh|WRc zjd#koINVmj_&dcI&G_a6dm74LjW0X+FtSQT^4}d_M$%?}!SyK}$-D1=2okl5HI*G( zCBfF}@eZyTnGu;t{L|V66BEJ{UY~n?e^%JjH|^$*W^HBd9FgZb(X!8O$diw%U7nGG zkHqG$iL9)nib)?FiC=RXqO4o7L$_~daw$mS73Fs`J#p5(hoWysF+N)TOMfIpqAGh= zLCLP6WCHdsIL)&9Z1@2P84LI!G62_TVHKHc#=LI?^6oQ~^S-m<%^7aBseAJ8C;<@L z^al9E?RL>PMh%dWJag90dN)w1h)Xla*bDbqUEl0`F;Kg@zwQR58 ze>e830>Ua&-z98co>k0tr<$c)Fl-ZiN`?iKut`Z zfzYe1<$aTwnTCL^=$SHI!)}1;AlIn|xWqQP*y_$IN3&`1S$p;qde~Xtv=7}p_xSpN zPB!;s|L+hEtQFf~j~4KgBN(bghy(E|S^f<8?m#{`km1r8BvgX0%${_3jp-et!jVI} zWTxvrQPbZYE^6XjtXLbP}7mEVy_*}VaNWtVwOq;pzG*kUr>!*fzIcWq(aspffS>SHi>x|c1!9h9?wikkisw2Fkeg;* zvTHmHL6J>`TuIs|A)}@tz9wqJ3=Y&aCNrPA+xj=czI$%I4-y~`;cwku{3m{G$&Nq& zgdXNKpp!Fq5Sek$4dP3l&=u9Jawa3f26*e03-UWYSK_EZeTN*X;Ew7Ll}U*8Ryfzq z5Gu-+#!BzXXSn-z1c$SUXInbYO2@dOj7f;79gWP&wXXYgB$)InzPuX$REsrKeDQb2 zm(vhRo!G;OfzBq%9g%poBGgH1xj0fKf|VU;2}V@^2joeXN_T@JVW+`Rm9tPG`kf~I z86wklY`A-L#Y~66I|m_aUw{8$e1_ZqPI~Jgw)+6@NT?8*DqfrByr?x{&o7I$V6Z3f zQ=9q$URg5@kvWP$sv_oFZ69|=W)04sg4D`NfCu^AY5qQo8^9S-RekA*f~$_KqFcf? z)C0d(2q*$LYu_4#yxnarSGuK&IH;5_-vu_5UPZ-#z}%lQRMj^69Rfbvzju?FZhBuv z%)XPDz8gqh4P@M~FqnOIN5;HjpLZN217cY~!zKe}HYIBl9OgN9a|Sb8-3f6PCnFBz z1EeN&MP8O2RiJkVi0=3zwWNt91P%wKta z89y0gkM%eOBwd=#I`66M~2C=LZnJOS|R(#3Ex#&zoSTQx?x7lFB}5z zxMbRZ@80PfyjX@cyYP=u+D}yp_aeT`2xezXD(Aa{Cq0!<_@yF~Z7ddqsY#VpLMXct zgy3=z!e@#=ejpzJ(2}1SiSy2;rz@gy2vTa75Khqyjwq!0Yw*VX+~X^oo3 zjsUqV$Jy&+8O_WF-l@UG&S*7|W;)QV0Nzy)qcnvwqG?S69>m$N`*#{U!hG!{K&%pw z?EuXkX_Vcdo@v&tM5O{sM{-u8j`fNOdO||Q=XEUCP??&kh?8%|emzgxo2=rq2_iEi z9Aj&n(`e1AtB*kLF|m7gAAMv0RQB;&wdyJhfd9_;AIMv;vcW&=x((!2I%E0$2XsZ| zfNzDn!~awg=_>g#3jq)#`4qwU4Z5Pn1*sMLreYuVygRrgg&G3(E_})E>qrQEH*jIs zKfB7DDW1!_@nxkVQ&pty4!`=-@a4St{cK=sBr=u#x{5D%W7)Gr=0Gjc%HrB7;^U0e zibNJWcdV1A6F=Gn(U)QLLH7RZ>nUvh4z6q`ZC_Qo&=HwK*tkkXx{JB9WO9b(o*@Qc z)rt|{GP~EI3lF~;BJ&6Neiy!v`CVlf85YV4OfvG9#XAQ=YdH!V@$9e>2QqdX1OqKu zMrB>-o^0%ae4447R^! zyRM2x4oo1$M6fI5r~_nKTXKW$M2IaYtYxNB+1dq>Q1P?XsiD>VR~c64u3xnyMItkj ziOR-Cz!)WHp7?dbc9!INefA>&{i<|Bd{*C*{~zF;DJZP7vYQQjpy4P2`SssV;}gDz z=ldi?aRqapk)Lpw!c9VbhJYR+09?tePOxNFnKzJk9XY-D%CNAjL`Ri~Xd9%~?zP2= z%u&GF%=Rn$Rry{c%+~s7+V6Yy;cdBs5X&k!hRn=*WKvZVhz|R6XS&?2i zGqD^dzT5F{tw@BjIH8%ig^`8d5>hTEb!T!-ZIj4kMB&2_nIEVXM^%P)Xa8miW2QqL zeU-Bbj~9_S!vkBZMZSj%SdD&`X~-_}2R^rdMlsUtLXYJjso?k{F{-N`(!6B+N0mYTF&tNTt%MK+xlVFn_VZnf{=W3Bl+f%GBv?z&%|!3O|bZbP;2tTx|O zjdgskh+EhDnFM7W!2cy==Idww0Y8;jN$WhwnIFsfb42++ALMMWzta|<>Vl^D z_XByy&J&*#!cIrb1)A9&_yE@)a{~7(E@T1ow*~OW_m8%eRk_Tc=QvhByzpaB2+;$- zR%^y8&1X12jOhOWA8?SJ|E&8#y*><)KZH$WJ}zo}Wi66X+UgmC#m9nQ2Y8irwEZi# zU*nZWz^@ucPeH5R;H2CtHAt{|M zo@;k~n)i1azyQ~{9R*UodVh*&b@#_wl6OcyhA-9N+#|6+anC&oZXbr&stgQavLic% z7$dp=X_6#|z%|hZe}K2;w}cbvCz4hfzC4onZzTRXEAWc;kP%_4G)g6L+z6IZucyJ6 z6M0AP6MGuc@vL`zmRZa8>UVRNqn>PExS>p1Cd0UA2wsMVqOJaJ2+1MvZv*iE3VgZ# z{6UD+hv6Z9kQnmC?|hFz4l^8Xsx9F41YPEJCqt^TawKd+I|E${91;RUI&5jP^nPC)XvXNQKa;2(W4Iy*lo@pGy47csX+K7y*##mh zW1I~uia=AX$uPF(5kTe(Xg&+UvpZ`OzV+S78g#Rto(A){p(Yi(r*KRq5n1s)mGf1_ zLT4r|?-KVAK6{#=TP0|sZu`!Z_(tqK;HT)`VT&sjrHoW=A?R5vpCRnS&OWL7$Mx%b zAU9X?_DTG3=6AXwB^=gwli=O+&AJ$}R#&H`HVIZ&$#)og@6O~Ee92m$T?_(&u_oRl z3$Sa8t5vX9@TGfITbG?goQg@Zb*tL5dC{gJiGSR=yK`Nx;>#-Df+6IYzHL7d%k5O; zI(+%uSVLtW8NM85U4~h+M?z$-@BM*%m}Hg6YzF_axd6|EU_Y~u&*IAp9|-(fks4#Y zhW{QWnP&Uclsz{1X6GQXg=z+fF(Os9=Kww<)5(Tt#4*Q7n=TNkw6okfSY`+CR*Xp` z60?dX#mIjc(BBOZiUX-$pz?uyVtQP=gRCu^%2*v#vO{FDDYrmAom~YwY|scJB4Q<; zA~#fWp_6}4)Z2?$w!1I&h`Ob5d?4W7KwNWvT%2p&=q`{*~@JB z7<5sc`;DndQnJ3;C!q!%Z%$ut9Lc#3Bw~o*^&S|NoXe<7fE$r?w@)i}kC3q$1WI7ipkYk)c{wvxQVb-9W9C z5oBT41!nDZJ=y4P(XsmY9J3olpM&1(J^u>PCw3q_4T=_ zVNfc7ZYTC=B@j`%jg9!+S+G@XZ*=HMo;~^AL5R%kc~`)+1FBgCX-kOAD1p+FK&zQR zyfSR3QYETL182XlYFt+FWhD?8(DDl1TqmnM!UmC=B`KaHkYx9#Iuh7t-7)pIomkVI zHSYwAu$KENFrL%u%5WwGfvU9cG8u}VoMERksPMib;$k406^%sPoM9!1xT`X3se&(6 z9CQ_5vURBv#$6E3yF?kYKWA_dBZ_yit;3gRagbVzj?b;-P6CZR3pdGrZa&v0aBZe7 zJBV$lRPBESzRYw7C$X7~Y@H(BcbKg@4DwEV3FxF%l?+$BjFUTJQ{z{jVIPWD~OZJMQNWUyz{iB~X_u%6|5d*oqfE`X3+tfUZ_RVFNY-;xZtZf#HtYczDIa zyDHM17H3UzpyeuH*BuX#?u=7ul?+oi z3)n2{*lT3JF)da_ z)D5ynccM+r5LMkIna}9RJ2IFwA4}StAu_XSg3E~`N27k?ncXDRBaXyN)0=$d^@VUaIn>E;}=ukj&Yyie- zh|El{^$ZAQ&Rl8CT-6A1MC4iN0|-)tNkd=>2MnpZ0_9g$hVmn@Op&2!x$dl+_R z(giTK%d?2rcp71)g%APS_(NWXqWkgel zukww=z>^RL%2q24%Xsb&5~S|NH_QfSNf3uY*i3}#)cZS$%vRjvjNrVAFWqZ^>oI0) z*@6#d1L$VKMx8A_*}<16;>>A?KM11do%ph!ATn8eJ*#hF-@D<<6(Kh^AOv;Uw$V4GK!ZsokfmH#L zA~9J&%`(0nzLi{+{toCYR|nU-r~qWAUD660!#&3_hoTxNrT48^+g0pSd)6#M+@UH#YRX9b%{S@R#T+3`N zMsa;B6$-%p6`6n^YTz{9*w0sjh6Cp{hcY5`7pOf=Qh@m*}X^-e;h@T~iJ001BW zNkl$PPG)C{ja4W7=DbpyO=Y1PYRReX)Cvr3Rm z5$slccPp+x!<3A48u(SNDQm;eD$H79uhfvIRWV zuvqoVut|k4cUqfUA?}zYe$RAfEB5<9-rkKO4zJ+LS&Zc)-spl{z8iy9)<0@wW|ORu z@HtJ8n4S1jB>42q{&e`V6Ed=TP946iCQ2$2hO9EVU5Jk!Cy30b$?fdy%DId}B48lb zlU5y9?)**gPKi%hMyCM*Ln>DP?KTP{f1F0As+M3GNtmF&33j=n+r(P!)HD5xK)RZ- z$N=yWz$OFzC>U@Tcn@%mA{Ko2Bv3oRD_PWlo!yGV9Szb+p1%XJ*jO_aY-NE~29Ve_ zR;H6yG)5qTRrmf`P~zIro%29}0ILk)dB>i)s+HY#&ZZ=IB&|1Yzej@X~*_j+C_gLGogS(w0YE9Sb(qTTA>7R}b zf~PvD>ug0>hW(y5*+4gJqKcp5upgz(s{A{{@eWT#!tP&7u=rTc+*(Bw17Z|#0_!Yu zHijh?RJ;X3s=hR^5AeZ&9bB5K70w|Ffp(QtJA*G9iQQD|ZMGlIw0+(|WVRx{yeome zTaoGXuCaOk7019@XIWL=UHB5voeHikyKSuZ-T2bQSN>kT9Tb86fG^#CKf?n(pogIyNxYxQoUpj;!^D3Td|4?}WY2s+ccwhDhrp&PuWy)% zlt#8TdvL7X^E>itv)B85OAb=zklCbNWoWbM=Bg@kt@e9O&i)7w_#hx}K({l4u+?1z z?U9jJMlL?%*oqx>V_rn%4`NU<(AUHJzJQVn&W8Yab6J0cfb<#G{z&fc5bXZz>mSSa z;t++loRMt(7@^<7`mlDqgY1ut(D=Z=1#WvFlAnvwVTOTK4js^K5j`PHoFiI){|9t6 z0Ry6Q2_#}5v#!;*qO{D&R0AmKtAk*Y2vQ32&)!mHjVJZ0Er`Pd-AOQ zAAHXGujeYOgc=01vIK|IXsYTAclcJ*mf)bwZ)CpZv8-bg_;G!{gRI@Umon^~4W)5O zf$Yzx`Ta=bNBr`U_~|3yIaZB17yCCzEb@(_ znuz>n@a4C{`HXSH>;J#M@bLq@C4jYBvv#+$2D2h??J@`My;LPw7ff^3mVg9!pMACB zVN-urG$1N#FyV)}w2Swe{adxRvCPZ5_dWb^zcEVJR2-Ea{ziP_aXDLv#W3F-X1YBS%( zm+izEX@zx}f)5*p=g8)m%#HiqiD9StzqS&YO$1S+0F+!d$2sR};KB^r6b2zW?PyH8 z0s60ndLq~I8^sM-aY~MOQd6BO8$ku$9lRyYX_}q|wb4*1@`@S#X9(Ei`>&Y-riUl2GuYY7 zSrtrH(Z%e``u`u$!+9!GX0H&sRm^dgY;sZ!Zn#DD?}~_IdO;JqVs(muK}{2F&^k|5 zxdT8~NiksC3TwYhVovN0LD{i?&PPFDr%}9jhM%9%71c1ox!T(md|7FQtDJ#W`1>9H zNbS`MfyC_dlaQd9?p!x#pGIwCWB?*Uyz;G|0i>hcc?f4Tv|yIfi;;Ij;04%8$| zGL9z09Ij&B$w!o=)8eq7GXcJ8rK?tVRfYuZk_4{39D-&JLVe8#Upr@v0u~zBB08)0qRHYOnUMl2#25=cjTbRJaTDPYFq*eQwkxX|6Y_mYJowZ+V z+I8HMmHm*(G(63^GNQY(eri}jmPoGR(n`glTYp7ncATq7>B#khn>fb)skQYy zBU7G&*qHb{Oiv}77{09Faz;`gWN*(T207q|kXHPF(iT<{VA;^gj#{F}5!F}l4Gd{e z@vZF7IIO7~VnM}Fe`O-GS_BYD%x965YJyi#|Lz7SxsIQe3>pPH{0<@$gct;Lw^Tzu z3~7?}o5izP>Ecnt>?-TYTJbyflIjDsLNm7aMiF1`l9{teWM%~ltdLCUEq8EvlxB!z zBp7z>xK;jlzKF~NI^(srtq$asC@pcsEXY&UU6qN;YI8HK8ATo`5{ZdI4-#0Z>v9{g zG7yPP;@jEemF#=ld}cc!vlU1pM*d`9-;itas6(~30A<8qHaLTkvBRv7GA?XNc{YrP z1*}i90GAIejesDINCA-!j zJR2OszP~F?usay9I_zv3Kc)ha>d=}2UZL$;%VE|LB6!)^54(Q?T$TbjmmF7tcQ5$Y z>|8Ug#Z@EuNCNYJ;qx#UATJJxc5)`M)Y!oAFmcp0G0ytDMzXipe;?2tIir9%uXLa= zEqXO{h>_TL4`fvSYi#;&r4`qa7Yd!}l3tv;8wgTvOFVu2$uKyok)65G&b@PQoI)j2v^iJ$e6X)q|TdeT6WIplgH! zTWu+?8a5b0(GiWi6%i_PkTLRCb;v3$cg(>|1AP0khg%YSO%srJa8d9{3|vJQjTw5T zTf`=JHUl!V&sIckrS%WcrSlCwTj$yUszg5{B6p{bR|xZ6{*^^{sxS6Kv-|amBw>+Kpo(oF%%3 z2=3heskE@4B{Bg&tfx9)vL{3t4B-J{^PJR;+CNo%i4EJTf-0v`+&9SbonWjL@ueEv zbl|fNB_pDmAu`$LGdna3_%eGBNJLrB%T<= z9=rQf(gaF+Y!9Imk4xYZ+0@_8zO)%mVx@Y1BwiSRpcJeBV*n$BuYZQ#Ktbyy7pV@x%hLwPHBaD|!g>U{}LV5x0YMS#C@ujNt8PHu#?0Ev8r%GqZ#zDvrRq4w1d8VWNEbcFcGnv1vlI2w*s6u95 zCGOOq-FH=+{^>-f8ZxP3E$$8JDrx;d55=XEio-_Ni`u$3x66Opk2`*KU zsjhPv`xiUnT0*on@aktZ^?ej<&M^3n*&bJ*feoIiQplm?jVkXq6K-K5@3Mffdrq28 z;mWLY?tuVuvlj8}gF6X+oOV`)jGG1UbyYi}sUW{Jz_N)kLRzmI^=Z z;B9wrj*zVAe^$QF+JG7UJVRz?*X=ae+5dHD9owwsdXU6MB`9qLGFA}2l@u?~@l zWd3I$PgJ?*(*%*~?0-fS?6lZ7L4>TnY7}hC9sbMVz%zq@D!=!4Au<798JwLPr?L4o zJ`9ELL&R%C?0Z&8`<0XE2Xykh70)MIpMiQ;QD%cOqA(JV4l5~4%qlsD;KE#$KRfd( znODJ=XZWL?_^;w~qQuifaCy_<6-U-j6gyfT_-~EDfzJa_K7M{3;Xn?;Xs?=mjMa{n zo(=!4F{4U`zb6Z`l37pWCDE*1F1{Yd={%st@*mKxc^!TVb4CoUnmm~Sd|l7OfZ`6_ zy8jSl^$L_!Mhx(iJRc!g84JzgCqVBzXUaF|-e8;qEAwo@pz+ zGRv>8kAyf_?|Z%fbrShO_G0EVfX}TA03SBM9M+Kp$v}N_dr$6d{fv&!S)M5X!XyB7 zCkxK10+0kEPvZ!I&qHClA%#a`2Uu(KL4utw2<7$f9|jbDPi(H*4{X>@B|yuZ+Bajr z9a()C+rWOmC*RK!CJKb8LHK~ahI%BLm0jp|L{om>P|-z3qoGc{U6CScGUH(|GDhp zBk_y>CGba;sEUK?R^Rad3wWIcV_Bkk2AtiLy8iA6e&!*_jF*P1 zN}P3rAMeDM6#_=>tx7v?T<34eSsIDot#tHc-+z#MIt2b)?FFke8_Cc2giLxQ_#?y5 z%)fm=4@e&7j6V%gJH_w!W&d<=4e96dIY(kgV?4=p(4)5I>wHw(-PQSFF=tOWvxCHY z&mumV#y_ud!!z(@bKxJJB7uj%Z!n$ZgCrArct!`o!d;yCY=%MV#~;XB6WH|3toq_< z3{*!hb{-v%Yq_q1(;W@1UB;WWM*#cU1n#qTTM-z5s=kL4i9d7wYyy@7{S~4@Ihf30 zw3As56v(h63GNQ$6CPolqlJCPc^e8|3*;aqrHi zoV5?`_cF2h%KJ?7`#bNc?9;AhXZ7btaX)2yxZ!#g>)ow6nGm_Es+t?;7lt&yqg8FU zvffn;o;e%pT(Xv{N>GD~=T{};rU|-Q;eIOnQ<1RBK4j#n!Yl5+)%C}UN=0P43d9w# zX2T@2r0ALRU(s{lv7N4)<7|Z_tISZ?NS|AL$dd5MX0prT33_?P86Cn5E zL1l;c0p2Qe6_`g-KW5*1;h=VLA5$11Ho>hj?X_)?nQjkMbVOKYekS&&!)s&!K1*9& z+m3TpE+~S^U7)&qUk>nBr`WRVaDny?k;(R4){1i_c)nvTK?35I_{S_!w?kZ20YD|= z%c=+~#Buif4p5u{QWJGS_*kJh30cgNnw7JCc9>GE5O)*oXW`jY$wvfW&VsIneDK9Y z-U0^kf0=zh3Sg5}GIZqCGBMatg8fcI%aMNbqW$Q&))uHpQS}_}A~MgA`@1^vZ6omA zeLaLNP#VZg*Ow8c2R>H|Wzs>cvWX?O*nrhok?SgAryy?}zJ%Fx3SUlheTTsvSMg;- zT^qML6&J;TdzaihgP|NgJEJA5;>$l3U$X0G(gWE($@Z_?UkCKio4#TDVEoSjZ(n~B z{$v``>tP5ahcBC1AE(XQPVD_1vd~R~ep0F5D-htdvdt4prR+g<1Q*&NJV6+;VTspQ3!`yB^#8kBg=}W&CNJ-x-aBU7)H;{RgzhW8VP2E>n@|>^;b{890{}nb@0;R3OwrS;bRG`Eheg;yfu?@r6&n|2v z1X)_0Tsw=;0>(~eRY#R!AMYkIM==1)hL1U*-^lx`z)MxiFn_5k44V0UV861bYS&bj zc7O|vGZH*ICvGp#1mwCvbtd4f3(^fHc+U0`P@5W>wV>@1Rio&))YN2v4@p_=U?;>= zW&>V8hyJyZi4&A_{ zxq*Mr#8=bcuUW8j6MVAppM)=Ah*UR7m&x>0?MxR~YKEndLuedJ;!8=3PwDor$h4WJ>1lt+bncdG>e5s@jR5FTPXSC-Z8yHg! zOLFlclOCAsB4txp*IxcCn0Wp94WCP)hXBdz|E)dtipXRwv8_Oa9f`Bu1!c+@J`=F% z447-PU|FmTtXvKBCkZ&JL}s{MLrAbqQt19-BGPY zJAmw}7=GLv6%hO#MCNWl!8!qk_?bHQO!%8s?`3B!4m4uzl?U>v+3x*!fM!KMiP?f- zezyrQ?gE|6woZXr8X;u{_=HoYD~tj;-jOF>RRGd1?(J8?pd~nt5h9i3ml_I`0o-ga zJd*1;q1(J0{6M0JpPG3;+fP}m>4|HJa;4qOg7dRz|Edx&Rl9k`{!SBMT_rMAfbOQM zI=`P)?sVb5vX~{aWzIIKz&{e{Z1|ian%q9=2@%M!TBae4O(OFuzRaYHSTfjkxm1R^ zwSrHp#B^8VGZctzCr6=3%>Oog2}9KG;?MX@4)ZxK$#fTAy1{PQnIF*AZI$&0csFYk zB$_)DR}$sf{Z^l^>-fo%pmFN9vK1(vA9X$yvDXX!=MKKCcK2rd32j{y0A~5?Cc~uE(^NIxLYlz8HY|1Q%aTS@FE<`UnN#H%BI4+VF%*hSHR;y{<%o(sL zx$b=|Xt=x4u4wx>k!}dXcZIZw+M7)nf~+m_dE*{I9QZWG8Q9M{RfmDFsy>zwaDkG` z#ygZ_x4thgheK}4fFn}VTes1QLR+3h{G%G-HM*0BY1#( zAX76KCL^X%1cEyq2Ou^K;+Zt)VRq4m#>8(Y_@bKtKbsi6lIbcaZV6^n&p?6nZb*n( zyax!9L;0mUzC9ZvxcllNxq&3W>;){jD=h&+K7EQTWp+19)b6(Ao(V>c6+7(t#298* zD?N4(vBYRKz`x=zk0QRT5??418CURSb`5T-vg?@0_IWpWRN3LHt>p}#jRJ`QXbsH& zW_($dPP?o9?FgK!iT1nra}pA3Y<#Yg3#t&oL!1RhG9j^l4YexZ-HusT>8aLg8sAjW zpsiHI!z4N!k$DwgLd3}o1MS4MI~>zU{IcR_vd$k`k@-MgA(>4DZvtpOgYzGP`OhX( zsj0^h2S)+hwY6jrK)4e~>V#^w~0pS;^v7^^4ZeIf=1lQ`gpKt_DUm17IQS z!n|m(**;e1a2lY7!v1GO0Kf(K8zHfrP7$!LkEW6{{o?uf6p?xL{V}6oS-0v?kV@qe z%V;v7c?2SJz$Z5%V9o|H9mVJ8k}Jx7Ra%CzVMiJ99DRyfpKKC6BU;to9vi`q8)~** z*NOK;3F}CS6C_&_z%ac*H|!_g=Yik#%9wOfR^6Dj^s_ZoS^bs}c{@ZV!=oz^etv*N z%7Q>_COR0AiQs>m!3eB6w5kz!wX&mn#+kqC0*~(y32dL8hRlJ$6qO)2oAjPl0XsVf zV>{R$aQLz#ADU6YoGswLEBMmc%UQ&MFz0KMHBqGHE54}4b-QHd4(a2jlK;2jOLd>k z_~*)AIX067tmCU152(*mxUmOY7N?dg?qR}LU$W0QjU8Fz_yb(RqZRk}CpvyA_M;+s z(l*aeEBMFVfwFh;T1943MwHUX_0?E-PvYQJlz+yEAr2y*sq7neGmcNar_ z!sli+i2+9ghSot{vc$+k?h$CE!B{% z;g@*6FZ)u_pqV1rQNsid)LyFMUk#aIq(TQD%(4D?!pkB6T(9&LI>AN}uI@rhuQN3bz7d3Nh}euZax{=$vV z#s9wk`-Lyp-}%44uJPw$Z;s_zJeO-Z0)aXJ{2${R{+vKK{ZvOgpEq_2K=O2kp z90@i$0@1tTWF;MQ;=S|bT<#x))QH0*+6CL%2@Zm!|#}n^!0A?Xs60yq+ z=R4wq*LhhnVpd4ei7y)o&UtuBiv3F-U@0nibAif};pUnRP z@4A5TnjU!XP>VSI6_1YO`TQgC-E2ZVYoCtKZA~EkEu7hbnk>fa?>|ZWielmOguc=?hnk#mys)DxfA4Zd8l~}TkiVq z>U~YKzn;Vaj$)$3Y2eNR(dhP$yO+CFL4ej1!v}3yBV^QF+lL$XTJg^)tRYMyB=ez4 z3#)SdYAR+Eb^yiw?QEl)idYE@tG+TD3RE4O<|-4|BwDqW4PMW=i#;)ld(~CU?w;!& z_Fwdajo`?c0P`#f+VNgZ%Jyy(wqY9ER?*HH24AY-3d**!z?uyp+{HMb^!@H^-@zMq zHSFTP8_?5T9ZA}g09vh=!sdrjo50j?b#( zvUciE$f11t6>WTW|9#`LqWvGxlkOofwweL4v!-sUcfW}*TLEt~eB*}tR%Ib7*r4*v z*r3*deByhh!!auiXvhnkW|0GEn`gS>Kbs)()tTw!9wzn@50#?10j;Tjwd%a;E3;T( z2oB3($jUW#crED?k$EI6cxJewhTY3a{sFC#Iq}{;0sNlDVHH$pNw^D+n+a6hIsy6A z$VrH;DGaGK1_G4qICgA;HV0&#L7l?619_D&11lYT@}&dX&47y?LUVoZPZHdWBG4S< zS+7zeN=K>}_lz4tRtOA((L$lKN1WA?BK|G^{`TrzJY>%B8M z(h=OV5FkwP8Aow{$9+AZCn2)yZK$>OvcM&t`@?|C>TnD8ELkO!Tbrz^cnWguDv^ne zJ)ha~4FA0_ifGM#0v0Lg=j>848yvt^X<3%weNyQ17tx0o`#j3M6I|WXfUoRkii@?hwEo*)6t? zY$`O0YtY~mk8b$Lr>3BzxV~40$}n4UM`MqDhr_>5gB$uyeCd32H_wad-&Sn0^8pon z>7I2@_I~WnQy6m?A2SMg;tGL@!gEI<{!!8t6Tf$q?Ao6!)=>K@OFU$H=Ip&Y-{X?x zNO-|d4RB_AFzasECNg776Kh@WVUe<7L2GN{69BP5PQQ5tMpm_XB*aZO;G8iWk+1073uG*;zPAV0b12yd*2#~0{*W5>H@C~MVL`;!IES>+Wrh=@!&!X-blMEy=hrrJ*x%=F*z+O5hv z3*==5$5n_g)i&4@d_RJHW7UgQo#dX_^DgZ0N@TJ?xuP!)=pl>QJ|4;YMv-{gA!C%Z zn2JrZ>L*qmS{=6Os<$DC@T>SzwY9P;-if*fWTxRfMI1NquKf)7PK2FdKQ6XV@#vjd z8grA#jDBmUfMgoXF^jfN5w}sgCQ1)QLO5H?vp{ZV@fX8i4f_?Dt?=Db_zyLhvf|?v zzRcnw7JCfjg?y~-9PqMTO%SzAZq9Kg>vgpvPFD7X*@(77WHKkPYMf*(KraXVBVq5? zes?y_8Ue6o?dKCb;~1;&l*Y+UOLHdn9IGh@36Rxi4gr!;bSihr&WfY^1PEmsI@tjq zCU|xlM!O`M5-VnoPZ5N}05ueiVD;edkc^IWU>YfETCQ@8j?8hb+|xKI1~36$xikyp z^iD>8H~CNjYAukCS6cBwh^^D?l_7$v319U-4Txuie6?!tllCvWPnX5)hBS9o{FQUB z-XB|Pvms-5&%WB)Hb~&y6L8#x-Dmo~E{I@1%P>w$NJBQModql{ zymvrXn@3EQ1)Z~aZefCfJC!zT0=46J4Le569e7V}zwG5eKB2r9NF){yQJNPo%lgO`3c-b^3H&yArti;6?T+#5Z zBV2hO@U9J-RrES8pc@iV?P(URDAa3YCA%WFsO@sM^K8k))_r zg{z7!mwd~TM;-YvffpuWRerJ3{E51xg94cB^DFo=t468f%WR0v#P3}{@!B2%XI9C2 z7$T_}813ks}^t*qs|@V+~*s{g&3&^<}u>MB{QT>~*D>Vk-=-iO;qceIM5 zPjYL1g)mU0{Ys*<3E%8oX8&H*f~)%ANo*R!D;Y622+o|~GBgl2bglElC_ylV)rUS=IS2zO3LSbuK$}8-KN1%~kL2#&Fr5$j)qs9@6FF^(?WF z4V!aBp^L4uWS*N*5#yX}80cYa-Z1!bn*CX|TXA@fvXAUp472Z6KJF;+CDZUGJ2s0I zJkBbS`Ah)eN@PBew?D2^vCriX0+IP+0iUmFk39jVGa(%teEX=8zUimMgh2~>uZLz{{)E{3I7#XJU5>& za}aDWz-b)yX^5f|UVl&#I)m7pStLs;2`_a`g9J{qu*dHVeY^Y0Dp?fK$C3fcPgXMK zhah=Tu#L{YJn)_+uSjcTXEy40Gk^&~q%ps{Lu6L8i7L}(**=P`Y_s6^9Dr`n?a@0# zXtYHSyeGlePCT|BW`vm@7_T>tGT5d17?o7k^lj(eqxJ>^=S5_7D z!1unc;L9BnYY1E7Ix8A-jq)rQ&xp)d{L~3aQ_(DQBxW_y!-#@E4fg5M zkUm%U0N{rXsWVa?*2&1JY$`U}|0+>@1z)?>=KDp{T*YQ*xvRIu3!HN(V{&1h!i%Ex1Rb*D;16IJ4?VDbR-xaq&jKGq9=2(WM2`+z4FXd+qBB^WSQCyUH#-*ZCc^_J^?J72zIgx zkgLO#oPEehV-?5@crDo-L2_k(GEwy1VF9jkUlICFuNTHYusyUpkgIY{6F%eHpmo1? zgUSj?>@?Qme>?xO4h8Js8o^T#n3ce{Y9E+h*aT0+>}IE@AiorG)`~d=FRb~+t)0;=l2S6a@U_G&gflKH?%2$%2H$ecHR?~1g_ zgdYZ#X?;x+R4IZn(}GkQiaP{_v$2ZAXe5vZu2;S)X$Dn&I8jR!Urn^^+BB6I&%QI8 zTE717PeGbhv<$~heCd*LyBfhTc+rt04!_6$9?5xX8}?&t5Sdr-r6YEnbQ7S9tE%=+ z>AYVVyjiuq-4MPN5~~$$(3Ps;9k~}r%DI7O72B-VoF!45ELA0rt>BI-Up9;QT*b*( zFfS{J!vlX+^u!jewe|NAHtnj5`3L@L2|pH+@$1*`tQDRAz&|s9FA(;%{Onu|&+9v0 znq#sqH_B<9z=5j4!!1DobCV2+uQ*JkFVAa+wK|dj;~Ac-%b3LKoNQ|B`aS!;{Kx%cs&E zuiy``oQqxv#MJa^=6GXe&4G8}^Xd?R6YsjwYjW9#UfARB zVsA76|MTlJp7_1ZyodG8o_|&`-h)4dS-(MS)=7xT*YEzo@53V3?v8BW$&vW^*Ew1- z=la}x;#1>VJ`yj}X_yM0<=E9AV(rH5<@a2^QzCbHwgV4SpEN zr}nz3(kj`RU9Yq6U&(i$$fZR_h(msWcl>1?Zy71`GuZVb!AdXtIs(RM$mc!)??pR< zVCVrY>Efh^x=EI~MB*U(>I_)QHD^4Hqy1;I@T*Q12cs)nfDy@bUXKmiu`Z-CdL->Vt z|781-T@QkN$vRBG@Ov^dKDSO1RhfOw{QtRdcWbwF+*5~HpY<~t;hl9ftp1m+&%gH9 zV+JRZtJS&|Ziv#$-!T7C?;YWA?(E(J+0}uyQtyF5*(<`WE#TaprwSFlw z;i^{V&Xg?$X4Ungt(Kn{`s zq$Ah*xiZC%Wo8&DH!o&vlvw!A)aS~x&$N2g&nx7}-Ir_m+WF2aqUUOFDs5lYma;n9 zk@$hL08|t~?TD!ftz+Y~UsUkxzMt*Cif?I!eZjK#)m9V~o@px*k-HVOm1n}PMhDvQeZ#jb-ZI#&>wXC+++>asQQtn?6^Ry2q+4cxVbd?v(a4}nBW-t+Sp2>u)X zN|+;%P95(978&thNls0Jk$3ENRRhsg53$y?p4ew*zg#tX#eY;P;deB8cPplxjDo@u z5cYc{q*1n(%1`X*6*rTNnVa_UDyFMcHD#n~$GcwqPK6!YZwh~WC%&xsY?WAW{&|{n z&(2P@b^9(3?Hg-!=lfVfv7(`ryXYLtP^tM%XAR`>Hxkk_eOf~hEwR(0!xDQ;L+1=gVICVnvLjz7cy%`nsH+m01J@)8TG7_u1#H=Mbz_UWu^%9$(TTc5iqguxJB;E= z5C!>Nx%nBnGqS8QvX@{S^r!~DZY&UUN-015P8xNz-oS!IaUijCKI{9H)P zwUg(^@_WxENd1wJ#l1j6XLhXNJwaU=Fyrv0@?VYwiuV%9=CcrZ@3bFQhk#YiMrA)& zvBYo(P3fOdH<}CcTBjz$ka2k?zATLR7 z36N6NVeT1pnT$t5u&BjmV53UfX+tdg~KVYX{#Y_1XnnlTGi0uqzdPw{8fbAqbRR5;hxL zq6T0z@%>rHK_>kY+xigpL2Uhtdm@udX?SnLf03SlOYmcc`LZB4lkahR=#h|Gt6WND z5-kXps7z1q(3P*#_}_|6hagT_a<-Brubj`yL{#U$aRXmgr>bWYsv99xCOKD?`_G0& zOkA&Y8s?l&^V|pc?0`njc?Tb)x=VC9g2ds=cH{E_-JzJ_=xIp#3MryGB9#W~9ei0K zS}R1)E>W$pb!9kfY;9F~o!Pxc>4_*6GN9!W*qT@5AF^{(X%hrxVgUw$L#!sWhq7IXld= zjJlH1e*7&2>IkH0Odx*YpSqy0pFIPCvJ&cT`K*(WIc};d3lxq(!d8e92rR|?S4#+A zB))82$E-M@BAwJW5;6^1AF&nBXSI8X?Z1vZaX-y{I2_V8@J%+15=q=O3rVAl*t~hAK(^ir;eI(TaS_4o2%D4q_b*YW-Yth9%^kv>-@){;y#_5p;CuNo+%a z+-NAyg-BdQuGb9xIxOfBe*P2hRiLA=2{H{OX7rg(%YdHNTn$8bDsbHWtk*jVpPvl| z0dfr}RhAF%D#}(2?pUyVKx=ZfB2aT0q#1Bjjzrx*6X|D;>kg4QiiWlca#K0GDw)7q zDk`P%700@hsmsR||^;PsIfxL25wXbK@VyxY`74XdrSPa6C3=$}hSb%15m{X%Lzw-W z1Y-_-Pir}lcT8oruqT1;EaFQiUy{WQRg$%l@5|ob3o*zntUn6Db`=XSKQRfx!6Xar zNZWL?f5yKFU&7dmY=E94f0T5K!_Zayc7??K)MxB=D`pto4YNGqJAME!LDm9x%VK9W z%#Q7kC$ye^1z%?0Qyuow1qqg6>rq%kH4{YrH%Kh3q*Yj=Y9|qLx3wH3mfxAaUOhj~ zX1GM_j&^CBLBeEAD(mQmtPbSE&`LJtfxI0Ac(1Tz27Dx7Fb3_f&p*Q7uM7H#e@>77 z!uzC1KW{e1$mK zZ7*`q24pW}paf(sCTf}IiX(Jo+YTHw1ALW^5z|@RG5QAy*hhho+i8<>`bAmb5Q)s4 zHoz*G*Awz%y{~h_epG=rHh=^RSgOz8wfr>bEWE2uJq?lH!F8xIAQ+wR7a@P+`Y54( z_bf7Ecft>x18NnjpCrOTK<$98jOYo7Rsnq#Xjk;dc74;`XV=6Tj3m=AKDa~cG6Q~M zxFa%^k74INO8|_7{CD`nwb?!iu39^S&Tx*_iRLSYJ@7t7^d$&?;-7k$Kk!#_{fRuO zrR+^hh|Gu=JN%#qX8$WgU8YEGWUcwEI+{(@orcJ7NuVkR+z zR)ltu^l%kSpByN82cIgUdbc8Tw<}?Ym?PS+%ywlyZ%xpQ3q)qb|Eefxr+Y0{LsyAt zwWl31cr`u&>aFFXc@5(a2l&uIRaDgs=KyR} z7C*o<_UquDP8@M3KxP$YKNrCF16(x!k0r2N+kYnX)bd#Xn;m(nEqlmaFwnbN2d;{( zlV_4m`-333P}q2t>sJnWUNj5}taR*`c25HY9FYM61VM;gSFxm8WZQ<*P#G2!jDiDq z&bUo+4{m^r17dD^?^Qh?=O~?VuLv+JGQO%|!&;V4eE#J~%TG->cl)OTm>jr2p)-sv z3CL$5kOK6i$4Q8w>N8;XJ#Vh315j7=id6962=YPfRW~52O2jGhW2YkXQv|RYpoIeQ zqHF<@J?tvlo&6Zb-ro&&mEimY*UgNbHY@H~hfF>Vsk#QE=R&MJ@w-gXTrlrr`J5v; zw;g#h*%6Kny7e=&L1!^IbXY<8U)A=QRgOtna{vG!07*naR1>c{hLvQuI^QlJymCI3 zgiAxMwY-Wio%~9r;z^OR6I%ba8DCY!gw?a$HtpbXA$VrV&O5rrZqV9y;meNt^m4U- znSbus8;tsC^3tuvaf2wkb4^pkwh+W;+!Kz-%qog29a?T}Cf++to8ct@KQm(&V^&*) z)jjM=6QS_g)wAEtGuy?7SL~sh%WzlPs3LcFg`26IZ5Ol55A8eEnNlj$dmz^pi$vOq zccIaj!#x(@_*@R=k!-Xl{+S&g3u*aG$jUF|CC}&b{x9Sc)#D~#Cse*b+M4Chrmkli zNo-g}_I@Cr%6lTu+Q-d)AlK461M&Q7$&Z1-`o2d2fGLB(S{Jk7HeGv!pA1D zW`gaRMh(C#HnPgkbsdkQBVq*k4{}|v=k^Ek>YA~9|N3v)x!G|R(cwP?iG0Nov#LNP zgs-OByFl&Bkdkq@K@9HVkhe_pMmfqjtiUBYqK*3p-n#_WN$X$a+(n&YMmjx{^ZPW! z0ISFucyC`k2#M5!ePMR_fSy|H^eDR_FJ0@`!vqpcR-jrzbYTC*T4#E4?w`ro9tmy& z^6E^bVGZQcD9o>}x{;YC+Xy!PEAh+mdsaJmBx|dP$}9=JUR!0F?*qTL2R;*gcH(zk zN+dWBzp&%~hre3Sk7R$I(38|Nf;eKJsNtzJum1vXO*Md7=+t^>Ko=#lv26|ejm z_IK3K{DHjNYV{pQVqXVpt$#!8>xc;kcn441OJlLWt6pRD*+T?%GugXy`P{g_GrQ$l zSDQIM>%ASxd!NRZJ@Br(pB02;*Td`&Hi%pn*k>_NR^56e>(jxzqvHBEgD>6sok<+A z#%PBjQkC=?O9ZI_YexagyWyofm55aPjgK_4B6rK-}Bc!y!^;(?nV#% zfg1LkCD1a$6T<(+0bPTTMN{w%S%FjR7#hJYbb~JkA#O*3NNeCN#;hYT`mrwd?3ySU ziT{ck*cm@_iUiPlo;tB>)sCrZkpoL~P2vwu64R&-SauB=ng0+R#fk+ojJUp^;kP)= zJZh3ZiEYb;623L-Vs-){fyw5~cJ9SPNed}8@-WyXN6 z{^><~lw}&T_EQ!hsEK?G__(%85VCp4ezoG7U)^60KkV8Ez_<2(si%j$chT{-ctm5Jm`#3|+nbj50RwklOVY9Dp; z%zF~VW}nfCk9Qpr&X>mb9)dh``w7Ss@hTai@a5dVh|2d@<&-LG%81B}lmU4rJGS$# z{Zikfu2ppyeFwgDiL;DIVnl^|4(d#Fc)foJyx`)K4lUyW^Rvp@?&{88kq){O?CnWOjusrrm-3$XY6b`8Cht5K*)<~j5+2l{*%PA5UJNvjnOB_|@Mxw@a z#kc(@UP|NH%>-eDb2j^-vd5hscq`!VDePxv|F6h5ZMVfqWJkBYt9_Qoj_Pk z_hvzxD{UX*^Facc>b>j^qF_~7%9*oaGa&2Raj#9a5|~s7&J1X(Ok9PGxT1~e*2GBz zbh9^}!UkR;8~W`ob#hwTHqzghhGD4e&~?>>!x7{sQs z$?l9Cic?ita8tD(RWj2}@a~4l1bB2J7NQor(us~0Gu0qI?$0%VV*Z?U ztn@&_c49{=5-7^vDe`>9nN6EBNv1 zu&64&bQp0Ie(vIrkzm!TeUIxCiOZ+Khi!w*VH(lOz6|kQ+0^xJ@Z>JOto-Z>7Hh^Q zL?W;{%=O<*WLE4y8?IQ9W6Or^Dc)^|Lu=w$It<{3&Q^&`cSe6BGBc7Zl4U~}k^$Z( z(L`|T1af1=z}2axs=_pu?#2w-AZ&jm0tf2VCYeED#Ia-SC-i`mo_z1I0OgD*UZ2qc ztzmHGFtgwyJ77-3Zwe5rNOVB1!={Vnx}Y zP6&`Ecv5)%`GI#?jSP!6LBzNU>~3sAMy4xbX&M}~wnKN++u$mg%5^n$aGhC4ZZ&8P zuO^;l^kuHK^SdiD2i^-WR++0I>=^LbicCPaS;L&snUI1iZm9T;Cwbo_L?*LeO1cMv z+^%R4-o=-I*2BI-Bskw*#h1)4IeaxuWm1JG%%1x& zK<**#y(0AQG@y=xJ*p77Ov435a=HS9m{@$QV7hbOD(BDb_nq&pR%EgO{3*V(I+aqj zm}G%WH96!0^(ygQC4@3Xz`#|T z9q&K-{R4R`tP12{NbZLF6=klP=>Sj2s_R)RRx&-`*UulwD>+d(t5+&AmG8{^G8BvX8g!5zKpH=pC0VQu=Th=Bv#_NPZOD+ zx^K1q@plfvyT$uw(gaz@3-fC(DXPA|7oV{ldilV6#xw$vAz0i9teKdx8n3>J(sy|A z+}(}n%G#ZyQ;sY;)e2$7KzSENEYpn{fyiMD`9lQvGXVlDBgxvhabXQw!D&~jZzufJ z=~f^tV8DnoG%9fG2Iw*krpkod$~9i8xMHo>S6e&g#@bi1x$Mlks&J>^4CJyTS<4=KKC0b}Wml_h zmuoP!3UybeGFR6jR>{op-@OogDbm`tsoy30dtvYFv{*-w+2Ip(FeJRP30)8<&c3mI zngQagM5Y_2(GAfayIoE~Vnu(n4h3igo5t##I8gDb{Z-N!@iPxWiogULRT2}zCw5~? zv!QS;Ap)jY-wM8j2()(ey5e{BLcGvK@YtdC=p25S2G>l3DL;Yl7|vA0EmF~hE|h;F~;r&j||ji7{Khs`2l>%Bq~tEm>|9;+aFQN<3L_)SDB;o-9-=9U+LY>@=8 zsE^;@jeYn8zHEY6b>Hy-A4Zf(da2fOhc7e#>^fw+!M`dF2HvG7ut_A}#h0JLpWlHm zue7yiF-=TPF*zegin8m=s?%md#Hbjgfy?VL!m~msJw&_;c#TYlFI9DDwc?K1vS|M@ z(#>fyUXe`uBvDzB{;0_I?Py=Jic9v{ENK?IgnM${p9YJZH}^yrMCQMq+oQm^GcBe} zi-w8nD#H+oGS(6}!b7>6F(0U9AmjBpk?5-=k`uFKQ_EH5PZr!%j5Ny*-XR&>R5zIG zfFRr$L74&59gV}Q6`5`dAv3P3Dv<@H-%*hXLqx3C@-Tp6XDWQVKx96lB`w;<-*bbs z+zqTI>N-WAZqH~%TXnVKw=xZr4R9GBuq!BlO$L?@;>ar*cLuPOh`kDm*mVGTwsa=8 zxhLQwt3K$cx6W4VUk?GkT32Sb=f+w3E+DEZZs!J(nzgREcE<^=!N$JZRq_G4ts3UM zR(*RTfk-yYs+0FejQJ2jA`;R!4$L{>+lsN^%X8EAWVM5UUAb2QLow@+r}B*ZI?&E$5fM!%4b!RQrR^Rkip;zAIU_$*f@oKUq*|#C zLol*Ea0mi+*B2;!$<|Ym27uNOZ17X6&ky*siquxawTjyc5pxG$R>>e$y{i6>MB8!U z>{RwP!*~NeF_R6jtqcj823s%DuyJwTx)lT+YOn^?ZFPn+Wzx!1=KiRXc z@GY+LyrM%tu-E0$3Ts!f4-K`M5L-lM23nY&V>Sq3b&v=Cs&eW0r`T+)2#Gh6X>z`R z=pT3=CbVYukMQ}iUHuR6c9)qj#;STRYxNt6Q(MK`|AZcBb0F6Xc-`-rIPaERe@EUX zcMvwcC4u}}N%Z>rAK;prt~DOu8Rgft{vbxUFGQ6B7sC)6S&NJ#*t^|hyn2*hPasI+6QVHLQyZ3fwMCq71&fk^{gTx600Of zVwaSCZ^R#T{Il9wfteNS}2$$@-l?O`wov z(a$7MWO}8nnyaJMqE`*17{L2SvQO5t?kc7p%X>y3gxW9v--!EAgz5EluOAM`pK-SA$I-nE48PH~Xx6;Wng4A3{r)ouHBLr@S319DhhP`=!xB9WE;ShoRnc(u4 zJij;(1D-GNF06`_$teQEkr2`m-(;0o>wfraC( zfxHtp@)I3-Lcf!>etp(I7OW7HLLGbtLL<*R>(qrHek-lZ>fcZBxd{O9cSC+h{}p|a zlA~h99)rXsnVgXtHr0OF*B*E%7W1zD=K1Sqe>eD8*#)(}jjT_ah6WfQ$ZdE2ys{3=T#V+%!v|d)RXg7hHRlHT45hJ6s?BOTc4t6tW?zuLTAyktx zcQdk;>V{^>m5y91Y7!!pwTD)+f^GA@*mJLb25vrI2ms?I8!|EJ_})P>f*o4(#c6FZ zG8lwVtvs_U6%ALU1G1^zvv9WDnXIn4s|eWH^Ht*aN=7}KS{hp{tJ%klV5<%fQQB#2 z{aCh}0o;s8A9$aRJ_C`vW4nQx9+}!VC_HBdh^`D%bKtl#HMx>Ft6~mEM0B#gqi}ZJ zUOvE+ps{sx7S?lTAR3zlUG;StX*Yyzcbcr#sqQ=L**5<_!FoYheErFn^Y@Ivb+~26_f&0I1z)P+ zfI|@SD(*VNe~-U~0?9C7jgcMMea8D6VR2(+#;aoBiQlVTvTC}9 zx}fpv^(ZppjO}-UG;{W@-ACz*brL*wLn1L}zGKjOfy9O&wz7&5HsoQ3Gj^q|;`pE; z-Z9dj)ZT2uIJ)c++bh|$bXIMV>HcPwGb|8P6H%*rTMV$x4?X7zU&*(lrL+qa)wE#; z%)c{$8pa_%@t%yx5)TfLDD5H?2@(eyT!JfRYzNuPnVpK6*s3H$HzYwNz;SXQRU$J3 zbKUIyZtR^KX4A>uR?|jz&li)t$b|WwbVhdlT@Zs4z7D56_0pK#w$%6s~O+eNkplt_~E9$p>bu z&SK!sY}84}wCd|9{+`oFuaM5F1L_Ki&h*|AY8v<{MQtWfL}^ z`M0xRfBu{CWiw~B+PZs}@VbgGGZJ%M*Dn#X@19HNpR#K_68xG~F~_~8@K{!;wpPTR z8}_F%B*{q`>_~O&lJG+ixDL-{g->u|-9I-SC* zGk1aOj?wRe*v?3!NGu#=Z)6U&L5m-Qkm@VwYsEk?d;TuKnu5%1MPR#2WUB#WQ=Gls zwO7dxZ1@vLcI^`Q(~#@yJ;%w#rvZ#v8(38za~6SS#b;#|nQTh4N;bv!jR1739UEC| z4GXf>^mq4r89Cy}UNza30k54Y;%X3$(miw<*AM}FGd{?57)*i}UWk;?99O&z%J9&G?I5!ZjlVob8T#+MQ*EDaVF?-I*$!{XL4$gpq_-2ZlCrPLwam zh?WYG$?)Zx49b#X2Xs|i2Tz8(_Dcx+!q#UuM)+=g*^1Y5wIcJ1ec5?c@MRMi@nNvx zZXwGo?0t8wZjwAme2yfhiuQ2edKDzQ&kDZ0vbQU19QhnqIhrLOo3J01!FcL>oX=75 z7@Lo>N@xs%QwQFq5m6v$k*ur2FUO0>bQ{HqfsUesZp0BNpq^>WxZZmtP9s*HKm-b{ zXt*2ljPFD~3GhfZebfkL*+q5u4swv!jPD@NuaV8_f;~m@s6*(cNjGqfo2yg#K=w~F zfn9~ce3e;1K?8ldSkgm!_Xug6AoSD|bF-kpQn$^hc063W5F*# z8Sc9y*K1T5z}X)NI}5W$&h{$egOL&}Ag=^nD}HmW+&l6mZR6U9A=I5VnoBMyLOT+f zqd=7H_!oy8E5unOR0rM%k~zZMtv{=hbAjc1uEVcf*9Cia9lRKT;USlxX7+>aqdzhtlLgW&)2SA0SMPxh9CB?x zOebpMz5G36se2J@K!ECIjLS<*HLDmnpfkx$FxAnybrHCn&{dfbWM;ME!&R|Xg0I!V zsw$A(;Jh-VLV-+1cpm0HJGdUkCtJ984YVULc3VH3uABp!?t5K@sGBsaS{377?+NLh zosab#cX9@Y0g|{#)G$J}LL?|1l(`A09MC*&+?!hWd0~HMzTrSVy%@&MWq!bEl1=RC z+yJ^gafcY5;<_0ScKSWhz9}F#5uGLm!x&lDNb&{0a3tfWIAaF zkU;+RZ%^by*do!jqZ8`Lrb+hqH1BPOd}exKY6|FtZ@=FObY|iol+AOk;7&Vn5-gGt z8LYKXwOmi**I)bP1h3|~Vy_&2W9u8=cjCRh5k(Snr(&=X{M?KFZ^F0GXV-ENd+6gx2r%`!zY1yRNTFto zH+%kFTw6wFR>Y)tD>7NeAPdA@`(4Euuj~7j7;>PlW%P+*K)ZzKF2P#K7)OW041PsW zd76L{(3M>f*B2f037%PIM5d}jY$kYS!6`26^GwTR7S41=p6n9pnFbG_b*HKU&5m?} zs|f1iS-hqys=-}Z1yWW$H7+I?hB%uF*sXy)Yp;xxo!7Sd9m2|WNHB5mRy?-~$eze$ zDS8rAI9Z3+=bd=(WME*PkvuUWH$||i?A#Oi#O5edGZNdCty?4e5(xpfLt<6~Otzlq zLOQWFtL%H8&{fVu_I%j*+ zwW&Aw1RR@M-%;0l%!*Z3`#8v%m;!(8to!(8e0haT-#MTCgZuvuzGTnvY3xYl`yCPF z)>mn;XFh2q;TVw_3$<1v?A(Z72O+{Dj$-)o?u>~uIrp)XR$&`Q44^dZWD}wJm4p}0=oR%Jsj5}>YOhU zLp(&r0c0~)h8V=d){@UxKqw>N2HvLJ zu+4;U&szUG-t`yzMPfra_$wNjO+436iz71~MYVs~JylvxTaloKF#P960F?#cr?E{H zV(Kc1=`=VQnbIz-_Y{E@us3{-oplDTb_mv)0F_RFLI?1Z0Huc7^uDT3W7j;P1@D>7 ziix!N`(v?78IjoudC&@HQY9IOvGo;=%&cRi6LRM?`$av=ftsdd7bI`inva6bjnXg? zUkz{#PDTW0&-+Mh(Q3OUkLr(p~%S z2tklUjw0(b9k3AywDApufqSmiN;!tJ)tR|^eHDBeD=OLjFh6+W`&(`A;1cC4uB^4% z>kMD2wq#Y&q~b@XXU@(snbGrpq5qqUlK^hj0~&zskVkRvHz9P9LTk@M)>|{NaJ~kK&>y1Y#pQ$wUMGm zkeZIT?weNt@TWO%50O-PJstv+Y9 z#}5&3ulIkD=YN_Y>rcFE1-)$G>)Aa7_{uWceFMa0iKX@4eh`~Df_-N8<4kO456_wr zo$OpTW2e{Wd64yetxcv;dl0{#5%wqez==2&`{je?Vm}Y$Rr!i|ihDg)QXcqyiY#lJ z#;^6A$-Y03S8D@#tN4jL`4}g6#-Q{}erJSd|5*ItpT97}B=>jVeE^}V7>!u2g|l@8 zypUaER*AlT{<)k})^;EFjcN(a@a0474~8)h;lCjK!Rr4{@WEkgps?tw`&66he@*ZKw_Q&W3oWrRSq`eSFo%*!*;LdmvvDb zi~m={+MMrv2yFL?FDfJ*D|&Dp3r+)%Vb0gR{wUm|O2&;sP@d^bs+Ri>-oX`rp2eH% zz|}v=^~L8l!1ax@YU&x*UnLe!f|D{W-WFojpN0%+1d{<=ZsJVh$BM>g_Vd3B;unMf zsV1OSeBQ%Zi}=!=j~MU1{{8PK9)(QQ@d!gi;op~fcuFCFKHOrd$tV(Hk)`l1z z>CRM9l}*c9A1f7AER&>$g;d4MvkVxpUyi#1-pnv$?fkBE+!5i`>6s{G6Iq7#&P!=W zRLZnJHTAEWO|N7t-LRsHUJ$FSVC&Cx)s#k@bG+^uRP0BkV&+qNrB^b3m3wqS#?EBE zSY6MCxims>fDlbiZ%SR?S{=whlWOg)WCpRhPpZ$@wek-5A!^_GQr8y!XHS4COO~)! zc{Ow|YVE84dudWdT+l|3-leaqZ!6^)=y3ebufg>{6{(hpa zXQLc_*1rEbgB7BtGP&K6+Df!N6EW_>iFV`~Q1Ry{0d#6Ap(0taxelrVaejcvbVCTP z0L{2wm0>_mV^9rYQexhUJOc7zS35!ffxL>x4cTHERJ-e0Z3ST(ox_~Boz|!C0GB89 zgx1VHDWBssi{mprNnimJz_MqfhW@SJ9b4wvT4j^U6@X=dcEvwcCXgf8)dzlW_lbJT z&+wj}TxS;i#0q4kdm5`*M?zdNT(?eVMM7lmXyhp$c=dIFYc(lM)HdzOReX7xGjJN8 zIEwbT6GHObz?a!%)wM!=O;jDo2XW5A`FBzcnKoN15^r}%t0ssT_r89SXmI$F`NK?7 zi`nyvG!(;^Q+$8Lz5-sZ1OyjNc#Tr0VR(0cw3|d`r9y9q&{TU>RY)p);qWDjSn@mY zWi}=JT!@unu-i^z(Ak8_AhcE>+}YlAG16|^`jx%agni1A8r|T_2Hn2xhPFKozC4l7 zd11tRB#=)-WICC}AILS&J9Hrzvzsi=X35$k!8+?%$vU3za4u{;S)sv+yu0bQq{IX7 zRWL4luLhogF{Z+3?Px({Ag31yh6XO6ssebxi~4ueG(x6glnt5DpmjwU$q~P2AfIA2 zi-*PS6E$TVA`ny?etr;W?gG-v{<=$)bokb0rz2AVEN#=+s7e*pIt>F{vl4c7zIX3q z2beX~DuQ>3sH+-M5JVFLfk%PhWJ3APfCZ%==qfj=py|~W@EU4zCO}r5k8XmH9Wn9B z9#9oku4Sj9IgAh6w}D&|0mv&NGlHK58m&Mu4CIm(?D?^T9{V%E+yA;CGNVKVYjr_F zZXF2-XTi%f_tu4teO=#Ji2f725)y@g-?c&wcn#JFKs)rXofCPR@hTltv5(b?=DU?n zE*NYE>!<-DV-sHv_^IK_{`3N2tOi=a;LDMmrykDHnfUrcU~`6V6hV@;5B9>oQiMXq z2Ja5Taos+^sD-Jpkyxvm+YRt40GM9dDpWPT^JRk1yv`7)PKa*3+yFwQ%P@@fJR zMZ%dqdq;XOBD0DsVQ}hq;mfG~z1pV}HR*(__!5GoRqHbgd!aIH^0*nl?%Y=sL>^0& zJABzqe3D@R<3Jq0to2+x4Za-6C6fRy`_b?|>?gyI43}kO?3(C1P}gvt@JTD6rh&Rj zG(C|II;sxlX@uMz2^OymYh?HK=Nd#-NH~CNg(#uVyF{kC$&6@ngj`mM;DEgQJmp|^ z#EM;&DGQL?)a@4TInx-+TFYa`VO}6NPjkrHrqjIwGdbBsBTbMR<-rR zkR4}{Fk!DuBXMMd6)RXP zgMnC})RVnBg3Vil7DZ%M3A>1CjzAJApX7!cIe)qW-ApVU$=Xcl_E6P&e}x=j`ae>Vdr}FW<9Z$@@TlO+Ot+7{zr*XIRo1eJ0Bi~jGZXyh?ycAbzsku=Fled9f|fdCElNrLe@2RTGD zF+@tw(^YiN0_nS}1;v8zW=PCRiFh=`6>xk9XjXw9BbT$viXBH*X^pD1mMbE+l1*0u z(;(LZ_#sJdSWm-V%V?##%~g&@r3E--r`G3b&U!Dd-Oey2_xV`>HH*Z>cj#uhv#yB!X3p0{Ui~x+XTnLmM4-uh zVb=P5Ag>mjCLoIED-x+kLZntmDJIo13Z&KgvtxPRAmH*0*PYqZDfX%(E8}1&rI~y; zfMRXyYBKSz?^l{#laS}`9;YDnD;*3-@Z&%}zzN`bq22fm*Cy%krE0~Ezt@p#8O{Qs z+BS)VthE@>lTxqxaW_4CckjjO)jRkS#=p3U(WQs3a?_~*H z_r6b)niVdGogarU2XyC{^AXOjFyghFXS;SF0Dc%Td*06iW~p?fI_U~#f1OXt3LsXZ zvx{p0bhii!oWP1Nv$-tCi^x0-2vZt;s=YiCRaZ5R+_0Z6$X8W$(FE9>1*W@UZ>peb zm8oPC*gYNKf~m|-ZLXjT7jsY_F#xGn6T0BAT8+jq zLdB(p+>DTvHw{P|rCcGXd{JM3p7*9g3dFHs-})!)sKAUpVS zigjaa^9=ZO2%>7IYoiqt2`&j)iT?)j>A(Z^L~8{vR`v(m?^iL1lf+WCKa2l9jW46U z?8*C7Lh3HQ%y48&&Npj4c7-Yrb3Gk?VAdx{ObF5p8@`9(%U+D%<9GGKo@Ud+Ro71o zM0bT($)3ZXcu$gdLgoWJ38lCfMWFZO^VaWu63qH)KmQ`J`s@EckPrLGw2CvCoSqPw zZ!yCId5g6(Z0tZ(fx?bZdp7K+6`W^A#7^u@lvG5Q%HGFe5N>k0)9V51<>QqMv(v!K z^emW$%_**@74EC5llfh*gE-r$u~8A8-z7~Q;aqt>)r__y{#2W%Y8lCh(Diqo_;|4%*Eu9tMS0$3~0vQ*eGy71}M9f7|p2E_?2({4#yUEVy=4%h~5Y z@%!X(gzs?Y*;Tz|8ShR2>KcTt$)IfiMuK??pqc$H8%P6O)0DbvA6)?Es$;#t8ElqdKkw^IOB;C*WC zGd!E)S2pKK_DZZCn`V7tJ6){UV^yvX;gpmE$kwe28e;3TA`Bj8{Ta#ddVL9pj{=dL zO(q_KG|Hyes@D(m{10P4e;5Eh43PLTfTWYP8-a*dt)r@K$Z1H&irHufPvVoA&s3lw z+rvXV)A;`fxIDrn_T>w{GI0|B3cTy=Mf-o^_jc=e9bd)!XEyyOA@=(6`Rky8Og>?4 z)A{=Krzb>OoVxn=U;g31d!^|5dB<{&&R~n5cpt2>KC`FTKPwPF!g|Dt_eTQC59B(X zD)?yxKPda?NS+b=`&u3GFhm^!aUB0V4T%~3cU#u07wrGfVxp!a*Bf@NwFB=J!K?i{ z5}Xd?nz%qNk-!Lsbr=V$%oxzRrhhKq*Ax4R#AY(RSQYdku@itEM#OOK%kMo5A@_>I}<29a1{E_h+jAw}7c^3Ru_V*9M zCuNDcmOS^bC4M~vU(%EKJjMrqLtc0n&v%Bi=CVK7J^n3V)CYcV|DFqui`>*B;GgI6 zSug){CU_;{$;YyHqK$lnSZc+-Kf$Gy5cr!JIKStw_y33_8j=8E8j#~EC{V~Y0De+B zW7JjFj2VvT3{R2O1oBo)H|3OprJX6rPRLw=2Uk7#sVYa;vIgORJG8j`&L5CxzpFP< z9RN|yngOjhbyv*0O31kVJi&FKAhM9vNuaJuN4>8>ODwqOvm=?I)@NrL zWyNOT#y)knyYhLJ{c)IJtvbw%tywSbP4+A!=;|T3?nxlavgSvjjHUHSb%{Ae8T!8FY8zL?}m zwS$bs6>NIEY7d;y)3~$mc9k@)ORNi0ru`f6<@^AKyz_D`p;z$b9sJY^`@5otzl$&3 zx-(xfiuYcLsdwVn`GGZV8!>^h9}pPw?_^JpqW{PUI!7L68h}pPie0}OCfP2mgZutF zHb8M0F41rYUtaO4P56L}c$=tK#WTzr3z7!B)_JsbvA9iPP&aJ4ll>IsjHa;#3Rh3V zEwO3#|B|bFAQ!E7Q-hg9Zie)87u*WQY!`@iv2h~P&n7gfjdz;B^@J|1#zjNG480qg zvitp&scCKsoeG{haoPjAQj6({tb{`|z@sv?a=^EQq43{svg+!N7ViCw4$!j8OV_AT>8S@nKg>w#Lk3Ip7y32N_>6$3TNmkI!#hJ5L$ z57EdHV^0ArSpbk#lEiAvk=P#~uT07+wxh1>`Z|SOVndonLfSepc?UezaGO{yQPF+8 zI#t>QqOMgoUc1wnclfeenRXSQ?T{GR`kvsON(y&>g2aqOaWgwHX@*=Jey& zzmEc8Ss^`@w3E_g{&(QZJ2>*w14Xh5ScNb9rhTZ8d~Jh3>crPoH6RE4+=f|LKNlL9v)m?87BGS$jj{cx5Ao7U(?OG8Rp+A z8m-ldx7qcp{iT4n3gTEcyBB;cvjZpc!C+tHdpjXA*L@rb!xn&N6MJb**!6_CjzpRw zepvM>v;FRzXRZGk5zv!8)v-5t(go_rCYh$`&hWkXG=K)j-;jAb_v-{}jG-1jBa{?G^viZ`_;n{S|VqnZ4IV zQe>CNL_)Cb4!hiqzjw&Yt4R#k7QaJ`R`y>ujBDV15L0E+{Q=$C;GW$VbVX(?u82CK zt;kup^K(ZNxJqcN86!@2_b$FvF{vt2nj%hx;6z|-??7JF$VmMII&nOZ>&9mK!f^nZ zy3Q`v1q*&X1XrahG6(thl_NR{Z}%^J`~Yvo>PaxrMK+~DS0pGy+(dSvAr}D!czJ9` zy`t(MfrtZ3NQg=mOabr1HnPBjW$z&}H%gaJ8gR@U!MwyQD>3tCVKB@!Rs8c+`^*SQmN3XL=^cD|hy+IEJ9aCs6z=Zi*;M2_6hZh2 ze8B#j4b`gp@J4JzWx&lW;E(FQb)Thh{eK!?-r1j3{C^d{?vgQ1KCRl}k|ndRcEz!H z#XWW| zr_JAWhF$5X*uj@O(it%1q$>^siTg4V-U?+~Fo?{`&ID$C}i8C**_3|OuH>`K5j3fFRnXsk|!z5+5`AX2Fa*a4bV zZJAEanH!GAhCTs&m|H9 z86dW$5-2zcljxT~z+0BcZ3&^64NW?cSBYl;cozL_2BKlWq`5Rn``S<=G*z-Bs{+bezXtZCSt|IU;=?8(7ZiSt z$&kw6H5f9G;kc@dh$A+qA#^{DFYoTZ?`SOtbn;~v!?{E`!&;Tra@NgNX?x$bZ&&eS z+t>??^t?mTW(hLoza0UU;Y;>ho&^$G*&T%~DnzDxW=Fz>3_(Or_$uc0?}y+IoUU#) z5u)NYH}Bv|HSkVxmFf~?^E=pihVlC>Mi>dN0YPR**~1Y?&xq9&k(uGNRqp68`xs>3 zXT#Ez25iO+y@pZ7LDp|rb|o^`UiWD>2P2EFw3a&}^SJ1kn4ypNa~gv^#C@}XN@=($ zkyU22JNa(lT^N=f;H)ftx4onl3=TvfmTh9zTHC>^pR&*C=KeuIM@2i6IR!>!y6;5D zxB$EwxT--Jt5PTQ)bxKBk;wo`2XDbv6~KTW;N|qB6j7H=aIDyxs=)g$ky!~OD(|_X zHO%%g42irG#0(Rpo#t7MgotD5kIMXgmAgef4}5~44gKt52@lyw<* z_T1R8yG#S@%2de*-m4d#Zc#=+v3r^qNcW1(YtWje%;!g6obAyw0dIr&@DAN|km0H! z0kmx^Fk7}H5NjKW$?;{Pj&b4L`$ z3eHCSa5h^YYQkpt@Fe!B2cMw!egp3~VZ*ATO+O7D`BxCZZrA}YCQf}7sHo50J@``u zqH%+t0_ep+Zf96gRRG+9%&aX9;KOLLshU%4@~R_XMoy8tndTLcSEg1-mldQ80ro0u zP|?FeLhjE3$>YEbk|3^16fvObh{j!l$&oNur=GLn3Rl};6miMcMQOCefc7pC=>mqk z6_Z!0J$FEesw@Vswfj_(2CIEmQ~Owjd$z}V68LmMbW}k20X?BhN?^m_dxfC;xp z86lq$vCRMcyh-G{eHasfXVFe&6-P{L+*NQnJ2?rVqFQks$*BPAKrUl22*_0DTUD}* zLa@wmS+wT^ylY1R_ez`EEGABN@MYzmXTjzTVY}NBXg1U|!eI8tCy2}r-TgDjdC9cn z9?09|KGj;zg3K=L>H70i*u{0vc7jQruXFg)#YGieJ4G;kH@?Kp{f7^KzN=zwNt{q6 zSFXgE4wI>vv4gih?+}^FhPDg$U){S7&s>rIK#^3s5-()-&gq$V>}e~zb5M zphkzDT+R0UEChofL{7)=tp~4b{Ye~hWe^GQJ}f~w*6cbD6ST9|k4^$aRcV$HHz#;y zZKY~6tGJuN(5lyi1cX^@p=u2u34smxHo>u+zsyD|V3vtV$KN}l^>-`M2nwh?Oz@ZO zYXww#_}=8|`7!_iAOJ~3K~yu@KdyaIwUxv+j=qryP#JZWuvqM+~m*=v6$708$DE!y2d-#d>Y1^@7Y5lhs_INDc(G!3E1g~IlawBVN z62f|~{#{j_X2YIZSdYwi$9rc!=V89TkZ00Us#P}Y2&j^m*=x1`JHuAg zRNtLsfWwcD?0F>qs6rZ5U)4gP=zmARFM~W^SCQz5Oed$~Y}nrfNe%p-2xfLH#{E6P zXIU&Ti)UD2&p(%a)KQ-v|N6U%FWDNL24A{DkDu@|LJ3J}eU*EkD%vZ8mPKzlW#eP!Q# zdMdlR$17sjY?ALC+gbs!ir7;CsIm^97{uYScUNAYXl<*4-f0pwlLT@KY`ThTSH)8$ zk~^`Rih#Of`y6>&1+uEbvB6jQJ%TOhcppN;);A-%GKqnaoC}s1$y$V%p9AuWjA~K{ zfuwcX<`6+CBlFnj4Us6x)^VcV(#R@e*^ot7d5UkeMa-^r_(|PYx-3|=VASh66QX3I z*6p!_VRow9)cxPF|5YsErjXz9U$cPS6sA@(Pj262*L%f(Uy&}li!bl^bl~4tQCi)% zyU)-KcB~A3+{Hn==gVQG@5FE_Hm_6^It}po!M)fFQJTrMFu#?NqS;>jD(<~mz*`Jo zszR7ue7V~JJU+0;uf+2p{_{jWseG*t?%>2b5;A*07bC!68TBl?u$gR5jvD|T_cB|1 zmPmf{3lDMgEqM^G%1{}StRl!wlbiyWj-nyDYa}ya=3X@DPSl%i1ol1zkU8*IMIr+= zm4OBss8Ov7Rbl@DpYg0tJ!Bc>u@Nk*R&e(7EECv>!L3L#>=Jem-!T(I3HWmL>ad4d z0Glq^p){FV!IAF(rz?S{BQhP)ccnF=qRp}kh8UU93<$UaOx<(80yOSugsMR3u2x$l zJUVz*JtJrwQRj%va|38*-&ggIy=big~)7#$az(?ua)i% zyvi@z2XR_B#QMhl+M!#r*}iEB7+m*n97e^2-&GQ^BhS#YipWeilT~?TKCc;n$b8%> z)*g7TsEcH4-@pqygb&CwT?z67c~ZGTmN0zMpvCvyTs<_WIp+%|o{RU-2azPw8mefMi@oY85pe09w~Nn}*>^{QXum5jc9kfs@9RZsVWRR%z0!pY}Sg~6L|}J z?A~TFg5BVNwCynib10BtYNM=G4w-SUY|?q-8b0xAhMjJx3Chk5f+%Wuw1mh!z;(eY zWM(stf-&L{-?gj3sa~fcQe9=+G^E@RYtjnfNlhxRl*?DE6s`(gcLU5(*qErA^_^iF zS*7`dINk?-mv&%#?Jz%Y#kI+#HCplh+NRyPQjyLG`bz7e3eKhgquDxU(ji&k5AccM z>-&!aX&QYwt4PQy6i-9&szHD+|Jf5lbtYscNWjEMMMdUk!;B(6Xhniv5lI!zrm8(q z0{jivb*51uA}Si`irCnx_=@;|>5RvJulUCSuPM$F6^=m5B!un~nKU>;u3^{;dvRx< z%niFa3+G{{Ln{)UclY;|_uj>qR|u4UXGNwu35XCFDj2elVELxNvxzh17FT_f_>sLwATqQAg_E{!j!Zenn{meMB zCeCP2&Pg_CTgAqwAS_v-z{;6ahuOOQ5iuTXFVCd5VrOy1U#0f(LBQH91n^f``CUUX zzL~t-nHuLxovRg(fF4MsrUFJLeh{{O;$0(?Wpt`pJ(aQ81yEOj9;*~(<;~1MIrv_PTHCeqO*Llj`n+?CJ$QYsM zPaL`4&H4=JjtW;DSlOHN;?FAjg{~sb4KHFOJ(D)b68AAManclb{Qsx%ePs_hdm(y>G(H_o(4NS37=&i6tCSdAH+d z++44_MCy5S5AAepWuNQRwNG4eoGSD}!awW`ts2O?HdG6HCSQ~#%9->L2oC*?$Q;OZ0M*#}iCk=4E%G2_ zl>6_quvp*u8U;edY31y+mS^{$WePGNo^4{4>5Chw7mX`BD6E>`%JXFglpSVw@G3fv z>UukBt-C;8;;kw!*rd6ZtZ{4&%g$974xthhxhhs>lq-S08usN{S6oK*PV0lJ2!MEY zl|Zc#68sZD`$XQJ2ea;70G{<4&cgYukhE6=j%r2acWD^?4SMSIfUkm3`>Wb|Rwdfq zU@`Xmm`%u9^>-_F6}jj%f_K*+$@(yoB@&v=fc;hs*qokFFWAM1f0)*8PxeuE{-5D_ zWNqdhxkl%Ju0VNJrjCRhbpU@7@^%*OOO}uvV&7*Ks|w$^sj@p{#w7SDOF(CSw;5Zc zWColMo#bq}XPJ@L>)Jn|tEGFv2gILu>`Rw8zr(6wDy`*;jCbFE7|f*XlB?#ee1A9R z=1RqA)=^gV6TA3whlo&t@^`*=l8~x!Xs0?;#c*xIzYe?)KJCTxu%7R$?csN)qIVIW zRrj|d((X#zIs5k~bk|5Wki|Wl-FY4=`QA6q-!#vYaTbm%`owD%h|HhKaS+U_D*LNmy5|cBE*YFHB(vTz|N3o!ErWe^=hRXyZ<;jHfpr77Tu~w<}(<;BMI!(l=)c<#I8R7wgFDt z#r1a@H1WA-6(-K%vgw=Ej87v*Zjklq2@zGz{sOv+l?6hs^^xgb!2GwWI=Nes*#w|= z`drmONmWWXBCZmsRR;JlQefOXL#nm?4uQD?G{3XjVwmrGhG*F}iMl&M5QzPsg}uOl zrW$U80{Kx{Cu{&whYud`$(a>oo`R&z2*#)RxwBynUQ@RTGIc;#U#U)zIGuYe`}J7J zN04ic+3-mMjUKR2Y<(N3CpxcK0sBC+l-OZW5Viu!p^fE2h}LI~wzDK-vybI8jUBWbb#n zqo0Uxv-LTGoty!~WN}(g&YvsPP|_ZETDu>pb@MuW$?)IZ^Ot?+`kt>1{$OpR&U7go z;k{gpzwQI46<(QbvUZL=jW2N(q70+Fp1~J#eR;*7M4xep@BXbK(^XWlz+gA4GDy}y zvG%Uw<-1?ANT{?6pNYc#vr5!n3u1apMO;&4ra6O8chWZtC{A8 z`al=wNGf~DX)HP&!RoWEPL*te(5({iHQy8=(Ij7wy%rlc$Lh|97HCEFwOh# zkg4uIc7WV}8uI*%3WKI0ywTF3RD6yVwRDR zy{xV0XIT4)U5?~=R`)Tpjl1@pkw{qf-}wu)KEt&#;w%etR!yVR_$pS-&WM|=O}T=v zn(+xw=tSZaHmnii`|7!1(lxO)t3rP7>QYxoHxM$nLV7SVeF&fLs>QNvZpohf6vn?2 zAn#N*Rf$YjRj(2vY7Lcs@0D&UMYuLx_Z>U=EHv;wC=(#|N<8 zO#Hd;y&ZO0tUWOoVxe zfFZswR^fN#8Y@inJ)6qMS}oR}eSue93FW+dlH|J=}|@>_%yb;f-i>&l+T3Z9Si9lJ9IMr)c9=H z{qi8VIVObN^#S>W)M4;wrQ;xWkDSQ$WP9SDev+WO2_k>}jA!y(058=OZS{)bTaoZq zazrdq!~QL6tyI!WstPu%n2uQCiT5hv?EIe_M0xg{9^%@geaLL^k=Tq*_6QRD`ZM|d ztcu=Mt%LZWKMlF_H|T0nM|3<3i2yb1=m1Y5E4{srTplWZ{||%D9A2%o_GZITUZ3}; zNoE`cB2XnN4(N)=PHY16?`)mf`8^V@WsTpE*!!3Lefg1N`O`_fr&_nw^{+8gM*99i z@YV=+DDJ@+XE7V(Is$$qn4t?&a*`xROR#K~ppKZm8{+mzFy;i;aX$$^btbroCD2zt z`Hu`FuAsAr3p~Nw&?}65_8=-*JJlvV1Q`Ys=r+U559q9YC3CjZ`r`DrcB<)ivJ6)y zMek%#M&bJ#yeO~&q1EcqiMkGxYpdTG&Y_-BK6+mJKpdZFIXCS%|$FLG6I926TF}k<@U$57?{JP(+5>7c8Ns&MXRKHcPZT%=(-H z^i_rsW=Tdhm_oHUvg>O}0O~3@uC}LT&(Tf$1PQ3(ROUwRFB|@Z;`L`T9C2D@*5T7O z?0FNmZ%4iX2~pn-zO3TlhT3FkX1g7}+r?!H|G6Rq<<}}53OiMX3ZnyD-@j7fT=6e% zKwd>UqV<6TAFDD1OJRZe-!c6!=jDiL1RSbOcrOSG+0$usGy5&RQB1-5yivXNQU65 z7OKQg#e)9 z9NB)&v^$hmQ9LgX=oZ0jFRs&U9|mZ4a}91-0}ScNS~FYWOjYdHK;9~-g05IGTeTmm zO4^;jDv_C0Y*y?Y(@1Luw2s35P|t4{Xe;uEof~Dh6uE{%pgRknrIHY?BBhJ{5?gCC zO}h!+y34d~U2-e#PY|*S0Z3*Q=Sn~FYH+o_){3EwKdT zorbluw`x`fv;PoSDy!J6;7jFSSf}TNuc(J0(qlzy>=tF`I;*^9+Tz{#*N2H8ev(*` z4K#EyXoHuN*uj@Bxx#QIE5K;@y{qUnM83n=PZLkIgk)AyUa23?G%{Zwd?43X0ro^! znXqgXtUdx@L0D9n?1Y+HHVv!nNX}R5BcKJ(cYvl6Gj|#n%Gfy)vlRm=Mr67P?d(u> z=&7h`a{BuH9eMypB*iL~m@Zp03qag~r%?b&0B=q1g)`@*4pimqqmXq`wxF4S(@kxE znDcoSKz%Eae{PThJCEH2al?=V596G6&R-_*eI-$p*$xO|qlv(Y4I^`aE;}FDP?T;Q zYz1hyLU1;Tt!`$oxCx}Q0KO|EGXtWh@v~px8TD336g*8p7b{{$*t0(i`@4yAJCJMh z3<8vQKwfni0-!Y*-Eb47i|E?9s%JWDaf*q?Y;PS2c^RdBU~J~v(F6S6_0u;A1_=K( zac`=vdfw{XqL@@*`m78$He&;-$pD~MG02jxj#QWh?8b;TH^ml)V0ReCRUJA1azg8R zHnS(4PFXiZM)vQO&Y~*5WY^Z=E8bfmI$7)L6l-)8@TKbNQABy=-+EzRV`KfN3G^%W zZIYPf3cfrH5wSB>eqGa@j!H+wsy#M}_>$SLCj5F6=Oa6(s&!f2dvy?|A_}h#X*~=0 z@=5^%+dqxONC)v}t8`&jfHuf;$SSTgyPG8vlw<(&-HgNpA;guBY8yoTF!)mO6>e~C zcK(<&MJHTCd@k`^oW|a%p~xM+a{cEkh<@U|btnUxR|hE!+-t4KbctO119Se_T!3RauWdi|F7;_yX4k!Bta_e>DjaY|EKQG zb*0Gtu(!Hp7UBU)<(|oNd~DYvQ=&*95C8(m5M@Nu5agiBDk(>;3=3ML5uUyc3J^Lt zZ!-Zpv$*dv4Zx8YWLB-w#d%j1cdx)2AZmbw3XFFr-%VhH)PzxVW-~%`0HQV{qEL`g zJ+F)io5XRifqDx*Fe^+F)1Ao50%g~}pzCacI2Z=G(8w8@#%DW3hWdL5qEG=P1oTH> z9nZE9r4CV{d?U(+kKmbd)LPE2YiBC*nl&H6D?Jb~qlmRI_J5{d$cQaQ#Iywb_xLJ} zG0AhuvhFVcl&jTfJJ`~Fo(f+w@`F_gXZV%{inDO8v-7G*dUQTmB_m3fx6rNkGrVC! zjo81Q_|NK4M&@4*v9~%QNhbLI^$Zu3k!|_FT@Z|_TNW|@!i^was?h=_Qkv5C?((wV+p8izjp);5L+H1nS_$XNQw&i;!OXU4NvQYK(F8v z2VXiduv7Su5t*GN6{a9EBY4M3mNZ+F<>RssGJN^#lO*^EUXl5VTs(Ig7pe|-3xBHh zjJ(C|G(Iih0~ zYf)>>tt9eT2D_U+djjx{fc+{15eeCVfb?pU-l1EsIw4;xfpWI?=Z*CZ^Y@hoAQ}W2 z@l_gO22R{X_&UZ_oY}#-MV&^7xOVLC6#hTMF35iFw8mEaOE=H{Bm_%FezwrV;v%%h z<6V52*_07^Vzq~_x#tA$)4-SN<>E`VKU8wmT|eeO8c8rrvKOAfmq;SZ>G+v~2)Xkb zh4ZTh450*J7T2sK8`C64F*ti~bQVyTAR7FnTDPmy=UGKE!-;4;!thV4q*zb*mlnGE zIFe)sN`!v?>?`3*vSDJGzaEQUWW(gtj1`vXQd~zBU!wiNBmx{FlVKi2WS(NbA`Fpf z{AO|2KU>S+3CkVvwY6dvQb_A~cbcj%gBxV|Og9LurRKu*I zQIRKEU>ds~vIz>_)X5nrc;BFC&mz?m&UL^snkabDddPj*PSYar|-Cw7R; zkN7=97QtJpg9HMd5Q9wstxB?`@{ACX8OxbKL7dVo?D4f7tD=F~4X{`xIIf>_4RnqK zq+W-C4M2dffa6#E-r3O$Bzr9OLuuS)1khUq8x;-cDv7D2U!s6zQ1$bRkh|BZl3BIW zIu$r;=UIukY&vy-Ys>so5WrP1v>v`TpZoo+g?j|np;bi29egB!dZOn$Z#|KJQ}$p)N^$g76qW(=wDrP8-^q~REm>2y>&-*?)rr)mF# z*t{ulGVAC>_peAK_Ss$B;{Y*jrhV#G+(&q`03z@J(n*pySqIHELGrqs+abex#Qh;3-HrVn2_9tfPHZ1F5ONKrtOO&xrT`%oF%Q>?Q?PDNnt7?qJ$ zK)o-{uZzIFQpMvAgIe3fM&OB_>%Wmk)aTa@;>aU(MUb+OJ7*RpA|@c3QSxJg#0lD4 zO6$xW3W0!-+7p?0cmpJNB$7n2 zWdzn6bP`7s__9{Smx!=LMBCMVsCKhE)tEDQ2gF#;bPr$WPswgn{E;Ftk$qQ0rmDDg zD*2oa2d06hhAT~DZ|`8sD!vRsbT^V{QbZ4vAY%AZ5t&^)-$ShBn|zj|fvtS3+m?*< z2FFc&`3l?(Gn4osguifF+oRy$ovK}iFL$IwTKI|L16*e%zGhu+N?u9LVdw?>iuSMS z=u|$Xg&vZ;;=sO;n`@QhRpT6Wdt6Dkg%MaYb_(C7q~lrv zU$R8DiZ7f*1!^f*+|xU_bk`AITlO0v>DM#({vpI=zwTaZG>u|SeO7u z0nIb=l72R12N7j2LV7h|SF>kz#@BWW1q4xs@%p|m0J3&8g)$q{lYKf8pnzV=k-wKc zxjz4s?ECEV)i9u}VsI`#?DhA#KH~pZR5IdV2s?Vsyq|*T$o~D8AaGt6zmn+}{Svt1 z75Ri$rN5nh{xvz#!>guMT>=R2%nQC?_V2I2lcxtD2Ci7;wd}()exF47`Lk=1>Ad`G zkFTvl#|67&5-BrsO~DmQtgU5p!50c&j?fhlSvO0+oZsvHf5h)q@~cl+vEV;0Yjwu& z`g5Nev*)t6ujlwJ2%x?MhpT;g0sn~ba4dM_GzkNgC{h@c>87%(BP4z0R^%Ds7byS$ zAOJ~3K~%V;>W|1<>q6Y$yqwP_5@{+f%7Wf7@uecfe?;DD>1udSfiGWyb&iAh_6`W= zM({y45b>uVI)4}#li{ba*uzW;C_oIl;>+ysGrZ1}N$!vNs6i4?3KKfX7?d=~THt4L zM$Y)!y37XVuCEV)KMrtRJvmPZQzBx!C;Z0xb0hMJ-aYuRtqgymVJTU+)VL6jEx43j zh&A}c0q-TQ@A3Pv7fA;se?4K!!VARo@b-Z1%?0+sc z@eJHOllh4cfiG1eqltvtugG=tQ8IefzKsU^wJ4iBUlH|-t zh_E4^C)4noN#L4QYqIKiHOvT+$_&>=d~LH`ZQTg0ovSMTG7ND>o{U#^m-!D>HLS4a z&cLp0ou9%1cYNfCdllJF;ar6Q{$2QzRZTh-VW+@I9V9JKqAVknD)>_2H#PjH8Sj_H zEZxLeOj{J4WoOu|Gw^Ar;=4V(=TRcVk>uGKvg=g;I?uR*j~TXfDuB^YHC7Cv@Z}`u z7jZuoJC;eNt@`I`-=ZQFXT}608}IIa_S`bxw_4$p0)BQ;$sb7)}KG(YnJE$ z1TK2OYJf=A8pbp}t5egNR;MDmD?rmV7U+Oif#x0X?6!})8e6QT&LKC{wX%T_>iMiB z+>sd60K{e!Km-w8cY=~m_7fr{v-YMg?#0oN$=fVYled1Y~4FZbi9+jnfVVzWHOC+m%!Yyfm8UP@4%PU zpnH-v>^J<$4#C5Sjyr=s+Ji*$s?k>=LRWm*6FjiC4mRWYsI^fe28=67fC7SZ*3=H~hN&LWr&xB#^dJ7*SY@$X`9MPxS9mZ=1Hi+hQRl_+9efIIdr z^EF6snGs*t-(>|M>TG7$Q6&P|o>cAoS%F*DDKG_wa;DBJ`>bZ%sE&`fz{HLCbCguc z64e$$~njIkf`o5xmqJIWja|a7NzRkyT_mg2Kr0 zvEN%OGIlcUD9Cn!WaV?JWXVVX_%(1k3fEAr=yLam3q&1<6gNrCS-95BFtEW;s`b@z zZjBi1u?hScm}($U&a!(wv^JK?s;}?+0Z88ntig0AaB@Lr+XT#2l3#&jcWP!2T;a;d z)Om9arvXyjK)xdRu>wrg;eZIPMo5gt->g8k3p=~ExUU^K zDoLTv>@bMTc_DqT@?w#r$@)m>|S+MY@Ho3P1Zym1sl5LNfba#g~ZaVgssX z@Yd^UqHPy*?GTyjy(hU>wLg1c?MIe~a;|?0B2x`xodh?vB4%Z_yczNLdRCladf8B; zGk77xwUCDSqHE%~Z{SDub3OD7hGyV8l#E{2vj>-88{k@;LPLfx9siiwN0o?v344+G z1|+`$&)+KvI7VO{r2&Xfm&nY-TRSlJL7Z;I$gX0q>w|GKdT2s<0Mav?w&VzV2MIiz zFmy999B#(E($0Vw_9~g;R-`on%ZRR7rNhF5{i9|m91x>;bl5Q^zV0g!-5=;?*P3D$h$*eG9X(?6jVQBCXTo|K*0(2 z9HMP*ygveCNcLnzK9Sj-3h3A$_ujIfbEcB6df9`JvTXlPL1d1NfE%?9$A#!&t&5q4 zsv6eh+#kYR2n4DYB6s?0_WlSzu_>*QkeC^69Dyg6Un^n}<{H5(GMm7c>O2kNXV+(U z?fPLFe%a?Zn%2txx6l>q3d3aQ7wLJs_>vJzF44Gy17hR)s(#Dq?sCaKMYLx>;}Qw6 zNk*zYISTs|RgAMCE=OU1PxGAaRHULaqlnB^^L7x7Z?kG`_)kH$pjg|RXHf%H73qAN?xnbhW2tMIHZrE2;bvF(C;&cE^fG-`Q zQdKlY@Q#!z{78tHHtW{w#2@s?wSE~9%kbrC?q8NDMV(@57#o`zqN-zm`~EBV1R@r6 zDSbv(L6RAWYfJbDJZ-rept=+CSRjtth_cN5+L9X}$VM$c%vet2UMnOaBQq-*TNePR zR?Ry^l}m)~wCAvFFe-iS1n4O}m-YaubPdF-L>SV53vg~DylIauaK>w=8Z&~og|X+H z4MtLB?5uSYy-?M=GYF{C+Tg5@LsIQbWkl!PA@{rSzDTS1CswT+>h&6*uY$g$`h|Ez8JRDqtu4N`?p#|4lMMIfTHB^Q#qhJqN zFftNiW`KQyg4qm5X12;g3 zpe{}aUk+l+RY8$c89hWSdI+1#uEVLiJOz>22oKW?oA3IN2FO)Jct%3hw=K64#7`XYQ9no1r9exD{kpfrl7ATn9UbdRrv2qW>|sN?6K@AneS z^b`jylD{JX@SPmY?4b4{@R}g-RN%craG?pdYRJGKV2Kf3&izh84!VF$wOu@wT|5=2FgI`3jZA9?R#2;YZN*oWZ9(vns9(m`wl{mBx{y;g@BXkKip!XYi@kNAk5D zv3N!5B8_53pg8Soh#XusGSRRX2U{s3QxRv`1kAnw-BogCl5^dSz{2&9j1+FBk85Nv zypsEO@C+Ij6;YSQsM{U}j<3lZ)Y_iyU)53P5SfDznP`w% zEHQH@xOPp#uNu~$#PSimTHoPtko40ok?CRvq{H6gYw|ja4Nx&lzY>|M{5gd2XIUOb zyeX&IjKFM)KomXfYL#B*z)(+rPk;szuJ7Xh)b~}3>R}q0T@8>s2EH=+Ed%a%#LDkZ zJg>YrlSg=(jEmTBaY96958fg^$(cFA)7X6qC}hFXQ-hvZWffY#S90$|keK~u@K^zr zcQumKK0}%>?*3F6)n<_St{uv%Wp}HiLx885fJ&5=jKKPI?EM4mB`4#rK=>8tu6o|}`*i=Q-z68EhQW|69nJQiOh&?F}w}|BWz1I@l&&Y?hu(e^* zVwFOeAo2ba*fop&lysXb&7?4ki~rev$cP+81SwyoeDxqiW`ynzJPmy5V(hH@R7sy) z6P1j+nF0^0Y2qwVJ`!w>TCN))+eh$0)|qV2RgUq9yehMY*Qv|!Z(Di$Obfh z&>i-HK;{v+_3t`WE5HHn32}^u1!TtINPg#9X@%OYKR@@UdH<~9mQ7hcgSVEl-(SyH z7Qm`1*EaxxpRbSQS-zH^`xTx*I|6(!5(GN>L_+}E7kKXuY$2Q2nq9*?u(U@8 z23@^w2DmKY&_ZkXAzi}`0PE`Xev17t#Q8w`n6)gepay00ua%-GqdUZ2IulUET5s0O z^>vyu3glQ-=aK9mRB^4UNwdB1AxP6x?9Z&K^LiaW#GXBYpIHM%6vSSuY0u>6{t};m zB!2xQd#nf7pq=3*%vi8G7R(Z+&1Zz_O#JKBzYK6De+eHPiG7&BfA@>eJ}&RC&aaYA zx>ig?Vqcl=Sf+uyp6?FM>-xMVumvr?R&%WQT}ck~$SdX)zK8|$t}Tln%NnlwrXRw; zy@cO#hzwTAa+>(EMLtCANY=H3{qy;I?`0kOvS+Vrd(MS#uJG6`a z&+O4m&eZxdr?6?+H0HLf4?Evy)HO^a!5=o6^lTgUiTA=#u%d-0T3XHk%}cuD1iD z$i&!#kVqW>{meM3i~-AFxY>>;O8lKcFRC;8H*i(W|y>KSs3>HD$pJq zzvuiMs_JPZm~p`C&N`y!UY#1hlT|{bfV!tjr$01GgPkhvg}`n$<2=D=t;HN(8U)%>sQl5gFhd-fdk*djMgf5nm^O?)nvE z<0I-)Dekn{fXXcV9;EsxBrs;S3+E%AovD#FxyEHsO1BiQJvF+wlR;nzaP? zwui6jPrr7nkJVbKs?DeHCBlyiUv^;MDiwWf4=C-_5FAETTmR14aAS#X#0#sf7)yM1 zO^moPmKw0~bgWm^NUp@H%#SG^D#9n~neTf7UuH#f+1bt#7}@hv1D~q=k<#c_L!8(U zs&zOTl8*e1$jm0evg*9u7QRV{#1IdG0lP^Sx&_yxi1?cExEk_7fa*JVDRUT~^8}GO zKv2B%Y*=~kFpS?0P<{#=>`Z2?I-j-x0XEGx1DXgZgaPWRV)o1-WKN4^;IfM7r$|lJ z4!%odR`il~r#4PvzpfQWY?3{C{U{I|A;=u15yOD43Ir=e<}L}nR&lAeBSd6Ifhe4S zoI*)}bsrrdaIb)@9U$?Pt(yhk%!o?oJ~B< zcLTvDe1S?7yF{Iu(z$lB?6fu_Jk)@lJ{RALo-M<3E%D!|rA+PnH8|;n=$(N(B-Bus zok1L`b@6)LSrFBO4>LktMQ+E$-9YT$jW5+1J;JX9Y#a91k-qpYpMr*~#$rF8Z25Qa z;axc*MMPHpryCFMU@nC(-C=vme`ZyAjx<4bCQxhn&K_|IOouRK&kz0l4BZjH?Dvt_ z-%Q(b8nFi&z8BwU;}pI`ac_liR$Ajv+L87Dck$&JeD28+d>~}D4&%Xf8037c@$Vq^ z0}UT-;2e#W$YfKR(4?RpXM%upR^@g5EHt%=k(q02;o8Vk((}1pTPy7ovDZG)I~%ppo(u5lwAKlL${=>^O8~p3AXno|1zP_T@THPBVH*Ft6`7T_zDruLGl^s%oT<4_ zlbKJEm;quaw!hH%8wFgiq`NBkQVk<=r>|cVHlrA)vSE8_&!d=v4NGeRn^p)@R=h9; zVY;qA8UU14v9<6zwwmyD^MSK94O^w=t~l$@V#N_(3(~5^Uar1yHVkPOUk-!xWy2sH z4fLJ(IXhDwJf|t1b*9_uRNem8TJDf}cY=i;SX(N0G^D{ zZ2*8}nrRtPJ0h|zoAwEDvM%MYH5^;AEDgSPK$uvnDi4UH}U%U9H>L0@( zq7`BLB$26t`u5H1Tk(%9nbZW##J`o5-POVb?pmalq z`TOYLw&2r39YYY{ejTGV#d}OZ3OgX!0lG~4;sE=v6Y_k=kYpmbJ47t2&S8cQ5w}mY z9W>!UQ0aP=2ye!@aUBhF&TP+RL(L-i)W|8W`3SGI2LY8Xe*ZM>JNnauX8{jEWM-}F z&fq6h2^r-66-b)od?Z^WMdmEQnFW#Tk5fgEJ8{>lT`Yvy4d8%yy2b$tyY9 zVftiW4+}&RJtd#AXg^&)Iew2IU?-u5SbbH%%;-b0TnwMJv01@5*3Jz;M$lyct#EpnW&9~Rg5Z(2;C*oBKRcSrvk-n-FwuCc+_&`Y7ncbmG0M&UECSUwn{Zb zV7<&J*uU($RKmK6y)p`WHX|MfA!n);nTj~c5_V_glW(00hPDu~NP@>%pAmRikRtyo zL}vADW-adPUKt4~wN{{a(>@^o{-=n{r}5=cJpXJeZIo!@MK zFbS`J-ajKUCjg33WKDYl%ANOEfp#V^KY^h_Mq)hxD-ex@J?`;UK>qswP7Zeyz*SA& zoyCo$+BjUYtExw|Q;q3X4>_&H%t?HQ?hgwzTJXwS*8#1>;uByC8ItUph9FL#Y)y09 zOYdr@DF+`>Z(UcqovNzf6hNaJpT#on5j^v$DmoPr^bxgTKS)|*B|Drcl+ys4tO~p; zz`te}2LML_0u3htpoYbv3@jP|a>uqkJ*>(3J{v@n+4CWYmR7h%XQE}6*knQ4kD~vc z0O+;gRT>rBs_b|pwqxBNDiOn4iLMnx4yFka=(zrHwf*D9nL)#asvQ?ACR76$nN3k$ z0hIt$1wpFPlO^m`kXFH$ckR!ACwz&9X|6-Ep3>O=4t%VzT`c=!5YqbT;QLR$6uxvT zG9AgACJ5jieCeD+hA&%qauM$Nog@y+u0gey50k{aLuMl1&ZJMSI8#Y1O+vVJfp7m* z^1|I?ijYG?ngi@JwO>>r#|)lOR8kF&?&uUeRmG>NIRVwzC_c|g_zO2yyZ(6xpD_}j zM5dacG{bA*Q}-7y&i}QF0{CSV38Gqf(}_4%X9I8=h44dJ@}`z1)8YT$&xo~q<{3G!0~ zmpybAmI0yH1%#gq!4-gbiO4k~GiT^XH>~!tCH4_H>JIFECcvEi{tp52UJLQJ24E-H z7xp31bU8y=wQ0fy|{myu%9nMiZc+M0h85_ ztEub53>+pnLr3WLT*vn!@u;S@C@CGcSbJm&NKke zO?-)@HxR+McKDpYcC**dWS?Ho_|N#gjeXULYl+XDf8&mi_&W7-^{vY8C?fqOe2JR& zdMq~fOzfjmd5iv>8{}93|B~7Em%vYlxYoZ4fncV)`C15z)h>2IaGsa_r*I%5$5o(s z#MhyKNDn)b{n8El!vfqM-oU9IT;5@d{ek@7s;$=n>Ezh+U7Ou6Hf1b!L=98?N&It! zSLuA!?Oo+xvN&QyUP+bNlLq$91mwn%{6FiW{CwXJ@JxDmTI~NN@Z|~iwL4(-FLC}* z!N~ggsFT#~NWA_m!l#*!|6!2a6X55Fh<^xt8HpVnkq=(p!IvKK>$QzpNDl ziZn#QEz9EUWW~{Es4Ne2v{UShyDwEHU(HzVe*SKd{~fIr4LE>GRf@YlUD(~j02-`v zvJpEn4f`H~G&=}k;jF*X$gAk_R>`1>2ALzvk*)I}0md};$Wt14j5wVH0HZdO7SHN= zssIgveb&Cs$UE1z9f7MTG7Z{E2+y6$G)EeO?Ws{%|1f-@qqWNPWmU!Z`twSRe~Rbh z5@p$X^b0=B$VjK+J%Y;?-F>ZicM#h(!>?qChwx>;dA}VH1!@|0mgsN5W~lXbb@(dy zt-2;o)h@!9)k*PBzEn5DH16R$@NST}v_0tGLYxs7pYBxdD?--kx=}yV6XGHx@YFCj zv?iH!(bXoLV%@45%!>SaY9F+M?Pbq*3Zgp%k*4;l>JU?YKWi&)e-K}0y8N?fo7}Uk z;+q**Dh;(>4`UxOZ24q-JY!!PhU#m-BA=q#2>HW+e8!3^M)$oKmjnDCWmFYVKa+!b z#@EV7Gk!PUTRLL+mOON_gOlI_yb5H{3@sP3Zk!w!Q2Z+oj$ih<)I6;E2 z2(Ag?K3@kQDxE#mW<14S-ZfN181jm!aNGF36YPtp#Ecb?AAo=e0MwZ6WOfGqz5|Kya4?bO_8A-el2f*a2i091WtKd+y}3D$jX$jk_TG zvPvS>dbRp+b$-<|d=Wr;t%#ZgTe-u$cK5eq-zq>`$snLM(nj`(Y5$A>03ZNKL_t&v z!k5iB0}j#4q+%TZx2{3f330`jqu^hwiP6gav-8ma&Q(dRN?@~_$gb?q%tsE>f1!a+ zE(RZgJ7paE5ykz-?5C1`ssxqnYZd&}3btv7$ZR+9C5v}erPdQf$`k~PtARMhenbAP z8$=}Q>SzLAu8GJY_F@wR8Pcdl9eJZ@f1HZ6?~-Xyaa{;5Cwsob#Fh?0j)px|@TMz2 z$Yi4aB)+`jw*feoJD*=EM9C_8N9d$6dw!$9|LqW&j{lm0E57HI$ZP~WPJ<}P+Vos8 z-Rz-X3A-a91uF+{h=+CxvSJbvEyBxU+!>B?2G$U$Fy;sZ97RJp;&~0V^;wVL8M(Ic z8OZsa!6$etFo?c4!mrqJ0_ig;W)EK) zAqzBuyl;fB!K=<)Gl<9)CpbVp!xQbs^9_K%Gl6|H+$_SYh90_z~!Aq#g2y(#vV3WzI-AlB``?EOehxj~%KJFjM6IJLG;r-NB9gxo zU(V2^J)4t}?XzCon~2MBwX4^ED|~ymB2&e5)z%CFS3EN zip!lAhgEaM)lfh!C~Ck?CMLYQ5zg@2G?62#OjE50Z95gQ>h(?lAF6JR*sHj608cXl zId>}PC;-uJ2D)ntm}+lwz84P|DrV%XgQhYdU&;D7V$VB3(rLG7p(mI-fk-Q?FLDfO zDqjR2<~9q#mdaRX#xI<(j9LVsc8>loB z!?^^3bB>yUyIg6U-Bww5m>^phc0Pu%Rd?~F+8=JBGYd+?c+VcS4gp0(DT#n;MW&Lb z>gF>+_;Q-}qAI3#@ulicVT4+H7+<=i(9S?gb^oeJ=)3UcT9v(4)Hgw-G=X`tp;bLF zInMli=3`HSKb+*mVc<)LDA8AKK7YPxzgX0A#bR;39?@Z_*XWM*Qv2!yT!9Wt@_?C+liVA5i* zsv-gpOBuuvuS6!BDq3l=s5qm$S)Kua3Mf#)tB7iy+6~fJ06cDjx$5t&wqV4wt;I@Tis?G4HmD&8vmU%+kI7ne z!%?v|)@)j)(j`Jf=8=Gx0Rr=#WEE>o?SZG~?j*yiLSTf=U(W zv9-9H=wnmLvv$xPd>C9NHhzc5L{qs}B966KD`|;4_ALuEMq$sq$v(?ko2o>ni!TG% z;ZCq)R(-fW_jAMkAObSmW3K%e1Si~i{!WV^Yu}q92)c_e?@q2B@wJ_skwvO9cqfp{ za9oc(VaR;p6SjL6@nr;0gdw8My>_>?b0siV``W=;-ywArk&0~PcW7jyz38-Vs>)H- zHoDsJe)(HrDupkD#J6sO=~|$)UhgQJS0%mBOdI?ida@2Su6FIASQGIZlMr%f|5Yp5 zGkm%3Usjy(G`>8Oby5XIlU$24m3$Y!Wpa?+h+&!ksZ=DR>th=9PNEzY7|x7MR{C5H z0R0ptsWzMeEk{ukZbwZWf+R?#7JCpB^$Xj_bLvTi(QR)H+DY4-SFi{7wI*n)$ z0z9hLa;4##T^Fi&cfjV=sILi^PR_1sVO6ABiHT( z3p^?N+}Q6G`&X6g2w`v5bvp!6a<{cSK=7&bj9tylyA_!ZzFc)@GZG9Dne!&TR0QsK z6PbuCcH2RxAhQ*|%rK@(E>xt}6nV((z}1gj_rP^N!4bJ$AZrh=;Ls!dAzDwp)O9%p zKot#3)p1d|??LvX!f+XvqBx+t_;Q3NZ-=T%kK{R2{JGnawqEZ@@YmQNa#eii#$Q!Q zgIKs2DrNHuJvCBkL^fdDSD=X&;27S-+TziJ~rOp5e7!tJT_1xJ8Tt0rGi%GG}MrY zwqe97Kr;iLJA%N~)+$CI&w`=dIbSoh7M`Oq=~NiAMAJ;jk0A(6Rso5!u1Zf!wUuXI zKVon4AKL%Sm&J|XViFSaP9V+pyaI9Swe`p~gLVP2y8Z^vJF3p!0r)$CdJ9}VjEGEU zAQrOq73q~#b|zc5ik51FG6%i{43F3 zsendAUrR`raWk-;gkXQ7wOrk+s!rOuw+g;otG`w<`ZVv24Mku+gFQb7->5`u58keP z_xY+$3WYBjG4&l&nbEUDn%b5R!&+2~QXx#$Op0uXW2Ud( z1ilOd|21-!2RY+ce2F@8)Kq83-nRHY(z1%zs_}!8Sc&*rq;g&JQ`ikPqvIv;rAr)s z7rsRM>zeRo9eGD!UF@p9WVX)Pj1yEL+9MxM>)4399i6)agRHqTufP8=qHh!es|+ms zT0qGPMAl5&0L*e$RoN1v>a$Hb8yJ(doGLOA3HlGfOt06>j0y^1kfF~0R)GuxQl|k@ zT15N+;Ib!14G|XCXA<#ytLZx-S6TKkt7z#LA{@1AUP;|+EBlZ5y$riA*YjTPHyaYQ z?zMgis{R5%%h8{Th0yOH7-z8SsKZ3U&sS2ba_Q6~1NfZ!Yee|j=x{`t{kU9juRMJIA zgEtE_KA*=KybW>1R}By+Aqcw(uKz6HGo_iRD&G%*zlQLCOj>|l?=bD#Y1p?${;a<{ zf)Cz|#C~MK_~+jJk@($n@h@3B;1Rig|9X!fk$0PYUi+^FyH*pyQ^a3G5DX3ArT`?M z(qltJ62gB~QWH&kpCGA{5yjUcl^>?>Lq4kutfqz`zJZ;{;=UeV+o;z#WbG#W3Gj0i z_E*-G`T0I;d=wxiLNUvK74TEGhCeRrIFh~h4xOlPCeelPCG+2hfmay5e-YnT!I$VW z-o^8m;jBy!WJKQDJR_eWG2-{`*ba!p703ND@w1XYLGevbY(^*ei&bPEWPhx2Ul!ju zvG?aSzmk2IabvILa|bwI2xFeXHPJu7`ox7_x?b0MhJOP8{o6Bq#a^ols!FIj-mIrz zRV6qXqZvFKUNPhd)T+#$J4tFJfldIDr)^{uzB5y#gt%GeIYP@8WI%GnSG|^XGHnk& zWJCq42()*St(pJ`sx@;nMl9fA+BQ#=ukY-O5bMfFjTX2f2vsDGBrsnc5dvj*USlCt ztJztlq328pblP4kCH>BTBew$KEdo{5&Ze$6%dqcA8&m_Ts&qt!$UuQx3tR=9$vU{x zC7TFzcQ8SOHwO!SOH{xDJ-HtC-TDeUmVjL{@`0NK5P+vd>6|QVmUGamz~7&O*E}4GdNJ{SjUz&v)TV71J^DWf=Qul2`|=pVF$Y zYILsHMit7S_;5!iXAnY@bzd;TaHr#j;mh@!dgw~P-Opb!R=c^^Ri)=$e5pRC(vggS%yY<$>s}cSTl**oWG&WoK zGg#6!ewjo>gs-!}rU9~GOjReM1vr<_9r3j_9F-x@;)A&JaI0E04v_zDqS7Irn0DW~ z_E~nM3*z@j-Fb*|w@lMN_ zd(VixN9~p_5MK>>R*`bt1mNdQATmPhwmAWf14NO7WEsg3_bM_^L1eOofTK?~!<(=e zg>&fGxE<*OCxB;D4c+!2JG`TGvOR7sm2c}EAT5M2MhJ8VF;+BJYb zg4orH{rM9wHMo%B%WkeK!k0&2X`B#*SZ1Fc{BxQlCbQquuz!vYBC}=4PBK5(jBCEL zPnf*YH1=>?2pKk*auTv)U6%pKkGn+fN)(Uc`wn4C&cg2_Y_wjds%owHPsIhOM0q!` zWd)xF@INz&6IEfB!Wk|>S-p>SYP_@mPzUJ%I7SUdo(B0>xqgKW)G!-0Ej?SSNjRCT zQ@0875ml=0a!>32ACXsSj>x4BS=Tjtrjroe2p{!i|AdIQ{`s|+5iC1{2-LJJ24dHi z${w{$)(YCP^7`x{xJ008okAG`RdvL)Kq|uoDnY}Yj0Fmmn*ktD>p>V!AGOc+3mJdL zS54EkWd;G&(*Q|qV8H6kX5iLPw5OFLVS#KH@72h)JK(Ug$DFqENS+5Xz^6e5XIg5J zJVP|uy9x?ipyxhc)}rZDR4PX?1>n!@+yF!*dZy?c53y$(A=*^6;xtIov$%)V6vtV# z!7fq3h(Kprb`YPU1_QW2zZvAi9ij&L-;AspWF1;?4O%v|hz0QMd^-DpRfeHwa3Z~@Bm%>i6_Tim zFGJuW6jwDt%tdHD@d)1WbA7(M_#p@(SgFX|9rQVXKUM@Yk{hTJnJP{kV*lM8Cg~*M z1MGsy-CA|n;{LD}hsc^Di2D4wLGGsoPP8E)t3ET+fXeg&S+(O`eCZ_Up2C+bfv#E< z9a7)5|4N6x;-gUIX1j6CPrlq?l8i`-z^$GNU!tx8Q~=S$&#!ygwSNO#ue(pxd1CP! z!kNuDpWVQhQ{av}__Fe~5N9BQx2_`T6GqAnK_uOc$J~yO-GN6V+0UvtNBNamzz3@0 zeTp-5ntOub4~8#yTjLc*ehP0i5hp(3MekOkLl_mx#zb!8Iw8agCdh zh9>Lmd@{yZ@#akUm1fvLcKsu~&RiB_v7`{fX0jr)0@Ny+H4(TiowfRQLW+biat!#o z4ir696(9v+;hA>ReBdD8&6r1cZ7j%9T(xLMXz_jq1hR}kR*~2vuM|Q1nrZj331E>p zIo8HJH;h#y0L-bVa0!p^Y%OO%HY3WM3XBLm3?|~M9*6?9yUybv#@4OaW7U^VATx5$JdE9SBZ^&n@eI>oq|HlRmdRhj+X z5a*^EzcIpMisyr#-=AnLNB4Ug&(G0_Ryw4!fJZ7C)Jg|9ioef>%)0)0B=3Q`AXRI* zO9VPep3JA+ogvY~*Q`f_&{Q?%?nGzz`tR%?XJ4()b{zuj5Shb_(eBIum?VxzF-G?F z3HEvR_gn1M*Ujgf*`6%EM)Bj0i~*8v$kyi_x}ra;upR{Wec8J&ayXfmPDO*S@?f%! zc1Etxgrb0tQ5;7No%xi6Pc+!6C-L^%RnnTE^|*L8;wQb9MfGfjLw+Z#POJ4{1#1(73o zTbf#j!*D1Lk*V4m(6c%P&>LjWF|D}?h>jg1Q?-6KV~?Pu$C*6KUJRm@p4xWbog&%7n3?gVz zhha8M$(4q)df=qH>mOaMTvZ6-6lyerW7NRXv-rH2bfS8$5#F#k$CfrD zUS*v>?iput8G~>szuoss5C}>%Jq*AZ<|0Sn3dGNw>ZT!PM5aTws%xxFFAqUx_Q(gt zgt@MFTlek&P8Kk#jOk%Mi!O-Be%NY-S8b3D^|=x?hX|J5fXJu>@=C9d z1r4s&w?(myJHi#j**t8K}5|qmRFD_O%2Z zBVo)(vVpFK@C0ma_An4>vu@g70-T;?p_?F;G7TA}L$+2@4M9@e&4|Cn_kRGUoDnIJ z+y?`4j^RV={Bdz8nO@~P@^?by8S%Ax^!oju$$ed)%P(;+ti^qOK28wlY71tq z$18#GX=qu+$w$;G5}5Hk!>dHg0MWH7cU(y3*X7@h1aj;2w$Eqz5_|I$f$Ul-x@z62 z(*MkOU$fsMc=h8*)_b+HQxI*aWrl%_nGlI=SV#!_G0F9zz%e4PSiOSX0iKy_XO+gx zx!9LRh}cN%&pSLF8MQvFHIY>>{fe&xQ!@YU5dE3hxEfX#f!npN>yIiq)vzRWeGxqK zd<1UoM)+hb_-GpTZ6-lufPE1QP-gaI^_izhLbeMg%ZBL%IG267#zWxCGx7<+BMGQ8 z|MH4_>UbwaU<4o5vF?9{FW1R;>&e^jKGs- z(K=;1<_!>W%vLj!VFcFGMtXluVBagzkOkQDZ~UE+sh{`zm$-H{tn?HZyNkedB-o}4 zqGba6l%3~a!alx@;5i!_*%JSf6_LEa&t@8W%xBGn82?=V9$zH|m|x7KyHJvA3jg+# ztjDK+isbs+CH|U8Y&9dVh*Jp*CgGK>!H)t_?hLC#pO5h6hu{PTv0JF)F9^?39SZjg zT-ViqGa}EKY97RYs}7Je@y(N*uS_0-={2g3AN75-K3Q@k+sj9ANsPY&7k8}dcq}|c z#MfcPtKAu5e}4!vbVS~@)lD+=M`B-*^id=><`j0KT|pAcBA^VoGr4<)KQYi@-;o}H z62YEEwu2do9($9^f&eXNGE-K5z248Cc(IJ)YFHehewMY`X-7e=|CNkz4_ukqg^@<$ z&pWyk-~F0|yxGmDI28#y*BGHSZYrcVYnP0|XH+woDnqL(?uM|rDEq92D7p93!q-sS z8A$P@^o8z6Kwyg zAud6D_X@OoLX;ojx1Q}(wvQ!fTEX?3{O)&%$+I)4&LOfXN+UN5Fst^*(dcA0yV8+! z{ftA{&b#<>fb-+%*Z(Pe$$XQVn$6C8wnjUH{8X&4R=iGN|9fybC01QsnP9$S=kJ_- zR|X|SP#U3!vR3h>(zIO3{{Z+CB@$J2`xNWd19#;_VeKkw9)?X|@lTdO-}NhM5YgRz ztE%+x;>)Kx?54mz%=Wl`gYgYb#0lSJR}OIRJ6&Jd?{wndX7B-lckF5_?tO(xugQ)x z@}j8$h)88O8NQr?Ll_1Z=io#YOQN6aS&+hvCAzr|Hj_(YGA$7VQqj~iWz;ia`%cIX z1uEQf=nVLd&~5rn1U!nUdm3m4APSu-z_~cV%+Txv=p!K>8NgZ{#8m_72wd5LvLqcG zxVdQ%8wt$rI&xH1Q+fVXpgC?{^B`wXkrwOu?a8`k8ig%z26cVD-2gnwz$=@Dh}aMW zS=Q3C+b*qw$yOj#8L?3Xv6ZQyEp$r*8^+-1*r7y94{sop17ss=tzmbFc4pU~-8Hr?m(X7};kG1LtHwc@WZ~5xYpN}vc1%eeVbKmGA$)F zh^z;%1aa`CGX(F7FIX!&!fKR*PSS-GzhV7&}e zoFGuYR@3z0QZ5dO83lZ)TK}FN`VmP0UWqT2%utnVSBbV6SOy>?GBbSdCR#$o52)fl zLJxbaXwqe8#rb(P;3=Zsx~vLe?&6pEfPG^4QW0S;zI4{Wku!0JB26Rqe0nI5BJ-5~ zB}zK8XLAS}GB$090FgeMENl6?20e1HtTKJ2Z!5p_D_Z#evU|yAh2$RS}%yAQro*5dY@um*y88r<$W#HDe`BOxuYe0h#DQ>2Gr=n{m zM^~UZNFcFh%#pF3#{FllXU_Fk2NzTviIa$M0}TakR7S@o@FoZ(*0#+|SiVPIs?NwG zmy|=8wMzu3p(^Na<)0P4%%(Q4(n)Nv&UfQWG*kiY zU*xyZpCQ)YC0aY#Yix*CUx-XJAjlK{z7u%KEE zwqvm@o7<4Ja85$TFb(=3akq*;JNb;2C_>UYPJH5M=iMbT?{xereCeFOCdhw9;V_S8MV$f$j|83qh()1M4gQJ`H?cDI&=T){ICT;0%8UzMKWj zQN=$FA)L)fSqHeqE3l>!yT~jf$ri~uK+cA9h|DTDS48Gn`2EU3LWZEy68b0Fk%u^- zT?7IuYo(@!SK6OdB_yh-%t$g8G*|Z8PQ}!d?SJ!u?>9l7RVTr!fMy0B_Tiknwc;cK zPx=fJNM!foI08rVB8UTYGTN0X%o7BOPDWCR>EGRd-~Cb~SrXUF zM5co;T_RIeRIC59{ncZywYQ1uQ}6QxzU;<1jt6bZj{Rvy?4gL}>`x~B&^PcE!k0?2 z;Q&PP46Tdi5+!Q?%nkeXr(O<`sRk)U(LS>7GLaqt02F^oL_t)f7a9h{$mAxl7sHp; zYiA_p44oWb&;CjFd4-5V`)L$^|7q;#$l-nGt5Pw^e36srax|VDOjp^b--SOje7Pp5 zvd*6tUu8ZbbfUWwe`SgKCO89h{+J&B4Bc^8#g}t~V`#(|p9P!1I%HK$g*tcsNn{?8 zS6LtjUL`W!stg1W2XM$EF_hV2bl{NO)^Y`u`o@9HGR{#jX#ZWv0S8o6h|C`OBykt$ zqwM1~lhXjO+#RAc1(CKh74S(%F@#}pGUm()55rJa?>`e8?#X8=r zBQhDjbcoCjo^21DSXEP**)X6r&}bWfBJyDd5q?Fc!k0nFx6D4>)s%ZW*jM;c;q!Ok z_SI(iKNO=3vaeA!eglCj^W#IDeFtB%xUS!PcIx`vip&htJ%KN~@U4TKZ$)}L&nFVQ zkH~@S>^qfJE#3%be%uWUMMv2U(!N zu48?^hv`7B=YMU@V$uUAA@&pz>$dKwvyuVL5xAP52@)@gM0SwCegGiqzQ59lt5hs0 z`{b^TYByoSj!+^@+3_qeX~DH7pCB?THlrm3PG;|}NrxVKu#Q7CIz!|laAhLezg^g+ zWBH78A!$d^e!2QZY+W)Uc{k9wvk%ecF5OC}=*0>qR(@}yn_myx+*ww_!!o2Kqmr0#S-AsfC*Qe;z? z71mt8b{Nm!jW3+|ft}x;*x$SOa+oonYWG%&vt1(d5Ty4>_T3Xzt1kWz^Es@=0BV*& zi+z1vMdr?pc!fPnG|186BAiYaR-uZXzbfdM1=7}8BbLlrIiG*74QefShbAzCSZR%z zf%OwrX)hC*kI>VKn_&o8M%~R=OvBNulJcF__ooR>ba2(wPvn$FU|pQbbs=ND>S~}? z&k4YTA~G4!tbolwRr#fD1fA+y^0{?xuvdlG3AcN1T-O#klG-)tYE zK-wMfrO4j(`$vJ)+rgJ?2!}(){0SnH`7H-uvINH&xDst{?(-mfEgLrJRK_534h>ys zQInSWE}WTZAy;)+8(Z$m~lO z7(2qRd}NsFt_Gv3m_Ikxs!|B$;L9C+!UhYi4Mlx`=;f!S0Um zD}k$0UJi~!t>#FF9t{Ii_SAWPuAj`f62!SFjnT@mAN2db5t-MllM?G^H`)?_b)5+P z=^Q@)WS<#HpnxhN&kLd9R9LL<^D}sBlWGBcB@gcN-mU{*UdtMMI*Wf?erF`kVkAyY zwHH*$TDHy~!jKPffD|}eg>~2c@+Lt2T0*{x0JF;A@%Q_l@w=EX6Kh9?_{SlCf@G7H5LNuVNK{q(bUMINz8MyWS`u8tk-(Din z7?Ee`-Qh3U-dc$-M4YfnO?D=)@A)>*6l&9ODiYYhqAAYq8C)k+O-)2+;PcOa1fC}D z1guWQ_#{4|UF^kmAB>CbP=8dQ5&#=Sd~L06$@#e2!nXL@GkBu*BfbtaadZ{k!56Ap z_Z|5#zIDjNu{@VSY;q*;uLx9hCeFyKkWiv+^^w04yMKNE_uucaV#o7hJFgh?^I3iT z{pUXxyginm{V<**!v_T6~C>h%-&gmGCP=F5)2!)n5aZxlZMFp>|Mk2x>bzhcNWcIg)z zs|rJ|PW)**foX^#dckrBDBBnw_j`&(xt6mCU z{_iDzU;X4kY+fvJ2%5;vY^y4KI00t3;wN@KE9;Ahdgu4i3sav25O!BpBd@=s z)`tMNRI^IE#!qR#D3BAOMXxLWzI(4~7*$n+@y=TBRJ|#IUWYub5Uo*s-mBvp!tuG~ z?M$Zw4bZvMvM@I?V!LPisbNx1M!Tw^quPg6YniIxa@MhlXQG0lUAx29$7yX>B&MU$ zQ$3&R^A7;jC-85KbYByEZ0h(^_EWWlSN*9oG|W8@&I{okr_!v_QiXmetFl2u0hK>Q z$;_4zwO7($O?opTY+b7tI8R4>t$gW(6mzE1MtmJ?5aCM_Wb1ZDE=7XQ|IVUmN& zq|)(J?U-M{A-R^?%@be!8lkVWlkKjoH<=5HgIr1aNMy!Wo8>I<- z2miTo5W>F5kFMva1)m=fiGO4rLtXGMPraIHLs3@(!Ria`LGHjP^sb+&)kc4Ws9vFq;wG=%{0cb$2Kq*arS9fvrD z{n`n}vcRK>z2$z!-S2l|^Bkc1Hs7CpKdYF`rkZEZ_q_n07GDQ#1o2NHh~RG89!6j~ z)wDDA6A~?W)rCuBs`p}v4y6gm)}7%O_5Dr)#kET4NU+_$S4ihp;tH*UvQeb`;JP@^6k^b+DFdU7iA? zB64SEXx9$@8wP3VRy4Z!a94}BFXU1d=zb?Yp2BXg=eI}Rk+F*}SFK+MQ!D>amF7a- zjt+_F;7g{R&JuN%VUI2mvto(6`0`_U&Wz{@^PZdOXV;E8Cw8yepYJ9zU3|%;x3Vh1 zDz>^-yN~7iSr^H;i7yp#-2_LY?ANX~`1P!yWN*c%sexeue5k^d{~Y$Crm`Kvu#e;* zXGCTOJg9ue}oTG$R^L;p9|n(hvk(1fEv<**cwp%j^2FsjbNA zbm2%NF$~jm!W97HiXms~H$v;~jKEbd4H%dix;l-OrdL428F@8ukGwVH32^%)k=X@! z?>C64o$s%oe-eOz#PwZp=MXK~@1csZ5J5cJU+j-tv7%acvonS&P8+e$cVFl{Dh<|( zhA(O@ZX0J$>CvfcbX!l*9(Ra1mb|-L(WyTFwb=8u0z^$_J(Byrp6|CHqNV`C-LT(5 zY;!NH<8Gjai18M_G{BC%%{o|`c>d}fs@A4#{jY7&aUm@aKy3Df1pNH^nUFVK1Q$oL z2ds!m1K7tqt>tLYibJwJfiJ7W5*YSVn4T36>w|i1bWj z-O;Ac?%((?A za7?f8T3Ryj>`eQ9B|#2i^i{=I1{j>F#!fpEGW4g(jt>Gf*2>j2E5<6eUP(ZhX~-}D zvt}gR41q(sRfltGn4?e-$bv~;u=Jih|_Ph)9Dx%_%5KVUiF*QsLIbM|! ztW?K_0IJo50RksGi695W?Gl+g8kw0!j(WB;zE)F)0aC9)Wz1mp!<&)ByIJ4dt!e^O@kw zN}@Av?2j;Fx5K#pyF~mQeAz)P{keWWg@2gEI9m%N=F%rxdF@sAO@ z*x~y95Apd&{9Z^GOFTD27n0qw@-KHYDZT0A~)FJqRiIT|jf!(YMH}sZ`ne zeBk;+oIj`C69pa)s8V`~8PURI3x)}%)U>)v_Md_NNyvUDNpSbolQW3G+9d150_gw* zfMeerM~^bfZdGPA5m9Z8W`VdfOpN`0)t2-G^efwu`KVU3CA&I7mGzwl&QCf_Fxt4y(94e|H!UO4MWt2<2BQ6OSDtP3cEwm_9`u4OH0;VQ2^|2NU*Gq;rI#2vz(~sZFup|JQ*E+N^|0#~cGlU!m)XyuM0FK^ zIm2k2KTqJxjL2m2XH8&Thty>6n+;<@pO1*HC*ns3Um_w?aVY969LDu!QZ6I%VL6DX zysMvy{KgBAtgHQOuVRDte})>bJLGp0nGDpZL=BtDSJ6AHfVHf3@JS-G z@_nY=RH+Eut>_%$d?+9|6aP69ppKFpuEtT7$W#?y0c_8T6`YFxNyrh`=M3;HvI>AT zJKg{ZomGDH$U7XI*2C-!_xL)1;`+P)h~KM;vVF#aI(OJmMBX_QV*ho5T|;~=LRTJN z3EC{d_!D5`NQl&x@I|dRw~{@vMzA$oXth)5y$*Lu4IAYZAE9 zdcA|6X7DPUrzBy<&G#LI@ExXoyYqcDG$Y9Vd=g*I&FA03(_VM+Yd7p*1z(~G-0c5P zYOr@gqOAC12Vai(T4l|ApTa-uzq`PW!;D2#LE7E*WkjV*mZ>=ytO6R{)5{>j8;C=) z_#p~JYh_p!iWz(G0g6td+>sY^v44b?W9RytaQuD(%-{V?KwYw%s5S8Z)v4e2SK*>|-5C@6=OYkqI@Nq8zFZ?;D%0YziY!$t9dhg!YlG2 zM43&XZVZS%MM=6eB}G){$v%q&XAwG70YOVC(|{r;L9`NL$3Sg zG%*CiKq>*wq~q9Z5M+lVxZFqeratv%~_D z2wK0tCjGO&-9&yPq$%U)5WjcC??pM+iIEfA_xbeck)d?TdW+ScOIS1B2U+XF@CoKpBx~h$Uqd*`M{N*n- zC2)nvpY#wokocmsV4%uj?jOJjrJarz95@31j@4Ttfdh>f!ps*0qGP)JB>_FpVFxZ! z`DyEEP|c9A(%hDuob{GM^p%w`)pMPkrw@p$Cp8{g*bO^#0qtN0XBew@wfeitn#BiEDg-5GcGK^wQ& z>wQt&Nz(JtY?#gkD^>}v>95k}3am`iErQK!)N$|GmC*l_p=(C(cki#L4r? zP=5g1Yu_BxU7VdS5xse+?&!ZhINYc_f4HzUe(|UW`^IQ}Zma!)*?!r2uxuR&M$I3? z;B((#jv|JL2R1qFN9}eFHWyB%Q1A z|2R?$Fv5fxVeHt;cYSa+wz&+*n3T^!dxJu}U#@0yVJX{&!c4H=MBdzZWe)4JYjnSCj*3E(saet*!Te5gL6t zfoop~CIPW{b$U42R)Ia)ZBcQNLic8b_g_DlMB5u!V{yR;@PCm!~ds<9G z;PGrgcjWzl*TK|LvmQAE==hk+fg!ev)}OhoqNu8%=ka*@lxj$NCr7T@oWg3uVI^K>rQqts^2&=9SR$}o~*^8d_0^aV)4$~K(o*Q-k*AZ|1YdHfSpj=j2@1c|%X!++|J)w6NwQ64wD6aljt z(yU3ceQ@M*Bz}Q&UpUBSYZxC~ojV`)Z=Uf(mB4>;O#4EfLCID7KMR$E2u%JnmG?+g$eWxh=2K6UA=}Z= zXMJ>a=>wTr;>O7781)p_4aIMD--3J>{2CR^>tx)-L3hI3JX);X(7J(h^8L8fKu{|| zDfw*Q0@P01IYsVsOdUmkt10ZKO=RHvLIj|Nt$aC7P!;J;I_R7)>LGbokSc?QYt!2W z1)q(BR+X8V90{J8oFBz_Ck&i(T+}55&6=Rk`^kJC{LGk@7NRZD(W4<-ae5I(*(pVG zBoE40onG7wCeQ#%UyHYA>dYiL>INU#SVl<`QK7S3H6jyMt8lv~fjxs?JzilE9FbT?IvgIxS>~Z|v}z`3!OT1L|51q@dyluA>UIFY1va=8m&YJDsg)zSxF3lOGLu ztFj5w&YIIeTY9Z@Q-y`oEQ2$&C;3i3+2h8*gFKQQ641pKFn(6W6JY$+UVdp}$hmOT zCgLqV?U~e-N32fFv4>?atQvAu5&6?>1zPZ|>!jS!gnHVn@K3p68^JE|iQUmC_D@E; zaaaw3xYrA6|3I?_>Kq|CVo&%D7@~t24?W3|GAOcda7may$$(RtAx|2b1EPhh>KzjjN#Cgjk~^f=!U?9 z^J`I$0Fj4dE8+|wtAZa^r(Rs)g0x)i$crmV5^{2!Xmu zdoM^JDzMp4j}5DwM7O+CWJ~HjO#``Q^-wbRb2Ea7e&&~9Vcuv}2JDC&W^9Z#NBP>@ zo+;7BDA=t4$ZqeRAjorJ;mfHN=&pBl$Ejh1Bn+G4&l1;ZAbg<@lIr#u8cJ5y7w!G3 zBfzXF{p+o`l5Da61ukJVqZ@bA%G1StIX$ zeQF44vuG#nq<7!`6;9HbY%knX=K*XowI=xfK-(-22SUF$L-3Jdzugn1v%>+nK#g!u z2zV4-c%pz};t*iW+}fj(hG6cXMiEFz*J-P!@Xh<&Ll&Mn(@voChoJmLfbtHGY+$pp z3=D3i?39d}(pddkQm)_nx-efji2!$XpB+37a@p-WA8@#A8WHh!D-t1 z5P8@xMZsJI>Ynjf)8jQNKyi5#)&0+b4ROFft-l-8&eA#MwE8un@OME{j*=gsF(wED z7cF_`^zWfWup!D6#GWx0l7BppwTCb=LBROwN?F+G!ukvok{3THMsmhGdpop)bgAUp zLEs~Y4Je?np}iFLV#x8eoT}i7ApyZuRi@yW*=~Y~xaci5{9AQpH)iS#0YQjr%>l@6;Q+vo5-o^dN3de z`RG>G&KBv_wMRbS-NIxUbUlW;I}@(U9?pO!5*gEU#7~qm$56^UZv`PSO4o%7 zp81(PLO5a*b^G>njQfgkVUzGl+~M`jF|%+!0#9cn$x#}>$z4CdL}(h!0TU_XOJ?m< zBnx`M)NcsgQ__a>v|ADfJeEAgrc7iK>Fxd0#2~L_e?bLy2Kv`a$EP zdpw-SJZ3e*(E6(!**V${>_T>&H*f^fF_y_9=1G{Ew(b0Slb?w$&rT0$8zLoIfH#1M zGCV6y!Si_}Z~( zWIMa62%zsJ`npv=MFj@O@|+ z!oSy{;7Rx$)Rv3=_If47< zjk<4gxi_9z-2i_uwt|zpys3W4BUWu8^~sU8R6O$T$!zr6dfp#AVx5bm)f>>E*0G-k z5O_3U)T~LCRP_0@7^B5o_aza9-}yGdm6<5R(h>h(Q$^5UH`&cI%0HsOP5Qs_0MEYX2hT5P5kX|+urCXz(jOe2Qo>I zxRgSNwMzIXN<(_`Sp3r{tFG ztNBZapSJ7gBVao$gZcySEUfHa+?x^v96^L3--X08PR!ktxnwoFA7vVF9?l=u@TLVs z_;Qykr0V%w{JjvAmQ=31-?l&5)r!0NaP3>gb&1Mp2wh5rUB!$s_nHd}-7JyO18jJX zGEa@Y;!t-oBB?E4r>zpr;6qEd0c9SrAUSgh9HkaW(fF#b@Q|tceaM@adCz&v{=llQ zttM=&Pb$thu|F1mhUlrnvfJ~=RwHR!MitJL@YC#!k>MgQcOyzLVHqK@8vE6q9&PA| z5pfo5R^OA5@|7n@Il4%%wfxzIFD?GS{zj4~0qj4o)E1I#$wSJiCJi;YZ6!Oj!c44j zLGwM1K&t*kAVy2wOFyTLt)2T4csHxMrK2r5b!bT*K~Pu5U&^6o%*xzcblzE9svk)I& zuhk;y{;34e!q=HAfO}3+dl+zqj3zw#sBoma@)aE+RR1{kkFks?n`FGQ0M(0kOMN`n z>7nmF{|E_H{?Cg&H=az2T=*DnZsO7f7776R5cHfgz zQ=wgry@06zAb{|wR%_=6N6)?Yp)WVR3Y9+>5KrviO4Q>^vm6n@9XTX6QQw$!8)B9` z2q5&DGBHYm8DZ}h%%YSN;Np92bsu9o#2&sJ88m+QYihdYyCKhg@WPcumBuYNB-L{% z8;(tRA(C>z*)8Cn3?{vWrH206OcQ;5i2Ys|K;H5wrZN2ouLb6s`<7k%El*r(SE5m# zcu}3DUjb2i^9yD_2kOpmp1l`Yn~f-w%aZvlZ!R=uZ?&A24~6@XFIiYwT)I#9NRN@A z+la$1Wg5xzS9k2}!6!6#x4P(x*cGYNXXUJJOloOwgFKmnF7E(a$e4Za@L!Ol1^k5TKoZInCB z`eD4E@?$#XYIYBWeBk>}`#Wz$-XzER`7QX6oW~%}3*0OK^K=tW=?ArPt@GM%u#I+O_}Op-Nv9@rtxD5M!-w~U zHMklSAlZ$$2P@SBFPT`2+O`?WAfG6YRM)dgeUep2t50>*Dqp$U(SsbaX)AyMOK z)D?jleE#!xTNrhvWW>9mA&5qMc-8D5;k8UBBtx*eaMz? zuD*unL1Zx@9${czGn&7iWa^N`l2ICwUC|Mk=ytXxYL<~j8Sb3 zqw0Ux`Ar^4TsUI~BJSf*hj-cDuYXlwJnJ}HPdGB_KP9`;z4%JhgWD~iSN1$-T5gxV zso@}UmtYTtO$yNlb44jSLQ=dF)m(XsACRNQjovhHxx0soJRsN2LKYco0AVFM@|6gp0^Zh%I*Z_w9b?9;0ut;#&vnZvjq_Ji`DNNf=#5 z|C1wM+ulCP$E#FDYw_=j48H_)9XzKi*9gb)?_Uo+5NDj~ovOmVlWfPO2KX*yoLA0t z2;68e&({6YDAM#N9Wsii{@gK2t+5A*^7KY0m&-h9vDu{9V|W&aJT_`x+|@sl^a=c; zQIPW7aIFa;5b#yk%FoxOY{u9mEAQ5PM#ySe{ed26fpqB;sDY%_l6qIvZL@?VjJ1;_ z3OE>0?|%KLI`XNI#e=SqZdJ&cyHUGG$c=y>DLUL+EVHo+p6%Q3v+#Vn_VHAo&W5a$ zyA$1bo)Q|~5BL>2cetjQ0B_KOk957nkG_y0jREoVfj~+Y!T`hV>ik_#uRM#n|8InT z(9UW3?Q04?<4yvQ($eI_Q}jJY=-hWtxQI*4N!(cmpc@eFc=RL%4borabR9cC%H-{V%mNS=KO zV;tzsjA|l&RM!<=VcxB1RMiyf_c&IbV!e2jmkKO9Rl@-`k|3eI*gs>xKkC@uEB?sB zl7JL9N!A=Ls;T^tTX}lhh%vqb1B01mVJsPl?H|dpn66XlnR|S7v4Lm~BdhH>Ag*Y< z46>HLG+9>**5;Ao+4FF!zF>}gB>UvOE}EmRJf)hh;N;JOT)HeBMx$}1_KeSHfpV*FkP=c`|V6>IWlN+yf3=f>Q>N1nl}n;wtUd$XzO?Jb)1L6JU^4d*zN$SY?u$0_cn)r|Rjd z<_!yi8&A6&>M4!Uc*F!X^w#$sAR6*=f6vGCFj4aAf4ctW!v1x`dN1t6X0$3LaEhW| z-wH>*uQvmhuviyw_uk7cudOoGv?SB|l)M}m5ytn$_{y4L`tloX=QX&j0kRhZvY$PG#pp~wKMMCi?!$cP;fS2&NLT31EVdIYtwcmh6GGn(-O_0YE1`* zVyP1~pRo$~kdUIqzCMNZDa|l^SfN|XDrfiefsh@vX~ab7-Pa6C7bzkZ*<+%gm5Qm! zv;D4Ep2Y8E@qr(T(NM8<%}zyp60oGo*x)~3hhQ8Wysq?bC+hr|!CjgB8#1UgyKTzG zv9^Z>MI>sa4z>fZF);m95WFunJ1{zs%sBAKi^g(=r|Ipc=m9Ln$BJ)YR_ zlEuF!hFFW!uC`;Kf$mX0uiA=n-(eP97vXGhf$LEvmKK75P)EW-Q~KhsUeQrGyz_vo zCieE&G}CEuz}+IXttteP{v+ug{ZRb%QxsZ4ytbcG{KTcgbKQ^#ANY%dS#N6aN8D36 z5H{j!QcuKD0AJ9Q28yK+3ZHrn)bALLmvdN%!ZYDSnD}zCrRr`2Zgik5m|29;=i-P- z>8>DDp1nFbXS#@SopmibCT;v7^FTThy+$ee4Q}+N^hi-$W$Yg6Ri|5{~_>o z!rb{V)NsICgBdLLq?j@*-RY~I3b$zMECq#+Bb=1EZ@nk!pP(eo9iQ;Bm4Wy2ihrXYn1Z#q3 zA7OIVl1m5>saDtn4dyW|)%zO!rFJ2oo)$#;92#o!Jrsis@`$Zcr53yLH^_4CmZ%SE z2t4W)xSXxOkxIznk@xz;c$j;Un(Mf!%x(%*KOrQe)Say1zl`FygVic^Em8m{hN2tk zAZu1E{7gimONPH#mR7`{rb62}x5Y+=wh1+gsYp~n{wSXdl-naS`g=f=!#grT5|r(> z0T^25$H=(fDz#nf#r=IT#E=iGKJ!@&Xn3fjA>TuV3P-`>dOM@(2>=jsS?*piuPNaT zsH|WDLOwg@0#F#!aPn0ep-G+n*%5S|Y1?C-N+Z50b*Rx#zB0IY6Z$LRR)m}^>vYFp zeK4@Zb(Z%r_ura6&rq2PznQ+C2ac`2=F|3CCBUcvFM^hk7l66j^-cZuGK8$|9jTjE zytID4wG6QeEL^r>_E{^$i@?lofNQc2puNV?f9ZEIz;iw*v#U{6>g_M{bR6{Vne)g1tmQNs7uU-DjL)&X|NH?ZYu>D8w51NdoDCzUf zl>iK?<4AL5Jm;lsx_o{9#Y9ffmYsU#BXhdU>1)M_H{WQxkaWulKZ%P6^Oyb3Vw=fC znHkak%w&m`#?|w%ltA+n`J=v)wcOy zbl^?@g=~NN5oxqg>f%T@;EjJiHWy#VMEi--VVPJ4l69?1#iUH>%t{`w$~K=vAau|k zylY1v)4u{FakD-cmB(w!0pBT7L zb8DjGI*)nGA8id&0P4cF-gzhXd)&0e#-Q`-B#200ZaB2Gv|BZe+BTy#wes`QNir<(O;Oi>!wz#VnG;TM%mm8 zQKf7@uP4tjx~Nid_`=kmcY{T$11H!XlL+g0l-+feu92wbW=y0c5XDbax78^g!h)B= z8W)WJ7&e2ZVREQ(9ia?L{;4b)k&5RHMn*TqG;Ykaxcq$L3t-vAC;d-_$@6q|mpv*Q zN^~W2ABaBh8{>5dhv1*DsQMQSqpYCr{SiHzjTimF06C};w^m_j#;`2*yS=LlQBEJk zGCLT8B_2$#uj1pKe9@ESiaPCT%7OX-HO6}m0J=n%tY(#ewiEjL9sBB*X7-S|x+uzg z0A5=YY4pNcK2||Bj|xbEVN+=Cu;jo?3qp|0#a<6NZtuFGIBcM`2YAG$vk?{ad7_OS znNxRV`~BS=fb2X)yWnAQXpfoRsB+S$w>A&}MH!|6 zvay}7)H#5nmTlA&!kOl_1j3Z*+V_IMvyznI~>2GES2=PMT^6T@$mMw_WPsd zSzz2*xg|1#?3xIpEMAMLYoLv4XuRXT%An`i+wC;yvbEwpW~1cDAEP9Kzkj>B3MB9C zsbN!;u`&B8V}mBMy@!y%)D7`eL%v2YlUDT8wc^vWgR3bBJucz;SE$fZkvALhT;hP_ zK4Qn%^gVpF+2Y=eOqDuk)CYVpKSjE2a)DY&IsvDdv{Q`a&hntccw1!A>DfML!KNbo z>FJ@{4MMzq*yxB3BL)ZOBMh((UGCS~p)dK8H%&%yQW@X$a&i^t`Zjgjw z(+10=|B!;WLc7``(@)PTXCt^euY=+yXS)5HrMYwcYNsfLax>Z#mWdm^1>-0#v1aQJ z8YLPfI7>hCKQjaRZcXg%VxegG6j%NC`d{^i3HoLFZeQHS|Fq$A6_9S@elxElg5=v2 z^rkjUxMu&%yq(F?bi2LrHqXE9i>cqqE9)1tjS4d*st%hkc$O+}wNfqWMck+MUYq?K zo`!&tTQDuIOYW3zHcIiu&(bfyymPSgEpuVvv7!h1ZJ^@Jx6$Krv$wckPB>17QQ>)o zJ$EbZd0`iGA*@O1JqYT#A^XAy1)Lm;8epElY$D>q72JFsNh?sKCQ$SMX?|!WR%F^Z zGY}N^h-4{&q?NP#OgA~`a)Z_KQivR1*;)+mYwM`f2Qn5n2n3k6NMgO6?<8h{-8L~+ z!GzOo^icDlkGcZ)Uthd6mrFTI_+3m7&6=@zn~YBi#>C3gSP`KaF!Q={>dlm1M(A*8MO0F ztU6)KWN6u=H*m{gf!C=$Gi|^Yt`>I)lV(drz&I^9?zuaXd*Akn?#O-DS<>JsC<(6L zRs>&sK0T4nF)OpK8C7udUC6TdJ?Z|DvrfiSlYbgW)%kz$ei3R*h)Ljnxms<7w6!AG zrW4p5`HP|$yz+C0$Vj^bV;NFlY9I!N4HHw|nhw>HM{kXV)KXFq(Ot|yJlio zHBdE-mIU*4_?01w-HkscrvB;U#JAO~B?aE8xBgag^pI>8u-_Lfn4x2W>X%1>?e-Rc*Zm}kvZclE3_**7-UsV8H;*O2AIUP5!8f6HOTTZ(8k-JaaUOxCZak$3z!SA^M{Kgk79JRdW}8 zm9h$sjtX#Kq2#|GPNnNP78B>%4ozb%RADVyrdh5jruCHShcf>N%Y}%fBtC2 z`~suo7Iz})R}X<_mq1bURS91DhI#+d?dwweoI`5?aPh{rLkoS@ zuVC95cb4o#DuX6Emz7DbL+jYtys*7NtwfohSfHk7fW5Gxp~0FG#Kpx$e;6*c{`>e{ z>%70!&HNGPgx&)5Y=99^=rJeThbWq8-45lCnVvAG4)U7|Wda^5g zYh93rUlGJlP9&tDVALf1&ju{1Ns5>WsDQI1hAyPYD*|VS^NV5_d<-YCg?C6inod5?q6!Pz!??~I9Uv(o9JkCZt`9T{q zZQI>wvH3@`;HJi~#f6R_2RC0Q#r2B$97QMl$!VOKFDv%#8iKeBVO(oS#$!_V!S_4+m9rO5XzlE`e7{f&C zkbd~EK+rB4SE*QRIP(_y+?sP-%%0>*No`bp_i%Eea0aWiiOms&uYx_5da`+f5OsZ= ze)7sEenX-iRjZ`;d69TrGlw58Q}idRd0T5 zj4a0mJKHO6&4Q%46JPx1D`5}g?Q)Hh^?o6h5EY9*Gkyuy8yZzoHGvu4ZFRp;+v09A zaG?N(E0elVYq+08s-k%6!llPv=4iQ5+Vx6Pqs$2eSI$a zv03BZ5R>;vU;92Rcj)$uL^ahd=w6E{aJ8~O{d+xQpZTjeZ=Q#?IRi3LCA^)I!F(%l zL64Sm;FG%e?YJTTOA**R6M@P6$ldQ^TRedsRfc=RFK684_m7VO{JPh?o`=6gt~-x(wy%r6k){oYk2n1$Not2XJmwz`vBd3tf3k)@JsWP;=wM3PCny-ZO3999;9X7$KyF1)6LQO& z2@hfhkx`bQ%ik}U=kYA9?UpQx4-CWx+lyC{;F|B#i*+pBRT+wIOWC3Oz9a zObHp?2c~Z}VmHHo_3lIH>2AP=xE;58Ohn$4Y@L}PHOh_XC2GfNDqPg-(Zu3+3((=K zfMd%J0IOCS%n(_;`kPLk+k?F^#yxt%)oDNaA31oSd~#Ln7C&hUY|R1DUFlMxQvMk7 zvwE@LE(-^q7~*5dqi7)r5lAx*ed8h(aU#!_n^;<&yq9trmpDI3Lp;E!o51$yTkF+Fd2%!P^9dt&4$DQXvh=%}Vj+fnaF z_6-3;1XB(Z5bmcFDY@Sa&}4$OL@RE{20pI`Kz#r`F1@uSk1i>Go#)yw3XXldq^1t& z%D1}XwyI&p{wgCa(JwBuC9PbfoX(*yLAt13)tFcdASXGNsHr?-(aC&@qd(j`|Kcg+ zxxbfUhG=DpE7bNnoK+H3-{zJzX1<6Z9=uC{S)}3*OF0orpU#5DSGB%gJilaj{P?Q) z-N5&Eoq+t7;o!t=ZQa%uB4Sd9tpoMAAdAi4VWR^#8rCH?~VfS+noogZuKW4MNc zY>^}?Bpt=6>r%nUgfc4~@u@$FWLTa$7=9yCd%vwtoF>+?LwL1z=AJfBeOukx#OCSzEj6I3ghUmy#_cT% z87z9&m1b&XC)YJIu#bbeCVS#cnTJ+jT^Iq@=%Xt7Jpg)HT@E8%4}DyOG8YZ1Fc-pS zncTHC-v}wLk>>9*t-oFhYth9L{n0>W-RcvO3Z70WEjWMzrBm|gv-A+`#BTVgjG3}w zVaS5g>o!?Bj`g63FZJQT8q--~6E!k7qU5o5@{~-n>i}{h%-Om>(Dg&0ZcEV(wxAw> z(BLzLs82%#6Ma?@?-;W7GjyURdu&f1_uvx)R}T*qsCZgB;Jgl&sjy8*4$d^dUC>MX>o~iQk_9f#Hz~%Xz~&? zT_wehTm@I(%M^X%7n@ZRq0Jr>>^?Y4yW;>n7I z?Hv1|)NmlkcYL{=RhD&PaeGDys2o#ST{pb@q)m_$AA2KZyFDA}rmYEmC`gKD8Z(vk z{-pyM)Znidn25~NN(QiGRnB0N&N#335)-Z*0>Cd#i>2tq+JG+`arL^ihR-7k2pE-* z8cF4_?HPO7v=F5Sq2-|1yx%>;J59QJ4Wr!Mj=zjR~ zaSWu%lT-v}Af=aXG_Gma!(pEQVby&rcZUP|_dJQxnMvY=V!z{qzz`zl&e7vlUr+?=2dju~j)?9b z23^ML<(>6i_QiES6`w0DpX2z0>+944ZFN&(QEYd7{=H+HsUnRQ&F%s$=D-_+n-14GrH5oc4)6| zw~`BjRyvsfp%CXS%AF~ODx4gP3uaD39a@k+X2c8_=CuHz3dX*oXV5;>x$4iaJ(LRE zn5S;%C?Wm;@1|3T=rSL8UY|dU zS)Yf3yTgk|zf<0C({6~d?#>Kk<#F6)+kz;cUw9Z-^e{d4QI(xYmb;HT94M-`8~;j# zGA7Zuv;s9AW2e}sf9D^qaeP3;Sn8cC4>zAZyMH&asQx)z8IsXHur^}ERx;OH;ndYJ zzW;(bJqW0o`TJT>GzXG0_XjFFuK!$@Q!LE&Yq48l43K#&7#;8hFvv*W&f9av3ke9$ zM&o-#n{>S0~X7={fC>4tXqN^B$IdFBIe~Wx>Fj1R->?gGDvx z=Rn@k_l^;eFRDKVMR|G!Mn{;75!6?TDqz8{W0YJa7X(wtNP`FX938gVvQ4CZqjN>0oW)jgXHWkONB+FE^cBpmmI(eYVLL% znh@M!9TKv8QL*2Upe7eVzML$ft#M=BVflP<3Mq_zuBG>fkx8@irRoDdJ(#F%595m) z@AGFIlGYYX?*>(OxCK1}QgI=e)yo|2U6Lh>*2m;Pc`G^Fp)rxs!zexS*(dmonu!eR zh)2RnL|u?+pke#osP<~Kq0uTn#9BvBs_D6lu8*OXsnUHkePIe^=Y8&9+Y#~3f&j&A z7o?q$G)w;0aR68$(gu}kILN=fIVeOoU`VVNZKV8JYh1(dwZ_ehSCO)(5`?mGaetx zrpnSia)L2G893PSRKgjY{q@Nw;+eEWa1X#pmyd`~-~Xhlp{gd`Zmt~K`=`j@_6u`{ zo&m!?gi4{efBn4yy1Nt;jnVBokiOw5QEe%JH?3?rg6$evtTY&KXEDUW$Ib5%d?X)y zvs%q;AKy2Bt7la#IXZ6&oy21lOz>K+0Shx86E!aGsHcW6FiLj*c-Hj|zC!r<*uT06 zrYW{0rX~)^v2avA<&JcQR$bhRR@XhdqFqppNW1U&;MB*@#vu(Fl?cn{&ooxs$K3=% z&@l>{?Dn=Fm$JOAUVQxxM7`FlhsI}r>o2B6PEDNPhF}DHYz*M?Fz-o6Dv-o9fOL#Ksan`cLbx^D0SS++9M6KEh~>vxKPpD*uxg_7ErSF=`6(r%El(A{or zjFK_=GxHM0Ua-?>X-trRO1{=(PXHr+;Xg!JV2f&0f6Z{)DkqdPMqcl{AX|Dh;H&2)2xZr>b7%otCXS=DMVMn!U^(YyHmhi7a%d6zC#R|xN;J>SdN!z+gmJ`%Ci5t9n5Z8G>(l0*1+9*=IC7O$;HtT-u zK(cgNeP`B_9sl+ob80-I>o~P5Gtn}~r;g-~?cjF<}y*e}HdCVZ){9`pZrD(1N62$algkD}WHF{1qaPYUeK_er^vA z4kfrCp`yOdx8>&_G@I&|J|&Ks49fkdJw>N733oSOs!`X2y9wwww|`@-wOd{^Nox?@ zEPL+vV3S!;V%aL}Z)IyEg!DLKst*XrCQYFuq(_W_V|SSu2j^N$-{LXQxr`TI;kGDih1=Cej`)rL5Uw5c3C1LUR=FLcT?L?8_3?Al; z*+o%=OMSMVNmf_tz1eB%f|T&7;>+5-6vX*m(B0Uz%8tgT2^ylb*iUoM!Mg5{j)^nf zS8~PH)ovj%8j;^dwT0?y_TDB`sYtxe57_t+pMwz@uv4w zSa3(^Wrd8Ey>o(_4zRiv4WJiSIzw+lXn+zhgD!%WI45@Pv*Wh{!JDN#+1maUvKE^^ z4skX1Dh|KCg+3qVq}vEVIAe#X3lFwY*%LXi_DRE;D!|=w0ryKQIK3XEUTv$q3TSxF z2H#5Gc?y9vv0xm&Nw|G8+KUCsar^RCCG$#~wYHKTF^@Udj%&K2V*?E1IL1ua*T%R6 z-Zm7B7k@kEs#&a%jr1(FzvpV6D#)KU-R^m_-_0_gqJKuJAdWOR-|aR)JM-XHr~u=j zsrzCg98$-(&scm9I!tenMuQ)KhmxN5eHZZh*f2$->KFgQ87QgY=3@Tgn+WL+C z>N&5>t#1cbN;qvMZQr7#*(j`@4VUa97s1pY@DZo=8Uht-#`t$~E#Yd@4VRkQjdX^X|Kv_C0vc z*mIzfth=7%vbClbkpxtRc8)BUuV?V4_fQHpyr(GBv;00YKv7f5jQByyou;z~>G%$$ zBV{#1#$VVl$17+a%nbDIVfHz-KYz@cHI9ciRL#V^wD0GWkNPiJl_#M8WPWR!DK#e6 zA0-B+TjB+3nZvoe#XCzAmPywWHX}wLTxLls)qVXxPx6md>dttqC_iW%?zHSo-dG-C zH4C8(tHS-fPsPnCvtXaAA6!uJy&m7DuyVm-Dp}B#wT&%%llfwH{cVA~_2NzTjFBAuxMYMhD6>Tkck9Srs<$Xtmo<+WmYs!xYjVUg zVrU>Zf^mwrTQ2hDxTe4Q*RZgpla%4HJ`H|zznK9K;qnp)qZvQmfD?le5WK=cEg(pb ztt)8SD@dx@8h!Woq664_BA!%a0_cS3;3^Z~L@v@S(c7_GfHejBO)E2d9Ke+&1x#Fc z3>G8skk0I9Zc)8UACI{{q{J$$#XA4s&3}9BlAhU9L|) z1RWJ!R%Wv50N=ta8g`(wE+Ebs|JMvgDN?y$ktDl2Zdp2!-gP`fElPZnh{%W;b17`L zEyw)#?W2ZO)hk@D^nV6%c!Xs74S{Xnv7N^CJbAE=MeN?=CljBmY=TI?Cb$;?I-j~H zC`Ed-3kWNpqMB~Wf9uI40J{}8X}(IF1zKZJ+kdHhpeQpzru5DPm?ac)UjXmDr{S4{ zc>3FFRXunBj?@u^fDIX_ydrFt=Vn>c`s+XkK&#o^K@&i!KGz-hv_TiA0P#STGFy}u zM0U3@bwS7fICkIsl?@DD3r($@`Z1N)4*WTRi_5Ri6VptUl%LI;Yt z(%G?+MGqLMKNFT>$CKnNSyDDwC`u{`euIlWekYtEmk^Vh0P`8ec-KB|UU*$O?lZap zbo6c1e^&33^S<;R06sR!;Ax@)fvBL3vitR+ zVyL0EaC$o*GdXGydxJ9;Bt0`-eAs+UD?~a~|Ip8VTiiYzJAfUR=1s9}_+w zDc-?-4PGw~28wIu5ZPhi&SYRX74oGG&>4pi?cL9x*@-z5VO_KX_pZnpZsz%bsK)Kl731g|`VFDVUn>Pv_cGh1)px;&?@L$^Ma? zR{E`cSg>67{*JBT|C)x==wpE{3I0q0f&i%F+R_xTG5xRQnZ4LFxc7TBf|zO{Ss|s| z=3o2W8ORiV;=I9i^NPY9>pwuw4fy=&FbYiPZWDC!=%=MCtWz~|C;J_|AdO7`@#%yub+H!`);Qu!tkOxH*dbquinLz_k|WMoCVye9k-`i>DRp# zhZi4xlX5Zt%dI=#RD|X^@3WZ4{2@@i+keOR@(2--o5Q2E#11U1u9Z2U&(tva^c~J; zf(-pk6=(L!)&KbR=kzwS^zFCY?ARQ1b|oHo2yCFQk#(D}aKk?q9oQs5M^8Xc8vt%jpZbV}p+&&^J^0Louj(C7 zG(iTP=&AsomH~9vk`r^CREpYncYqS(EsrBb;A1v|4kv!7d#E(g^%FPIzC#(n2MjHK21A zCZ+1k>c2d@<*~~HD~ad z8%>a7HNqb0F#wk%{GSK1NywGMaM>!q`PxcL-w4>aANef@3^m|!EHj0l=m1lQOU4dv zj>tpu1r^?2I}5-82|Rvfnc$am;1Ch9?6uibGEE+MNC+^ry6#+!(myZ{e3C}UrjXAw z&Zen-w*WIe2fb+rDXGzL4h7}vGlGXDAg2STGo6_8Z82Dz=XCqH~Q>e2hfoQL70(Y)*K0-AbW|YuPgg4E)F3v*$JN9+Zh;`e|fq%hE&{o zJI6Nfvz36W{z}G6E@fRMkzwB^=cZa}21~Ee+?UnzG2&mGxTp;qi)z;+Nm*+rZL$Bn|9Vtt_SIeMe*O6qlI^?JwAaw&*oAGmzeBw) zZp-CAe_SGK?aSZ4qd%N~9IfdpFE77p>#8YAo>9|M+bbA%Zirf~H@!P5``6#USGVO( zT5|7qoX7iG{R8@*zt68VJ!n5Y|N86F_T%rmSY0dL90}@*%C2_*dhb2MPUXk%|JnU1 z{%Kk_Q(R!Tp514qB*o+&*;n6hH1bU;VgGIol$&OKzI{f7LyZ{s$A?cPHN?xVO#N{F zY4p7OM;|upbRU!WU-K+pVtvGf@=Uq9KYagV_EoAsU3dC(&>I{1x@oC9U$5afcX!6Y zjn)t6AK!i>ws5QDZe6j7_s=_b$Mf|c_HX%qZ)@)C2lLN-=lkLx6LCcUvp?IBO0D~k ztv6nt|5yIc{^z$ZW*L{?y!hzI{m#3kCU2$$eS3TI|JtU9|84JoDtO#IiDR0I@osHB zJ*Q7H!q%qioc0RLUtRUSsb25?r#X}T=RTU4^5(z}Udvg{G7`JLWUOWay6|XinoY`y z^otv{|Gry&Ve!MKH$6l2#QyE9IeomZQlo42g_^9X?X!4Jq+hPAI8`000U4 z+qY-e)zw{z+8rHnWN*6P;ypWVzg>21*1h}pAI?9apWNd(&rbjTiObKQNmu^5^T%tR zojIIWqwGI_cK(x>#hN%3iObKQHUIQw=TCn1Mxc_9XBT^X`eON$)t;e_ z;Zw;Uh9@t7FrK*lk$J-M$LtFJ$N3%R^~pEb$l5bhT9KpRJjjH8pb7Fo6YPK{)Bvsc z3AExf(2D0kE67&x;4ynczdQrb%pX4(2a-c<(0t+i@t@JU+{^E0arhx%!NB0@>gTe~ HDWM4frr9*~ literal 0 HcmV?d00001 diff --git a/data/objects/multip.edc b/data/objects/multip.edc new file mode 100644 index 0000000..66be6bb --- /dev/null +++ b/data/objects/multip.edc @@ -0,0 +1,17 @@ +collections { + group { name: "point"; + images { + image: "cross.png" COMP; + } + parts { + part { name: "sky"; + mouse_events: 0; + description { state: "default" 0.0; + min: 301 301; + image.normal: "cross.png"; + } + } + } + } +} + diff --git a/data/objects/over.png b/data/objects/over.png new file mode 100644 index 0000000000000000000000000000000000000000..5303e2dc4906b6c7f5c1642efa8983350a105c03 GIT binary patch literal 73621 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≥hshj}6NDxm^A^edf0U$sfJ{+zk!$ZwFKG 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 TJ##4Q00000NkvXXu0mjfq;&;4 literal 0 HcmV?d00001 diff --git a/data/objects/sky.jpg b/data/objects/sky.jpg new file mode 100644 index 0000000000000000000000000000000000000000..6132e7c22f11187127784f856ae7bf73e2a27d9d GIT binary patch literal 69378 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 z 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 b|6cwEjpqg=LQVGK00000NkvXXu0mjfdNt&_ literal 0 HcmV?d00001 diff --git a/data/themes/arrow_down.xcf.gz b/data/themes/arrow_down.xcf.gz new file mode 100644 index 0000000000000000000000000000000000000000..3d4e89c5471aed93a5432fc7cc8e99e8a954c9cb GIT binary patch literal 4262 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 Id`Kz)06R`L#{d8T literal 0 HcmV?d00001 diff --git a/data/themes/arrow_left.png b/data/themes/arrow_left.png new file mode 100644 index 0000000000000000000000000000000000000000..fbe0795eaa894d98b817a7acc8c7afc1837c981d GIT binary patch literal 1637 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

    +9>0QgZL!y;^6E;ly4yMW+kG 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 literal 0 HcmV?d00001 diff --git a/data/themes/bar_shine.png b/data/themes/bar_shine.png new file mode 100644 index 0000000000000000000000000000000000000000..95df605ac943baacf7f5ed80f2309ae6c9b78535 GIT binary patch literal 3045 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 literal 0 HcmV?d00001 diff --git a/data/themes/black.png b/data/themes/black.png new file mode 100644 index 0000000000000000000000000000000000000000..28f520afdb47debb0468cdd6661d68de0bb2f3b4 GIT binary patch literal 124 zcmeAS@N?(olHy`uVBq!ia0vp^JRr=$1SD^YpWXnZ7>k44ofy`glX(f`a29w(7Bet# z3xhBt!>lPx#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOG$ z4=y?xWpnKS000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}0009MNklY> z*e(`rcijJy468)KQYW1%+g(-PSLN!!pK*TU8u%Zu6TW_A8?O&J^Y+9YnY-TZL&nbZ znjj^>`!javefFXI032`!tj;v=e*%wysM#q!V`s>=De}0VXnMiOd^W>zBridM-xCk8VRt z1_CK1+Sn=}zT}Xq!#f2LR24Hos*su>ViNQLA=jI;LjpfjtKN^&_ZD%`$t@lmSGz}s$q+Mwo28YaX zsW7g4ecc+I_)F+6Y~C3|O5MG4ZkwgztH^v*m8+)d@@T$eIGx-9h%pjlKtw(kmCqpv zA%uTI2(JK~D{auU5bu8NYu04BC`+B6Mh}lQcA>_2-`pi;T;g_F5BJS-hQ~e zynLam&zw_KYuX*^H0>Tbs`oNk=yau;Gv`cXyWO(ceCO`&?!WbVeGPmD+Op#V;0f^j z>gwwC#l^+T)oS&$F5$V0TPU45VaLU&qHLYq$Iz+tZ}s$|3n7HIZErT4&A;pQ`VFuK zz5rXPLbC$?0-geY1CN2`6jKP;0^fie;1lpQzqOi-YDWV+%&)WME$|da1ls(!!6rLs a0KWjIB_5&9XL%9;0000Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOG$ z4=*(5#&4?t000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}0009pNklvY8ax4peke#o++G0UATh zA4NMNQ8hI~G%)PfuloTQVb}z4fVaDFoK1lQM7wJZpfm@Z1OEW;f!9DdLQo29ffeu* z_yw#D*Z|C1;4^S-gY<~6&V0N!pWhmWo~4&&xIJO?xiZnOI)TuTPJOjkd$oHu>!Pc3q+s+|QKtV*ZS=rsk zuJQY7eSPig_980fi87E)ym)=ZVZaS=;w5g))!r?@}YbP?Lf{ zN{KeMj2Q9+??43S9IAj+Ayq*{Q3O$ojaYvbdX+p)Yi|`qK#hG>H88S^wB*nW#h%}* zlsQv>AdwWL>-z4BAxH25abgU~o*X$OopsOer^e4QI~}9yP*u9Bf5(vbgeD-)A-z^; z9ps4vC5BRsE^KMffL8N|P7TXK2LCxM7n$`(RY@tcG-b#KLTIu$h#Z*3%YFKn_3TpZ7VN#^Rh>Grm%hD8p^Av$oSy*F&;*`8e@4?ZyLrY`FSC{8 zPLjfG^_->gb7P;fjr$?5Kdy7MZQJK{C?`M>i6Jz;X&OXin0963Fj!;`D}}M{^}01! z@t4?LczJe)l=8E4F4`$pgB@L0z=L!0u4!@|&F>hFr*;5hj71P03_}X`q2Xt{X>Yo& z`?m;0-UdyDc=v1HW=)nwS?c;!db(6+*0|-CQXw zy!RixcQ{w4-BUYF{R11-K~olXx>Ajq0~6V9w>&Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOS^ z2PzS7B>PhU000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}00079Nkl=IVvfvclLT+WPvA+UG$PyR0GbOZd5 zH9Fp=(4hnN1gL;>V61JW-wS8JTS3;q5}0dS>-Qb#Q3vcZU;@07y#Ou*9V6{w#K_hH zy#sD!_qt{WIt4BT^&EHuyald+scyiTL*NEj0S~|oxCTzelh*Vv;8>R7#6Q$^fcI$P*Qr5Itq0iVTUgVc7_@K`B)sr@t6g{SCR;8Oe1?}_#+1vPX%rQ^G| z5@eOUgS|yJ`rVo}L-hMJQ-Yz$OfC)hD6`V?yi6`KzS~t}Hew-TL+TAe4%9xG`z9XT zD0pJy2z&%S0v{%D+b5G88gQGjp$w~lWc@EX+O3Ti00000NkvXXu0mjfU#nO8 literal 0 HcmV?d00001 diff --git a/data/themes/bt_basew.png b/data/themes/bt_basew.png new file mode 100644 index 0000000000000000000000000000000000000000..8d787dd2b6540c9501fefd39d854313f14d97745 GIT binary patch literal 1527 zcmVPx#24YJ`L;&Id;{f7L_rh%e000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOS< z0wpfr3E0#C000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000G2NklZ|G&v_G+D#U8=c{1JfKLwkw= z@p}!x4FER*ya!-gG|G*67r@qRHhVmu&tIx4mCE67-17hbE-o(K z&gb)&v)Sx1fP1F9L}S(g+&elt`bJZtYGO)>DJfNzNfVR3Rh62QNpoL*Y>xG5Ql^xc zWm#Jpx9oe#!~AAwqp}%8RURH5errap1CWWu%FX@#{V#TRcRzy&$ZV#7APCUE1*Es- zb~3=4`JG1!D5z~@9_tf01PO{vp94hsSu(;j0@&Q#+}hsWetU3ma0uXH>IUuX?0lL9 z^ubU zHGp$B==#RS#$8p~ge+X#qmt>QB9u_GRIE=LgQR*ky12Na-O;K)2fJpiQoTW+6C8f) z*2Y}`*8xnXw!-RkI$eVhbezyOSO$9xf&vID1R+x3;6^fNmYpiL^9mCHQo`7}kPNbg z`82qzwt>KOI#~m-ib%^T^`Nd*uQN=}T5 z2)eE-%M5miqs18aJH)qxgHS-ES%@W6>Y`#AE2J={2wK505{VMeFr@ex8R(Z%8XMH7 zl$9@FTaH%-Xu*sDSz@V)Hx3EcDco?2AsMi)DF8K!q`^-cejx-Y^<#sW5|mo#80JZ> zA*6bkO~6a35LgygR2YdfW{61%vYf?yTt*f{StVnd z7lEiE^-CeAP$gCjW);UnJV`D^SXHg~X2Xbu!oBut!XnapP*S7rY{-1TAyy~@X;}<) zT?bIDMyp!I99H5=8^W#Qy@F_xtwWShmVK;ck5vr?$d)JQ^F*3TqnH;`SDzCr-5>(! z&d$y*@7%ewHknRJgiKm6hF;Pmtq-DOvlf@WjfI1=T}kuqA0P*p1=TxnO% z6g2#+9Tuyi?g-88je}SW@&DarhxxB_eE;<6f!#0Y#5v*l^XEU`xbgnSw{L&AwZ68F z$?7E3T8;)&)ZQGNBH0w0;bdFlrVJQc#c#G^FF+yA~H zlW7$xq^3d{I_c?`G<=}zdX6h dzqIV4@o!J^&6x%qZa)A3002ovPDHLkV1kq_$YlTk literal 0 HcmV?d00001 diff --git a/data/themes/bt_dis_base.png b/data/themes/bt_dis_base.png new file mode 100644 index 0000000000000000000000000000000000000000..06f3dd51afa201dfc7006c71793dee9be634f1ae GIT binary patch literal 1101 zcmV-T1hV^yP)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOG$ z5Cbu}=M={P000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000B1NklkTl5f85prQXz`&@EO znsc+iiOk{SmXF*3AR<5zqCjPs+9weRASyc`)PboM#~H1r7@3N&=AzxJ0(`EQ70v3@ zZL+m1JarDYZCR<42xwLM2y}L%g5(x7EC$w(90(|%ubXt{eO$-Bmp;y#rxW6RLJ<(z z!Qu=S3s2G%PbY9RRhB*9Rb~eOQaJ}f+A}naNi%5;d6g$2+$9teAX!~vU{Q(52%-hg zjWA>`IzS|u&uOdj#G&oF3e^a4zHHB~0YyAWD5`Qms4%}a{sIq%LmfLa`^ub`2@w|q zZiKf23CU#)ytM)gornDza_c)=@#+Xu?LK!NcQ`Rt*y@OAFmB`q+?Mna6kr-hP{e;wqJ2Y8_PLT>WkNN%yE{_E@O(GErS0*=5q;yDtGEqUY3f$;@n z8o4#)%@ein&Z?CxcqP%<0BvmF{x>#|+f26+(E1ZnLP8}F?1n1~d#S~-1P9gW%m zx8R!!2R!3YBup$&tiCi5G8!E)6io3Rw5PRB&Qk?2@-)v%=?a)+uB*)m0Q{aqx(d{S z*|1^eYUVKRZXP%uH#{6)KPnwc$_a$n== z4w38zyLD}o@%C0>lNW_$prZAQ(c~>#S+qk>NQ` zbeqyeFxtHL65vq_utbSANtsIvfyQe5RX~N$`G%n{XE)7O>#1}mEYGZ)93zmI`Jk|nMYCC>S| zxv6<249-QVi6yBi3gww484B*6z5(HleBwYwj-D=#As)w*6C_xhr40^A{Qv*|zR?of zLnmGwJ^%zJcal0-JO5VhsC;p{;PZv+7gfw>J#n)&d9^SxR-;F4=RppJ|AxFPx#24YJ`L;wH)0002_L%V+f000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOV{ z2|EC>dS~DO000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000BrNklrAo;f&l4M`6G&)MMQyC$*%NjkS?HL zeJJTY@`;iS@Q3~ILj5cK)Ds|8P5%=J`$JWRMjve0e@DcB06;oN>K6cf%XLjDQ3xUB zr#d@HDPagfT_5Bz7($TTE-59f0Pc~h6;cyvsmsQ8*4DW}KT}GxGsKjV0F;?AgdirlDuMt2Vnn*GGvX^L zzP-I2n}p_hKJ7#SEfPdjvL7Onw>NJhBC4upnHBGP&$?)+cb1LKPl+)?*L9_xnX&6S zwaC7_yqubZ-rwKn%JaoLecz+13NwR<2z{iaLcZ%dW#+R@kBBCdRWw|C0c=1$aIqAa z$JqRKJgBNZK0dZ3cRU`a8bm#rfwqOM-=t>1L_~?GcygX+wSH9%`AAqrqy@b0S5=KM zmI(HJuQxY0Z9=cFuglfdRjDt_Qb<|EmSq70OGKE{sfvht+kCG0G%PVj?EAg|T$ZIc zAL)tJLcy*LB@lnszDL zNLd#2ks_bj>Umr9JwHD~lhDJ%L+tw=V~pDOz26^Nfk`gaLw(-VPwVq*#TZNG^Yiz8 zFTP$o!Y2tACEAKmY8aRDJkMt*J2Q*Fvh4kaVL(d`IjbTOsk^_e%8fR$a-PTLY7@G@ zzt@eMLMe~qD3*8*hXb5Wr*dqJPYxh*;Wftvn}f zNlxl>%?$!q_xlO+hTj9U1^m+M1vcjJZMHUTokQ5TWR?tdeSK|pe;L)i``!jP{EfF{ zywHXK5SoNC(AH~ti^$f^x@GejaP{rHo?AC;xA&0mxZo|l0F)XL+ylG!eWTS+6^2bh z*pShdclII!zX5cQ_-CU}XL167zX9N{FZ|W#hbKkw^?w8a<+e;0K4g5A?~C#unBL<- Tor;6l00000NkvXXu0mjfFE0%8 literal 0 HcmV?d00001 diff --git a/data/themes/bt_glow.png b/data/themes/bt_glow.png new file mode 100644 index 0000000000000000000000000000000000000000..e995ff1079107ab34d9e8fa5a6a0add7fc3cff96 GIT binary patch literal 1028 zcmV+f1pE7mP)Px#24YJ`L;wH)0002_L%V+f000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iXGx z1uGZlB=1=O000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000ADNkl0-f zaBlV7px^^CP;}2Q-Cd`u`c!oTchA55r08SL`8j|`02%-@fK2kY^mM5JTm!gBDV;9@ z$~m6^cn9DWfCm63lV1Upf5)f`fNC@HHvnG&d`c-@l>mJJ@Ybx*0q6mYHo;s_)Zb_7 z=Y{`u?TVCD<@LYHqNW9~wz)s2l-}K*fI$GwO~%Gi4o=du*`pqqGx&%hm@OBiawC0K%1b zk2L0$wXFyH=LEo00DFLrZ1Ucu1F*A}z135n!7)hn8hc1Xh`}@@D{4K&Hm2vXjdM?J z97H2~VIn0v06$E2CK0H}Yoh?l0w@JwR@Abz1ZZpPWYc|P-%|vL!^FXSH|dBZygyJo z2sjSKEQG;qRf$(x2{Q-M()zQFZ_Qg<3hg})`9}9}yAki~0$@D>>j~T#?5QlF#^J@@ zXk`xexQ}z4CZ^7%kW;01vadRtw3C1Pz*`KcE&$<8ugvMsiVVk5um_0q$0Yk<2--n_ z?*v#Uxoje4Y9yQ{QJNXi4KP?6g)~ZlAo+tgwdR>AkWoCWVG07mOgECUP7JzME|3fk z0g4iy_HUC6SG2fOEQHA#A_s1xwIdzU5}+jU&55ls>otM(l#+dXAM6JNd#DvzQz)*4 z`8Zdx@zN3?U&tr!g?9O=M8Q^)?kFr58Lk9O0eWKHQ2z1U6?&+W?0ZB>Ohc+6wrPXP zK}(^0i#)VC0B!@|p6TWJ$4jEB$pjPG6W zAGT!0wS-YGG(AZ%ItkV1f`=mZs>O3!7PSIwZO4a;JwPd?^PKZ3fHxMSwM{Sv=OM29 z=0eU=AX#X(1WW;HUk`YvDW$Vg9{OklU)mA84p=HLBx4*n*hMGhR5-DgfcrhiC4f`Y y`QRnV3jmL4@S)@MpSsMc5(ej@)Wnk16ovB4 zk_-iRPv3y>Mm}+%q9dLzjv*e$-(FE%cgR8D*hl-DQ?t!7Hxx4k#UJ)~V}1DY9JaHP z8%`X2puH-<*758ln@MJseIgu_mU#bKd2-Fn_%vgK^jncO=4Wzva~iI;Jpae6cOWp- zKi@I!o3zspLBXy?GuEU@uWP!PC{xWt~$(696pTgbe@y literal 0 HcmV?d00001 diff --git a/data/themes/bt_hilightw.png b/data/themes/bt_hilightw.png new file mode 100644 index 0000000000000000000000000000000000000000..b97a4f81be4d2a8a8733682cf2be6f5a89babe0e GIT binary patch literal 279 zcmeAS@N?(olHy`uVBq!ia0vp^CP2)`!3HD~X4)$NDaPU;cPEB*=VV?2Ih+L^k;M!Q z+`=Ht$S`Y;1W=H@#M9T6{RXE12Q!beg?|iCNV3E=qQp5rH#aq}gu%HeHL)Z$MWH;i zBtya7(>EZzkxv|`sKwL8F~sBe+bbJ+4><_9TugUi&TEvCiT?6%PRk4}naL9_x4Y_Y zNpP^R5MnyL>&BgVw@8bS81#_jZDizuGb=syL zP-QD|nx1j#-40#l>ksB?1PC*)`sgXLqHpSlnS{i*DjxPiXNtU=qlsM<- z=BDPAFgO>bCYGe8D3oWGWGJ|M`UZqI@`(c#^?15ChD02GJKd14RY8FD>FtQ${D%%& z$V}g~Q6PEk$r}L@TuJJy^Sw45zb{N8 zdb;K>UWYZJJ_j;9GFYCyzPWzI&AG)Vy8_;QUBRi^T%5C#Q#W6D(~N*1r)k2MCI>qS sT?(iOcY2z>-h9V?-djnn0{0)Xa4q`ZWSglI0dyCGr>mdKI;Vst09X5J-2eap literal 0 HcmV?d00001 diff --git a/data/themes/bt_sm_base1.png b/data/themes/bt_sm_base1.png new file mode 100644 index 0000000000000000000000000000000000000000..c37e182ed27b9b54dfb24bdeb3d94c585e10f16f GIT binary patch literal 477 zcmeAS@N?(olHy`uVBq!ia0vp@KrF$*1|$_fl!pK*#^NA%Cx&(BWL^R}Y)RhkE)4%c zaKYZ?lYt_f1s;*b3=G`DAk4@xYmNj^kiEpy*OmPShY%-+*@x^Snm{4R64!_l=ltB< z)VvY~=c3falGGH1^30M91$R&1fbd2>aiCQeo-U3d7N^%vKI?VFK%{lQiuqhIN6CY8 zqvfxZOT-^-m5x7nbdRh1(SwtgnRU)i(dhdeys^MT^RLBoxx5GS<))T?JJ0X%Ya#E3 zS~EA(b%a>(utI?n6N!RWDRv8%x` znQb1O0!+S_mpoeH!jk>gF+;|kVNS7E5oeT3gpOFcIAcIJM`)<*?DX}vxod5?rdF^9 zHCR41;W=F6;qonQQn2fjw5ug**=vtRbzl3r!>|*@c#Gt=XNgtT2;%R z)99GGfpJ}<^aHJUv&q2~512C=%@0i7ozft+aiCSUo-U3d7N_S<@y$AHAmBFtpNue5-oldD zU2iyN?f#k(Svom)`c8*(-qxn3rygPAvQw9I&fOtjlW_X;49Q64qx~icja&tv)-}fM zVYgCX+B>OV^a4Zq0p0*+HV+5x8YcMz(+`9ku-(8C=I}3B|MhvHa7LYm<%|z5Xm>_u zynGmD)SIbU=;!^`)L=iuS?~2xVm#MRGI%k2)%1q^w4a=My7`*a(qqEQrt~Rh>mK9T zKCRe}-|{)zLW#$jmDi%uHs9PbZ_U<_(9(_bl}}ijbMa0yXDf|0m)&$t&QbEjbTg+i zGx;>HbCz?8Gis|me(lqrDKsH>reE?Iz2`Re;Yl2f$!GkQS!B-qe_rCTRf~gH=dN}2 zbBonl9C`|MllSXCUv@uld%o{w8;zxMd%ufp&)xm`-u^tZ+2RjmKm6Ypq4rujWJ$f* U-yK?pz|dy!boFyt=akR{0MI+P@&Et; literal 0 HcmV?d00001 diff --git a/data/themes/bt_sm_hilight.png b/data/themes/bt_sm_hilight.png new file mode 100644 index 0000000000000000000000000000000000000000..63899caac8e015162306ef2a8088af573044dbaa GIT binary patch literal 285 zcmeAS@N?(olHy`uVBq!ia0vp@K+MCz1|)ZGH@^v_7>k44ofy`glX(f`a29w(7Bet# z3xhBt!>lO88kb?lj0n31Z52?&a>Ic34L`*eZ!s;n_?V)m~ zkbtc{=aGWWM~AE5zI}J#-KX{9yB274nSQ&GaPRfb$2~TuH=UO5GL+kJc-4G&m)>BG zha8*Z3cJ})9dX&XR(jDg*2I*lYOPv2>H%||OvQxVR|l<-`Lo~YI)6sVo)6qrehZ?- a_b>!XDC}*jKQ{~LDh5wiKbLh*2~7Y831e~q literal 0 HcmV?d00001 diff --git a/data/themes/bt_sm_shine.png b/data/themes/bt_sm_shine.png new file mode 100644 index 0000000000000000000000000000000000000000..23bf3110e10797618b2b3ec49c3678405a8c9bd9 GIT binary patch literal 275 zcmeAS@N?(olHy`uVBq!ia0vp@KrF$*1|$_fl!pK*#^NA%Cx&(BWL^R}Y)RhkE)4%c zaKYZ?lYt_f1s;*b3=G`DAk4@xYmNj^kiEpy*OmPShY%-^*%Wq0U7(O;iEBiObAE1a zYF-J0b5UwyNotBhd1gt5g1e`0KzJjcI8afZr;B5V#p$P$47m;{2(XyuO2wx?4PL`k zxuDKPkzYcZyZC{l0!tIOn6<&3!i+QfnPl!1Go{r8bsS)Ax##>oaP}ky{Tb|&)KU*{ zK5MYq literal 0 HcmV?d00001 diff --git a/data/themes/bt_spinner_down.png b/data/themes/bt_spinner_down.png new file mode 100644 index 0000000000000000000000000000000000000000..233f2a9f0c6cbdad10a1eee0a4913920b9cfcccb GIT binary patch literal 687 zcmV;g0#N;lP)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iXe^ z2qg*QV>fUB000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}0006CNkl=Gaimn4mVtTi}ivDRKyXqwgX zJ?F~;yeUb6PeFGckE-H*!25m)&`_ZP(BI_t-;=5$;^}+00La(~${|J;iy(kXp>R{y z4Y>$t^p}`Aktg2GrcgyhFviXRsdbjRUQt!m#V%G#RmXce&zd62a+{L=lI}~gDIXw& zfawiw+m3zh;-M1}*6a0EFnLASlxp2As9j!&c+xIbbvY_ z0FA0r*Y$rhI{@DMv=9zJ0|WP#pHzG>AIfN>B#f1 z=dZin?g7{*Knk3ys-kI{`0~p_ZVUWu_-D%~o5Os#U(-&5&p2xnS=V*GZQH}~czoJ! zw-3NK;FOl|xVhtR&_zlXF VCKkvlgGK-V002ovPDHLkV1kP-F!%rf literal 0 HcmV?d00001 diff --git a/data/themes/bt_spinner_hilight.png b/data/themes/bt_spinner_hilight.png new file mode 100644 index 0000000000000000000000000000000000000000..55d50b8575a5d43a4f25011f0421067afbdb5a8d GIT binary patch literal 344 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 literal 0 HcmV?d00001 diff --git a/data/themes/bubble_1.png b/data/themes/bubble_1.png new file mode 100644 index 0000000000000000000000000000000000000000..fd6d00c4b88c85084630bc6ef12eb5dbd9571beb GIT binary patch literal 1335 zcmV-71<3k|P)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L00!&;00!&<9(6c100007bV*G`2iOW6 z4kQ~B)xjhH00g&5L_t(|+U=XqODk6t$G>-Gl1ZvB#$r(+tH4`z)$*WF1nWv@>C$c# zEK=ctF6yF-Zu|$jkfQK-*t#fm(b69vwA7Uq25iluZmK(1fl@^DrOCvZxpQw9xi{X# z#Eg0Iy*%fBVH_qTFn;EH?m2fjhj7l(N`w#st(M|#ppoX!6^I4^q8w1pv0|s3<-uA( zZGb628se}3BmkIAVB-i=0t^8J0I0ZTD$qJi1!Mw%y|uOV=JfRRXM=--?<5k5@wkU} z5Cs2}%jG|Jc6Pp4SXlTQfG5CS0TpKnG6i7Rah%8Ha@h@nfHTIp7UzsH9s~g|m&>l> zIFA7g3tomaW$h0kh6v}^*4EbET3lTGHJwhUIp+w10PT`goJ0sgB9QsYAUjSSHA?KV)m?nTEfT5F?HCx`wKq`BI%}ME#;xXFk`$To&sZ=*?=isnO27YiH^N z)EQ=EXKHmPU9|VGG}3kEUDlaeJq~lN9&RUPM%QXzW9l%!W9bBRmkCIN)Y-g$!(1nz z9wi_RvHQ|UzcuO+NS)1JL;}(vwKKId?~^lCm>i-_Tf>a(OxdE{5a#v1ZO%Dmj9Gfv zq9aV%*Iox|C@>iS>ihm_7>1hI4GO~$zVDynYEa-BObWnr9OtR$d0dBjdslj%#~sIc zirSC>l`yZhVFMW5+uK{q<#O-YwoOdagbw){#4rruc^)qoi@#4!PObp>7fKuUwE+PD zSpaWrY;1fqH8r(h+xBqO7b2-t3YKNv>Lw|r2!a5wz|z7z&pY4U-Q8MVUj81yDS!*K z7!Z(shDp@=v@-%~MqDS+daz19gw)c~(%Y-6tDi<)9w?>oeIJz4%l-ZR?fLonA5a@w z>Zks1b)d=zPz6vD5KH3P7gZ2%J5(hgrg7D`Z8U)-5+s1k(b3VDBO@aZJN3e=5DyLx zex93~`$jz7%jN~WkAO0nQv|>&S`1ZL%9_9lAxwNB6vSP$ANP~sAFQvhzdJTI_VA_& zjV6dc35X>C{{g6oo9j1cHoG(0xL^H)XoIM#D_<`bi@&8(sXV1LD#T|3Vp%*euTNbG z++q;5)!v*7sO=m=6wv1O_V$NELqqvWrE*({6(v+?)6MpKW{)-^-ATf^rdUsh&(6;N zAcTy|5bpwF-Hoq$acgz)8wt~P9OvVKfr0Uhi;J!y-lyHct(>X2(gu)qUH8a!-At)e z0;Tk_P$>L3J3Ff;mRLZ1Zf71JAAfF|X6F3-+&w%z{BCAu=34=-B+jvc*e%R@cBhm+ zC=?1$CMG7n7N9N#KsRm>yA5+g3G+0rhSz058%v1YI#bqIfw=a?XQ2QX#u4K4mPUqB tYpR7TkMp}b(#`*_?2^cRsS$gj{{d1zyp#ipss#W5002ovPDHLkV1gA!W^Vuh literal 0 HcmV?d00001 diff --git a/data/themes/bubble_2.png b/data/themes/bubble_2.png new file mode 100644 index 0000000000000000000000000000000000000000..6e1e847a06bb34c254a557cda8f2461697f9fec0 GIT binary patch literal 1339 zcmV-B1;qM^P)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L00!&;00!&<9(6c100007bV*G`2iOW6 z4kRVgwA_yX00g^9L_t(|+U=W9NGnGi$G@{XyK53(jMyTDK*3{*hr-i7L9o(;r3ImX z=vDX-Up*B-POh8pfNh2fVZ)+@!HJH%+vn<{x=-Qd8OA&I}F3; zl}hF3ot>Sp=H}*p1HdHMbD;9BK=uI`^nL$HrBXQ!!%%R}g^>`Pa}kE2s8lMazVAN) zFerIh%9M>Cgjlki(<>`0ug}lV|CmapQbGuXVTg83s+U9vf#WzJgrHijR@c|p-&tB( z`W3(_fJg|z6-*m|3t-^z@bKGwKL4&|SzwHr*4-k{^T0Vrxm^BXWMt$M0Dl1pgb z*GeKAPAZqnJ+y5bK@b>nF$#hJwrwMq%RK~;lH3R(gitN=Pyn9my2FGJaLx_6_>2ic z2wc}42H+`}Dog4OhzcRh8kqp7WJI;t*aVXRunfrLKwI-S)f<+cI}OxCFq<|qRtF0k zU0&u*vf2c2ae8qxKool=%(IG@zSoKnA4g=C`-ZO#`~724o;! zJsO#}M%M(=bo2kB0U40SnZ}v-$(cG#0eMW@z)b8+bwsD~ z3g(4l*Z_uicXwCv`TU!n=MmesVM@LMF^VEE#zeVX{%LAzY6-ya(2ikW7!UxE1Mu?d z>gq?+)6;XF=MCQW7b3Q8!*Lu?O1t{MdcBTXt(JI8&KP@9DwQ@C78bq(a0K8_#0&_i zbA~P&=d`mDYF0kGxSfMl765y5bMwQAiHTWCX`k!5iJ=lgu)Mtd_1fCnF92$23{COY zgd;x-08{~-NQfu$Iglwxv>mFF5K}lmw{6`rkY`87(U`|cZ*6To9v>fnFDX>ZvT%HS zd{8J9K9g`1P|*UEtDYhORuMB)b=SxJ)biv3$N+c%AS66!z_sFYIFYPG|BKL0j=KVsZ@wL#Q2P;ayJFPmyh zRHhrKnM?+yQt9*A+1afYcZxQhJ=uu#U6b~ula}QvF;v%eA%u87G&J-Gzzex1M%{*O za-YJvmP)#Yn#<*|x3~A@bUIy- z(T8>IPW}DmeY;}f(*po60eBTa0l*^wZ*6aHZyX#P{KFU%`}_N=GG9B&Y)LQD3w!Vm zPEAX<_5rYb-~V`EU?4L(I{K+xH|yP$I_aes8XcgjjR}|0sH&B@f!PIATY|LZXHCJp xn>Ca4@~gHMsOonSx4SVgua;Fsr(oVm{{ryw-W;VWXR-hQ002ovPDHLkV1nB=ZkPZ7 literal 0 HcmV?d00001 diff --git a/data/themes/bubble_3.png b/data/themes/bubble_3.png new file mode 100644 index 0000000000000000000000000000000000000000..cbdcf9ca84f27e95a98547333de73e637ba326f4 GIT binary patch literal 1308 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 literal 0 HcmV?d00001 diff --git a/data/themes/bubble_shine3.png b/data/themes/bubble_shine3.png new file mode 100644 index 0000000000000000000000000000000000000000..398062f6223b3e6ee9ddd9909efae5f82f095d99 GIT binary patch literal 336 zcmeAS@N?(olHy`uVBq!ia0vp^o| zgW!U_%O?XxI14-?i-8hvK$uak)WQ@f$X?><>&kwEn}uJSUwwvYB2egpr;B4q#=W;U z47m;&NF4oGuP{4U-I3kaU0q+P%3S|Z;Hw7@80U!CP4^eb&7Q0`Yae?n&&;|?&)ICo z%8JqpKBgOWc7B#lV4u_QIAnuU(qx8j2TmQIeBhL0RQ2q*V3RPuOVzWxj-PVP$`0Nb zvD2eASBo#3=hAjF(PmS&%#7Lpw-rWLMELX#%caeA_EpQWOr$m!`(wR@#!*Mv=< Z7;-8DVxCMp8vyhhgQu&X%Q~loCIEYpdMy9| literal 0 HcmV?d00001 diff --git a/data/themes/bubble_shine4.png b/data/themes/bubble_shine4.png new file mode 100644 index 0000000000000000000000000000000000000000..9ab6fd04852664535fb9cde29db09d9b3478522c GIT binary patch literal 327 zcmeAS@N?(olHy`uVBq!ia0vp^o| zgW!U_%O?XxI14-?i-8hvK$uak)WQ@f$X?><>&kwEn}uIn%FFd)7f|T9r;B4q#=W=K zHu4@a5NUb%-}BvyAVo*U;w7h)c-kXW7CSf|WC&5Pm0Ip_NWhx6^L^FrOUplRUbtz; z?|XN5&oN!7CbNLK>_DJLrc6Wk%(<;!B-1_S?+#zVv3!MVx6`l2;5&<46?%_o=3QJf z(WpReYsNGWR*T6|ED0YUMFc>ra*?!qzPYkt@P}g(DjMw;WN)~m%r{7 Q0(yzT)78&qol`;+0AFT&?*IS* literal 0 HcmV?d00001 diff --git a/data/themes/busy-1.png b/data/themes/busy-1.png new file mode 100644 index 0000000000000000000000000000000000000000..0997dee380dc74fab7b5d5d0f26bdb81c4869769 GIT binary patch literal 2124 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 JPDHLkV1fqEfLs6o literal 0 HcmV?d00001 diff --git a/data/themes/busy-3.png b/data/themes/busy-3.png new file mode 100644 index 0000000000000000000000000000000000000000..96e63aba495f7432721cc060dea46a1ae47abf26 GIT binary patch literal 2395 zcmV-h38eOkP)DK1|kDJo_{OAaF|whGBc0~l^myH1frO;i7*2#O$Riv-P2P&9zy zuK-11AaUcihz4&%q zE%=dsb%2WxRSOa9WmyQmHiY-h1!8dg|1v3;>ODZf?b)_W`Fkn=e8({Qay9#%-GV>QWgOGe*eguZ@&4DlP6D(0`L+-gohF! zgpld!>2DfTV!MBpgX0r=^zrR>47RNG~%wJVi zExKH;;Iq#@`-ivQdh5FYy0(&_Tfr|}xX>Gq$IptQ*txp8y8OWhADp9<-rBo&Z;>%} z$+9eF1Gd(H5CYCQ&tx+5i9|vj92~6l_4VB<6bfg`D&hZpMCb( zL^7GI?A*Dt5{tzQx7%&WvdmOfy~H`U?9?z@Kp_^=U2?$Uq|2n3D*z{0{pPF2-~9Xoc^!r^dJ6h%%c<)SEZ zpU+oN6lJzuZHzHvib>z4^3*uQ`O&j18$El~UP zQ&UsJPN#FY*=!o)(sI=Vp$fEB*}8S-OH6qWx*zq$z*PKcX#WuEHg?eXN(a=QM`ph;Xt)oeS=bZP!vV4 zP598EL(c&40ubz6KwU1^ep?&e-QBThG#WEa^V_vrZ7!eB-w;J{&g=CuNs_G2&Q3F* z&wuXmcoOw`UB7eZ&eEPedkj$&d9_*%7>4l_A!LXUA`(J2qogh2aJUbE2Y_RffFKCT zcC~WOAqaxQ=kujxSxy;-p;juDnNq2Aoe+|zl**M#1)8S09(m-EKDXO#HJiF7!PnQ< z^?R*tKaeeqF#{XdkZ#rkhG7&$QS{$SWi8);X_`En%`RQNdNtkE)fF5V7#MCgo8+U9 zKAQJ>y;lYX2Ey@pye|@o#3`lX{SMS@HXGQe8z6GdIU&T-b$vmSq<-4E7@YG>6EMci znVFf~k6R8^hw`Fsc4ZLjOPar5TQ`RmuOPrKdj^<*-s_V)H_p-`yF zIp5yV(c$KtV`OCHiM6%0xkMtNxm+$wRn=OtSS&0rFaIZ#$pmCsPK83DWJgDb&$2Ac z&(GfkpaWo=1STdX{_@;&&%HqifvT$7jT<+z)6>(p!r^dbaB#35kH@ueIBa-49uoi* zMH#exA{L7!a=Bbc(=;_03^u#Ex>zt6Y;N1OO;;49wzjsGUtCBwK zQ~->$R80VQ=H});_j!DDn>G60>Q4~1viFaFTVIb=X}@N+S=@a0|$N%U*w(QLTG}7tx zZ!F8g?%lgn{r&yEL?WT}_VzYpS!PbBb2G%Ms=5<^qus7OJw5&Td_Gt#79EVSjZ8-= zr<6j|v>wj+la^&+Y;5e$0LlPr0L=De#70L)|5_*%{sn-hQmOAKiqfg;`dulTF-A<& ze6k(9Km~M+n*09v5us>FG(WuC98k)vCxCBlUV+nxCIPY?@|N z)3nl&BS+o_um(T@(BzzdMWAH{h=0f&iMsNl3o-=F=Vf6FUKv*f~u`SX7|e*E~SEt}_Cc5m=4fDh}8C;%6LE&##TUw{3ZBO@bE#pCgBbai#b1VNAp zAx=%x*30E`etCI$;ge5389#UK+%z^kz1RX)0kC^@M-S}{?Y^)@#Ep$grn5D7wZ3rx zO>BhMI)G|RbZmILb>IEJZhPLAw#Ak>@KuKl0A`DXiB_V)LmE>6_%CIWc?J}dw-x{Z N002ovPDHLkV1ka3i^2c^ literal 0 HcmV?d00001 diff --git a/data/themes/busy-4.png b/data/themes/busy-4.png new file mode 100644 index 0000000000000000000000000000000000000000..4ecb44cc90ae2d7e735d554af57e0fde98024284 GIT binary patch literal 2395 zcmV-h38eOkP)gS&v(9i&v(utoOAp?ix5HpfPc+DBLB8n$En~JlE}+K(U^y1Y z#>NJs(ddhUAPl-(t}G!$VT>7uVKke~=47o_yOqo3F2C@?3m*Y!1E8F9_O$_6j)hz< z_me;%@JpxDxzql}Ils>sV;j#(r7}J>HTB2mo_p>LfF=O_VT=fma(?^v?QfRL<;&4% z^v|*^?<9m^d3kw>5Q5Dn2*So*QIws#cklkg#KgpfS6_WK3&2YV5g(fYLI|0hoP0Ww zNSqf%F$4hle187s&6~GXRV^Jka^#0zuh(x!-N^!D42EHthG7^EheK{Qn`1M&bb6r{rCUX+uOUcbLY-VUteD<7z|R6 z$72#gz5u{CI|qR4*RM|`5{XJSo2@?i$Kx>tLEwTQK$hi3v)Np+o!YBdESB^6 z{8T!fuE%0Ay{oIs$Ye5=cDp^oIX8QHdiK8i?z=Am2w+`D?qfhy6y+BHz!*a+l?o|} zLT$$z6bS;CWtp{Ft(gw+;GFZTSFe8D+uPgd>+5TJJRVb$B<}P1%y>M$qG{SBAq4yO z?RyzO*k(bnqrY?K&Td(j_XB{_>2&SizkmP0z`#puYis?*V$rE-n#dR<)^|=R&Dj7r z=lJZi&*pSpFKpSer4b5+s3b|;1{@3qsl(y;z%)%33E=~d&kDc?)rSbayp%E1Ofq*F$PMhplO=3)oS(Wx}IT-rDa);nx=_xINT4w+X+B) zI2_qdO|bWzb34_sb1sUa2to)<(*)-nfk2?wIs!@RsBm&80LIvTIc_h9!{JRN5<}H$6_H2;tyT-$ zwrv}bBq`wadSikhxCtQ}qGXFyXHX7@!wMz^XJd!4jw#M+rE8!Ruo0Y=1RHQOw%;5-akO%oO415*EH>O zr_;HG5Q4R}wQ8YISkCA3i%UyO1zDDxU0q#zJRaAx*{tsIcuZNAn?9cp)6>&Sfk5DT zrBbQixN+llGMPLOkH@!i&dGxc6=Mv`%gYM@C;-!DfHfM8PZdS^UM`ng7#SJ4mPjNT z(P*@lPN&<7qR>DfK;3S)>2x}ItJU%Y*hdIKI-QQ(y?fVq;)y5ffj~el6bcu{$H#k9 zsnkJ5QM#>&?*ov_{r&w?e}BK4N~KyppU;#eiQB?L zDJ7<9en%8VCu0nfBsoH%P?Qi-ibkV)S67!&DwRIZ<#PGO#l;<|RBEpzNuJJ2dF|S@ zn*bUBs4Yb7*s){d^?LnNLI}xbvpWF5=kuAeEHkIm$!s~U)oKYs$Ux_13xz^SRaG5~ zG5CBwGnq`bckS9$jmP6RbGh7K=H}+cbzL_ZV<;2~Q)kbfod8hZ0ARIC?a9f>-!aC} z-QB%aRn_iFr6Mu*WlKjXC5B-P+2?CV6%L2vs;W9QO%nmY>2$JSFi5v<-Kq@^4z7AU zo^jJOb;cMjUApv70BaTiv$Gh{XPVcVADfw(Nt8;ZZvzNy z2GGGmLRD3VuImD&l&r0-1!rexk5Wow?RL9)>eQ*<+`4sZ+5({2?fQdyLJ@%f?YG}P z{QUFJpLDrgA;U15q9{59VMDk!RL*8WRaN!gy?cM(wQCnBrTcVU-@!Q-o6TnBop;{( z_36{6{|#UkKnXzGZqpyu6-xm8hYug#{@QD={kEs4XK!b9v;lNBrKV|Ob#-+n7!39@ z#stO~78e)C-hA`T-;a)t-UToZU=={Cb4GaRU}7=h1<-x+fA{>#}{&W83}XaVtHy_4|)a9i)} z;gn)MwKS~fcn#}vYdmT`eC+Aio)axF4giw1w=>DKK-gwtJ-Hs~;6M9vXcPU#UhV(@ N002ovPDHLkV1gN&j|2b! literal 0 HcmV?d00001 diff --git a/data/themes/busy-5.png b/data/themes/busy-5.png new file mode 100644 index 0000000000000000000000000000000000000000..2978f49068eb23579aef6927a80a8056a1e34c6f GIT binary patch literal 2299 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 Vr(*IEKR*Bf002ovPDHLkV1gA(Sik@P literal 0 HcmV?d00001 diff --git a/data/themes/busy-6.png b/data/themes/busy-6.png new file mode 100644 index 0000000000000000000000000000000000000000..a73d583955c66632d0b3485ce5386552fddd7e78 GIT binary patch literal 2216 zcmV;Z2v_%sP)grNMKR7DN<2rOCX_&R28W}6R9OqB_2>yH4+c- z*ceqpq6pg1NIdi*eOMk0LZJ#V6s1;5tCnE9)CMXeduwOcHeT=L+-If_dyczymrFC! zzcZ^nd%o|#&i@lBCBEz;gplAYzvPR^|MNc|Fc8JxDFEq<2;_MQJr@BVSQ#H5-=XXJ z>#C~uGsa#bgoLG(itD=;)O<-+XfnfCIoq)i_TCc`5-Pm`+Vi9gN50 z$5d7QYVezsa+L@nR`yb(&nE5}5JJer z#Kg{yj*iQWu_ge>X0y|`Z{NPdIbTR7lXg5FcSE6&P!uJZN~PYaM?eSx+qR3DOyWw$vNCSuw zLTFtA0BCP-@B4w-2_fj{=xE-(d-uyi2tp~9j4??mm3~YBKrDE+jy18gv{YPNTwDx= zLi+LJ$4>!h0T2pm2(5XTJbLu#P!MpnTJ`kwyr}E?%QG`GVau{sk(N@%)`A8yGc)tW z)vH&pPfkvLCZ$Asd;2%eo;`a2KpfRNvdRKVLqo$)*MbN8=FOW2Y}-!H&d!D$$DzIj z2q7d^Py4a4v4=Nq+_>4>+ne9GapQf%FzypVFfcH17(i2C1sZ67_wLyAK~ej4v!KsJJJ^_5#%S{zN&1f^6)qfx;ao0n3e zt*xyW)!=189Z(o!eE|ribQOuUK29VOFLZZz|9~+TFBXfeP$-nHU%&oIM@Pp(I-M?d zb#6;TI}f(=_RM9-+R6DWwoXKv9&U>$*@BMFXG$P*`x`2qA=& z66@Emr;$ixuC=w*;+zxLb*bYxv`{Ee$8o6RIMgr!*yLd za7_?|vRp3zQwV`@I2;o~5XP8{Mx#6$jdESrJzdv%B9ZVyp-{Y~rR9g6ot<&U*kUG= z88QsxN~KaM)(hHt*Y*7T{J#Nk06ZWdDwWFTQcA>Pu|%<0WS-}(iaa3%ipAnaLdcI5 zMQIX3z;#`F)227B+rNK* zCZEs$QA&x{*4A%QO5aix<;AtYH7>9;O%uTtt!bLj2oCbC{-SoIZVe@b>N7qX2RMD!#(2dqTe`neV*w&d23)`N+Y82R{gfLJg?1{1`A* zRTX}k62B#HTv%B6mTlWFDT+c&(=47jbLN+sOy*Mn)4ujAjp_e1rBX^x2q~XDdGh1? z_wRr2=+UFUXm4*H2%61c2_c}WDg*G9d_EtNQtGyCH*?OnNGTN|1hU!epHG}P@#{Nx z?)(eDjPHB9c1C#GT%e$OWxjCk+_}R80|SSfnwnC9_Q75om^GDde0X^H>U;0KcLPA) zH~SLm3@FczLQKQH#Idibt#Gx5<+m!xwE*q_-JNk=Hc-0 z@Lw{S%!F_1MIYDz;MJRso;e!^bD>WpifShl^UoTp1FA&Tua*y1K{d}!JYzn5?&&zV qwo#3nKotD8f6p8qyMM0ISst6uhMf3$#JS2~4 zREUJCT0+TFU(!?&5s6A8M1m42U<9HR3=YP!&905(wY}@Lcf8EZ&gGmw?2Nm(CZQSW z*BQ;sIp6pH^Ir+)9N+gMgb@Fpf6s%+|Fh2n^hNYm0RZ=e`SQ4g9*cknERK$jz7UN@ zeev)LRQA0PkAzJ2>X0-yu19!27j1PCGI!i5Xlo_p@OzpASG zQ~!CR(O4~)%QJIxbMvw+6IE4ZMNt$=X`omv{;-oswOSqd@WT)P@YY*z-3DNA&fUi% zKnNid6BC15w{HDArL+qGMn^~QOioVTV~j1PQmNLKEnDnhFzAY+$X(YZ017=lJwNXx zz!-yJ7%QhwpFVW#*s(7GG&$!^Cl=id{LY;_FFx_a6Q58@L*6qqn@v-e<@sW7e9(^QY->qr zU}$LQ&qG5)PXh=MLWE5T01yg=!YN8=(%0OVKp>#>_4VzpR4S@znh))3wORp5lCqmv zvvYs^%{SjXsVGVsfa2#6q2pt6@7}!wzQg%i_y-7rfS#V7K26hd^?F@$9ESh^V~jYC zv)w=NQC0weOeXXE+i$j*pMuC4^w_-o3v9ko2t}_}bsRdGlFCQJw+XF}`v2C6mcyDW%25 z#YNe&EMi%fAd2Gl&A?}8XDc6n{PDR`sWf8S_D#+?y1Kghj~qF&3qTNn;70*TBoeQA zCgq|i65o?IBU3CE_guSnZ7Lp*+mzCXs;cqM_sh%6+U3iaZ)%!0Qz#Ug-QC@KI2?9t z+pZEqQUe16F9G-pKx3T%rSus97#SJ4xv;QM?d|Q&a%BIOi};)4F=~>Yb^nsquV1zqVt?jtBXC-i$`04gk!}&5a9!kjmw9 zPXh=6kbD9nrL>Q84%c-bgu~&IWmyxqZ{HR*O$#OxiCiX=$z`+IY&;&10l@a{+n+TI z;~C4c#D#?gwzRY~edWrPTZu%XF)%RD?C$Q?lgXs5sw$(Da>f{uWqH!J?U$p`XaPU~ z0A06$D2fU1KO6acUhnDY(HUbz*Y!0`)0XS?`kk4X8QC<=NIIQ{EF5UF2q7-Kf)9IaN% zR8^HlA`#bPZZpP+X_|tr>w>0f+T!A3RoC?wP16(|$ARm*La|uf*45Ru8i_<4O6fW% zV~qGD2q7wC41^E~?Fd|VLhd+Di&6^L{cpVx1c3{J005j)%2icmk|fE|Xmsz|+8Qa9 zN@%rO?Ed}xWN>hBFX#M6hGA4|wOW~TUQ!fgCKwE^{|4K(1D=wak3l)-oDjkd!?-KU z^0s_Fzpd43O*xK3WLaL``74ytv>yqs>+))~IzKQlP&EwWE6cLBi=wD@<_tmzRTSk(Q52taUH4@| z2y@J$->OhHyBXux&fJva&)~S635_M&mU>5PmI+V!E@;)@rp? zS(ewjySw$?-rjnxR=d2hIqCe~dnRzs@#&|ZjsP$^3Gn^<_y4QWXk6!Njn~oJApvpx~}WX8~Xv*bst)*)#}WdGiSyDG}j4u z?NV!EV&YxK7z%~Lv$0rg7w4RA2F@76{QP_+9*tPm8H|^mZoW6Y;4au!5L#X zfByU@09HH#Zf7xaUVZh|k7~8r$Of}*G$Sm_a+j8tD#>KhQdN}+g202ppxf2eHPvV| zrhQOf{JrIJ`SytuC(Z+?dcT0L6X2XP0LJj}@Dal>Rvx7}V+@Oni_4)d_uIs`yP4nc*lYhE&>Cz~G3IN?x_~DMo^9AGe*I)nV z`|rPh&@ha~W&|pgN+lAB*ovYsKTr6*0U;zRilXC#H=9lE)TvV^PM%>^RbB{MxdJp9W&d-nV$9*_5Umhvt3kfZwR($dn` zpMU=O+2hBLf9W|~#nZgCaX|U5$w&a8pxwiD9XfPqU~q8om2^7Y6OBf5vMfg&$FW`4 zwd?hIxl}5RU%Ytn-yeMN!Pg$(GTIKO18_E*j=pm?^yfm4ND#ml&oTkDORDcj4%+je zj&_VU(GE4+ceqW@f86QVFWYDjGrou&1YD1VFD|}gFa?1B0BBr?-uzuZ#sB~S07*qo IM6N<$f~l2cU;qFB literal 0 HcmV?d00001 diff --git a/data/themes/busy-8.png b/data/themes/busy-8.png new file mode 100644 index 0000000000000000000000000000000000000000..c07cddc168f8162e5d22b14b78c470b33b4ad5b3 GIT binary patch literal 2293 zcmVh*#(WupGwff4+N<-K64qex`YMRy+i^Vnr0HqX*i;Mqw_uY4YIXXHz z3BY8G`42>Z5W-!#a^FYz zHId`EZ9_vtKcFt0zvJc=^zwL*oDp#+cWRCEU;Q$;ru`-QC@%1wn`f?*ITi z&y$gnk*saoHwOj=j6@>g3xdD^!1Fv}7zXb+&bCm85CTO}lKb}U`-3Qozj*Dn*FGeK zEVp}tTMs@lG0~UHEG_%yLS*kj1a=zmjD2+x3~BAf*^FZThT7bWO6gdaa-&4y6Aac3yD$+*LA<& zzIeM{BofgM9Xj+o06G9U%pdI^lbM;BpDK#-RJ+^51vrjtJ?C<{?d5V=b{wZgpxJE3 zMNu4V2VFlpJ3EJ7fBp4m0c--mulE42Y1*&WZOK3qO7c}2$WLdc^+|H zcNZb#D>1cxy(gY{;sAh-&{lvt?4q285DW&w-v15Oknwpw%9LEFJo_PR>L?TK& z9`CJGDx%{!#57Gs5QO0kk%Qs;KI`b{7&v(F;G+Pd0JzWtMA!9w08p(~tAvo!ty{PL zIzB#ryih3QEz5GkL=#Fbmm64ESdf>Omj%~#M>vjC?nk!SY+6%OQ!{7IocUy7Vc|9a z3=a=K3Lp+Z2wg@5L3jiJN~KaMlgTu9?AWnP2&tFL<;wW@_^0V~da%F0|KUg^5@n1b zlgV`F^ZCU5{JhuG)3d8RpSZ5;6^q6B>FMbki;IhQQmK^L-Q8_Vl9XhO<+9oAAb?mq z0gmVSZHzILN~Lltm9mq`q#KP!{f>?fHGsvnI;sitXOI-R!5ra3Y)Vr|*7#ooMmv!|-6FG&&&Vql@!Y=YxB8Gs0YZ*2jk)MAW5 z)3hkh^K0@m$8jtmXg!u01u#bY>4N1O;Hq~Y1*cC@bH*9jw3ma^KAfwnM|f zQcYD=Tla@!gmw=%|X>eQ)oSS?iiRz3Ip^UqJLtgPe-AtYR6 zBgyCUGrF!f)9JLOX__aB;uX*H-1U_ar4#^!Xf*nWBuV=jWBk2)_hvu%;Dc!Z1^|x> ztYQG{LZL7gDsDu=G)?E~)vI6Ra=At-m2wnCp@~GoY&06z+x6P@ecx~WK6B>G2>>+! zEA1Wt0PmS+o;g{qRxh;!t|u}zH8q<|CXIADZAGI|%5fZ1Rn_->f3p2M-}hS*zAF}s zpTG6iTW0}O0ayT7ivVMc0%*Sd_S-L8mQ}r<^^W8Cg+k#>= zHmZtw0Eri0d~x`dS6=x|S6A2f2qEx&pIVl+!1H`jmgO6gB$XLsanJKop67L#rr8N# zfH6iWrI?$W`{MB7!*AyE`6~c!0k{XiYVQ%gt}o!RdS!OL@x~i_AAkJupKF@d7kDc4 z815JO3kwU^PoF-0a%^nuZ-L9_1Iz984azrlMjQYct2JE5{{8#EyJydyAL+W@r>bgN zmgUW^>)M{@+4Xw;?)B@}3+K?|$9UH}-~MdlnFhVzrWqVf8+j zuo_1UtNUtWHNzQ!m{^T=y5af{+8qZ(xPXip%mTg)WIrGgijQw-Oab6Ouz^;eM-jSN P00000NkvXXu0mjfXBlQ6 literal 0 HcmV?d00001 diff --git a/data/themes/busy-9.png b/data/themes/busy-9.png new file mode 100644 index 0000000000000000000000000000000000000000..9fdf098c65d3f56012c0bb29713eae48617192ef GIT binary patch literal 2249 zcmV;)2sZbLP)@ckkXky?giWj{uYaSWAIe5&$8D+_-V0sk5{5&#J2a zu=1U0ns#4b-#^3Qu%l@jD5aD!=5K0hS``k58$2MXRO;4+3m1-@Jb7{$Kv_!ZycPgL z2pJg}>5j+ay*{5WUZJ)56Myi*2Oq9lwQ8oZv9SyQmSxdgF6SeJG{)ocO?7p3EdXe_ zTuxoSeEGejM~{9AAio#{dztg$;opnkw~p=+muo&HBA!$plO<@s;YAQet#_?WTUr6Q51F0o;`oOef#!Q zZ*T9Hgph)iQUG%yR5@r{Tic%)V-4PEm$FDC5-t=9%(ATcJt(D82tg^O?@&rv<^KbL zK;+o5V}Afp55Vu`kom=g5c2Th!*~3C|J$5%`}+0kgQjWP-UgJ?r2r5i1OWifIVlth zJ&dshy75Ld8tpuF>eOBU)tJj83m8x$k;rcWU}9q8(b(A7@YSnVFD8@8>6cwaI2^7n z7K_X@O)7+d5Q60M`4x(yy!8#w75dq+W5;g*L_HR$cltyk(V?p9_oS4#d-v{F>(;Hy zwzs!G9vK+d9tagsoc`iVsv(P<^g>u`C^ePIX{piO-TgLzDgexj0^;-ewgAA`*w{og8a2b=FxNCqxK^sEsrm2F(9mDw z@%Z+YD_3>^Al22?wW(A}Ef$L_L!nUTVy7?3mQqSdR;*aD$z@<3fTAc$vy>8!<5=Nv z*wS^~p_EDh&~@EewrrUU1Ok~SPo8|5NF*lKuV24&_3G6d%jNQhQmG_Dq0oY~oX_Wr zsZ=VLPN%b(xseJ6gX)$oTXyKW9sv+oz<{DC%cPVbgm7Kg9md##<1of#ZEda17?YEe zlOvX8{UjEP!7vPEe0*HFbLY;(Y&M%sr_-rSCX@2{e1@*;JQxh}>gsA9kH@*DX-%$v zLI8XK6b}FuLKsrYkPyP5ltKtWIOoKhIp;pkd4mw5p`oE6UM`oJVHn_?!!%9t$tR!O z>FDT4z468y#`^W^ZC%$LUDqAI-!D{Em5ec&PN%tH7*G_&kGTk>9sp@sR+=$ZZ&{Y) zoY&=Yxs{5d#0ViV##lXLEUc>Pyu#Dzv^6$1#vI3?bNrC&#SHk+kVN|Z{a7xT;|u-kq43Xh|lMs$m$^%aTF}n5NkwguvwFbTw6tW`tXWfxL?Ybp z_s_WTJ-?0+qC}(7ZJhI8Jb3V+A(>37v$L~5kWwO@PLK8V^*sbooCn~ROXkqf(5cGP zECw(zFmR7j`n0XBEgy|WEjLM7mStrZuaidVFS3n4HyHTB~D{rf|0ZEgAH=4M0JbwMeWs;UaxwqGm;>o^V^ z#{nTk4Tr-&l2WQqpFaK1nKNfT2QceuK+Xej3xx8ybLW0tE|*i4n;C{-_xJaI(c0RY zZ*6TYR##VZFH17Uq!8kH1_raUQ^P0BHcWlu|A(NUU?`&fULq<;oG; zwoMN}B9XYKX0Gwj6NC51YQqsz+o0^&$Iez^3nZd!qdjKALcVF2fys9ryF!#x z`a&0o4j|+*6TsXj)l($LTt8R@P;jk`Z|M(TyF2#!M9c}7xz4=~82}s?glEpH9DCz` X4q0~euV!ia00000NkvXXu0mjfb7)ik literal 0 HcmV?d00001 diff --git a/data/themes/check.png b/data/themes/check.png new file mode 100644 index 0000000000000000000000000000000000000000..7d58e851bb5bf12c76161c4e872a3eb24dbe36a9 GIT binary patch literal 3058 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 literal 0 HcmV?d00001 diff --git a/data/themes/check2.png b/data/themes/check2.png new file mode 100644 index 0000000000000000000000000000000000000000..1748d5d62d5b0b5647a7093d9e3476d07cfd3c43 GIT binary patch literal 2561 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 Rz`Vx5;OXk;vd$@?2>>By|KI=s literal 0 HcmV?d00001 diff --git a/data/themes/color_picker_brightness.png b/data/themes/color_picker_brightness.png new file mode 100644 index 0000000000000000000000000000000000000000..b2bbf5df56ba1f8466a8376798cdc45a4086f35a GIT binary patch literal 657 zcmeAS@N?(olHy`uVBq!ia0y~yV6*|U6*<^|q>GjKcOb=C;1OBOz`!jG!i)^F=12eq zS<)SS9T^xl_SO6joDAeEBzpw;GB8xBGB7kWGcf%852Rl*Fq9fFFuY1&V6d9Oz#yJK zDgLM%0|OJgr;B4q#jPWg4)PvQ;9>TaXkgbDc(XsAU7>ZA|16f45S7#4RQEq%h>5*( zHE#Y&&f00JX2rd4Q@sCod)AtJpQ)18T>nqdPxD~)`K@6`Bx27=Hn$4wn9{V+P`|Ux(yCYixWh8ngR`!7#tXS#VWu&L1qS~ zj4cPGSwTDr1_6h~toJk|fV?9N4GdDcAKVTCdCF`IEEh5w&AC84Lk5KgH|{-w20&g1 zBLkyJ)Pr82p*tCGUbDQZ$KF^ESfn-_mp&V2{8FEc)I$ztaD0e0sx-& B$RPj# literal 0 HcmV?d00001 diff --git a/data/themes/color_picker_color.png b/data/themes/color_picker_color.png new file mode 100644 index 0000000000000000000000000000000000000000..1c609f8f26374f95b1122dedda3f18bcf09373ec GIT binary patch literal 4480 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 kMAPSucachj-Bdx{10hTOg`~Uy| literal 0 HcmV?d00001 diff --git a/data/themes/color_picker_opacity.png b/data/themes/color_picker_opacity.png new file mode 100644 index 0000000000000000000000000000000000000000..370ea1c1aecc31705af1fa27b6892138a8d24a01 GIT binary patch literal 3886 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 b|6iWrWvQJ1*_wwQKs^keu6{1-oD!M<%1bpi literal 0 HcmV?d00001 diff --git a/data/themes/cur_glow.png b/data/themes/cur_glow.png new file mode 100644 index 0000000000000000000000000000000000000000..fd922bd26f39d2b7a46f52882adf608ce7107e83 GIT binary patch literal 391 zcmeAS@N?(olHy`uVBq!ia0vp^0zk~g!3HGv?z=Y!NHG=%xjQkeJ16rJ$YD$Jc6R~N zK=9LfcRi5eEbxddW?9iMfAkVRn@oyBiB_CA^ z6^|2eWT|Di|KD(zpm8KbLh*2~7Zx+LW09 literal 0 HcmV?d00001 diff --git a/data/themes/cur_hi.png b/data/themes/cur_hi.png new file mode 100644 index 0000000000000000000000000000000000000000..cbafef893de3fee14d0cf458a6951ba356fced50 GIT binary patch literal 188 zcmeAS@N?(olHy`uVBq!ia0vp^JV4CE!3HFA>TRb3DaPU;cPEB*=VV?2Ic!PZ?k)`f zL2$v|<&%LToCO|{#S9GG!XV7ZFl&wkP>{XE)7O>#2A2RMi{8YHn+iZ7$r9Iy66gHf z+|;}h2Ir#G#FEq$h4Rdj3FVdQ&MBb@02&A}CjbBd literal 0 HcmV?d00001 diff --git a/data/themes/cur_shad.png b/data/themes/cur_shad.png new file mode 100644 index 0000000000000000000000000000000000000000..3e899ded5309e3bbb0d0837edfdb568cd97592a1 GIT binary patch literal 252 zcmeAS@N?(olHy`uVBq!ia0vp^0zk~h!3HEx)yO>uQjEnx?oJHr&dIz4$s~EZyDx`7I;J!Gca%qgD@k*tT_@uLG}_)Usv`UTmp=&QY(+kTmcG6mbgZgIOpf) zrskC}I2WZRmZYXAlxLP?D7bt2281{Ai31gdd%8G=NL-$J-jJ_BLBQo=dqB31&E)cL z0TOFfHwN&i{wtbnZ!B%&(&O=KN5P_y#3Nmj3zZd;o!2qGoI3qn!>(HwWDfEFR5rDL nDu1tUQD)DKS8MpV_@+pooyRM3#Ub)1&| zgW!U_%O?XxI14-?iy0WWg+Z8+Vb&Z8pdfpRr>`sf4K4vjHm>=x@j!V7$r9Iy66gHf z+|;}h2Ir#G#FEq$h4Rdj3= 1.0) { + emit("elm,action,focus,anim,end", ""); + set_state(PART:"shine", "default", 0.0); + } + } + + public update_offset(x, y, w, h) { + new x1, y1, x2, y2; + x1 = x + w - 15; + y1 = y - 15; + x2 = x + w + 14; + y2 = y + 14; + set_state_val(PART:"shine", STATE_REL1_OFFSET, x1, y1); + set_state_val(PART:"shine", STATE_REL2_OFFSET, x2, y2); + } + + public message(Msg_Type:type, id, ...) { + if ((type == MSG_INT_SET) && (id == 1)) { + new x1, y1, w1, h1; + new x2, y2, w2, h2; + new px1, px2, py1, py2; + new rd; + + x1 = getarg(2); + y1 = getarg(3); + w1 = getarg(4); + h1 = getarg(5); + x2 = getarg(6); + y2 = getarg(7); + w2 = getarg(8); + h2 = getarg(9); + + set_int(s_x, x1); + set_int(s_y, y1); + set_int(s_w, w1); + set_int(s_h, h1); + set_int(difx, x2 - x1); + set_int(dify, y2 - y1); + set_int(difw, w2 - w1); + set_int(difh, h2 - h1); + + px1 = x1 + w1; + px2 = x2 + w2; + py1 = y1 + h1; + py2 = y2 + h2; + if (px2 > px1) { + rd = 1; + } else if (px1 > px2) { + rd = -1; + } else { + if (py2 > py1) { + rd = 1; + } else { + rd = -1; + } + } + set_int(rot_dir, rd); + + custom_state(PART:"shine", "default", 0.0); + set_state_val(PART:"shine", STATE_REL1, 0.0, 0.0); + set_state_val(PART:"shine", STATE_REL2, 0.0, 0.0); + set_state_val(PART:"shine", STATE_MAP_ON, 1); + set_state_val(PART:"shine", STATE_MAP_ROT_Z, 0.0); + update_offset(x1, y1, w1, h1); + set_state(PART:"shine", "custom", 0.0); + + anim(0.2, "animator1", 1); + } + } + } + + parts { + part { name: "base"; + type: RECT; + repeat_events: 1; + description { state: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + visible: 0; + } + } + part { name: "shine"; + type: IMAGE; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + image { + normal: "emo-unhappy.png"; + } + rel1.to: "base"; + rel1.relative: 1.0 0.0; + rel1.offset: -15 -15; + rel2.to: "base"; + rel2.relative: 1.0 0.0; + rel2.offset: 14 14; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 0; + } + } + + program { name: "show"; + signal: "elm,action,focus,show"; + source: "elm"; + action: ACTION_STOP; + target: "hide"; + target: "hide_start"; + target: "hide_end"; + after: "show_start"; + } + program { name: "show_start"; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.2; + target: "shine"; + after: "show_end"; + } + program { name: "show_end"; + action: SIGNAL_EMIT "elm,action,focus,show,end" ""; + } + program { name: "hide"; + signal: "elm,action,focus,hide"; + source: "elm"; + action: ACTION_STOP; + target: "show"; + target: "show_start"; + target: "show_end"; + after: "hide_start"; + } + program { name: "hide_start"; + action: STATE_SET "disabled" 0.0; + transition: LINEAR 0.2; + target: "shine"; + after: "hide_end"; + } + program { name: "hide_end"; + action: SIGNAL_EMIT "elm,action,focus,hide,end" ""; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/focus_highlight/bottom/default"; + parts { + part { name: "shine"; + type: RECT; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + color: 0 255 0 50; + rel1.offset: 0 0; + rel2.offset: 0 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 0; + } + } + + program { name: "show"; + signal: "elm,action,focus,show"; + source: "elm"; + action: ACTION_STOP; + target: "hide"; + target: "hide_start"; + target: "hide_end"; + after: "show_start"; + } + program { name: "show_start"; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.2; + target: "shine"; + after: "show_end"; + } + program { name: "show_end"; + action: SIGNAL_EMIT "elm,action,focus,show,end" ""; + } + program { name: "hide"; + signal: "elm,action,focus,hide"; + source: "elm"; + action: ACTION_STOP; + target: "show"; + target: "show_start"; + target: "show_end"; + after: "hide_start"; + } + program { name: "hide_start"; + action: STATE_SET "disabled" 0.0; + transition: LINEAR 0.2; + target: "shine"; + after: "hide_end"; + } + program { name: "hide_end"; + action: SIGNAL_EMIT "elm,action,focus,hide,end" ""; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/bg/base/default"; + images { + image: "dia_grad.png" COMP; + image: "dia_topshad.png" COMP; + image: "dia_botshad.png" COMP; + } + parts { + part { name: "base"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "dia_grad.png"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "elm.swallow.rectangle"; + type: SWALLOW; + description { state: "default" 0.0; + } + } + part { name: "elm.swallow.background"; + type: SWALLOW; + description { state: "default" 0.0; + } + } + part { name: "shadow"; + mouse_events: 0; + description { state: "default" 0.0; + rel2.relative: 1.0 0.0; + rel2.offset: -1 31; + image.normal: "dia_topshad.png"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "shadow2"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.relative: 0.0 1.0; + rel1.offset: 0 -9; + image.normal: "dia_botshad.png"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/scroller/base/default"; + + alias: "elm/list/base/default"; + alias: "elm/genlist/base/default"; + alias: "elm/carousel/base/default"; + alias: "elm/gengrid/base/default"; + + data { + item: "focus_highlight" "on"; + } + + script { + public sbvis_v, sbvis_h, sbalways_v, sbalways_h, sbvis_timer; + public timer0(val) { + new v; + v = get_int(sbvis_v); + if (v) { + v = get_int(sbalways_v); + if (!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + v = get_int(sbvis_h); + if (v) { + v = get_int(sbalways_h); + if (!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + set_int(sbvis_timer, 0); + return 0; + } + } + images { + image: "shelf_inset.png" COMP; + image: "bt_sm_base2.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "sl_bt2_2.png" COMP; + } + parts { + part { name: "bg"; + type: RECT; + description { state: "default" 0.0; + rel1.offset: 2 2; + rel2.offset: -3 -3; + color: 255 255 255 0; + } + } + part { name: "clipper"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + rel1.offset: 2 2; + rel2.offset: -3 -3; + } + } + part { name: "elm.swallow.content"; + clip_to: "clipper"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + rel1.offset: 2 2; + rel2.offset: -3 -3; + } + } + part { name: "conf_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + description { state: "enabled" 0.0; + inherit: "default" 0.0; + color: 200 155 0 255; + } + } + part { name: "focus_highlight"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: -1 -1; + rel2.offset: 0 0; + image { + normal: "sl_bt2_2.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + color: 200 155 0 0; + } + description { state: "enabled" 0.0; + inherit: "default" 0.0; + color: 200 155 0 255; + } + } + part { name: "sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar_clip"; + clip_to: "sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 10 17; + align: 1.0 0.0; + rel1 { + relative: 1.0 0.0; + offset: 0 2; + to_y: "elm.swallow.content"; + to_x: "elm.swallow.content"; + } + rel2 { + relative: 1.0 0.0; + offset: -1 -1; + to_y: "sb_hbar"; + to_x: "elm.swallow.content"; + } + } + } + part { name: "elm.dragable.vbar"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + dragable { + x: 0 0 0; + y: 1 1 0; + confine: "sb_vbar"; + } + description { state: "default" 0.0; + fixed: 1 1; + min: 10 17; + max: 10 99999; + rel1 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_vbar"; + } + rel2 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_vbar"; + } + image { + normal: "bt_sm_base2.png"; + border: 6 6 6 6; + middle: SOLID; + } + } + } + part { name: "sb_vbar_over1"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.vbar"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + } + part { name: "sb_vbar_over2"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.to: "elm.dragable.vbar"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + } + + part { name: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar_clip"; + clip_to: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 17 10; + align: 0.0 1.0; + rel1 { + relative: 0.0 1.0; + offset: 2 0; + to_x: "elm.swallow.content"; + to_y: "elm.swallow.content"; + } + rel2 { + relative: 0.0 1.0; + offset: -1 -1; + to_x: "sb_vbar"; + to_y: "elm.swallow.content"; + } + } + } + part { name: "elm.dragable.hbar"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + dragable { + x: 1 1 0; + y: 0 0 0; + confine: "sb_hbar"; + } + description { state: "default" 0.0; + fixed: 1 1; + min: 17 10; + max: 99999 10; + rel1 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_hbar"; + } + rel2 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_hbar"; + } + image { + normal: "bt_sm_base2.png"; + border: 4 4 4 4; + middle: SOLID; + } + } + } + part { name: "sb_hbar_over1"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.hbar"; + image { + normal: "bt_sm_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "sb_hbar_over2"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.to: "elm.dragable.hbar"; + image { + normal: "bt_sm_shine.png"; + border: 4 4 4 0; + } + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "clipper"; + rel2.to: "clipper"; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 128 128 128 128; + } + } + } + programs { + program { name: "load"; + signal: "load"; + source: ""; + script { + set_state(PART:"sb_hbar_clip", "hidden", 0.0); + set_state(PART:"sb_vbar_clip", "hidden", 0.0); + set_int(sbvis_h, 0); + set_int(sbvis_v, 0); + set_int(sbalways_v, 0); + set_int(sbalways_h, 0); + set_int(sbvis_timer, 0); + } + } + + program { name: "vbar_show"; + signal: "elm,action,show,vbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_hide"; + signal: "elm,action,hide,vbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_show_always"; + signal: "elm,action,show_always,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + set_int(sbalways_v, 1); + emit("do-show-vbar", ""); + set_int(sbvis_v, 1); + } + } + } + program { name: "vbar_show_notalways"; + signal: "elm,action,show_notalways,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_v); + if (v) { + set_int(sbalways_v, 0); + v = get_int(sbvis_v); + if (!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + } + } + program { name: "sb_vbar_show"; + signal: "do-show-vbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "sb_vbar_clip"; + } + program { name: "sb_vbar_hide"; + signal: "do-hide-vbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.5; + target: "sb_vbar_clip"; + } + + program { name: "hbar_show"; + signal: "elm,action,show,hbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_hide"; + signal: "elm,action,hide,hbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_show_always"; + signal: "elm,action,show_always,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + set_int(sbalways_h, 1); + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + } + } + program { name: "hbar_show_notalways"; + signal: "elm,action,show_notalways,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_h); + if (v) { + set_int(sbalways_h, 0); + v = get_int(sbvis_h); + if (!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + } + } + program { name: "sb_hbar_show"; + signal: "do-show-hbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "sb_hbar_clip"; + } + program { name: "sb_hbar_hide"; + signal: "do-hide-hbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.5; + target: "sb_hbar_clip"; + } + + program { name: "scroll"; + signal: "elm,action,scroll"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + emit("do-show-vbar", ""); + set_int(sbvis_v, 1); + } + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + v = get_int(sbvis_timer); + if (v > 0) cancel_timer(v); + v = timer(1.0, "timer0", 0); + set_int(sbvis_timer, v); + } + } + + program { name: "highlight_show"; + signal: "elm,action,focus_highlight,show"; + source: "elm"; + action: STATE_SET "enabled" 0.0; + transition: ACCELERATE 0.3; + target: "focus_highlight"; + target: "conf_over"; + } + program { name: "highlight_hide"; + signal: "elm,action,focus_highlight,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.3; + target: "focus_highlight"; + target: "conf_over"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disabler"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disabler"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/scroller/entry/default"; + + data { + item: "focus_highlight" "on"; + } + + script { + public sbvis_v, sbvis_h, sbalways_v, sbalways_h, sbvis_timer; + public timer0(val) { + new v; + v = get_int(sbvis_v); + if (v) { + v = get_int(sbalways_v); + if (!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + v = get_int(sbvis_h); + if (v) { + v = get_int(sbalways_h); + if (!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + set_int(sbvis_timer, 0); + return 0; + } + } + images { + image: "shelf_inset.png" COMP; + image: "bt_sm_base2.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "sl_bt2_2.png" COMP; + } + parts { + part { name: "bg"; + type: RECT; + description { state: "default" 0.0; + rel1.offset: 2 2; + rel2.offset: -3 -3; + } + } + part { name: "clipper"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + rel1.offset: 2 2; + rel2.offset: -3 -3; + } + } + part { name: "contentclipper"; + type: RECT; + mouse_events: 0; + clip_to: "clipper"; + description { state: "default" 0.0; + rel1.to: "elm.swallow.icon"; + rel1.relative: 1.0 0.0; + rel2.to: "elm.swallow.end"; + rel2.relative: 0.0 1.0; + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + clip_to: "clipper"; + description { state: "default" 0.0; + fixed: 1 1; + rel1 { + to: "bg"; + relative: 0.0 0.0; + offset: 0 0; + } + rel2 { + to: "bg"; + relative: 0.0 1.0; + offset: -1 -1; + } + visible: 0; + } + description { state: "visible" 0.0; + fixed: 1 1; + align: 0.0 1.0; + rel1 { + to: "bg"; + relative: 0.0 0.0; + offset: 0 0; + } + rel2 { + to: "bg"; + relative: 0.0 1.0; + offset: -1 -1; + } + visible: 1; + } + } + part { name: "elm.swallow.end"; + type: SWALLOW; + clip_to: "clipper"; + description { state: "default" 0.0; + fixed: 1 1; + rel1 { + to: "bg"; + relative: 1.0 0.0; + offset: 0 0; + } + rel2 { + to: "bg"; + relative: 1.0 1.0; + offset: -1 -1; + } + visible: 0; + } + description { state: "visible" 0.0; + fixed: 1 1; + align: 1.0 1.0; + rel1 { + to: "bg"; + relative: 1.0 0.0; + offset: 0 0; + } + rel2 { + to: "bg"; + relative: 1.0 1.0; + offset: -1 -1; + } + visible: 1; + } + } + part { name: "elm.swallow.content"; + clip_to: "contentclipper"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -5 -5; + } + } + } + part { name: "conf_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + description { state: "enabled" 0.0; + inherit: "default" 0.0; + color: 200 155 0 255; + } + } + part { name: "focus_highlight"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: -1 -1; + rel2.offset: 0 0; + image { + normal: "sl_bt2_2.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + color: 200 155 0 0; + } + description { state: "enabled" 0.0; + inherit: "default" 0.0; + color: 200 155 0 255; + } + } + part { name: "sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar_clip"; + clip_to: "sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 10 17; + align: 1.0 0.0; + rel1 { + relative: 0.0 0.0; + offset: -2 2; + to_y: "elm.swallow.content"; + to_x: "elm.swallow.end"; + } + rel2 { + relative: 0.0 0.0; + offset: -2 -1; + to_y: "sb_hbar"; + to_x: "elm.swallow.end"; + } + } + } + part { name: "elm.dragable.vbar"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + dragable { + x: 0 0 0; + y: 1 1 0; + confine: "sb_vbar"; + } + description { state: "default" 0.0; + fixed: 1 1; + min: 10 17; + max: 10 99999; + rel1 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_vbar"; + } + rel2 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_vbar"; + } + image { + normal: "bt_sm_base2.png"; + border: 6 6 6 6; + middle: SOLID; + } + } + } + part { name: "sb_vbar_over1"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.vbar"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + } + part { name: "sb_vbar_over2"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.to: "elm.dragable.vbar"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + } + + part { name: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar_clip"; + clip_to: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 17 10; + align: 0.0 1.0; + rel1 { + relative: 0.0 1.0; + offset: 2 0; + to_x: "elm.swallow.content"; + to_y: "elm.swallow.content"; + } + rel2 { + relative: 0.0 1.0; + offset: -1 -1; + to_x: "sb_vbar"; + to_y: "elm.swallow.content"; + } + } + } + part { name: "elm.dragable.hbar"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + dragable { + x: 1 1 0; + y: 0 0 0; + confine: "sb_hbar"; + } + description { state: "default" 0.0; + fixed: 1 1; + min: 17 10; + max: 99999 10; + rel1 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_hbar"; + } + rel2 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_hbar"; + } + image { + normal: "bt_sm_base2.png"; + border: 4 4 4 4; + middle: SOLID; + } + } + } + part { name: "sb_hbar_over1"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.hbar"; + image { + normal: "bt_sm_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "sb_hbar_over2"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.to: "elm.dragable.hbar"; + image { + normal: "bt_sm_shine.png"; + border: 4 4 4 0; + } + } + } + } + programs { + program { name: "load"; + signal: "load"; + source: ""; + script { + set_state(PART:"sb_hbar_clip", "hidden", 0.0); + set_state(PART:"sb_vbar_clip", "hidden", 0.0); + set_int(sbvis_h, 0); + set_int(sbvis_v, 0); + set_int(sbalways_v, 0); + set_int(sbalways_h, 0); + set_int(sbvis_timer, 0); + } + } + program { name: "icon_show"; + signal: "elm,action,show,icon"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.icon"; + } + program { name: "icon_hide"; + signal: "elm,action,hide,icon"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.icon"; + } + program { name: "end_show"; + signal: "elm,action,show,end"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.end"; + } + program { name: "end_hide"; + signal: "elm,action,hide,end"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.end"; + } + program { name: "vbar_show"; + signal: "elm,action,show,vbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_hide"; + signal: "elm,action,hide,vbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_show_always"; + signal: "elm,action,show_always,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + set_int(sbalways_v, 1); + emit("do-show-vbar", ""); + set_int(sbvis_v, 1); + } + } + } + program { name: "vbar_show_notalways"; + signal: "elm,action,show_notalways,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_v); + if (v) { + set_int(sbalways_v, 0); + v = get_int(sbvis_v); + if (!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + } + } + program { name: "sb_vbar_show"; + signal: "do-show-vbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "sb_vbar_clip"; + } + program { name: "sb_vbar_hide"; + signal: "do-hide-vbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.5; + target: "sb_vbar_clip"; + } + + program { name: "hbar_show"; + signal: "elm,action,show,hbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_hide"; + signal: "elm,action,hide,hbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_show_always"; + signal: "elm,action,show_always,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + set_int(sbalways_h, 1); + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + } + } + program { name: "hbar_show_notalways"; + signal: "elm,action,show_notalways,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_h); + if (v) { + set_int(sbalways_h, 0); + v = get_int(sbvis_h); + if (!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + } + } + program { name: "sb_hbar_show"; + signal: "do-show-hbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "sb_hbar_clip"; + } + program { name: "sb_hbar_hide"; + signal: "do-hide-hbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.5; + target: "sb_hbar_clip"; + } + + program { name: "scroll"; + signal: "elm,action,scroll"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + emit("do-show-vbar", ""); + set_int(sbvis_v, 1); + } + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + v = get_int(sbvis_timer); + if (v > 0) cancel_timer(v); + v = timer(1.0, "timer0", 0); + set_int(sbvis_timer, v); + } + } + + program { name: "highlight_show"; + signal: "elm,action,focus_highlight,show"; + source: "elm"; + action: STATE_SET "enabled" 0.0; + transition: ACCELERATE 0.3; + target: "focus_highlight"; + target: "conf_over"; + } + program { name: "highlight_hide"; + signal: "elm,action,focus_highlight,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.3; + target: "focus_highlight"; + target: "conf_over"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// +#define TEXT_SLIDE_DURATION 10 + + group { name: "elm/label/base/default"; + data.item: "default_font_size" "10"; + data.item: "min_font_size" "6"; + data.item: "max_font_size" "60"; + styles { + style { name: "textblock_style"; + base: "font=Sans font_size=10 color=#000 wrap=word text_class=label"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "hilight" "+ font=Sans:style=Bold"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "tab" "\t"; + } + } + parts { + part { name: "label.swallow.background"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 1; + } + } + part { name: "label.text.clip"; + type: RECT; + description { state: "default" 0.0; + rel1 { relative: 0 0; to: "label.swallow.background"; } + rel2 { relative: 1 1; to: "label.swallow.background"; } + } + } + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + clip_to: "label.text.clip"; + description { state: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + text { + style: "textblock_style"; + min: 1 1; + } + } + } + } + } + + group { name: "elm/label/base_wrap/default"; + data.item: "default_font_size" "10"; + data.item: "min_font_size" "6"; + data.item: "max_font_size" "60"; + parts { + part { name: "label.swallow.background"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 1; + rel1 { relative: 0 0; to: "elm.text"; } + rel2 { relative: 1 1; to: "elm.text"; } + } + } + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + text { + style: "textblock_style"; + min: 0 1; + } + } + } + } + } + + group { name: "elm/label/base_wrap_ellipsis/default"; + data.item: "default_font_size" "10"; + data.item: "min_font_size" "6"; + data.item: "max_font_size" "60"; + parts { + part { name: "label.swallow.background"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 1; + rel1 { relative: 0 0; to: "elm.text"; } + rel2 { relative: 1 1; to: "elm.text"; } + } + } + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + multiline: 1; + description { state: "default" 0.0; + fixed: 0 1; + text { + style: "textblock_style"; + min: 0 1; + } + } + } + } + } + + group { name: "elm/label/base/marker"; + data.item: "default_font_size" "10"; + data.item: "min_font_size" "6"; + data.item: "max_font_size" "60"; + styles { + style { name: "textblock_style2"; + base: "font=Sans:style=Bold font_size=10 align=center color=#fff wrap=word text_class=label"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "hilight" "+ color=#ffff"; + tag: "b" "+ color=#ffff"; + tag: "tab" "\t"; + } + } + parts { + part { name: "label.swallow.background"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 1; + rel1 { relative: 0 0; to: "elm.text"; } + rel2 { relative: 1 1; to: "elm.text"; } + } + } + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + text { + style: "textblock_style2"; + min: 1 1; + } + } + } + } + } + + group { name: "elm/label/base_wrap/marker"; + data.item: "default_font_size" "10"; + data.item: "min_font_size" "6"; + data.item: "max_font_size" "60"; + parts { + part { name: "label.swallow.background"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 1; + rel1 { relative: 0 0; to: "elm.text"; } + rel2 { relative: 1 1; to: "elm.text"; } + } + } + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + text { + style: "textblock_style2"; + min: 0 1; + } + } + } + } + } + + group { name: "elm/label/base/slide_long"; + data.item: "default_font_size" "10"; + data.item: "min_font_size" "6"; + data.item: "max_font_size" "60"; + + script { + public g_duration, g_stopslide, g_timer_id, g_anim_id; + + public message(Msg_Type:type, id, ...) { + if ((type == MSG_FLOAT_SET) && (id == 0)) { + new Float:duration; + duration = getarg(2); + set_float(g_duration, duration); + } + } + public slide_to_end_anim(val, Float:pos) { + new stopflag; + new id; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + set_tween_state(PART:"elm.text", pos, "slide_begin", 0.0, "slide_end", 0.0); + if (pos >= 1.0) { + id = timer(0.5, "slide_to_begin", 1); + set_int(g_timer_id, id); + } + } + public slide_to_end() { + new stopflag; + new id; + new Float:duration; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + duration = get_float(g_duration); + id = anim(duration, "slide_to_end_anim", 1); + set_int(g_anim_id, id); + } + public slide_to_begin() { + new stopflag; + new id; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + set_state(PART:"elm.text", "slide_begin", 0.0); + id = timer(0.5, "slide_to_end", 1); + set_int(g_timer_id, id); + } + public start_slide() { + set_int(g_stopslide, 0); + set_state(PART:"elm.text", "slide_begin", 0.0); + slide_to_end(); + } + public stop_slide() { + new id; + set_int(g_stopslide, 1); + id = get_int(g_anim_id); + cancel_anim(id); + id = get_int(g_timer_id); + cancel_timer(id); + set_state(PART:"elm.text", "default", 0.0); + } + } + + parts { + part { name: "label.swallow.background"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 1; + } + } + part { name: "label.text.clip"; + type: RECT; + description { state: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { relative: 0 0; to: "label.swallow.background"; } + rel2 { relative: 1 1; to: "label.swallow.background"; } + } + } + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + clip_to: "label.text.clip"; + description { state: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + align: 0.0 0.0; + text { + style: "textblock_style"; + min: 1 1; + } + } + description { state: "slide_end" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 0.0 1.0; + align: 1.0 0.0; + } + description { state: "slide_begin" 0.0; + inherit: "default" 0.0; + rel1.relative: 1.0 0.0; + rel2.relative: 1.0 1.0; + align: 0.0 0.0; + } + } + } + programs { + program { name: "start_slide"; + source: "elm"; + signal: "elm,state,slide,start"; + script + { + start_slide(); + } + } + program { name: "stop_slide"; + source: "elm"; + signal: "elm,state,slide,stop"; + script + { + stop_slide(); + } + } + } + } + + + group { name: "elm/label/base/slide_short"; + data.item: "default_font_size" "10"; + data.item: "min_font_size" "6"; + data.item: "max_font_size" "60"; + + script { + public g_duration, g_stopslide, g_timer_id, g_anim_id; + + public message(Msg_Type:type, id, ...) { + if ((type == MSG_FLOAT_SET) && (id == 0)) { + new Float:duration; + duration = getarg(2); + set_float(g_duration, duration); + } + } + public slide_to_end_anim(val, Float:pos) { + new stopflag; + new id; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + set_tween_state(PART:"elm.text", pos, "slide_begin", 0.0, "slide_end", 0.0); + if (pos >= 1.0) { + id = timer(0.5, "slide_to_begin", 1); + set_int(g_timer_id, id); + } + } + public slide_to_end() { + new stopflag; + new id; + new Float:duration; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + duration = get_float(g_duration); + id = anim(duration, "slide_to_end_anim", 1); + set_int(g_anim_id, id); + } + public slide_to_begin() { + new stopflag; + new id; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + set_state(PART:"elm.text", "slide_begin", 0.0); + id = timer(0.5, "slide_to_end", 1); + set_int(g_timer_id, id); + } + public start_slide() { + set_int(g_stopslide, 0); + set_state(PART:"elm.text", "slide_begin", 0.0); + slide_to_end(); + } + public stop_slide() { + new id; + set_int(g_stopslide, 1); + id = get_int(g_anim_id); + cancel_anim(id); + id = get_int(g_timer_id); + cancel_timer(id); + set_state(PART:"elm.text", "default", 0.0); + } + } + + parts { + part { name: "label.swallow.background"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 1; + } + } + part { name: "label.text.clip"; + type: RECT; + description { state: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { relative: 0 0; to: "label.swallow.background"; } + rel2 { relative: 1 1; to: "label.swallow.background"; } + } + } + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + clip_to: "label.text.clip"; + description { state: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + align: 0.0 0.0; + text { + style: "textblock_style"; + min: 1 1; + } + } + description { state: "slide_end" 0.0; + inherit: "default" 0.0; + rel1.relative: 1.0 0.0; + rel2.relative: 1.0 1.0; + align: 1.0 0.0; + } + description { state: "slide_begin" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 0.0 1.0; + align: 0.0 0.0; + } + } + } + programs { + program { name: "start_slide"; + source: "elm"; + signal: "elm,state,slide,start"; + script + { + start_slide(); + } + } + program { name: "stop_slide"; + source: "elm"; + signal: "elm,state,slide,stop"; + script + { + stop_slide(); + } + } + } + } + + group { name: "elm/label/base/slide_bounce"; + data.item: "default_font_size" "10"; + data.item: "min_font_size" "6"; + data.item: "max_font_size" "60"; + + script { + public g_duration, g_stopslide, g_timer_id, g_anim_id; + + public message(Msg_Type:type, id, ...) { + if ((type == MSG_FLOAT_SET) && (id == 0)) { + new Float:duration; + duration = getarg(2); + set_float(g_duration, duration); + } + } + public slide_to_end_anim(val, Float:pos) { + new stopflag; + new id; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + set_tween_state(PART:"elm.text", pos, "slide_begin", 0.0, "slide_end", 0.0); + if (pos >= 1.0) { + id = timer(0.5, "slide_to_begin", 1); + set_int(g_timer_id, id); + } + } + public slide_to_end() { + new stopflag; + new id; + new Float:duration; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + duration = get_float(g_duration); + id = anim(duration, "slide_to_end_anim", 1); + set_int(g_anim_id, id); + } + public slide_to_begin_anim(val, Float:pos) { + new stopflag; + new id; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + set_tween_state(PART:"elm.text", pos, "slide_end", 0.0, "slide_begin", 0.0); + if (pos >= 1.0) { + id = timer(0.5, "slide_to_end", 1); + set_int(g_timer_id, id); + } + } + public slide_to_begin() { + new stopflag; + new id; + new Float:duration; + stopflag = get_int(g_stopslide); + if (stopflag == 1) return; + duration = get_float(g_duration); + id = anim(duration, "slide_to_begin_anim", 1); + set_int(g_anim_id, id); + } + public start_slide() { + set_int(g_stopslide, 0); + set_state(PART:"elm.text", "slide_begin", 0.0); + slide_to_end(); + } + public stop_slide() { + new id; + set_int(g_stopslide, 1); + id = get_int(g_anim_id); + cancel_anim(id); + id = get_int(g_timer_id); + cancel_timer(id); + set_state(PART:"elm.text", "default", 0.0); + } + } + + parts { + part { name: "label.swallow.background"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 1; + } + } + part { name: "label.text.clip"; + type: RECT; + description { state: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { relative: 0 0; to: "label.swallow.background"; } + rel2 { relative: 1 1; to: "label.swallow.background"; } + } + } + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + clip_to: "label.text.clip"; + description { state: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + align: 0.0 0.0; + text { + style: "textblock_style"; + min: 1 1; + } + } + description { state: "slide_end" 0.0; + inherit: "default" 0.0; + rel1.relative: 1.0 0.0; + rel2.relative: 1.0 1.0; + align: 1.0 0.0; + } + description { state: "slide_begin" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 0.0 1.0; + align: 0.0 0.0; + } + } + } + programs { + program { name: "start_slide"; + source: "elm"; + signal: "elm,state,slide,start"; + script + { + start_slide(); + } + } + program { name: "stop_slide"; + source: "elm"; + signal: "elm,state,slide,stop"; + script + { + stop_slide(); + } + } + } + } + + +/////////////////////////////////////////////////////////////////////////////// + + group { name: "elm/button/base/default"; + images { + image: "bt_base1.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "button_image"; + mouse_events: 1; + description { state: "default" 0.0; + min: 15 15; + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + visible: 0; + align: 0.0 0.5; + rel1.offset: 4 4; + rel2.offset: 3 -5; + rel2.relative: 0.0 1.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + fixed: 1 0; + visible: 1; + aspect: 1.0 1.0; +// aspect_preference: VERTICAL; + rel2.offset: 4 -5; + } + description { state: "icononly" 0.0; + inherit: "default" 0.0; + fixed: 0 0; + visible: 1; + align: 0.5 0.5; +// aspect: 1.0 1.0; + rel2.offset: -5 -5; + rel2.relative: 1.0 1.0; +// aspect_preference: VERTICAL; + } + } + part { + name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: 0 4; + rel2.offset: -5 -5; + color: 224 224 224 255; + color3: 0 0 0 64; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.5; + text_class: "button"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { + name: "button_click"; + signal: "mouse,down,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,press" ""; + after: "button_click_anim"; + } + program { + name: "button_click_anim"; + action: STATE_SET "clicked" 0.0; + target: "button_image"; + } + program { + name: "button_unclick"; + signal: "mouse,up,1"; + source: "over3"; + action: SIGNAL_EMIT "elm,action,unpress" ""; + after: "button_unclick_anim"; + } + program { + name: "button_pressed_anim"; + signal: "elm,anim,activate"; + source: "elm"; + action: STATE_SET "clicked" 0.0; + target: "button_image"; + target: "over3"; + after: "button_unpressed_anim"; + } + program { + name: "button_unpressed_anim"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "button_image"; + target: "over3"; + } + program { + name: "button_unclick_anim"; + action: STATE_SET "default" 0.0; + target: "button_image"; + } + program { + name: "button_click2"; + signal: "mouse,down,1"; + source: "over3"; + action: STATE_SET "clicked" 0.0; + target: "over3"; + } + program { + name: "button_unclick2"; + signal: "mouse,up,1"; + source: "over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "over3"; + } + program { + name: "button_unclick3"; + signal: "mouse,clicked,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "icononly")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + set_state(PART:"elm.text", "visible", 0.0); + } + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "icononly", 0.0); + set_state(PART:"elm.text", "default", 0.0); + } + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + else + set_state(PART:"elm.swallow.content", "icononly", 0.0); + } + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "button_image"; + target: "over1"; + target: "over2"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "button_image"; + target: "over1"; + target: "over2"; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.text", "visible", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + } + } + } + } + + group { name: "elm/button/base/hoversel_vertical/default"; + alias: "elm/button/base/hoversel_vertical/entry"; + alias: "elm/button/base/hoversel_horizontal/default"; + alias: "elm/button/base/hoversel_horizontal/entry"; + images { + image: "bt_base1.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "updown.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "button_image"; + mouse_events: 1; + description { state: "default" 0.0; + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "arrow"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "updown.png"; + aspect: 0.6666666666 0.6666666666; + aspect_preference: VERTICAL; + rel1.offset: 6 7; + rel2.offset: 6 -7; + rel2.relative: 0.0 1.0; + align: 0.0 0.5; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + visible: 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + offset: 2 4; + relative: 1.0 0.0; + } + rel2 { + to_x: "arrow"; + offset: 1 -5; + relative: 1.0 1.0; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + fixed: 0 0; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel2.offset: 2 -5; + } + description { state: "icononly" 0.0; + inherit: "default" 0.0; + fixed: 0 0; + visible: 1; + align: 0.5 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "button_image"; + offset: -5 -5; + relative: 1.0 1.0; + } + aspect_preference: VERTICAL; + } + } + part { + name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: 0 4; + rel2.offset: -5 -5; + color: 224 224 224 255; + color3: 0 0 0 64; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.5; + text_class: "button"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { + name: "button_click"; + signal: "mouse,down,1"; + source: "over2"; + action: STATE_SET "clicked" 0.0; + target: "button_image"; + } + program { + name: "button_unclick"; + signal: "mouse,up,1"; + source: "over2"; + action: STATE_SET "default" 0.0; + target: "button_image"; + } + program { + name: "button_click2"; + signal: "mouse,down,1"; + source: "over3"; + action: STATE_SET "clicked" 0.0; + target: "over3"; + } + program { + name: "button_unclick2"; + signal: "mouse,up,1"; + source: "over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "over3"; + } + program { + name: "button_unclick3"; + signal: "mouse,up,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "icononly")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + set_state(PART:"elm.text", "visible", 0.0); + } + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "icononly", 0.0); + set_state(PART:"elm.text", "default", 0.0); + } + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + else + set_state(PART:"elm.swallow.content", "icononly", 0.0); + } + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "button_image"; + target: "over1"; + target: "over2"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "button_image"; + target: "over1"; + target: "over2"; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.text", "visible", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + } + } + } + } + + group { name: "elm/button/base/hoversel_vertical_entry/default"; + alias: "elm/button/base/hoversel_vertical_entry/entry"; + alias: "elm/button/base/hoversel_horizontal_entry/default"; + alias: "elm/button/base/hoversel_horizontal_entry/entry"; + images { + image: "hoversel_entry_bg.png" COMP; + } + parts { + part { name: "button_image"; + mouse_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image.normal: "hoversel_entry_bg.png"; + image.border: 0 0 2 2; + fill.smooth: 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 0; + align: 0.0 0.5; + rel1.offset: 4 4; + rel2.offset: 3 -5; + rel2.relative: 0.0 1.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel2.offset: 4 -5; + } + description { state: "icononly" 0.0; + inherit: "default" 0.0; + visible: 1; + align: 0.5 0.5; + aspect: 1.0 1.0; + rel2.offset: -5 -5; + rel2.relative: 1.0 1.0; + aspect_preference: VERTICAL; + } + } + part { name: "textvis"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + } + description { state: "visible" 0.0; + visible: 1; + } + } + part { + name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + clip_to: "textvis"; + description { state: "default" 0.0; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: 0 4; + rel2.offset: -5 -5; + color: 224 224 224 255; + color3: 0 0 0 64; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.5; + text_class: "button"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + text.min: 1 1; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + text.min: 1 1; + color: 0 0 0 255; + color3: 0 0 0 0; + } + } + part { name: "over2"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + } + programs { + program { + name: "button_click"; + signal: "mouse,down,1"; + source: "over2"; + action: STATE_SET "clicked" 0.0; + target: "button_image"; + target: "elm.text"; + } + program { + name: "button_unclick"; + signal: "mouse,up,1"; + source: "over2"; + action: STATE_SET "default" 0.0; + target: "button_image"; + target: "elm.text"; + } + program { + name: "button_unclick3"; + signal: "mouse,up,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "icononly")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + set_state(PART:"textvis", "visible", 0.0); + set_state(PART:"elm.text", "visible", 0.0); + } + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "icononly", 0.0); + set_state(PART:"textvis", "default", 0.0); + set_state(PART:"elm.text", "default", 0.0); + } + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"textvis", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + else + set_state(PART:"elm.swallow.content", "icononly", 0.0); + } + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + } + } + + group { name: "elm/button/base/anchor"; + images { + image: "bt_base1.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "button_image"; + mouse_events: 1; + description { state: "default" 0.0; + min: 15 15; + color: 255 255 255 0; + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + inherit: "visible" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + inherit: "visible" 0.0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + visible: 0; + align: 0.0 0.5; + rel1.offset: 4 4; + rel2.offset: 3 -5; + rel2.relative: 0.0 1.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + fixed: 1 0; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel2.offset: 4 -5; + } + description { state: "icononly" 0.0; + inherit: "default" 0.0; + fixed: 0 0; + visible: 1; + align: 0.5 0.5; + aspect: 1.0 1.0; + rel2.offset: -5 -5; + rel2.relative: 1.0 1.0; + aspect_preference: VERTICAL; + } + } + part { + name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: 0 4; + rel2.offset: -5 -5; + color: 224 224 224 255; + color3: 0 0 0 64; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.5; + text_class: "button"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + color: 255 255 255 0; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + inherit: "visible" 0.0; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { + name: "button_mouse_in"; + signal: "mouse,in"; + source: "over2"; + action: STATE_SET "visible" 0.0; + target: "button_image"; + target: "over1"; + transition: DECELERATE 0.5; + } + program { + name: "button_mouse_out"; + signal: "mouse,out"; + source: "over2"; + action: STATE_SET "default" 0.0; + target: "button_image"; + target: "over1"; + transition: DECELERATE 0.5; + } + program { + name: "button_unclick"; + signal: "mouse,up,1"; + source: "over2"; + action: STATE_SET "visible" 0.0; + target: "button_image"; + } + program { + name: "button_click2"; + signal: "mouse,down,1"; + source: "over3"; + action: STATE_SET "clicked" 0.0; + target: "over3"; + } + program { + name: "button_unclick2"; + signal: "mouse,up,1"; + source: "over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "over3"; + } + program { + name: "button_unclick3"; + signal: "mouse,up,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "icononly")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + set_state(PART:"elm.text", "visible", 0.0); + } + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "icononly", 0.0); + set_state(PART:"elm.text", "default", 0.0); + } + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + else + set_state(PART:"elm.swallow.content", "icononly", 0.0); + } + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "button_image"; + target: "over1"; + target: "over2"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "button_image"; + target: "over1"; + target: "over2"; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.text", "visible", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/toggle/base/default"; + images { + image: "shelf_inset.png" COMP; + image: "bt_basew.png" COMP; + image: "bt_bases.png" COMP; + image: "bt_hilightw.png" COMP; + image: "tog_base.png" COMP; + image: "tog_dis_base.png" COMP; + } + parts { + part { name: "bg"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.relative: 1.0 0.0; + rel1.offset: -4 3; + rel2.offset: -4 -4; + align: 1.0 0.5; + min: 96 16; + max: 96 16; + aspect: 4.0 4.0; + aspect_preference: VERTICAL; + color: 255 255 255 255; + } + } + part { name: "clipper"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + color: 255 255 255 255; + } + } + part { name: "button"; + type: RECT; + scale: 1; + clip_to: "clipper"; + mouse_events: 1; + dragable { + x: 1 1 0; + y: 0 0 0; + confine: "bg"; + } + description { state: "default" 0.0; + fixed: 1 1; + rel1.to: "bg"; + rel2.to: "bg"; + min: 16 16; + max: 16 16; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + color: 0 0 0 0; + } + } + part { name: "button_events"; + type: RECT; + dragable { + events: "button"; + } + description { state: "default" 0.0; + rel1.to_x: "bg"; + rel1.offset: 0 0; + rel1.relative: 0.0 0.0; + rel2.to_x: "bg"; + rel2.offset: -1 -1; + rel2.relative: 1.0 1.0; + color: 0 0 0 0; + } + } + part { name: "onrect"; + type: RECT; + scale: 1; + clip_to: "clipper"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button"; + rel1.relative: -5.0 0.0; + rel2.to: "button"; + rel2.relative: 0.0 1.0; + color: 0 0 0 0; + } + } + part { name: "offrect"; + type: RECT; + scale: 1; + clip_to: "clipper"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button"; + rel1.relative: 1.0 0.0; + rel2.to: "button"; + rel2.relative: 6.0 1.0; + color: 0 0 0 0; + } + } + part { name: "togbase"; + mouse_events: 0; + clip_to: "clipper"; + description { state: "default" 0.0; + rel1.to: "onrect"; + rel2.to: "offrect"; + image.normal: "tog_base.png"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image.normal: "tog_dis_base.png"; + } + } + part { name: "elm.offtext"; + type: TEXT; + mouse_events: 0; + scale: 1; + clip_to: "clipper"; + description { state: "default" 0.0; + fixed: 1 1; + rel1.to_x: "offrect"; + rel2.to_x: "offrect"; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 1; + align: 0.5 0.5; + text: "OFF"; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + } + } + part { name: "elm.ontext"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + clip_to: "clipper"; + description { state: "default" 0.0; + fixed: 1 1; + rel1.to_x: "onrect"; + rel1.offset: 1 1; + rel2.to_x: "onrect"; + rel2.offset: 0 0; + color: 224 224 224 255; + color3: 0 0 0 64; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 1; + align: 0.5 0.5; + text: "ON"; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + color3: 0 0 0 24; + } + } + part { name: "conf_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: -1 -1; + rel1.to: "bg"; + rel2.offset: 0 0; + rel2.to: "bg"; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "button0"; + mouse_events: 0; + clip_to: "clipper"; + description { state: "default" 0.0; + rel1.to: "button2"; + rel1.offset: -4 -4; + rel2.to: "button2"; + rel2.offset: 3 3; + image { + normal: "bt_bases.png"; + border: 11 11 11 11; + } + image.middle: SOLID; + color: 255 255 255 128; + } + } + part { name: "button2"; + mouse_events: 0; + clip_to: "clipper"; + description { state: "default" 0.0; + rel1.to: "button"; + rel1.offset: -2 -2; + rel2.to: "button"; + rel2.offset: 1 1; + image { + normal: "bt_basew.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + } + part { name: "button3"; + mouse_events: 0; + clip_to: "clipper"; + description { state: "default" 0.0; + rel1.to: "button2"; + rel2.to: "button2"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilightw.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + visible: 0; + align: 0.0 0.5; + rel1.offset: 4 4; + rel2.relative: 0.0 1.0; + rel2.offset: 3 -5; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + aspect: 1.0 1.0; + rel2.offset: 4 -5; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + visible: 1; + aspect: 1.0 1.0; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: 0 4; + rel2.to_x: "bg"; + rel2.relative: 0.0 1.0; + rel2.offset: -5 -5; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.0 0.5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + visible: 1; + text.min: 1 1; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { name: "drag_end"; + signal: "mouse,up,1"; + source: "button"; + script { + new Float:dx, Float:dy; + get_drag(PART:"button", dx, dy); + if (dx > 0.5) + { + set_drag(PART:"button", 1.0, 0.0); + emit("elm,action,toggle,on", ""); + } + else + { + set_drag(PART:"button", 0.0, 0.0); + emit("elm,action,toggle,off", ""); + } + } + } + program { name: "toggle_on"; + signal: "elm,state,toggle,on"; + source: "elm"; + script { + set_drag(PART:"button", 100.0, 0.0); + } + } + program { name: "toggle_off"; + signal: "elm,state,toggle,off"; + source: "elm"; + script { + set_drag(PART:"button", 0.0, 0.0); + } + } + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.content"; + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "togbase"; + target: "elm.offtext"; + target: "elm.ontext"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "disabled_visible", 0.0); + else + set_state(PART:"elm.swallow.content", "disabled", 0.0); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.text", "visible", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + else + set_state(PART:"elm.swallow.content", "default", 0.0); + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/clock/flipdigit/default"; + images { + image: "flip_base.png" COMP; + image: "flip_base_shad.png" COMP; + image: "flip_shad.png" COMP; + image: "flip_0t.png" COMP; + image: "flip_0b.png" COMP; + image: "flip_1t.png" COMP; + image: "flip_1b.png" COMP; + image: "flip_2t.png" COMP; + image: "flip_2b.png" COMP; + image: "flip_3t.png" COMP; + image: "flip_3b.png" COMP; + image: "flip_4t.png" COMP; + image: "flip_4b.png" COMP; + image: "flip_5t.png" COMP; + image: "flip_5b.png" COMP; + image: "flip_6t.png" COMP; + image: "flip_6b.png" COMP; + image: "flip_7t.png" COMP; + image: "flip_7b.png" COMP; + image: "flip_8t.png" COMP; + image: "flip_8b.png" COMP; + image: "flip_9t.png" COMP; + image: "flip_9b.png" COMP; + image: "arrow_up.png" COMP; + image: "arrow_down.png" COMP; + } + script { + public v0_cur, v0_pre, v0_lock, v0_next; + + public animator2(val, Float:pos) { + new st1[11], st2[11], v; + + v = get_int(v0_cur); + snprintf(st1, 10, "%ih", v); + snprintf(st2, 10, "%i", v); + set_tween_state(PART:"bot", pos, st1, 0.0, st2, 0.0); + set_tween_state(PART:"sh", pos, "half", 0.0, "full", 0.0); + if (pos >= 1.0) { + set_state(PART:"sh", "default", 0.0); + set_int(v0_lock, 0); + v = get_int(v0_next); + if (v >= 0) { + set_int(v0_next, -1); + message(MSG_INT, 1, v); + } + } + } + public animator1(val, Float:pos) { + new st1[11], st2[11], v; + + v = get_int(v0_pre); + snprintf(st1, 10, "%i", v); + snprintf(st2, 10, "%ih", v); + set_tween_state(PART:"top", pos, st1, 0.0, st2, 0.0); + set_tween_state(PART:"sh", pos, "default", 0.0, "half", 0.0); + if (pos >= 1.0) anim(0.2, "animator2", val); + } + public message(Msg_Type:type, id, ...) { + if ((type == MSG_INT) && (id == 1)) { + new value, v, buf[11]; + + value = getarg(2); + if (get_int(v0_lock) == 1) { + set_int(v0_next, value); + return; + } + v = get_int(v0_cur); + set_int(v0_pre, v); + set_int(v0_cur, value); + set_int(v0_lock, 1); + snprintf(buf, 10, "%i", get_int(v0_pre)); + set_state(PART:"bot0", buf, 0.0); + snprintf(buf, 10, "%ih", get_int(v0_cur)); + set_state(PART:"bot", buf, 0.0); + snprintf(buf, 10, "%i", get_int(v0_cur)); + set_state(PART:"top0", buf, 0.0); + snprintf(buf, 10, "%i", get_int(v0_pre)); + set_state(PART:"top", buf, 0.0); + set_state(PART:"sh", "default", 0.0); + anim(0.2, "animator1", 1); + } + } + } + parts { + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: -4 -4; + rel1.to: "base"; + rel2.offset: 3 3; + rel2.to: "base"; + image { + normal: "flip_base_shad.png"; + border: 8 8 8 8; + } + } + } + part { name: "base"; + scale: 1; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + // FIXME 48x96 should be the native pixel design, right now + // its 80x160. fix int he artwork later + min: 24 48; + aspect: 0.5 0.5; +// max: 24 48; + image.normal: "flip_base.png"; + } + } + part { name: "b"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to: "base"; + rel1.relative: 0.0 0.5; + rel2.to: "base"; + color: 0 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "t"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to: "base"; + rel2.to: "base"; + rel2.relative: 1.0 0.5; + color: 0 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "bot0"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "b"; + rel2.to: "b"; + image.normal: "flip_0b.png"; + } + description { state: "0" 0.0; + inherit: "default" 0.0; + image.normal: "flip_0b.png"; + } + description { state: "1" 0.0; + inherit: "default" 0.0; + image.normal: "flip_1b.png"; + } + description { state: "2" 0.0; + inherit: "default" 0.0; + image.normal: "flip_2b.png"; + } + description { state: "3" 0.0; + inherit: "default" 0.0; + image.normal: "flip_3b.png"; + } + description { state: "4" 0.0; + inherit: "default" 0.0; + image.normal: "flip_4b.png"; + } + description { state: "5" 0.0; + inherit: "default" 0.0; + image.normal: "flip_5b.png"; + } + description { state: "6" 0.0; + inherit: "default" 0.0; + image.normal: "flip_6b.png"; + } + description { state: "7" 0.0; + inherit: "default" 0.0; + image.normal: "flip_7b.png"; + } + description { state: "8" 0.0; + inherit: "default" 0.0; + image.normal: "flip_8b.png"; + } + description { state: "9" 0.0; + inherit: "default" 0.0; + image.normal: "flip_9b.png"; + } + } + part { name: "sh"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "b"; + rel2.to: "b"; + rel2.relative: 1.0 0.0; + image.normal: "flip_shad.png"; + } + description { state: "half" 0.0; + inherit: "default" 0.0; + rel2.relative: 1.0 0.5; + } + description { state: "full" 0.0; + inherit: "default" 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "bot"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 1; + rel1.to: "b"; + rel2.to: "b"; + image.normal: "flip_0b.png"; + } + description { state: "0" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_0b.png"; + } + description { state: "0h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_0b.png"; + } + description { state: "1" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_1b.png"; + } + description { state: "1h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_1b.png"; + } + description { state: "2" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_2b.png"; + } + description { state: "2h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_2b.png"; + } + description { state: "3" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_3b.png"; + } + description { state: "3h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_3b.png"; + } + description { state: "4" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_4b.png"; + } + description { state: "4h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_4b.png"; + } + description { state: "5" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_5b.png"; + } + description { state: "5h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_5b.png"; + } + description { state: "6" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_6b.png"; + } + description { state: "6h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_6b.png"; + } + description { state: "7" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_7b.png"; + } + description { state: "7h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_7b.png"; + } + description { state: "8" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_8b.png"; + } + description { state: "8h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_8b.png"; + } + description { state: "9" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_9b.png"; + } + description { state: "9h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_9b.png"; + } + } + part { name: "top0"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "t"; + rel2.to: "t"; + image.normal: "flip_0t.png"; + } + description { state: "0" 0.0; + inherit: "default" 0.0; + image.normal: "flip_0t.png"; + } + description { state: "1" 0.0; + inherit: "default" 0.0; + image.normal: "flip_1t.png"; + } + description { state: "2" 0.0; + inherit: "default" 0.0; + image.normal: "flip_2t.png"; + } + description { state: "3" 0.0; + inherit: "default" 0.0; + image.normal: "flip_3t.png"; + } + description { state: "4" 0.0; + inherit: "default" 0.0; + image.normal: "flip_4t.png"; + } + description { state: "5" 0.0; + inherit: "default" 0.0; + image.normal: "flip_5t.png"; + } + description { state: "6" 0.0; + inherit: "default" 0.0; + image.normal: "flip_6t.png"; + } + description { state: "7" 0.0; + inherit: "default" 0.0; + image.normal: "flip_7t.png"; + } + description { state: "8" 0.0; + inherit: "default" 0.0; + image.normal: "flip_8t.png"; + } + description { state: "9" 0.0; + inherit: "default" 0.0; + image.normal: "flip_9t.png"; + } + } + part { name: "top"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 1; + rel1.to: "t"; + rel2.to: "t"; + image.normal: "flip_0t.png"; + } + description { state: "0" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_0t.png"; + } + description { state: "0h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_0t.png"; + } + description { state: "1" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_1t.png"; + } + description { state: "1h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_1t.png"; + } + description { state: "2" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_2t.png"; + } + description { state: "2h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_2t.png"; + } + description { state: "3" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_3t.png"; + } + description { state: "3h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_3t.png"; + } + description { state: "4" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_4t.png"; + } + description { state: "4h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_4t.png"; + } + description { state: "5" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_5t.png"; + } + description { state: "5h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_5t.png"; + } + description { state: "6" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_6t.png"; + } + description { state: "6h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_6t.png"; + } + description { state: "7" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_7t.png"; + } + description { state: "7h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_7t.png"; + } + description { state: "8" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_8t.png"; + } + description { state: "8h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_8t.png"; + } + description { state: "9" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_9t.png"; + } + description { state: "9h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_9t.png"; + } + } + part { name: "atop"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 15 15; + max: 15 15; + align: 0.5 0.0; + rel1.to: "t"; + rel2.to: "t"; + image.normal: "arrow_up.png"; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "abot"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 15 15; + max: 15 15; + align: 0.5 1.0; + rel1.to: "b"; + rel2.to: "b"; + image.normal: "arrow_down.png"; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { name: "load"; + signal: "load"; + source: ""; + script { + set_int(v0_cur, 0); + set_int(v0_pre, 0); + set_int(v0_lock, 0); + set_int(v0_next, -1); + } + } + program { name: "edit_on"; + signal: "elm,state,edit,on"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "atop"; + target: "abot"; + target: "t"; + target: "b"; + } + program { name: "edit_off"; + signal: "elm,state,edit,off"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "atop"; + target: "abot"; + target: "t"; + target: "b"; + } + program { name: "up"; + signal: "mouse,down,1"; + source: "t"; + action: SIGNAL_EMIT "elm,action,up,start" ""; + } + program { name: "up,stop"; + signal: "mouse,up,1"; + source: "t"; + action: SIGNAL_EMIT "elm,action,up,stop" ""; + } + program { name: "down"; + signal: "mouse,down,1"; + source: "b"; + action: SIGNAL_EMIT "elm,action,down,start" ""; + } + program { name: "down,stop"; + signal: "mouse,up,1"; + source: "b"; + action: SIGNAL_EMIT "elm,action,down,stop" ""; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/clock/flipampm/default"; + images { + image: "flip_base.png" COMP; + image: "flip_base_shad.png" COMP; + image: "flip_shad.png" COMP; + image: "flip_amt.png" COMP; + image: "flip_amb.png" COMP; + image: "flip_pmt.png" COMP; + image: "flip_pmb.png" COMP; + image: "arrow_up.png" COMP; + image: "arrow_down.png" COMP; + } + script { + public v0_cur, v0_pre, v0_lock, v0_next; + + public animator2(val, Float:pos) { + new st1[11], st2[11], v; + + v = get_int(v0_cur); + snprintf(st1, 10, "%ih", v); + snprintf(st2, 10, "%i", v); + set_tween_state(PART:"bot", pos, st1, 0.0, st2, 0.0); + set_tween_state(PART:"sh", pos, "half", 0.0, "full", 0.0); + if (pos >= 1.0) { + set_state(PART:"sh", "default", 0.0); + set_int(v0_lock, 0); + v = get_int(v0_next); + if (v >= 0) { + set_int(v0_next, -1); + message(MSG_INT, 1, v); + } + } + } + public animator1(val, Float:pos) { + new st1[11], st2[11], v; + + v = get_int(v0_pre); + snprintf(st1, 10, "%i", v); + snprintf(st2, 10, "%ih", v); + set_tween_state(PART:"top", pos, st1, 0.0, st2, 0.0); + set_tween_state(PART:"sh", pos, "default", 0.0, "half", 0.0); + if (pos >= 1.0) anim(0.2, "animator2", val); + } + public message(Msg_Type:type, id, ...) { + if ((type == MSG_INT) && (id == 1)) { + new value, v, buf[11]; + + value = getarg(2); + if (get_int(v0_lock) == 1) { + set_int(v0_next, value); + return; + } + v = get_int(v0_cur); + set_int(v0_pre, v); + set_int(v0_cur, value); + set_int(v0_lock, 1); + snprintf(buf, 10, "%i", get_int(v0_pre)); + set_state(PART:"bot0", buf, 0.0); + snprintf(buf, 10, "%ih", get_int(v0_cur)); + set_state(PART:"bot", buf, 0.0); + snprintf(buf, 10, "%i", get_int(v0_cur)); + set_state(PART:"top0", buf, 0.0); + snprintf(buf, 10, "%i", get_int(v0_pre)); + set_state(PART:"top", buf, 0.0); + set_state(PART:"sh", "default", 0.0); + anim(0.2, "animator1", 1); + } + } + } + parts { + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: -4 -4; + rel1.to: "base"; + rel2.offset: 3 3; + rel2.to: "base"; + image { + normal: "flip_base_shad.png"; + border: 8 8 8 8; + } + } + } + part { name: "base"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + // FIXME 48x96 should be the native pixel design, right now + // its 80x160. fix int he artwork later + aspect: 0.5 0.5; + min: 24 48; +// max: 24 48; + image.normal: "flip_base.png"; + } + } + part { name: "b"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel1.relative: 0.0 0.5; + rel2.to: "base"; + color: 0 0 0 0; + } + } + part { name: "t"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + rel2.relative: 1.0 0.5; + color: 0 0 0 0; + } + } + part { name: "bot0"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "b"; + rel2.to: "b"; + image.normal: "flip_amb.png"; + } + description { state: "0" 0.0; + inherit: "default" 0.0; + image.normal: "flip_amb.png"; + } + description { state: "1" 0.0; + inherit: "default" 0.0; + image.normal: "flip_pmb.png"; + } + } + part { name: "sh"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "b"; + rel2.to: "b"; + rel2.relative: 1.0 0.0; + image.normal: "flip_shad.png"; + } + description { state: "half" 0.0; + inherit: "default" 0.0; + rel2.relative: 1.0 0.5; + } + description { state: "full" 0.0; + inherit: "default" 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "bot"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 1; + rel1.to: "b"; + rel2.to: "b"; + image.normal: "flip_amb.png"; + } + description { state: "0" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_amb.png"; + } + description { state: "0h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_amb.png"; + } + description { state: "1" 0.0; + inherit: "default" 0.0; + visible: 1; + rel2.relative: 1.0 1.0; + image.normal: "flip_pmb.png"; + } + description { state: "1h" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + image.normal: "flip_pmb.png"; + } + } + part { name: "top0"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "t"; + rel2.to: "t"; + image.normal: "flip_amt.png"; + } + description { state: "0" 0.0; + inherit: "default" 0.0; + image.normal: "flip_amt.png"; + } + description { state: "1" 0.0; + inherit: "default" 0.0; + image.normal: "flip_pmt.png"; + } + } + part { name: "top"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 1; + rel1.to: "t"; + rel2.to: "t"; + image.normal: "flip_amt.png"; + } + description { state: "0" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_amt.png"; + } + description { state: "0h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_amt.png"; + } + description { state: "1" 0.0; + inherit: "default" 0.0; + visible: 1; + rel1.relative: 0.0 0.0; + image.normal: "flip_pmt.png"; + } + description { state: "1h" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + image.normal: "flip_pmt.png"; + } + } + part { name: "atop"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 15 15; + max: 15 15; + align: 0.5 0.0; + rel1.to: "t"; + rel2.to: "t"; + image.normal: "arrow_up.png"; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "abot"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 15 15; + max: 15 15; + align: 0.5 1.0; + rel1.to: "b"; + rel2.to: "b"; + image.normal: "arrow_down.png"; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { name: "load"; + signal: "load"; + source: ""; + script { + set_int(v0_cur, 0); + set_int(v0_pre, 0); + set_int(v0_lock, 0); + set_int(v0_next, -1); + } + } + program { name: "edit_on"; + signal: "elm,state,edit,on"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "atop"; + target: "abot"; + } +/* + program { name: "edit_off"; + signal: "elm,state,edit,off"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "atop"; + target: "abot"; + } + */ + program { name: "up"; + signal: "mouse,down,1"; + source: "t"; + action: SIGNAL_EMIT "elm,action,up,start" ""; + } + program { name: "up,stop"; + signal: "mouse,up,1"; + source: "t"; + action: SIGNAL_EMIT "elm,action,up,stop" ""; + } + program { name: "down"; + signal: "mouse,down,1"; + source: "b"; + action: SIGNAL_EMIT "elm,action,down,start" ""; + } + program { name: "down,stop"; + signal: "mouse,up,1"; + source: "b"; + action: SIGNAL_EMIT "elm,action,down,stop" ""; + } + } + } + + /////////////////////////////////////////////////////////////////////////////// + group { name: "elm/menu/item/default"; + images { + image: "bt_base1.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + script { + public menu_text_visible; //0:hide (default), 1:visible + public menu_disable; //0:enable, 1:disable + } + parts { + part { name: "item_image"; + mouse_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + inherit: "visible" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + } + } + part { name: "item_image_disabled"; + mouse_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + visible: 1; + align: 0.0 0.5; + rel1.offset: 4 4; + rel2.offset: 3 -5; + rel2.relative: 0.0 1.0; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel2.offset: 4 -5; + } + } + part { + name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: 5 7; + rel2.offset: -10 -8; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 1 1; + align: 0.0 0.5; + text_class: "menu_item"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + inherit: "visible" 0.0; + color: 254 254 254 255; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + inherit: "visible" 0.0; + color: 0 0 0 128; + } + } + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + color: 255 255 255 0; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + } + } + part { name: "over_disabled"; + mouse_events: 0; + description { state: "default" 0.0; + color: 255 255 255 0; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + // + program { + name: "item_mouse_in"; + signal: "mouse,in"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,activate" ""; + after: "item_mouse_in_2"; + after: "item_mouse_in_3"; + } + program { + name: "item_mouse_in_2"; + transition: DECELERATE 0.5; + script { + new v, d; + v = get_int(menu_text_visible); + d = get_int(menu_disable); + + if (v==1 && d==0) + run_program(PROGRAM:"selected_text"); + } + } + program { + name: "item_mouse_in_3"; + action : STATE_SET "visible" 0.0; + target: "item_image"; + target: "over1"; + transition: DECELERATE 0.5; + } + program { + name: "selected_text"; + action: STATE_SET "selected" 0.0; + target: "elm.text"; + transition: DECELERATE 0.5; + } + // + + // + program { + name: "item_mouse_out"; + signal: "mouse,out"; + source: "over2"; + after: "item_mouse_out_2"; + after: "item_mouse_out_3"; + } + program { + name: "item_mouse_out_2"; + transition: DECELERATE 0.5; + script { + new v, d; + v = get_int(menu_text_visible); + d = get_int(menu_disable); + + if (v==1 && d==0) + run_program(PROGRAM:"visible_text"); + } + } + program { + name: "item_mouse_out_3"; + action: STATE_SET "default" 0.0; + target: "item_image"; + target: "over1"; + transition: DECELERATE 0.5; + } + program { + name: "visible_text"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + transition: DECELERATE 0.5; + } + // + + program { + name: "item_unclick"; + signal: "mouse,up,1"; + source: "over2"; + action: STATE_SET "visible" 0.0; + target: "item_image"; + } + program { + name: "item_click2"; + signal: "mouse,down,1"; + source: "over3"; + action: STATE_SET "clicked" 0.0; + target: "over3"; + } + program { + name: "item_unclick2"; + signal: "mouse,up,1"; + source: "over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "over3"; + } + program { + name: "item_unclick3"; + signal: "mouse,up,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + script { + set_int(menu_text_visible, 1); + set_state(PART:"elm.text", "visible", 0.0); + } + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + script { + set_int(menu_text_visible, 0); + set_state(PART:"elm.text", "default", 0.0); + } + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "item_image"; + target: "item_image_disabled"; + target: "over1"; + target: "over2"; + target: "over_disabled"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new v; + v = get_int(menu_text_visible); + if (v==1) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else if (v==0) + set_state(PART:"elm.text", "disabled", 0.0); + set_int(menu_disable, 1); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "item_image"; + target: "item_image_disabled"; + target: "over1"; + target: "over2"; + target: "over_disabled"; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new v; + v = get_int(menu_text_visible); + if (v==1) + set_state(PART:"elm.text", "visible", 0.0); + else if (v==0) + set_state(PART:"elm.text", "default", 0.0); + set_int(menu_disable, 0); + } + } + } + } + + group { name: "elm/menu/item_with_submenu/default"; + images { + image: "bt_base1.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + image: "arrow_right.png" COMP; + } + script { + public menu_text_visible; //0:hide (default), 1:visible + public menu_disable; //0:enable, 1:disable + } + parts { + part { name: "item_image"; + mouse_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + inherit: "visible" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + } + } + part { name: "item_image_disabled"; + mouse_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "arrow"; + mouse_events: 1; + description { state: "default" 0.0; + color: 255 255 255 255; + align: 1.0 0.5; + aspect: 1 1; + aspect_preference: BOTH; + image { + normal: "arrow_right.png"; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + visible: 1; + align: 0.0 0.5; + rel1.offset: 4 4; + rel2.offset: 3 -5; + rel2.relative: 0.0 1.0; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel2.offset: 4 -5; + } + } + part { + name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: 5 7; + rel2.offset: -10 -8; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 1 1; + align: 0.0 0.5; + text_class: "menu_item"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + inherit: "visible" 0.0; + color: 254 254 254 255; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + inherit: "visible" 0.0; + color: 0 0 0 128; + } + } + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + color: 255 255 255 0; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + } + } + part { name: "over_disabled"; + mouse_events: 0; + description { state: "default" 0.0; + color: 255 255 255 0; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + // + program { + name: "item_mouse_in"; + signal: "mouse,in"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,activate" ""; + after: "item_mouse_in_2"; + after: "item_mouse_in_3"; + } + program { + name: "item_mouse_in_2"; + transition: DECELERATE 0.5; + script { + new v, d; + v = get_int(menu_text_visible); + d = get_int(menu_disable); + + if (v==1 && d==0) + run_program(PROGRAM:"selected_text"); + } + } + program { + name: "item_mouse_in_3"; + action : STATE_SET "visible" 0.0; + target: "item_image"; + target: "over1"; + transition: DECELERATE 0.5; + } + program { + name: "selected_text"; + action: STATE_SET "selected" 0.0; + target: "elm.text"; + transition: DECELERATE 0.5; + } + // + + // + program { + name: "item_mouse_out"; + signal: "mouse,out"; + source: "over2"; + after: "item_mouse_out_2"; + after: "item_mouse_out_3"; + } + program { + name: "item_mouse_out_2"; + transition: DECELERATE 0.5; + script { + new v, d; + v = get_int(menu_text_visible); + d = get_int(menu_disable); + + if (v==1 && d==0) + run_program(PROGRAM:"visible_text"); + } + } + program { + name: "item_mouse_out_3"; + action: STATE_SET "default" 0.0; + target: "item_image"; + target: "over1"; + transition: DECELERATE 0.5; + } + program { + name: "visible_text"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + transition: DECELERATE 0.5; + } + // + + program { + name: "item_unclick"; + signal: "mouse,up,1"; + source: "over2"; + action: STATE_SET "visible" 0.0; + target: "item_image"; + } + program { + name: "item_click2"; + signal: "mouse,down,1"; + source: "over3"; + action: STATE_SET "clicked" 0.0; + target: "over3"; + } + program { + name: "item_unclick2"; + signal: "mouse,up,1"; + source: "over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "over3"; + } + program { + name: "item_unclick3"; + signal: "mouse,up,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { + name: "menu_open"; + signal: "mouse,in"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,open" ""; + } + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + script { + set_int(menu_text_visible, 1); + set_state(PART:"elm.text", "visible", 0.0); + } + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + script { + set_int(menu_text_visible, 0); + set_state(PART:"elm.text", "default", 0.0); + } + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "item_image"; + target: "item_image_disabled"; + target: "over1"; + target: "over2"; + target: "over_disabled"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else if (!strcmp(st, "default")) + set_state(PART:"elm.text", "disabled", 0.0); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "item_image"; + target: "item_image_disabled"; + target: "over1"; + target: "over2"; + target: "over_disabled"; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new v; + v = get_int(menu_text_visible); + if (v==1) + set_state(PART:"elm.text", "visible", 0.0); + else if (v==0) + set_state(PART:"elm.text", "default", 0.0); + set_int(menu_disable, 0); + } + } + } + } + + group { name: "elm/menu/separator/default"; + images { + image: "separator_h.png" COMP; + } + parts { + part { name: "separator"; // separator group + description { state: "default" 0.0; + min: 2 2; + rel1.offset: 4 4; + rel2.offset: -5 -5; + image { + normal: "separator_h.png"; + } + fill { + smooth: 0; + } + } + } + } + } +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/clock/base-all/default"; + parts { + part { name: "d0"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.0000000 0.0; + rel2.relative: 0.1250000 1.0; + } + } + part { name: "d1"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.1250000 0.0; + rel2.relative: 0.2500000 1.0; + } + } + part { name: "c0"; + type: SWALLOW; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.relative: 0.2500000 0.0; + rel2.relative: 0.3125000 1.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + text: ":"; + size: 10; + min: 1 1; + align: 0.5 0.5; + } + } + } + part { name: "d2"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.3125000 0.0; + rel2.relative: 0.4375000 1.0; + } + } + part { name: "d3"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.4375000 0.0; + rel2.relative: 0.5625000 1.0; + } + } + // (if seconds) + part { name: "c1"; + type: SWALLOW; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.relative: 0.5625000 0.0; + rel2.relative: 0.6250000 1.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + text: ":"; + size: 10; + min: 1 1; + align: 0.5 0.5; + } + } + } + // (if seconds) + part { name: "d4"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.6250000 0.0; + rel2.relative: 0.7500000 1.0; + } + } + // (if seconds) + part { name: "d5"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.7500000 0.0; + rel2.relative: 0.8750000 1.0; + } + } + // (if am_pm) + part { name: "ampm"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.8750000 0.0; + rel2.relative: 1.0 1.0; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/clock/base-seconds/default"; + parts { + part { name: "d0"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.000000000 0.0; + rel2.relative: 0.142857143 1.0; + } + } + part { name: "d1"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.142857143 0.0; + rel2.relative: 0.285714286 1.0; + } + } + part { name: "c0"; + type: SWALLOW; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.relative: 0.285714286 0.0; + rel2.relative: 0.357142857 1.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + text: ":"; + size: 10; + min: 1 1; + align: 0.5 0.5; + } + } + } + part { name: "d2"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.357142857 0.0; + rel2.relative: 0.500000000 1.0; + } + } + part { name: "d3"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.500000000 0.0; + rel2.relative: 0.642857143 1.0; + } + } + // (if seconds) + part { name: "c1"; + type: SWALLOW; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.relative: 0.642857143 0.0; + rel2.relative: 0.714285714 1.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + text: ":"; + size: 10; + min: 1 1; + align: 0.5 0.5; + } + } + } + // (if seconds) + part { name: "d4"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.714285714 0.0; + rel2.relative: 0.857142857 1.0; + } + } + // (if seconds) + part { name: "d5"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.857142857 0.0; + rel2.relative: 1.000000000 1.0; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/clock/base-am_pm/default"; + parts { + part { name: "d0"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.000000000 0.0; + rel2.relative: 0.181818182 1.0; + } + } + part { name: "d1"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.181818182 0.0; + rel2.relative: 0.363636364 1.0; + } + } + part { name: "c0"; + type: SWALLOW; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.relative: 0.363636364 0.0; + rel2.relative: 0.454545455 1.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + text: ":"; + size: 10; + min: 1 1; + align: 0.5 0.5; + } + } + } + part { name: "d2"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.454545455 0.0; + rel2.relative: 0.636363636 1.0; + } + } + part { name: "d3"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.636363636 0.0; + rel2.relative: 0.818181818 1.0; + } + } + // (if am_pm) + part { name: "ampm"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.818181818 0.0; + rel2.relative: 1.0 1.0; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/clock/base/default"; + parts { + part { name: "d0"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.000000000 0.0; + rel2.relative: 0.222222222 1.0; + } + } + part { name: "d1"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.222222222 0.0; + rel2.relative: 0.444444444 1.0; + } + } + part { name: "c0"; + type: SWALLOW; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.relative: 0.444444444 0.0; + rel2.relative: 0.555555556 1.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + text: ":"; + size: 10; + min: 1 1; + align: 0.5 0.5; + } + } + } + part { name: "d2"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.555555556 0.0; + rel2.relative: 0.777777778 1.0; + } + } + part { name: "d3"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.777777778 0.0; + rel2.relative: 1.000000000 1.0; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/frame/base/default"; + images { + image: "frame_1.png" COMP; + image: "frame_2.png" COMP; + image: "dia_grad.png" COMP; + } + parts { + part { name: "base0"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "dia_grad.png"; + rel1.to: "over"; + rel2.to: "over"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "base"; + mouse_events: 0; + description { state: "default" 0.0; + rel2.to: "elm.swallow.content"; + rel2.offset: 9 9; + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.0 0.0; + fixed: 0 1; + rel1 { + relative: 0.0 0.0; + offset: 6 6; + } + rel2 { + relative: 1.0 0.0; + offset: -7 6; + } + color: 0 0 0 64; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 1 1; + max: 1 1; + align: 0.0 0.0; + } + } + } + part { name: "over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.to: "elm.swallow.content"; + rel2.offset: 5 5; + image { + normal: "frame_1.png"; + border: 2 2 28 22; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1 { + to_y: "elm.text"; + relative: 0.0 1.0; + offset: 8 2; + } + rel2.offset: -9 -9; + } + } + } + } + + group { name: "elm/frame/base/pad_small"; + parts { + part { name: "b0"; + mouse_events: 0; + type: RECT; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 4 4; + max: 4 4; + align: 0.0 0.0; + } + } + part { name: "b1"; + mouse_events: 0; + type: RECT; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 4 4; + max: 4 4; + align: 1.0 1.0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to: "b0"; + relative: 1.0 1.0; + offset: 0 0; + } + rel2 { + to: "b1"; + relative: 0.0 0.0; + offset: -1 -1; + } + } + } + } + } + + group { name: "elm/frame/base/pad_medium"; + parts { + part { name: "b0"; + mouse_events: 0; + type: RECT; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 8 8; + max: 8 8; + align: 0.0 0.0; + } + } + part { name: "b1"; + mouse_events: 0; + type: RECT; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 8 8; + max: 8 8; + align: 1.0 1.0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to: "b0"; + relative: 1.0 1.0; + offset: 0 0; + } + rel2 { + to: "b1"; + relative: 0.0 0.0; + offset: -1 -1; + } + } + } + } + } + + group { name: "elm/frame/base/pad_large"; + parts { + part { name: "b0"; + mouse_events: 0; + type: RECT; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 16 16; + max: 16 16; + align: 0.0 0.0; + } + } + part { name: "b1"; + mouse_events: 0; + type: RECT; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 16 16; + max: 16 16; + align: 1.0 1.0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to: "b0"; + relative: 1.0 1.0; + offset: 0 0; + } + rel2 { + to: "b1"; + relative: 0.0 0.0; + offset: -1 -1; + } + } + } + } + } + + group { name: "elm/frame/base/pad_huge"; + parts { + part { name: "b0"; + mouse_events: 0; + type: RECT; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 32 32; + max: 32 32; + align: 0.0 0.0; + } + } + part { name: "b1"; + mouse_events: 0; + type: RECT; + scale: 1; + description { state: "default" 0.0; + visible: 0; + min: 32 32; + max: 32 32; + align: 1.0 1.0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to: "b0"; + relative: 1.0 1.0; + offset: 0 0; + } + rel2 { + to: "b1"; + relative: 0.0 0.0; + offset: -1 -1; + } + } + } + } + } + + group { name: "elm/frame/base/outdent_top"; + images { + image: "outdent-top.png" COMP; + } + parts { + part { name: "base0"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "outdent-top.png"; + image.border: 0 0 0 13; + fill.smooth: 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.offset: 2 2; + rel2.offset: -3 -13; + } + } + } + } + + group { name: "elm/frame/base/outdent_bottom"; + images { + image: "outdent-bottom.png" COMP; + } + parts { + part { name: "base0"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "outdent-bottom.png"; + image.border: 0 0 13 0; + fill.smooth: 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.offset: 2 12; + rel2.offset: -3 -3; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/label/base/tooltip"; + styles { + style { name: "tooltip_style"; + base: "font=Sans font_size=8 color=#666 wrap=word"; + tag: "br" "\n"; + tag: "hilight" "+ font=Sans:style=Bold"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "tab" "\t"; + } + } + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + text { + style: "tooltip_style"; + min: 1 1; + } + } + } + } + } + + group { name: "elm/tooltip/base/default"; + min: 30 30; + data { + item: "pad_x" "20"; + item: "pad_y" "20"; + item: "pad_border_x" "10"; + item: "pad_border_y" "10"; + item: "hide_timeout" "0.35"; /**< tooltip is hidden after this amount, keep in sync with hide animations */ + } + images { + image: "tooltip-base.png" COMP; + image: "tooltip-corner-top-left-tip.png" COMP; + image: "tooltip-corner-top-right-tip.png" COMP; + image: "tooltip-corner-bottom-left-tip.png" COMP; + image: "tooltip-corner-bottom-right-tip.png" COMP; + image: "tooltip-edge-left-tip.png" COMP; + image: "tooltip-edge-right-tip.png" COMP; + image: "tooltip-edge-bottom-tip.png" COMP; + image: "tooltip-edge-top-tip.png" COMP; + } + script { + hide_corners() { + set_state(PART:"corner-top-left", "default", 0.0); + set_state(PART:"corner-top-right", "default", 0.0); + set_state(PART:"corner-bottom-left", "default", 0.0); + set_state(PART:"corner-bottom-right", "default", 0.0); + } + hide_edges() { + set_state(PART:"clipper-edge-left", "default", 0.0); + set_state(PART:"clipper-edge-right", "default", 0.0); + set_state(PART:"clipper-edge-top", "default", 0.0); + set_state(PART:"clipper-edge-bottom", "default", 0.0); + } + + show_corner_top_left() { + set_state(PART:"corner-top-left", "visible", 0.0); + + set_state(PART:"corner-top-right", "default", 0.0); + set_state(PART:"corner-bottom-left", "default", 0.0); + set_state(PART:"corner-bottom-right", "default", 0.0); + hide_edges(); + } + show_corner_top_right() { + set_state(PART:"corner-top-right", "visible", 0.0); + + set_state(PART:"corner-top-left", "default", 0.0); + set_state(PART:"corner-bottom-left", "default", 0.0); + set_state(PART:"corner-bottom-right", "default", 0.0); + hide_edges(); + } + + show_corner_bottom_left() { + set_state(PART:"corner-bottom-left", "visible", 0.0); + + set_state(PART:"corner-bottom-right", "default", 0.0); + set_state(PART:"corner-top-left", "default", 0.0); + set_state(PART:"corner-top-right", "default", 0.0); + hide_edges(); + } + show_corner_bottom_right() { + set_state(PART:"corner-bottom-right", "visible", 0.0); + + set_state(PART:"corner-bottom-left", "default", 0.0); + set_state(PART:"corner-top-left", "default", 0.0); + set_state(PART:"corner-top-right", "default", 0.0); + hide_edges(); + } + + show_edge_left(Float:val) { + set_state(PART:"clipper-edge-left", "visible", 0.0); + set_drag(PART:"edge-drag-left", 0.0, val); + + set_state(PART:"clipper-edge-right", "default", 0.0); + set_state(PART:"clipper-edge-top", "default", 0.0); + set_state(PART:"clipper-edge-bottom", "default", 0.0); + hide_corners(); + } + show_edge_right(Float:val) { + set_state(PART:"clipper-edge-right", "visible", 0.0); + set_drag(PART:"edge-drag-right", 0.0, val); + + set_state(PART:"clipper-edge-left", "default", 0.0); + set_state(PART:"clipper-edge-top", "default", 0.0); + set_state(PART:"clipper-edge-bottom", "default", 0.0); + hide_corners(); + } + + show_edge_top(Float:val) { + set_state(PART:"clipper-edge-top", "visible", 0.0); + set_drag(PART:"edge-drag-top", val, 0.0); + + set_state(PART:"clipper-edge-bottom", "default", 0.0); + set_state(PART:"clipper-edge-left", "default", 0.0); + set_state(PART:"clipper-edge-right", "default", 0.0); + hide_corners(); + } + show_edge_bottom(Float:val) { + set_state(PART:"clipper-edge-bottom", "visible", 0.0); + set_drag(PART:"edge-drag-bottom", val, 0.0); + + set_state(PART:"clipper-edge-top", "default", 0.0); + set_state(PART:"clipper-edge-left", "default", 0.0); + set_state(PART:"clipper-edge-right", "default", 0.0); + hide_corners(); + } + + public message(Msg_Type:type, id, ...) { + if ((type == MSG_FLOAT_SET) && (id == 1)) { + new Float:x, Float:y; + + x = getfarg(2); + y = getfarg(3); + + if (x < 0.0) + { + if (y < 0.0) show_corner_top_left(); + else if (y > 1.0) show_corner_bottom_left(); + else show_edge_left(y); + } + else if (x > 1.0) + { + if (y < 0.0) show_corner_top_right(); + else if (y > 1.0) show_corner_bottom_right(); + else show_edge_right(y); + } + else + { + if (y < 0.0) show_edge_top(x); + else if (y > 1.0) show_edge_bottom(x); + else + { + hide_corners(); + hide_edges(); + } + } + } + } + } + parts { + part { name: "clipper"; + type: RECT; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "pop"; + mouse_events: 0; + clip_to: "clipper"; + description { state: "default" 0.0; + min: 30 30; + rel1 { + to: "elm.swallow.content"; + offset: -15 -15; + } + rel2 { + to: "elm.swallow.content"; + offset: 14 14; + } + image { + normal: "tooltip-base.png"; + border: 14 14 14 14; + } + image.middle: SOLID; + } + } + +#define TT_CORNER(name_, rx, ry, ax, ay, ox, oy) \ + part { name: "corner-"name_; \ + type: IMAGE; \ + mouse_events: 0; \ + clip_to: "clipper"; \ + description { state: "default" 0.0; \ + color: 255 255 255 0; \ + visible: 0; \ + min: 14 14; \ + max: 14 14; \ + align: ax ay; \ + fixed: 1 1; \ + rel1 { \ + relative: rx ry; \ + offset: ox oy; \ + to: "elm.swallow.content"; \ + } \ + rel2 { \ + relative: rx ry; \ + offset: ox oy; \ + to: "elm.swallow.content"; \ + } \ + image.normal: "tooltip-corner-"name_"-tip.png"; \ + } \ + description { state: "visible" 0.0; \ + inherit: "default" 0.0; \ + color: 255 255 255 255; \ + visible: 1; \ + } \ + } + TT_CORNER("top-left", 0, 0, 1, 1, 4, 4); + TT_CORNER("top-right", 1, 0, 0, 1, -5, 4); + TT_CORNER("bottom-left", 0, 1, 1, 0, 4, -5); + TT_CORNER("bottom-right", 1, 1, 0, 0, -5, -5); +#undef TT_CORNER + +#define TT_EDGE_VERT(name_, rx, ax, ox) \ + part { name: "clipper-edge-"name_; \ + type: RECT; \ + clip_to: "clipper"; \ + description { state: "default" 0.0; \ + color: 255 255 255 0; \ + visible: 0; \ + min: 14 14; \ + align: ax 0.5; \ + fixed: 1 1; \ + rel1 { \ + relative: rx 0.0; \ + offset: ox 0; \ + to: "elm.swallow.content"; \ + } \ + rel2 { \ + relative: rx 1.0; \ + offset: ox 0; \ + to: "elm.swallow.content"; \ + } \ + } \ + description { state: "visible" 0.0; \ + inherit: "default" 0.0; \ + color: 255 255 255 255; \ + visible: 1; \ + } \ + } \ + part { name: "edge-area-"name_; \ + type: RECT; \ + mouse_events: 0; \ + clip_to: "clipper-edge-"name_; \ + description { state: "default" 0.0; \ + color: 0 0 0 0; \ + min: 14 14; \ + align: ax 0.5; \ + fixed: 1 1; \ + rel1 { \ + relative: rx 0.0; \ + offset: ox 0; \ + to: "elm.swallow.content"; \ + } \ + rel2 { \ + relative: rx 1.0; \ + offset: ox 0; \ + to: "elm.swallow.content"; \ + } \ + } \ + } \ + part { name: "edge-drag-"name_; \ + type: RECT; \ + mouse_events: 0; \ + clip_to: "clipper-edge-"name_; \ + dragable { \ + x: 0 0 0; \ + y: 1 1 0; \ + confine: "edge-area-"name_; \ + } \ + description { state: "default" 0.0; \ + color: 0 0 0 0; \ + min: 14 14; \ + rel1.to: "edge-area-"name_; \ + rel2.to: "edge-area-"name_; \ + } \ + } \ + part { name: "edge-img-"name_; \ + type: IMAGE; \ + mouse_events: 0; \ + clip_to: "clipper-edge-"name_; \ + description { state: "default" 0.0; \ + min: 14 14; \ + max: 14 14; \ + align: ax 0.5; \ + fixed: 1 1; \ + rel1.to: "edge-drag-"name_; \ + rel2.to: "edge-drag-"name_; \ + image.normal: "tooltip-edge-"name_"-tip.png"; \ + } \ + } + TT_EDGE_VERT("left", 0, 1, -2); + TT_EDGE_VERT("right", 1, 0, 1); +#undef TT_EDGE_VERT + +#define TT_EDGE_HORIZ(name_, ry, ay, oy) \ + part { name: "clipper-edge-"name_; \ + type: RECT; \ + clip_to: "clipper"; \ + description { state: "default" 0.0; \ + color: 255 255 255 0; \ + visible: 0; \ + min: 14 14; \ + align: 0.5 ay; \ + fixed: 1 1; \ + rel1 { \ + relative: 0.0 ry; \ + offset: 0 oy; \ + to: "elm.swallow.content"; \ + } \ + rel2 { \ + relative: 1.0 ry; \ + offset: 0 oy; \ + to: "elm.swallow.content"; \ + } \ + } \ + description { state: "visible" 0.0; \ + inherit: "default" 0.0; \ + color: 255 255 255 255; \ + visible: 1; \ + } \ + } \ + part { name: "edge-area-"name_; \ + type: RECT; \ + mouse_events: 0; \ + clip_to: "clipper-edge-"name_; \ + description { state: "default" 0.0; \ + color: 0 0 0 0; \ + min: 14 14; \ + align: 0.5 ay; \ + fixed: 1 1; \ + rel1 { \ + relative: 0.0 ry; \ + offset: 0 oy; \ + to: "elm.swallow.content"; \ + } \ + rel2 { \ + relative: 1.0 ry; \ + offset: 0 oy; \ + to: "elm.swallow.content"; \ + } \ + } \ + } \ + part { name: "edge-drag-"name_; \ + type: RECT; \ + mouse_events: 0; \ + clip_to: "clipper-edge-"name_; \ + dragable { \ + x: 1 1 0; \ + y: 0 0 0; \ + confine: "edge-area-"name_; \ + } \ + description { state: "default" 0.0; \ + color: 0 0 0 0; \ + min: 14 14; \ + rel1.to: "edge-area-"name_; \ + rel2.to: "edge-area-"name_; \ + } \ + } \ + part { name: "edge-img-"name_; \ + type: IMAGE; \ + mouse_events: 0; \ + clip_to: "clipper-edge-"name_; \ + description { state: "default" 0.0; \ + min: 14 14; \ + max: 14 14; \ + align: 0.5 ay; \ + fixed: 1 1; \ + rel1.to: "edge-drag-"name_; \ + rel2.to: "edge-drag-"name_; \ + image.normal: "tooltip-edge-"name_"-tip.png"; \ + } \ + } + TT_EDGE_HORIZ("top", 0, 1, -2); + TT_EDGE_HORIZ("bottom", 1, 0, 1); +#undef TT_EDGE_HORIZ + + part { name: "clipper_content"; + type: RECT; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clipper_content"; + description { state: "default" 0.0; } + } + programs { + program { + name: "show0"; + signal: "elm,action,show"; + source: "elm"; + action: ACTION_STOP; + target: "hide0"; + target: "hide1"; + target: "hide2"; + target: "hide3"; + after: "show1"; + after: "show2"; + } + program { + name: "show1"; + action: STATE_SET "visible" 0.0; + transition: LINEAR 0.15; + target: "clipper"; + } + program { + name: "show2"; + in: 0.1 0.0; + action: STATE_SET "visible" 0.0; + transition: LINEAR 0.15; + target: "clipper_content"; + } + + program { + name: "hide0"; + signal: "elm,action,hide"; + source: "elm"; + action: ACTION_STOP; + target: "show0"; + target: "show1"; + target: "show2"; + after: "hide1"; + after: "hide2"; + after: "hide3"; + } + program { + name: "hide1"; + script { + hide_corners(); + hide_edges(); + } + } + program { + name: "hide2"; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.1; + target: "clipper_content"; + } + program { + name: "hide3"; + in: 0.1 0.0; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.1; + target: "clipper"; + } + } + } + } + group { name: "elm/tooltip/base/transparent"; + parts { + part { name: "elm.swallow.content"; + type: SWALLOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + + /* TODO: replicate diagonal swallow slots to the other hover styles */ + group { name: "elm/hover/base/default"; + images { + image: "shad_circ.png" COMP; + } + parts { + part { name: "elm.swallow.offset"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 0.0 0.0; + } + } + part { name: "elm.swallow.size"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.to: "elm.swallow.offset"; + rel1.relative: 1.0 1.0; + rel2.to: "elm.swallow.offset"; + rel2.relative: 1.0 1.0; + } + } + part { name: "base"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 64; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.size"; + rel1.offset: -32 -32; + rel2.to: "elm.swallow.size"; + rel2.offset: 31 31; + fill.smooth: 0; + } + } + part { name: "box"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.to: "elm.swallow.size"; + rel1.offset: -2 -2; + rel2.to: "elm.swallow.size"; + rel2.offset: 1 1; + } + } + part { name: "elm.swallow.slot.left"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 0.5; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 0.0; + rel1.offset: -1 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 0.0 1.0; + rel2.offset: -1 -1; + } + } + part { name: "elm.swallow.slot.top-left"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 1.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 0.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 0.0 0.0; + rel2.offset: -1 -1; + } + } + part { name: "elm.swallow.slot.top"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.5 1.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 0.0; + rel1.offset: 0 -1; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 0.0; + rel2.offset: -1 -1; + } + } + part { name: "elm.swallow.slot.top-right"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 1.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 1.0 0.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 0.0; + rel2.offset: -1 -1; + } + } + part { name: "elm.swallow.slot.right"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.5; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 1.0 0.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 1.0; + rel2.offset: 0 -1; + } + } + part { name: "elm.swallow.slot.bottom-right"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 1.0 1.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 1.0; + rel2.offset: -1 -1; + } + } + part { name: "elm.swallow.slot.bottom"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.5 0.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 1.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 1.0; + rel2.offset: -1 0; + } + } + part { name: "elm.swallow.slot.bottom-left"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 0.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 1.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 0.0 1.0; + rel2.offset: -1 0; + } + } + part { name: "elm.swallow.slot.middle"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "elm.swallow.size"; + rel2.to: "elm.swallow.size"; + } + } + } + programs { + program { name: "end"; + signal: "mouse,up,1"; + source: "base"; + action: SIGNAL_EMIT "elm,action,dismiss" ""; + } + } + } + + group { name: "elm/hover/base/popout"; + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "elm.swallow.offset"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 0.0 0.0; + } + } + part { name: "elm.swallow.size"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.to: "elm.swallow.offset"; + rel1.relative: 1.0 1.0; + rel2.to: "elm.swallow.offset"; + rel2.relative: 1.0 1.0; + } + } + part { name: "base"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 1.0; + color: 0 0 0 64; + } + } + part { name: "leftclip"; + type: RECT; + description { state: "default" 0.0; + rel2.to_x: "pop"; + rel2.relative: 0.0 1.0; + rel2.offset: 1 -1; + } + } + part { name: "left"; + clip_to: "leftclip"; + description { state: "default" 0.0; + visible: 0; + rel1.to: "elm.swallow.slot.left"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.slot.left"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.swallow.slot.left"; + type: SWALLOW; + clip_to: "leftclip"; + description { state: "default" 0.0; + align: 0.0 0.5; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 0.0; + rel1.offset: -1 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 0.0 1.0; + rel2.offset: -1 -1; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.offset: -7 0; + rel2.offset: -7 -1; + align: 1.0 0.5; + } + } + part { name: "leftover"; + clip_to: "leftclip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "left"; + rel2.to: "left"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "rightclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to_x: "pop"; + rel1.relative: 1.0 0.0; + rel1.offset: -2 0; + } + } + part { name: "right"; + clip_to: "rightclip"; + description { state: "default" 0.0; + visible: 0; + rel1.to: "elm.swallow.slot.right"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.slot.right"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.swallow.slot.right"; + type: SWALLOW; + clip_to: "rightclip"; + description { state: "default" 0.0; + align: 1.0 0.5; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 1.0 0.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 1.0; + rel2.offset: 0 -1; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.offset: 6 0; + rel2.offset: 6 -1; + align: 0.0 0.5; + } + } + part { name: "rightover"; + clip_to: "rightclip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "right"; + rel2.to: "right"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "topclip"; + type: RECT; + description { state: "default" 0.0; + rel2.to_y: "pop"; + rel2.relative: 1.0 0.0; + rel2.offset: -1 1; + } + } + part { name: "top"; + clip_to: "topclip"; + description { state: "default" 0.0; + visible: 0; + rel1.to: "elm.swallow.slot.top"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.slot.top"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.swallow.slot.top"; + type: SWALLOW; + clip_to: "topclip"; + description { state: "default" 0.0; + visible: 1; + align: 0.5 0.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 0.0; + rel1.offset: 0 -1; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 0.0; + rel2.offset: -1 -1; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.offset: 0 -7; + rel2.offset: -1 -7; + align: 0.5 1.0; + } + } + part { name: "topover"; + clip_to: "topclip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "top"; + rel2.to: "top"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "bottomclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to_y: "pop"; + rel1.relative: 0.0 1.0; + rel1.offset: -1 -2; + } + } + part { name: "bottom"; + clip_to: "bottomclip"; + description { state: "default" 0.0; + visible: 0; + rel1.to: "elm.swallow.slot.bottom"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.slot.bottom"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.swallow.slot.bottom"; + type: SWALLOW; + clip_to: "bottomclip"; + description { state: "default" 0.0; + align: 0.5 1.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 1.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 1.0; + rel2.offset: -1 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.offset: 0 6; + rel2.offset: -1 6; + align: 0.5 0.0; + } + } + part { name: "bottomover"; + clip_to: "bottomclip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bottom"; + rel2.to: "bottom"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.size"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.size"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.slot.middle"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "elm.swallow.slot.middle"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "elm.swallow.size"; + rel2.to: "elm.swallow.size"; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + } + programs { + program { name: "end"; + signal: "mouse,up,1"; + source: "base"; + action: SIGNAL_EMIT "elm,action,dismiss" ""; + } + + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + + program { name: "leftshow"; + signal: "elm,action,slot,left,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "left"; + target: "elm.swallow.slot.left"; + } + program { name: "lefthide"; + signal: "elm,action,slot,left,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "left"; + target: "elm.swallow.slot.left"; + } + program { name: "rightshow"; + signal: "elm,action,slot,right,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "right"; + target: "elm.swallow.slot.right"; + } + program { name: "righthide"; + signal: "elm,action,slot,right,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "right"; + target: "elm.swallow.slot.right"; + } + program { name: "topshow"; + signal: "elm,action,slot,top,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "top"; + target: "elm.swallow.slot.top"; + } + program { name: "tophide"; + signal: "elm,action,slot,top,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "top"; + target: "elm.swallow.slot.top"; + } + program { name: "bottomshow"; + signal: "elm,action,slot,bottom,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "bottom"; + target: "elm.swallow.slot.bottom"; + } + program { name: "bottomhide"; + signal: "elm,action,slot,bottom,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "bottom"; + target: "elm.swallow.slot.bottom"; + } + } + } + + //In the hover used by the menu only the bottom part is used. + group { name: "elm/hover/base/menu"; + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + } + parts { + part { name: "elm.swallow.offset"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 0.0 0.0; + } + } + part { name: "elm.swallow.size"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.to: "elm.swallow.offset"; + rel1.relative: 1.0 1.0; + rel2.to: "elm.swallow.offset"; + rel2.relative: 1.0 1.0; + } + } + part { name: "base"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 1.0; + color: 0 0 0 64; + } + } + part { name: "elm.swallow.slot.left"; + type: SWALLOW; + description { state: "default" 0.0; + } + } + part { name: "elm.swallow.slot.right"; + type: SWALLOW; + description { state: "default" 0.0; + } + } + part { name: "elm.swallow.slot.top"; + type: SWALLOW; + description { state: "default" 0.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + } + } + part { name: "bottomclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to_y: "pop"; + rel1.relative: 0.0 1.0; + rel1.offset: -1 -2; + } + } + part { name: "bottom"; + clip_to: "bottomclip"; + description { state: "default" 0.0; + visible: 0; + rel1.to: "elm.swallow.slot.bottom"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.slot.bottom"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.swallow.slot.bottom"; + type: SWALLOW; + clip_to: "bottomclip"; + description { state: "default" 0.0; + align: 0.5 1.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 1.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 1.0; + rel2.offset: -1 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.offset: 0 6; + rel2.offset: -1 6; + align: 0.5 0.0; + } + } + part { name: "pop"; + mouse_events: 1; + repeat_events:1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.slot.middle"; + rel2.offset: 4 4; + } + } + part { name: "elm.swallow.slot.middle"; + type: SWALLOW; + repeat_events:1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.size"; + rel2.to: "elm.swallow.size"; + } + } + } + programs { + program { name: "end"; + signal: "mouse,up,1"; + source: "base"; + action: SIGNAL_EMIT "elm,action,dismiss" ""; + } + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + // transition: DECELERATE 0.5; + target: "base"; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + // transition: DECELERATE 0.5; + target: "base"; + } + program { name: "bottomshow"; + signal: "elm,action,slot,bottom,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.3; + target: "bottom"; + target: "elm.swallow.slot.bottom"; + } + program { name: "bottomhide"; + signal: "elm,action,slot,bottom,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "bottom"; + target: "elm.swallow.slot.bottom"; + } + } + } + + //In the hover used by the submenu only the bottom part is used + //and no part should interact except the bottom area + group { name: "elm/hover/base/submenu"; + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + } + parts { + part { name: "elm.swallow.offset"; + type: SWALLOW; + repeat_events:1; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 0.0 0.0; + } + } + part { name: "elm.swallow.size"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.to: "elm.swallow.offset"; + rel1.relative: 1.0 1.0; + rel2.to: "elm.swallow.offset"; + rel2.relative: 1.0 1.0; + } + } + //here we do non catch events like the hover hover does + part { name: "base"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + } + part { name: "elm.swallow.slot.left"; + type: SWALLOW; + description { state: "default" 0.0; + } + } + part { name: "elm.swallow.slot.right"; + type: SWALLOW; + description { state: "default" 0.0; + } + } + part { name: "elm.swallow.slot.top"; + type: SWALLOW; + description { state: "default" 0.0; + } + } + part { name: "bottomclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to_y: "pop"; + rel1.relative: 0.0 1.0; + rel1.offset: -1 -2; + } + } + part { name: "bottom"; + clip_to: "bottomclip"; + description { state: "default" 0.0; + visible: 0; + rel1.to: "elm.swallow.slot.bottom"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.slot.bottom"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.swallow.slot.bottom"; + type: SWALLOW; + clip_to: "bottomclip"; + description { state: "default" 0.0; + align: 0.5 1.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 1.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 1.0; + rel2.offset: -1 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.offset: 0 6; + rel2.offset: -1 6; + align: 0.5 0.0; + } + } + part { name: "pop"; + mouse_events: 1; + repeat_events:1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.slot.middle"; + rel2.offset: 4 4; + } + } + part { name: "elm.swallow.slot.middle"; + type: SWALLOW; + repeat_events:1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.size"; + rel2.to: "elm.swallow.size"; + } + } + } + programs { + program { name: "end"; + signal: "mouse,up,1"; + source: "base"; + action: SIGNAL_EMIT "elm,action,dismiss" ""; + } + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + // transition: DECELERATE 0.5; + target: "base"; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + // transition: DECELERATE 0.5; + target: "base"; + } + program { name: "bottomshow"; + signal: "elm,action,slot,bottom,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.3; + target: "bottom"; + target: "elm.swallow.slot.bottom"; + } + program { name: "bottomhide"; + signal: "elm,action,slot,bottom,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "bottom"; + target: "elm.swallow.slot.bottom"; + } + } + } + + group { name: "elm/hover/base/hoversel_vertical/default"; + alias: "elm/hover/base/hoversel_vertical/entry"; + images { +// image: "shad_circ.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "outdent-top.png" COMP; + image: "outdent-bottom.png" COMP; + } + parts { + part { name: "elm.swallow.offset"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 0.0 0.0; + } + } + part { name: "elm.swallow.size"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + rel1.to: "elm.swallow.offset"; + rel1.relative: 1.0 1.0; + rel2.to: "elm.swallow.offset"; + rel2.relative: 1.0 1.0; + } + } +/* + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "button_image"; + rel1.offset: -64 -64; + rel2.to: "button_image"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + */ + part { name: "button_image"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to_x: "elm.swallow.slot.top"; + rel1.to_y: "elm.swallow.slot.top"; + rel1.offset: -2 -6; + rel2.to_x: "elm.swallow.slot.top"; + rel2.to_y: "elm.swallow.slot.bottom"; + rel2.offset: 1 5; + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + description { state: "bottom" 0.0; + rel1.to_x: "elm.swallow.slot.bottom"; + rel1.to_y: "elm.swallow.slot.top"; + rel1.offset: -2 -6; + rel2.to_x: "elm.swallow.slot.bottom"; + rel2.to_y: "elm.swallow.slot.bottom"; + rel2.offset: 1 5; + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + } + + part { name: "base"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 1.0; + color: 0 0 0 64; + } + } + + part { name: "topclip"; + type: RECT; + description { state: "default" 0.0; + rel2.to_y: "edge_top"; + rel2.relative: 1.0 0.0; + rel2.offset: -1 7; + } + } + part { name: "elm.swallow.slot.top"; + type: SWALLOW; + clip_to: "topclip"; + description { state: "default" 0.0; + visible: 1; + align: 0.5 0.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 0.0; + rel1.offset: 0 -1; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 0.0; + rel2.offset: -1 -1; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.offset: 0 -7; + rel2.offset: -1 -7; + align: 0.5 1.0; + } + } + + part { name: "bottomclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to_y: "edge_bottom"; + rel1.relative: 0.0 1.0; + rel1.offset: -1 -8; + } + } + part { name: "elm.swallow.slot.bottom"; + type: SWALLOW; + clip_to: "bottomclip"; + description { state: "default" 0.0; + align: 0.5 1.0; + rel1.to: "elm.swallow.slot.middle"; + rel1.relative: 0.0 1.0; + rel1.offset: 0 0; + rel2.to: "elm.swallow.slot.middle"; + rel2.relative: 1.0 1.0; + rel2.offset: -1 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.offset: 0 6; + rel2.offset: -1 6; + align: 0.5 0.0; + } + } + + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button_image"; + rel2.to: "button_image"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + rel1.to: "button_image"; + rel2.to: "button_image"; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + } + part { name: "edge_top"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1 { + to: "elm.swallow.size"; + offset: 0 -10; + } + rel2 { + to: "elm.swallow.size"; + } + image.normal: "outdent-bottom.png"; + image.border: 0 0 13 0; + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "edge_bottom"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1 { + to: "elm.swallow.size"; + } + rel2 { + to: "elm.swallow.size"; + offset: -1 9; + } + image.normal: "outdent-top.png"; + image.border: 0 0 0 13; + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.swallow.slot.middle"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "elm.swallow.size"; + rel2.to: "elm.swallow.size"; + } + } + } + programs { + program { name: "end"; + signal: "mouse,up,1"; + source: "base"; + action: SIGNAL_EMIT "elm,action,dismiss" ""; + } + + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + program { name: "topshow"; + signal: "elm,action,slot,top,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "edge_top"; + after: "topshow2"; + } + program { name: "topshow2"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "elm.swallow.slot.top"; + } + program { name: "topshow3"; + signal: "elm,action,slot,top,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "button_image"; + } + program { name: "tophide"; + signal: "elm,action,slot,top,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "elm.swallow.slot.top"; + after: "tophide2"; + } + program { name: "tophide2"; + action: STATE_SET "default" 0.0; + target: "edge_top"; + } + program { name: "bottomshow"; + signal: "elm,action,slot,bottom,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "edge_bottom"; + after: "bottomshow2"; + } + program { name: "bottomshow2"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "elm.swallow.slot.bottom"; + } + program { name: "bottomshow3"; + signal: "elm,action,slot,bottom,show"; + source: "elm"; + action: STATE_SET "bottom" 0.0; + target: "button_image"; + } + program { name: "bottomhide"; + signal: "elm,action,slot,bottom,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "elm.swallow.slot.bottom"; + after: "bottomhide2"; + } + program { name: "bottomhide2"; + action: STATE_SET "default" 0.0; + target: "edge_bottom"; + } + } + } +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/scroller/base/ctxpopup"; + data { + item: "focus_highlight" "on"; + } + script { + public sbvis_v, sbvis_h, sbalways_v, sbalways_h, sbvis_timer; + public timer0(val) { + new v; + v = get_int(sbvis_v); + if (v) { + v = get_int(sbalways_v); + if(!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + v = get_int(sbvis_h); + if (v) { + v = get_int(sbalways_h); + if(!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + set_int(sbvis_timer, 0); + return 0; + } + } + images { + image: "bt_sm_base2.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "sl_bt2_2.png" COMP; + } + parts { + part { name: "clipper"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + } + } + part { name: "elm.swallow.content"; + clip_to: "clipper"; + type: SWALLOW; + scale: 1; + description { state: "default" 0.0; + align: 0.5 0.5; + } + } + part { name: "focus_highlight"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: -1 -1; + rel2.offset: 0 0; + image { normal: "sl_bt2_2.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + color: 200 155 0 0; + } + description { state: "enabled" 0.0; + inherit: "default" 0.0; + color: 200 155 0 255; + } + } + part { name: "sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar_clip"; + clip_to:"sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.0 0.0; + rel2{ to:"clipper"; relative: 1.0 1.0;} + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + align: 1.0 0.0; + rel1{ to:"clipper"; relative: 1.0 0.0; } + rel2{ to:"clipper"; relative: 1.0 1.0; } + } + } + part { name: "elm.dragable.vbar"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + scale: 1; + dragable { + x: 0 0 0; + y: 1 1 0; + confine: "sb_vbar"; + } + description { state: "default" 0.0; + fixed: 1 1; + min: 10 17; + max: 10 99999; + rel1 { relative: 0.5 0.5; to: "sb_vbar"; } + rel2 { relative: 0.5 0.5; to: "sb_vbar"; } + image { normal: "bt_sm_base2.png"; + border: 6 6 6 6; + middle: SOLID; + } + } + } + part { name: "sb_vbar_over1"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.vbar"; + image { normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + } + part { name: "sb_vbar_over2"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.to: "elm.dragable.vbar"; + image { normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + } + part { name: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar_clip"; + clip_to: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.0 0.0; + rel2{ to:"clipper"; relative: 1.0 1.0;} + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + align: 0.0 1.0; + rel1 { to:"clipper"; relative: 0.0 1.0; } + rel2 { to:"clipper"; relative: 1.0 1.0; } + } + } + part { name: "elm.dragable.hbar"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + scale: 1; + dragable { + x: 1 1 0; + y: 0 0 0; + confine: "sb_hbar"; + } + description { state: "default" 0.0; + min: 17 10; + max: 99999 10; + fixed: 1 1; + rel1 { relative: 0.5 0.5; to: "sb_hbar"; } + rel2 { relative: 0.5 0.5; to: "sb_hbar"; } + image { normal: "bt_sm_base2.png"; + border: 4 4 4 4; + middle: SOLID; + } + } + } + part { name: "sb_hbar_over1"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.hbar"; + image { normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + } + part { name: "sb_hbar_over2"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.to: "elm.dragable.hbar"; + image { normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + } + } + programs { + program { name: "load"; + signal: "load"; + source: ""; + script { + set_state(PART:"sb_vbar_clip", "hidden", 0.0); + set_state(PART:"sb_hbar_clip", "hidden", 0.0); + set_int(sbvis_v, 0); + set_int(sbvis_h, 0); + set_int(sbalways_v, 0); + set_int(sbalways_h, 0); + set_int(sbvis_timer, 0); + } + } + program { name: "vbar_show"; + signal: "elm,action,show,vbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_hide"; + signal: "elm,action,hide,vbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_show_always"; + signal: "elm,action,show_always,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + set_int(sbalways_v, 1); + emit("do-show-vbar", ""); + set_int(sbvis_v, 1); + } + } + } + program { name: "vbar_show_notalways"; + signal: "elm,action,show_notalways,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_v); + if (v) { + set_int(sbalways_v, 0); + v = get_int(sbvis_v); + if (!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + } + } + program { name: "sb_vbar_show"; + signal: "do-show-vbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 1.0; + target: "sb_vbar_clip"; + } + program { name: "sb_vbar_hide"; + signal: "do-hide-vbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 1.0; + target: "sb_vbar_clip"; + } + program { name: "hbar_show"; + signal: "elm,action,show,hbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_hide"; + signal: "elm,action,hide,hbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_show_always"; + signal: "elm,action,show_always,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + set_int(sbalways_h, 1); + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + } + } + program { name: "hbar_show_notalways"; + signal: "elm,action,show_notalways,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_h); + if (v) { + set_int(sbalways_h, 0); + v = get_int(sbvis_h); + if (!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + } + } + program { name: "sb_hbar_show"; + signal: "do-show-hbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 1.0; + target: "sb_hbar_clip"; + } + program { name: "sb_hbar_hide"; + signal: "do-hide-hbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 1.0; + target: "sb_hbar_clip"; + } + program { name: "scroll"; + signal: "elm,action,scroll"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + emit("do-show-vbar", "") + set_int(sbvis_v, 1); + } + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + v = get_int(sbvis_timer); + if (v > 0) cancel_timer(v); + v = timer(1.0, "timer0", 0); + set_int(sbvis_timer, v); + } + } + program { name: "highlight_show"; + signal: "elm,action,focus_highlight,show"; + source: "elm"; + action: STATE_SET "enabled" 0.0; + transition: ACCELERATE 0.3; + target: "focus_highlight"; + } + program { name: "highlight_hide"; + signal: "elm,action,focus_highlight,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.3; + target: "focus_highlight"; + } + } + } +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/ctxpopup/bg/default"; + parts { + part { name: "ctxpopup_bg"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 64; + } + } + } + programs { + program { name: "clicked_event"; + signal: "mouse,clicked,1"; + source: "ctxpopup_bg"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { name: "show"; + signal: "elm,state,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "ctxpopup_bg"; + } + program { name: "hide"; + signal: "elm,state,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "ctxpopup_bg"; + } + } + } +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/ctxpopup/base/default"; + images { + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + } + parts { + part { name: "base"; + scale: 1; + description { state: "default" 0.0; + rel1.offset: -3 -3; + rel2.offset: 3 3; + image { normal: "bt_base2.png"; + border: 7 7 7 7; + } + } + } + part { name: "over1"; + scale: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + rel2.relative: 1.0 0.5; + image { normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + } + part { name: "over2"; + scale: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + image { normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { to:"base"; offset: 4 4; }; + rel2 { to:"base"; offset: -5 -5; }; + } + } + } + } +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/ctxpopup/arrow/default"; + images { + image: "icon_arrow_left.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_up.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { name: "ctxpopup_arrow"; + type: IMAGE; + scale: 1; + description { + state: "default" 0.0; + min: 40 40; + fixed: 1 1; + visible: 0; + align: 0.5 0.5; + } + description { + state: "left" 0.0; + min: 40 40; + fixed: 1 1; + align: 0.0 0.5; + image { normal: "icon_arrow_left.png"; + } + } + description { state: "right" 0.0; + min: 40 40; + fixed: 1 1; + align: 1.0 0.5; + image { normal: "icon_arrow_right.png"; + } + } + description { state: "top" 0.0; + min: 40 40; + fixed: 1 1; + align: 0.5 0.0; + image { normal: "icon_arrow_up.png"; + } + } + description { state: "bottom" 0.0; + min: 40 40; + fixed: 1 1; + align: 0.5 1.0; + image { normal: "icon_arrow_down.png"; + } + } + } + } + programs { + program { name: "enable_left_arrow"; + signal: "elm,state,left"; + source: "elm"; + action: STATE_SET "left" 0.0; + target: "ctxpopup_arrow"; + } + program { name: "enable_right_arrow"; + signal: "elm,state,right"; + source: "elm"; + action: STATE_SET "right" 0.0; + target: "ctxpopup_arrow"; + } + program { name: "enable_top_arrow"; + signal: "elm,state,top"; + source: "elm"; + action: STATE_SET "top" 0.0; + target: "ctxpopup_arrow"; + } + program { name: "enable_bottom_arrow"; + signal: "elm,state,bottom"; + source: "elm"; + action: STATE_SET "bottom" 0.0; + target: "ctxpopup_arrow"; + } + } + } +/////////////////////////////////////////////////////////////////////////////// + group { + name: "elm/ctxpopup/icon_text_style_item/default"; + alias: "elm/ctxpopup/text_style_item/default"; + alias: "elm/ctxpopup/icon_style_item/default"; + images { + image: "hoversel_entry_bg.png" COMP; + } + parts { + part { name: "event"; + mouse_events: 1; + description { state: "default" 0.0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: 2 2; + rel2.offset: -3 -3; + image { normal:"hoversel_entry_bg.png"; + border: 0 0 2 2; + } + fill.smooth: 0; + color: 255 255 255 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + scale: 1; + description { state: "default" 0.0; + min: 25 25; + max: 25 25; + align: 0 0.5; + aspect: 1.0 1.0; + rel1 { offset: 10 10; } + rel2 { offset: 0 -10; } + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + min: 1 40; + fixed: 0 1; + align: 0.5 0.5; + rel1 { relative: 1.0 0.0; to: "elm.swallow.icon"; offset: 10 0; } + rel2 { relative: 1.0 1.0; offset: -11 -1; } + color: 255 255 255 255; + text { + font: "Sans"; + size: 10; + align: 0.0 0.5; + min: 1 1; + } + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + color: 0 0 0 255; + } + } + part { name: "over1"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + color: 255 255 255 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + visible: 0; + } + description { state: "enabled" 0.0; + visible: 1; + color: 50 50 50 127; + rel1.offset: 4 4; + rel2.offset: -5 -5; + } + } + } + programs { + program { + name: "item_unclick"; + signal: "mouse,up,1"; + source: "over1"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "enabled" 0.0; + target: "disclip"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { name: "item_click2"; + signal: "mouse,down,1"; + source: "over2"; + script { + set_state(PART:"elm.text", "clicked", 0.0); + set_state(PART:"bg", "clicked", 0.0); + } + } + program { name: "item_unclick2"; + signal: "mouse,up,1"; + source: "over2"; + script { + set_state(PART:"elm.text", "default", 0.0); + set_state(PART:"bg", "default", 0.0); + } + } + } + } +/////////////////////////////////////////////////////////////////////////////// +// emoticon images from: +// Tanya - Latvia +// http://lazycrazy.deviantart.com/ +// http://lazycrazy.deviantart.com/art/Very-Emotional-Emoticons-144461621 + group { name: "elm/entry/emoticon/angry/default"; images.image: + "emo-angry.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-angry.png"; } } } } + group { name: "elm/entry/emoticon/angry-shout/default"; images.image: + "emo-angry-shout.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-angry-shout.png"; } } } } + group { name: "elm/entry/emoticon/crazy-laugh/default"; images.image: + "emo-crazy-laugh.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-crazy-laugh.png"; } } } } + group { name: "elm/entry/emoticon/evil-laugh/default"; images.image: + "emo-evil-laugh.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-evil-laugh.png"; } } } } + group { name: "elm/entry/emoticon/evil/default"; images.image: + "emo-evil.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-evil.png"; } } } } + group { name: "elm/entry/emoticon/goggle-smile/default"; images.image: + "emo-goggle-smile.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-goggle-smile.png"; } } } } + group { name: "elm/entry/emoticon/grumpy/default"; images.image: + "emo-grumpy.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-grumpy.png"; } } } } + group { name: "elm/entry/emoticon/grumpy-smile/default"; images.image: + "emo-grumpy-smile.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-grumpy-smile.png"; } } } } + group { name: "elm/entry/emoticon/guilty/default"; images.image: + "emo-guilty.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-guilty.png"; } } } } + group { name: "elm/entry/emoticon/guilty-smile/default"; images.image: + "emo-guilty-smile.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-guilty-smile.png"; } } } } + group { name: "elm/entry/emoticon/haha/default"; images.image: + "emo-haha.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-haha.png"; } } } } + group { name: "elm/entry/emoticon/half-smile/default"; images.image: + "emo-half-smile.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-half-smile.png"; } } } } + group { name: "elm/entry/emoticon/happy-panting/default"; images.image: + "emo-happy-panting.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-happy-panting.png"; } } } } + group { name: "elm/entry/emoticon/happy/default"; images.image: + "emo-happy.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-happy.png"; } } } } + group { name: "elm/entry/emoticon/indifferent/default"; images.image: + "emo-indifferent.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-indifferent.png"; } } } } + group { name: "elm/entry/emoticon/kiss/default"; images.image: + "emo-kiss.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-kiss.png"; } } } } + group { name: "elm/entry/emoticon/knowing-grin/default"; images.image: + "emo-knowing-grin.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-knowing-grin.png"; } } } } + group { name: "elm/entry/emoticon/laugh/default"; images.image: + "emo-laugh.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-laugh.png"; } } } } + group { name: "elm/entry/emoticon/little-bit-sorry/default"; images.image: + "emo-little-bit-sorry.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-little-bit-sorry.png"; } } } } + group { name: "elm/entry/emoticon/love-lots/default"; images.image: + "emo-love-lots.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-love-lots.png"; } } } } + group { name: "elm/entry/emoticon/love/default"; images.image: + "emo-love.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-love.png"; } } } } + group { name: "elm/entry/emoticon/minimal-smile/default"; images.image: + "emo-minimal-smile.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-minimal-smile.png"; } } } } + group { name: "elm/entry/emoticon/not-happy/default"; images.image: + "emo-not-happy.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-not-happy.png"; } } } } + group { name: "elm/entry/emoticon/not-impressed/default"; images.image: + "emo-not-impressed.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-not-impressed.png"; } } } } + group { name: "elm/entry/emoticon/omg/default"; images.image: + "emo-omg.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-omg.png"; } } } } + group { name: "elm/entry/emoticon/opensmile/default"; images.image: + "emo-opensmile.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-opensmile.png"; } } } } + group { name: "elm/entry/emoticon/smile/default"; images.image: + "emo-smile.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-smile.png"; } } } } + group { name: "elm/entry/emoticon/sorry/default"; images.image: + "emo-sorry.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-sorry.png"; } } } } + group { name: "elm/entry/emoticon/squint-laugh/default"; images.image: + "emo-squint-laugh.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-squint-laugh.png"; } } } } + group { name: "elm/entry/emoticon/surprised/default"; images.image: + "emo-surprised.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-surprised.png"; } } } } + group { name: "elm/entry/emoticon/suspicious/default"; images.image: + "emo-suspicious.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-suspicious.png"; } } } } + group { name: "elm/entry/emoticon/tongue-dangling/default"; images.image: + "emo-tongue-dangling.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-tongue-dangling.png"; } } } } + group { name: "elm/entry/emoticon/tongue-poke/default"; images.image: + "emo-tongue-poke.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-tongue-poke.png"; } } } } + group { name: "elm/entry/emoticon/uh/default"; images.image: + "emo-uh.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-uh.png"; } } } } + group { name: "elm/entry/emoticon/unhappy/default"; images.image: + "emo-unhappy.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-unhappy.png"; } } } } + group { name: "elm/entry/emoticon/very-sorry/default"; images.image: + "emo-very-sorry.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-very-sorry.png"; } } } } + group { name: "elm/entry/emoticon/what/default"; images.image: + "emo-what.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-what.png"; } } } } + group { name: "elm/entry/emoticon/wink/default"; images.image: + "emo-wink.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-wink.png"; } } } } + group { name: "elm/entry/emoticon/worried/default"; images.image: + "emo-worried.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-worried.png"; } } } } + group { name: "elm/entry/emoticon/wtf/default"; images.image: + "emo-wtf.png" COMP; parts { part { name: "icon"; mouse_events: 0; description { state: "default" 0.0; max: 64 64; image.normal: + "emo-wtf.png"; } } } } +//------------------------------------------------------------ + group { name: "elm/entry/base/default"; + styles + { + style { name: "entry_textblock_style"; + base: "font=Sans font_size=10 color=#000 wrap=word text_class=entry"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "tab" "\t"; + tag: "em" "+ font=Sans:style=Oblique"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "link" "+ color=#800 underline=on underline_color=#8008"; + tag: "hilight" "+ font=Sans:style=Bold"; + } + style { name: "entry_textblock_disabled_style"; + base: "font=Sans font_size=10 color=#00000080 wrap=word text_class=entry"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "tab" "\t"; + tag: "em" "+ font=Sans:style=Oblique"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "link" "+ color=#00000080 underline=on underline_color=#00000080"; + tag: "hilight" "+ font=Sans:style=Bold"; + } + } + data { +// item: context_menu_orientation "horizontal"; + } + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 1; + scale: 1; + entry_mode: EDITABLE; + select_mode: EXPLICIT; + multiline: 1; + source: "elm/entry/selection/default"; // selection under + // source2: "X"; // selection over + // source3: "X"; // cursor under + source4: "elm/entry/cursor/default"; // cursorover + source5: "elm/entry/anchor/default"; // anchor under + // source6: "X"; // anchor over + description { state: "default" 0.0; + /* we gotta use 0 0 here, because of scrolled entries */ + fixed: 0 0; + text { + style: "entry_textblock_style"; + min: 0 1; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + text { + style: "entry_textblock_disabled_style"; + min: 0 1; + } + } + } + } + programs { + program { name: "focus"; + signal: "load"; + source: ""; + action: FOCUS_SET; + target: "elm.text"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "elm.text"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + } + } + + group { name: "elm/entry/base-charwrap/default"; + styles + { + style { name: "entry_textblock_style_charwrap"; + base: "font=Sans font_size=10 color=#000 wrap=char text_class=entry"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "tab" "\t"; + tag: "em" "+ font=Sans:style=Oblique"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "link" "+ color=#800 underline=on underline_color=#8008"; + tag: "hilight" "+ font=Sans:style=Bold"; + } + style { name: "entry_textblock_disabled_style_charwrap"; + base: "font=Sans font_size=10 color=#00000080 wrap=char text_class=entry"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "tab" "\t"; + tag: "em" "+ font=Sans:style=Oblique"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "link" "+ color=#00000080 underline=on underline_color=#00000080"; + tag: "hilight" "+ font=Sans:style=Bold"; + } + } + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 1; + scale: 1; + entry_mode: EDITABLE; + select_mode: EXPLICIT; + multiline: 1; + source: "elm/entry/selection/default"; // selection under +// source2: "X"; // selection over +// source3: "X"; // cursor under + source4: "elm/entry/cursor/default"; // cursorover + source5: "elm/entry/anchor/default"; // anchor under +// source6: "X"; // anchor over + description { state: "default" 0.0; + fixed: 1 0; + text { + style: "entry_textblock_style_charwrap"; + min: 0 1; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + text { + style: "entry_textblock_disabled_style_charwrap"; + min: 0 1; + } + } + } + } + programs { + program { name: "focus"; + signal: "load"; + source: ""; + action: FOCUS_SET; + target: "elm.text"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "elm.text"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + } + } + + group { name: "elm/entry/base-nowrap/default"; + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 1; + scale: 1; + entry_mode: EDITABLE; + select_mode: EXPLICIT; + multiline: 1; + source: "elm/entry/selection/default"; // selection under + source4: "elm/entry/cursor/default"; // cursorover + source5: "elm/entry/anchor/default"; // anchor under + description { state: "default" 0.0; + text { + style: "entry_textblock_style"; + min: 1 1; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + text { + style: "entry_textblock_disabled_style"; + min: 0 1; + } + } + } +/* + part { name: "sel"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + align: 1.0 1.0; + max: 16 16; + aspect: 1.0 1.0; + color: 255 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 0 0 50; + } + } + */ + } + programs { + program { name: "focus"; + signal: "load"; + source: ""; + action: FOCUS_SET; + target: "elm.text"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "elm.text"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } +/* + program { name: "selmode0"; + signal: "elm,state,select,on"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "sel"; + } + program { name: "selmode1"; + signal: "elm,state,select,off"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sel"; + } + */ + } + } + + group { name: "elm/entry/base-single/default"; + styles + { + style { name: "entry_single_textblock_style"; + base: "font=Sans font_size=10 color=#000 wrap=none text_class=entry"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "tab" "\t"; + tag: "em" "+ font=Sans:style=Oblique"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "link" "+ color=#800 underline=on underline_color=#8008"; + tag: "hilight" "+ font=Sans:style=Bold"; + } + style { name: "entry_single_textblock_disabled_style"; + base: "font=Sans font_size=10 color=#00000080 wrap=none text_class=entry"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "tab" "\t"; + tag: "em" "+ font=Sans:style=Oblique"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "link" "+ color=#00000080 underline=on underline_color=#00000080"; + tag: "hilight" "+ font=Sans:style=Bold"; + } + } + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 1; + scale: 1; + entry_mode: EDITABLE; + select_mode: EXPLICIT; + multiline: 0; + source: "elm/entry/selection/default"; // selection under + source4: "elm/entry/cursor/default"; // cursorover + source5: "elm/entry/anchor/default"; // anchor under + description { state: "default" 0.0; + text { + style: "entry_single_textblock_style"; + min: 1 1; + max: 0 1; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + text { + style: "entry_single_textblock_disabled_style"; + } + } + } + } + programs { + program { name: "focus"; + signal: "load"; + source: ""; + action: FOCUS_SET; + target: "elm.text"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "elm.text"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + } + } + + group { name: "elm/entry/base-single-noedit/default"; + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 1; + scale: 1; + entry_mode: PLAIN; + select_mode: EXPLICIT; + multiline: 0; + source: "elm/entry/selection/default"; // selection under + source5: "elm/entry/anchor/default"; // anchor under + description { state: "default" 0.0; + text { + style: "entry_single_textblock_style"; + min: 1 1; + max: 0 1; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + text { + style: "entry_single_textblock_disabled_style"; + } + } + } + } + programs { + program { name: "focus"; + signal: "load"; + source: ""; + action: FOCUS_SET; + target: "elm.text"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "elm.text"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + } + } + + group { name: "elm/entry/base-noedit/default"; + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 1; + scale: 1; + entry_mode: PLAIN; + select_mode: EXPLICIT; + multiline: 1; + source: "elm/entry/selection/default"; // selection under + source5: "elm/entry/anchor/default"; // anchor under + description { state: "default" 0.0; + fixed: 1 0; + text { + style: "entry_textblock_style"; + min: 0 1; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + text { + style: "entry_textblock_disabled_style"; + } + } + } + } + programs { + program { name: "focus"; + signal: "load"; + source: ""; + action: FOCUS_SET; + target: "elm.text"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "elm.text"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + } + } + + group { name: "elm/entry/base-noedit-charwrap/default"; + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 1; + scale: 1; + entry_mode: PLAIN; + select_mode: EXPLICIT; + multiline: 1; + source: "elm/entry/selection/default"; // selection under + source5: "elm/entry/anchor/default"; // anchor under + description { state: "default" 0.0; + fixed: 1 0; + text { + style: "entry_textblock_style_charwrap"; + min: 0 1; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + text { + style: "entry_textblock_disabled_style_charwrap"; + } + } + } + } + programs { + program { name: "focus"; + signal: "load"; + source: ""; + action: FOCUS_SET; + target: "elm.text"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "elm.text"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + } + } + + group { name: "elm/entry/base-nowrap-noedit/default"; + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 1; + scale: 1; + entry_mode: PLAIN; + select_mode: EXPLICIT; + multiline: 1; + source: "elm/entry/selection/default"; // selection under + source5: "elm/entry/anchor/default"; // anchor under + description { state: "default" 0.0; + text { + style: "entry_textblock_style"; + min: 1 1; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + text { + style: "entry_textblock_disabled_style"; + } + } + } + } + programs { + program { name: "focus"; + signal: "load"; + source: ""; + action: FOCUS_SET; + target: "elm.text"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "elm.text"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + } + } + + group { name: "elm/entry/base-password/default"; + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 1; + scale: 1; + entry_mode: PASSWORD; + select_mode: EXPLICIT; + multiline: 0; + source: "elm/entry/selection/default"; // selection under + source4: "elm/entry/cursor/default"; // cursorover + source5: "elm/entry/anchor/default"; // anchor under + description { state: "default" 0.0; + text { + style: "entry_single_textblock_style"; + repch: "*"; + min: 1 1; + max: 0 1; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + text { + style: "entry_single_textblock_disabled_style"; + } + } + } + } + programs { + program { name: "focus"; + signal: "load"; + source: ""; + action: FOCUS_SET; + target: "elm.text"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "elm.text"; + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + } + } + + group { name: "elm/entry/cursor/default"; + images { + image: "cur_box.png" COMP; + image: "cur_hi.png" COMP; + image: "cur_shad.png" COMP; + image: "cur_shine.png" COMP; + image: "cur_glow.png" COMP; + } + parts { + part { name: "clip2"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "clip"; + rel2.to: "clip"; + visible: 0; + } + description { state: "focused" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "clip"; + type: RECT; + mouse_events: 0; + clip_to: "clip2"; + description { state: "default" 0.0; + rel1.offset: -10 0; + rel2.offset: 9 9; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "bg"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + rel1.to: "base"; + rel1.offset: -2 0; + rel2.to: "base"; + rel2.offset: 1 1; + image.border: 2 2 2 2; + image.normal: "cur_shad.png"; + } + } + part { name: "base"; + mouse_events: 0; + scale: 1; + clip_to: "clip"; + description { state: "default" 0.0; + min: 2 2; + align: 0.5 1.0; + rel1.relative: 0.0 1.0; + rel1.offset: 0 -1; + rel2.relative: 1.0 1.0; + rel2.offset: -1 -1; + image.normal: "cur_box.png"; + } + } + part { name: "hi"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + rel2.relative: 1.0 0.5; + image.normal: "cur_hi.png"; + } + } + part { name: "shine"; + mouse_events: 0; + clip_to: "clip"; + clip_to: "clip2"; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + rel2.relative: 1.0 0.75; + image.border: 2 2 1 0; + image.normal: "cur_shine.png"; + fill.smooth: 0; + } + } + part { name: "glow"; + mouse_events: 0; + clip_to: "clip2"; + description { state: "default" 0.0; + rel1.to: "base"; + rel1.relative: 0.0 -2.0; + rel1.offset: -2 0; + rel2.to: "base"; + rel2.relative: 1.0 0.0; + rel2.offset: 1 1; + image.border: 2 2 0 4; + image.normal: "cur_glow.png"; + fill.smooth: 0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + } + } + } + programs { + program { name: "show"; + signal: "show"; + source: ""; + action: STATE_SET "hidden" 0.0; + in: 1.0 0.0; + transition: DECELERATE 2.0; + target: "glow"; + after: "show2"; + } + program { name: "show2"; + action: STATE_SET "hidden" 0.0; + in: 0.2 0.0; + target: "clip"; + after: "show3"; + } + program { name: "show3"; + action: STATE_SET "default" 0.0; + in: 0.5 0.0; + target: "clip"; + after: "show4"; + } + program { name: "show4"; + action: STATE_SET "default" 0.0; + in: 0.5 0.0; + transition: DECELERATE 0.5; + target: "glow"; + after: "show"; + } + program { name: "focused"; + signal: "elm,action,focus"; + source: "elm"; + action: STATE_SET "focused" 0.0; + target: "clip2"; + } + program { name: "unfocused"; + signal: "elm,action,unfocus"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "clip2"; + } + } + } + + group { name: "elm/entry/selection/default"; + parts { + part { name: "bg"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + color: 128 128 128 128; + } + } + } + } + + group { name: "elm/entry/anchor/default"; + parts { + part { name: "bg"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + color: 128 0 0 64; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/bubble/top_left/default"; + alias: "elm/bubble/base/default"; + images { + image: "bubble_3.png" COMP; + image: "bubble_shine3.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + align: 0.0 0.0; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + to_y: "elm.text"; + relative: 0.0 1.0; + offset: 4 -1; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.0 0.0; + fixed: 0 1; + visible: 0; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "elm.info"; + relative: 0.0 0.0; + offset: -5 4; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 0 0 0 255; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 0 1; + max: 0 1; + align: 0.0 0.0; + } + } + } + part { name: "elm.info"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 1.0 0.0; + fixed: 1 1; + visible: 0; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 0.0; + offset: -5 4; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 0 0 0 64; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 1 1; + max: 1 1; + align: 1.0 0.0; + } + } + } + part { name: "base0"; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to_y: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 0 0; + } + image { + normal: "bubble_3.png"; + border: 36 11 18 9; + } + image.middle: SOLID; + fill.smooth: 0; + } + description { state: "infobase" 0.0; + inherit: "default" 0.0; + rel1.to_y: "elm.info"; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to: "base0"; + offset: 9 16; + } + rel2 { + to: "base0"; + offset: -10 -9; + } + } + } + part { name: "shine"; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base0"; + offset: 5 4; + } + rel2 { + to: "base0"; + relative: 1.0 0.5; + offset: -6 7; + } + image { + normal: "bubble_shine3.png"; + border: 36 5 14 0; + } + fill.smooth: 0; + } + } + } + programs { + program { + name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"base0", st, 30, vl); + if (!strcmp(st, "infobase")) + set_state(PART:"base0", "default", 0.0); + set_state(PART:"elm.swallow.icon", "visible", 0.0); + } + } + program { + name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.info", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"base0", "infobase", 0.0); + set_state(PART:"elm.swallow.icon", "default", 0.0); + } + } + program { + name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { + name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { + name: "info_show"; + signal: "elm,state,info,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.icon", st, 30, vl); + if (!strcmp(st, "default")) + set_state(PART:"base0", "infobase", 0.0); + set_state(PART:"elm.info", "visible", 0.0); + } + } + program { + name: "info_hide"; + signal: "elm,state,info,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.info"; + target: "base0"; + } + } + } + + group { name: "elm/bubble/top_right/default"; + images { + image: "bubble_4.png" COMP; + image: "bubble_shine4.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + align: 1.0 0.0; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + to_y: "elm.text"; + relative: 1.0 1.0; + offset: -5 -1; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.0 0.0; + fixed: 0 1; + visible: 0; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "elm.info"; + relative: 0.0 0.0; + offset: -5 4; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 0 0 0 255; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 0 1; + max: 0 1; + align: 0.0 0.0; + } + } + } + part { name: "elm.info"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 1.0 0.0; + fixed: 1 1; + visible: 0; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + to_x: "elm.swallow.icon"; + relative: 0.0 0.0; + offset: -5 4; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 0 0 0 64; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 1 1; + max: 1 1; + align: 1.0 0.0; + } + } + } + part { name: "base0"; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to_y: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 0 0; + } + image { + normal: "bubble_4.png"; + border: 11 36 18 9; + } + image.middle: SOLID; + fill.smooth: 0; + } + description { state: "infobase" 0.0; + inherit: "default" 0.0; + rel1.to_y: "elm.info"; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to: "base0"; + offset: 9 16; + } + rel2 { + to: "base0"; + offset: -10 -9; + } + } + } + part { name: "shine"; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base0"; + offset: 5 4; + } + rel2 { + to: "base0"; + relative: 1.0 0.5; + offset: -6 7; + } + image { + normal: "bubble_shine4.png"; + border: 5 36 14 0; + } + fill.smooth: 0; + } + } + } + programs { + program { + name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"base0", st, 30, vl); + if (!strcmp(st, "infobase")) + set_state(PART:"base0", "default", 0.0); + set_state(PART:"elm.swallow.icon", "visible", 0.0); + } + } + program { + name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.info", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"base0", "infobase", 0.0); + set_state(PART:"elm.swallow.icon", "default", 0.0); + } + } + program { + name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { + name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { + name: "info_show"; + signal: "elm,state,info,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.icon", st, 30, vl); + if (!strcmp(st, "default")) + set_state(PART:"base0", "infobase", 0.0); + set_state(PART:"elm.info", "visible", 0.0); + } + } + program { + name: "info_hide"; + signal: "elm,state,info,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.info"; + target: "base0"; + } + } + } + + group { name: "elm/bubble/bottom_left/default"; + images { + image: "bubble_1.png" COMP; + image: "bubble_shine.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + align: 0.0 1.0; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + to_y: "elm.text"; + relative: 0.0 0.0; + offset: 4 0; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.0 1.0; + fixed: 0 1; + visible: 0; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 1.0; + offset: 4 -5; + } + rel2 { + to_x: "elm.info"; + relative: 0.0 1.0; + offset: -5 -5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 0 0 0 255; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 0 1; + max: 0 1; + align: 0.0 1.0; + } + } + } + part { name: "elm.info"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 1.0 1.0; + fixed: 1 1; + visible: 0; + rel1 { + relative: 1.0 1.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 0 0 0 64; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 1 1; + max: 1 1; + align: 1.0 1.0; + } + } + } + part { name: "base0"; + mouse_events: 0; + description { state: "default" 0.0; + rel2 { + to_y: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: -1 -1; + } + image { + normal: "bubble_1.png"; + border: 36 11 10 19; + } + image.middle: SOLID; + fill.smooth: 0; + } + description { state: "infobase" 0.0; + inherit: "default" 0.0; + rel2.to_y: "elm.info"; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to: "base0"; + offset: 9 8; + } + rel2 { + to: "base0"; + offset: -10 -17; + } + } + } + part { name: "shine"; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base0"; + offset: 5 4; + } + rel2 { + to: "base0"; + relative: 1.0 0.5; + offset: -6 -16; + } + image { + normal: "bubble_shine.png"; + border: 5 5 5 0; + } + fill.smooth: 0; + } + } + } + programs { + program { + name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"base0", st, 30, vl); + if (!strcmp(st, "infobase")) + set_state(PART:"base0", "default", 0.0); + set_state(PART:"elm.swallow.icon", "visible", 0.0); + } + } + program { + name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.info", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"base0", "infobase", 0.0); + set_state(PART:"elm.swallow.icon", "default", 0.0); + } + } + program { + name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { + name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { + name: "info_show"; + signal: "elm,state,info,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.icon", st, 30, vl); + if (!strcmp(st, "default")) + set_state(PART:"base0", "infobase", 0.0); + set_state(PART:"elm.info", "visible", 0.0); + } + } + program { + name: "info_hide"; + signal: "elm,state,info,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.info"; + target: "base0"; + } + } + } + + group { name: "elm/bubble/bottom_right/default"; + images { + image: "bubble_2.png" COMP; + image: "bubble_shine.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0.0; + align: 1.0 1.0; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + to_y: "elm.text"; + relative: 1.0 0.0; + offset: -5 0; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.0 1.0; + fixed: 0 1; + visible: 0; + rel1 { + relative: 0.0 1.0; + offset: 4 -5; + } + rel2 { + to_x: "elm.info"; + relative: 0.0 1.0; + offset: -5 -5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 0 0 0 255; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 0 1; + max: 0 1; + align: 0.0 1.0; + } + } + } + part { name: "elm.info"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 1.0 1.0; + fixed: 1 1; + visible: 0; + rel1 { + relative: 1.0 1.0; + offset: -5 -5; + } + rel2 { + to_x: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: -5 -5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 0 0 0 64; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 1 1; + max: 1 1; + align: 1.0 1.0; + } + } + } + part { name: "base0"; + mouse_events: 0; + description { state: "default" 0.0; + rel2 { + to_y: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: -1 -1; + } + image { + normal: "bubble_2.png"; + border: 11 36 10 19; + } + image.middle: SOLID; + fill.smooth: 0; + } + description { state: "infobase" 0.0; + inherit: "default" 0.0; + rel2.to_y: "elm.info"; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to: "base0"; + offset: 9 8; + } + rel2 { + to: "base0"; + offset: -10 -17; + } + } + } + part { name: "shine"; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base0"; + offset: 5 4; + } + rel2 { + to: "base0"; + relative: 1.0 0.5; + offset: -6 -16; + } + image { + normal: "bubble_shine.png"; + border: 5 5 5 0; + } + fill.smooth: 0; + } + } + } + programs { + program { + name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"base0", st, 30, vl); + if (!strcmp(st, "infobase")) + set_state(PART:"base0", "default", 0.0); + set_state(PART:"elm.swallow.icon", "visible", 0.0); + } + } + program { + name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.info", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"base0", "infobase", 0.0); + set_state(PART:"elm.swallow.icon", "default", 0.0); + } + } + program { + name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { + name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { + name: "info_show"; + signal: "elm,state,info,visible"; + source: "elm"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.swallow.icon", st, 30, vl); + if (!strcmp(st, "default")) + set_state(PART:"base0", "infobase", 0.0); + set_state(PART:"elm.info", "visible", 0.0); + } + } + program { + name: "info_hide"; + signal: "elm,state,info,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.info"; + target: "base0"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/photo/base/default"; + images { + image: "frame_1.png" COMP; + image: "frame_2.png" COMP; + image: "dia_grad.png" COMP; + image: "head.png" COMP; + } + parts { + part { name: "base0"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "dia_grad.png"; + rel1.to: "over"; + rel2.to: "over"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "base"; + mouse_events: 0; + description { state: "default" 0.0; + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "head"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + aspect: 1.0 1.0; + aspect_preference: BOTH; + image.normal: "head.png"; + } + } + part { name: "clip"; + mouse_events: 0; + type: RECT; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + color: 255 255 255 255; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clip"; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + } + } + part { name: "over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + image { + normal: "frame_1.png"; + border: 2 2 28 22; + middle: 0; + } + fill.smooth: 0; + } + } + } + } + + group { name: "elm/photo/base/shadow"; + images { + image: "shadow.png" COMP; + image: "black.png" COMP; + } + script { + public message(Msg_Type:type, id, ...) { + if( (type==MSG_INT_SET) && (id==0) ) + { + new w; + new h; + + custom_state(PART:"size", "default", 0.0); + + w = getarg(2); + h = getarg(3); + set_state_val(PART:"size", STATE_REL1_OFFSET, - w/2, - h/2); + set_state_val(PART:"size", STATE_REL2_OFFSET, w/2 + 1, h/2 + 1); + set_state(PART:"size", "custom", 0.0); + } + } + } + parts { + part { name: "size"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.5 0.5; + rel2.relative: 0.5 0.5; + } + } + part { + name: "shadow"; + type: IMAGE; + repeat_events: 1; + description { + state: "default" 0.0; + rel1.to: "size"; + rel2.to: "size"; + rel1.relative: -0.06 -0.06; + rel2.relative: 1.07 1.07; + image.normal: "shadow.png"; + } + } + + + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.offset: 3 3; + rel2.offset: -3 -3; + fixed: 1 1; + } + } + + part { + name: "border"; + type: IMAGE; + repeat_events: 1; + description { + state: "default" 0.0; + visible: 1; + color: 0 0 0 255; + rel1.to: "size"; + rel2.to: "size"; + image.normal: "black.png"; + image.border: 1 1 1 1; + image.middle: 0; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/thumb/base/default"; + images { + image: "frame_1.png" COMP; + image: "frame_2.png" COMP; + image: "dia_grad.png" COMP; + image: "busy-1.png" COMP; + image: "busy-2.png" COMP; + image: "busy-3.png" COMP; + image: "busy-4.png" COMP; + image: "busy-5.png" COMP; + image: "busy-6.png" COMP; + image: "busy-7.png" COMP; + image: "busy-8.png" COMP; + image: "busy-9.png" COMP; + } + parts { + part { name: "base0"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "dia_grad.png"; + rel1.to: "over"; + rel2.to: "over"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "base"; + mouse_events: 0; + description { state: "default" 0.0; + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "clip"; + mouse_events: 0; + type: RECT; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + color: 255 255 255 255; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clip"; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + } + } + part { name: "progress"; + mouse_events: 0; + + clip_to: "clip"; + description { state: "default" 0.0; + min: 32 32; + max: 32 32; + visible: 0; + aspect: 1.0 1.0; + aspect_preference: BOTH; + } + description { state: "pulse" 0.0; + inherit: "default" 0.0; + visible: 1; + image { + normal: "busy-9.png"; + tween: "busy-1.png"; + tween: "busy-2.png"; + tween: "busy-3.png"; + tween: "busy-4.png"; + tween: "busy-5.png"; + tween: "busy-6.png"; + tween: "busy-7.png"; + tween: "busy-8.png"; + border: 7 7 7 7; + } + } + } + part { name: "over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + image { + normal: "frame_1.png"; + border: 2 2 28 22; + middle: 0; + } + fill.smooth: 0; + } + } + programs { + program { name: "start_pulse"; + signal: "elm,state,pulse,start"; + source: "elm"; + action: STATE_SET "pulse" 0.0; + target: "progress"; + transition: LINEAR 0.5; + after: "start_pulse"; + } + program { name: "stop_pulse"; + signal: "elm,state,pulse,stop"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "progress"; + } + } + } + } + + group { name: "elm/thumb/base/noframe"; + images { + image: "busy-1.png" COMP; + image: "busy-2.png" COMP; + image: "busy-3.png" COMP; + image: "busy-4.png" COMP; + image: "busy-5.png" COMP; + image: "busy-6.png" COMP; + image: "busy-7.png" COMP; + image: "busy-8.png" COMP; + image: "busy-9.png" COMP; + } + parts { + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + } + } + part { name: "progress"; + mouse_events: 0; + description { state: "default" 0.0; + min: 32 32; + max: 32 32; + visible: 0; + aspect: 1.0 1.0; + aspect_preference: BOTH; + } + description { state: "pulse" 0.0; + inherit: "default" 0.0; + visible: 1; + image { + normal: "busy-9.png"; + tween: "busy-1.png"; + tween: "busy-2.png"; + tween: "busy-3.png"; + tween: "busy-4.png"; + tween: "busy-5.png"; + tween: "busy-6.png"; + tween: "busy-7.png"; + tween: "busy-8.png"; + border: 7 7 7 7; + } + } + } + programs { + program { name: "start_pulse"; + signal: "elm,state,pulse,start"; + source: "elm"; + action: STATE_SET "pulse" 0.0; + target: "progress"; + transition: LINEAR 0.5; + after: "start_pulse"; + } + program { name: "stop_pulse"; + signal: "elm,state,pulse,stop"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "progress"; + } + } + } + } + + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/icon/home/default"; alias: "elm/icon/toolbar/home/default"; min: 32 32; + images.image: "icon_home.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_home.png"; } } } } + group { name: "elm/icon/close/default"; alias: "elm/icon/toolbar/close/default"; min: 32 32; + images.image: "icon_close.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_close.png"; } } } } + group { name: "elm/icon/apps/default"; alias: "elm/icon/toolbar/apps/default"; min: 32 32; + images.image: "icon_apps.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_apps.png"; } } } } + group { name: "elm/icon/arrow_up/default"; alias: "elm/icon/toolbar/arrow_up/default"; min: 32 32; + images.image: "icon_arrow_up.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_arrow_up.png"; } } } } + group { name: "elm/icon/arrow_down/default"; + alias: "elm/icon/toolbar/arrow_down/default"; + alias: "elm/icon/toolbar/more_menu/default"; min: 32 32; + images.image: "icon_arrow_down.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_arrow_down.png"; } } } } + group { name: "elm/icon/arrow_left/default"; alias: "elm/icon/toolbar/arrow_left/default"; min: 32 32; + images.image: "icon_arrow_left.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_arrow_left.png"; } } } } + group { name: "elm/icon/arrow_right/default"; alias: "elm/icon/toolbar/arrow_right/default"; min: 32 32; + images.image: "icon_arrow_right.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_arrow_right.png"; } } } } + group { name: "elm/icon/chat/default"; alias: "elm/icon/toolbar/chat/default"; min: 32 32; + images.image: "icon_chat.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_chat.png"; } } } } + group { name: "elm/icon/clock/default"; alias: "elm/icon/toolbar/clock/default"; min: 32 32; + images.image: "icon_clock.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_clock.png"; } } } } + group { name: "elm/icon/delete/default"; alias: "elm/icon/toolbar/delete/default"; min: 32 32; + images.image: "icon_delete.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_delete.png"; } } } } + group { name: "elm/icon/edit/default"; alias: "elm/icon/toolbar/edit/default"; min: 32 32; + images.image: "icon_edit.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_edit.png"; } } } } + group { name: "elm/icon/refresh/default"; alias: "elm/icon/toolbar/refresh/default"; min: 32 32; + images.image: "icon_refresh.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_refresh.png"; } } } } + group { name: "elm/icon/folder/default"; alias: "elm/icon/toolbar/folder/default"; min: 32 32; + images.image: "icon_folder.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_folder.png"; } } } } + group { name: "elm/icon/file/default"; alias: "elm/icon/toolbar/file/default"; min: 32 32; + images.image: "icon_file.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_file.png"; } } } } +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/icon/menu/home/default"; min: 24 24; max: 24 24; + images.image: "icon_home.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_home.png"; } } } } + group { name: "elm/icon/menu/close/default"; min: 24 24; max: 24 24; + images.image: "icon_close.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_close.png"; } } } } + group { name: "elm/icon/menu/apps/default"; min: 24 24; max: 24 24; + images.image: "icon_apps.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_apps.png"; } } } } + group { name: "elm/icon/menu/arrow_up/default"; min: 24 24; max: 24 24; + images.image: "icon_arrow_up.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_arrow_up.png"; } } } } + group { name: "elm/icon/menu/arrow_down/default"; min: 24 24; max: 24 24; + images.image: "icon_arrow_down.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_arrow_down.png"; } } } } + group { name: "elm/icon/menu/arrow_left/default"; min: 24 24; max: 24 24; + images.image: "icon_arrow_left.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_arrow_left.png"; } } } } + group { name: "elm/icon/menu/arrow_right/default"; min: 24 24; max: 24 24; + images.image: "icon_arrow_right.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_arrow_right.png"; } } } } + group { name: "elm/icon/menu/chat/default"; min: 24 24; max: 24 24; + images.image: "icon_chat.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_chat.png"; } } } } + group { name: "elm/icon/menu/clock/default"; min: 24 24; max: 24 24; + images.image: "icon_clock.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_clock.png"; } } } } + group { name: "elm/icon/menu/delete/default"; min: 24 24; max: 24 24; + images.image: "icon_delete.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_delete.png"; } } } } + group { name: "elm/icon/menu/edit/default"; min: 24 24; max: 24 24; + images.image: "icon_edit.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_edit.png"; } } } } + group { name: "elm/icon/menu/refresh/default"; min: 24 24; max: 24 24; + images.image: "icon_refresh.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_refresh.png"; } } } } + group { name: "elm/icon/menu/folder/default"; min: 24 24; max: 24 24; + images.image: "icon_folder.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_folder.png"; } } } } + group { name: "elm/icon/menu/file/default"; min: 24 24; max: 24 24; + images.image: "icon_file.png" COMP; parts { part { name: "base"; + description { state: "default" 0.0; aspect: 1.0 1.0; aspect_preference: BOTH; + image.normal: "icon_file.png"; } } } } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/toolbar/base/default"; + images { + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + image: "bt_dis_shine.png" COMP; + image: "icon_left_arrow.png" COMP; + image: "icon_right_arrow.png" COMP; + } + parts { + part { name: "base"; + mouse_events: 1; + description { state: "default" 0.0; + rel1 { + relative: 0.0 0.0; + offset: 2 2; + } + rel2.offset: -3 -3; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "clipper"; + type: RECT; + mouse_events: 0; + description { + state: "default" 0.0; + rel1 { + to: "base"; + offset: 2 2; + } + rel2 { + to: "base"; + offset: -3 -3; + } + } + } + part { name: "elm.swallow.content"; + clip_to: "clipper"; + type: SWALLOW; + description { + state: "default" 0.0; + rel1.to: "clipper"; + rel2.to: "clipper"; + } + } + part { name: "over2"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + image { + normal: "bt_dis_shine.png"; + border: 4 4 4 4; + } + } + } + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + color: 255 255 255 128; + } + } + part { name: "left_arrow"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "icon_left_arrow.png"; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + align: 0.0 0.5; + min: 32 32; + max: 32 32; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "right_arrow"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "icon_right_arrow.png"; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + align: 1.0 0.5; + min: 32 32; + max: 32 32; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "event"; + type: RECT; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + } + programs { + program { name: "sb_hbar_show"; + signal: "elm,action,show,hbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "left_arrow"; + target: "right_arrow"; + } + program { name: "sb_hbar_hide"; + signal: "elm,action,hide,hbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "left_arrow"; + target: "right_arrow"; + transition: LINEAR 0.5; + } + } + } + + group { name: "elm/toolbar/item/default"; + images { + image: "toolbar_sel.png" COMP; + } + data.item: "transition_animation_on" "1"; + parts { + part { name: "label2"; + type: TEXT; + mouse_events: 0; + scale: 1; + clip_to: "elm.text.clipper"; + description { state: "default" 0.0; + align: 0.5 1.0; + fixed: 0 1; + rel1.to: "elm.text"; + rel2.to: "elm.text"; + color: 0 0 0 255; + text { + font: "Sans"; + text_source: "elm.text"; + size: 10; + min: 1 1; + align: 0.5 0.5; + text_class: "toolbar_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "label2_new"; + type: TEXT; + mouse_events: 0; + scale: 1; + clip_to: "elm.text_new.clipper"; + description { state: "default" 0.0; + align: 0.5 1.0; + fixed: 0 1; + rel1.to: "elm.text_new"; + rel2.to: "elm.text_new"; + color: 0 0 0 255; + text { + font: "Sans"; + text_source: "elm.text_new"; + size: 10; + min: 1 1; + align: 0.5 0.5; + text_class: "toolbar_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + image { + normal: "toolbar_sel.png"; + border: 3 3 0 0; + } + image.middle: SOLID; + fill.smooth: 0; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + clip_to: "elm.icon.clipper"; + description { state: "default" 0.0; + align: 0.5 0.5; + fixed: 0 0; + rel1 { + relative: 0.0 0.0; + offset: 2 2; + } + rel2 { + to_y: "elm.text"; + relative: 1.0 0.0; + offset: -3 -1; + } + color: 0 0 0 0; + } + } + part { name: "elm.swallow.icon_new"; + type: SWALLOW; + clip_to: "elm.icon_new.clipper"; + description { state: "default" 0.0; + align: 0.5 0.5; + fixed: 0 0; + rel1 { + relative: 0.0 0.0; + offset: 2 2; + } + rel2 { + to_y: "elm.text_new"; + relative: 1.0 0.0; + offset: -3 -1; + } + color: 0 0 0 0; + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + clip_to: "elm.text.clipper"; + description { state: "default" 0.0; + align: 0.5 1.0; + fixed: 0 1; + rel1 { + relative: 0.0 1.0; + offset: 0 -1; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -1; + } + visible: 0; + color: 224 224 224 255; + color3: 0 0 0 32; + text { + font: "Sans:style=Bold"; + size: 10; + min: 1 1; + align: 0.5 0.5; + text_class: "toolbar_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "elm.text_new"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + clip_to: "elm.text_new.clipper"; + scale: 1; + description { state: "default" 0.0; + align: 0.5 1.0; + fixed: 0 1; + rel1 { + relative: 0.0 1.0; + offset: 0 -1; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -1; + } + visible: 0; + color: 224 224 224 255; + color3: 0 0 0 32; + text { + font: "Sans:style=Bold"; + size: 10; + min: 1 1; + align: 0.5 0.5; + text_class: "toolbar_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "elm.text.clipper"; + type: RECT; + description { state: "default" 0.0; + color: 255 255 255 255; + } + description { state: "animation" 0.0; + color: 255 255 255 0; + } + } + part { name: "elm.text_new.clipper"; + type: RECT; + description { state: "default" 0.0; + color: 255 255 255 0; + } + description { state: "animation" 0.0; + color: 255 255 255 255; + } + } + part { name: "elm.icon.clipper"; + type: RECT; + description { state: "default" 0.0; + color: 255 255 255 255; + } + description { state: "animation" 0.0; + color: 255 255 255 0; + } + } + part { name: "elm.icon_new.clipper"; + type: RECT; + description { state: "default" 0.0; + color: 255 255 255 0; + } + description { state: "animation" 0.0; + color: 255 255 255 255; + } + } + part { name: "event"; + type: RECT; + mouse_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + } + programs { + program { name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "elm.text"; + target: "label2"; + target: "elm.text_new"; + target: "label2_new"; + transition: LINEAR 0.2; + } + program { name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "elm.text"; + target: "label2"; + target: "elm.text_new"; + target: "label2_new"; + transition: LINEAR 0.1; + } + program { name: "go"; + signal: "mouse,up,1"; + source: "event"; + action: SIGNAL_EMIT "elm,action,click" "elm"; + } + program { name: "mouse,in"; + signal: "mouse,in"; + source: "event"; + action: SIGNAL_EMIT "elm,mouse,in" "elm"; + } + program { name: "mouse,out"; + signal: "mouse,out"; + source: "event"; + action: SIGNAL_EMIT "elm,mouse,out" "elm"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "label2"; + target: "label2_new"; + target: "bg"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + { + set_state(PART:"elm.text", "disabled_visible", 0.0); + set_state(PART:"elm.text_new", "disabled_visible", 0.0); + } + else + { + set_state(PART:"elm.text", "disabled", 0.0); + set_state(PART:"elm.text_new", "disabled", 0.0); + } + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "label2"; + target: "label2_new"; + target: "bg"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + { + set_state(PART:"elm.text", "visible", 0.0); + set_state(PART:"elm.text_new", "visible", 0.0); + } + else + { + set_state(PART:"elm.text", "default", 0.0); + set_state(PART:"elm.text_new", "default", 0.0); + } + } + } + program { name: "label_set,animation,forward"; + signal: "elm,state,label_set,forward"; + source: "elm"; + after: "label_set,animation"; + } + program { name: "label_set,animation,backward"; + signal: "elm,state,label_set,backward"; + source: "elm"; + after: "label_set,animation"; + } + program { name: "label_set,animation"; + signal: "elm,state,label_set"; + source: "elm"; + action: STATE_SET "animation" 0.0; + target: "elm.text.clipper"; + target: "elm.text_new.clipper"; + transition: LINEAR 0.2; + after: "label_set,animation,done"; + } + program { name: "label_set,animation,done"; + action: SIGNAL_EMIT "elm,state,label_set,done" "elm"; + } + program { name: "label,reset"; + signal: "elm,state,label,reset"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text.clipper"; + target: "elm.text_new.clipper"; + } + program { name: "icon_set,animation,forward"; + signal: "elm,state,icon_set,forward"; + source: "elm"; + after: "icon_set,animation"; + } + program { name: "icon_set,animation,backward"; + signal: "elm,state,icon_set,backward"; + source: "elm"; + after: "icon_set,animation"; + } + program { name: "icon_set,animation"; + signal: "elm,state,icon_set"; + source: "elm"; + action: STATE_SET "animation" 0.0; + target: "elm.icon.clipper"; + target: "elm.icon_new.clipper"; + transition: LINEAR 0.2; + after: "icon_set,animation,done"; + } + program { name: "icon_set,animation,done"; + action: SIGNAL_EMIT "elm,state,icon_set,done" "elm"; + } + program { name: "icon,reset"; + signal: "elm,state,icon,reset"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.icon.clipper"; + target: "elm.icon_new.clipper"; + } + } + } + + group { name: "elm/toolbar/separator/default"; + images { + image: "toolbar_separator_v.png" COMP; + } + parts { + part { name: "separator"; // separator group + description { state: "default" 0.0; + min: 2 2; + max: 2 9999; + rel1.offset: 4 4; + rel2.offset: -5 -5; + image { + normal: "toolbar_separator_v.png"; + } + fill { + smooth: 0; + } + } + } + } + } + + /////////////////////////////////////////////////////////////////////////////// + group { name: "elm/notify/block_events/default"; + parts { + part { name: "block_events"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 64; + visible: 1; + } + } + } + programs { + program { + name: "block_clicked"; + signal: "mouse,clicked,1"; + source: "block_events"; + action: SIGNAL_EMIT "elm,action,clicked" "elm"; + } + } + } + group { name: "elm/notify/top/default"; + //this group is a design similar to the inwin group + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 0; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.offset: 10 10; + rel2.offset: -10 -10; + rel1.relative: 0.0 -1.0; + rel2.relative: 1.0 0.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 64; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + } + program { name: "show_2"; + signal: "show"; + action: STATE_SET "default" 0.0; + target: "base"; + after: "show_3"; + } + program { name: "show_3"; + signal: "show"; + action: STATE_SET "visible" 0.0; + target: "base"; + transition: LINEAR 0.5; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + } + } + group { name: "elm/notify/center/default"; + //this group is a design similar to the inwin group + images { + image: "bt_dis_base.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 0; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + program { name: "show_2"; + signal: "show"; + action: STATE_SET "default" 0.0; + target: "base"; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + } + } + group { name: "elm/notify/bottom/default"; + //this group is a design similar to the inwin group + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 0; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.offset: 10 10; + rel2.offset: -10 -10; + rel1.relative: 0.0 1.0; + rel2.relative: 1.0 2.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 64; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + } + program { name: "show_2"; + signal: "show"; + action: STATE_SET "default" 0.0; + target: "base"; + after: "show_3"; + } + program { name: "show_3"; + signal: "show"; + action: STATE_SET "visible" 0.0; + target: "base"; + transition: LINEAR 0.5; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + } + } + group { name: "elm/notify/left/default"; + //this group is a design similar to the inwin group + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 0; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.offset: 10 10; + rel2.offset: -10 -10; + rel1.relative: -1.0 0.0; + rel2.relative: 0.0 1.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 64; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + } + program { name: "show_2"; + signal: "show"; + action: STATE_SET "default" 0.0; + target: "base"; + after: "show_3"; + } + program { name: "show_3"; + signal: "show"; + action: STATE_SET "visible" 0.0; + target: "base"; + transition: LINEAR 0.5; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + } + } + group { name: "elm/notify/right/default"; + //this group is a design similar to the inwin group + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 0; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.offset: 10 10; + rel2.offset: -10 -10; + rel1.relative: 1.0 0.0; + rel2.relative: 2.0 1.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 64; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + } + program { name: "show_2"; + signal: "show"; + action: STATE_SET "default" 0.0; + target: "base"; + after: "show_3"; + } + program { name: "show_3"; + signal: "show"; + action: STATE_SET "visible" 0.0; + target: "base"; + transition: LINEAR 0.5; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + } + } + group { name: "elm/notify/top_left/default"; + //this group is a design similar to the inwin group + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 0; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.offset: 10 10; + rel2.offset: -10 -10; + rel1.relative: 0.0 -1.0; + rel2.relative: 1.0 0.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 64; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + } + program { name: "show_2"; + signal: "show"; + action: STATE_SET "default" 0.0; + target: "base"; + after: "show_3"; + } + program { name: "show_3"; + signal: "show"; + action: STATE_SET "visible" 0.0; + target: "base"; + transition: LINEAR 0.5; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + } + } + group { name: "elm/notify/top_right/default"; + //this group is a design similar to the inwin group + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 0; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.offset: 10 10; + rel2.offset: -10 -10; + rel1.relative: 0.0 -1.0; + rel2.relative: 1.0 0.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 64; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + } + program { name: "show_2"; + signal: "show"; + action: STATE_SET "default" 0.0; + target: "base"; + after: "show_3"; + } + program { name: "show_3"; + signal: "show"; + action: STATE_SET "visible" 0.0; + target: "base"; + transition: LINEAR 0.5; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + } + } + group { name: "elm/notify/bottom_left/default"; + //this group is a design similar to the inwin group + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 0; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.offset: 10 10; + rel2.offset: -10 -10; + rel1.relative: 0.0 1.0; + rel2.relative: 1.0 2.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 64; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + } + program { name: "show_2"; + signal: "show"; + action: STATE_SET "default" 0.0; + target: "base"; + after: "show_3"; + } + program { name: "show_3"; + signal: "show"; + action: STATE_SET "visible" 0.0; + target: "base"; + transition: LINEAR 0.5; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + } + } + group { name: "elm/notify/bottom_right/default"; + //this group is a design similar to the inwin group + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 0; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + rel1.offset: 10 10; + rel2.offset: -10 -10; + rel1.relative: 0.0 1.0; + rel2.relative: 1.0 2.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 64; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + } + program { name: "show_2"; + signal: "show"; + action: STATE_SET "default" 0.0; + target: "base"; + after: "show_3"; + } + program { name: "show_3"; + signal: "show"; + action: STATE_SET "visible" 0.0; + target: "base"; + transition: LINEAR 0.5; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/slideshow/base/default"; + data { + item: transitions "fade black_fade horizontal vertical square"; + item: layouts "fullscreen not_fullscreen"; + } + parts { + part { name: "whole"; + type: RECT; + description { + state: "default" 0.0; + visible: 1; + color: 20 20 20 255; + } + } + part { name: "image_1_whole"; + description { + state: "default" 0.0; + color: 255 255 255 255; + } + description { + state: "fade_prev_next" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + } + description { + state: "black_fade_prev_next_init" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { + state: "black_fade_prev_next" 0.0; + inherit: "default" 0.0; + color: 0 0 0 255; + } + description { + state: "horizontal_next_init" 0.0; + inherit: "default" 0.0; + } + description { + state: "horizontal_next" 0.0; + inherit: "default" 0.0; + rel1.relative: -1.0 0.0; + rel2.relative: 0.0 1.0; + } + description { + state: "horizontal_prev_init" 0.0; + inherit: "default" 0.0; + } + description { + state: "horizontal_prev" 0.0; + inherit: "default" 0.0; + rel1.relative: 1.0 0.0; + rel2.relative: 2.0 1.0; + } + description { + state: "vertical_next_init" 0.0; + inherit: "default" 0.0; + } + description { + state: "vertical_next" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 -1.0; + rel2.relative: 1.0 0.0; + } + description { + state: "vertical_prev_init" 0.0; + inherit: "default" 0.0; + } + description { + state: "vertical_prev" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 1.0; + rel2.relative: 1.0 2.0; + } + description { + state: "square_prev_next" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + } + } + part { name: "image_2_whole"; + description { + state: "default" 0.0; + visible: 1; + color: 255 255 255 0; + } + description { + state: "fade_prev_next" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { + state: "black_fade_prev_next_init" 0.0; + inherit: "default" 0.0; + color: 0 0 0 0; + } + description { + state: "black_fade_prev_next" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { + state: "horizontal_next_init" 0.0; + inherit: "default" 0.0; + rel1.relative: 1.0 0.0; + rel2.relative: 2.0 1.0; + color: 255 255 255 255; + } + description { + state: "horizontal_next" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { + state: "horizontal_prev_init" 0.0; + inherit: "default" 0.0; + rel1.relative: -1.0 0.0; + rel2.relative: 0.0 1.0; + color: 255 255 255 255; + } + description { + state: "horizontal_prev" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { + state: "vertical_next_init" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 1.0; + rel2.relative: 1.0 2.0; + color: 255 255 255 255; + } + description { + state: "vertical_next" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { + state: "vertical_prev_init" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 -1.0; + rel2.relative: 1.0 0.0; + color: 255 255 255 255; + } + description { + state: "vertical_prev" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + description { + state: "square_prev_next_init" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.5 0.5; + rel2.relative: 0.5 0.5; + color: 255 255 255 255; + } + description { + state: "square_prev_next" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + color: 255 255 255 255; + } + } + part { name: "elm.swallow.1"; + type: SWALLOW; + clip_to: "image_1_whole"; + description { + state: "default" 0.0; + rel1.to: "image_1_whole"; + rel2.to: "image_1_whole"; + color: 255 255 255 255; + } + description { + state: "not_fullscreen" 0.0; + rel1.relative: 0.1 0.1; + rel1.to: "image_1_whole"; + rel2.relative: 0.9 0.9; + rel2.to: "image_1_whole"; + color: 255 255 255 255; + } + } + part { name: "elm.swallow.2"; + type: SWALLOW; + clip_to: "image_2_whole"; + description { + state: "default" 0.0; + color: 255 255 255 255; + rel1.to: "image_2_whole"; + rel2.to: "image_2_whole"; + } + description { + state: "not_fullscreen" 0.0; + color: 255 255 255 255; + rel1.relative: 0.1 0.1; + rel1.to: "image_2_whole"; + rel2.relative: 0.9 0.9; + rel2.to: "image_2_whole"; + } + } + part { name: "events_catcher"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + visible: 1; + color: 0 0 0 0; + } + } + } + programs { + //Substyle + program { name: "layout_fullscreen"; + signal: "layout,fullscreen"; + source: "slideshow"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.1"; + target: "elm.swallow.2"; + transition: SINUSOIDAL 1.0; + } + program { name: "layout_not_fullscreen"; + signal: "layout,not_fullscreen"; + source: "slideshow"; + action: STATE_SET "not_fullscreen" 0.0; + target: "elm.swallow.1"; + target: "elm.swallow.2"; + transition: SINUSOIDAL 1.0; + } + // + program { name: "fade_next"; + signal: "fade,next"; + source: "slideshow"; + action: STATE_SET "default" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + after: "fade_next_2"; + } + program { name: "fade_next_2"; + action: STATE_SET "fade_prev_next" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + transition: SINUSOIDAL 1.5; + after: "end"; + } + program { name: "fade_previous"; + signal: "fade,previous"; + source: "slideshow"; + action: STATE_SET "default" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + after: "fade_previous_2"; + } + program { name: "fade_previous_2"; + action: STATE_SET "fade_prev_next" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + transition: SINUSOIDAL 1.5; + after: "end"; + } + program { name: "black_fade_next"; + signal: "black_fade,next"; + source: "slideshow"; + action: STATE_SET "black_fade_prev_next_init" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + after: "black_fade_next_2"; + } + program { name: "black_fade_next_2"; + action: STATE_SET "black_fade_prev_next" 0.0; + target: "image_1_whole"; + transition: SINUSOIDAL 0.75; + after: "black_fade_next_3"; + } + program { name: "black_fade_next_3"; + action: STATE_SET "black_fade_prev_next" 0.0; + target: "image_2_whole"; + transition: SINUSOIDAL 0.75; + after: "end"; + } + program { name: "black_fade_previous"; + signal: "black_fade,previous"; + source: "slideshow"; + action: STATE_SET "black_fade_prev_next_init" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + after: "black_fade_previous_2"; + } + program { name: "black_fade_previous_2"; + action: STATE_SET "black_fade_prev_next" 0.0; + target: "image_1_whole"; + transition: SINUSOIDAL 0.75; + after: "black_fade_previous_3"; + } + program { name: "black_fade_previous_3"; + action: STATE_SET "black_fade_prev_next" 0.0; + target: "image_2_whole"; + transition: SINUSOIDAL 0.75; + after: "end"; + } + program { name: "horizontal_next"; + signal: "horizontal,next"; + source: "slideshow"; + action: STATE_SET "horizontal_next_init" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + after: "horizontal_next_2"; + } + program { name: "horizontal_next_2"; + action: STATE_SET "horizontal_next" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + transition: SINUSOIDAL 1.5; + after: "end"; + } + program { name: "horizontal_previous"; + signal: "horizontal,previous"; + source: "slideshow"; + action: STATE_SET "horizontal_prev_init" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + after: "horizontal_previous_2"; + } + program { name: "horizontal_previous_2"; + action: STATE_SET "horizontal_prev" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + transition: SINUSOIDAL 1.5; + after: "end"; + } + program { name: "vertical_next"; + signal: "vertical,next"; + source: "slideshow"; + action: STATE_SET "vertical_next_init" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + after: "vertical_next_2"; + } + program { name: "vertical_next_2"; + action: STATE_SET "vertical_next" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + transition: SINUSOIDAL 1.5; + after: "end"; + } + program { name: "vertical_previous"; + signal: "vertical,previous"; + source: "slideshow"; + action: STATE_SET "vertical_prev_init" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + after: "vertical_previous_2"; + } + program { name: "vertical_previous_2"; + action: STATE_SET "vertical_prev" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + transition: SINUSOIDAL 1.5; + after: "end"; + } + program { name: "square_next"; + signal: "square,next"; + source: "slideshow"; + action: STATE_SET "square_prev_next_init" 0.0; + target: "image_2_whole"; + after: "square_next_2"; + } + program { name: "square_next_2"; + action: STATE_SET "square_prev_next" 0.0; + target: "image_2_whole"; + target: "image_1_whole"; + transition: SINUSOIDAL 1.5; + after: "end"; + } + program { name: "square_previous"; + signal: "square,previous"; + source: "slideshow"; + action: STATE_SET "square_prev_next_init" 0.0; + target: "image_2_whole"; + after: "square_next_2"; + } + program { name: "end"; + action: SIGNAL_EMIT "end" "slideshow"; + } + program { name: "end_signal"; + signal: "anim,end"; + source: "slideshow"; + action: STATE_SET "default" 0.0; + target: "image_1_whole"; + target: "image_2_whole"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/win/inwin/default"; + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 1.0; + color: 0 0 0 64; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.relative: 0.1 0.1; + rel2.relative: 0.9 0.9; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + } + } + + group { name: "elm/win/inwin/minimal"; + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 1.0; + color: 0 0 0 64; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 1; + rel1.relative: 0.5 0.5; + rel2.relative: 0.5 0.5; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + } + } + + group { name: "elm/win/inwin/minimal_vertical"; + images { + image: "shad_circ.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + } + parts { + part { name: "base"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + description { state: "visible" 0.0; + inherit: "default" 1.0; + color: 0 0 0 64; + } + } + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "shad_circ.png"; + rel1.to: "elm.swallow.content"; + rel1.offset: -64 -64; + rel2.to: "elm.swallow.content"; + rel2.offset: 63 63; + fill.smooth: 0; + } + } + part { name: "pop"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.swallow.content"; + rel1.offset: -5 -5; + rel2.to: "elm.swallow.content"; + rel2.offset: 4 4; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + image.middle: SOLID; + } + } + part { name: "popover"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "pop"; + rel2.to: "pop"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 1; + rel1.relative: 0.1 0.5; + rel2.relative: 0.9 0.5; + } + } + } + programs { + program { name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "visible" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + program { name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; +// transition: DECELERATE 0.5; + target: "base"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/list/item/default"; + data.item: "stacking" "above"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + } + programs { + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + } + } + group { name: "elm/list/item_odd/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { + name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { + name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { + name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + } + programs { + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + } + } + group { name: "elm/list/item_compress/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + align: 0.0 0.0; + min: 0 10; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { + name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + } + programs { + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + } + } + group { name: "elm/list/item_compress_odd/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { + name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + } + programs { + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/list/h_item/default"; + data.item: "stacking" "above"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1_h.png" COMP; + image: "ilist_item_shadow_h.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 10 0; + fixed: 1 1; + rel1 { + to: "base"; + relative: 1.0 0.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: 0 -1; + } + image { + normal: "ilist_item_shadow_h.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1_h.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 0.0; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.0; + offset: -5 4; + } + } + } + part { name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 1.0; + rel1 { + relative: 0.0 1.0; + offset: 4 -5; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + fixed: 0 1; + rel1 { + to_x: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 4 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 1.0 0.0; + offset: -5 -1; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; + align: 0.5 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + } + programs { + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + } + } + group { name: "elm/list/h_item_odd/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2_h.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2_h.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { + name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 0.0; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.0; + offset: -5 4; + } + } + } + part { + name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 1.0; + rel1 { + relative: 0.0 1.0; + offset: 4 -5; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + fixed: 1 1; + rel1 { + to_x: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 4 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 1.0 0.0; + offset: -5 -1; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; + align: 0.5 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + } + programs { + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + } + } + group { name: "elm/list/h_item_compress/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1_h.png" COMP; + image: "ilist_item_shadow_h.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + align: 0.0 0.0; + min: 10 0; + rel1 { + to: "base"; + relative: 1.0 0.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: 0 -1; + } + image { + normal: "ilist_item_shadow_h.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1_h.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 0.0; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.0; + offset: -5 4; + } + } + } + part { name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 1.0; + rel1 { + relative: 0.0 1.0; + offset: 4 -5; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { + name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + fixed: 1 1; + rel1 { + to_x: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 4 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 1.0 0.0; + offset: -5 -1; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; + align: 0.5 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + } + programs { + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + } + } + group { name: "elm/list/h_item_compress_odd/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2_h.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2_h.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 0.0; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.0; + offset: -5 4; + } + } + } + part { name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 1.0; + rel1 { + relative: 0.0 1.0; + offset: 4 -5; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + fixed: 1 1; + rel1 { + to_x: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 4 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 1.0 0.0; + offset: -5 -1; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; + align: 0.5 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + } + programs { + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/slider/horizontal/default"; + alias: "elm/slider/horizontal/disabled"; + images { + image: "sl_bg.png" COMP; + image: "sl_bg_over.png" COMP; + image: "sl_bt_0.png" COMP; + image: "sl_bt_1.png" COMP; + image: "sl_bt_2.png" COMP; + image: "sl_bt_3.png" COMP; + image: "sl_bt2_0_0.png" COMP; + image: "sl_bt2_0_1.png" COMP; + image: "sl_bt2_0_2.png" COMP; + image: "sl_bt2_1.png" COMP; + image: "sl_bt2_2.png" COMP; + image: "sl_units.png" COMP; + } + script { + public value_hide = 0; + public set_value_show() { + set_int(value_hide, 0); + } + public set_value_hide() { + set_int(value_hide, 1); + } + public thumb_down() { + if (get_int(value_hide) == 1) { + set_state(PART:"elm.indicator", "default", 0.0); + set_state(PART:"button3", "default", 0.0); + set_state(PART:"button4", "default", 0.0); + set_state(PART:"button5", "default", 0.0); + set_state(PART:"button6", "default", 0.0); + set_state(PART:"button7", "default", 0.0); + } else { + set_state(PART:"elm.indicator", "visible", 0.0); + set_state(PART:"button3", "visible", 0.0); + set_state(PART:"button4", "visible", 0.0); + set_state(PART:"button5", "visible", 0.0); + set_state(PART:"button6", "visible", 0.0); + set_state(PART:"button7", "visible", 0.0); + } + } + public thumb_up() { + set_state(PART:"elm.indicator", "default", 0.0); + set_state(PART:"button3", "default", 0.0); + set_state(PART:"button4", "default", 0.0); + set_state(PART:"button5", "default", 0.0); + set_state(PART:"button6", "default", 0.0); + set_state(PART:"button7", "default", 0.0); + } + } + parts { + part { name: "base"; + mouse_events: 0; + description { state: "default" 0.0; + max: 99999 6; + min: 0 6; + rel1 { to: "bg"; + offset: 1 0; + } + rel2 { to: "bg"; + offset: -2 -1; + } + image.normal: "sl_bg.png"; + fill.smooth: 0; + } + } + part { name: "level"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + rel1.to: "base"; + rel2 { + to_y: "base"; + to_x: "elm.dragable.slider"; + relative: 0.5 1.0; + } + color: 255 0 0 200; + } + description { state: "inverted" 0.0; + inherit: "default" 0.0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 0 0 100; + } + description { state: "disabled_inverted" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "level2"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + rel1 { + to_y: "base"; + to_x: "elm.dragable.slider"; + relative: 0.5 0.0; + } + rel2.to: "base"; + color: 255 0 0 200; + } + description { state: "inverted" 0.0; + inherit: "default" 0.0; + visible: 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + } + description { state: "disabled_inverted" 0.0; + inherit: "default" 0.0; + color: 255 0 0 100; + visible: 1; + } + } + part { + name: "base_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "base"; + rel1.offset: -1 -1; + rel2.to: "base"; + rel2.offset: 0 0; + image { + normal: "sl_bg_over.png"; + border: 3 3 3 3; + } + fill.smooth: 0; + } + } + part { name: "bg"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to: "elm.swallow.bar"; + rel2.to: "elm.swallow.bar"; + color: 0 0 0 0; + } + } + part { name: "elm.swallow.bar"; + type: SWALLOW; + scale: 1; + description { state: "default" 0.0; + min: 48 24; + max: 99999 24; + align: 1.0 0.5; + rel1 { + to_x: "elm.text"; + relative: 1.0 0.0; + offset: 8 0; + } + rel2 { + to_x: "elm.units"; + relative: 0.0 1.0; + offset: -10 -1; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 0; + align: 0.0 0.5; + rel1 { + offset: 4 0; + to_y: "elm.swallow.bar"; + } + rel2 { + offset: 3 -1; + relative: 0.0 1.0; + to_y: "elm.swallow.bar"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel2.offset: 4 -1; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 0.0 0.5; + rel1.to_x: "elm.swallow.icon"; + rel1.relative: 1.0 0.0; + rel1.offset: -1 4; + rel2.to_x: "elm.swallow.icon"; + rel2.relative: 1.0 1.0; + rel2.offset: -1 -5; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.0 0.5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + rel1.offset: 0 4; + rel2.offset: 0 -5; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 128 128 128; + visible: 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { + name: "elm.swallow.end"; + type: SWALLOW; + description { + state: "default" 0.0; + visible: 0; + align: 1.0 0.5; + rel1 { + offset: -4 0; + relative: 1.0 0.0; + to_y: "elm.swallow.bar"; + } + rel2 { + offset: -3 -1; + to_y: "elm.swallow.bar"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel2.offset: -4 -1; + } + } + part { name: "units"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1 { + to_x: "elm.units"; + offset: 0 5; + } + rel2 { + to_x: "elm.units"; + offset: 5 -3; + } + image { + normal: "sl_units.png"; + border: 0 5 3 8; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.units"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 1.0 0.5; + rel1.to_x: "elm.swallow.end"; + rel1.relative: 0.0 0.0; + rel1.offset: 0 8; + rel2.to_x: "elm.swallow.end"; + rel2.relative: 0.0 1.0; + rel2.offset: 0 -9; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.0 0.5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + fixed: 1 1; + visible: 1; + text.min: 1 1; + rel1.offset: -5 0; + rel2.offset: -5 -1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 128 128 128; + visible: 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "elm.dragable.slider"; + type: RECT; + mouse_events: 0; + scale: 1; + dragable { + x: 1 1 0; + y: 0 0 0; + confine: "bg"; + } + description { state: "default" 0.0; + min: 0 24; + max: 0 24; + fixed: 1 1; + rel1 { + relative: 0.5 0.0; + to_x: "bg"; + } + rel2 { + relative: 0.5 1.0; + to_x: "bg"; + } + color: 255 0 0 100; + } + } + part { name: "button_events"; + type: RECT; + dragable { + events: "elm.dragable.slider"; + } + mouse_events: 1; + description { state: "default" 0.0; + fixed: 1 1; + min: 16 16; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1.to_x: "elm.dragable.slider"; + rel2.to_x: "elm.dragable.slider"; + color: 0 0 0 0; + } + } + part { name: "button0"; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + max: 17 999; + min: 17 24; + rel1.to: "elm.dragable.slider"; + rel2.to: "elm.dragable.slider"; + image { + normal: "sl_bt_0.png"; + border: 5 5 5 10; + } + fill.smooth: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "sl_bt_3.png"; + border: 5 5 5 10; + } + } + } + part { name: "button1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button0"; + rel2 { + to: "button0"; + relative: 1.0 0.5; + offset: -1 -5; + } + image { + normal: "sl_bt_1.png"; + border: 5 5 5 0; + } + } + } + part { name: "button2"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button0"; + rel2.to: "button0"; + image { + normal: "sl_bt_2.png"; + border: 5 5 5 10; + } + fill.smooth: 0; + } + } + part { name: "button3"; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 8 32; + align: 1.0 0.5; + rel1 { + to_x: "elm.indicator"; + to_y: "button4"; + relative: 0.0 0.0; + offset: -7 0; + } + rel2 { + to: "button4"; + relative: 0.0 1.0; + offset: -1 -1; + } + image { + normal: "sl_bt2_0_0.png"; + border: 6 0 6 12; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "button4"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + max: 15 999; + min: 15 32; + rel1 { + to_x: "button0"; + to_y: "elm.indicator"; + offset: 0 0; + } + rel2.to: "button0"; + image { + normal: "sl_bt2_0_1.png"; + border: 0 0 6 12; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "button5"; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 8 32; + align: 0.0 0.5; + rel1 { + to: "button4"; + relative: 1.0 0.0; + offset: 0 0; + } + rel2 { + to_x: "elm.indicator"; + to_y: "button4"; + relative: 1.0 1.0; + offset: 6 -1; + } + image { + normal: "sl_bt2_0_2.png"; + border: 0 6 6 12; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.indicator"; + type: TEXT; + mouse_events: 0; + effect: SOFT_SHADOW; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 0.5 1.0; + rel1 { + to: "button0"; + relative: 0.0 -0.25; + offset: 0 0; + } + rel2 { + to_x: "button0"; + relative: 1.0 -0.25; + offset: -1 0; + } + color: 224 224 224 255; + color3: 0 0 0 64; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + rel1.offset: 0 -1; + rel2.offset: -1 -1; + } + } + part { name: "button6"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1.to: "button3"; + rel2 { + to: "button5"; + relative: 1.0 0.3; + offset: -1 -1; + } + image { + normal: "sl_bt2_1.png"; + border: 5 5 5 0; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "button7"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1.to: "button3"; + rel2.to: "button5"; + image { + normal: "sl_bt2_2.png"; + border: 5 5 5 0; + middle: 0; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.icon"; + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.icon"; + } + program { name: "end_show"; + signal: "elm,state,end,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.end"; + } + program { name: "end_hide"; + signal: "elm,state,end,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.end"; + } + program { name: "units_show"; + signal: "elm,state,units,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.units"; + target: "units"; + } + program { name: "units_hide"; + signal: "elm,state,units,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.units"; + target: "units"; + } + program { name: "invert_on"; + signal: "elm,state,inverted,on"; + source: "elm"; + action: STATE_SET "inverted" 0.0; + target: "level"; + target: "level2"; + } + program { name: "invert_off"; + signal: "elm,state,inverted,off"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "level"; + target: "level2"; + } + program { name: "set_val_show"; + signal: "elm,state,val,show"; + source: "elm"; + script { + set_value_show(); + } + } + program { name: "set_val_hide"; + signal: "elm,state,val,hide"; + source: "elm"; + script { + set_value_hide(); + } + } + program { name: "val_show"; + signal: "mouse,down,*"; + source: "elm.dragable.slider"; + script { + thumb_down(); + } + + } + program { name: "val_hide"; + signal: "mouse,up,*"; + source: "elm.dragable.slider"; + script { + thumb_up(); + } + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "button0"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + + get_state(PART:"elm.units", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.units", "disabled_visible", 0.0); + else + set_state(PART:"elm.units", "disabled", 0.0); + + get_state(PART:"level2", st, 30, vl); + if (!strcmp(st, "inverted")) + { + set_state(PART:"level", "disabled_inverted", 0.0); + set_state(PART:"level2", "disabled_inverted", 0.0); + } + else + { + set_state(PART:"level", "disabled", 0.0); + set_state(PART:"level2", "disabled", 0.0); + } + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "button0"; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.text", "visible", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + + get_state(PART:"elm.units", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.units", "visible", 0.0); + else + set_state(PART:"elm.units", "default", 0.0); + + get_state(PART:"level2", st, 30, vl); + if (!strcmp(st, "disabled_inverted")) + { + set_state(PART:"level", "inverted", 0.0); + set_state(PART:"level2", "inverted", 0.0); + } + else + { + set_state(PART:"level", "default", 0.0); + set_state(PART:"level2", "default", 0.0); + } + } + } + } + } + + group { name: "elm/slider/vertical/default"; + images { + image: "slv_bg.png" COMP; + image: "slv_bg_over.png" COMP; + + image: "sl_bt_0.png" COMP; + image: "sl_bt_1.png" COMP; + image: "sl_bt_2.png" COMP; + image: "sl_bt_3.png" COMP; + image: "sl_bt2_0_0.png" COMP; + image: "sl_bt2_0_1.png" COMP; + image: "sl_bt2_0_2.png" COMP; + image: "sl_bt2_1.png" COMP; + image: "sl_bt2_2.png" COMP; + + image: "slv_units.png" COMP; + } + script { + public value_hide = 0; + public set_value_show() { + set_int(value_hide, 0); + } + public set_value_hide() { + set_int(value_hide, 1); + } + public thumb_down() { + if (get_int(value_hide) == 1) { + set_state(PART:"elm.indicator", "default", 0.0); + set_state(PART:"button3", "default", 0.0); + set_state(PART:"button4", "default", 0.0); + set_state(PART:"button5", "default", 0.0); + set_state(PART:"button6", "default", 0.0); + set_state(PART:"button7", "default", 0.0); + } else { + set_state(PART:"elm.indicator", "visible", 0.0); + set_state(PART:"button3", "visible", 0.0); + set_state(PART:"button4", "visible", 0.0); + set_state(PART:"button5", "visible", 0.0); + set_state(PART:"button6", "visible", 0.0); + set_state(PART:"button7", "visible", 0.0); + } + } + public thumb_up() { + set_state(PART:"elm.indicator", "default", 0.0); + set_state(PART:"button3", "default", 0.0); + set_state(PART:"button4", "default", 0.0); + set_state(PART:"button5", "default", 0.0); + set_state(PART:"button6", "default", 0.0); + set_state(PART:"button7", "default", 0.0); + } + } + parts { + part { name: "base"; + mouse_events: 0; + description { state: "default" 0.0; + max: 6 99999; + min: 6 0; + rel1 { to: "bg"; + offset: 1 0; + } + rel2 { to: "bg"; + offset: -2 -1; + } + image.normal: "slv_bg.png"; + fill.smooth: 0; + } + } + part { name: "level"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + rel1.to: "base"; + rel2 { + to_x: "base"; + to_y: "elm.dragable.slider"; + relative: 1.0 0.5; + } + color: 255 0 0 200; + } + description { state: "inverted" 0.0; + inherit: "default" 0.0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 0 0 100; + } + description { state: "disabled_inverted" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "level2"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + rel1 { + to_x: "base"; + to_y: "elm.dragable.slider"; + relative: 0.0 0.5; + } + rel2.to: "base"; + color: 255 0 0 200; + } + description { state: "inverted" 0.0; + inherit: "default" 0.0; + visible: 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 0 0 100; + } + description { state: "disabled_inverted" 0.0; + inherit: "default" 0.0; + color: 255 0 0 100; + visible: 1; + } + } + part { + name: "base_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "base"; + rel1.offset: -1 -1; + rel2.to: "base"; + rel2.offset: 0 0; + image { + normal: "slv_bg_over.png"; + border: 3 3 3 3; + } + fill.smooth: 0; + } + } + part { name: "bg"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to: "elm.swallow.bar"; + rel2.to: "elm.swallow.bar"; + color: 0 0 0 0; + } + } + part { name: "elm.swallow.bar"; + type: SWALLOW; + scale: 1; + description { state: "default" 0.0; + min: 24 48; + max: 24 9999; + align: 0.5 1.0; + rel1 { + to_y: "elm.text"; + relative: 0.0 1.0; + offset: 0 10; + } + rel2 { + to_y: "elm.units"; + relative: 1.0 0.0; + offset: -1 -8; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 0; + align: 0.5 0.0; + rel1 { + offset: 0 4; + to_x: "elm.swallow.bar"; + } + rel2 { + offset: -1 3; + relative: 1.0 0.0; + to_x: "elm.swallow.bar"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: HORIZONTAL; + rel2.offset: -1 4; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 0 1; + align: 0.5 0.0; + rel1.to_y: "elm.swallow.icon"; + rel1.relative: 0.0 1.0; + rel1.offset: 0 -1; + rel2.to_y: "elm.swallow.icon"; + rel2.relative: 1.0 1.0; + rel2.offset: -1 -1; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.0; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + rel1.offset: 4 0; + rel2.offset: -5 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 128 128 128; + visible: 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { + name: "elm.swallow.end"; + type: SWALLOW; + description { + state: "default" 0.0; + visible: 0; + align: 0.5 1.0; + rel1 { + offset: 0 -4; + relative: 0.0 1.0; + to_x: "elm.swallow.bar"; + } + rel2 { + offset: -1 -3; + to_x: "elm.swallow.bar"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: HORIZONTAL; + rel2.offset: -1 -4; + } + } + part { name: "units"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1 { + to: "elm.units"; + offset: -8 0; + } + rel2 { + to: "elm.units"; + offset: 7 8; + } + image { + normal: "slv_units.png"; + border: 8 8 0 9; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.units"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 0.5 1.0; + rel1.relative: 0.0 0.0; + rel1.to_y: "elm.swallow.end"; + rel1.offset: 8 0; + rel2.relative: 1.0 0.0; + rel2.to_y: "elm.swallow.end"; + rel2.offset: -9 0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.0; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + fixed: 1 1; + visible: 1; + text.min: 1 1; + rel1.offset: 8 -9; + rel2.offset: -9 -9; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + fixed: 1 1; + visible: 1; + text.min: 1 1; + rel1.offset: 8 -9; + rel2.offset: -9 -9; + color: 0 0 0 128; + color3: 0 0 0 0; + } + } + part { name: "elm.dragable.slider"; + type: RECT; + mouse_events: 0; + scale: 1; + dragable { + x: 0 0 0; + y: 1 1 0; + confine: "bg"; + } + description { state: "default" 0.0; + min: 24 0; + max: 24 0; + fixed: 1 1; + rel1 { + relative: 0.5 0.0; + to_y: "bg"; + } + rel2 { + relative: 0.5 1.0; + to_y: "bg"; + } + color: 0 0 0 0; + } + } + part { name: "button_events"; + type: RECT; + dragable { + events: "elm.dragable.slider"; + } + mouse_events: 1; + description { state: "default" 0.0; + fixed: 1 1; + min: 16 16; + aspect: 1.0 1.0; + aspect_preference: HORIZONTAL; + rel1.to_y: "elm.dragable.slider"; + rel2.to_y: "elm.dragable.slider"; + color: 0 0 0 0; + } + } + part { name: "button0"; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + max: 17 999; + min: 17 24; + rel1.to: "elm.dragable.slider"; + rel2.to: "elm.dragable.slider"; + image { + normal: "sl_bt_0.png"; + border: 5 5 5 10; + } + fill.smooth: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "sl_bt_3.png"; + border: 5 5 5 10; + } + } + } + part { name: "button1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button0"; + rel2 { + to: "button0"; + relative: 1.0 0.5; + offset: -1 -5; + } + image { + normal: "sl_bt_1.png"; + border: 5 5 5 0; + } + } + } + part { name: "button2"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button0"; + rel2.to: "button0"; + image { + normal: "sl_bt_2.png"; + border: 5 5 5 10; + } + fill.smooth: 0; + } + } + part { name: "button3"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + min: 8 32; + align: 1.0 0.5; + rel1 { + to_x: "elm.indicator"; + to_y: "button4"; + relative: 0.0 0.0; + offset: -7 0; + } + rel2 { + to: "button4"; + relative: 0.0 1.0; + offset: -1 -1; + } + image { + normal: "sl_bt2_0_0.png"; + border: 6 0 6 12; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "button4"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + max: 15 999; + min: 15 32; + fixed: 1 1; + rel1 { + to_x: "button0"; + to_y: "elm.indicator"; + offset: 0 -7; + } + rel2.to: "button0"; + image { + normal: "sl_bt2_0_1.png"; + border: 0 0 6 12; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "button5"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + min: 8 32; + align: 0.0 0.5; + rel1 { + to: "button4"; + relative: 1.0 0.0; + offset: 0 0; + } + rel2 { + to_x: "elm.indicator"; + to_y: "button4"; + relative: 1.0 1.0; + offset: 6 -1; + } + image { + normal: "sl_bt2_0_2.png"; + border: 0 6 6 12; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.indicator"; + type: TEXT; + mouse_events: 0; + effect: SOFT_SHADOW; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 0.5 1.0; + rel1 { + to: "button0"; + relative: 0.0 -1.0; + offset: 0 0; + } + rel2 { + to: "button0"; + relative: 1.0 -1.0; + offset: -1 0; + } + color: 224 224 224 255; + color3: 0 0 0 64; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + rel1.offset: 0 -1; + rel2.offset: -1 -1; + } + } + part { name: "button6"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1.to: "button3"; + rel2 { + to: "button5"; + relative: 1.0 0.3; + offset: -1 -1; + } + image { + normal: "sl_bt2_1.png"; + border: 5 5 5 0; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "button7"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1.to: "button3"; + rel2.to: "button5"; + image { + normal: "sl_bt2_2.png"; + border: 5 5 5 0; + middle: 0; + } + fill.smooth: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + + programs { + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.icon"; + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.icon"; + } + program { name: "end_show"; + signal: "elm,state,end,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.end"; + } + program { name: "end_hide"; + signal: "elm,state,end,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.end"; + } + program { name: "units_show"; + signal: "elm,state,units,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.units"; + target: "units"; + } + program { name: "units_hide"; + signal: "elm,state,units,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.units"; + target: "units"; + } + program { name: "invert_on"; + signal: "elm,state,inverted,on"; + source: "elm"; + action: STATE_SET "inverted" 0.0; + target: "level"; + target: "level2"; + } + program { name: "invert_off"; + signal: "elm,state,inverted,off"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "level"; + target: "level2"; + } + program { name: "set_val_show"; + signal: "elm,state,val,show"; + source: "elm"; + script { + set_value_show(); + } + } + program { name: "set_val_hide"; + signal: "elm,state,val,hide"; + source: "elm"; + script { + set_value_hide(); + } + } + program { name: "val_show"; + signal: "mouse,down,*"; + source: "elm.dragable.slider"; + script { + thumb_down(); + } + } + program { name: "val_hide"; + signal: "mouse,up,*"; + source: "elm.dragable.slider"; + script { + thumb_up(); + } + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "button0"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + + get_state(PART:"elm.units", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.units", "disabled_visible", 0.0); + else + set_state(PART:"elm.units", "disabled", 0.0); + + get_state(PART:"level2", st, 30, vl); + if (!strcmp(st, "inverted")) + { + set_state(PART:"level", "disabled_inverted", 0.0); + set_state(PART:"level2", "disabled_inverted", 0.0); + } + else + { + set_state(PART:"level", "disabled", 0.0); + set_state(PART:"level2", "disabled", 0.0); + } + } + } + + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "button0"; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.text", "visible", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + + get_state(PART:"elm.units", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.units", "visible", 0.0); + else + set_state(PART:"elm.units", "default", 0.0); + + get_state(PART:"level2", st, 30, vl); + if (!strcmp(st, "disabled_inverted")) + { + set_state(PART:"level", "inverted", 0.0); + set_state(PART:"level2", "inverted", 0.0); + } + else + { + set_state(PART:"level", "default", 0.0); + set_state(PART:"level2", "default", 0.0); + } + } + } + } + } + +//////////////////////////////////////////////////////////////////////////////// +// actionslider +//////////////////////////////////////////////////////////////////////////////// + group { name: "elm/actionslider/base/default"; + + images { + image: "shelf_inset.png" COMP; + image: "ilist_1.png" COMP; + image: "bt_bases.png" COMP; + image: "bt_basew.png" COMP; + image: "bt_hilightw.png" COMP; + } + + parts { + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + min: 75 25; + rel1.offset: 1 1; + rel2.offset: -2 -2; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "conf_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "icon.dragable.area"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1.to: "base"; + rel2.to: "base"; + } + } + part { name: "elm.text.left"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + align: 0.05 0.5; + min: 1 1; + } + } + } + part { name: "elm.text.center"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + align: 0.5 0.5; + min: 1 1; + } + } + } + part { name: "elm.text.right"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + align: 0.95 0.5; + min: 1 1; + } + } + } + part { name: "elm.drag_button_base"; + type: SWALLOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + fixed: 1 1; + min: 50 25; + align: 0.5 0.5; + rel1.to: "icon.dragable.area"; + rel2 { + relative: 0.0 1.0; + to: "icon.dragable.area"; + } + } + dragable { + confine: "icon.dragable.area"; + x: 1 1 0; + y: 0 0 0; + } + } + part { name: "elm.drag_button"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + min: 50 25; + color: 255 255 255 0; + rel1.to_x: "elm.drag_button_base"; + rel1.to_y: "icon.dragable.area"; + rel2.to_x: "elm.drag_button_base"; + rel2.to_y: "icon.dragable.area"; + } + dragable { + events: "elm.drag_button_base"; + } + } + part { name: "button0"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button2"; + rel1.offset: -4 -4; + rel2.to: "button2"; + rel2.offset: 3 3; + image { + normal: "bt_bases.png"; + border: 11 11 11 11; + middle: SOLID; + } + color: 255 255 255 128; + } + } + part { name: "button2"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.drag_button"; + rel2.to: "elm.drag_button"; + image { + normal: "bt_basew.png"; + border: 7 7 7 7; + middle: SOLID; + } + color: 255 255 255 210; + } + } + part { name: "button3"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button2"; + rel2.to: "button2"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilightw.png"; + border: 4 4 4 0; + } + color: 255 255 255 190; + } + } + part { name: "elm.text.indicator"; + type: TEXT; + scale: 1; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "elm.drag_button"; + offset: 5 0; + } + rel2 { + to: "elm.drag_button"; + offset: -5 0; + } + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + align: 0.5 0.5; + min: 0 1; + } + } + } + } + programs { + program { name: "elm.drag_button,mouse,up"; + signal: "mouse,up,1"; + source: "elm.drag_button"; + action: SIGNAL_EMIT "elm.drag_button,mouse,up" ""; + } + program { name: "elm.drag_button,mouse,down"; + signal: "mouse,down,1"; + source: "elm.drag_button"; + action: SIGNAL_EMIT "elm.drag_button,mouse,down" ""; + } + program { name: "elm.drag_button,mouse,move"; + signal: "mouse,move"; + source: "elm.drag_button_base"; + action: SIGNAL_EMIT "elm.drag_button,mouse,move" ""; + } + } + } + + group { name: "elm/actionslider/base/bar"; + + images { + image: "shelf_inset.png" COMP; + image: "ilist_1.png" COMP; + image: "bt_bases.png" COMP; + image: "bt_basew.png" COMP; + image: "bt_hilightw.png" COMP; + } + + parts { + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + min: 150 30; + rel1.offset: 1 1; + rel2.offset: -2 -2; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "conf_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "icon.dragable.area"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + rel1.to: "base"; + rel2.to: "base"; + } + } + part { name: "elm.text.left"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + align: 0.05 0.5; + min: 1 1; + } + } + } + part { name: "elm.text.center"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + align: 0.5 0.5; + min: 1 1; + } + } + } + part { name: "elm.text.right"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + align: 0.95 0.5; + min: 1 1; + } + } + } + part { name: "bar"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "base"; + rel1.offset: 0 2; + rel2 { + relative: 0 1; + offset: 3 -3; + to_x: "elm.drag_button_base"; + to_y: "base"; + } + color: 0 0 0 180; + } + } + part { name: "elm.drag_button_base"; + type: SWALLOW; + mouse_events: 1; + scale: 1; + description { state: "default" 0.0; + fixed: 1 1; + min: 50 25; + align: 0.5 0.5; + rel1.to: "icon.dragable.area"; + rel2 { + relative: 0.0 1.0; + to: "icon.dragable.area"; + } + } + dragable { + confine: "icon.dragable.area"; + x: 1 1 0; + y: 0 0 0; + } + } + part { name: "elm.drag_button"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + min: 50 25; + color: 255 255 255 0; + rel1.to_x: "elm.drag_button_base"; + rel1.to_y: "icon.dragable.area"; + rel2.to_x: "elm.drag_button_base"; + rel2.to_y: "icon.dragable.area"; + } + dragable { + events: "elm.drag_button_base"; + } + } + part { name: "button0"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button2"; + rel1.offset: -4 -4; + rel2.to: "button2"; + rel2.offset: 3 3; + image { + normal: "bt_bases.png"; + border: 11 11 11 11; + middle: SOLID; + } + color: 255 255 255 128; + } + } + part { name: "button2"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.drag_button"; + rel2.to: "elm.drag_button"; + image { + normal: "bt_basew.png"; + border: 7 7 7 7; + middle: SOLID; + } + color: 255 255 255 210; + } + } + part { name: "button3"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button2"; + rel2.to: "button2"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilightw.png"; + border: 4 4 4 0; + } + color: 255 255 255 190; + } + } + part { name: "elm.text.indicator"; + type: TEXT; + scale: 1; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "elm.drag_button"; + offset: 5 0; + } + rel2 { + to: "elm.drag_button"; + offset: -5 0; + } + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + align: 0.5 0.5; + min: 0 1; + } + } + } + } + programs { + program { name: "elm.drag_button,mouse,up"; + signal: "mouse,up,1"; + source: "elm.drag_button"; + action: SIGNAL_EMIT "elm.drag_button,mouse,up" ""; + } + program { name: "elm.drag_button,mouse,down"; + signal: "mouse,down,1"; + source: "elm.drag_button"; + action: SIGNAL_EMIT "elm.drag_button,mouse,down" ""; + } + program { name: "elm.drag_button,mouse,move"; + signal: "mouse,move"; + source: "elm.drag_button_base"; + action: SIGNAL_EMIT "elm.drag_button,mouse,move" ""; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/genlist/item/default/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item/group_index/default"; + alias: "elm/genlist/item_odd/group_index/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_item_shadow.png" COMP; + image: "group_index.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 0; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "group_index.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_compress/message/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.title.1 elm.title.2 elm.text"; +// data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + styles { + style { name: "genlist_textblock_style"; + base: "font=Sans font_size=10 color=#000 wrap=char text_class=list_item"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "tab" "\t"; + } + style { name: "genlist_textblock_style2"; + base: "font=Sans font_size=10 color=#fff wrap=char text_class=list_item"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "tab" "\t"; + } + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.title.1"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + fixed: 0 1; +// min: 16 16; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.0; + offset: -5 4; + } + color: 0 0 0 255; + color3: 0 0 0 0; + align: 0.0 0.0; + text { + font: "Sans"; + size: 10; + min: 0 1; +// min: 1 1; + align: 0.0 0.0; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.title.2"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + fixed: 0 1; +// min: 16 16; + rel1 { + to_y: "elm.title.1"; + relative: 0.0 1.0; + offset: 4 0; + } + rel2 { + to_y: "elm.title.1"; + relative: 1.0 1.0; + offset: -5 0; + } + color: 0 0 0 255; + color3: 0 0 0 0; + align: 0.0 0.0; + text { + font: "Sans"; + size: 10; + min: 0 1; +// min: 1 1; + align: 0.0 0.0; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// fixed: 0 1; +// min: 16 16; + rel1 { + to_y: "elm.title.2"; + relative: 0.0 1.0; + offset: 4 0; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + align: 0.0 0.0; + text { + style: "genlist_textblock_style"; + min: 0 1; +// min: 1 1; + align: 0.0 0.0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + text { + style: "genlist_textblock_style2"; + } + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.title.1"; + target: "elm.title.2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.title.1"; + target: "elm.title.2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_compress_odd/message/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.title.1 elm.title.2 elm.text"; +// data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.title.1"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + fixed: 0 1; +// min: 16 16; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.0; + offset: -5 4; + } + color: 0 0 0 255; + color3: 0 0 0 0; + align: 0.0 0.0; + text { + font: "Sans"; + size: 10; + min: 0 1; +// min: 1 1; + align: 0.0 0.0; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.title.2"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + fixed: 0 1; +// min: 16 16; + rel1 { + to_y: "elm.title.1"; + relative: 0.0 1.0; + offset: 4 0; + } + rel2 { + to_y: "elm.title.1"; + relative: 1.0 1.0; + offset: -5 0; + } + color: 0 0 0 255; + color3: 0 0 0 0; + align: 0.0 0.0; + text { + font: "Sans"; + size: 10; + min: 0 1; +// min: 1 1; + align: 0.0 0.0; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// fixed: 0 1; +// min: 16 16; + rel1 { + to_y: "elm.title.2"; + relative: 0.0 1.0; + offset: 4 0; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + align: 0.0 0.0; + text { + style: "genlist_textblock_style"; + min: 0 1; +// min: 1 1; + align: 0.0 0.0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + text { + style: "genlist_textblock_style2"; + } + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.title.1"; + target: "elm.title.2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.title.1"; + target: "elm.title.2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_compress/default/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; +// min: 1 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_odd/default/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_compress_odd/default/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; +// min: 1 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + + group { name: "elm/genlist/tree/default/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + group { name: "elm/genlist/tree_compress/default/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + group { name: "elm/genlist/tree_odd/default/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + group { name: "elm/genlist/tree_compress_odd/default/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + + group { name: "elm/genlist/item/default_style/default"; + styles + { + style { name: "genlist_style"; + base: "font=Sans font_size=10 align=left valign=0.5 color=#000 text_class=list_item"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "hilight" "+ font=Sans:style=Bold"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "tab" "\t"; + } + style { name: "genlist_selected_style"; + base: "font=Sans font_size=10 align=left valign=0.5 color=#fff text_class=list_item"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "hilight" "+ font=Sans:style=Bold"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "tab" "\t"; + } + } + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + min: 16 28; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + align: 0.0 0.5; + fixed: 0 1; + rel1 { + to_x: "elm.swallow.icon"; + to_y: "base"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + to_y: "base"; + relative: 0.0 0.5; + offset: -1 -5; + } + text { + style: "genlist_style"; + min: 1 1; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + text { + style: "genlist_selected_style"; + } + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_odd/default_style/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + min: 16 28; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + align: 0.0 0.5; + fixed: 0 1; + rel1 { + to_x: "elm.swallow.icon"; + to_y: "base"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + to_y: "base"; + relative: 0.0 0.5; + offset: -1 -5; + } + text { + style: "genlist_style"; + min: 1 1; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + text { + style: "genlist_selected_style"; + } + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + + group { name: "elm/genlist/tree/default_style/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + min: 16 28; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXTBLOCK; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + align: 0.0 0.5; + fixed: 0 1; + rel1 { + to_x: "elm.swallow.icon"; + to_y: "base"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + to_y: "base"; + relative: 0.0 0.5; + offset: -1 -5; + } + text { + style: "genlist_style"; + min: 1 1; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + text { + style: "genlist_selected_style"; + } + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + group { name: "elm/genlist/tree_odd/default_style/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + min: 16 28; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXTBLOCK; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + align: 0.0 0.5; + fixed: 0 1; + rel1 { + to_x: "elm.swallow.icon"; + to_y: "base"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + to_y: "base"; + relative: 0.0 0.5; + offset: -1 -5; + } + text { + style: "genlist_style"; + min: 1 1; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + text { + style: "genlist_selected_style"; + } + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + + + group { name: "elm/genlist/item/double_label/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text elm.text.sub"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.sub"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_compress/double_label/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text elm.text.sub"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.sub"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_odd/double_label/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text elm.text.sub"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.sub"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_compress_odd/double_label/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text elm.text.sub"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.sub"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + + group { name: "elm/genlist/tree/double_label/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text elm.text.sub"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.sub"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + group { name: "elm/genlist/tree_compress/double_label/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text elm.text.sub"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.sub"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + group { name: "elm/genlist/tree_odd/double_label/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text elm.text.sub"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.sub"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 1 1; +// min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + + group { name: "elm/genlist/item/icon_top_text_bottom/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.5 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 0.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_y: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 0 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.5 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_odd/icon_top_text_bottom/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.5 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 0.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_y: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 0 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.5 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + + group { name: "elm/genlist/tree/icon_top_text_bottom/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.5 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -4 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_y: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 0 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.5 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + group { name: "elm/genlist/tree_odd/icon_top_text_bottom/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.5 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -4 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_y: "elm.swallow.icon"; + relative: 0.0 1.0; + offset: 0 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; +// min: 0 1; + align: 0.5 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/check/base/default"; + images { + image: "check_base.png" COMP; + image: "check.png" COMP; + image: "check2.png" COMP; + } + parts { + part { name: "bg"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.offset: 1 1; + rel2.relative: 0.0 1.0; + rel2.offset: 1 -2; + align: 0.0 0.5; + min: 16 16; + max: 16 16; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + image { + normal: "check_base.png"; + border: 5 5 5 5; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "check"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1 { + to: "bg"; + offset: 1 1; + } + rel2 { + to: "bg"; + offset: -2 -2; + } + visible: 0; + color: 255 255 255 255; + image.normal: "check.png"; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + color: 128 128 128 128; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + visible: 1; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + visible: 0; + align: 0.0 0.5; + rel1.to_x: "bg"; + rel1.relative: 1.0 0.0; + rel1.offset: 1 1; + rel2.to_x: "bg"; + rel2.offset: 1 -2; + rel2.relative: 1.0 1.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + fixed: 1 0; + visible: 1; + aspect: 1.0 1.0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + fixed: 1 0; + visible: 1; + aspect: 1.0 1.0; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: 1 1; + rel2.relative: 1.0 1.0; + rel2.offset: -2 -2; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "events"; + type: RECT; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { name: "click"; + signal: "mouse,up,1"; + source: "events"; + action: SIGNAL_EMIT "elm,action,check,toggle" ""; + } + program { name: "check_on"; + signal: "elm,state,check,on"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "check"; + } + program { name: "check_off"; + signal: "elm,state,check,off"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "check"; + } + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.content"; + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "disabled_visible", 0.0); + else + set_state(PART:"elm.swallow.content", "disabled", 0.0); + + get_state(PART:"check", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"check", "disabled_visible", 0.0); + else + set_state(PART:"check", "disabled", 0.0); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.text", "visible", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + else + set_state(PART:"elm.swallow.content", "default", 0.0); + + get_state(PART:"check", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"check", "visible", 0.0); + else + set_state(PART:"check", "default", 0.0); + } + } + } + } +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/radio/base/default"; + images { + image: "radio_base.png" COMP; + image: "radio.png" COMP; + image: "radio2.png" COMP; + } + parts { + part { name: "bg"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.offset: 1 1; + rel2.relative: 0.0 1.0; + rel2.offset: 1 -2; + align: 0.0 0.5; + min: 16 16; + max: 16 16; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + image.normal: "radio_base.png"; + } + } + part { name: "radio"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + visible: 0; + image.normal: "radio.png"; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + visible: 0; + align: 0.0 0.5; + color: 0 0 0 0; + rel1.to_x: "bg"; + rel1.relative: 1.0 0.0; + rel1.offset: 1 1; + rel2.to_x: "bg"; + rel2.relative: 1.0 1.0; + rel2.offset: 2 -2; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + aspect: 1.0 1.0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 128 128 128 128; + visible: 1; + aspect: 1.0 1.0; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: 1 1; + rel2.relative: 1.0 1.0; + rel2.offset: -2 -2; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.0 0.5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled_visible" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + visible: 1; + text.min: 1 1; + } + } + part { name: "events"; + type: RECT; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { name: "click"; + signal: "mouse,up,1"; + source: "events"; + action: SIGNAL_EMIT "elm,action,radio,toggle" ""; + } + program { name: "radio_on"; + signal: "elm,state,radio,on"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "radio"; + } + program { name: "radio_off"; + signal: "elm,state,radio,off"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "radio"; + } + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.content"; + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.text", "disabled_visible", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "disabled_visible", 0.0); + else + set_state(PART:"elm.swallow.content", "disabled", 0.0); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_visible")) + set_state(PART:"elm.text", "visible", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + + get_state(PART:"elm.swallow.content", st, 30, vl); + if (!strcmp(st, "visible")) + set_state(PART:"elm.swallow.content", "visible", 0.0); + else + set_state(PART:"elm.swallow.content", "default", 0.0); + } + } + } + } + group { name: "elm/genlist/tree_compress_odd/double_label/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text elm.text.sub"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + data.item: "treesize" "20"; +// data.item: "states" ""; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + image: "icon_arrow_right.png" COMP; + image: "icon_arrow_down.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "arrow"; + clip_to: "disclip"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + aspect: 1.0 1.0; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + image.normal: "icon_arrow_right.png"; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "arrow"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + to_x: "arrow"; + relative: 1.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.0; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.sub"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; +// min: 16 16; + rel1 { + to_x: "elm.swallow.icon"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; +// min: 1 1; + min: 0 1; + align: 0.0 0.5; + text_class: "list_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + target: "elm.text.sub"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + name: "expand"; + signal: "mouse,up,1"; + source: "arrow"; + action: SIGNAL_EMIT "elm,action,expand,toggle" "elm"; + } + program { + name: "go_expanded"; + signal: "elm,state,expanded"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "arrow"; + } + program { + name: "go_contracted"; + signal: "elm,state,contracted"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow"; + } + } + } + + group { name: "elm/genlist/item_compress/media/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text.title elm.text.album-artist"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.text.title"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.album-artist"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + relative: 0.0 0.5; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.album-artist"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.album-artist"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_compress_odd/media/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text.title elm.text.album-artist"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.text.title"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.album-artist"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + relative: 0.0 0.5; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.album-artist"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.album-artist"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + + group { name: "elm/genlist/item_compress/media-album/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text.title elm.text.trackno elm.text.length"; + data.item: "states" "elm.state.trackno"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + script { + public dot_visible; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { + name: "elm.text.trackno"; + type: TEXT; + scale: 1; + mouse_events: 0; + description { + state: "default" 0.0; + color: 255 255 255 255; + align: 0.0 0.0; + fixed: 1 0; + rel1 { + to_y: "elm.text.title"; + relative: 0.0 0.0; + offset: 5 0; + } + rel2 { + to_y: "elm.text.title"; + relative: 0.0 1.0; + offset: 20 0; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; + align: 1.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { + name: "dot"; + type: TEXT; + scale: 1; + mouse_events: 0; + description { + state: "default" 0.0; + color: 255 255 255 255; + visible: 0; + fixed: 1 1; + align: 0.0 0.0; + rel1 { + to_x: "elm.text.trackno"; + to_y: "elm.text.title"; + relative: 1.0 0.0; + offset: 1 0; + } + rel2 { + to_x: "elm.text.trackno"; + to_y: "elm.text.title"; + relative: 1.0 1.0; + offset: 1 0; + + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; + align: 0.0 0.5; + text: "."; + } + } + description { + state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + visible: 1; + } + } + programs { + program { + signal: "elm,state,elm.state.trackno,active"; + source: "elm"; + script { + set_state(PART:"dot", "visible", 0.0); + set_int(dot_visible, 1); + } + } + } + part { name: "elm.text.title"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + to_x: "dot"; + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.length"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + relative: 0.0 0.5; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.trackno"; + target: "elm.text.length"; + after: "dot_active"; + } + program { + name: "dot_active"; + script { + if (get_int(dot_visible) == 1) + set_state(PART:"dot", "selected", 0.0); + } + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.length"; + target: "elm.text.trackno"; + transition: LINEAR 0.1; + after: "dot_passive"; + } + program { + name: "dot_passive"; + script { + if (get_int(dot_visible) == 1) + set_state(PART:"dot", "visible", 0.0); + } + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_compress_odd/media-album/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text.title elm.text.trackno elm.text.length"; + data.item: "states" "elm.state.trackno"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + script { + public dot_visible; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { + name: "elm.text.trackno"; + type: TEXT; + scale: 1; + mouse_events: 0; + description { + state: "default" 0.0; + color: 255 255 255 255; + align: 0.0 0.0; + fixed: 1 0; + rel1 { + to_y: "elm.text.title"; + relative: 0.0 0.0; + offset: 5 0; + } + rel2 { + to_y: "elm.text.title"; + relative: 0.0 1.0; + offset: 20 0; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; + align: 1.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { + name: "dot"; + type: TEXT; + scale: 1; + mouse_events: 0; + description { + state: "default" 0.0; + color: 255 255 255 255; + visible: 0; + fixed: 1 1; + align: 0.0 0.0; + rel1 { + to_x: "elm.text.trackno"; + to_y: "elm.text.title"; + relative: 1.0 0.0; + offset: 1 0; + } + rel2 { + to_x: "elm.text.trackno"; + to_y: "elm.text.title"; + relative: 1.0 1.0; + offset: 1 0; + + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 1 1; + align: 0.0 0.5; + text: "."; + } + } + description { + state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + visible: 1; + } + } + programs { + program { + signal: "elm,state,elm.state.trackno,active"; + source: "elm"; + script { + set_state(PART:"dot", "visible", 0.0); + set_int(dot_visible, 1); + } + } + } + part { name: "elm.text.title"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + to_x: "dot"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.length"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + relative: 0.0 0.5; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.length"; + target: "elm.text.trackno"; + after: "dot_active"; + } + program { + name: "dot_active"; + script { + if (get_int(dot_visible) == 1) + set_state(PART:"dot", "selected", 0.0); + } + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.length"; + target: "elm.text.trackno"; + transition: LINEAR 0.1; + after: "dot_passive"; + } + program { + name: "dot_passive"; + script { + if (get_int(dot_visible) == 1) + set_state(PART:"dot", "visible", 0.0); + } + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + + group { name: "elm/genlist/item_compress/media-preview/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text.title elm.text.artist"; + data.item: "icons" "elm.swallow.preview"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.preview"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + min: 68 68; + max: 68 68; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.text.title"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + to_x: "elm.swallow.preview"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.artist"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + to_x: "elm.swallow.preview"; + relative: 1.0 0.5; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.artist"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.artist"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/genlist/item_compress_odd/media-preview/default"; + data.item: "stacking" "below"; + data.item: "selectraise" "on"; + data.item: "labels" "elm.text.title elm.text.artist"; + data.item: "icons" "elm.swallow.preview"; + data.item: "treesize" "20"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_2.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.preview"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + min: 68 68; + max: 68 68; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.text.title"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + to_x: "elm.swallow.preview"; + relative: 1.0 0.0; + offset: 4 4; + } + rel2 { + relative: 1.0 0.5; + offset: -1 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "elm.text.artist"; + clip_to: "disclip"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + rel1 { + to_x: "elm.swallow.preview"; + relative: 1.0 0.5; + offset: 4 4; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -5; + } + color: 0 0 0 128; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 8; + min: 0 1; + align: 0.0 0.5; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + color3: 0 0 0 32; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { + name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.artist"; + } + program { + name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text.title"; + target: "elm.text.artist"; + transition: LINEAR 0.1; + } + program { + name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { + name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/pager/base/default"; + data.item: "onshow" "raise"; +// other options +// data.item: "onhide" "lower"; +// data.item: "onshow" "lower"; + images { + image: "frame_1.png" COMP; + image: "frame_2.png" COMP; + image: "dia_grad.png" COMP; + } + parts { + part { name: "clip"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: -9999 -9999; + } + rel2 { + to: "base"; + offset: 9999 9999; + } + color: 255 255 255 255; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + } + part { name: "base0"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + image.normal: "dia_grad.png"; + rel1.to: "over"; + rel2.to: "over"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "base"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + fill.smooth : 0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + rel1.relative: -1.0 0.0; + rel2.relative: 0.0 1.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "over"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: 4 4; + } + rel2 { + to: "base"; + offset: -5 -5; + } + image { + normal: "frame_1.png"; + border: 2 2 28 22; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: 8 8; + } + rel2 { + to: "base"; + offset: -9 -9; + } + } + } + } + programs { + program { name: "push_start"; + signal: "elm,action,push"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "base"; + target: "clip"; + after: "show_start2"; + } + program { name: "show_start"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "base"; + target: "clip"; + after: "show_start2"; + } + program { name: "show_start2"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "base"; + target: "clip"; + after: "show_end"; + } + program { name: "show_end"; + action: SIGNAL_EMIT "elm,action,show,finished" ""; + } + program { name: "pop_start"; + signal: "elm,action,pop"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + target: "clip"; + after: "hide_start2"; + } + program { name: "hide_start"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + target: "clip"; + after: "hide_start2"; + } + program { name: "hide_start2"; + action: STATE_SET "hidden" 0.0; + transition: DECELERATE 0.5; + target: "base"; + target: "clip"; + after: "hide_end"; + } + program { name: "hide_end"; + action: SIGNAL_EMIT "elm,action,hide,finished" ""; + } + program { name: "reset"; + signal: "elm,action,reset"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + target: "clip"; + } + } + } + + group { name: "elm/pager/base/slide"; + images { + image: "frame_1.png" COMP; + image: "frame_2.png" COMP; + image: "dia_grad.png" COMP; + } + parts { + part { name: "clip"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: -9999 -9999; + } + rel2 { + to: "base"; + offset: 9999 9999; + } + color: 255 255 255 255; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + description { state: "hidden2" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + } + part { name: "base0"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + image.normal: "dia_grad.png"; + rel1.to: "over"; + rel2.to: "over"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "base"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + fill.smooth : 0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + rel1.relative: -1.0 0.0; + rel2.relative: 0.0 1.0; + } + description { state: "hidden2" 0.0; + inherit: "default" 0.0; + rel1.relative: 1.0 0.0; + rel2.relative: 2.0 1.0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "over"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: 4 4; + } + rel2 { + to: "base"; + offset: -5 -5; + } + image { + normal: "frame_1.png"; + border: 2 2 28 22; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: 8 8; + } + rel2 { + to: "base"; + offset: -9 -9; + } + } + } + } + programs { + program { name: "push_start"; + signal: "elm,action,push"; + source: "elm"; + action: STATE_SET "hidden2" 0.0; + target: "base"; + target: "clip"; + after: "show_start2"; + } + program { name: "show_start"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "base"; + target: "clip"; + after: "show_start2"; + } + program { name: "show_start2"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "base"; + target: "clip"; + after: "show_end"; + } + program { name: "show_end"; + action: SIGNAL_EMIT "elm,action,show,finished" ""; + } + program { name: "pop_start"; + signal: "elm,action,pop"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + target: "clip"; + after: "pop_start2"; + } + program { name: "pop_start2"; + action: STATE_SET "hidden2" 0.0; + transition: DECELERATE 0.5; + target: "base"; + target: "clip"; + after: "hide_end"; + } + program { name: "hide_start"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + target: "clip"; + after: "hide_start2"; + } + program { name: "hide_start2"; + action: STATE_SET "hidden" 0.0; + transition: DECELERATE 0.5; + target: "base"; + target: "clip"; + after: "hide_end"; + } + program { name: "hide_end"; + action: SIGNAL_EMIT "elm,action,hide,finished" ""; + } + program { name: "reset"; + signal: "elm,action,reset"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + target: "clip"; + } + } + } + group { name: "elm/pager/base/slide_invisible"; + parts { + part { name: "clip"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: -9999 -9999; + } + rel2 { + to: "base"; + offset: 9999 9999; + } + color: 255 255 255 255; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + description { state: "hidden2" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + } + part { name: "base"; + type: RECT; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + color: 0 0 0 0; + } + description { state: "hidden" 0.0; + color: 0 0 0 0; + rel1.relative: -1.0 0.0; + rel2.relative: 0.0 1.0; + } + description { state: "hidden2" 0.0; + color: 0 0 0 0; + rel1.relative: 1.0 0.0; + rel2.relative: 2.0 1.0; + } + description { state: "visible" 0.0; + color: 0 0 0 0; + rel1.relative: 0.0 0.0; + rel2.relative: 1.0 1.0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clip"; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + } + } + } + programs { + program { name: "push_start"; + signal: "elm,action,push"; + source: "elm"; + action: STATE_SET "hidden2" 0.0; + target: "base"; + target: "clip"; + after: "show_start2"; + } + program { name: "show_start"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "base"; + target: "clip"; + after: "show_start2"; + } + program { name: "show_start2"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "base"; + target: "clip"; + after: "show_end"; + } + program { name: "show_end"; + action: SIGNAL_EMIT "elm,action,show,finished" ""; + } + program { name: "pop_start"; + signal: "elm,action,pop"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + target: "clip"; + after: "pop_start2"; + } + program { name: "pop_start2"; + action: STATE_SET "hidden2" 0.0; + transition: DECELERATE 0.5; + target: "base"; + target: "clip"; + after: "hide_end"; + } + program { name: "hide_start"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "base"; + target: "clip"; + after: "hide_start2"; + } + program { name: "hide_start2"; + action: STATE_SET "hidden" 0.0; + transition: DECELERATE 0.5; + target: "base"; + target: "clip"; + after: "hide_end"; + } + program { name: "hide_end"; + action: SIGNAL_EMIT "elm,action,hide,finished" ""; + } + program { name: "reset"; + signal: "elm,action,reset"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "base"; + target: "clip"; + } + } + } + + group { name: "elm/pager/base/fade"; + data.item: "onshow" "raise"; + // other options + // data.item: "onhide" "lower"; + // data.item: "onshow" "lower"; + images { + image: "frame_1.png" COMP; + image: "frame_2.png" COMP; + image: "dia_grad.png" COMP; + } + parts { + part { name: "clip_base"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: -9999 -9999; + } + rel2 { + to: "base"; + offset: 9999 9999; + } + color: 255 255 255 120; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + } + part { name: "clip"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: -9999 -9999; + } + rel2 { + to: "base"; + offset: 9999 9999; + } + color: 255 255 255 255; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + } + part { name: "base0"; + mouse_events: 0; + clip_to: "clip_base"; + description { state: "default" 0.0; + image.normal: "dia_grad.png"; + rel1.to: "over"; + rel2.to: "over"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "base"; + mouse_events: 0; + clip_to: "clip_base"; + description { state: "default" 0.0; + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "over"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: 4 4; + } + rel2 { + to: "base"; + offset: -5 -5; + } + image { + normal: "frame_1.png"; + border: 2 2 28 22; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: 8 8; + } + rel2 { + to: "base"; + offset: -9 -9; + } + } + } + } + programs { + program { name: "push_start"; + signal: "elm,action,push"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "clip"; + target: "clip_base"; + after: "show_start2"; + } + program { name: "show_start"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "clip"; + target: "clip_base"; + after: "show_start2"; + } + program { name: "show_start2"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "clip"; + target: "clip_base"; + after: "show_end"; + } + program { name: "show_end"; + action: SIGNAL_EMIT "elm,action,show,finished" ""; + } + program { name: "pop_start"; + signal: "elm,action,pop"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "clip"; + target: "clip_base"; + after: "hide_start2"; + } + program { name: "hide_start"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "clip"; + target: "clip_base"; + after: "hide_start2"; + } + program { name: "hide_start2"; + action: STATE_SET "hidden" 0.0; + transition: DECELERATE 0.5; + target: "clip"; + target: "clip_base"; + after: "hide_end"; + } + program { name: "hide_end"; + action: SIGNAL_EMIT "elm,action,hide,finished" ""; + } + program { name: "reset"; + signal: "elm,action,reset"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "clip_base"; + target: "clip"; + } + } + } + group { name: "elm/pager/base/fade_translucide"; + data.item: "onshow" "raise"; + // other options + // data.item: "onhide" "lower"; + // data.item: "onshow" "lower"; + images { + image: "frame_1.png" COMP; + image: "frame_2.png" COMP; + image: "dia_grad.png" COMP; + } + parts { + part { name: "clip_base"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: -9999 -9999; + } + rel2 { + to: "base"; + offset: 9999 9999; + } + color: 255 255 255 120; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + } + part { name: "clip"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: -9999 -9999; + } + rel2 { + to: "base"; + offset: 9999 9999; + } + color: 255 255 255 255; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + } + part { name: "base0"; + mouse_events: 0; + clip_to: "clip_base"; + description { state: "default" 0.0; + image.normal: "dia_grad.png"; + rel1.to: "over"; + rel2.to: "over"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "base"; + mouse_events: 0; + clip_to: "clip_base"; + description { state: "default" 0.0; + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "over"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: 4 4; + } + rel2 { + to: "base"; + offset: -5 -5; + } + image { + normal: "frame_1.png"; + border: 2 2 28 22; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "base"; + offset: 8 8; + } + rel2 { + to: "base"; + offset: -9 -9; + } + } + } + } + programs { + program { name: "push_start"; + signal: "elm,action,push"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "clip"; + target: "clip_base"; + after: "show_start2"; + } + program { name: "show_start"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "clip"; + target: "clip_base"; + after: "show_start2"; + } + program { name: "show_start2"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "clip"; + target: "clip_base"; + after: "show_end"; + } + program { name: "show_end"; + action: SIGNAL_EMIT "elm,action,show,finished" ""; + } + program { name: "pop_start"; + signal: "elm,action,pop"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "clip"; + target: "clip_base"; + after: "hide_start2"; + } + program { name: "hide_start"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "clip"; + target: "clip_base"; + after: "hide_start2"; + } + program { name: "hide_start2"; + action: STATE_SET "hidden" 0.0; + transition: DECELERATE 0.5; + target: "clip"; + target: "clip_base"; + after: "hide_end"; + } + program { name: "hide_end"; + action: SIGNAL_EMIT "elm,action,hide,finished" ""; + } + program { name: "reset"; + signal: "elm,action,reset"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "clip_base"; + target: "clip"; + } + } + } + group { name: "elm/pager/base/fade_invisible"; + data.item: "onshow" "raise"; + // other options + // data.item: "onhide" "lower"; + // data.item: "onshow" "lower"; + parts { + part { name: "clip"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + offset: -9999 -9999; + } + rel2 { + offset: 9999 9999; + } + color: 255 255 255 255; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + offset: 8 8; + } + rel2 { + offset: -9 -9; + } + } + } + } + programs { + program { name: "push_start"; + signal: "elm,action,push"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "clip"; + after: "show_start2"; + } + program { name: "show_start"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "clip"; + after: "show_start2"; + } + program { name: "show_start2"; + action: STATE_SET "visible" 0.0; + transition: DECELERATE 0.5; + target: "clip"; + after: "show_end"; + } + program { name: "show_end"; + action: SIGNAL_EMIT "elm,action,show,finished" ""; + } + program { name: "pop_start"; + signal: "elm,action,pop"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "clip"; + after: "hide_start2"; + } + program { name: "hide_start"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "clip"; + after: "hide_start2"; + } + program { name: "hide_start2"; + action: STATE_SET "hidden" 0.0; + transition: DECELERATE 0.5; + target: "clip"; + after: "hide_end"; + } + program { name: "hide_end"; + action: SIGNAL_EMIT "elm,action,hide,finished" ""; + } + program { name: "reset"; + signal: "elm,action,reset"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "clip"; + } + } + } + + group { name: "elm/pager/base/flip"; + data.item: "onshow" "raise"; + images { + image: "frame_1.png" COMP; + image: "frame_2.png" COMP; + image: "dia_grad.png" COMP; + } + parts { + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + map { + on: 1; + smooth: 1; + backface_cull: 1; + perspective_on: 1; + } + perspective { + zplane: 0; + focal: 1000; + } + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + map.rotation.y: 90.0; + } + description { state: "before_hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + map.rotation.y: -90.0; + } + } + } + programs { + program { name: "push_start"; + signal: "elm,action,push"; + source: "elm"; + after: "push1"; + } + program { name: "push1"; + action: STATE_SET "hidden" 0.0; + target: "elm.swallow.content"; + after: "push2"; + } + program { name: "push2"; + action: STATE_SET "default" 0.0; + in: 0.5 0.0; + transition: LINEAR 0.5; + target: "elm.swallow.content"; + after: "push3"; + } + program { name: "push3"; + action: SIGNAL_EMIT "elm,action,show,finished" ""; + } + + program { name: "show_start"; + signal: "elm,action,show"; + source: "elm"; + after: "show1"; + } + program { name: "show1"; + action: STATE_SET "before_hidden" 0.0; + target: "elm.swallow.content"; + after: "show2"; + } + program { name: "show2"; + action: STATE_SET "default" 0.0; + in: 0.5 0.0; + transition: LINEAR 0.5; + target: "elm.swallow.content"; + after: "show3"; + } + program { name: "show3"; + action: SIGNAL_EMIT "elm,action,show,finished" ""; + } + + program { name: "pop_start"; + signal: "elm,action,pop"; + source: "elm"; + after: "pop1"; + } + program { name: "pop1"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + after: "pop2"; + } + program { name: "pop2"; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.5; + target: "elm.swallow.content"; + after: "pop3"; + } + program { name: "pop3"; + action: SIGNAL_EMIT "elm,action,hide,finished" ""; + } + + program { name: "hide_start"; + signal: "elm,action,hide"; + source: "elm"; + after: "hide1"; + } + program { name: "hide1"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + after: "hide2"; + } + program { name: "hide2"; + action: STATE_SET "before_hidden" 0.0; + transition: LINEAR 0.5; + target: "elm.swallow.content"; + after: "hide3"; + } + program { name: "hide3"; + action: SIGNAL_EMIT "elm,action,hide,finished" ""; + } + + program { name: "reset"; + signal: "elm,action,reset"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + } + } + + + +/////////////////////////////////////////////////////////////////////////////// +// FIXME: this doesn't look too hot. need to fix it up + group { name: "elm/progressbar/horizontal/default"; + images { + image: "shelf_inset.png" COMP; + image: "bt_sm_base2.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "bt_sm_shine.png" COMP; + } + parts { + part { name: "elm.background.progressbar"; + mouse_events: 0; + description { + state: "default" 0.0; + rel1 { + relative: 0.0 0.0; + offset: 0 0; + } + rel2 { + relative: 1.0 1.0; + } + } + } + part { name: "elm.swallow.bar"; + mouse_events: 0; + type: SWALLOW; + description { + min: 48 28; + max: 99999 28; + state: "default" 0.0; + rel1 { + to_x: "elm.text"; + to_y: "elm.background.progressbar"; + relative: 1.0 0.0; + } + rel2 { + to: "elm.background.progressbar"; + relative: 1.0 1.0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 0; + align: 0.0 0.5; + rel1 { + offset: 4 0; + to_y: "elm.background.progressbar"; + } + rel2 { + offset: 3 -1; + relative: 0.0 1.0; + to_y: "elm.background.progressbar"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel2.offset: 4 -1; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 0.0 0.5; + rel1.to_x: "elm.swallow.content"; + rel1.relative: 1.0 0.0; + rel1.offset: -1 4; + rel2.to_x: "elm.swallow.content"; + rel2.relative: 1.0 1.0; + rel2.offset: -1 -5; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.0 0.5; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + rel1.offset: 0 4; + rel2.offset: 0 -5; + } + } + + part { name: "background"; + mouse_events: 0; + clip_to: "elm.background.progressbar"; + description { + state: "default" 0.0; + rel1 { + to: "elm.swallow.bar"; + relative: 0.0 0.0; + } + rel2 { + to: "elm.swallow.bar"; + relative: 1.0 1.0; + offset: -1 -1; + } + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + } + } + } + + part { name: "elm.text.status"; + type: TEXT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 1; + rel1 { + to: "background"; + relative: 0.5 0.5; + } + rel2 { + to: "background"; + relative: 0.5 0.5; + } + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 1 1; + align: 0.5 0.0; + } + color: 0 0 0 255; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + text.min: 0 0; + } + } + + part { name: "elm.progress.progressbar"; + mouse_events: 0; + clip_to: "elm.background.progressbar"; + description { + state: "default" 0.0; + min: 14 28; + fixed: 1 1; + rel1 { + to: "elm.swallow.bar"; + relative: 0.0 0.0; + } + rel2 { + to_y: "elm.swallow.bar"; + to_x: "elm.cur.progressbar"; + offset: -1 -1; + } + image { + normal: "bt_sm_base2.png"; + border: 6 6 6 6; + } + } + description { + state: "invert" 0.0; + inherit: "default" 0.0; + rel1 { + to_y: "elm.swallow.bar"; + to_x: "elm.cur.progressbar"; + } + rel2 { + to: "elm.swallow.bar"; + relative: 1.0 1.0; + } + } + description { + state: "state_begin" 0.0; + inherit: "default" 0.0; + rel1 { + to: "elm.swallow.bar"; + relative: 0.0 0.0; + } + rel2 { + to: "elm.swallow.bar"; + relative: 0.1 1.0; + } + } + description { + state: "state_end" 0.0; + inherit: "default" 0.0; + rel1 { + to: "elm.swallow.bar"; + relative: 0.9 0.0; + } + rel2 { + to: "elm.swallow.bar"; + relative: 1.0 1.0; + } + } + } + part { name: "text-bar"; + type: TEXT; + mouse_events: 0; + clip_to: "progress-rect"; + effect: SOFT_SHADOW; + scale: 1; + description { state: "default" 0.0; + align: 0.0 0.0; + fixed: 1 1; + visible: 1; + rel1.to: "elm.text.status"; + rel1.offset: -1 -1; + rel2.to: "elm.text.status"; + text { + text_source: "elm.text.status"; + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 1 1; + align: 0.0 0.0; + } + color: 224 224 224 255; + color3: 0 0 0 64; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + text.min: 0 0; + } + } + + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.progress.progressbar"; + rel2.to: "elm.progress.progressbar"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + } + + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.progress.progressbar"; + rel2.to: "elm.progress.progressbar"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + } + + part { name: "elm.cur.progressbar"; + mouse_events: 0; + dragable { + confine: "background"; + x: 1 1 1; + y: 0 0 0; + } + description { state: "default" 0.0; + min: 14 28; + fixed: 1 1; + visible: 0; + rel1 { + to: "background"; + relative: 0 0; + } + rel2.to: "background"; + } + } + part { name: "progress-rect"; + mouse_events: 0; + description { + state: "default" 0.0; + rel1.to: "elm.progress.progressbar"; + rel2.to: "elm.progress.progressbar"; + } + } + } + programs { + program { name: "label_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { name: "label_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.content"; + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + program { name: "units_show"; + signal: "elm,state,units,visible"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "text-bar"; + target: "elm.text.status"; + } + program { name: "units_hide"; + signal: "elm,state,units,hidden"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "text-bar"; + target: "elm.text.status"; + } + program { name: "slide_to_end"; + action: STATE_SET "state_end" 0.0; + transition: LINEAR 0.5; + target: "elm.progress.progressbar"; + after: "slide_to_begin"; + } + program { name: "slide_to_begin"; + signal: "elm,state,slide,begin"; + action: STATE_SET "state_begin" 0.0; + target: "elm.progress.progressbar"; + transition: LINEAR 0.5; + after: "slide_to_end"; + } + program { name: "start_pulse"; + signal: "elm,state,pulse,start"; + source: "elm"; + after: "slide_to_end"; + } + program { name: "stop_pulse"; + signal: "elm,state,pulse,stop"; + source: "elm"; + action: ACTION_STOP; + target: "slide_to_begin"; + target: "slide_to_end"; + target: "start_pulse"; + after: "state_pulse"; + } + program { name: "state_pulse"; + signal: "elm,state,pulse"; + source: "elm"; + action: STATE_SET "state_begin" 0.0; + target: "elm.progress.progressbar"; + after: "units_hide"; + } + program { name: "state_fraction"; + signal: "elm,state,fraction"; + source: "elm"; + action: ACTION_STOP; + target: "slide_to_begin"; + target: "slide_to_end"; + target: "start_pulse"; + action: STATE_SET "default" 0.0; + target: "elm.progress.progressbar"; + } + program { name: "set_invert_on"; + signal: "elm,state,inverted,on"; + source: "elm"; + action: STATE_SET "invert" 0.0; + target: "elm.progress.progressbar"; + } + program { name: "set_invert_off"; + signal: "elm,state,inverted,off"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.progress.progressbar"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/progressbar/vertical/default"; + images { + image: "shelf_inset.png" COMP; + image: "bt_sm_base2.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "bt_sm_shine.png" COMP; + } + parts { + part { name: "elm.background.progressbar"; + type: RECT; + mouse_events: 0; + description { + state: "default" 0.0; + rel1 { + relative: 0.0 0.0; + offset: 0 0; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -1; + } + } + } + part { name: "elm.swallow.bar"; + type: SWALLOW; + scale: 1; + description { state: "default" 0.0; + min: 28 48; + max: 28 9999; + align: 0.5 1.0; + rel1 { + to_y: "elm.text"; + relative: 0.0 1.0; + offset: 0 2; + } + rel2 { + to_y: "elm.text.box"; + relative: 1.0 0.0; + offset: -1 -3; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 0; + align: 0.5 0.0; + rel1 { + offset: 0 4; + to_x: "elm.swallow.bar"; + } + rel2 { + offset: -1 3; + relative: 1.0 0.0; + to_x: "elm.swallow.bar"; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: HORIZONTAL; + rel2.offset: -1 4; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 0.5 0.0; + rel1.to_y: "elm.swallow.content"; + rel1.relative: 0.5 1.0; + rel1.offset: 0 -1; + rel2.to_y: "elm.swallow.content"; + rel2.relative: 0.5 1.0; + rel2.offset: -1 -1; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.0; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + text.min: 1 1; + rel1.offset: 4 0; + rel2.offset: -5 0; + } + } + + part { name: "background"; + mouse_events: 0; + clip_to: "elm.background.progressbar"; + description { + state: "default" 0.0; + rel1 { + to: "elm.swallow.bar"; + relative: 0.0 0.0; + } + rel2 { + to: "elm.swallow.bar"; + relative: 1.0 1.0; + offset: -1 -1; + } + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + } + } + } + + part { name: "elm.progress.progressbar"; + mouse_events: 0; + clip_to: "elm.background.progressbar"; + description { + state: "default" 0.0; + min: 28 14; + fixed: 1 1; + rel1 { + to: "elm.swallow.bar"; + relative: 0.0 0.0; + } + rel2 { + to_x: "elm.swallow.bar"; + to_y: "elm.cur.progressbar"; + offset: -1 -1; + } + image { + normal: "bt_sm_base2.png"; + border: 6 6 6 6; + } + } + description { + state: "invert" 0.0; + inherit: "default" 0.0; + rel1 { + to_x: "elm.swallow.bar"; + to_y: "elm.cur.progressbar"; + } + rel2 { + to: "elm.swallow.bar"; + relative: 1.0 1.0; + } + } + description { + state: "state_begin" 0.0; + inherit: "default" 0.0; + rel1 { + to: "elm.swallow.bar"; + relative: 0.0 0.0; + } + rel2 { + to: "elm.swallow.bar"; + relative: 1.0 0.1; + } + } + description { + state: "state_end" 0.0; + inherit: "default" 0.0; + rel1 { + to: "elm.swallow.bar"; + relative: 0.0 0.9; + } + rel2 { + to: "elm.swallow.bar"; + relative: 1.0 1.0; + } + } + } + + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.progress.progressbar"; + rel2.to: "elm.progress.progressbar"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + } + + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.progress.progressbar"; + rel2.to: "elm.progress.progressbar"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + } + + part { name: "elm.cur.progressbar"; + mouse_events: 0; + dragable { + confine: "background"; + x: 0 0 0; + y: 1 1 1; + } + description { state: "default" 0.0; + min: 28 14; + fixed: 1 1; + visible: 0; + rel1 { + to: "background"; + relative: 0 0; + } + rel2.to: "background"; + } + } + + part { name: "elm.text.box"; + mouse_events: 0; + type: RECT; + description { state: "default" 0.0; + visible: 0; + rel1 { + to: "elm.text.status"; + offset: -2 -2; + } + rel2 { + to: "elm.text.status"; + offset: 2 2; + } + color: 255 255 255 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.text.status"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 0.5 1.0; + rel1.relative: 0.0 1.0; + rel1.offset: 2 0; + rel2.relative: 1.0 1.0; + rel2.offset: -2 0; + color: 0 0 0 255; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 10; + min: 0 0; + align: 0.5 0.0; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + fixed: 1 1; + visible: 1; + text.min: 1 1; + rel1.offset: 8 -9; + rel2.offset: -9 -9; + } + } + } + programs { + program { name: "label_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { name: "label_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { name: "icon_show"; + signal: "elm,state,icon,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.content"; + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.content"; + } + program { name: "units_show"; + signal: "elm,state,units,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text.status"; + target: "elm.text.box"; + } + program { name: "units_hide"; + signal: "elm,state,units,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text.status"; + target: "elm.text.box"; + } + program { name: "slide_to_end"; + action: STATE_SET "state_end" 0.0; + transition: LINEAR 0.5; + target: "elm.progress.progressbar"; + after: "slide_to_begin"; + } + program { name: "slide_to_begin"; + action: STATE_SET "state_begin" 0.0; + target: "elm.progress.progressbar"; + transition: LINEAR 0.5; + after: "slide_to_end"; + } + program { name: "start_pulse"; + signal: "elm,state,pulse,start"; + source: "elm"; + action: STATE_SET "state_begin" 0.0; + target: "elm.progress.progressbar"; + after: "slide_to_end"; + } + program { name: "stop_pulse"; + signal: "elm,state,pulse,stop"; + source: "elm"; + action: ACTION_STOP; + target: "slide_to_begin"; + target: "slide_to_end"; + target: "start_pulse"; + after: "state_pulse"; + } + program { name: "state_pulse"; + signal: "elm,state,pulse"; + source: "elm"; + action: STATE_SET "state_begin" 0.0; + target: "elm.progress.progressbar"; + after: "units_hide"; + } + program { name: "state_fraction"; + signal: "elm,state,fraction"; + source: "elm"; + action: ACTION_STOP; + target: "slide_to_begin"; + target: "slide_to_end"; + target: "start_pulse"; + action: STATE_SET "default" 0.0; + target: "elm.progress.progressbar"; + } + program { name: "set_invert_on"; + signal: "elm,state,inverted,on"; + source: "elm"; + action: STATE_SET "invert" 0.0; + target: "elm.progress.progressbar"; + target: "elm.cur.progressbar"; + } + program { name: "set_invert_off"; + signal: "elm,state,inverted,off"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.progress.progressbar"; + target: "elm.cur.progressbar"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/separator/horizontal/default"; + images { + image: "separator_h.png" COMP; + } + parts { + part { name: "separator"; // separator group + description { state: "default" 0.0; + min: 2 2; + rel1.offset: 4 4; + rel2.offset: -5 -5; + image { + normal: "separator_h.png"; + } + fill { + smooth: 0; + } + } + } + } + } + + /////////////////////////////////////////////////////////////////////////////// + group { name: "elm/separator/vertical/default"; + images { + image: "separator_v.png" COMP; + } + parts { + part { name: "separator"; // separator group + description { state: "default" 0.0; + min: 2 2; + rel1.offset: 4 4; + rel2.offset: -5 -5; + image { + normal: "separator_v.png"; + } + fill { + smooth: 0; + } + } + } + } + } + + group { name: "elm/progressbar/horizontal/wheel"; + images { + image: "busy-1.png" COMP; + image: "busy-2.png" COMP; + image: "busy-3.png" COMP; + image: "busy-4.png" COMP; + image: "busy-5.png" COMP; + image: "busy-6.png" COMP; + image: "busy-7.png" COMP; + image: "busy-8.png" COMP; + image: "busy-9.png" COMP; + } + parts { + part { name: "elm.background.progressbar"; + mouse_events: 0; + type: RECT; + description { + state: "default" 0.0; + } + } + part { name: "elm.swallow.bar"; + mouse_events: 0; + type: SWALLOW; + description { state: "default" 0.0; + min: 0 0; + max: 0 0; + visible: 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + min: 0 0; + max: 0 0; + visible: 0; + } + } + part { name: "background"; + mouse_events: 0; + clip_to: "elm.background.progressbar"; + description { + state: "default" 0.0; + min: 32 32; + max: 32 32; + visible: 1; + aspect: 1.0 1.0; + aspect_preference: BOTH; + image { + normal: "busy-9.png"; + border: 7 7 7 7; + } + } + description { + state: "pulse" 0.0; + inherit: "default" 0.0; + image { + normal: "busy-9.png"; + tween: "busy-1.png"; + tween: "busy-2.png"; + tween: "busy-3.png"; + tween: "busy-4.png"; + tween: "busy-5.png"; + tween: "busy-6.png"; + tween: "busy-7.png"; + tween: "busy-8.png"; + border: 7 7 7 7; + } + } + } + } + programs { + program { name: "start_pulse"; + signal: "elm,state,pulse,start"; + source: "elm"; + action: STATE_SET "pulse" 0.0; + target: "background"; + transition: LINEAR 0.5; + after: "start_pulse"; + } + program { name: "stop_pulse"; + signal: "elm,state,pulse,stop"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "background"; + } + } + } + + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/spinner/base/default"; + images { + image: "shelf_inset.png" COMP; + image: "bt_base1.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + image: "sp_bt_l.png" COMP; + image: "sp_bt_r.png" COMP; + } + parts { + part { name: "bg"; + type: RECT; + description { state: "default" 0.0; + min: 0 30; + rel1.offset: 1 1; + rel2.offset: -2 -2; + color: 255 255 255 0; + } + } + part { name: "conf_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "left_bt"; + mouse_events: 1; + description { state: "default" 0.0; + rel1 { to: "bg"; + offset: 3 3; + } + rel2 { to: "bg"; + offset: -4 -4; + } + align: 0.0 0.5; + min: 24 24; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + image { + normal: "bt_base1.png"; + border: 6 6 6 6; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "left_over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "left_bt"; + rel2 { to: "left_bt"; + relative: 1.0 0.5; + } + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "left_over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + rel1.to: "left_bt"; + rel2.to: "left_bt"; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "left_over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "left_bt"; + rel2.to: "left_bt"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "right_bt"; + mouse_events: 1; + description { state: "default" 0.0; + rel1 { to: "bg"; + offset: -26 3; + } + rel2 { to: "bg"; + offset: -4 -4; + } + align: 1.0 0.5; + min: 24 24; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + image { + normal: "bt_base1.png"; + border: 5 5 4 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "right_over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "right_bt"; + rel2 { to: "right_bt"; + relative: 1.0 0.5; + } + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "right_over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + rel1.to: "right_bt"; + rel2.to: "right_bt"; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "right_over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "right_bt"; + rel2.to: "right_bt"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "left_bt_icon"; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "left_bt"; + rel1.offset: 4 4; + rel2.to: "left_bt"; + rel2.offset: -5 -5; + align: 0.5 0.5; + min: 16 16; + aspect: 1.0 1.0; + aspect_preference: BOTH; + image.normal: "sp_bt_l.png"; + } + } + part { name: "right_bt_icon"; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "right_bt"; + rel1.offset: 4 4; + rel2.to: "right_bt"; + rel2.offset: -5 -5; + align: 0.5 0.5; + min: 16 16; + aspect: 1.0 1.0; + aspect_preference: BOTH; + image.normal: "sp_bt_r.png"; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 1; + align: 0.0 0.5; + rel1 { relative: 1.0 0.0; + offset: 3 2; + to_x: "left_bt"; + to_y: "bg"; + } + rel2 { relative: 0.0 1.0; + offset: -3 -2; + to_x: "right_bt"; + to_y: "bg"; + } + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 1 1; + align: 0.5 0.5; + } + } + description { state: "active" 0.0; + inherit: "default" 0.0; + visible: 0; + } + description { state: "disabled_active" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + } + part { name: "elm.dragable.slider"; + type: RECT; + mouse_events: 0; + scale: 1; + dragable { + x: 1 1 0; + y: 0 0 0; + } + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + fixed: 1 1; + color: 0 0 0 0; + } + } + part { name: "button_events"; + type: RECT; + dragable { + events: "elm.dragable.slider"; + } + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.text"; + rel2.to: "elm.text"; + color: 0 0 0 0; + } + } + part { name: "elm.swallow.entry"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 0; + align: 0.5 0.5; + rel1 { relative: 1.0 0.5; + offset: 3 2; + to_x: "left_bt"; + to_y: "bg"; + } + rel2 { relative: 0.0 0.5; + offset: -3 -2; + to_x: "right_bt"; + to_y: "bg"; + } + fixed: 1 1; + color: 0 0 0 0; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + description { state: "disabled_active" 0.0; + inherit: "default" 0.0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { name: "dec"; + signal: "mouse,down,1"; + source: "left_bt"; + action: SIGNAL_EMIT "elm,action,decrement,start" ""; + } + program { name: "dec2"; + signal: "mouse,up,1"; + source: "left_bt"; + action: SIGNAL_EMIT "elm,action,decrement,stop" ""; + } + program { name: "inc"; + signal: "mouse,down,1"; + source: "right_bt"; + action: SIGNAL_EMIT "elm,action,increment,start" ""; + } + program { name: "inc2"; + signal: "mouse,up,1"; + source: "right_bt"; + action: SIGNAL_EMIT "elm,action,increment,stop" ""; + } + program { + name: "left_bt_click"; + signal: "mouse,down,1"; + source: "left_over2"; + action: STATE_SET "clicked" 0.0; + target: "left_bt"; + } + program { + name: "left_bt_unclick"; + signal: "mouse,up,1"; + source: "left_over2"; + action: STATE_SET "default" 0.0; + target: "left_bt"; + } + program { + name: "left_bt_click2"; + signal: "mouse,down,1"; + source: "left_over3"; + action: STATE_SET "clicked" 0.0; + target: "left_over3"; + } + program { + name: "left_bt_unclick2"; + signal: "mouse,up,1"; + source: "left_over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "left_over3"; + } + program { + name: "left_bt_unclick3"; + signal: "mouse,up,1"; + source: "left_over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { + name: "left_bt_pressed_anim"; + signal: "elm,left,anim,activate"; + source: "elm"; + action: STATE_SET "clicked" 0.0; + target: "left_bt"; + target: "left_over3"; + after: "left_bt_unpressed_anim"; + } + program { + name: "left_bt_unpressed_anim"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "left_bt"; + target: "left_over3"; + } + + program { + name: "right_bt_click"; + signal: "mouse,down,1"; + source: "right_over2"; + action: STATE_SET "clicked" 0.0; + target: "right_bt"; + } + program { + name: "right_bt_unclick"; + signal: "mouse,up,1"; + source: "right_over2"; + action: STATE_SET "default" 0.0; + target: "right_bt"; + } + program { + name: "right_bt_click2"; + signal: "mouse,down,1"; + source: "right_over3"; + action: STATE_SET "clicked" 0.0; + target: "right_over3"; + } + program { + name: "right_bt_unclick2"; + signal: "mouse,up,1"; + source: "right_over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "right_over3"; + } + program { + name: "right_bt_unclick3"; + signal: "mouse,up,1"; + source: "right_over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { + name: "right_bt_pressed_anim"; + signal: "elm,right,anim,activate"; + source: "elm"; + action: STATE_SET "clicked" 0.0; + target: "right_bt"; + target: "right_over3"; + after: "right_bt_unpressed_anim"; + } + program { + name: "right_bt_unpressed_anim"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "right_bt"; + target: "right_over3"; + } + + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "left_bt"; + target: "left_over1"; + target: "left_over2"; + target: "right_bt"; + target: "right_over1"; + target: "right_over2"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "active")) + set_state(PART:"elm.text", "disabled_active", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + + get_state(PART:"elm.swallow.entry", st, 30, vl); + if (!strcmp(st, "active")) + set_state(PART:"elm.swallow.entry", "disabled_active", 0.0); + else + set_state(PART:"elm.swallow.entry", "disabled", 0.0); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "left_bt"; + target: "left_over1"; + target: "left_over2"; + target: "right_bt"; + target: "right_over1"; + target: "right_over2"; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_active")) + set_state(PART:"elm.text", "active", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + + get_state(PART:"elm.swallow.entry", st, 30, vl); + if (!strcmp(st, "disabled_active")) + set_state(PART:"elm.swallow.entry", "active", 0.0); + else + set_state(PART:"elm.swallow.entry", "default", 0.0); + } + } + program { name: "active"; + signal: "elm,state,active"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "elm.text"; + target: "elm.swallow.entry"; + } + program { name: "inactive"; + signal: "elm,state,inactive"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + target: "elm.swallow.entry"; + } + program { name: "toggle_text"; + signal: "mouse,up,1"; + source: "button_events"; + action: SIGNAL_EMIT "elm,action,entry,toggle" ""; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/spinner/base/vertical"; + images { + image: "shelf_inset.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + image: "up.png" COMP; + image: "down.png" COMP; + image: "bt_spinner_up.png" COMP; + image: "bt_spinner_down.png" COMP; + image: "bt_spinner_hilight.png" COMP; + } + parts { + part { name: "bg"; + type: RECT; + description { state: "default" 0.0; + min: 0 30; + rel1.offset: 1 1; + rel2.offset: -2 -2; + color: 255 255 255 0; + } + } + part { name: "conf_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "bg"; + relative: 0.0 0.0; + } + rel2 { + to: "bg"; + } + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "down_bt"; + mouse_events: 1; + description { state: "default" 0.0; + fixed: 1 1; + rel1 { + to: "up_bt"; + relative: 0 1; + offset: 0 1; + } + rel2 { + to_y: "bg"; + to_x: "up_bt"; + relative: 1 1; + offset: -1 -4; + } + align: 1.0 0.5; + min: 24 16; + image { + normal: "bt_spinner_down.png"; + border: 6 6 6 6; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_spinner_down.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "down_over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "down_bt"; + rel2.to: "down_bt"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "up_bt"; + mouse_events: 1; + description { state: "default" 0.0; + fixed: 1 0; + rel1 { to: "bg"; + relative: 0 0; + offset: 0 2; + } + rel2 { to: "bg"; + relative: 1 0.5; + offset: -3 0; + } + align: 1.0 0.5; + min: 24 16; + aspect: 1.5 1.0; + aspect_preference: BOTH; + image { + normal: "bt_spinner_up.png"; + border: 6 6 6 6; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_spinner_up.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "up_over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "up_bt"; + rel2 { to: "up_bt"; + relative: 1.0 0.5; + } + image { + normal: "bt_spinner_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "up_over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "up_bt"; + rel2.to: "up_bt"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "down_bt_icon"; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "down_bt"; + rel1.offset: 5 3; + rel2.to: "down_bt"; + rel2.offset: -6 -3; + align: 0.5 0.5; + image.normal: "down.png"; + } + } + part { name: "up_bt_icon"; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "up_bt"; + rel1.offset: 5 3; + rel2.to: "up_bt"; + rel2.offset: -6 -3; + align: 0.5 0.5; + image.normal: "up.png"; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 1; + align: 0.0 0.5; + rel1 { relative: 0.0 0.0; + offset: 3 2; + to_x: "bg"; + to_y: "bg"; + } + rel2 { relative: 0.0 1.0; + offset: -3 -2; + to_x: "down_bt"; + to_y: "bg"; + } + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 1 1; + align: 0.5 0.5; + } + } + description { state: "active" 0.0; + inherit: "default" 0.0; + visible: 0; + } + description { state: "disabled_active" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 0 0 0 128; + color3: 0 0 0 0; + } + } + part { name: "elm.dragable.slider"; + type: RECT; + mouse_events: 0; + scale: 1; + dragable { + x: 1 1 0; + y: 0 0 0; + } + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + fixed: 1 1; + color: 0 0 0 0; + } + } + part { name: "button_events"; + type: RECT; + dragable { + events: "elm.dragable.slider"; + } + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "elm.text"; + rel2.to: "elm.text"; + color: 0 0 0 0; + } + } + part { name: "elm.swallow.entry"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 0; + align: 0.5 0.5; + rel1 { relative: 0.0 0.5; + offset: 3 2; + to: "bg"; + } + rel2 { relative: 1.0 0.5; + offset: -3 -2; + to: "bg"; + } + fixed: 1 1; + color: 0 0 0 0; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + description { state: "disabled_active" 0.0; + inherit: "default" 0.0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "disabler"; + type: RECT; + description { state: "default" 0.0; + color: 0 0 0 0; + visible: 0; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + } + programs { + program { name: "text_show"; + signal: "elm,state,text,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.text"; + } + program { name: "text_hide"; + signal: "elm,state,text,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + } + program { name: "dec"; + signal: "mouse,down,1"; + source: "down_bt"; + action: SIGNAL_EMIT "elm,action,decrement,start" ""; + } + program { name: "dec2"; + signal: "mouse,up,1"; + source: "down_bt"; + action: SIGNAL_EMIT "elm,action,decrement,stop" ""; + } + program { name: "inc"; + signal: "mouse,down,1"; + source: "up_bt"; + action: SIGNAL_EMIT "elm,action,increment,start" ""; + } + program { name: "inc2"; + signal: "mouse,up,1"; + source: "up_bt"; + action: SIGNAL_EMIT "elm,action,increment,stop" ""; + } + program { + name: "down_bt_click2"; + signal: "mouse,down,1"; + source: "down_over3"; + action: STATE_SET "clicked" 0.0; + target: "down_over3"; + } + program { + name: "down_bt_unclick2"; + signal: "mouse,up,1"; + source: "down_over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "down_over3"; + } + program { + name: "up_bt_click2"; + signal: "mouse,down,1"; + source: "up_over3"; + action: STATE_SET "clicked" 0.0; + target: "up_over3"; + } + program { + name: "up_bt_unclick2"; + signal: "mouse,up,1"; + source: "up_over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "up_over3"; + } + program { name: "disable"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "down_bt"; + target: "up_bt"; + target: "disabler"; + after: "disable_text"; + } + program { name: "disable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "active")) + set_state(PART:"elm.text", "disabled_active", 0.0); + else + set_state(PART:"elm.text", "disabled", 0.0); + + get_state(PART:"elm.swallow.entry", st, 30, vl); + if (!strcmp(st, "active")) + set_state(PART:"elm.swallow.entry", "disabled_active", 0.0); + else + set_state(PART:"elm.swallow.entry", "disabled", 0.0); + } + } + program { name: "enable"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "down_bt"; + target: "up_bt"; + target: "disabler"; + after: "enable_text"; + } + program { name: "enable_text"; + script { + new st[31]; + new Float:vl; + get_state(PART:"elm.text", st, 30, vl); + if (!strcmp(st, "disabled_active")) + set_state(PART:"elm.text", "active", 0.0); + else + set_state(PART:"elm.text", "default", 0.0); + + get_state(PART:"elm.swallow.entry", st, 30, vl); + if (!strcmp(st, "disabled_active")) + set_state(PART:"elm.swallow.entry", "active", 0.0); + else + set_state(PART:"elm.swallow.entry", "default", 0.0); + } + } + program { name: "active"; + signal: "elm,state,active"; + source: "elm"; + action: STATE_SET "active" 0.0; + target: "elm.text"; + target: "elm.swallow.entry"; + } + program { name: "inactive"; + signal: "elm,state,inactive"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.text"; + target: "elm.swallow.entry"; + } + program { name: "toggle_text"; + signal: "mouse,up,1"; + source: "button_events"; + action: SIGNAL_EMIT "elm,action,entry,toggle" ""; + } + } + } + + + /////////////////////////////////////////////////////////////////////////////// + group { name: "elm/index/base/vertical/default"; + images { + image: "bt_base1.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + } + parts { + part { name: "clip"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + } + description { state: "active" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "clip2"; + type: RECT; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + } + description { state: "active" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "elm.swallow.index.0"; + type: SWALLOW; + clip_to: "clip"; + description { state: "default" 0.0; + align: 1.0 0.5; + fixed: 1 1; + rel1 { + relative: 1.0 0.5; + offset: -1 5; + } + rel2 { + relative: 1.0 0.5; + offset: -1 -6; + } + } + } + part { name: "button_image"; + mouse_events: 1; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "elm.text.body"; + offset: -5 -5; + } + rel2 { + to: "elm.text"; + offset: 4 4; + } + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + } + part { name: "elm.text.body"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + clip_to: "clip"; + description { state: "default" 0.0; + align: 1.0 0.5; + fixed: 1 1; + rel1 { + to: "elm.text"; + relative: 0.0 0.0; + offset: 5 0; + } + rel2 { + to: "elm.text"; + relative: 0.0 1.0; + offset: 5 -1; + } + color: 224 224 224 255; + color3: 0 0 0 64; + text { + font: "Sans,Edje-Vera"; + size: 20; + min: 1 1; + align: 1.0 0.5; + } + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + clip_to: "clip"; + description { state: "default" 0.0; + align: 1.0 0.5; + fixed: 1 1; + rel1 { + to_x: "elm.swallow.event.0"; + to_y: "elm.dragable.pointer"; + relative: 0.0 0.5; + offset: -16 0; + } + rel2 { + to_x: "elm.swallow.event.0"; + to_y: "elm.dragable.pointer"; + relative: 0.0 0.5; + offset: -16 -1; + } + color: 255 0 0 255; + color3: 0 0 0 64; + text { + font: "Sans,Edje-Vera"; + size: 20; + min: 1 1; + align: 1.0 0.5; + } + } + } + part { name: "over1"; + mouse_events: 0; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "button_image"; + } + rel2 { + to: "button_image"; + relative: 1.0 0.5; + } + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + clip_to: "clip"; + description { state: "default" 0.0; + rel1 { + to: "button_image"; + } + rel2 { + to: "button_image"; + } + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + } + part { name: "elm.dragable.pointer"; + type: RECT; + mouse_events: 0; + dragable { + x: 1 1 0; + y: 1 1 0; + } + clip_to: "clip"; + description { state: "default" 0.0; + fixed: 1 1; + min: 8 8; + max: 8 8; + rel1 { + relative: 0.0 0.0; + offset: 0 0; + } + rel2 { + relative: 0.0 0.0; + offset: 0 0; + } + color: 0 0 255 128; + } + } + part { name: "elm.swallow.event.0"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 0.5; + fixed: 1 1; + rel1 { + relative: 1.0 0.0; + offset: -1 0; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -1; + } + } + } + } + programs { + program { name: "active"; + signal: "elm,state,active"; + source: "elm"; + action: STATE_SET "active" 0.0; + transition: DECELERATE 0.5; + target: "clip"; + } + program { name: "inactive"; + signal: "elm,state,inactive"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "clip"; + } + } + } + + group { name: "elm/index/item/vertical/default"; + data.item: "stacking" "above"; + data.item: "selectraise" "on"; + images { + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { + name: "base_sh"; + mouse_events: 0; + description { + state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + rel1 { + offset: -16 0; + } + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + // min: 16 16; + rel1 { + to: "base"; + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -5 -5; + } + color: 0 0 0 128; + text { + font: "Sans"; + size: 10; + min: 1 1; + // min: 0 1; + align: 0.0 0.5; + } + } + description { state: "active" 0.0; + inherit: "default" 0.0; + color: 0 0 0 255; + } + } + } + programs { + program { name: "active"; + signal: "elm,state,active"; + source: "elm"; + action: STATE_SET "active" 0.0; + transition: DECELERATE 0.5; + target: "elm.text"; + target: "base"; + } + program { name: "inactive"; + signal: "elm,state,inactive"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "elm.text"; + target: "base"; + } + } + } + + group { name: "elm/index/item_odd/vertical/default"; + data.item: "stacking" "below"; + images { + image: "ilist_2.png" COMP; + } + parts { + part { + name: "base"; + mouse_events: 0; + description { + state: "default" 0.0; + image { + normal: "ilist_2.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + description { state: "active" 0.0; + inherit: "default" 0.0; + rel1 { + offset: -16 0; + } + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + // min: 16 16; + rel1 { + to: "base"; + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -5 -5; + } + color: 0 0 0 128; + text { + font: "Sans"; + size: 10; + min: 1 1; + // min: 0 1; + align: 0.0 0.5; + } + } + description { state: "active" 0.0; + inherit: "default" 0.0; + color: 0 0 0 255; + } + } + } + programs { + program { name: "active"; + signal: "elm,state,active"; + source: "elm"; + action: STATE_SET "active" 0.0; + transition: DECELERATE 0.5; + target: "elm.text"; + target: "base"; + } + program { name: "inactive"; + signal: "elm,state,inactive"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "elm.text"; + target: "base"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/gengrid/item/default/default"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { + state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "base_sh"; + mouse_events: 0; + description { state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { name: "base"; + mouse_events: 0; + description { state: "default" 0.0; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 1.0; + offset: 0 -10; + } + rel2 { + to_y: "elm.text"; + relative: 0.0 0.0; + offset: -1 -1; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.5 0.5; + rel1 { + relative: 0.0 0.0; + offset: -1 4; + } + rel2 { + to_y: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.0; + aspect: 1.0 1.0; + aspect_preference: HORIZONTAL; + rel1 { + relative: 1.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 5 5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1 { + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.5 0.0; + text_class: "grid_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + group { name: "elm/gengrid/item/default_style/default"; + styles + { + style { name: "gengrid_style"; + base: "font=Sans font_size=10 align=left valign=0.5 color=#000 text_class=grid_item"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "hilight" "+ font=Sans:style=Bold"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "tab" "\t"; + } + style { name: "gengrid_selected_style"; + base: "font=Sans font_size=10 align=left valign=0.5 color=#fff text_class=grid_item"; + tag: "br" "\n"; + tag: "ps" "ps"; + tag: "hilight" "+ font=Sans:style=Bold"; + tag: "b" "+ font=Sans:style=Bold"; + tag: "tab" "\t"; + } + } + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon elm.swallow.end"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_item_shadow.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "base_sh"; + mouse_events: 0; + description { state: "default" 0.0; + align: 0.0 0.0; + min: 0 10; + fixed: 1 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -1 0; + } + image { + normal: "ilist_item_shadow.png"; + } + fill.smooth: 0; + } + } + part { name: "base"; + mouse_events: 0; + description { state: "default" 0.0; + min: 16 28; + image { + normal: "ilist_1.png"; + border: 2 2 2 2; + } + fill.smooth: 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + relative: 0.0 0.0; + offset: -5 -5; + } + rel2 { + relative: 1.0 1.0; + offset: 4 4; + } + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + } + image.middle: SOLID; + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + rel1 { + relative: 0.0 0.0; + offset: -2 -2; + } + rel2 { + relative: 1.0 1.0; + offset: 1 1; + } + } + } + part { name: "elm.swallow.pad"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0.0 0.0; + offset: 4 4; + } + rel2 { + relative: 0.0 1.0; + offset: 4 -5; + } + } + } + part { name: "elm.swallow.icon"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + to_x: "elm.swallow.pad"; + relative: 1.0 0.0; + offset: -1 4; + } + rel2 { + to_x: "elm.swallow.pad"; + relative: 1.0 1.0; + offset: -1 -5; + } + } + } + part { name: "elm.swallow.end"; + clip_to: "disclip"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 1.0 0.5; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + rel1 { + relative: 1.0 0.0; + offset: -5 4; + } + rel2 { + relative: 1.0 1.0; + offset: -5 -5; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { + state: "default" 0.0; + align: 0.0 0.5; + fixed: 0 1; + rel1 { + to_x: "elm.swallow.icon"; + to_y: "base"; + relative: 1.0 0.5; + offset: 0 4; + } + rel2 { + to_x: "elm.swallow.end"; + to_y: "base"; + relative: 0.0 0.5; + offset: -1 -5; + } + text { + style: "gengrid_style"; + min: 1 1; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + text { + style: "gengrid_selected_style"; + } + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.relative: 1.0 0.5; + rel2.to: "bg"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.to: "bg"; + rel2.to: "bg"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + // signal: elm,state,%s,active + // a "check" item named %s went active + // signal: elm,state,%s,passive + // a "check" item named %s went passive + // default is passive + program { name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + + group { name: "elm/gengrid/item/up/default"; + data.item: "labels" "elm.text"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "arrow_up.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.offset: -3 -3; + rel2.offset: 2 2; + image { normal: "bt_sm_base1.png"; + border: 6 6 6 6; + middle: SOLID; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "image"; + type: IMAGE; + mouse_events: 0; + description { state: "default" 0.0; + aspect_preference: BOTH; + aspect: 1.0 1.0; + image.normal: "arrow_up.png"; + rel2 { + to_y: "elm.text"; + relative: 1.0 0.0; + offset: -1 -2; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1 { + relative: 0.0 1.0; + offset: 20 -25; + } + rel2 { + relative: 1.0 1.0; + offset: -21 -3; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.5 0.0; + text_class: "grid_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 224 224 224 255; + color3: 0 0 0 64; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.offset: -3 -3; + rel2 { + relative: 1.0 0.5; + offset: 2 -1; + } + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.offset: -3 -3; + rel2.offset: 2 2; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + program { name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + } + } + + group { name: "elm/gengrid/item/album-preview/default"; + data.item: "labels" "elm.text"; + data.item: "icons" "elm.swallow.icon.1 elm.swallow.icon.2 elm.swallow.icon.3 elm.swallow.icon.4"; + data.item: "states" "have_files"; + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "icon_folder.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "bg"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.offset: -3 -3; + rel2.offset: 2 2; + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + middle: SOLID; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "image"; + type: IMAGE; + mouse_events: 0; + description { state: "default" 0.0; + aspect_preference: BOTH; + aspect: 1.0 1.0; + image.normal: "icon_folder.png"; + rel2 { + to_y: "elm.text"; + relative: 1.0 0.0; + offset: -1 -2; + } + } + } + part { name: "have-files-clipper"; + type: RECT; + description { state: "default" 0.0; + color: 255 255 255 0; + visible: 0; + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + visible: 1; + } + } + part { name: "icon_box_margin"; + type: RECT; + mouse_events: 0; + clip_to: "have-files-clipper"; + description { state: "default" 0.0; + color: 0 0 0 255; + rel1 { + to: "icon_box"; + offset: -1 -1; + } + rel2 { + to: "icon_box"; + offset: 0 0; + } + } + } + part { name: "icon_box"; + type: RECT; + mouse_events: 0; + clip_to: "have-files-clipper"; + description { state: "default" 0.0; + color: 255 255 255 255; + align: 1.0 1.0; + min: 32 32; + rel1 { + relative: 0.25 0.25; + offset: 0 0; + } + rel2 { + relative: 1.0 0.0; + offset: -11 -4; + to_y: "elm.text"; + } + } + } + part { name: "elm.swallow.icon.1"; + type: SWALLOW; + mouse_events: 0; + clip_to: "have-files-clipper"; + description { state: "default" 0.0; + rel1 { + relative: 0.0 0.0; + to: "icon_box"; + } + rel2 { + relative: 0.5 0.5; + offset: -1 -1; + to: "icon_box"; + } + } + } + part { name: "elm.swallow.icon.2"; + type: SWALLOW; + mouse_events: 0; + clip_to: "have-files-clipper"; + description { state: "default" 0.0; + rel1 { + relative: 0.5 0.0; + to: "icon_box"; + } + rel2 { + relative: 1.0 0.5; + offset: -1 -1; + to: "icon_box"; + } + } + } + part { name: "elm.swallow.icon.3"; + type: SWALLOW; + mouse_events: 0; + clip_to: "have-files-clipper"; + description { state: "default" 0.0; + rel1 { + relative: 0.0 0.5; + to: "icon_box"; + } + rel2 { + relative: 0.5 1.0; + offset: -1 -1; + to: "icon_box"; + } + } + } + part { name: "elm.swallow.icon.4"; + type: SWALLOW; + mouse_events: 0; + clip_to: "have-files-clipper"; + description { state: "default" 0.0; + rel1 { + relative: 0.5 0.5; + to: "icon_box"; + } + rel2 { + relative: 1.0 1.0; + offset: -1 -1; + to: "icon_box"; + } + } + } + part { name: "elm.text"; + clip_to: "disclip"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1 { + relative: 0.0 1.0; + offset: 20 -30; + } + rel2 { + relative: 1.0 1.0; + offset: -21 -15; + } + color: 0 0 0 255; + color3: 0 0 0 0; + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.5 0.0; + text_class: "grid_item"; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "fg1"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.offset: -3 -3; + rel2 { + relative: 1.0 0.5; + offset: 2 -1; + } + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + clip_to: "disclip"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.offset: -3 -3; + rel2.offset: 2 2; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "disclip"; + type: RECT; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + color: 255 255 255 64; + } + } + } + programs { + program { name: "go_active"; + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + } + program { name: "go_passive"; + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + target: "elm.text"; + transition: LINEAR 0.1; + } + program { name: "go_disabled"; + signal: "elm,state,disabled"; + source: "elm"; + action: STATE_SET "disabled" 0.0; + target: "disclip"; + } + program { name: "go_enabled"; + signal: "elm,state,enabled"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "disclip"; + } + program { + signal: "elm,state,have_files,active"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "have-files-clipper"; + } + } + } + + group { name: "elm/gengrid/item/thumb/default"; + data { + item: "icons" "elm.swallow.icon"; + item: "labels" "elm.text"; + } + images { + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "thumb_shadow.png" COMP; + } + parts { + part { name: "event"; + type: RECT; + repeat_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "bg"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.offset: -3 -3; + rel2.offset: 2 2; + image { + normal: "bt_sm_base1.png"; + border: 6 6 6 6; + middle: SOLID; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "border-shadow"; + type: IMAGE; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "elm.swallow.icon"; + offset: -18 -18; + } + rel2 { + to_x: "elm.swallow.icon"; + to_y: "elm.text"; + offset: 17 17; + } + image { + normal: "thumb_shadow.png"; + border: 17 17 17 17; + middle: NONE; + } + } + } + part { name: "border"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1 { + to: "border-shadow"; + offset: 16 16; + } + rel2 { + to: "border-shadow"; + offset: -15 -15; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + mouse_events: 0; + description { state: "default" 0.0; + aspect_preference: BOTH; + aspect: 1.0 1.0; + rel1.offset: 0 8; + rel2 { + to_y: "elm.text"; + relative: 1.0 0.0; + offset: -1 -2; + } + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + color: 0 0 0 255; + color3: 0 0 0 0; + align: 0.5 1.0; + rel1 { + relative: 0.0 1.0; + offset: 20 -30; + } + rel2 { + relative: 1.0 1.0; + offset: -21 -15; + } + text { + font: "Sans"; + size: 10; + min: 0 1; + align: 0.5 0.0; + text_class: "grid_item"; + } + } + } + part { name: "fg1"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.offset: -3 -3; + rel2 { + relative: 1.0 0.5; + offset: 2 -1; + } + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "fg2"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1.offset: -3 -3; + rel2.offset: 2 2; + image { + image: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + description { state: "selected" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + } + programs { + program { + signal: "elm,state,selected"; + source: "elm"; + action: STATE_SET "selected" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + } + program { + signal: "elm,state,unselected"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "fg1"; + target: "fg2"; + transition: LINEAR 0.1; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/photocam/base/default"; + script { + public sbvis_v, sbvis_h, sbalways_v, sbalways_h, sbvis_timer; + public timer0(val) { + new v; + v = get_int(sbvis_v); + if (v) { + v = get_int(sbalways_v); + if (!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + v = get_int(sbvis_h); + if (v) { + v = get_int(sbalways_h); + if (!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + set_int(sbvis_timer, 0); + return 0; + } + } + images { + image: "shelf_inset.png" COMP; + image: "bt_sm_base2.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "busy-1.png" COMP; + image: "busy-2.png" COMP; + image: "busy-3.png" COMP; + image: "busy-4.png" COMP; + image: "busy-5.png" COMP; + image: "busy-6.png" COMP; + image: "busy-7.png" COMP; + image: "busy-8.png" COMP; + image: "busy-9.png" COMP; + } + parts { + part { name: "bg"; + type: RECT; + description { state: "default" 0.0; + rel1.offset: 1 1; + rel2.offset: -2 -2; + color: 255 255 255 0; + } + } + part { name: "clipper"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + } + part { name: "elm.swallow.content"; + clip_to: "clipper"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.offset: 1 1; + rel2.offset: -2 -2; + } + } + part { name: "busy_clip"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + } + description { state: "active" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "busy"; + clip_to: "busy_clip"; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + min: 32 32; + aspect: 1.0 1.0; + align: 1.0 1.0; + aspect_preference: BOTH; + rel1 { + relative: 0.9 0.9; + offset: -9 -9; + } + rel2 { + relative: 0.9 0.9; + offset: -9 -9; + } + image { + normal: "busy-9.png"; + tween: "busy-1.png"; + tween: "busy-2.png"; + tween: "busy-3.png"; + tween: "busy-4.png"; + tween: "busy-5.png"; + tween: "busy-6.png"; + tween: "busy-7.png"; + tween: "busy-8.png"; + } + } + } + part { name: "conf_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: 0 0; + rel2.offset: -1 -1; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar_clip"; + clip_to: "sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 10 17; + align: 1.0 0.0; + rel1 { + relative: 1.0 0.0; + offset: -2 0; + } + rel2 { + relative: 1.0 0.0; + offset: -2 -1; + to_y: "sb_hbar"; + } + } + } + part { name: "elm.dragable.vbar"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + dragable { + x: 0 0 0; + y: 1 1 0; + confine: "sb_vbar"; + } + description { state: "default" 0.0; + fixed: 1 1; + min: 10 17; + max: 10 99999; + rel1 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_vbar"; + } + rel2 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_vbar"; + } + image { + normal: "bt_sm_base2.png"; + border: 6 6 6 6; + middle: SOLID; + } + } + } + part { name: "sb_vbar_over1"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.vbar"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + } + part { name: "sb_vbar_over2"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.to: "elm.dragable.vbar"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + } + + part { name: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar_clip"; + clip_to: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 17 10; + align: 0.0 1.0; + rel1 { + relative: 0.0 1.0; + offset: 0 -2; + } + rel2 { + relative: 0.0 1.0; + offset: -1 -2; + to_x: "sb_vbar"; + } + } + } + part { name: "elm.dragable.hbar"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + dragable { + x: 1 1 0; + y: 0 0 0; + confine: "sb_hbar"; + } + description { state: "default" 0.0; + fixed: 1 1; + min: 17 10; + max: 99999 10; + rel1 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_hbar"; + } + rel2 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_hbar"; + } + image { + normal: "bt_sm_base2.png"; + border: 4 4 4 4; + middle: SOLID; + } + } + } + part { name: "sb_hbar_over1"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.hbar"; + image { + normal: "bt_sm_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "sb_hbar_over2"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.to: "elm.dragable.hbar"; + image { + normal: "bt_sm_shine.png"; + border: 4 4 4 0; + } + } + } + } + programs { + program { name: "load"; + signal: "load"; + source: ""; + script { + set_state(PART:"sb_hbar_clip", "hidden", 0.0); + set_state(PART:"sb_vbar_clip", "hidden", 0.0); + set_int(sbvis_h, 0); + set_int(sbvis_v, 0); + set_int(sbalways_v, 0); + set_int(sbalways_h, 0); + set_int(sbvis_timer, 0); + } + } + + program { name: "vbar_show"; + signal: "elm,action,show,vbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_hide"; + signal: "elm,action,hide,vbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_show_always"; + signal: "elm,action,show_always,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + set_int(sbalways_v, 1); + emit("do-show-vbar", ""); + set_int(sbvis_v, 1); + } + } + } + program { name: "vbar_show_notalways"; + signal: "elm,action,show_notalways,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_v); + if (v) { + set_int(sbalways_v, 0); + v = get_int(sbvis_v); + if (!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + } + } + program { name: "sb_vbar_show"; + signal: "do-show-vbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "sb_vbar_clip"; + } + program { name: "sb_vbar_hide"; + signal: "do-hide-vbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.5; + target: "sb_vbar_clip"; + } + + program { name: "hbar_show"; + signal: "elm,action,show,hbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_hide"; + signal: "elm,action,hide,hbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_show_always"; + signal: "elm,action,show_always,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + set_int(sbalways_h, 1); + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + } + } + program { name: "hbar_show_notalways"; + signal: "elm,action,show_notalways,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_h); + if (v) { + set_int(sbalways_h, 0); + v = get_int(sbvis_h); + if (!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + } + } + program { name: "sb_hbar_show"; + signal: "do-show-hbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "sb_hbar_clip"; + } + program { name: "sb_hbar_hide"; + signal: "do-hide-hbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.5; + target: "sb_hbar_clip"; + } + + program { name: "scroll"; + signal: "elm,action,scroll"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + emit("do-show-vbar", ""); + set_int(sbvis_v, 1); + } + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + v = get_int(sbvis_timer); + if (v > 0) cancel_timer(v); + v = timer(1.0, "timer0", 0); + set_int(sbvis_timer, v); + } + } + program { name: "go1"; + signal: "elm,state,busy,start"; + source: "elm"; + action: STATE_SET "active" 0.0; + transition: SINUSOIDAL 1.0; + target: "busy_clip"; + } + program { name: "go2"; + signal: "elm,state,busy,start"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "busy"; + after: "go2"; + } + program { name: "stop1"; + signal: "elm,state,busy,stop"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: SINUSOIDAL 1.0; + target: "busy_clip"; + after: "stop2"; + } + program { name: "stop2"; + action: ACTION_STOP; + target: "go2"; + } + } + } + + /////////////////////////////////////////////////////////////////////////////// + group { name: "elm/map/base/default"; + script { + public sbvis_v, sbvis_h, sbalways_v, sbalways_h, sbvis_timer; + public timer0(val) { + new v; + v = get_int(sbvis_v); + if (v) { + v = get_int(sbalways_v); + if (!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + v = get_int(sbvis_h); + if (v) { + v = get_int(sbalways_h); + if (!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + set_int(sbvis_timer, 0); + return 0; + } + } + images { + image: "shelf_inset.png" COMP; + image: "bt_sm_base2.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "busy-1.png" COMP; + image: "busy-2.png" COMP; + image: "busy-3.png" COMP; + image: "busy-4.png" COMP; + image: "busy-5.png" COMP; + image: "busy-6.png" COMP; + image: "busy-7.png" COMP; + image: "busy-8.png" COMP; + image: "busy-9.png" COMP; + } + parts { + part { name: "bg"; + type: RECT; + description { state: "default" 0.0; + rel1.offset: 1 1; + rel2.offset: -2 -2; + color: 255 255 255 0; + } + } + part { name: "clipper"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + } + part { name: "elm.swallow.content"; + clip_to: "clipper"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.offset: 1 1; + rel2.offset: -2 -2; + } + } + part { name: "busy_clip"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + } + description { state: "active" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "busy"; + clip_to: "busy_clip"; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + min: 32 32; + aspect: 1.0 1.0; + align: 1.0 1.0; + aspect_preference: BOTH; + rel1 { + relative: 0.9 0.9; + offset: -9 -9; + } + rel2 { + relative: 0.9 0.9; + offset: -9 -9; + } + image { + normal: "busy-9.png"; + tween: "busy-1.png"; + tween: "busy-2.png"; + tween: "busy-3.png"; + tween: "busy-4.png"; + tween: "busy-5.png"; + tween: "busy-6.png"; + tween: "busy-7.png"; + tween: "busy-8.png"; + } + } + } + part { name: "conf_over"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: 0 0; + rel2.offset: -1 -1; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar_clip"; + clip_to: "sb_vbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_vbar"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 10 17; + align: 1.0 0.0; + rel1 { + relative: 1.0 0.0; + offset: -2 0; + } + rel2 { + relative: 1.0 0.0; + offset: -2 -1; + to_y: "sb_hbar"; + } + } + } + part { name: "elm.dragable.vbar"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + dragable { + x: 0 0 0; + y: 1 1 0; + confine: "sb_vbar"; + } + description { state: "default" 0.0; + fixed: 1 1; + min: 10 17; + max: 10 99999; + rel1 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_vbar"; + } + rel2 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_vbar"; + } + image { + normal: "bt_sm_base2.png"; + border: 6 6 6 6; + middle: SOLID; + } + } + } + part { name: "sb_vbar_over1"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.vbar"; + image { + normal: "bt_sm_hilight.png"; + border: 6 6 6 0; + } + } + } + part { name: "sb_vbar_over2"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.vbar"; + rel2.to: "elm.dragable.vbar"; + image { + normal: "bt_sm_shine.png"; + border: 6 6 6 0; + } + } + } + + part { name: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar_clip"; + clip_to: "sb_hbar_clip_master"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + } + description { state: "hidden" 0.0; + visible: 0; + color: 255 255 255 0; + } + } + part { name: "sb_hbar"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + fixed: 1 1; + visible: 0; + min: 17 10; + align: 0.0 1.0; + rel1 { + relative: 0.0 1.0; + offset: 0 -2; + } + rel2 { + relative: 0.0 1.0; + offset: -1 -2; + to_x: "sb_vbar"; + } + } + } + part { name: "elm.dragable.hbar"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + dragable { + x: 1 1 0; + y: 0 0 0; + confine: "sb_hbar"; + } + description { state: "default" 0.0; + fixed: 1 1; + min: 17 10; + max: 99999 10; + rel1 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_hbar"; + } + rel2 { + relative: 0.5 0.5; + offset: 0 0; + to: "sb_hbar"; + } + image { + normal: "bt_sm_base2.png"; + border: 4 4 4 4; + middle: SOLID; + } + } + } + part { name: "sb_hbar_over1"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.relative: 1.0 0.5; + rel2.to: "elm.dragable.hbar"; + image { + normal: "bt_sm_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "sb_hbar_over2"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.dragable.hbar"; + rel2.to: "elm.dragable.hbar"; + image { + normal: "bt_sm_shine.png"; + border: 4 4 4 0; + } + } + } + } + programs { + program { name: "load"; + signal: "load"; + source: ""; + script { + set_state(PART:"sb_hbar_clip", "hidden", 0.0); + set_state(PART:"sb_vbar_clip", "hidden", 0.0); + set_int(sbvis_h, 0); + set_int(sbvis_v, 0); + set_int(sbalways_v, 0); + set_int(sbalways_h, 0); + set_int(sbvis_timer, 0); + } + } + + program { name: "vbar_show"; + signal: "elm,action,show,vbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_hide"; + signal: "elm,action,hide,vbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_vbar_clip_master"; + } + program { name: "vbar_show_always"; + signal: "elm,action,show_always,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + set_int(sbalways_v, 1); + emit("do-show-vbar", ""); + set_int(sbvis_v, 1); + } + } + } + program { name: "vbar_show_notalways"; + signal: "elm,action,show_notalways,vbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_v); + if (v) { + set_int(sbalways_v, 0); + v = get_int(sbvis_v); + if (!v) { + emit("do-hide-vbar", ""); + set_int(sbvis_v, 0); + } + } + } + } + program { name: "sb_vbar_show"; + signal: "do-show-vbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "sb_vbar_clip"; + } + program { name: "sb_vbar_hide"; + signal: "do-hide-vbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.5; + target: "sb_vbar_clip"; + } + + program { name: "hbar_show"; + signal: "elm,action,show,hbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_hide"; + signal: "elm,action,hide,hbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "sb_hbar_clip_master"; + } + program { name: "hbar_show_always"; + signal: "elm,action,show_always,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + set_int(sbalways_h, 1); + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + } + } + program { name: "hbar_show_notalways"; + signal: "elm,action,show_notalways,hbar"; + source: "elm"; + script { + new v; + v = get_int(sbalways_h); + if (v) { + set_int(sbalways_h, 0); + v = get_int(sbvis_h); + if (!v) { + emit("do-hide-hbar", ""); + set_int(sbvis_h, 0); + } + } + } + } + program { name: "sb_hbar_show"; + signal: "do-show-hbar"; + source: ""; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "sb_hbar_clip"; + } + program { name: "sb_hbar_hide"; + signal: "do-hide-hbar"; + source: ""; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.5; + target: "sb_hbar_clip"; + } + + program { name: "scroll"; + signal: "elm,action,scroll"; + source: "elm"; + script { + new v; + v = get_int(sbvis_v); + v |= get_int(sbalways_v); + if (!v) { + emit("do-show-vbar", ""); + set_int(sbvis_v, 1); + } + v = get_int(sbvis_h); + v |= get_int(sbalways_h); + if (!v) { + emit("do-show-hbar", ""); + set_int(sbvis_h, 1); + } + v = get_int(sbvis_timer); + if (v > 0) cancel_timer(v); + v = timer(1.0, "timer0", 0); + set_int(sbvis_timer, v); + } + } + program { name: "go1"; + signal: "elm,state,busy,start"; + source: "elm"; + action: STATE_SET "active" 0.0; + transition: SINUSOIDAL 1.0; + target: "busy_clip"; + } + program { name: "go2"; + signal: "elm,state,busy,start"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: LINEAR 0.5; + target: "busy"; + after: "go2"; + } + program { name: "stop1"; + signal: "elm,state,busy,stop"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: SINUSOIDAL 1.0; + target: "busy_clip"; + after: "stop2"; + } + program { name: "stop2"; + action: ACTION_STOP; + target: "go2"; + } + } + } + group { name: "elm/map/marker/radio/default"; + data { + item: size_w 24; + item: size_h 24; + item: size_max_w 58; + item: size_max_h 58; + } + images { + image: "map_item.png" COMP; + } + parts { + part { name: "whole"; + description { state: "default" 0.0; + } + } + part { name: "base"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + image.normal: "map_item.png"; + } + } + part { name: "elm.icon"; + type: SWALLOW; + clip_to: "whole"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.relative: 0.27 0.27; + rel2.relative: 0.73 0.73; + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.5 0.5; + color: 224 224 224 255; + color3: 0 0 0 64; + rel1.relative: 0.28 0.25; + rel2.relative: 0.75 0.75; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.5; + } + } + } + } + programs { + program { name: "open"; + signal: "mouse,clicked,1"; + source: "base"; + action: SIGNAL_EMIT "open" "elm"; + } + program { name: "bringin"; + signal: "mouse,down,1,double"; + source: "base"; + action: SIGNAL_EMIT "bringin" "elm"; + } + } + } + group { name: "elm/map/marker/radio2/default"; + data { + item: size_w 24; + item: size_h 24; + item: size_max_w 58; + item: size_max_h 58; + } + images { + image: "map_item_2.png" COMP; + } + parts { + part { name: "base"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + image.normal: "map_item_2.png"; + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.5 0.5; + color: 224 224 224 255; + color3: 0 0 0 64; + rel1.relative: 0.28 0.25; + rel2.relative: 0.75 0.75; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.5; + } + } + } + } + programs { + program { name: "open"; + signal: "mouse,clicked,1"; + source: "base"; + action: SIGNAL_EMIT "open" "elm"; + } + program { name: "bringin"; + signal: "mouse,down,1,double"; + source: "base"; + action: SIGNAL_EMIT "bringin" "elm"; + } + } + } + group { name: "elm/map/marker/empty/default"; + data { + item: size_w 22; + item: size_h 22; + item: size_max_w 64; + item: size_max_h 64; + } + parts { + part { name: "whole"; + description { state: "default" 0.0; + } + } + part { name: "base"; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + } + } + part { name: "elm.icon"; + type: SWALLOW; + clip_to: "whole"; + mouse_events: 0; + description { state: "default" 0.0; + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0.5 0.5; + color: 224 224 224 255; + color3: 0 0 0 64; + rel1.relative: 0.28 0.25; + rel2.relative: 0.75 0.75; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 0; + align: 0.5 0.5; + } + } + } + } + programs { + program { name: "open"; + signal: "mouse,clicked,1"; + source: "base"; + action: SIGNAL_EMIT "open" "elm"; + } + program { name: "bringin"; + signal: "mouse,down,1,double"; + source: "base"; + action: SIGNAL_EMIT "bringin" "elm"; + } + } + } + group { name: "elm/map/marker_bubble/default"; + images { + image: "bubble.png" COMP; + image: "bubble_shine.png" COMP; + } + data { + item: size_w 400; + item: size_h 100; + } + parts { + part { name: "clipper"; + mouse_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + } + description { state: "show" 0.0; + inherit: "default" 0.0; + color: 255 255 255 255; + } + } + part { name: "base0"; + mouse_events: 0; + clip_to: "clipper"; + description { state: "default" 0.0; + image { + normal: "bubble.png"; + border: 11 36 10 19; + } + image.middle: SOLID; + fill.smooth: 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clipper"; + description { state: "default" 0.0; + align: 0.5 0.5; + rel1 { + offset: 9 8; + } + rel2 { + offset: -10 -17; + } + } + } + part { name: "shine"; + mouse_events: 0; + clip_to: "clipper"; + description { state: "default" 0.0; + rel1 { + to: "base0"; + } + rel2 { + to: "base0"; + relative: 1.0 0.5; + } + image { + normal: "bubble_shine.png"; + border: 5 5 5 0; + } + fill.smooth: 0; + } + } + } + programs { + program { name: "show"; + signal: "show"; + action: STATE_SET "show" 0.0; + target: "clipper"; + transition: ACCELERATE 0.5; + } + } + } + +///////////////////////////////////////////////////////////////////////////// +// PANES +///////////////////////////////////////////////////////////////////////////// + group { + name: "elm/panes/vertical/default"; + images { + image: "bt_base1.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + image: "arrow_right.png" COMP; + image: "arrow_left.png" COMP; + } + parts + { + part + { + name: "whole"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + visible: 0; + } + } + + //2 contents + part + { + name: "whole_left"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + rel2.to_x: "elm.bar"; + rel2.relative: 0.0 1.0; + visible: 1; + } + } + part + { + name: "elm.swallow.left"; + type: SWALLOW; + clip_to: "whole_left"; + description + { + state: "default" 0.0; + rel1.to: "whole_left"; + rel2.to: "whole_left"; + } + } + + part + { + name: "whole_right"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + rel1.to_x: "elm.bar"; + rel1.relative: 1.0 0.0; + visible: 1; + } + } + part + { + name: "elm.swallow.right"; + type: SWALLOW; + clip_to: "whole_right"; + description + { + state: "default" 0.0; + rel1.to: "whole_right"; + rel2.to: "whole_right"; + } + } + //BAR + part { name: "elm.bar"; + mouse_events: 1; + dragable { + confine: "whole"; + x: 1 1 1; + y: 0 0 0; + } + description { state: "default" 0.0; + max: 15 9999; + min: 15 100; + rel1.relative: 0.0 0.5; + rel2.relative: 1.0 0.5; + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.bar"; + rel2.to: "elm.bar"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + rel1.to: "elm.bar"; + rel2.to: "elm.bar"; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "elm.bar"; + rel2.to: "elm.bar"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + + //Arrow + part { + name: "arrow_right"; + description { state: "default" 0.0; + min: 45 45; + max: 45 45; + color: 255 255 255 0; + + rel1.relative: 1.0 0.5; + rel1.to_x: "elm.bar"; + rel1.offset: 45/2 -45/2; + + rel2.relative: 1.0 0.5; + rel2.to_x: "elm.bar"; + rel2.offset: 45/2 45/2; + + image.normal: "arrow_right.png"; + + fixed: 1 1; + } + description { state: "anim_1" 0.0; + inherit: "default" 0.0; + color: 255 255 255 200; + rel1.offset: (45/2 + 10) -45/2; + rel2.offset: (45/2 +10) 45/2; + } + description { state: "anim_2" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + rel1.offset: (45/2 + 20) -45/2; + rel2.offset: (45/2 + 20) 45/2; + } + } + part { + name: "arrow_left"; + description { state: "default" 0.0; + min: 45 45; + max: 45 45; + color: 255 255 255 0; + + rel1.relative: 0.0 0.5; + rel1.to_x: "elm.bar"; + rel1.offset: -45/2 -45/2; + + rel2.relative: 0.0 0.5; + rel2.to_x: "elm.bar"; + rel2.offset: -45/2 45/2; + + image.normal: "arrow_left.png"; + + fixed: 1 1; + } + description { state: "anim_1" 0.0; + inherit: "default" 0.0; + color: 255 255 255 200; + rel1.offset: (-45/2 - 10) -45/2; + rel2.offset: (-45/2 - 10) 45/2; + } + description { state: "anim_2" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + rel1.offset: (-45/2 - 20) -45/2; + rel2.offset: (-45/2 - 20) 45/2; + } + } + + } + programs { + program { + name: "button_click"; + signal: "mouse,down,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,press" ""; + after: "button_click_anim"; + after: "arrow_anim_start"; + } + program { + name: "button_click_anim"; + action: STATE_SET "clicked" 0.0; + target: "elm.bar"; + } + program { + name: "button_unclick"; + signal: "mouse,up,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,unpress" ""; + after: "button_unclick_anim"; + after: "arrow_anim_stop"; + } + program { + name: "button_unclick_anim"; + action: STATE_SET "default" 0.0; + target: "elm.bar"; + } + program { + name: "button_click2"; + signal: "mouse,down,1"; + source: "over3"; + action: STATE_SET "clicked" 0.0; + target: "over3"; + } + program { + name: "button_unclick2"; + signal: "mouse,up,1"; + source: "over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "over3"; + } + program { + name: "button_unclick3"; + signal: "mouse,up,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { + name: "button_down_double"; + signal: "mouse,down,1,double"; + source: "over3"; + action: SIGNAL_EMIT "elm,action,click,double" ""; + } + + //arrows animation + program { + name: "arrow_anim_start"; + action: STATE_SET "anim_1" 0.0; + target: "arrow_right"; + target: "arrow_left"; + transition: LINEAR 0.6; + after: "arrow_anim_1"; + } + program { + name: "arrow_anim_1"; + action: STATE_SET "anim_2" 0.0; + target: "arrow_right"; + target: "arrow_left"; + transition: LINEAR 0.6; + after: "arrow_anim_2"; + } + program { + name: "arrow_anim_2"; + action: STATE_SET "default" 0.0; + target: "arrow_right"; + target: "arrow_left"; + after: "arrow_anim_start"; + } + program { + name: "arrow_anim_stop"; + action: ACTION_STOP; + target: "arrow_anim_start"; + target: "arrow_anim_1"; + target: "arrow_anim_2"; + after: "arrow_anim_stop_1"; + } + program { + name: "arrow_anim_stop_1"; + action: STATE_SET "default" 0.0; + target: "arrow_right"; + target: "arrow_left"; + transition: DECELERATE 0.4; + } + } + } + + group { + name: "elm/panes/horizontal/default"; + images { + image: "bt_base1.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + image: "arrow_up.png" COMP; + image: "arrow_down.png" COMP; + } + parts + { + part + { + name: "whole"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + visible: 0; + } + } + + //2 contents + part + { + name: "whole_left"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + rel2.to_y: "elm.bar"; + rel2.relative: 1.0 0.0; + visible: 1; + } + } + part + { + name: "elm.swallow.left"; + type: SWALLOW; + clip_to: "whole_left"; + description + { + state: "default" 0.0; + rel1.to: "whole_left"; + rel2.to: "whole_left"; + } + } + + part + { + name: "whole_right"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + rel1.to_y: "elm.bar"; + rel1.relative: 0.0 1.0; + visible: 1; + } + } + part + { + name: "elm.swallow.right"; + type: SWALLOW; + clip_to: "whole_right"; + description + { + state: "default" 0.0; + rel1.to: "whole_right"; + rel2.to: "whole_right"; + } + } + //BAR + part { name: "elm.bar"; + mouse_events: 1; + dragable { + confine: "whole"; + x: 0 0 0; + y: 1 1 1; + } + description { state: "default" 0.0; + max: 999 15; + min: 100 15; + rel1.relative: 0.5 0.0; + rel2.relative: 0.5 1.0; + image { + normal: "bt_base2.png"; + border: 7 7 7 7; + } + image.middle: SOLID; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part { name: "over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.bar"; + rel2.to: "elm.bar"; + rel2.relative: 1.0 0.5; + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + image { + normal: "bt_dis_hilight.png"; + border: 4 4 4 0; + } + } + } + part { name: "over2"; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + rel1.to: "elm.bar"; + rel2.to: "elm.bar"; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + description { state: "disabled" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "elm.bar"; + rel2.to: "elm.bar"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + + //Arrow + part { + name: "arrow_right"; + description { state: "default" 0.0; + min: 45 45; + max: 45 45; + color: 255 255 255 0; + + rel1.relative: 0.5 1.0; + rel1.to_y: "elm.bar"; + rel1.offset: -45/2 45/2; + + rel2.relative: 0.5 1.0; + rel2.to_y: "elm.bar"; + rel2.offset: 45/2 45/2; + + image.normal: "arrow_down.png"; + + fixed: 1 1; + } + description { state: "anim_1" 0.0; + inherit: "default" 0.0; + color: 255 255 255 200; + rel1.offset: -45/2 (45/2 +10); + rel2.offset: 45/2 (45/2 +10); + } + description { state: "anim_2" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + rel1.offset: -45/2 (45/2 + 20); + rel2.offset: 45/2 (45/2 + 20); + } + } + part { + name: "arrow_left"; + description { state: "default" 0.0; + min: 45 45; + max: 45 45; + color: 255 255 255 0; + + rel1.relative: 0.5 0.0; + rel1.to_y: "elm.bar"; + rel1.offset: -45/2 -45/2; + + rel2.relative: 0.5 0.0; + rel2.to_y: "elm.bar"; + rel2.offset: 45/2 -45/2; + + image.normal: "arrow_up.png"; + + fixed: 1 1; + } + description { state: "anim_1" 0.0; + inherit: "default" 0.0; + color: 255 255 255 200; + rel1.offset: -45/2 (-45/2 - 10); + rel2.offset: 45/2 (-45/2 - 10); + } + description { state: "anim_2" 0.0; + inherit: "default" 0.0; + color: 255 255 255 0; + rel1.offset: -45/2 (-45/2 - 20); + rel2.offset: 45/2 (-45/2 - 20); + } + } + + } + programs { + program { + name: "button_click"; + signal: "mouse,down,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,press" ""; + after: "button_click_anim"; + after: "arrow_anim_start"; + } + program { + name: "button_click_anim"; + action: STATE_SET "clicked" 0.0; + target: "elm.bar"; + } + program { + name: "button_unclick"; + signal: "mouse,up,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,unpress" ""; + after: "button_unclick_anim"; + after: "arrow_anim_stop"; + } + program { + name: "button_unclick_anim"; + action: STATE_SET "default" 0.0; + target: "elm.bar"; + } + program { + name: "button_click2"; + signal: "mouse,down,1"; + source: "over3"; + action: STATE_SET "clicked" 0.0; + target: "over3"; + } + program { + name: "button_unclick2"; + signal: "mouse,up,1"; + source: "over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "over3"; + } + program { + name: "button_unclick3"; + signal: "mouse,up,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + program { + name: "button_down_double"; + signal: "mouse,down,1,double"; + source: "over3"; + action: SIGNAL_EMIT "elm,action,click,double" ""; + } + + //arrows animation + program { + name: "arrow_anim_start"; + action: STATE_SET "anim_1" 0.0; + target: "arrow_right"; + target: "arrow_left"; + transition: LINEAR 0.6; + after: "arrow_anim_1"; + } + program { + name: "arrow_anim_1"; + action: STATE_SET "anim_2" 0.0; + target: "arrow_right"; + target: "arrow_left"; + transition: LINEAR 0.6; + after: "arrow_anim_2"; + } + program { + name: "arrow_anim_2"; + action: STATE_SET "default" 0.0; + target: "arrow_right"; + target: "arrow_left"; + after: "arrow_anim_start"; + } + program { + name: "arrow_anim_stop"; + action: ACTION_STOP; + target: "arrow_anim_start"; + target: "arrow_anim_1"; + target: "arrow_anim_2"; + after: "arrow_anim_stop_1"; + } + program { + name: "arrow_anim_stop_1"; + action: STATE_SET "default" 0.0; + target: "arrow_right"; + target: "arrow_left"; + transition: DECELERATE 0.4; + } + } + } + + + +///////////////////////////////////////////////////////////////////////////// +// PANEL +///////////////////////////////////////////////////////////////////////////// + group { + name: "elm/panel/base/left"; + alias: "elm/panel/base/top"; + images + { + image: "bt_base1.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "icon_arrow_left.png" COMP; + image: "icon_arrow_right.png" COMP; + } + data { + item: "focus_highlight" "on"; + } + parts + { + part { name: "focus_highlight"; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + to: "btn"; + offset: -8 -8; + } + rel2 { + to: "btn"; + offset: 7 7; + } + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + } + description { state: "enabled" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part + { + name: "bg"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + color: 255 255 255 0; + rel1.relative: 0.0 0.0; + rel1.offset: 0 0; + rel2.relative: 1.0 1.0; + rel2.offset: -1 -1; + } + description + { + state: "hidden" 0.0; + inherit: "default" 0.0; + rel1.relative: -1.0 0.0; + rel1.offset: 21 0; + rel2.relative: 0.0 1.0; + rel2.offset: 20 -1; + } + } + part + { + name: "base"; + type: IMAGE; + mouse_events: 0; + description + { + state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + rel2.offset: -20 -1; + image + { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part + { + name: "clipper"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + rel1 + { + offset: 4 4; + to: "base"; + } + rel2 + { + offset: -5 -5; + to: "base"; + } + } + } + part + { + name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clipper"; + description + { + state: "default" 0.0; + rel1.to: "clipper"; + rel2.to: "clipper"; + } + } + part + { + name: "btn"; + type: IMAGE; + mouse_events: 1; + description + { + state: "default" 0.0; + max: 32 48; + fixed: 1 1; + align: 0.0 0.5; + rel1 + { + relative: 1.0 0.0; + offset: -3 0; + to_x: "base"; + } + rel2.to_x: "bg"; + image + { + normal: "bt_base1.png"; + border: 0 5 4 12; + } + fill.smooth: 0; + } + description + { + state: "clicked" 0.0; + inherit: "default" 0.0; + } + } + part + { + name: "btn_over"; + type: IMAGE; + mouse_events: 0; + description + { + state: "default" 0.0; + rel1.to: "btn"; + rel2 + { + relative: 1.0 0.5; + to: "btn"; + } + image + { + normal: "bt_hilight.png"; + border: 0 7 7 0; + } + } + } + part + { + name: "btn_over2"; + type: IMAGE; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description + { + state: "default" 0.0; + rel1.to: "btn"; + rel2.to: "btn"; + image + { + normal: "bt_shine.png"; + border: 0 7 7 7; + } + } + } + part + { + name: "btn_over3"; + type: IMAGE; + mouse_events: 1; + repeat_events: 1; + description + { + state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "btn"; + rel2.to: "btn"; + image + { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth: 0; + } + description + { + state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part + { + name: "btn_icon"; + type: IMAGE; + repeat_events: 1; + description + { + state: "default" 0.0; + rel1.to: "btn"; + rel2.to: "btn"; + align: 0.5 0.5; + min: 16 16; + max: 16 16; + image.normal: "icon_arrow_left.png"; + } + description + { + state: "hidden" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_right.png"; + } + } + } + programs + { + program + { + name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "btn_icon"; + transition: LINEAR 0.5; + } + program + { + name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "bg"; + target: "btn_icon"; + transition: LINEAR 0.5; + } + program + { + name: "btn_click"; + signal: "mouse,down,1"; + source: "btn_over2"; + action: STATE_SET "clicked" 0.0; + target: "btn"; + } + program + { + name: "btn_unclick"; + signal: "mouse,up,1"; + source: "btn_over2"; + action: STATE_SET "default" 0.0; + target: "btn"; + } + program + { + name: "btn_click2"; + signal: "mouse,down,1"; + source: "btn_over3"; + action: STATE_SET "clicked" 0.0; + target: "btn_over3"; + } + program + { + name: "btn_unclick2"; + signal: "mouse,up,1"; + source: "btn_over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "btn_over3"; + } + program + { + name: "btn_unclick3"; + signal: "mouse,clicked,1"; + source: "btn_over2"; + action: SIGNAL_EMIT "elm,action,panel,toggle" ""; + } + program { name: "highlight_show"; + signal: "elm,action,focus_highlight,show"; + source: "elm"; + action: STATE_SET "enabled" 0.0; + transition: ACCELERATE 0.3; + target: "focus_highlight"; + } + program { name: "highlight_hide"; + signal: "elm,action,focus_highlight,hide"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.3; + target: "focus_highlight"; + } + } + } + + group { + name: "elm/panel/base/right"; + alias: "elm/panel/base/bottom"; + images + { + image: "bt_base1.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "icon_arrow_left.png" COMP; + image: "icon_arrow_right.png" COMP; + } + parts + { + part { name: "focus_highlight"; + description { state: "default" 0.0; + visible: 0; + color: 255 255 255 0; + rel1 { + to: "btn"; + offset: -8 -8; + } + rel2 { + to: "btn"; + offset: 7 7; + } + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + } + description { state: "enabled" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part + { + name: "bg"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + color: 255 255 255 0; + rel1.relative: 0.0 0.0; + rel1.offset: 0 0; + rel2.relative: 1.0 1.0; + rel2.offset: -1 -1; + } + description + { + state: "hidden" 0.0; + inherit: "default" 0.0; + rel1.relative: 1.0 0.0; + rel1.offset: -22 0; + rel2.relative: 2.0 1.0; + rel2.offset: -23 -1; + } + } + part + { + name: "base"; + type: IMAGE; + mouse_events: 0; + description + { + state: "default" 0.0; + rel1.to: "bg"; + rel1.offset: 20 0; + rel2.to: "bg"; + image + { + normal: "bt_dis_base.png"; + border: 4 4 4 4; + } + } + } + part + { + name: "clipper"; + type: RECT; + mouse_events: 0; + description + { + state: "default" 0.0; + rel1 + { + offset: 4 4; + to: "base"; + } + rel2 + { + offset: -5 -5; + to: "base"; + } + } + } + part + { + name: "elm.swallow.content"; + type: SWALLOW; + clip_to: "clipper"; + description + { + state: "default" 0.0; + rel1.to: "clipper"; + rel2.to: "clipper"; + } + } + part + { + name: "btn"; + type: IMAGE; + mouse_events: 1; + description + { + state: "default" 0.0; + max: 32 48; + fixed: 1 1; + align: 1 0.5; + rel1 + { + to_x: "bg"; + } + rel2 + { + offset: 2 0; + relative: 0.0 1; + to_x: "base"; + } + image + { + normal: "bt_base1.png"; + border: 5 0 4 12; + } + fill.smooth: 0; + } + description + { + state: "clicked" 0.0; + inherit: "default" 0.0; + } + } + part + { + name: "btn_over"; + type: IMAGE; + mouse_events: 0; + description + { + state: "default" 0.0; + rel1.to: "btn"; + rel2 + { + relative: 1.0 0.5; + to: "btn"; + } + image + { + normal: "bt_hilight.png"; + border: 7 0 7 0; + } + } + } + part + { + name: "btn_over2"; + type: IMAGE; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description + { + state: "default" 0.0; + rel1.to: "btn"; + rel2.to: "btn"; + image + { + normal: "bt_shine.png"; + border: 7 0 7 7; + } + } + } + part + { + name: "btn_over3"; + type: IMAGE; + mouse_events: 1; + repeat_events: 1; + description + { + state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "btn"; + rel2.to: "btn"; + image + { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth: 0; + } + description + { + state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part + { + name: "btn_icon"; + type: IMAGE; + repeat_events: 1; + description + { + state: "default" 0.0; + rel1.to: "btn"; + rel2.to: "btn"; + align: 0.5 0.5; + min: 16 16; + max: 16 16; + image.normal: "icon_arrow_right.png"; + } + description + { + state: "hidden" 0.0; + inherit: "default" 0.0; + image.normal: "icon_arrow_left.png"; + } + } + } + programs + { + program + { + name: "show"; + signal: "elm,action,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "bg"; + target: "btn_icon"; + transition: LINEAR 0.5; + } + program + { + name: "hide"; + signal: "elm,action,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "bg"; + target: "btn_icon"; + transition: LINEAR 0.5; + } + program + { + name: "btn_click"; + signal: "mouse,down,1"; + source: "btn_over2"; + action: STATE_SET "clicked" 0.0; + target: "btn"; + } + program + { + name: "btn_unclick"; + signal: "mouse,up,1"; + source: "btn_over2"; + action: STATE_SET "default" 0.0; + target: "btn"; + } + program + { + name: "btn_click2"; + signal: "mouse,down,1"; + source: "btn_over3"; + action: STATE_SET "clicked" 0.0; + target: "btn_over3"; + } + program + { + name: "btn_unclick2"; + signal: "mouse,up,1"; + source: "btn_over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "btn_over3"; + } + program + { + name: "btn_unclick3"; + signal: "mouse,up,1"; + source: "btn_over2"; + action: SIGNAL_EMIT "elm,action,panel,toggle" ""; + } + program { name: "highlight_show"; + signal: "elm,action,focus"; + source: "elm"; + action: STATE_SET "enabled" 0.0; + transition: ACCELERATE 0.3; + target: "focus_highlight"; + } + program { name: "highlight_hide"; + signal: "elm,action,unfocus"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.3; + target: "focus_highlight"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "elm/conformant/base/default"; + parts { + part { name: "elm.swallow.shelf"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 1; + align: 0.0 0.0; + rel2.relative: 1.0 0.0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.5 0.5; + rel1.relative: 0.0 1.0; + rel1.to_y: "elm.swallow.shelf"; + rel2.relative: 1.0 0.0; + rel2.to_y: "elm.swallow.panel"; + } + } + part { name: "elm.swallow.panel"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 1; + align: 0.0 1.0; + rel1.relative: 0.0 1.0; + } + } + } + } + +///////////////////////////////////////////////////////////////////////////// +// CALENDAR +///////////////////////////////////////////////////////////////////////////// +#define CH(_pos) \ + part { name: "ch_"#_pos".base"; \ + type: RECT; \ + description { state: "default" 0.0; \ + rel1 { \ + relative: (_pos % 7 * 7 / 8 / 6) 0; \ + to: "header"; \ + } \ + rel2 { \ + relative: (_pos % 7 * 7 / 8 / 6 + 1 / 8) 1; \ + to: "header"; \ + } \ + color: 0 0 0 0; \ + visible: 0; \ + } \ + } \ + part { name: "ch_"#_pos".text"; \ + type: TEXT; \ + effect: SOFT_SHADOW; \ + mouse_events: 0; \ + scale: 1; \ + clip_to: "ch_"#_pos".clipper"; \ + description { \ + state: "default" 0.0; \ + rel1.to: "ch_"#_pos".base"; \ + rel2.to: "ch_"#_pos".base"; \ + color: 0 0 0 255; \ + color3: 0 0 0 0; \ + text { \ + font: "Sans"; \ + size: 10; \ + min: 1 1; \ + align: 0.5 0.5; \ + } \ + } \ + } \ + part { name: "ch_"#_pos".clipper"; \ + type: RECT; \ + description { state: "default" 0.0; \ + rel1.to: "ch_"#_pos".base"; \ + rel2.to: "ch_"#_pos".base"; \ + } \ + } + +#define CIT(_pos) \ + part { name: "cit_"#_pos".rect"; \ + type: RECT; \ + description { state: "default" 0.0; \ + rel1 { \ + relative: (_pos % 7 * 7 / 8 / 6) \ + (_pos / 8 / 5 - _pos % 7 / 8 / 5); \ + to: "base"; \ + } \ + rel2 { \ + relative: (_pos % 7 * 7 / 8 / 6 + 1 / 8) \ + (_pos / 8 / 5 - _pos % 7 / 8 / 5 + 1 / 8); \ + to: "base"; \ + } \ + color: 0 0 0 0; \ + visible: 0; \ + } \ + } \ + part { \ + name: "cit_"#_pos".event"; \ + type: RECT; \ + repeat_events: 1; \ + description { \ + rel1.to: "cit_"#_pos".rect"; \ + rel2.to: "cit_"#_pos".rect"; \ + state: "default" 0.0; \ + color: 0 0 0 0; \ + } \ + } \ + part { name: "cit_"#_pos".shelf"; \ + type: RECT; \ + mouse_events: 0; \ + description { state: "default" 0.0; \ + rel1 { \ + to: "cit_"#_pos".bg"; \ + offset: -1 -1; \ + } \ + rel2 { \ + to: "cit_"#_pos".bg"; \ + } \ + color: 200 200 200 255; \ + } \ + } \ + part { name: "cit_"#_pos".hd"; \ + type: RECT; \ + mouse_events: 0; \ + description { state: "default" 0.0; \ + rel1 { \ + to: "cit_"#_pos".bg"; \ + offset: -1 -1; \ + } \ + rel2 { \ + to: "cit_"#_pos".bg"; \ + } \ + visible: 0; \ + color: 160 0 0 255; \ + } \ + description { state: "visible" 0.0; \ + inherit: "default" 0.0; \ + visible: 1; \ + } \ + } \ + part { \ + name: "cit_"#_pos".base_sh"; \ + mouse_events: 0; \ + description { \ + state: "default" 0.0; \ + align: 0.0 0.0; \ + min: 0 1; \ + rel1 { \ + to: "cit_"#_pos".base"; \ + relative: 0.0 1.0; \ + offset: 0 0; \ + } \ + rel2 { \ + to: "cit_"#_pos".base"; \ + relative: 1.0 1.05; \ + offset: -1 0; \ + } \ + image { \ + normal: "ilist_item_shadow.png"; \ + } \ + fill.smooth: 0; \ + } \ + } \ + part { \ + name: "cit_"#_pos".base"; \ + mouse_events: 0; \ + description { \ + state: "default" 0.0; \ + rel1.to: "cit_"#_pos".rect"; \ + rel2.to: "cit_"#_pos".rect"; \ + rel2.offset: -1 -1; \ + image { \ + normal: "ilist_1.png"; \ + border: 2 2 2 2; \ + } \ + fill.smooth: 0; \ + } \ + description { \ + state: "today" 0.0; \ + inherit: "default" 0.0; \ + image.normal: "ilist_2.png"; \ + color: 240 240 240 255; \ + } \ + } \ + part { name: "cit_"#_pos".bg"; \ + mouse_events: 0; \ + description { state: "default" 0.0; \ + visible: 0; \ + color: 255 255 255 0; \ + rel1 { \ + to: "cit_"#_pos".rect"; \ + relative: 0.0 0.0; \ + } \ + rel2 { \ + to: "cit_"#_pos".rect"; \ + relative: 1.0 1.0; \ + offset: -1 -1; \ + } \ + image { \ + normal: "bt_sm_base1.png"; \ + border: 6 6 6 6; \ + } \ + image.middle: SOLID; \ + } \ + description { state: "selected" 0.0; \ + inherit: "default" 0.0; \ + visible: 1; \ + color: 255 255 255 255; \ + } \ + } \ + part { name: "cit_"#_pos".text"; \ + type: TEXT; \ + effect: SOFT_SHADOW; \ + mouse_events: 0; \ + scale: 1; \ + description { \ + state: "default" 0.0; \ + rel1.to: "cit_"#_pos".bg"; \ + rel2.to: "cit_"#_pos".bg"; \ + color: 0 0 0 255; \ + color3: 0 0 0 0; \ + text { \ + font: "Sans"; \ + size: 10; \ + min: 1 1; \ + align: 0.5 0.5; \ + } \ + } \ + description { state: "selected" 0.0; \ + inherit: "default" 0.0; \ + color: 224 224 224 255; \ + color3: 0 0 0 64; \ + } \ + } \ + part { name: "cit_"#_pos".fg1"; \ + mouse_events: 0; \ + description { state: "default" 0.0; \ + visible: 0; \ + color: 255 255 255 0; \ + rel1.to: "cit_"#_pos".bg"; \ + rel2.relative: 1.0 0.5; \ + rel2.to: "cit_"#_pos".bg"; \ + image { \ + normal: "bt_sm_hilight.png"; \ + border: 6 6 6 0; \ + } \ + } \ + description { state: "selected" 0.0; \ + inherit: "default" 0.0; \ + visible: 1; \ + color: 255 255 255 255; \ + } \ + } \ + part { name: "cit_"#_pos".fg2"; \ + mouse_events: 0; \ + description { state: "default" 0.0; \ + visible: 0; \ + color: 255 255 255 0; \ + rel1.to: "cit_"#_pos".bg"; \ + rel2.to: "cit_"#_pos".bg"; \ + image { \ + normal: "bt_sm_shine.png"; \ + border: 6 6 6 0; \ + } \ + } \ + description { state: "selected" 0.0; \ + inherit: "default" 0.0; \ + visible: 1; \ + color: 255 255 255 255; \ + } \ + } \ + part { name: "cit_"#_pos".check"; \ + mouse_events: 0; \ + description { state: "default" 0.0; \ + rel1 { \ + to: "cit_"#_pos".bg"; \ + relative: 0.7 0.6; \ + offset: 1 1; \ + } \ + rel2 { \ + to: "cit_"#_pos".bg"; \ + relative: 1.1 1.2; \ + offset: -2 -2; \ + } \ + aspect: 1 1; \ + visible: 0; \ + color: 255 0 0 255; \ + image.normal: "check.png"; \ + } \ + description { state: "visible" 0.0; \ + inherit: "default" 0.0; \ + visible: 1; \ + } \ + } \ + programs { \ + program { \ + name: "cit_"#_pos".go_active"; \ + signal: "cit_"#_pos",selected"; \ + source: "elm"; \ + action: STATE_SET "selected" 0.0; \ + target: "cit_"#_pos".bg"; \ + target: "cit_"#_pos".fg1"; \ + target: "cit_"#_pos".fg2"; \ + target: "cit_"#_pos".text"; \ + } \ + program { \ + name: "cit_"#_pos".go_passive"; \ + signal: "cit_"#_pos",unselected"; \ + source: "elm"; \ + action: STATE_SET "default" 0.0; \ + target: "cit_"#_pos".bg"; \ + target: "cit_"#_pos".fg1"; \ + target: "cit_"#_pos".fg2"; \ + target: "cit_"#_pos".text"; \ + } \ + program { \ + name: "cit_"#_pos".is_today"; \ + signal: "cit_"#_pos",today"; \ + source: "elm"; \ + action: STATE_SET "today" 0.0; \ + target: "cit_"#_pos".base"; \ + } \ + program { \ + name: "cit_"#_pos".not_today"; \ + signal: "cit_"#_pos",not_today"; \ + source: "elm"; \ + action: STATE_SET "default" 0.0; \ + target: "cit_"#_pos".base"; \ + } \ + program { \ + source: "cit_"#_pos".clicked"; \ + signal: "mouse,clicked,1"; \ + source: "cit_"#_pos".event"; \ + action: SIGNAL_EMIT "elm,action,selected" #_pos; \ + } \ + program { \ + name: "cit_"#_pos".clear"; \ + signal: "cit_"#_pos",clear"; \ + source: "elm"; \ + action: STATE_SET "default" 0.0; \ + target: "cit_"#_pos".check"; \ + target: "cit_"#_pos".hd"; \ + } \ + program { \ + name: "cit_"#_pos".checked"; \ + signal: "cit_"#_pos",checked"; \ + source: "elm"; \ + action: STATE_SET "visible" 0.0; \ + target: "cit_"#_pos".check"; \ + } \ + program { \ + name: "cit_"#_pos".holiday"; \ + signal: "cit_"#_pos",holiday"; \ + source: "elm"; \ + action: STATE_SET "visible" 0.0; \ + target: "cit_"#_pos".hd"; \ + } \ + } + + group { name: "elm/calendar/base/default"; + images { + image: "shelf_inset.png" COMP; + image: "bt_base1.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.png" COMP; + image: "bt_glow.png" COMP; + image: "bt_dis_base.png" COMP; + image: "bt_dis_hilight.png" COMP; + image: "sp_bt_l.png" COMP; + image: "sp_bt_r.png" COMP; + image: "bt_sm_base1.png" COMP; + image: "bt_sm_shine.png" COMP; + image: "bt_sm_hilight.png" COMP; + image: "ilist_1.png" COMP; + image: "ilist_2.png" COMP; + image: "ilist_item_shadow.png" COMP; + image: "check.png" COMP; + } + parts { + part { name: "bg"; + type: RECT; + description { state: "default" 0.0; + min: 0 30; + rel1.offset: 1 1; + rel2.offset: -2 -2; + color: 255 255 255 0; + align: 0.0 0.5; + } + } + part { name: "spinner-base"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + min: 24 24; + max: 999999 24; + rel1.to: "bg"; + rel1.offset: 6 6; + rel2.to: "bg"; + rel2.offset: -7 -7; + color: 255 255 255 0; + align: 0.0 0.0; + } + } + part { name: "conf_over_spinner"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "spinner-base"; + rel1.offset: -3 -3; + rel2.to: "spinner-base"; + rel2.offset: 2 2; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "table-base"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + min: 256 220; + rel1.to_x: "bg"; + rel1.to_y: "spinner-base"; + rel1.offset: 6 6; + rel1.relative: 0 1; + rel2.to: "bg"; + rel2.offset: -7 -7; + color: 255 255 255 0; + } + } + part { name: "conf_over_table"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "table-base"; + rel1.offset: -3 -3; + rel2.to: "table-base"; + rel2.offset: 2 2; + image { + normal: "shelf_inset.png"; + border: 7 7 7 7; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "header"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "table-base"; + rel1.relative: 0 0; + rel2.to: "table-base"; + rel2.relative: 1 0.1; + color: 255 255 255 0; + } + } + part { name: "base"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to_x: "table-base"; + rel1.to_y: "header"; + rel1.relative: 0 1; + rel1.offset: 3 0; + rel2.to: "table-base"; + rel2.offset: -3 0; + color: 255 255 255 0; + } + } + part { name: "left_bt"; + mouse_events: 1; + description { state: "default" 0.0; + rel1 { to: "spinner-base"; + offset: 2 2; + } + rel2 { to: "spinner-base"; + offset: -3 -3; + } + align: 0.0 0.5; + min: 24 24; + max: 24 24; + fixed: 1 1; + image { + normal: "bt_base1.png"; + border: 6 6 6 6; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + } + part { name: "left_over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "left_bt"; + rel2 { to: "left_bt"; + relative: 1.0 0.5; + } + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + } + part { name: "left_over2"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "left_bt"; + rel2.to: "left_bt"; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + } + part { name: "left_over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "left_bt"; + rel2.to: "left_bt"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "right_bt"; + mouse_events: 1; + description { state: "default" 0.0; + rel1 { to: "spinner-base"; + offset: -27 3; + } + rel2 { to: "spinner-base"; + offset: -3 -3; + } + align: 1.0 0.5; + min: 24 24; + max: 24 24; + fixed: 1 1; + image { + normal: "bt_base1.png"; + border: 5 5 4 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_base1.png"; + image.middle: SOLID; + } + } + part { name: "right_over1"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "right_bt"; + rel2 { to: "right_bt"; + relative: 1.0 0.5; + } + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + } + part { name: "right_over2"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "right_bt"; + rel2.to: "right_bt"; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + } + part { name: "right_over3"; + mouse_events: 1; + repeat_events: 1; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "right_bt"; + rel2.to: "right_bt"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth : 0; + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "left_bt_icon"; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "left_bt"; + rel2.to: "left_bt"; + align: 0.5 0.5; + min: 16 16; + max: 16 16; + image.normal: "sp_bt_l.png"; + } + } + part { name: "right_bt_icon"; + repeat_events: 1; + description { state: "default" 0.0; + rel1.to: "right_bt"; + rel2.to: "right_bt"; + align: 0.5 0.5; + min: 16 16; + max: 16 16; + image.normal: "sp_bt_r.png"; + } + } + part { name: "month_text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + align: 0 0.5; + fixed: 1 1; + rel1 { relative: 1.0 0.0; + offset: 3 2; + to: "left_bt"; + to_y: "spinner-base"; + } + rel2 { relative: 0.0 1.0; + offset: -3 -2; + to_x: "right_bt"; + to_y: "spinner-base"; + } + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 12; + min: 1 1; + align: 0.5 0.5; + } + } + } + CH(0) CH(1) CH(2) CH(3) CH(4) CH(5) CH(6) + CIT(0) CIT(1) CIT(2) CIT(3) CIT(4) CIT(5) CIT(6) + CIT(7) CIT(8) CIT(9) CIT(10) CIT(11) CIT(12) CIT(13) + CIT(14) CIT(15) CIT(16) CIT(17) CIT(18) CIT(19) CIT(20) + CIT(21) CIT(22) CIT(23) CIT(24) CIT(25) CIT(26) CIT(27) + CIT(28) CIT(29) CIT(30) CIT(31) CIT(32) CIT(33) CIT(34) + CIT(35) CIT(36) CIT(37) CIT(38) CIT(39) CIT(40) CIT(41) + } + programs { + program { name: "dec_start"; + signal: "mouse,down,1"; + source: "left_bt"; + action: SIGNAL_EMIT "elm,action,decrement,start" ""; + } + program { name: "dec_stop"; + signal: "mouse,up,1"; + source: "left_bt"; + action: SIGNAL_EMIT "elm,action,stop" ""; + } + program { name: "inc_start"; + signal: "mouse,down,1"; + source: "right_bt"; + action: SIGNAL_EMIT "elm,action,increment,start" ""; + } + program { name: "inc_stop"; + signal: "mouse,up,1"; + source: "right_bt"; + action: SIGNAL_EMIT "elm,action,stop" ""; + } + program { + name: "left_bt_click"; + signal: "mouse,down,1"; + source: "left_over2"; + action: STATE_SET "clicked" 0.0; + target: "left_bt"; + } + program { + name: "left_bt_unclick"; + signal: "mouse,up,1"; + source: "left_over2"; + action: STATE_SET "default" 0.0; + target: "left_bt"; + } + program { + name: "left_bt_click2"; + signal: "mouse,down,1"; + source: "left_over3"; + action: STATE_SET "clicked" 0.0; + target: "left_over3"; + } + program { + name: "left_bt_unclick2"; + signal: "mouse,up,1"; + source: "left_over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "left_over3"; + } + program { + name: "right_bt_click"; + signal: "mouse,down,1"; + source: "right_over2"; + action: STATE_SET "clicked" 0.0; + target: "right_bt"; + } + program { + name: "right_bt_unclick"; + signal: "mouse,up,1"; + source: "right_over2"; + action: STATE_SET "default" 0.0; + target: "right_bt"; + } + program { + name: "right_bt_click2"; + signal: "mouse,down,1"; + source: "right_over3"; + action: STATE_SET "clicked" 0.0; + target: "right_over3"; + } + program { + name: "right_bt_unclick2"; + signal: "mouse,up,1"; + source: "right_over3"; + action: STATE_SET "default" 0.0; + transition: DECELERATE 0.5; + target: "right_over3"; + } + } + } + +#undef CIT +#undef CH + +//////////////////////////////////////////////////////////////////////////////// +// colorselector +//////////////////////////////////////////////////////////////////////////////// + group { name: "elm/colorselector/bg/default"; + parts { + part { name: "elm.colorbar_0"; + type: SWALLOW; + mouse_events: 1; + description { state: "default" 0.0; + min: 120 30; + rel1.relative: 0.0 0.00653594771; + rel2.relative: 1.0 0.254901961; + } + } + part { name: "elm.colorbar_1"; + type: SWALLOW; + mouse_events: 1; + description { state: "default" 0.0; + min: 120 30; + rel1.relative: 0.0 0.254901961; + rel2.relative: 1.0 0.503267974; + } + } + part { name: "elm.colorbar_2"; + type: SWALLOW; + mouse_events: 1; + description { state: "default" 0.0; + min: 120 30; + rel1.relative: 0.0 0.503267974; + rel2.relative: 1.0 0.751633987; + } + } + part { name: "elm.colorbar_3"; + type: SWALLOW; + mouse_events: 1; + description { state: "default" 0.0; + min: 120 30; + rel1.relative: 0.0 0.751633987; + rel2.relative: 1.0 1.0; + } + } + } + } + + group { name: "elm/colorselector/base/default"; + parts { + part { name: "elm.bar_bg"; + type: SWALLOW; + mouse_events: 0; + description { state: "default" 0.0; + min: 60 22; + rel1 { + relative: 0.0 0.8; + to_x: "elm.arrow_bg"; + to_y: "elm.arrow_icon"; + offset: 0 0; + } + rel2 { + relative: 1.0 0.83; + to_x: "elm.arrow_bg"; + offset: 0 0; + } + } + } + part { name: "elm.bar"; + type: SWALLOW; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "elm.bar_bg"; + rel2.to: "elm.bar_bg"; + } + } + part { name: "elm.arrow_bg"; + type: SWALLOW; + mouse_events: 1; + description { state: "default" 0.0; + rel1 { + relative: 1.0 0.17; + offset: 3 0; + to_x: "elm.l_button"; + } + rel2 { + relative: 0.0 0.83; + offset: -4 0; + to_x: "elm.r_button"; + } + } + } + part { name: "elm.arrow"; + type: RECT; + mouse_events: 1; + scale: 1; + description { state: "default" 0.0; + min: 1 1; + fixed: 1 1; + align: 0 0; + rel1 { + to_x: "elm.arrow_bg"; + } + rel2 { + relative: 0.0 0.17; + to_x: "elm.arrow_bg"; + } + color: 0 0 0 0; + visible: 0; + } + dragable { + confine: "elm.arrow_bg"; + x: 1 1 0; + y: 0 0 0; + } + } + part { name: "elm.arrow_icon"; + type: SWALLOW; + mouse_events: 0; + description { state: "default" 0.0; + min: 25 15; + max: 25 15; + fixed: 1 1; + align: 0.5 0; + rel1 { + to_x: "elm.arrow"; + } + rel2 { + relative: 1.0 0.0; + offset: 0 10; + to_x: "elm.arrow"; + } + } + } + part { name: "event"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + rel1 { + to: "elm.arrow_icon"; + } + rel2 { + to_x: "elm.arrow_icon"; + to_y: "elm.arrow_bg"; + offset: 0 0; + } + color: 0 0 0 0; + } + dragable { + events: "elm.arrow"; + } + } + part { name: "elm.l_button"; + type: SWALLOW; + mouse_events: 1; + scale: 1; + description { state: "default" 0.0; + min: 24 24; + fixed: 1 1; + rel1 { + relative: 0.0 0.0; + to_y: "elm.bar_bg"; + } + rel2 { + relative: 0.0 1.0; + to_y: "elm.bar_bg"; + } + align: 0.0 0.5; + } + } + part { name: "elm.r_button"; + type: SWALLOW; + mouse_events: 1; + scale: 1; + description { + state: "default" 0.0; + min: 24 24; + fixed: 1 1; + rel1 { + relative: 1.0 0.0; + to_y: "elm.bar_bg"; + } + rel2 { + relative: 1.0 1.0; + to_y: "elm.bar_bg"; + } + align: 1.0 0.5; + } + } + } + } + + group{ name: "elm/colorselector/image/colorbar_0"; + images { + image: "color_picker_color.png" COMP; + } + parts { + part { name: "colorbar_0_image"; + type: IMAGE; + mouse_events: 1; + description { state: "default" 0.0; + rel2.offset: -1 -1; + image.normal: "color_picker_color.png"; + } + } + } + } + + group { name: "elm/colorselector/image/colorbar_1"; + images { + image: "color_picker_opacity.png" COMP; + } + parts { + part { name: "colorbar_1_image"; + type: IMAGE; + mouse_events: 1; + description { state: "default" 0.0; + rel2.offset: -1 -1; + image.normal: "color_picker_opacity.png"; + } + } + } + } + + group { name: "elm/colorselector/image/colorbar_2"; + images { + image: "color_picker_brightness.png" COMP; + } + parts { + part { name: "colorbar_2_image"; + type: IMAGE; + mouse_events: 1; + description { state: "default" 0.0; + rel2.offset: -1 -1; + image.normal: "color_picker_brightness.png"; + } + } + } + } + + group { name: "elm/colorselector/image/colorbar_3"; + images { + image: "color_picker_alpha.png" COMP; + } + parts { + part { name: "colorbar_3_image"; + type: IMAGE; + mouse_events: 1; + description { state: "default" 0.0; + rel2.offset: -1 -1; + image.normal: "color_picker_alpha.png"; + } + } + } + } + + group { name: "elm/colorselector/bg_image/colorbar_3"; + images { + image: "color_picker_alpha_bg.png" COMP; + } + parts { + part { name: "colorbar_3_image"; + type: IMAGE; + mouse_events: 1; + description { state: "default" 0.0; + rel2.offset: -1 -1; + image.normal: "color_picker_alpha_bg.png"; + } + } + } + } + + group { name: "elm/colorselector/image/updown"; + images { + image: "icon_arrow_down.png" COMP; + } + parts { + part { name: "bg"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + color: 0 0 0 0; + } + } + part { name: "arrow_image"; + type: IMAGE; + mouse_events: 1; + description { state: "default" 0.0; + image.normal: "icon_arrow_down.png"; + } + } + } + } + + group { name: "elm/colorselector/button/left"; + images { + image: "bt_base1.png" COMP; + image: "bt_shine.png" COMP; + image: "sp_bt_l.png" COMP; + } + parts { + part { name: "button_image"; + mouse_events: 1; + description { state: "default" 0.0; + image.normal: "bt_base1.png"; + image.border: 6 6 6 6; + image.middle: SOLID; + } + + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_shine.png"; + image.border: 6 6 6 6; + image.middle: SOLID; + } + } + part { name: "btn_over"; + type: IMAGE; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button_image"; + rel2 { + relative: 1.0 0.5; + to: "button_image"; + } + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + } + part { name: "btn_over2"; + type: IMAGE; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + rel1.to: "button_image"; + rel2.to: "button_image"; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + } + part { name: "focus_image"; + type: IMAGE; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "button_image"; + rel2.to: "button_image"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth: 0; + + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "left_arrow"; + mouse_events: 1; + description { state: "default" 0.0; + min: 16 16; + max: 16 16; + image.normal: "sp_bt_l.png"; + } + } + } + + programs { + program { + name: "button_down"; + signal: "elm,state,left,button,down"; + source: "left_button"; + action: STATE_SET "clicked" 0.0; + target: "button_image"; + target: "focus_image"; + } + program { + name: "button_up"; + signal: "elm,state,left,button,up"; + source: "left_button"; + action: STATE_SET "default" 0.0; + target: "button_image"; + target: "focus_image"; + } + } + } + + group { name: "elm/colorselector/button/right"; + images { + image: "bt_base1.png" COMP; + image: "bt_shine.png" COMP; + image: "sp_bt_r.png" COMP; + } + parts { + part { name: "button_image"; + mouse_events: 1; + description { state: "default" 0.0; + image.normal: "bt_base1.png"; + image.border: 6 6 6 6; + image.middle: SOLID; + } + + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_shine.png"; + image.border: 6 6 6 6; + image.middle: SOLID; + } + } + part { name: "btn_over"; + type: IMAGE; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "button_image"; + rel2 { + relative: 1.0 0.5; + to: "button_image"; + } + image { + normal: "bt_hilight.png"; + border: 7 7 7 0; + } + } + } + part { name: "btn_over2"; + type: IMAGE; + mouse_events: 1; + repeat_events: 1; + ignore_flags: ON_HOLD; + description { state: "default" 0.0; + rel1.to: "button_image"; + rel2.to: "button_image"; + image { + normal: "bt_shine.png"; + border: 7 7 7 7; + } + } + } + part { name: "focus_image"; + type: IMAGE; + description { state: "default" 0.0; + color: 255 255 255 0; + rel1.to: "button_image"; + rel2.to: "button_image"; + image { + normal: "bt_glow.png"; + border: 12 12 12 12; + } + fill.smooth: 0; + + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + visible: 1; + color: 255 255 255 255; + } + } + part { name: "right_arrow"; + mouse_events: 1; + description { state: "default" 0.0; + min: 16 16; + max: 16 16; + image.normal: "sp_bt_r.png"; + } + } + } + + programs { + program { + name: "button_down"; + signal: "elm,state,right,button,down"; + source: "right_button"; + action: STATE_SET "clicked" 0.0; + target: "button_image"; + target: "focus_image"; + } + program { + name: "button_up"; + signal: "elm,state,right,button,up"; + source: "right_button"; + action: STATE_SET "default" 0.0; + target: "button_image"; + target: "focus_image"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// +#define FLIP_PICKER_MAX_LEN (50) +#define FLIP_PICKER_MAX_LEN_STR "50" + + group { name: "elm/flipselector/base/default"; + images { + image: "flip_base.png" COMP; + image: "flip_base_shad.png" COMP; + image: "flip_shad.png" COMP; + image: "arrow_up.png" COMP; + image: "arrow_down.png" COMP; + image: "flip_t.png" COMP; + image: "flip_b.png" COMP; + } + + data { + item: "max_len" FLIP_PICKER_MAX_LEN_STR; + } + + //FIXME: quick successive clicks on, say, up, lead to nastiness + script { + public cur, prev, next, lock; + + public animator_bottom_down(val, Float:pos) { + new tmp[FLIP_PICKER_MAX_LEN]; + + set_tween_state(PART:"bottom", pos, "shrink", 0.0, "default", 0.0); + set_tween_state(PART:"bottom_sheet", pos, "shrink", 0.0, "default", + 0.0); + set_tween_state(PART:"shadow", pos, "half", 0.0, "full", + 0.0); + + if (pos >= 1.0) { + set_state(PART:"shadow", "default", 0.0); + set_int(lock, 0); + + fetch_str(next, 0, tmp, FLIP_PICKER_MAX_LEN); + if (strncmp(tmp, "", FLIP_PICKER_MAX_LEN) != 0) { + replace_str(next, 0, ""); + message(MSG_STRING, 1, tmp); + } + } + } + + public animator_top_down(val, Float:pos) { + set_tween_state(PART:"top", pos, "default", 0.0, "shrink", 0.0); + set_tween_state(PART:"top_sheet", pos, "default", 0.0, "shrink", + 0.0); + set_tween_state(PART:"shadow", pos, "default", 0.0, "half", + 0.0); + + if (pos >= 1.0) + anim(0.2, "animator_bottom_down", val); + } + + public animator_bottom_up(val, Float:pos) { + set_tween_state(PART:"bottom", pos, "default", 0.0, "shrink", 0.0); + set_tween_state(PART:"bottom_sheet", pos, "default", 0.0, "shrink", + 0.0); + set_tween_state(PART:"shadow", pos, "full", 0.0, "half", + 0.0); + + if (pos >= 1.0) + anim(0.2, "animator_top_up", val); + } + + public animator_top_up(val, Float:pos) { + new tmp[FLIP_PICKER_MAX_LEN]; + + set_tween_state(PART:"top", pos, "shrink", 0.0, "default", 0.0); + set_tween_state(PART:"top_sheet", pos, "shrink", 0.0, "default", + 0.0); + set_tween_state(PART:"shadow", pos, "half", 0.0, "default", + 0.0); + + if (pos >= 1.0) { + set_state(PART:"shadow", "default", 0.0); + set_int(lock, 0); + + fetch_str(next, 0, tmp, FLIP_PICKER_MAX_LEN); + if (strncmp(tmp, "", FLIP_PICKER_MAX_LEN) != 0) { + replace_str(next, 0, ""); + message(MSG_STRING, 2, tmp); + } + } + } + + public message(Msg_Type:type, id, ...) { + /* flip down */ + if ((type == MSG_STRING) && (id == 1)) { + new value[FLIP_PICKER_MAX_LEN], tmp[FLIP_PICKER_MAX_LEN]; + + snprintf(value, FLIP_PICKER_MAX_LEN, "%s", getarg(2)); + + if (get_int(lock) == 1) { + replace_str(next, 0, value); + return; + } + + fetch_str(cur, 0, tmp, FLIP_PICKER_MAX_LEN); + + set_text(PART:"bottom_b", tmp); + + set_state(PART:"top", "shrink", 0.0); + set_text(PART:"top", tmp); + set_state(PART:"top", "default", 0.0); + set_text(PART:"top", tmp); + + replace_str(prev, 0, tmp); + + set_state(PART:"bottom", "default", 0.0); + set_text(PART:"bottom", value); + set_state(PART:"bottom", "shrink", 0.0); + set_text(PART:"bottom", value); + + set_text(PART:"top_b", value); + + replace_str(cur, 0, value); + + set_state(PART:"bottom_sheet", "shrink", 0.0); + set_state(PART:"top_sheet", "default", 0.0); + + set_int(lock, 1); + set_state(PART:"shadow", "default", 0.0); + anim(0.2, "animator_top_down", 1); + } + + /* flip up */ + if ((type == MSG_STRING) && (id == 2)) { + new value[FLIP_PICKER_MAX_LEN], tmp[FLIP_PICKER_MAX_LEN]; + + snprintf(value, FLIP_PICKER_MAX_LEN, "%s", getarg(2)); + + if (get_int(lock) == 1) { + replace_str(next, 0, value); + return; + } + + fetch_str(cur, 0, tmp, FLIP_PICKER_MAX_LEN); + + set_text(PART:"top_b", tmp); + + set_state(PART:"bottom", "shrink", 0.0); + set_text(PART:"bottom", tmp); + set_state(PART:"bottom", "default", 0.0); + set_text(PART:"bottom", tmp); + + replace_str(prev, 0, tmp); + + set_state(PART:"top", "default", 0.0); + set_text(PART:"top", value); + set_state(PART:"top", "shrink", 0.0); + set_text(PART:"top", value); + + set_text(PART:"bottom_b", value); + + replace_str(cur, 0, value); + + set_state(PART:"bottom_sheet", "default", 0.0); + set_state(PART:"top_sheet", "shrink", 0.0); + + set_int(lock, 1); + set_state(PART:"shadow", "full", 0.0); + anim(0.2, "animator_bottom_up", 1); + } + } + } + + parts { + part { name: "shad"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.offset: -4 -4; + rel1.to: "base"; + rel2.offset: 3 3; + rel2.to: "base"; + image { + normal: "flip_base_shad.png"; + border: 8 8 8 8; + } + } + } + + part { name: "base"; + scale: 1; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + min: 24 48; + image.normal: "flip_base.png"; + } + } + + part { name: "b"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel1.relative: 0.0 0.5; + rel2.to: "base"; + color: 0 0 0 0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + + part { name: "t"; + type: RECT; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + rel2.relative: 1.0 0.5; + color: 0 0 0 0; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + + part { name: "bottom_sheet_static"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 1; + rel1.to: "b"; + rel2.to: "b"; + image.normal: "flip_b.png"; + } + } + + part { name: "bottom_b"; + mouse_events: 0; + clip_to: "bottom_clipper"; + type: TEXT; + scale: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + color: 0 0 0 255; + color2: 0 0 0 255; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 30; + min: 1 1; + align: 0.5 0.5; + } + } + } + + part { name: "shadow"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "b"; + rel2.to: "b"; + rel2.relative: 1.0 0.0; + image.normal: "flip_shad.png"; + } + description { state: "half" 0.0; + inherit: "default" 0.0; + rel2.relative: 1.0 0.5; + } + description { state: "full" 0.0; + inherit: "default" 0.0; + rel2.relative: 1.0 1.0; + } + } + + part { name: "bottom_sheet"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 1; + rel1.to: "b"; + rel2.to: "b"; + image.normal: "flip_b.png"; + } + description { state: "shrink" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2.relative: 1.0 0.0; + } + } + + part { name: "bottom"; + mouse_events: 0; + clip_to: "bottom_clipper"; + type: TEXT; + scale: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + color: 0 0 0 255; + color2: 0 0 0 255; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 30; + min: 1 1; + align: 0.5 0.5; + } + } + description { state: "shrink" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel2.relative: 1.0 0.5; /* FIXME: same visual effect? --> MAP! */ + } + } + + part { name: "top_sheet_static"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 1; + rel1.to: "t"; + rel2.to: "t"; + image.normal: "flip_t.png"; + } + } + + part { name: "top_b"; + mouse_events: 0; + clip_to: "top_clipper"; + type: TEXT; + scale: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + color: 0 0 0 255; + color2: 0 0 0 255; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 30; + min: 1 1; + align: 0.5 0.5; + source: "top"; + } + } + } + + part { name: "top_sheet"; + mouse_events: 0; + description { state: "default" 0.0; + visible: 1; + rel1.to: "t"; + rel2.to: "t"; + image.normal: "flip_t.png"; + } + description { state: "shrink" 0.0; + inherit: "default" 0.0; + color: 128 128 128 255; + visible: 0; + rel1.relative: 0.0 1.0; + } + } + + part { name: "top"; + mouse_events: 0; + clip_to: "top_clipper"; + type: TEXT; + scale: 1; + description { state: "default" 0.0; + rel1.to: "base"; + rel2.to: "base"; + color: 0 0 0 255; + color2: 0 0 0 255; + text { + font: "Sans:style=Bold,Edje-Vera-Bold"; + size: 30; + min: 1 1; + align: 0.5 0.5; + } + } + description { state: "shrink" 0.0; + inherit: "default" 0.0; + visible: 0; + rel1.relative: 0.0 0.5; + } + } + + part { name: "arrow_top"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + min: 15 15; + max: 15 15; + align: 0.5 0.0; + rel1.to: "t"; + rel2.to: "t"; + image.normal: "arrow_up.png"; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + part { name: "arrow_bottom"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + min: 15 15; + max: 15 15; + align: 0.5 1.0; + rel1.to: "b"; + rel2.to: "b"; + image.normal: "arrow_down.png"; + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + } + } + + part { + type: RECT; + mouse_events: 0; + name: "top_clipper"; + description { + state: "default" 0.0; + rel1.to: "t"; + rel2.to: "t"; + visible: 1; + } + } + + part { + type: RECT; + mouse_events: 0; + name: "bottom_clipper"; + description { + state: "default" 0.0; + rel1.to: "b"; + rel2.to: "b"; + visible: 1; + } + } + } + + programs { + program { name: "load"; + signal: "load"; + source: ""; + script { + append_str(cur, ""); + append_str(prev, ""); + append_str(next, ""); + set_int(lock, 0); + } + } + + program { name: "hide_arrows"; + signal: "elm,state,button,hidden"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "arrow_top"; + target: "arrow_bottom"; + target: "t"; + target: "b"; + } + + program { name: "show_arrows"; + signal: "elm,state,button,visible"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "arrow_top"; + target: "arrow_bottom"; + target: "t"; + target: "b"; + } + + program { name: "up"; + signal: "mouse,down,1"; + source: "t"; + action: SIGNAL_EMIT "elm,action,up,start" ""; + } + program { name: "up,stop"; + signal: "mouse,up,1"; + source: "t"; + action: SIGNAL_EMIT "elm,action,up,stop" ""; + } + program { name: "down"; + signal: "mouse,down,1"; + source: "b"; + action: SIGNAL_EMIT "elm,action,down,start" ""; + } + program { name: "down,stop"; + signal: "mouse,up,1"; + source: "b"; + action: SIGNAL_EMIT "elm,action,down,stop" ""; + } + } + } + +//////////////////////////////////////////////////////////////////////////////// +// diskselector +//////////////////////////////////////////////////////////////////////////////// + group { name: "elm/diskselector/base/default"; + images { + image: "bar_shine.png" COMP; + } + + parts { + part { name: "bg"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + color: 0 0 0 255; + } + } + part { name: "shine_left"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel1.relative: -0.1 0; + rel2.to: "bg"; + rel2.relative: 0.1 1; + image.normal: "bar_shine.png"; + color: 255 255 255 120; + } + } + part { name: "shine_center"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel1.relative: 0.2 0; + rel2.to: "bg"; + rel2.relative: 0.8 1; + image.normal: "bar_shine.png"; + color: 255 255 255 180; + } + } + part { name: "shine_right"; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel1.relative: 0.9 0; + rel2.to: "bg"; + rel2.relative: 1.1 1; + image.normal: "bar_shine.png"; + color: 255 255 255 120; + } + } + part { name: "clipper"; + type: RECT; + mouse_events: 0; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + rel1.offset: 2 2; + rel2.offset: -3 -3; + } + } + part { name: "elm.swallow.content"; + clip_to: "clipper"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "bg"; + rel2.to: "bg"; + } + } + } + } + + group { name: "elm/diskselector/item/default"; + + data { + item: "len_threshold" "14"; + } + + parts { + part { name: "elm.swallow.icon"; + type: SWALLOW; + description { state: "default" 0.0; + fixed: 1 0; + align: 0.0 0.5; + rel1 { + relative: 0 0; + offset: 4 4; + } + rel2 { + relative: 0 1; + offset: 4 -5; + } + } + description { state: "show" 0.0; + inherit: "default" 0.0; + } + description { state: "default_small" 0.0; + inherit: "default" 0.0; + rel1.relative: 0 0.2; + rel2.relative: 0 0.8; + } + description { state: "left_side" 0.0; + inherit: "default" 0.0; + rel1.relative: 0 0.2; + rel2.relative: 0 0.8; + color: 255 255 255 160; + } + description { state: "right_side" 0.0; + inherit: "left_side" 0.0; + rel1.relative: 0.4 0.2; + rel2.relative: 0.4 0.8; + color: 255 255 255 160; + } + } + part { name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.relative: 1 0.0; + rel1.to_x: "elm.swallow.icon"; + rel2.relative: 1.0 1.0; + color: 255 255 255 255; + visible: 0; + text { + font: "Sans,Edje-Vera"; + size: 13; + align: 0.5 0.5; + min: 0 1; + } + } + description { state: "show" 0.0; + inherit: "default" 0.0; + visible: 1; + } + description { state: "default_small" 0.0; + inherit: "default" 0.0; + visible: 1; + text.size: 10; + } + description { state: "left_side" 0.0; + inherit: "default" 0.0; + color: 172 172 172 255; + text.size: 10; + visible: 1; + text.align: 0.2 0.5; + } + description { state: "right_side" 0.0; + inherit: "default" 0.0; + color: 172 172 172 255; + visible: 1; + text.size: 10; + text.align: 0.8 0.5; + } + } + } + + programs { + program { name: "center_text"; + signal: "elm,state,center"; + source: "elm"; + action: STATE_SET "show" 0.0; + target: "elm.text"; + target: "elm.swallow.icon"; + } + program { name: "center_small_text"; + signal: "elm,state,center_small"; + source: "elm"; + action: STATE_SET "default_small" 0.0; + target: "elm.text"; + target: "elm.swallow.icon"; + } + program { name: "l_side_text"; + signal: "elm,state,left_side"; + source: "elm"; + action: STATE_SET "left_side" 0.0; + target: "elm.text"; + target: "elm.swallow.icon"; + } + program { name: "r_side_text"; + signal: "elm,state,right_side"; + source: "elm"; + action: STATE_SET "right_side" 0.0; + target: "elm.text"; + target: "elm.swallow.icon"; + } + } + } + + group { name: "elm/entry/path/separator/default"; + images.image: "arrow_right.png" COMP; + parts { + part { name: "icon"; + mouse_events: 0; + description { state: "default" 0.0; + image.normal: "arrow_right.png"; + max: 64 64; + aspect: 1.0 1.0; + } + } + } + } + + group { name: "elm/fileselector/base/default"; + data { + item: "path_separator" ""; + } + parts { + part { name: "elm.swallow.up"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + min: 10 10; + fixed: 1 1; + rel2 { + relative: 0.0 0.0; + offset: 0 0; + } + } + } + part { name: "elm.swallow.home"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + min: 10 10; + fixed: 1 1; + rel1 { + to: "elm.swallow.up"; + relative: 1.0 0.0; + offset: 5 0; + } + rel2 { + to: "elm.swallow.up"; + relative: 1.0 1.0; + offset: 20 -1; + } + } + } + part { name: "elm.swallow.files"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 0.0; + min: 10 10; + fixed: 1 1; + rel1 { + to_y: "elm.swallow.home"; + relative: 0.0 1.0; + offset: 0 0; + } + rel2 { + to_y: "elm.swallow.path"; + relative: 1.0 0.0; + offset: -1 -1; + } + } + } + part { name: "elm.swallow.path"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.5 1.0; + fixed: 1 1; + rel1 { + to_y: "elm.swallow.filename"; + relative: 0.0 0.0; + offset: 0 -1; + } + rel2 { + to_y: "elm.swallow.filename"; + relative: 1.0 0.0; + offset: -1 -1; + } + } + } + part { name: "elm.swallow.filename"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.5 1.0; + fixed: 1 1; + rel1 { + to_y: "elm.swallow.ok"; + relative: 0.0 0.0; + offset: 0 -1; + } + rel2 { + to_y: "elm.swallow.ok"; + relative: 1.0 0.0; + offset: -1 -1; + } + } + } + part { name: "elm.swallow.cancel"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 1.0; + fixed: 1 1; + rel1 { + to: "elm.swallow.ok"; + relative: 0.0 0.0; + offset: -3 0; + } + rel2 { + to: "elm.swallow.ok"; + relative: 0.0 1.0; + offset: -3 -1; + } + } + } + part { name: "elm.swallow.ok"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 1.0; + fixed: 1 1; + rel1 { + relative: 1.0 1.0; + offset: -1 -1; + } + } + } + } + } + + group { name: "elm/fileselector_entry/base/default"; + parts { + part { name: "elm.swallow.entry"; + type: SWALLOW; + description { state: "default" 0.0; + align: 0.0 0.0; + min: 50 10; + rel2 { to_x: "elm.swallow.button"; + relative: 0.0 1.0; + offset: -1 -1; + } + } + } + part { name: "elm.swallow.button"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 0.0; + min: 10 10; + fixed: 1 1; + rel1 { + relative: 1.0 0.0; + offset: -21 0; + } + } + } + } + } + +//////////////////////////////////////////////////////////////////////// +// Standard layouts to be used // +//////////////////////////////////////////////////////////////////////// + /* application with toolbar and main content area */ + group { name: "elm/layout/application/toolbar-content"; + parts { + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { to_y: "elm.external.toolbar"; + relative: 0.0 1.0; + offset: -1 1; + } + } + } + + part { name: "elm.external.toolbar"; + type: EXTERNAL; + source: "elm/toolbar"; + description { state: "default" 0.0; + align: 0.5 0.0; + fixed: 0 1; + rel2 { + relative: 1.0 0.0; + offset: -1 47; + } + } + } + } + } + + /* application with toolbar and main content area with a back button and title area */ + group { name: "elm/layout/application/toolbar-content-back"; + parts { + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { to_y: "title_clipper"; + relative: 0.0 1.0; + offset: -1 1; + } + } + } + + part { name: "elm.external.toolbar"; + type: EXTERNAL; + source: "elm/toolbar"; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 0.0; + rel2 { + relative: 1.0 0.0; + offset: -1 47; + } + } + } + part { name: "title_clipper"; + type: RECT; + description { state: "default" 0.0; + visible: 1; + rel1 { + to_y: "back"; + } + rel2 { + to_y: "back"; + } + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2 { + relative: 1.0 0.0; + } + } + } + part { name: "back_clipper"; + type: RECT; + clip_to: "title_clipper"; + description { state: "default" 0.0; + visible: 1; + } + description { state: "hidden" 0.0; + visible: 0; + } + } + part { name: "back"; + type: EXTERNAL; + source: "elm/button"; + clip_to: "back_clipper"; + description { state: "default" 0.0; + align: 0.0 0.0; + fixed: 1 1; + rel1 { to_y: "elm.external.toolbar"; + relative: 0.0 1.0; + offset: 0 1; + } + rel2 { to_y: "elm.external.toolbar"; + relative: 0.0 1.0; + offset: 50 32; + } + params.string: "label" "Back"; + } + } + programs { + program { + signal: "clicked"; + source: "back"; + action: SIGNAL_EMIT "elm,action,back" ""; + } + program { + signal: "elm,back,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "back_clipper"; + } + program { + signal: "elm,back,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "back_clipper"; + } + program { + signal: "elm,title,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.1; + target: "title_clipper"; + } + program { + signal: "elm,title,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "title_clipper"; + } + } + + part { name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 0.0; + fixed: 1 1; + rel1 { to_y: "elm.external.toolbar"; + relative: 1.0 1.0; + offset: -2 1; + } + rel2 { to_y: "elm.external.toolbar"; + relative: 1.0 1.0; + offset: -1 32; + } + } + } + + part { name: "elm.text.title"; + type: TEXT; + effect: SOFT_SHADOW; + scale: 1; + description { state: "default" 0.0; + rel1 { to_y: "elm.external.toolbar"; + to_x: "back"; + relative: 1.0 1.0; + offset: 2 1; + } + rel2 { to_y: "back"; + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -3 -1; + } + text { + font: "Sans:style=Bold"; + size: 12; + } + } + } + } + } + + /* application with toolbar and main content area with a back and next buttons and title area */ + group { name: "elm/layout/application/toolbar-content-back-next"; + parts { + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { to_y: "title_clipper"; + relative: 0.0 1.0; + offset: -1 1; + } + } + } + + part { name: "elm.external.toolbar"; + type: EXTERNAL; + source: "elm/toolbar"; + description { state: "default" 0.0; + fixed: 0 1; + align: 0.5 0.0; + rel2 { + relative: 1.0 0.0; + offset: -1 47; + } + } + } + part { name: "title_clipper"; + type: RECT; + description { state: "default" 0.0; + visible: 1; + rel1 { + to_y: "back"; + } + rel2 { + to_y: "back"; + } + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2 { + relative: 1.0 0.0; + } + } + } + part { name: "back"; + type: EXTERNAL; + source: "elm/button"; + clip_to: "back_clipper"; + description { state: "default" 0.0; + align: 0.0 0.0; + fixed: 1 1; + rel1 { to_y: "elm.external.toolbar"; + relative: 0.0 1.0; + offset: 0 1; + } + rel2 { to_y: "elm.external.toolbar"; + relative: 0.0 1.0; + offset: 50 32; + } + params.string: "label" "Back"; + } + } + part { name: "back_clipper"; + type: RECT; + clip_to: "title_clipper"; + description { state: "default" 0.0; + visible: 1; + } + description { state: "hidden" 0.0; + visible: 0; + } + } + part { name: "next"; + type: EXTERNAL; + source: "elm/button"; + clip_to: "next_clipper"; + description { state: "default" 0.0; + align: 1.0 0.0; + fixed: 1 1; + rel1 { to_y: "elm.external.toolbar"; + relative: 1.0 1.0; + offset: -2 1; + } + rel2 { to_y: "elm.external.toolbar"; + relative: 1.0 1.0; + offset: -1 32; + } + params.string: "label" "Next"; + } + } + part { name: "next_clipper"; + type: RECT; + clip_to: "title_clipper"; + description { state: "default" 0.0; + visible: 1; + } + description { state: "hidden" 0.0; + visible: 0; + } + } + programs { + program { + signal: "clicked"; + source: "back"; + action: SIGNAL_EMIT "elm,action,back" ""; + } + program { + signal: "elm,title,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.1; + target: "title_clipper"; + } + program { + signal: "elm,title,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "title_clipper"; + } + program { + signal: "elm,back,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "back_clipper"; + } + program { + signal: "elm,back,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "back_clipper"; + } + program { + signal: "clicked"; + source: "next"; + action: SIGNAL_EMIT "elm,action,next" ""; + } + program { + signal: "elm,next,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "next_clipper"; + } + program { + signal: "elm,next,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "next_clipper"; + } + } + part { name: "elm.text.title"; + type: TEXT; + effect: SOFT_SHADOW; + scale: 1; + clip_to: "title_clipper"; + description { state: "default" 0.0; + rel1 { to_y: "elm.external.toolbar"; + to_x: "back"; + relative: 1.0 1.0; + offset: 2 1; + } + rel2 { to_y: "back"; + to_x: "next"; + relative: 0.0 1.0; + offset: -3 -1; + } + text { + font: "Sans:style=Bold"; + size: 12; + } + } + } + } + } + /* application with a main content area with a back button and title area */ + group { name: "elm/layout/application/content-back"; + parts { + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { to_y: "title_clipper"; + relative: 0.0 1.0; + offset: -1 1; + } + } + } + part { name: "title_clipper"; + type: RECT; + description { state: "default" 0.0; + visible: 1; + rel1 { + to_y: "back"; + } + rel2 { + to_y: "back"; + } + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2 { + relative: 1.0 0.0; + } + } + } + part { name: "back_clipper"; + type: RECT; + clip_to: "title_clipper"; + description { state: "default" 0.0; + visible: 1; + } + description { state: "hidden" 0.0; + visible: 0; + } + } + part { name: "back"; + type: EXTERNAL; + source: "elm/button"; + clip_to: "back_clipper"; + description { state: "default" 0.0; + align: 0.0 0.0; + fixed: 1 1; + rel1 { + relative: 0.0 0.0; + offset: 0 1; + } + rel2 { + relative: 0.0 0.0; + offset: 50 32; + } + params.string: "label" "Back"; + } + } + programs { + program { + signal: "clicked"; + source: "back"; + action: SIGNAL_EMIT "elm,action,back" ""; + } + program { + signal: "elm,back,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "back_clipper"; + } + program { + signal: "elm,back,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "back_clipper"; + } + program { + signal: "elm,title,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.1; + target: "title_clipper"; + } + program { + signal: "elm,title,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "title_clipper"; + } + } + + part { name: "elm.swallow.end"; + type: SWALLOW; + description { state: "default" 0.0; + align: 1.0 0.0; + fixed: 1 1; + rel1 { + relative: 1.0 0.0; + offset: -2 1; + } + rel2 { + relative: 1.0 1.0; + offset: -1 32; + } + } + } + + part { name: "elm.text.title"; + type: TEXT; + effect: SOFT_SHADOW; + scale: 1; + description { state: "default" 0.0; + rel1 { + to_x: "back"; + relative: 1.0 0.0; + offset: 2 1; + } + rel2 { to_y: "back"; + to_x: "elm.swallow.end"; + relative: 0.0 1.0; + offset: -3 -1; + } + text { + font: "Sans:style=Bold"; + size: 12; + } + } + } + } + } + + /* application with a main content area with a back and next buttons and title area */ + group { name: "elm/layout/application/content-back-next"; + parts { + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { to_y: "title_clipper"; + relative: 0.0 1.0; + offset: -1 1; + } + } + } + + part { name: "title_clipper"; + type: RECT; + description { state: "default" 0.0; + visible: 1; + rel1 { + to_y: "back"; + } + rel2 { + to_y: "back"; + } + } + description { state: "hidden" 0.0; + inherit: "default" 0.0; + visible: 0; + rel2 { + relative: 1.0 0.0; + } + } + } + part { name: "back"; + type: EXTERNAL; + source: "elm/button"; + clip_to: "back_clipper"; + description { state: "default" 0.0; + align: 0.0 0.0; + fixed: 1 1; + rel1 { + relative: 0.0 0.0; + offset: 0 1; + } + rel2 { + relative: 0.0 0.0; + offset: 50 32; + } + params.string: "label" "Back"; + } + } + part { name: "back_clipper"; + type: RECT; + clip_to: "title_clipper"; + description { state: "default" 0.0; + visible: 1; + } + description { state: "hidden" 0.0; + visible: 0; + } + } + part { name: "next"; + type: EXTERNAL; + source: "elm/button"; + clip_to: "next_clipper"; + description { state: "default" 0.0; + align: 1.0 0.0; + fixed: 1 1; + rel1 { + relative: 1.0 0.0; + offset: -2 1; + } + rel2 { + relative: 1.0 0.0; + offset: -1 32; + } + params.string: "label" "Next"; + } + } + part { name: "next_clipper"; + type: RECT; + clip_to: "title_clipper"; + description { state: "default" 0.0; + visible: 1; + } + description { state: "hidden" 0.0; + visible: 0; + } + } + programs { + program { + signal: "clicked"; + source: "back"; + action: SIGNAL_EMIT "elm,action,back" ""; + } + program { + signal: "elm,title,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 0.1; + target: "title_clipper"; + } + program { + signal: "elm,title,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "title_clipper"; + } + program { + signal: "elm,back,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "back_clipper"; + } + program { + signal: "elm,back,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "back_clipper"; + } + program { + signal: "clicked"; + source: "next"; + action: SIGNAL_EMIT "elm,action,next" ""; + } + program { + signal: "elm,next,hide"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + target: "next_clipper"; + } + program { + signal: "elm,next,show"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "next_clipper"; + } + } + part { name: "elm.text.title"; + type: TEXT; + effect: SOFT_SHADOW; + scale: 1; + clip_to: "title_clipper"; + description { state: "default" 0.0; + rel1 { + to_x: "back"; + relative: 1.0 0.0; + offset: 2 1; + } + rel2 { to_y: "back"; + to_x: "next"; + relative: 0.0 1.0; + offset: -3 -1; + } + text { + font: "Sans:style=Bold"; + size: 12; + } + } + } + } + } + + /* application with toolbar and main content area as a vertical box */ + group { name: "elm/layout/application/toolbar-vbox"; + parts { + part { name: "elm.box.content"; + type: BOX; + description { state: "default" 0.0; + rel1 { to_y: "elm.external.toolbar"; + relative: 0.0 1.0; + offset: -1 1; + } + box.layout: "vertical"; + } + } + + part { name: "elm.external.toolbar"; + type: EXTERNAL; + source: "elm/toolbar"; + description { state: "default" 0.0; + align: 0.5 0.0; + fixed: 0 1; + rel2 { + relative: 1.0 0.0; + offset: -1 47; + } + } + } + } + } + + /* application with toolbar and main content area as a table */ + group { name: "elm/layout/application/toolbar-table"; + parts { + part { name: "elm.table.content"; + type: TABLE; + description { state: "default" 0.0; + rel1 { to_y: "elm.external.toolbar"; + relative: 0.0 1.0; + offset: -1 1; + } + } + } + + part { name: "elm.external.toolbar"; + type: EXTERNAL; + source: "elm/toolbar"; + description { state: "default" 0.0; + align: 0.5 0.0; + fixed: 0 1; + rel2 { + relative: 1.0 0.0; + offset: -1 47; + } + } + } + } + } + + /* a simple title layout, with a label and two icons */ + group { name: "elm/layout/application/titlebar"; + images { + image: "toolbar_sel.png" COMP; + } + parts { + part { name: "base"; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + min: 0 33; + max: 99999 33; + align: 0.5 0.0; + rel1.offset: -1 0; + rel2.offset: 1 0; + image { + normal: "toolbar_sel.png"; + border: 3 3 0 0; + } + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + visible: 1; + rel1 { + to: "base"; + relative: 0.0 1.0; + } + } + } + part { name: "elm.swallow.icon"; + type: SWALLOW; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 0.0 0.0; + rel1 { + to: "base"; + relative: 0.0 0.0; + offset: 4 0; + } + rel2 { + to: "base"; + relative: 0.0 1.0; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.swallow.end"; + type: SWALLOW; + scale: 1; + description { state: "default" 0.0; + visible: 0; + fixed: 1 1; + align: 1.0 0.0; + rel1 { + to: "base"; + relative: 1.0 0.0; + offset: 0 0; + } + rel2 { + to: "base"; + relative: 1.0 1.0; + offset: -5 -1; + } + } + description { state: "visible" 0.0; + inherit: "default" 0.0; + visible: 1; + } + } + part { name: "elm.text"; + type: TEXT; + effect: SOFT_SHADOW; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + fixed: 1 1; + rel1 { + to_x: "elm.swallow.icon"; + to_y: "base"; + relative: 1.0 0.0; + } + rel2 { + to_x: "elm.swallow.end"; + to_y: "base"; + relative: 0.0 1.0; + } + text { + font: "Sans"; + size: 12; + min: 0 0; + align: 0.5 0.5; + text_class: "title_bar"; + } + } + } + } + programs { + program { name: "show_icon"; + signal: "elm,state,icon,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.icon"; + } + program { name: "hide_icon"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.icon"; + } + program { name: "show_end"; + signal: "elm,state,end,visible"; + source: "elm"; + action: STATE_SET "visible" 0.0; + target: "elm.swallow.end"; + } + program { name: "hide_end"; + signal: "elm,state,end,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.end"; + } + } + } +} + + + + diff --git a/data/themes/dia_botshad.png b/data/themes/dia_botshad.png new file mode 100644 index 0000000000000000000000000000000000000000..89a598e0f22795e2fa37f249c6bbe00504e2fcec GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^4nWMo!3HEflYZU@QjEnx?oJHr&dIz4a@dl*-CY>| zgW!U_%O?XxI14-?iy0WWg+Z8+Vb&Z8pdfpRr>`sf4OUhG75)w1M4khMBuiW)N}Tg^ zb5rw57@Uhz6H8K46v{J8G8EiBeFMT9`NV;WbUa-gLp+WrCrGd^PHpUXO@geCyluQy5n literal 0 HcmV?d00001 diff --git a/data/themes/dia_grad.png b/data/themes/dia_grad.png new file mode 100644 index 0000000000000000000000000000000000000000..bfd7d0e1d1da0dfb9eb6d2192614e9fedc1e87a7 GIT binary patch literal 5155 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 literal 0 HcmV?d00001 diff --git a/data/themes/dia_topshad.png b/data/themes/dia_topshad.png new file mode 100644 index 0000000000000000000000000000000000000000..1a772130a537475cefb08d825975a0e077194f88 GIT binary patch literal 249 zcmeAS@N?(olHy`uVBq!ia0vp^4nVBH!3HE3&8=$zQjEnx?oJHr&dIz4aySb-B8wRq zxP?KOkzv*x37{Z*iKnkC`wdoB9u~|0U;du}3Q3l@MwB?`=jNv7l`uFLr6!i7rYMwW zmSiZnd-?{1H}Z)C6{UH)IEG~0dwbQFt3iQ*^(q+~IjCqVK3Ctx%4zfSGe=XJg o@PT{97gir8j)XKIaC^hpxmqA#&%&K6fi^ODy85}Sb4q9e07Se}*8l(j literal 0 HcmV?d00001 diff --git a/data/themes/down.png b/data/themes/down.png new file mode 100644 index 0000000000000000000000000000000000000000..528c543492c900ccc90f2174fc2b81a8630bf44d GIT binary patch literal 841 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 UusiQM{4)SD5{lwgqK1M015?YXZU6uP literal 0 HcmV?d00001 diff --git a/data/themes/emo-angry.png b/data/themes/emo-angry.png new file mode 100644 index 0000000000000000000000000000000000000000..e1510772a4de238078ba82afd194e56db5780ba7 GIT binary patch literal 8959 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 TblG?OM*zr6t4P&K7zh6kM)TJw literal 0 HcmV?d00001 diff --git a/data/themes/emo-evil-laugh.png b/data/themes/emo-evil-laugh.png new file mode 100644 index 0000000000000000000000000000000000000000..1a0ec3a79934222ce918f9cebb30b2771e925391 GIT binary patch literal 9092 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 literal 0 HcmV?d00001 diff --git a/data/themes/emo-evil.png b/data/themes/emo-evil.png new file mode 100644 index 0000000000000000000000000000000000000000..32233fd8da495df0f7ddf1e761ebeea0fbef9fe7 GIT binary patch literal 8991 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 literal 0 HcmV?d00001 diff --git a/data/themes/emo-goggle-smile.png b/data/themes/emo-goggle-smile.png new file mode 100644 index 0000000000000000000000000000000000000000..a0e485908d8c9df46b1f12d6b1f28820c4f07d17 GIT binary patch literal 9670 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

    I z$x$sC&POziy$8iU=>Di?-4i8McXw5uL`%pZ)^LQ$;L#Zb(k^JCD|!Y`A~0Zq6t8Q& z1820kf0K3aR0&L#kb8C520i6HN^^u!Z5K#NhtC9HC8*hbQ6#$=W!zCmj^!R$%sN== zIN*mj!mHAg?$v7Wz?U+XFMl=aV`|k#ZJ`e9-rP{dlA$)Fzr6l{>)y;QDj+bbF)lnO zhnO)zA)3s_d+&X)=baMml@X&R7!I|o+sVXlU1o9t=_vDDzET<;9)evaz_-t8my+`I zbSCudbXI#GG@EpaT@ElYTyw+%NKAAJ$j)z48-%DjPfrd{^1<&9=-^eju;s{HY83ZZ zzs(J_c>ZB`6@fQZRU}89ms!I9{;OzQq;*_OoXm_|%venSDF6qU9n1peV&UM`Wakm! t<`-b+VqymifWbCB$x{DEu(da}{O&0N}ootzxFC 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 literal 0 HcmV?d00001 diff --git a/data/themes/emo-grumpy.png b/data/themes/emo-grumpy.png new file mode 100644 index 0000000000000000000000000000000000000000..7de77fa6d3287ec22138cb7e863ab00f4e8a1f1d GIT binary patch literal 8574 zcmai2RZN{-u>B4$#fodu;&8CyesC>PC|=y1;$HMnpjdG)?oM%ccXxMpxczT(pYNWm zS;@?-WHL`HJ4{(o3Jrw_1pojv8EJ^hKNk59NC^LOk%hx50H6q3h>I&*7#RV8+hUrk znVRYWp5Wc;wU}I}U!0ts3N8}4iWt;S%_94K43PDM;JwIkXhC~uHe~=VA&x`)1Xgq< zWq6QiBQ)Pe= z$pJ(@4&sCXcG3OiTvhCVPNb4p_iX@;k&2WAtu|m%o9Je~D+2&#SiJjp!K~`V;#0Te!Rv1Ok3c z-AFuDHXd4LR<5%b$E)*tEG_;(w%AhBIjv)?HxR*YDv zHbI5@HxC)ez99XZ>YabxwYk8j@L2f4ckpCb>w&1%>{W4&0@@!j!yQtD$u8Ddp08Zx zp_sJL9m7K92r0Sl#`hK|qeC&_)F?6uIKQReV#9o^k1-OPtpI}=AB0;mZRMsxgyY{V zxuz@A5z{(%?W|bg%}(Xzz-iQ2sQpPb$|c__#tsB z!+$al6e0+OpZB9`@Z)#$|1cb^92&r*35ZDt$w!N`Fa@bA!_ib=)rsLA2Wu6CNb

  1. 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�Ht+aMv9K~KNPkDn|>V3Xat=RVs-_xm|W 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 D1D1e& literal 0 HcmV?d00001 diff --git a/data/themes/emo-haha.png b/data/themes/emo-haha.png new file mode 100644 index 0000000000000000000000000000000000000000..760535dfc33dd856947fbe361028f1ab19eba703 GIT binary patch literal 8993 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 literal 0 HcmV?d00001 diff --git a/data/themes/emo-half-smile.png b/data/themes/emo-half-smile.png new file mode 100644 index 0000000000000000000000000000000000000000..529f60a17769c74279d8ae2e25fbc64355edfdb1 GIT binary patch literal 8667 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 literal 0 HcmV?d00001 diff --git a/data/themes/emo-happy-panting.png b/data/themes/emo-happy-panting.png new file mode 100644 index 0000000000000000000000000000000000000000..c6461bc6c5ce503f12959bcbc764d0a575cf89fd GIT binary patch literal 9206 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 Bt6l&A literal 0 HcmV?d00001 diff --git a/data/themes/emo-happy.png b/data/themes/emo-happy.png new file mode 100644 index 0000000000000000000000000000000000000000..a8a3c0bdbb324a7ec474de8940c52dceb0739c6a GIT binary patch literal 8571 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 p(6h4ev9Q?mq)7Z>{2vn9Q|tf$ literal 0 HcmV?d00001 diff --git a/data/themes/emo-indifferent.png b/data/themes/emo-indifferent.png new file mode 100644 index 0000000000000000000000000000000000000000..254133b0edba05208118092be94af0468c703c85 GIT binary patch literal 8526 zcmai2WlSAhu)IidcXxL!?(P&R?(Xh(ad+3^UbMJtaVYLu+_}KTdHr7Ue!rZ|PO^I@ z+3c^`jaF5bK}H}z0002Ua}gaC8T|bYC^LQMU;KnvZ&ToF40Y9{H^Duk!+g0n)||k~!hk5a#mOcToUR!LKYN zv|dmM8f3vxK+!B_#OV7(NWkvv?ajr%>JudN?zF?dRvlNNBldXTf>d!Q{vrUVkO1Ye z!)xMzQZxXED>la$00#o#qSQSb5g0l%lCLfblf|m`{&m4uysXFfK+zREL0j z1oS7#NZkP7I3eib((1kEwe-nn)B%8-CiB?Clr)Vmj^w|FiS-RSybF1GBx+Sx!{EbC zAv@rXEi5LW=SKjkoKOIuw5KExbq0LEC(zC>u)({|@844SN$?gM6(9SVDN;WO0RaeG zc#wK+?ye;OT;Ty)Z(}ol5f@q@1DD@fbH+&kOX9$z8l&ly0a4c8k72E0_h70`fey`2sbo+YVs76bSPuuBX~H0dtYb zLe_8sq`rUz{Po%isrrKk17L>ri35&@Zb%%66cDcQENxglbd>uQotjHe4}Df`utuQx%%J0lifm`yxWOGE$ls zlGzz@X7Ecp`w{Ov0CtC&fZ8G$vGviZ2}~AzX+zA-YycVjHnuq`ydrEM7AA zY>m(fH!Xws2iclhH>}^A-JOZ2t1=bb3OC>0N)bCEAUi_=s(iDW75<_s|txq^NRH= zkkm%2Y&F!Y3Axi4ido7tzS&hdEY>VSobf8&msn@y&v%sc zDvMm8zE8iGe=&KH@+Ey2k_a^!*=5JTlOKf{4IITE6&huvNwpchHy!1~ooku zI}*Uoi1~?NBvslZUZz{7bJ#h7s99ZIRo!+5x#YiuuvAj5r75#mX=`aK$Q``y+G5*s zVC%Iwx~Ox8a#nPfeO7h`yTn?BYLmo0#r4J|Nf1u($~9wi-^`Z59{U@k>3g%S&an=Z zJ;p}fv{gl;!sNW2IJ=k+w#o#^mCe4}!PTC?{>7fJ zb)fZ2D|0LBh2q8j<<~Wj^?+8drrC!2mZ06jJ+_Ua{-WtU9vMcNBD0o*>C>sxj|DA7 zr~D7shzF$GI0Mcr{>D7+)yC+o|>JcM@q5$iyC!p5_~!=;p_%vj?twEbnD+ z;aiSJ44)+*WM4hs3LnzDz&*2TN-*CMDC2lkZ&ctQ_8I00=hgGo=4tw&=FacJ>FHachZUE*F6qp|wq#2L@*9(zw2G)g*-N`@1;2F(V+c4lbgY~m)q zzk5UreDi$FMQ9VKTSPB(Q-b#2RulJ1ZyIjSZYt1G&=n~8DRq(&DN&_+qwk^_Vtv_G zOzT`7{eIcHi@OKhZ{Y1@-DPcScdc49YVEu4Q@Q-S{rhzC)cMrt69{UZA(VBNr;~3N z+VKzEep5hn$1!K(?NIe7GT!?mX=~HcnQnz@>w)^~=Y7bX-5)rS z1ed{ja@mjc%q7a^4D4}V+z#gTPHPPks`^Rkremu%hE;^@Vg;Kb{gR8x>~!^f5DO1K z*t)>CfUDlFacTb{78djl>N616rqG}7U35OJE(@6K&b%~8U{cZD?j7`&+KUNJhhRjl zE&eHQ^q?LbAm%f0zQkU$f$)H!h4WYsuf3pJsz$}y*}NQZdF2u2k>as+UQxf(`{CAD z`Q#cMASX5cTg~M3(21zG>dn$r;x6Kf!&S(8=j;)4fo?N3gFu$ZhQCi1{gF zpSiw`Wz)CHRC?sf;g`dNLr?lZ`p*reR;SI6MuwKN?=31G3n*K}=U&}g^y@wWnJaap zTfSWiob){Defu|qaQ0TDyX9j2I zsAnWhcA|u7$U~7BCdj6SsILgs|LEECI~Y{@m}YD{+C1wJ0zYmEz#$6TRo zO}2yY0%zWDVHrs=NO45e{4{R0!7kIY86rFn{NREM(B-)=#`9mXzJ||dk*3dEm%U(!?wimc%i`5XUjK-TY*b2*lo8RufV8hHr|5Q){{sXdClBwxq^Gl()jt;fUz~xSi~#@~NI6L{4e#~K zT%RNht$-boKDVno!)u|}iMUeqb$~@FoE%&U#uvPhxOnF7VJtMwYBjWKEaxax= zQnFB^?n&eQY_n}kc<1`r;TYV-Ts`qQJJh|1=w0=D2lGaab+?QpNTpw)2bk##9ZxB0x?mBiDB>+?hs@-s6<$ODj?PkVx}#b}hcc_&G?V+8~mu3j9-957TS8^eQRR2?8~F7G7lVk4!)9$K>^6 z-IAYUz=4DQ<8s@cW_+a#dLmB@#CUq)A_8KVs7Ck7%VS8_eV@=u52&~Klz5N2ekUN_ zJB}g0u4x|L#!GN(YHy@yA32y9yFN48Ei?Milc+M8)9?v$;uBEtl#I!y?x%3guct$i zz!P;{9>J^nQ2ia+PVCojQMfn=%zobfROCL8h)`zlr+~tTlHa+h(_^BFmlTzUErz+DE_8x^N4lBp-$cy^2)wrSggfkXaALaN-YCwNav*_#fX)q^NFeBTqaRnr#WiDr%A#X>ffq99HY^HOTM zQxUuuRDj8vN>$KWMO@L_>p_U_h&M%~X~5v-ep|eqpiAyE-RQ|~H=B&T9y|?G%Ha^@ zx23$-XG-RvgUaw#(dr4rDvs;)VY(Rvf?5O<2wpk>xQ?;Qu<>1!S$ipr<4B$xH#{gC z(@8!H@ z&4@u2A(~6y78`RLHIy}Yym+n8!5YfXEiGXeYQ_L4mQbJ2s=bOjqH7t?ZAEXXLvQA; zH-9G|tH{nzD^5oQOF(LdRAg*v_63#tX<3H_u{p{T5!v#SIQXJaJ9B(HA~5)#vC*(; z(z#@!E)Xm&0Dg*C+9J7mDvWZAi=3!)k+3KC64E6n|LmoRO4f8hd&V2Id%gQ(!ol|9 z-@iI+uCnw2GJ5xN^ga7(_?~DO4~MZKy3X+OA+z3hN{QJQkShg@%p`{0m`Il7+g8jL z+9_IAT7zdQj{!}LCZpX(aEbv;-R7Wx6U;wjk7K4Gj;%1iE*twZjaEc(f+i;9b)(Tb zqL|@s!|1%ARv;(sa)4v&(30P@HDN!V5PvKZ?lc%h+bY+(2OTs%vIaS^cfAE@tz@Hw z!ya??_MUk6W^;5c7A+{-m={nZMYHpo-G1jiWy(|z+eP3!sVcr#ifQoRIJ(7D@@Evm z_@Si6rBH=$VJld?@V)cwhM^K6#5iuCq|%D@<{XYxI~VA|wHp!S9k3IL+2uJup|+(; z`k=zvNgQ-zehk&cqg_YDvnh~z+pj;EEInb$SyWTth?TO)oDG)^=B=oNniixz?g}fS zC9e9}c^3jlpP-&%k*9Z>QWm(hOYMd6bNG)dKF&y(*oRB8cLg*|EnK!Y5FG3e>3t++ zCpv%mXd_z8oZ_iz312nvCVlSG(*EDs|%!E2hr;Png zN|G&jq-K8!Ga`h4z$YH<*(<8sjSgb8R;j<#KItsUx=x&K0{~ zQp=$^Bk^sf*f1nyMY+C;b8*B-QgU^o$K$wTmbJ_el=Y4wf4Tm`DvpJZaqN=iMRr#& zmqW`+Cc4l9-~Re{6cJxw6MBzyV>KaO&!X;-cR>@!GSj7*mi;%X$&vEG()?W1h;i7$ zE#BfNTk67M+l7g_DH5S{=@!-&Tex@dl!SBv7QHOd!q%IsG)oXQeZsP9=;#Gxpe2OE ztVt7gtsSPkxRBjJsq*(7c^st@ZK8sHg8jMq@hE@Lrr-Ss>c{98Z^t+8-IqOR*&Jjq zBI!UDBr)~LwZpjZ4p94b0IUOZa$Ldzcqc(wQNp@E1TR!~fUt;uFa~n8Sg#_9Y)XAs z10B}9~`Yo+6YPFb{+biwW{id@i{;F8U@CYH+Dk(YO_wcGI{)p}>HjB#0nh zVhn9xSMqGgZeB*DC9$L8$EAeZmR~TV5f(%}x|6tExF=(YUDy=D_WEW~mTAUaWoE2~ zsemlXTxzHaq8tJRQDtgz0##)eqPm&7zu^m8Srmo*_RbW%3Oa=yygk|4(~;i&xX2}K zp^qamvTOtznQLezMOBiwiYXF7RyWpuKp!U}Q)Un+0h>nmrH4jh)8L&58YZG_eL$-myoc-8S;QVmm=lM=XwZG8M-|3{rfv=4mz~##@-I)~ zTjU$IsGPhr0H<$h8BvM#I8;A{ag;D|NHKl~RliOi@59v74R6n`38T7M+VI=Z#!wpK-SAOEb4HyGgerV84s^TR z3Z|OjspSMK>g@W;0I{lSA2+ppR>h%XOH=GP6ML${+oyN^9zRCMSDd;oQ`~yLt(tEu zhaC$b!JvCC8LM2upgSZGNFnbzRmJ68WoID3p(s0}e^MV9qrx7J+Rz~zB@2g9L_;g8 zv`VnC-&}~37J#H^yi94Fm2*-{;3l<=JnrgT7QY_T17q^}I!dwJ;Fd~jJJoP_*Ym3@ zq3TpFC%eIK1EuwHbwH)(N;jjk!0Ly{i25wi@gG_gmy>gF^YuE<&9M9ue$%?!ysdkq zF{C791Ntf&JOx!8Ud={_edD`q(iIT;Ke$LSJ#kvCZ#$E z=x|GEV{tZi49P6IQAu<{8NRPUf4R;*0$$;7B)CLBXAMJcwgV5Oc!V zOgmqNW9AWVjUH{SaCCU&!EWFiy)AQqDo|WNUwj?Rl#R+_+j%FGF3u{%Dfu>L-hTggV4=bg8p81;6b2Q1Kg*b9 zDr4WmuJ3D&N`M8et&yIPKMG?e2)e*O!p(_-n|2(%&>vht6&cND8eB_KkNk+JdLA+d zRq%FYvGrbKE6$bDQ;uBLOxx&P1e$p%{s+~vHwg3|IVQNns|8OoFQ?%>*5=(YF3UHDP8r_oB%XK9f$e=++4TIa;ynJq z0~#K;yNTC%8$^`Uy0*Hw`BsXkJLgH7cZ_+k;?NF0=RVh!425`0x3zF@hzdqS4i%)Fm9^VAv(uhfTypMR9Zj zJ-v>vLOE4T;!MpoVdO(XQRRLY^gmwTipt#-lcr3lzB`1e-1{sRi&phmt7i3KMHXyVP2cw)U&{|f9?_@~ zLcz1e9y=piWyhbjH#$81flnhqd+e`)N9aN&M zO?4nb_8UuY8euRl7|>ha1^5h91fw!^ci(&X81$O*_c})vm_AA=^=AeZsw`l|8vkiX zXlC#I8ckOjf723g&6XgWcg<^3a3-HcYxb@8oCYQ7n}P$EvHzwjA-h$e|I1C#d$^3q z4=^R{Z(oAlJ{R0Ld#U|XeWSKMoa|nHE4={RC){HHpGcE@=sq0^HPZqNOSyM8MTRbw zQ#;g&TQm|Q;z>0vvQ^vEPjJjAe6mT`zShZO7|T#0-xRoTIM_{Y8V^G=TZ0Y{NT2f$ z-6{;{3}LHhr&c(FYrjm&d`md0w<47oVmE(f9xFdLzH90mUKNpiqE!QYgFa0kVxWrB zp)M)yWzx51i3w*D_0I|AVrO7q#qe%N*o5ww#@#JJpInvfA8R);pF&$i_M>^zA^-=y zB=+8S%pP6(SFol4O(+e-R5oJ^+Hs5F&42&&8ZT(uloWKqHg&z}p|w;rBLCHwXaLE| zRVc{1(H)YP*%8BLHAo~V#zHfeZ(>Z|1nn_79A>c)K?ZBY`7569xwYBosp9iZD`>pN zatC*L1XGoGyy>K|zP90JapP}!P!Isqesr}MGVK+W9+kdaUUY4o2~PASwz6E&E_8Do zdnJpk{!XKRqmxb8X0>y?$z-sw$OL`ETjl9z+vmjVjzDgijt*;QrAs5K0+>6~45YD1@X_rW&kGQIfH_=xghj{Hopx8|ShcLSh_!}U7(Gt=4dZrGzy9GYi*3S;u6Q#ZqPP35kCQ7A z-lwVLp(R=kSX7$Bm&g>hIG{=YLU-M!4R>l?~ zlZ^V1mr4Qe^3#FQ=jF_f|LFj2W(LM}KtqDBAIl&<3I-YOZD%4}Ce7p2sXB)U53Twv z$@A4rC~Bbb+33a&n;VGr?eB9{fL}`MKEEhK5|F0%1o_2~r?SF&)ELraBkl0_BY|PZ z5?ieE?wA{G;``d~Yn^tmx{+O7EmMuHK9G?BrrlHss;op93D*H~>CZ|ap6fvY)fP&# zn?YauuQW$Nug6?H(vQ2ns-6{n?!M1y9!sshE7$Bz?reADUgY)1Cn~2{op9N-TiI1U z$F)AFM`gqcOUv)QZ-=lbq+Q^kK(o``6;#iz{KI{7^oAS{WI^^{G!e0$A?FY*BK0&K zIxhJTRn;_dDef}``8IX6TnE$f=_Q0HBCVw_q}$n4Gg8myOCb+%?ZoDmLWsJ$0rk6WgvfudHXJ z+z~eYWblW`HHXFaKpkc|0EVUm4?((oH_<09dYqEbnq8Xtzq2s4yOg%OnX83~y9KlPzX0H1V`pP#<6`FE(P00| u&&|ir&c(>i#?QuPKbS80e*y<5a~n&a|3|>-cHsO^0FaYXmaG#u4*4HH`*+U( literal 0 HcmV?d00001 diff --git a/data/themes/emo-kiss.png b/data/themes/emo-kiss.png new file mode 100644 index 0000000000000000000000000000000000000000..5eb606df0d1d21beaed1dc69974a9bd859bbd2f0 GIT binary patch literal 9214 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 IBW4)%KdcVLqW}N^ literal 0 HcmV?d00001 diff --git a/data/themes/emo-knowing-grin.png b/data/themes/emo-knowing-grin.png new file mode 100644 index 0000000000000000000000000000000000000000..589b44d5716f3d9e8634043d93fdb1a024a7b2ae GIT binary patch literal 8481 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 dgN>cBg{k}hmvHx%Yq{QSz%SH74{s$UQ$T0u_ literal 0 HcmV?d00001 diff --git a/data/themes/emo-little-bit-sorry.png b/data/themes/emo-little-bit-sorry.png new file mode 100644 index 0000000000000000000000000000000000000000..fced0e22af4710b22096c5491095c1f6b16c18af GIT binary patch literal 8288 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 P1c02BvSgLGVc`D&9oy)& literal 0 HcmV?d00001 diff --git a/data/themes/emo-love-lots.png b/data/themes/emo-love-lots.png new file mode 100644 index 0000000000000000000000000000000000000000..4591fe8b68585649cc42198625e33cd85a972856 GIT binary patch literal 9671 zcmai3bxa&ius)=4xD+VvTHJ~pdbkuX?oM&H;x0uGcPsAh?(XhZD8=D$UVkrnf4^+L z`I4FavXf0VJ3AYpq#%WcOo$8s0MKNl#Z~^X$bSGL{Ig|Nj#~f#vY?fin39!=2>{@+ zmZfT;rh0-W2;I5`%Z2+x&f#fRSD1SApeCz~3UNAnk$XR$vPk26MAT9xpW6vyB zTrFi}h-fVo#uG@tzeE2;Z3|WlgIwPy7QjTBI_d4M+hKkSRP#gr-la9L*>b(jEA`(Q`WFhHWK*XohW%Oh5y zv=WRId;;4FJT@~MgP$7&Byz$5{3YGQ{V}GX`+T4le$YDa8vl>Rl6S(FsPLar?PKPoqv?BD&jH))K136a#uGRZh8((j28e)VS%YcZ$$zb$8G%%SF zJvkLTL4$|I816b?GH^4XGXS$kgdH(Jk(Q_{9Z<-tLTH6l3Ta4O z5a$;=rMOER8ZoW=vYLJ-icW(vg6xFl33|kQ{qODzLkn7`=%;z7X{SY}h>NVH7*=uI6I?G`;)EfD&s`}wmb?Wus zwT`vmY_QieCoPI=1BsSG)teCzR$H4-H8${-_I*7ZxwFlzeaH9R!5y`pGf{@ncXa2F9Q84uKtuuH@{xxu3#^oQ*cp~^Q&9p9r9KK zGj5n1Fkl$fYZYYCLVNzxVkgN1QRsV#HNIsD*M{|qEw7!a9oKS6Ps!--c=pLu>r9)D z!In*rg@GRG0n<{Mpiv*yGKOWYMVAb#;u9TC=X(75MssF!u_NuHA2&a45N^WoqKl6m3LR ziEEH8<5tn>ZnyKbGi=1Pyq?xX1Qf^hER0@hbKtyY}5RxuAmb9o-}!59thn_M;vV9`K&so~<4x@5-;e z&+HF!_O^F~33qU6sCVSa+1cnFRCh?aNDW4+k7K9Y(mHM2q%f)IIZ8hNmZ|wxBhbPO zkCsMK$9J$xJkK}B$DD^bhOtTfL_Z;5qr4KkTX

    d3srlg^ndh#ZRRbk3xkZ*%fge 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 literal 0 HcmV?d00001 diff --git a/data/themes/emo-minimal-smile.png b/data/themes/emo-minimal-smile.png new file mode 100644 index 0000000000000000000000000000000000000000..c0051740e1cbb3bec25c5348788259896d0992fc GIT binary patch literal 8896 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 w<>KSyu)FLzeh~n&l1dVFVn#v#1DY-zD*ylh literal 0 HcmV?d00001 diff --git a/data/themes/emo-not-happy.png b/data/themes/emo-not-happy.png new file mode 100644 index 0000000000000000000000000000000000000000..91b475952592bfb03c57612c29d0bd7f64e5d82c GIT binary patch literal 8885 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 literal 0 HcmV?d00001 diff --git a/data/themes/emo-opensmile.png b/data/themes/emo-opensmile.png new file mode 100644 index 0000000000000000000000000000000000000000..3e37d1876b048a0aa3dcc9860ea62f2f12cace0c GIT binary patch literal 9580 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 F{{V*-f4~3$ literal 0 HcmV?d00001 diff --git a/data/themes/emo-smile.png b/data/themes/emo-smile.png new file mode 100644 index 0000000000000000000000000000000000000000..082731dc5b0b6abbb99f7b71465b0d26a75d741a GIT binary patch literal 9590 zcmai3b8P2du>E{%ZtZT}t+vM2=GNHSwry{%w7gqSk{Qm(4>Ypt&v)cdwI36=0AvrSx0|0Pc$xt*=Qar}w zdEB@Ylnn8Wm$Xs9fFV*44EI$s%SDX^asshY`OiX%yF+qG{4sFQ?YgH?qH9RPf&^+F zL2fXVyIYiON*hQUxL$P!9Y1UysyZGxOfoLhy?6mp-D=^~pi+?GPmG%ofRLMwj)1}i z98QVI58RhOnHE0uE(#3TdcD3n`xkuzgV>s|`gc|9C5Yf{_BS6ntkFFn=>8{=w1T88B~~t;K zxdLFAL6i~kRjxBCn#7Ze0B}`n7``7HuLNmLT;KmyQ>(=_oBfASx!h79Y~V3i3(TRB z(I~{s01(Fv4)}^X3;QBXKJIdGHFI*UvafJ@HWYv2zJ-VU3I9yutLg=TfWX;%k=MHR za$Mj78)&=^Ppto%ZG`B%@J^pPLIBJQ`W}?&O!RI4tBq2S;DND8Qd*h?4GO$fP>Ig{ za~7-*Nawz8|6g=-G2k^U4ssL$k^p5Z0KSf?Hr}3F;~R3AT^b+3^(Niht&3DRGDY~l zeu-R!m}Gwosu|qmSZo*>oJ1melK5v_s88J)QgXWmpgZpk^&qGr*ER}umPAKXedJ4i z1_tc8Z2Ff>BSQg!Pq;}R!3F`oFf4MAY^DLc z*a47BzNF2*T&{kEl}v=H6*pkHzjcziB*}-US!6thl zo52>hFu8rTv3(C2;B0j91(2C~g;hh?^nH^_7D7mSMU08P#Tiij`iVou;YdW{hZPK2 z75w8#e+_Hr6Fd`eM5c?-5%Uc5=UeU{f-l7Fjk{q4p!EKTf

    %_0Pa!4h*N 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%0D{D= z2G469B1#kjzW||Xf(UsBk&lF_MFjKf0+RBfO7T*x%%NIpa5UA}4U+gLVfv-vvivYC z&M;#=@J%rD8wA3T&qR=Yb`&S@I|(e#9%FN1s{WRi8m0Xp0mlvX3%7(NI39kYAm|2DvP$E^$U$Q0j>C zCJ{Pd{+o9(<3s|326X_%728MX0qcSLLC^>C94lEur1p;CHOc#1lDc?V?z_UQe8Unn zb!eHbrbam_PZDE3YjMgayE2EFiW$%mzw!@Dm8)Et$tmj!>*PAwC7&g!B__cij?!L5 z;nOtN$=4qrO&(=@$zMdILQMW_aNrPqgd#u#pu|uSC=+d>4fNU+%7s6IKH|G4uxGX> zgrD;57mBe=;cv+z{UW{HmLXKF^769s#v_>7FS97K1?4(gaxou*51sNn6T-*gbSKJjmss9n&AYOm zvOgMeO6^rqNBW1d2dtB;CCf!Z#U)jQxpdRZm0l`N(m4fZMLETtGH*$*)u3T;N>Cp- zs@o>Ss)_bA#%d$k8&TA@)Q-rylzYW)!GYh=+>v{}w5xRR;5)}?nq8KC+n=UY@0q?X z>OS)_g^)pijdF&0?pgOto03BVF1K2u+ImYCOQ}8my)Rc^t`M%m36xM(qhttp2>4hO zQVfUPhkvBZ|5Rh5tI({lt*DqQt*@=`^DXfh=icI;x0$lxnLb@$w{LTBwI{KEv=?aT zZh&uKX<$21I@$WmyXdjx-{AFoyt=ABa3gnzpJN9iV&Y5W@}m#b<2r!bFYP4Z&T4qRHd{I`8<9l zo#A?`Kr6#aY}3n;<97CGz=Xeb@q^OE$Wr38C^le4wH zAx5%+S53X4M8UyM@2s)$zJttoplUyE%rm{+-ct^Xik`ES@j#(kt6I2;1r9y^{cnMt z&3DrRQvxh`SVNer?;hz#gzY~q#BCOySDzo9mtbRHD^dwk>3v6~!j$cZyo_Xw@@1bl zt#ozttFv{NboakrCR$IsOk2}!U9hOp*>c~acKLO&bANE(a$n;UaMdtID)0P}{$rEK z`j>#UXGK(Z0&`~mW;KsI@aCknsj1RdcVAqvnnVnkIWnh?%0_bl*AZ8g&?mAXBJ2;@ zmg@!hx16ibrP?>Sp}nL{&GDIUGuX(g>NGy-1ZfRIe;s_SA78H{qtl{`l|EXU?zxnO zaT_gtFUmHdXxPX$LuV|BJSa33&o~-fXij`0B z&N|ySo4d-cW_If)3i0aYs?$hP_k-b7$Bgq~d6EBcTk2nQdnayuO$si`o zpZUK&8sBIH`Ahh8AJ1}BETi0@=n&jiA?r@76{=ISwbah}|2_5i>XG2FdR$Vq-tp>I zQ+n?j>8~I&*spGKxa;(;qwLwzRO&M9lym>L5vc-c5vh~Y<%)Z*VY_f=TcF#(-X6<+ z$`(siBkPK9nW^lbQ-?Z-A&2(l?&M#~$_-8{uQiPIN80tO9@7}B?~lFORvDIj{8Q&E zp{u^Fik^WBREut2PF-tzB()je{0sdBp0ej;=RE_4Um7}8N-7IarvnaO*I=;`1&@r5 zjxmqOnC-+#lhAv^aWIUY#_n3@WHX`d%2~w;z0SHm_ltLt>+7O8?u9S(ch=jO#bPJ? zP(kgLXl^z~G6w~RLx&iW%QfTIB>b>qiIy^XLDm~G<4~hTG^fP zIH4=aiS-cj;xqPWUh*Bi(Ki?$$<~+`smf{J^xN)HejR0M+*>(n7P-4!6+-s%J^OZw zu{zvzcNsADa)HQ1jzdl$rtYVCp?l{tI-VlNcO!V0eRB2p*cazvN20U(?LqAK+l5Q+ zIm4CBpWJTnOZ@gkq{-W+-T0mesW+>isHpmN)FYeFXWh2@O`R&^R#`JS#Lq*8C|IbfSn8~Xv1Ay;8D+UPxfQPq#d;P~C1^~e{03dWqF#aR^?=FI= zqMS7F`rkPwnhE}wL3Wnca{~ZW-2VUqGO~#NOL{s>Sp8%1|HaYOJs1E8Tot4xG`*Mp zX8KfHX!)Osb=KcHpEjGRHqzxHl4M9Aq*D{o7Uh30K_YMw7iWo{OQhCfbDKE-pf$)f zJ`+;PFoVU-#u3bh`5i)$R0>A4hHJ^Qv2OW$s)*Ux>a@P>#lO8~_p(Orm$R8IG!cQE z?5n3$al7dE&&xjg2d>{3tk=(p=9fReWsPL6LimJU=l~~A*tL`E9H4Cx-MdzUeS63- zB)HAeh;x40pwVGJ>55gF_03`7mHQK3;)ypIt*1JYZyB=)eDgCwuxomq7Y(&dcA~Zl zuDsntO>7HX8|?muN3=PgaUcPo@!gycz~4gszJGBlFyg|47N|`xoIY*XhZ^mQMRZ@m zs4=FdF{&!Ffu$aOpO9gh%sC3C@5g44^S%LVA&)2DRJ+6Qda?FJB6hf6@A{odfMosT zn#hYocqQ?g3VK;ADkvCBLYS-FQ80FtQz#4rZ|5j;?7Nm#+vw{Nj}uSw9J|y+?m!STD$L+mlo)o*v=Fh;z7&1X$6k#_N zOnRg8=eW^YP(u0iPRHhTLX{(v|H(ty^jiI6ITxXOWH=sUfg}yStqYsP&bbFt&iy6H zU!lDd_nSXDK5QGMKAR;d>oBJXv~QyzB9WE;*i;=$x(`j}VqIci2$SR9;7R^K?{K6u@oP5x7t#&wjq^@oAQPjlXI<>gAHdthtZITtT9*}j zptsR{`$=>x@r!~a7!BwL`e9z!QlF2OJ?Y5bSGqm_2?60^1n}mal%gj8Wy4*0;Tbu{ z`fW}#wH{uK&_-E0&tT|D!=wIu6^AYMq`Z=!SXvdp$B0dj8Z-`*gV0WV&$tnA2&9Fu znHV<_0{g-`fxEa#C9xEf6rZ}~iQqmENpPzl;F}Yl6I5k2+e{hPnXKga%t5|SbcHc& z$|VjtHwU*KpGERMV_}`NB+>^Q@RbR~r2<)$DC%1>{(a=lK~qwS@&R8kJ>5x-?PiR6%6mEE$ZY;$imB*T)PG_K^kX7 z2>(_-GD%GaMG=zFW?fG3+h6qTxRFi>b%Ze}=XY%-s&;?AC!-za={Y4+XOpLw7Qybu zRdv10hiO$2ju}ku=Wto)J5St}mWsoQw$JO>Qg3tLJ(*Dy=i3t(zLf>iSVP-G3NaLZ zyuBg@N-~rUh#ODV9gF zhUeXR9%kL1%M=|%r@Q$S;K(JRiWUUHM}gm*X&SPs5{+42Z;qa(u~-Zb2w%HeM~0dX z_2PN1$nbaYkaE^`TQQW20ix%_u(>R&zE6CMjaKqgGd4#WIf7bR(fG)pSYl~fPW=#9 z(ZA>EatGrRX?TC>onCnwT;Cdi#+26o)Nf2-dp?X=dD`zB#4q`^wOaCP<5!f~3`un` zUl=|6b82Iim4a$el*;F^ALL>o6^Wxi^?cFnL@!&fvoDzB@vu(=qwhCVrE!Z}eYY87CMg``mJDtd-wIx6MZQB6~ArCS527im|N$qR<9^+%NZG z$Ibg=Y|dBVY+&yz)ii!isAgH;s@MAH*bkvd*x~PGC`an-FbL&1zn#ietkEzJ$>HrWi?pq->NUE*@)(6h4tn&?!jgSgf{-&hvQbV5@+wP<85cmV+M_N zdT(=t#^(0+(KR)npt6{5=GW}Qsccr(Z$zz3WGuJb>joN|gY6yxk0YLs1g!fTc_-;L zlh{zGEHMd*ZHh?Xi@M`eyVu29BL>a^wh|ur=inl>4yCKbtKaQPcd!kbZnG);ewLf( z)r#M^iA*p3WggFK9B-1SLHSdVVyf=vYOu$l(xr&r0(nD`(#d3iq2BMFt8Bk2JoWwEm1y zXB7>Izx&ad?QtBp+bH(vNfvNK&foU|CRyosMP+Z=F{JZ{$dNLp-&6wu6KsoO{Dv))^Hr_hV|~*K}dR?Aq~N zhRf@?xns3%oEF~ul#Yunp{qnaZfu3T)$!lZU1Zg$(#O06nqp5HVW%3*GS;sksn19| z2^u_|Io^iqbi`Fu{Pyo^xjuKN^6BW}%|)O};`A+0(_k=bIjPLPk2B0Qczd`YMr%5c z3ladZ_P?9Y2|#IrF=TCtSc;T3>DffW{!TL5n#dbT(S!1&U=taH3w#2H(T64CHMzEN zWu{ItiuJtI@YT{ghA5UY-2EgpRP|LA;tC_^lP63OQzV;ZQQYw*vqByjbOO{=noVf| zx*TpVv@XBW60T9g=9P%8J5^kNTM9~x|FUPZsQ0j5@g9m_3rd4zd0l2aAc0L z@=GnN@Gyf6$Oa3-_Eoj|nYOkuc-LVkb7^wxdIq)WHJxWY>!##Z7Pi zZ7o?;C(aB9jaey9Olz>2&XHCWY89~}5bnGz6Zb8TG-*=S6T|)-&vzJu85Btg%4I$x zC>Qej?Y|D1DyL%5!ZOoqsf*HY9{c_sWlC%y!HmESEGJ+FWK2pIqQmJM$-?1>@FDOJ zkbZ?Se|9M*eOo-etug+v2kH_k9S6WML>lbcE^FI;xe})iR$Os=P{ndA-D+Cncf$sZ zK2+`EDDWEjLRbi@pQXwS=|o)9d?)0}KkA4v3pR^ed`al_!^DDOD<}*Wm|@70!n%%! zKx#^Lt3g3L)a`Ux2gPXw8g-(Wz>#{LGUAR+s4i^e7ETCBBFCQxVTdv!WfX`&>EE}E zl3^*xhI*xv+DvTUSfjoBO76|c`NIX{a8V_KXy};fKH?i0Ih9FD`<7WZ7>%~tnG^&!BA62?FGp&6QiQ(^$rv}l#APB z9Z4rY4j_Hlh>D3#-!3fd6gDzymR3WDta9BdhB(xI10^S zXCz(y{-tnwSXyz#9(}W2H1hi4<_Tr(Pc;qlM?C8~Y8kE030#UK09@%;Z)P}9KkG@{ zzkQUt<1zdtDiCjqwq^l<)vG~G0D4ark54L+Boa5GIJQ|gktW{vXpks~kgYphrux%u zo9ZMryxk|_n3!H+`Q~UhQDQyvSg;JZ8 zPczVab~6MLccelnd;BMI$v*S23iJ!!uU*P`C>Sxlb8d4Zun=E)s{@D$39!N0*FNfL z0h>db1B=BS%gRL6fR7|2j^{8TZiEUqihifC+&nDK4!V)eBpK65L=Pm22dKrB;Amk; zO?rsXCAHmWjr~oyi`4A|csv5gfVOb=Fub**_zyVd-{;JCe>(AKzPBFxN+IS&@YCTi z$fk8aBbf$Ksn&7g=XmQ$<6X1#*t~@nSFem~l>vn~^+-${B{LY6!-fbu*?7s*+}%AT zTZ|5f2~$?2qHo2TqZHK$nBz_z`z`x4=j0j^Jvv0POc`}0zm|5$&8O^NA!HrUPJH7= z{41t?am2aM^y9F-`8IpqzkOA!t$l@iNk{zFBi3&p1T&y@1h0%6W47^Ncl)xSX)Tb_zBV= zLUgp%m-$S-L?x|a;w>S|*7txrdrLAD;wLVakvts6{VAuh(E&>L7vJZ%{OTBBQzP%+ z|5Rt;PBp~mxlRLTFYAYE>DwKaei4df8igmRM48)Y9X`$}g{e);DE%Hbu>aeFJ-NbY zS*8Jy%IW&e0WwzfCW)Yjh4>A)TT<$fsUu9+^T!6)aC z%G9hKy!5Vda=mxuJ{rWRN7yBu4i^_(d?Dc_@6}kO#w}NQAaGw~N9L=Rur#8l)-b_I z2o#AN1kuF@-K5XkgL+O4lOSE>pw8lt3+7EoF~7D`2BUorLs{cT8>2e##aq!S{3=Q6*gibqd&ea@r8Ag8J*zB8i4b&dY z3F%YU!<#QwQ4FtPyc`4mpc`Ynow&h9dVC2I1nW#bp1|);#{@CD6WnRM<&84lgPlz_ zcP(&OI|3+3riyvO1w9VRmS3OeI%oG#+^t-%IKZ--j4gMc+|LTs z48xcO-|M+d?jMSr&SQ&c^zGp+QY=Knn=V0eJy`2LwY&Vv+l9qS^b>|P$=FohX88(g z05ja`6EIif`7s-+TVJ{gMz82$Pz@HieB`zkef$*xZ(dnas|9CSk-@8;+W z!=Y#mp&;P!Ik%PdAC#~`3x%=0L?68spGWZ|-ZfYS%$B1Y~+%dIk2Or$cBNs@AH0Tv1n;t|^XJs{b-#<86|-N5WkRJsf2bV%+b3xb4xZ49cjU|_EzgHb zR(JrBVhYT)#Uv@~tk9YvA`PS-;>>2`&6@@~AUf-Tp z{Iq}iovA)n-Die)J}l0N%(nFNxwqSj%1x!{&p=t@ZE6a!6-V5+mF;!8!9K$%!y7Qe z5qxMmLx?&~_m5}xUpB_V8{4Y?NZ5e6?s5{L%0&dU}pkJ+ZntnPpK>G9JDaH&t&;fVK+? z8rPA*bnrcR-KaEhe3*&LSAikdKa}6G4Mf2WpJ2%OF!V|Zt7eWv?#bSXt zsCe=$>uxP|sK|U@tzML!!^hfre4JeL)X&(rShUGk`QjQ?#htFhA(T`&Zyc()HGrp7 zDk%Y`fb7;-*|4WSPUfh#pBI#13SVy{8n3;b#5HR6%Y}<5)zufg{D}EkTlcqg${rZu zjdt&Nr|%y-_B7V)?(SZv&7d>X?(dKL$JK&+vE3tcw(4$y{Rp|m&+p*y__xvOcP?$& z1m703Yqf{24v}rMaJkqS4L*?4t`DbJ${_D1lX&t8Zkq2}>@6Gm9_(gm$cEud=@op8 zD$zS1wsBIvqH^5bj}Oj8`jN0^sL-W_3QR2?&DkzLCoNLn=EK3dU)i#iyUj29Qf*VgLs<6OB;3rI;6NkYnH;r2BNrp7ezu9Iig--S5XVHe|o4p`)GOb zrDW5MXc~7JU3W8A3lnz>7W01r;AH1uXJO}N;pEfg w;1%Q%5ai%y;$RnKXSeT3mi|A1gOj<9rO*E(;Bwn`{wDwwWK^UpCBeb}15C|%nE(I) literal 0 HcmV?d00001 diff --git a/data/themes/emo-squint-laugh.png b/data/themes/emo-squint-laugh.png new file mode 100644 index 0000000000000000000000000000000000000000..0e1850b90d6f801267e96fc2152b644bb39e400c GIT binary patch literal 9103 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 Bm#6>$ literal 0 HcmV?d00001 diff --git a/data/themes/emo-surprised.png b/data/themes/emo-surprised.png new file mode 100644 index 0000000000000000000000000000000000000000..0b980c602b29eba2e5071fc42931ce57ced8a6bb GIT binary patch literal 8431 zcmai2WlS7gv|OCx4h4!!ad&rjDDLjX-F1;t+})*Uaogg$P~6=e7T4GBCGYpk$(%{% zoJnr(kDJK_sw&H%A`v11002}uSxNPOEczc1;s5n2TbB(007=MJLPFKn+#CS#Udh$4 z*3>x06MERV6<3H3PEl}H$3-Ml7mp3rv@OC)0u+W5V2PeZSAe36C_-^R7bj(`M$3Ep3ge>GABS7AZ=1FnH5n5Wg(Ay6Ad60 z1GZkSug?BWAE9BlCLRAB)oBSfa+~)xNELr<4+%hp z0w{|eSQZDAU;x-%aoOPj>_~vK68B7K05t%hPeO!`9&85%5U@;AfdP2VP(45cTE1$~ zLyHyzL}|uwfPiTz+eynOo}j& zHJ}jh0id5UQda;(4ydnjDRtg6+6Lrc4FKS((IR#~DMb^`iTwA#7X!m~?*d*Pi5k_V z@K52#(CvtamX>3%GlPI+4j4eNw5Mb+I{0CiPoRxoV3l`;-@m!ygYY#rIzILzU8JrL z3JMTDdnfhM)Kx4}4mh6QNV13H|_+s-JP_UeYLktMU$BaNuy~!CR zfC2;~a;m~{+k^=dguyKZQ?>;Qc!!WqM5;!I^6CJ@Wg`@SN-#4O^y!1!qt!L{s)jS&;|IvSNh{ zkOO6rD5O$G)GfHwLsKZVMvO{Go=Et9ICZ-&`DC5EiFTQf*KE#A=+cWd;l__KLE8ugasTR&rCLu4JqMOC$#-knesb% zPLf~Zg#0dfXvCtCdpYY&42>Fj1j!ZCN8kzLiSvoyC;0V;csYS8G2MHLcT9@9Xk`I$ zNluYLIg0vFrJbfm6%khoeGzk6nwov3<6QL|)CsRru9Y&RKf6*?`DfE-DPPhzA&D^4!7Vl{0{J2Mp}?WfLqbCgG|9F@w`M~exD%)o zz6X2<<_7|}X)(W$jHOB%#Y^={b@w~QkhQ9+Dyv#gpy&PPk>-o5w6$dBD(tN61i3<1 zT$}BhckR69hURon&`t_ZGEYiR5awAb(QSWnO>n+)N)kp8zHowVZ<|=t*kXsV8oxE! z=^pCBIAE>jOj?&WC@gI@bS@WX5oU347IQ&3tGQI{?p;}be2$tL-AZx!@!iQySn+T6 zj*yg~75wS;{B}h;zr4O(VJ{kfq5x*ZE|&!!eJM9 zMDt$rp|Y=XP$NOHyDs)b?^ybX`R{u9YN7N6LFW z)VN7n$bd=gAKNhNHkylg>#bC81Yx@hdjgvZ&NcfbM_wljC(gwRP{rs`BHLt!eU3xd zVB5O)+yIDbz@kzvY&1Zlif)l}-aXs4{8*pEt%;zi*^0?Z;y~}fAL0*zheY8iBCEto z;c?;dFv+DEjJuELrY+W}GSF6QR@+rqFH|%)H4pffdrWcea4y=;*mBKYEU`LtIl4L! zIy^h@wft#;Yhh|(Ia55_Ip<#XSP5wHYMiRCYYy5f*k)ZV1Qkwh^T;sB6q+~hP99Gj zzt3tbI_JK-M&6-Z#~E^5@Hga$=Pd9y3k0}&x}*v4@S}HTv{7}OeQ)o#bn9;`U5l-i z)FxfTt)(^C?BwgDTl>-WcH*>~cM&)pU{m&_cs;R_`9>m50-exJ(%p2W3v9ZdIJx7z z#qnP77QSY`$MTu?LG{)5E%zb43EVcnq%GUL$BxGapFl_pm`L`! z{8#xlp-un5jaLO^cRUM5-gZ@wLX+*kl4fR#JAVceLRH1$O&EdszbS1sN3fl+h4FoW zEzyyKBs;FxCXF(#J~yf{GGhlR+nQ5zF>{!oRMe?`GVwB61kN3OZJyt6fpHmeWs34v zW(O{nk(`DriKY3e>GPCLX}F`l`0Y$99X6UIRCVLhjfd8)^h-#YMGCfs2E}LNnW-AN z5N00!2b(A|s(7JD@f@jbY<+7WXGic+0uqi7hpd^6rC2v7`(KB%Tt))k~ytd?GHt_g;0|pa; z|HSa*6#ayR(O#4&1+_m43(fEa{Lr}|ojug8lv9?}|6RxDarptbxhah0Uh?+!!Dbh| zOyrDri2vJK94CttiKCq3v17dbIiK*0w_mp3Y6Gcb&{|O6mE@h=WU^(sO*xW^QVv)| z$Wz+WYR_S8`TaiP934EE*SUy_7YOZy;LfPk(A6Ph(N2F28%*Z?{kBeUhQ|VC|$`=;3}{;FFi{ zWy}TI`gq&JO(6K~8i9cnixf{p-B0sc=fP!iDoupvj{hO=403+zi}kc8)?5GaB+~eC z?NV?>2eBP2_+#?+b9WkO`mt?4bs$9K&Fm*EtbQB&%pzc<)AhKmU1!`WZ7zdgG-j;) z`t4c%W&VAU!>BbOB3>vk`N`_l@mk>A3t_`;(_J4o^WaSY2CwhJtv;N1T|BDmIqX__jTP!Cj zrs=(Mp6!=nsTFW2(%U_?yP@A&)mhc?ye=v+Ya*g5NfH*y-%ns@CA~YwD!Ic8{G7|R z8_mEE^=%l)fW5#joimUTon=w^vjP@Q4Bl2Xt)ffMh-qDPR%sT!sp@{Smwget#s6C0|NTW|sBS&n;mv+84*5z&M3z{>{D{^6$eE3P zx|M`flg#6%)z31H9V}Vwk(&SyI`8~(IdArl-GmALz*0gow`qzms~@y0jHnq5G(UH* zIsfEG*G>p=RzcoxJFr;Uh5JU1Wc4po2j>TG@9xYcSN?c~I#%^E-Q!*<6~*DGG!>?D zFzbNFP#KEHcHZUFQjK;6QyyoZ&vwx>&eQ)8Bf1ejfr&|m^J zv6VkOAqayD$&@2yWv8x(Dy@b$>!ceGq`PDFiVf;SryHzpE-J4U(Yv`!M^^iX9JJ!;@iZW>XebT|$c&wS+t;U!kmC0vy0b)MtuP7nfUky6;7zbRLkqMvjLLg5ChP51 ztIthr5Q->HWS8?tAXeSn>9p3hStvk_4Y9E5o213(dJ-MKf?8{TbJmymbv>h}{N7tW zn(FRX_oeH#5^MfDZ%oeLWPwAz-pI;-eCna4#RT;(s0{-!j~gM0m1-8x83oVw1s_(g)c%HtFTddr#{thJj@0pTo@scnMrQn;EUaJZ8^>Q0nZ%) z-{q@^pkU>i$cgtKF)Y2gNB@C%JS(+7$l=gnQ5rZXB|86benhk1oB&N462hh2?j2+(LJ(c+Z{AwCy&Xcg zlqrsbe3%~Lgq&PiZ?C>AaI6M9heOGNfwT3iK)OOYa(|w{7{81*btR>^Fj9KqtQ6V- zmISsIa1nUUX>tHZK>C*zD5 zL`^g|+&XRn^wo2$30XZoiG_qq5^t3HDy6NasI{&%?YnZ+FXHpBd zHLSQcR*jXO`aK=>>PwPwIF5N(;tN&@jmA=hJTerqHuSZWe+>*oEMm|V(PDN$ z_eZ7a208*wtN|ZYN%fU>ygA;1 ze8)a^U0{I@R3VqSIKsnkd?6||Ew@sk1cf}@4i{Xn_sfQm4N6gJ6yC$RK&QvBSXNzV z3IcNs7{u=AwNP0)Ykw$RRhT%k5Gm+!mgL;E>q%!@V;ikdS#zRCe0#m_=Z0re-4OH| zL;{DeBEF+8mkr^_V`D|U{Dq1~DUDYxPAa2F^P+98hR2qdm<0?dZ5I7V!jH9F74&wn zZ1AJq!+ePOnb%a15ph_?FFIof@kC2qE-;4_1gmFC5MEU;TpA(`^Yacdi z>xpf@Zj#DBT}PL*aScXFv3*m94crI}0Fry;vHws=lc9A_z$I@?O9(K*cF8DAvQKO% z1K0@1k1W^ez|g0%2LuHCdvE`4F3NZmMBzsz*booCzxM~uqCYIu>FDD@hh(GEtnsB> zFMZE#^^!0-0M|rCMJ+d&BQ)zdE<8;N;U!zuM3c8P2^@4=+t}EE4+j_O&0Hd4rwoyj zqOiH^b?ia%;arRRm#N`t! z`#7z!2@6jiNNwjp-VwtZ;o12#MnkRp0_x3qZDHB8`{dHaB4bInt_eftN>C34dma9e zXV<3i8GI#Ftu9ANP;MUO+)e(J+SfgFyV(a9cj zdKnr2X|A^%$7^v|c3l%fJUIW! z&ewq1U|blW!6lrXW`%nk3Du@?7~qgFztu7u69etc^o3x6SkU8cnu_s`M?0_5(c`ZK z4)4t-Umr?0IMkh4^_*2d!L(eG_E(R(0dx4e5I>7!z-PSAG8bKA`GnZLbFV`4A;_)J zWm737a#B`OTQs8>PZgw*bIDLLxJ=cW+GXw@xyLv7hC(2{b3XeImrKZo0X9{SnosjK z6WXLXtLJp8Q^dn%r^LBcYE#6PC=WtBp>8X9djxZOT{?;c6!Y&*VYPN!5;o~z?oRr% zFD3EI+R-)m(40_Fd+ps#6&l~=cNoz%%!Yf+bGpmW4^um0kAH~ofLcN+wM0`yx&ml> zGfpJrL#=$+Bo#sPUSD>Z?B#PhJIXx*4uqN+&ASrW^;9Y>KbNyy96bLL;Ps!Fl=MW3 zh8q2ZL1fZjYcvJ}!_Mb2()q+N{e>G;s5|2`sXn)T<&9e}=ERW0;_ADP82cD2gLXqZ zPjFnVKF&^WD$7?NzCadn`QB%!0>Pj9#wH|WQ}y#HXJmrSva0LB-tRGcQxBZI$VhRQ zH%E8JSe(XRg9+Aa%(xW1B5pk+wl*tCl<|}|MP5NVS~7-!g2ug>}+1z(ZB`i6wL2XJQiWc%BC7R9F1BV?PUh&BVE0oJYN65r;jy8Im3UOrSheAm$xKO|4+x!IB7*hFSc&W9fK!U~HEGDxj`Kh57KX_$+F)b1BKYir zD5vbZvdp4E#RE?T3q5c^<&C|iB)fUyIvH+N+qmct>pk+rEv)}(=7+5kNH z8KC`oab*inlQ4Hv(!Go`cL=9)X^nWrYz%NrDngqp)O%eph@17iYAJm;qh!T|C5Oet zf=!v(EA?H`>*p1NHb8(HGYbEVdW9A@uCQ`q9gN@ztAns`FjQ$mbKDCOkTv&zndB!@L+#<40Lom`p;&GaP=x;dJos!oKIh9ZxML19T< zvf1uIxZ$IrlKVg<7{G)_XVoeb;%}(vZ#1AW+tRmM)66AD7oAZGHFF|?BX08rKI##N z1r1jUw~S~IqG$g;=o`v{6+|b0qI5+waTtUlrYc^9sQ=^d*S+7u0q)-yak{T#;Hovh z5EeL|EZDsS9|qs~Agsj1GFjSE!sJgWIbx|U0g?}I_IV4c9iko8LYNo65Z$GiSR`Fb zW7bwW)1hR^_&%;J7Mnr|LlcF@Pk$Ace>y5x8+d+f&-Z^gLTmKiwtPfGHDQLvdE8`z zKG@Y5*@Yer5NuJ>r$X2X0VcxFVox4T7sElF2=2Q^5U3RA9iZRp#kGxoNC*;AgwPskZ(?A`VF>*?foEPX2{SC#@H^2Se?6Sn4Qm67x5^ za@YqhpDTT2MZ{U{q&b|dK3blwABn-ZLJ(^YUZsz?>(eNM2<8BkI#OcNe!Rk7PrpE* zXY^e6*#mu3GPz}s?=yFb<5M6c>)t;5TlZuK{zbjzUu(HEKcY*k?qO?rJ-3Q)0wAPqX>26g+Ck*8NRfq61{yl8Pi+zzol)JhB9^4N^r5)bSjw<81V| zpPD&tlWzRx+s%MqV!}HEqT#YB2^|AuE*CdNh(#DcXvI-1PlQ`{{XSO^?Nr|T*`0oG zp5@RaZw>dqczCofb{JAE*-rY$CN{dvlu^3F5Q$?t#yG2Z zle28HqLx}rp`;QDt0-wI$N|w5U}}Vp(#hCDI5Tfv`HiWZ@#aCRbu(!EyfyGLycd)u z1lLIC?!Xgw4*ukGU5;@_#;_5Cl7lW({szrvEPabj(H=Af1Dnm_XKsc4S5e1x&k>Y; zm|f-M_8=XMv#JZy-*QCjv8ZrIaKFgk*g@Df{#t?_^1YCLFE_{zkO-_Xu7yhlj`pUS8T8&-5{hq+E_h# zzn4EpK=f}ItzpTP|Y2ztlxDJ|; zWRV4$4sN1NlJf1p?^gqx)J%`EbPb_;EYF!-(k*R+Kv^Ndc7v)MX{gta@pqT6f0`fG zd|GW!cR#VH_pIS$oVw{iNhS!lL%!VfKM3~jPA7mJ~f4{yAw5BU?IS$y3LC?swWKv+?qF9NX(M!Lm|gD=p;0VH%A0b~WjQ!<^8! zS^e8VOgL9jIhYHB0Fe>vP}*soeVh&k3dn}SpIp2Cv3n}*`~qPKc-Z)r#iw1reDj?9 z0>NSnnYPmNYlQCZD)>iC=Ayp1Ze(RIJg;92)JS#7Knc%52S*pjwqoC|(@?((jh zy!}S!A2chQ^|_xwmhA>!pZ#BS=JoObfy~DLD0;ixF7@;Xe4NcDZ2Cc_9?(fRPy7)r z90P7AJV7gwyS!MT$$(AeP&ia+X_-mN1c%)xAr=dJmG!$`Fh8U(AKmEDuUBNoZD?6z zHjj$!QISl8%FQP!1-Ar8L5~S5OV^z3Io3Cv=NB5Ub84v*Q$jqK9gEXjXOOJZ`zvZ^ z6#Q@!r{hP3sK9-x`AbY0$Y8)d#T?N;ZJAOc%EIE2`gpnfFjGrq<6#p&|KXw)z56`u zlE|pp#ju!W=LAU(_LEJK>M8wsAWrHL^9|F1iC{H9=YNqU~k%;mg}F zOQ5y?M=gvLP=umjQSZMQI4tsjk^F@0%sSJpQp77WJ1lD|vGz_PSJQoMVYS-%X zybg_n4|BX~tS2)A;u$%6(DYy&_iWw1sy5V@IPls7>s=~;&JPnMIQSiH-FG@~aKCPy zqt8qK_;Ssvd;4JV>&?ClDpw1AxP~r7i*t15x98qbqKTa^y$(BDcdzy4Z1URkVM0Xr z+jyVGW<7--B$7I{wA@1*|3SvEw6RjBgu&iodD_JB%DR`Z{rWlz!Fa7X;A8G+r>?1k>F@~A{GX^gBN4xQ3zC1<9O)QpmDAAD4xijTC#qK(Fb%3n4Gl4L zUHOl8l1f+UR%{?t(Qj0j>84T3W$|8~!h!V2Jxn^57FG~tk!)!Ta}jfkKWO*i4k!!X z{+xrFiX=R4h`C|=7{~iYM}gm68xc{pvag+H9Y6nAtfEPT$Q_P&K|80z{b7*=8BlR1 zWa~}4bE&%*2_-s@yT+K$-$QaCt=+Tdpp{bWGyejCKRxtB(}8Z*Df6}-0utT#Z_54D z$X(UgnzYmHWv14~#-{xKW){CYlav#tm4^&oau>l5dEmoS;@(NP+ma99o!y$rVY_lR zn>NX{UEW7ka8DX+j?M64mT=vDW}VNA2;Y9j#bU3!#lL@BYIi9ecXL-uQ+G=yi+>Hk z&dSEh#LCIU&ZEi3&CkWh&&J8X#>&si>d==e`F{pSXA4^^pZ~|e;kNtzp8+5zr7T%1 HZW8)Gn-q2% literal 0 HcmV?d00001 diff --git a/data/themes/emo-suspicious.png b/data/themes/emo-suspicious.png new file mode 100644 index 0000000000000000000000000000000000000000..15bcdc00351e2a0753ed78626f637673d056b5ed GIT binary patch literal 8543 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 IlrRqdACBQ$X#fBK literal 0 HcmV?d00001 diff --git a/data/themes/emo-tongue-poke.png b/data/themes/emo-tongue-poke.png new file mode 100644 index 0000000000000000000000000000000000000000..932ef8569eb76f840c699c8cc0fec0bf04447387 GIT binary patch literal 8974 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 ZmOlR<0iWBh^FIObUO`>HTGk}w{{S4DQZ@hp literal 0 HcmV?d00001 diff --git a/data/themes/emo-uh.png b/data/themes/emo-uh.png new file mode 100644 index 0000000000000000000000000000000000000000..554ca35b31a8223fdad9c3f8197ac9f65ccc3a90 GIT binary patch literal 8641 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 literal 0 HcmV?d00001 diff --git a/data/themes/emo-very-sorry.png b/data/themes/emo-very-sorry.png new file mode 100644 index 0000000000000000000000000000000000000000..97091f2a13297288bf7732c8be99ecabc5f22c3b GIT binary patch literal 9009 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 LYBDuappgFo>a{+k literal 0 HcmV?d00001 diff --git a/data/themes/emo-what.png b/data/themes/emo-what.png new file mode 100644 index 0000000000000000000000000000000000000000..a4724341c3d0a605eabfb844ed906587b1177e74 GIT binary patch literal 8410 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 literal 0 HcmV?d00001 diff --git a/data/themes/emo-wink.png b/data/themes/emo-wink.png new file mode 100644 index 0000000000000000000000000000000000000000..ad4553a57692e0ea2fc220ab9190dd9c40fe15b8 GIT binary patch literal 8749 zcmai2b8sDQu)VplZQHhP>@-b-#*J;;4R6?}u^TnEZQHhOz5d?J`}@r|XV1*;cV>6? zuQMB=tR#bsK!5-M0FdQmB~|{h=zoBN`4>wq9X9{~1Yt`F31v%TV*tQoB~#U0P4yT@ z_;KS-Tp>IlQNdmX8;(px92}r#nTPQUkoyx4L-Z`XxGOx5A_yBF%du-3J+7J}GDNKU z5yBIWZg-20M{NUjgTS};pqwqCEV&i+-OfKXfGw*N-8TY?JR=6my3#vR#108k+T{($?I z#Q_Cq01hW?4rl-e0^qE`B^3yu1^{$O2ysyZtRMh_roX;I0^DY(9)W-cI#mXsXg)xc zW&|q&FogopOv%Rr1F8%FbR+TM&Jb1U0E1t-V~GHROF%#-J&p+^8XmwP4-HWj0`39O z6(=Kg1%Ts(po>bZ^qA4mC7)0Q0Iq6G!27=v)u8Rj>-vaw^_o3$_;@A$Dlh$n|9K2- zhC4Jh9f6wZ2PAMp0s^GnBm+<<9(VZ#n*;<``Bnsc>We=K-oW9};LjA1${q*^z|Yxx zsn^=JzXX5_JV3)WIJu5E#}qkW;hi;Ym;^8{9&k{mKi<3jZ#QZo;s<8tDe39fjOd8A zAtn0v&)M+)5c>DE`~Rw&i@~pv3D6@*&?M+v!HBgSHHl6_Iy7jJj_D#K*PASFx9*By zG+OY!QHgStj6z>Ch9$zp=&wjB1i56a6xq*&2>;qM)ZcB^0E2lymyDC#Qo2661OQ0?L{X+9vc z18|}Tx(T?rg(DR3125o^4Z+@kNDPgmM^ZDK$0*=8#X>k`kCYj?pDY_jU>|veECPj8 z;*g37w@OeVrTWm10+MGE{+J9Y7INVs;Q~~AX+H^24&I39axsZj=t{2c93irJ{?xMt zLJQou4B|Ah1+{iCiFo>S?Gg4J&I%YLGsxC;ga^ynXT!!a&?{c;!Gxb+JX&q^7g*L! zP|fofvo-MEh;qpr7|}(s1w|MnNFK+QLPo_z!9<&gQ3?kOH~tf)2U(odF!3sNi0TBR zJi<;A#Gd?He2f|goiW_C&$#clPp1!JhY%y8k32O&S2nPKPldn|z9g|OVNOy&;)MJ@ zVPMFlhG#kLObmq@aR|W)-Ba)x?V0OYz%$@2M!X15nTY-)(IYZZMYJS`s30Rxw+KmP zpu|c|wUm%Mks*)ePx3eG65F}5IfxU!FPUaaw>eVNGZtkQNp;dIo+}b7i~^ZMb5HR6TZg(4L?lG=6E=htAf>*8y%ez{(WOnc%M$PwHE3HEel7_G=elvu6*uWt}^bgRu4{WG5BGV!&`}tF%EXlAjRqQ9bqXU)Az&y z`o*HQ`LxpgLh1#E1*@5s!h12o#fMp?#f^gXym#5K9OFXFiiEOSg~PUqA+-m!$C93s ze$`mT_Db-H_ObL4%k+BDYN6ntqDtHx+S%0#cO`qt?EK5Z>_44SpNSt;5Tgdkfqe$x zZp&cvCYp>kON={-$-0xxOx{ zK9dr;;9+0YQu;-%d6#s{qGKIS=UTkldNXD-i39BepIe_>nAj&z7~I;6|cuuQr}6WNr18KB<;0VS`oDmV<-1qcUT?^9-wQE z2Mo`7Ph>A0uOd&<8^3MiOUg(7gWKf80i6NCUGOu^6V9vKtL4-9ec6ronf+e&&gPZ~ z!4_5()s`X|I~$#Y>K1VaiT+UKVeEukYP*e_3>qaJM=`^ZT$Os2P!ls0aw>5R|K2vy zEdLBYb1vEl>N?R2-I$Qgx24$af~%^lldB?h6m$hj0ZOfSL`qcYj)yH39mV;T%bb5+ETmVdw${i)Ag6@`e{++X2*wfb@7u^ zgs+^`@Suv}@xDD#N6DL+k;F~t1;=5H9-$mzA)&qf&6-P&Zo5!to4@nW!2$DA@(y!l zBg>jsiIH^wg>9Yfh;4gPcT)N4mj?T_k7|bclkfFkU1w3&iBH|z*6CL~eNz@I2G+e= z72N!nD3_hx?YlM(2x`+JeG7c~U$YjZ7v20u-y1rViYf{&X8n#oHXzYq1y1x%PEk)t zn5;z!6OntvFi`YfCmvfDq|*o5zhwOR)$5??`Lz5PvAGGta4C4Fd$ia^{UdV5Hz4qR zEsBfPj>J~Z_SiPs`kWv1>fxR4y;@Cb>%ZpTb0v8%H=bZxWKo3h^-IQth_IWqo7tYt z$nwWS$T{jne^%=<`o^>`=;*B<@dJ0l)yqArEw`wdSMa_++vO@4did*4gd(sTaoco>*tq=d(!7=e1+b75%Mc ze@?f-d))3+gyHA5_2hvtp$CgM2&8fceqj~-q1pDdtx>7pDs3zS`(s33>FxWA{OkP3 zBIl3B*pO&pzl3MAH`{B$b9dMc=S_FN@Mku@tk?Lr>YIf9qJ~MaY*Hl?CB-*P$lteb z)W)27|NJDGv8>7$0Kn^?6$=Ok0G>bp@i744$_4Xr;Qg0$a}YEC$D;p>liMc)003uOPEt(GW92;E zyN+7j_fVv>-CaG?`9k<{`tc$CVig$=ZKuco;pp9|0URQL6UZqyBnWW zZm#?9vZ^odpNpFD2HhZI`PEGY;bZ zPk&b0XKRv`C%i>ncS@((R>M=&i2UCZx07VByx+=Mi^$Pyw#%9zb%vAm;4EPU@J;Xw zEWi2`xlgEY6`+Z;6rm6GHu5luca;#&z_yUK-Nj#h&ezRQ8jycEb#xyW!Wb!%$LJB_ z_{bJ%fjSeedTdJXy+<#dXONb}0q6r+D<6YV_cq%|v0GT%{zp`Q`!j1ga{D9m*Dl(0`uMcVi7jYdR?{ zOVw=u-p24VM>;Bxj)MARhJZ+!8DuW%U4uD>>t6VIhB(RX?=0i8&zkKTtj3sUfe`JM zWX3pU2fx7Q!`K^1s>*PBY*MK_xjGksFbVy{a0R_}oXrm**!abT)oh%frL~QsAl1SM zu2hWM03F?!%pD#A!$6K)(UjoB#{7XWdo#(d81H)pksRKAPlwr-0Vmrmd_f6XPyh}E zOaWJ#?%DKVbuH|q(b3taYW3y!?ZBfUW74P?p$A$1fo5#p&L*h0=UIQ)J-0Tqx{*N^ z4`GtZb2G3!)^-MVe_$z@rWj0sdY2YL{$~0e?&tBu9W#E--9SqRLkYpn!xmPbLGX&K;vTxZ9rZXVd1@GTGE>178GOKGJ7$ z5i1_2mjnY@+l!&Nf={gua4Xs)2BuA;Du~#mu@YcK#3Y?g&9RzHCT`0nd3&t~C>a)+ ztBK^3>=hY5 zPAeIHB@Xjh1pgY0rpwOj6{z@1qZDZ1bZ!o8_^N2AuYyMLe5g!JyF^|SpF%z^S5S?b zpoH-&sS|wSMU(BxNqNZSrvk(&h6Z*B|1=W|wz?w!iKZsT76eJW&QVtBxo6?gTSZx_ z-3<)m*pJg#$%A5qVk~CnB8DfBvpcB(oGC)IeU*&sGdM+8spiL*vQZ}VUp3gsq;#Ppix*cNP zTRF)XcxqJh8_@zilQ|jpVzXeoe#2(9LE}3UVIOAR7JkNv%Q$TIg^!EtdQ6rGSs%rj z1$34TUApR0CcKQgMMNBe2W9i7rjvgo@H?V&ig>TEGjII%*Z>LWHFq=Tdn|qwkxt{; zLBi(RSYwt(o2Es<&$vNcN#$>7&DirrXrLENovy7dw&392IhfP8Nn4#%;VHx6krws| z>1xM#zFy+kMv*#SC5;ZNu^KL%EIW@5&U4R#+_$GIrd9Xz{h_RPuApD!KWBT0MoEGdB*w?eef;+bj7Ed%xD|&Ro2~JmcQ5s7yZnmGCm>c&KW**FFfkU9gLlMX zBd7wcFs{?7;gvIinvhDLW0G<&AfJ84@W)Q`L$v;8X2-*t*!GNJFXn7uCF!*gSGmw~ z(0Y=2?Y7bWFtf8gkk#je zMbSE@vExDf!uv33&IF-^Zw`(jXek3u(kRLYC;rF}UyRzv;(@a{rju^;o?NURW z_XwJKlhsA9&^hq9D?Yr`zYT;Pn(#k34QqGI8*KTRo5JU$x*cTy?l@@0(!nzu##TwSSOqZ)Rf?wdue4`ZPrPj$YZ}Lj2g)-d~>Wfyc_u z5QN^1*Zms6fD3sE06k+ui5(+|_D*o{uFg>@^$e0&xBJ$lW;%9P87}H>Rk{`W96Ait z)@HRc^Zn{^Ddkcr%%o3+?L0x6(bb zb!+W?dg3GGvDr%2vD+TwoZOqdXbzM8xv1yM(&>E8aP@^v9Iab3*tG$v>au?sBEwWn zYYfQZHC{>TZ0vK-H|bt_wv^tV?PqkcIcJ?rju=a#w9JLe2dtw6#|jZ3k>kN&_9GCD zV^zXLGt_G3d}APeMLTcoKrBa=0MPqV?qQfRFCgi3G~2UocsJOt4kR<{Xx5m( z6Y|=bOlAqM`Ms_>))QQMj50p2xQq10NJCR+N9ZPE#?dpf9q1daWmC{zKFKw+7=UVS zmjva1v?AJbse5nsdGswCv%?CV4d)m_lj3t#TbPh>s0n^q7$-4QH&0dykjPh9=Hwbs z%nxqA^<8oUKdf#}1{AqUM!eGP?kjVE)Y_MRE|NdQM%ZDU_!*??at#Ty{UhN25L6|=896j^*5g9)G z`2En?g6SF@4tsB){GDp#>Iw}L6Vqm`>AK0#MS$4M%uG2XlDlnZ-<-Yr#4#(orWn

    FCk3I%FZVSV&$B){XPIlvCDD?Muh;7|)#A&yRLi(} z0+Vr=%fvPgQUWRs@Lg3yyoLCM7pmW;is|$Hw4`hMDT}mmYkC6Lb_TXyjnxKR=-x;^CfjgwvN8;`6 zLzL?MF@>CX(bB2mGO_!(rKs8gs{(R|{xbiNRr}Shb@$C^cF)Ey>do7sgqodx!dl8f zFh-PXPW=KGFPq*LuWQDfP^_VR5l2YOoh&xqSE%sI^cZn0Pg_ZOFmfRc48#eCR|;Xo zm=f&wY5g$0v8d1_pfy7!XzLI!8#d`9D6o0rcaEMhg$c7o#Q>$D(?%pNXpTbdkk6X> z{uJJ?7^h0olU|s^mE~p^Q+_UXzxb>jHwZT-iaM_;VT=`At9rIXqt$!Wf5}UF^X!Er zz~PIZ5&Z%ARrmcFIg3A_$EY$uYSOH-fE6eiBm_%_TEg2LLvdIS{iUuC-BOHyBToIDpX^C3_}ac^t=0Ck^cYj1kBT8LO7z@(DDGn9;>I!0QC*$*p+MDe zCJf7O+kpg;FyY5Ef*!*~La1q$C>z!(P~$)oOO_5uEppIkr#C7A+{Ph@6(tRScD#gQ zbQE5>I=r6G8lIAo#w6ATp(HBneOi31Gt<*qN?#^<(qAra_rYq zjQ>b}7a3>nR(Mpw1IiMCUu=1m;f*EZiJvg%>fDf+cQnRr&j zV{iE`=twAU3ZAwJX_J*mo0JR|L9mgbV2AC%?Nm)v+nt}}np?Tnl&F$#dElZ+A`#q# z{?V)=sc)G2E#m{FG+lgjX&R}y>I?~S&J%a*l$pbCp$}N_L!=9b)3Sq4oBo1bUj;V| zdA@SH;Nb8`r3zc*42&Ab{Snm*?$sV_w$@lRFG7vWP(d1sK@5T@AoigHrVYa$5HIW_ZdbRyR@yiNZ_pUh2T|fanTW}?`j0^;cVGLY#gEsJ_P|bqY*W;2N6`C#Qa~S z5r1&seJCOFDx>DYc~P^kI76@pl~XVE?GzE5`CPUB^<6(j#}s1=?=zsNVs8pJAdY}% zHDN9!KBGt5ilr4bj1AY#!DE9^JWj9RwO|h5LnXkb!iK`D6(#(lOH%-pqzjT&q*V`c zHDE-OiKF^0A4S7{7+WZ^)P5_*UEi~!BrmGTreX)nL+-WhxJojzMIuTOEJ>ymFB`9k zwu??HD*)yqn6fk|2qy$dQSmz0y3ij`myz>_#lbJ%5tUQUKAnfbo8rn*u)&ja7UN1% z#DyzT^z~UJiV{&K!D&PfQ4A(s$9F#W#q^FHM=UD7JisxJ%=psb9_X#j_M}f#JRS^C_HGheUdz})R`!`^AvT07PL~cSpT}vMB>!6;BnKS zvVVi3Vc{aprx{5g!4<>6-J&cwA!}$mKx(!(+vS|CW~b%)^n_x18AF+>q<8}h6&1+< z`Qd*G39A<_t2IYAUEp?k?LL4G_y$`5tXmp>?FF=(}2dI^5AE(Wy|3 z!sdv+&0`py^3I|7-{`rohvD)qD|P))P#lZUd_s+EyXNabptzx*+B3SzAcB|W&7KUj zE<;j3R(Q6)lxT!pYayo zny|nG{Xjz{7@*!2zcM?#EHrZv$qw0wlo7aGb1ZZ&sYlV^3bd9inlpS0*&A?(HU>7)&>{Q7wu?fd5(yaqo!bt7fP zM76|mx)8gpc7%EpX3lI;K-E-`F(WzDBz1GAIA54L{iI(ZYyCf}1ut7(CBSJnZ|m1! zj45FoXnYW1vVP3pr$R!9q)N))L>3#AQx^xJ8yxP9Fh{YFdRy%;!i!B(irL5DQOHcm z^`-!4&t2+>|WV%pGytDyKC!zW((Cte8H@G_YR(Kz|d-_+5Q<) z%lVv?VrBGEPcGmXBWFLz;7z}pt2mqpGQ>0FK!oSBx5!|P!e%7;-&&~nHRKUc&N1g> zho2}f=q{MI5Sy=V6MH166t(Tk&-ibnCyt}P$Q7zW^Nou989nb_P&eI1QBmzTH~XKB z(8&;eaP!jYHT>T24O|3)DBK!SW9PIt(=IT_&&`lW5)Q6LR zCoO}7slcodhHPv7TZPlt`sIpH#Ch<1bK`C7p#On^^wt*y0k%#4f#*TaQ`fvZ(tGKZ zhm#ho6k}fnni}Gm`TJH6np$~8I8VQwe{hW%1!&$8N7Dm;bnKZihMFocnX|Y@p%9p% z{Sj~YbZzZ;Ir#K>%tW>KGpjAs^wI-7!9TLFN(PL*3i;>PMeOw1y>0J0T}zdVgj=Tw zKlYArlal4H9MM@GI47%5%}u^gX_2V*9MMu_ibBz0;qP^vP#HC> zx3P0eTmF3MDSBFM1=YKrCQBF1Dh;P-3AOu<7?Pmh>WSh~8gwkDgDB*;q!N1|&}B2! z80Jk!HIV-PsCHq~^&9;H%i@1qo^U<0Kh96B06mUWkgJKvq;mqzzw$N6#XK<(Vmog> zxoko6SLC*g^9k?gRywNE`~Kx7ck6wLZMo74&=xW?D4;Gj;1?1O#kLy!(PGCKq`mW% zzgWGjcQl!qkhB~%hG%d>bJ25|8&{pR+055^`Pn#?FnXxV z1xkfl1&^)jFASzcPinB3;B4z5$?DTp$KdBhrN7V7G;Edyv2cw@7ZV%u81~Fp(e#bH zRj{O912F92p=I-{DDqZ@$7w?|t=9vtdmg2{KX?&2CwWT5>slNpvM1 z9v)EygQLlA-1Eb<#5km2qmu1r+woNH`YI|B8UJ#h1|J#zs+-O)@^Y^e)KfRw zmKUa7IpgW9Jdz<`-b+Vq|9%U}LlCNs|0OfvvrXrJ3jdBj9x2b@(R$$Vn+l JR)`w}{STy3iLd|w literal 0 HcmV?d00001 diff --git a/data/themes/emo-worried.png b/data/themes/emo-worried.png new file mode 100644 index 0000000000000000000000000000000000000000..b081784d3d25cac418393576f679426b7faa645e GIT binary patch literal 9116 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 literal 0 HcmV?d00001 diff --git a/data/themes/flip.xcf.gz b/data/themes/flip.xcf.gz new file mode 100644 index 0000000000000000000000000000000000000000..36aca4d2b511ec96ee3c7ad8ef947d1858e1e5f9 GIT binary patch literal 10985 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 U`$L{*3HPl7=2$CCwTXM|e+P!eLjV8( literal 0 HcmV?d00001 diff --git a/data/themes/flip_0t.png b/data/themes/flip_0t.png new file mode 100644 index 0000000000000000000000000000000000000000..72506aa1b10c716c2a6d26895c4bcfd851ae1c0f GIT binary patch literal 1547 zcmV+m2K4!fP)Pa1J-Um1BDdszU*{ix%g))Sv(~(fz0cO3qZTXX82^~xnsbgZ z=KTL<0FyjDJ^iY^{mt6i`s3^0)bD>1FlzGh^75DV*WYbyY(C+C4fsQY_owzN^X~2r z-z#or2x#EI!NCDr^lR^bF_=c)A6Hjb3LFOkXJ=<@U5WtrwUPHxjXVx|T2s?V{A{Jk z2L+E0o@vZ!y0jljRae^v{h_m~m zsiv?bL#o71VB}ZNWfFuSp@J@ z6efVEf`|k}wFXMSQ)?grJhcWAKva34Bt#WNBmvq;>PxBP&FxD|OR%!C0^8f$`fG1* z4=yh+;rjYoe_^Dg_7QDyYaaC>`e zyuZH}wZW}-c6J6mJv}fwItsJ1vv6~B!)@cOf}^7&#Ky)#YHBKEXJ><_r>B%X9%Xxb z`|k&EYHA7^8yjI{WCR``A9?&_Zi~-uq@|@nad9!k$Hz14i8lN$0GF4Sp|Y|P#>dA+ z{S?wmN=kx?iVBE~j1FGZVJna1D=BDlw zuD{em3b3W61@iLp03VzE(L~EOASWjW+S=MkT_Xe7)zt-MWo4i}kWA_zr7`raw6qj@ zdwa>u8nk59D4SMbgvA`}y*%}aiFaRLA0#9sNP$E<(g1gMc63LudU#Lb>go!Ulat`@ z?=S2&0+gD<&(F_LR8;it;32V#iwh_zDUn`sqyW~|*24V!yznRZe=E++%s_p8y_6fm zQ+RiG7h+;!NXs(q8$%!?BLgxsGxZ9>%gYNNYKG(EV_02Xh5r72{YAOfVlKC^umFC3 ze%v7SHBkGq38RQZ`T6;JXQ%{sRvH=_AS5KjtVzu2aOz>FsU#~aOQ>SP+FJ3acm+3EWdp$5YYq<&!~Xt0uN(X$u&Jp@ z-zBDyxVSjLZ6{HY)qi_ktWrdFj=0W5FxYf5(9lpSa}X95256H?So_KqM6mFt65K+ z{eMcESd}0|7GVk^JW+||qTb%#EX}yuP}^KzU$=OD<{(0SK>jUm0P^tgu-IXq2CRK% zn!*PM2Rzrd*w)?M-C`Tw2GllL`^*IJZF5^8X)U8yE9E;>RW&*wz0mZPko;> xYoD0_vS#J1LyEHSf4wHPO;UiY#(qYCe*;S|O!Eakt z5%>0{p&wHqgKOYSHm|Y;+C{nR4)N|#%w4OY$WpRzFXuC#q!K+**6)vHtLF({QyHC!)GxG1+Ij9Ow2BfXQI&+OYhyd?}=~Wo@qxv&A&6}y>ibRMnW2&|3CKN z_y3=J`VIbZF_UR6k#3y7?)q!%c^hxl-0+=#`f24>rizD$^NMZc-fzGCR(syoQ-4aV zY<+g$eV1GJX@?i%ju(k$Z}#nLeXg$W{JF-?{@~32cCz)K+b(X9N_*U7&p4OKdBT<{ Shh_j{g~8L+&t;ucLK6TFnXCo? literal 0 HcmV?d00001 diff --git a/data/themes/flip_1t.png b/data/themes/flip_1t.png new file mode 100644 index 0000000000000000000000000000000000000000..6c1fba8f0e3a5682079858f86fed8e26b809325f GIT binary patch literal 666 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 literal 0 HcmV?d00001 diff --git a/data/themes/flip_3b.png b/data/themes/flip_3b.png new file mode 100644 index 0000000000000000000000000000000000000000..2eca7d4f24ab432324c846402e3e49c1ea0f98ba GIT binary patch literal 1408 zcmbu9`#%#30L6zH#ymE}#5^K3H$D_Ck48&lmyP5t^IWmQ$UN#c@3~{i^pVjFxi>0J z-qM(ftch;r8F`gkmphNh<>KmZxaadZ=ljb!zn)xz`#A_04h8@K5Em@QbDxACmIv)8 zQ*HI}K7jE~E?)Bcx-K712LNPkTriGaNf(#O0!$l&)cZ#A)+*>aIf@GybcRo9w<%M3?nXVABA z-)IbmqIM;R?1+|Ou~-CeZ_wc2V7TN8RNu3d!^vJMot&ien9SNXBRzE3ty@fHk?;zU*j0&sk1;YbDkv*^ zWWCrjn1zx9fj~~t(a40v#B>%57SD}J-`GfOG6*Gc>%Y&<%@I63rOV69HD#~3W(JF9 zW(-=}+bze`O=R+`L?Tf-n+^XB{T|fW(b3i2ojz_6r!phqj0_K_7Z)Fh@A?eH;c()O zOffnSS{zbcT`iU>g^|f*iwT&fzB9X|r2ilfCFt*0Xt1x4a>igR{3Y7d z)YOmmbQHZw0aD=OCQ*dfUH2^=0>oUs>N|JBmb0#>ny&zfC6RKFXeyN&nd&6da}+!n z*^j#5OKYWcfgyvMaJY!fR3QHHi-VcDxfQ-Li`&+wUH9Zk8(UdXF|4@{sH#{tHa12G z3{+w;7-H56l$g(}smU#F3r^%6dpUj=T>BB>(c9bW6cJ%ejEwRKwbT%gj%s;%d6`}y za|YhLQR97nnPO}r^)DD82=xxlJ>uZNnXvK+L;Lvn42_P;2L%OjUsRFpo^EY#mvq98 z0rE-fD=TRqJ_KU%_?-Lq4^du(M?{=G@+C~bq7G|sPmYYpp-`xsh-s=yw@_$s^r-6> zfj}@Vk*M(beA@RwUyu5RhK!t?oZy|!O|9mZmOBooPpgnfB(Y;Xm^c2sy&arl|JK;C zBs&%K^i&LFZl#exAP{dO7hnFw?oBycQ&XcU6h0us_3P~X{r#~Y>jtD7TUv6Oo2{4E z)>r^P1^o^tQyGiHh27b;p89M#G%x^ZfA-A4-29f33S>0C-jJ?lra8?=cQnnuCmYJF zT!c}pUyH@DStOV?{UKv(D}|nyH-9H#uR)k#l&>*eQDLB^rJb} zGViM^SnPSM79AbUXoUhS&9qqCR0^t~ z`pHtp7;Pw385qe0Vh^EzSZ7Uw(nXN78ylTepU}w>a>u5XKQPV(3zTN%r-V{=86mM zQ8cVO{>eQK=^WYY^FP?=e0sSoC$B)m@(f~6#%-;msUnHrw124pm$UAeIwxZKfAjN# AiU0rr literal 0 HcmV?d00001 diff --git a/data/themes/flip_3t.png b/data/themes/flip_3t.png new file mode 100644 index 0000000000000000000000000000000000000000..4de9804623b7ea0e7d8304f776b87bc2a734976c GIT binary patch literal 1444 zcmV;V1zY-wP)t1f}@Ci83=YQt}## znTd)2z(kSPi1G?~6vgMuV}RuS{Px=2`_K0ee`l|K`aAAkwVm5_);@dx?%r$dwe~s3 z1ZH`BeEf@jY_+wu^|O4Zj{hg{!sPk+`Cs;Jhn<~WAO6>be;B+Gb||^My~WRp+Xn;~ zIB;@u!ZUub&!r~w$m_klyj0*c5O8&M#k2oLfd8zrQ~;Ha0?ieLWv7vV{Y@zP^6BzrWX9w-EqZIu#HQ0PXGVP*hZ;xt|{?p!u+h zWz7EmKGfFMLQ_){pskiERsqlgY-nhR+r`t8;OjMk3)ZdKM5dTNHe4Q^6>DWxgsNZ;rBY{=H>mV9D=;=T#uE;D3MM;n8Yd1pWb=-~0TUNSK;Ap{WFkw+kVZvbRwW%vVI1{f6;#i5m#mxGUwk8lG%t5{lE3ZbE) zP+VLreOhC_QdCUL?z|Z3tsSGIqflL4E!y8V^*lX2VRv^|bDcOt4CjRl3JQMONXs@UMyu z4GpBdV-w4X;d?=)HAv5jFj~mX&E>a;$PkR%agRhae#bn3VMZWkOfYF73m*Oe-QC^7 z@GL)|)O41NQSrJCjL~OjXQ8XB3ub0!q*h;9SqUX2C8Ro~q_apZV9L0r!_97XhXl{E z?Ck9Dzv>gGRnXVhM{*pmuc+V|S= zC7cKa(p$PXMcdliAS5J2cGYjzXJWVD>iQn!KjB0$JS!|LK31Us0000Eakt z5%>1a{&k9pGRHnnZ|mrAQk)nezDVF#F|$VR(?5$DHewxnq4cD7~ zcISGzj>v5v9v1A#xqCDzF)Dmx#GahHC04no{?>l-&Uu)(J^R>aj>8WH9^PH^kMrPx z=!&gTJIi+G&I?+6v0$p#(K*%A92V&Ax&JRbTR1FWdsbxme7}Q^``)a##kFDn(F5dm|1N+PDt*^fSUic_>_dVtRb<^4GiX0Q;e@8_#+aGJO-54(E-|)eY zE1)5O;n-CNMkhvzaAsBx)`S>d5e1QkLQ|*&hs29qo;_|FA3gT+^SHk8WV%a~v4F?T|$5{&)7Bcj#ZiGlU9avr|&3wIb`wl6NOjaxkaO$K;;^XC) zU%2}OZ|>OMJ-=T3e{~A$gF|~`b9UdY^HvdhU$DmGSo!W)&3Qg*_4DlaxCSxk+?rjv z`}Fn?KM(V-ul#rLt)0Z@r;Gp9&oloNcJGY-5B{~9tIQ;i*CqhdB!j1`pUXO@geCw^ CNs4+>rGG)6c2)rPqF(gd?h}Rpa`NU3VY0= zB7!1Bu9{GhMSI@n^)ePYRC)FFWl4vWqyT z(dDXe4aBsFF&3rakpQxbc+{#aOF#iKhk^oBfJ_2Rxta(ApqdB+UQViWAQPejRDetZ zOu3o}1E87+1D=|Q06Yw#Cc*@%0J#8lJIgykH4*RZek-+vnGhAA0%Q_k$lWoC^L!ASe1a%q10H}8&40yVoB>+!dSOB7$2m_+dfed&$2MWN`IZyzi zt^=76)kL@enfebcR~Htz{851zzJxeGKZpAIdbqf_5RWezGqfhs+1cp}Jn5?uN)uUJ zT!f{iCFxwngL@5lc6J604Gq4IKB*EeDk=)!j&w&yhp+IwUf6%> zLNy02EG)qC^0IV}zQzkp37?*xLSthiTwY%KnlJ_zE#a_yE{vsX1D@p73C%)!etsTS zR#qf)vlh#_y}ivmKR;W0!M|T9old)@dv$eX?LA19aA9F#@GcyS#jL`UzDj|*@Z8)S ztgfy~=VUdWV-B0h1o1EbsZ)FtgIyKYzurf5iH%-)>bed8<6sC$_;Oe&~@=KpPIOd93CFR@bEC1 zL3ejIR99D%bwLWmO$1A~rKJV%G+;`@Ij^Uuhaw40U(piA65QV2CMAb%i>`|c=X`8p z01plhU}R*3%mCMWxbDl>CIT>5x{r^KBn}l770}z;OVWg`vxtc#lS$aw*&*eIhX-Tn z78e(jbYbc&Vj}zd`!G5>O3tgjy&Z73CEpvXgkN7@UDu_4Jr4KxaG&ozG!{TC-QC?? z5{F#rW)JiyX~WprGr+yQJs2AsBj?oI-0Xh$`MtDXJm;5nykvVu00000NkvXXu0mjf DlXnSa literal 0 HcmV?d00001 diff --git a/data/themes/flip_5b.png b/data/themes/flip_5b.png new file mode 100644 index 0000000000000000000000000000000000000000..8d9312a12836b65aec6f6eb6aad1d60b32fb70e2 GIT binary patch literal 1490 zcmbtU`#aMM9RAMCozRfm?64N`xDBH^TEhuRqTKCr+QT_WnY++(f!F{yNftbWZzJ2O z)%6)}%UeuQQ1$!N%e}#SQh(f+Gc^zh1WM)f{o;*{oS7M-wY4Js9YPIUr2B;24B6rwjq%a;^MBGc|I{G(COg@Fqj$y0?1=% z!>es=cJTG5JCC$2iiu9jm+TkR`jTcOl0*en)vL9&#(`mBXOo;Q6ZesDI9Nb3+qxhJ z0*i!#U2P<0>Le1W?#$$X@}c2^a9aGv1&f8-+iR7Tl>v>&)YMe3 ze3#j=F~2{~pD&-J>+9?DQxhOksnjPdteGjjK2;%;_C(Lz++5KZ+lM^te>yZY6vzjK zhll$%uC=xnb?1o+zdd_);v+Xuw!gpM8ig{kFAp4e3?hY1T$;Q|rD9W3I%~}mU<3>X zP*G7aU1}~_>bd59OD>PKmO1Y4dCoHe^ufF71)>bE&sgH(Gn#)y4j&cW(^};G{{77k~7Me5(G^ot~bCL$$RtJEE8S79TSh zjFFKMZm6k`yq!31`p($fw;>ObM_#@JO-)UWn%_hga=92&OG|3U;=woDO)(bNK+e?w zv8bTH{q@YwPDUUO=bx0pOx*0sEvGNP=eR^iTLipsahjD`NfPDcaxqNbbyzEyR5%giK{?sU#)zV_clEkKrrK2f->oCoBXv;nH zhZj!<pf~;-M$ zy-t3O*J6LEpwXfqWNi8!P*l(SEqu_sOSv&)Q~%F~oz-5vY_$>Y+V~MtR#S09%2M%eNdq2k-mXk6A@e^4G`bZ4 literal 0 HcmV?d00001 diff --git a/data/themes/flip_5t.png b/data/themes/flip_5t.png new file mode 100644 index 0000000000000000000000000000000000000000..df439296c17c5c79b2ae7517333edc2e4fce22fd GIT binary patch literal 824 zcmV-81IPS{P)8_u>ve6O{T2>~f9QV$`pe+`G@DPS(@7uG?F|6~C(&qB_xNQVe-5~3 z-uJ`dK)5Fa;_$3D;kBFBLsB0~fP1nYfW&J?!r@rRLP zBoYav{J*H(Znx0;V2D6`=9>we()TXNKG3_}y^@zOh)6&Jf&ySULj(Y1hyZw;&a!~V z=`0I~Okog_Ap!t0L;yU7hy^@71T>w6z6W$F34MJV^$ZbEks$&AGDHA8hKL0`-icU1 zWQc%>3=sg3Ap+nrL@eOF`<;lsf#q^31vXtQc23? zvQ(>8$>;Of0UxY33ouGxx7+FBv=5fN-VFux^r8G@9A2uAl=AW z&Xky1QdX>SSPqr&7_mDzNykVUy{TrRh3aP>`_Pk1&v#9B*sRm-G{@dpQ!O%_-G}{3^oA^`W(31G2H=b817K@L&x~AXO z*DLlup)~S?(NIy5NhA_eEr>ooi}NqDm z*85r1P+N=kr%)ocYGwXNOsxIQIdy)19fjHf1EcbCay8Fg z@L8P7zJ-N-qML;&_R&)z594mISggQ`$DXBQy}fCn^mrLP!gww8N3v6C z11wB#%_;*sJ`M=2jC&Ni*{h6as^0-=NROjwqL)YBbHlo0>GWy0&eqkHmHtr`nP&Qy zo#-AiFd$&=g&(AVg2;>G$V$F_(oPgU#hdVwsv3hyScduidZMIX-*=+PB$m! z1*IV2``TVWnUP(qlA8B00|QGwaK1dq#>S?eC+Dfzk2Al-^}pKHfZ4zQMI`44$nH9U z(gwXB)D)i$@=5^meFI4(qv^<|4hGnY-BM%!r1BJ%s(ezJW;kVIZ5`zpf$HOU6_wZ3 z4e`kV0eT=H@LtX~X6>hR3r{Hngl$%`*@SY0YgmE|`}E@KD#zH1m67&|E5w4sE8NiX z8ami3l6zHweSMc>PpC2462qYF;;*2~Mw%3E-h08`|2dEXRlma{ekX>4j* z?6|JjS#Ut5eK0xpV}GGzs9PW``}voK{uM=v4ct9L-e|G z!Vix=mPU*nD7DcTtZ6zyCSMePpM5wqIe7+RaNwz&VOGqE(&FN`y7P~Ys3t$-tX;|11%oU2{NZ6a^4>(O`O?yoiKAmcDev#2f7$kylUHY2 zN|u(+JYccxa#1a}rZLU5y9EWzKKfisHgOzGq$4Q~%RMmT+++f$11OI23SI6AE{>EAC_s#`+nbN~d}&vD d+78tJ37$uGMt1RxCwE>1;O^{6sKSR_`xp2r0nq>e literal 0 HcmV?d00001 diff --git a/data/themes/flip_6t.png b/data/themes/flip_6t.png new file mode 100644 index 0000000000000000000000000000000000000000..3cc4061fcee219b45f1912c207d53eeb8e0d07e7 GIT binary patch literal 1569 zcmV++2HyFJP)~BaIVPN+1a}CYo(QyRW1H&z#j$P-^#}y z2L}iEF1g)6KmkW~c6Qj~ALV2~Gn6M@L8O{U-pfDlN}Twmc2=lwB`c z;+lmbo)Vrmco$)hz|O*;h<0_U!4ilf7D{4~G;|UGI}4q zOd=crWfI|lcd064ASXl#Py*y6z^N{i2nRr!L^$BdBq9JFOvog{2~q;&1t`l|`U%P; zqMzM&O?eA*LX-d{Ku!W2>MRDzB*H;Z_5=Cg$&NHXKRFWNWhi4HCqdbb;Q%N{A{_8! zIZFUMnS}*Flu3jGqKttY@MH`W08hq10T5+BkQ1UzBAfuNIQ50AZ*FeV*w`2?E-upY z@-o{#eE2|Lzka1JU%s%<A2C^+O zGLk|=LrHleORb4(_p`ONH66f#fdOi5ZKXGF-q2k?iHV7jD zsJ6D2PESwoBL^;@j0zA5AuTP9=I7_RoV?G+UG+_P5@~O5r~LeUQl9KKCl0!N6<*FlpDrgS=eK}&NnBVAoSvSh?Ck6ZnQ3oo zoZ*Pxn`}_N} zva&+B8)jx^*tWiomuwhM49Yn4oad2$B#o@BEa4sk5L$I+W+wUh`RTTg>P~-uKlSwV z(7Si<{pzZB#-6wce5!I92+*~RyE+$u3S7CNx2n}U$aFE*C z+I}ixm<(W1Q4uvXGzdFM)bkn}8!0+ETA0o2456<0`t@sSYHA{M`t=A`3tU}YWig58 z_W#jo)a*JsI#@B(Tm%4hCy|<(8e#Cfy}hZkvy3?E8nn2*JB4O|FRX3!DG5{~fja0(6%W>uQI5={Ux zw<|(|f`WcAv$3&3FJ8PLRCiE@x=8>L+sBU|f9Vk*uExj5Q*v@LAxt z5tSUo!Dr8&83o+c<74$%b#*nx#>TRxb0S4Gz_qnCVaLU71&DVo7=9)tB~e{nov=fz z28arbC^6-nF+xR2NeK%dYGVIw=d5}pf-L!v1mOb^c|_Al1pTmwCeNQgClrQxMD;C< z38aT8$j+Fx(<`b0KGaEb+=f_Dv9q(Ii=k?Ord)`w>&!GLAv~3rmut}YZ`XeTzLtU| T`*M`o00000NkvXXu0mjfk5$>U literal 0 HcmV?d00001 diff --git a/data/themes/flip_7b.png b/data/themes/flip_7b.png new file mode 100644 index 0000000000000000000000000000000000000000..9afc419821ea62281fe80f94eb40e7c19998ae9b GIT binary patch literal 1110 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 N0Nl;TmF0Yn^dDJ`AyfbW literal 0 HcmV?d00001 diff --git a/data/themes/flip_8t.png b/data/themes/flip_8t.png new file mode 100644 index 0000000000000000000000000000000000000000..718e484ec3f60b16f320d9d289ebeba0619f1e48 GIT binary patch literal 1719 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 FO#q#UmID9) literal 0 HcmV?d00001 diff --git a/data/themes/flip_amt.png b/data/themes/flip_amt.png new file mode 100644 index 0000000000000000000000000000000000000000..bc6a7154c143b96d5191c3f361cf5c5e0374710d GIT binary patch literal 1075 zcmV-31kC%1P)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOS` z2OcM}y;ZgV000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000AyNklf(1$G3k_$s}8|J zOEE%-f{;QGA>u^XxrP*@W-`XanOp5;_s+!poejI3)8%=e%!D7$dC&U>07L*DRaL(f z3Wcv0RaT~HnuS8)tE#GB0C)h10)Vckr>DQWy1HgxUtduwl|Yr3BuVgiJkWLhxUaA8 zvv7BJ_s8(?@L#!Hj&y2JcXv0^>GYq1VHp3szrTOt&5MhYW!URZw6hnj|LJJchMSu(u zh6pW85g-BnLVF-XgcC@B1jvIl#R=q1gcC@B6hnl2AT3OQ6ag|sIDt%IiW5kH3=!^u z6fI1E1jrDf7$USV0TLj^5MhYW!URYWAVY*9LJLy_NPrBH-y%e$MjsN7$1yuQTe0u> z_!!gE({;V0zrVj?kKgad_V#v7&s|+zMI;ib*r#cldluf^-L0x`Z*R}lX^>?ZnM|hY z{>R5h$gRt^q6-iwK26Rrd#jK@^L{)&h)1qtJD|s@_~KhiEkF z>J)}TA-ui4RqQJi3N^uYEktUyrQ0^nWHMDb;^5!_*=)A8Ht-iFh^m9YxqqCpi?*{-ZFE2NIcC1EgYiqVzsZ>HR7_`-Qc6MNzW>wFq z)`^0qX*Cgid3k})=YwGwW%nSj*9%2aFg`x+*wfkBiQC&-^z`&Jd=t?$4Kp({NF)+J z)CUFzaD9D^j*bohKt7+x*w~ouRxvd-g_Dz$itlKeg%1x8%fg$On1I*o1pthUj9_wd z(y`AljHcWIzG;1Z-B!zHv)JF?|L=1o5^)4k@ATCT@FV;E-?rcE?6!^P=H@UsIB2VX ze>ZjtkD;L<%+JsNJbB{klO$N002ovPDHLkV1kV6=qvyL literal 0 HcmV?d00001 diff --git a/data/themes/flip_b.png b/data/themes/flip_b.png new file mode 100644 index 0000000000000000000000000000000000000000..bb7c7e77daff8f0abe895b212947cc0c3e97d7a0 GIT binary patch literal 384 zcmeAS@N?(olHy`uVBq!ia0vp^0U*r51|<6gKdl8)jKx9jP7LeL$-D$|*pj^6T^Rm@ z;DWu&Cj&(|3p^r=85p>QL70(Y)*K0-AbW|YuPgg4PB~#SP4UdbEI?BjJY5_^DsH{K zb+EA6K)@mJVC!3@kSDidTBQq|KVB8xuy|qt`^gzH22cJ9-8++Yu_H0|`qqqMWu^uO zMkWylAjzcwBv}Q3Bol|ggJXSPd_GTXIBdXRa)^oJ!*2h-Vy}eP`a`V67 z2ao&N(>M+k$NlwV-0?gxsfCe=g(KiNlg(w`H1Pw*cN2OHFicf&U}WJCSik^M3AC0) z18Vtv)*IFJNjJjY|Fzt9El*?H)u`RPr#IF3UjEYi_^(m1obscIGsR`{AIB;^GMpCV w<#NZkc-_{xi+^gKU5#2l)6)IO-YG$G%iX=3*<FVdQ&MBb@0KSEYpa1{> literal 0 HcmV?d00001 diff --git a/data/themes/flip_base.png b/data/themes/flip_base.png new file mode 100644 index 0000000000000000000000000000000000000000..607fba927270a70be28b5149dc568fe59ddc4eb9 GIT binary patch literal 598 zcmeAS@N?(olHy`uVBq!ia0vp^0YJQfgAGW|ZhpN5NHG=%xjQkeJ16rJ$YD$Jc6VX; z4}uH!E}sk(;VkfoEM{Qf76xHPhFNnYfP(BLp1!W^H#h~^<#bGLDPI5zNtU=qlsM<- z=BDPAFgO>bCYGe8D3oWGWGJ|M`UZqI@`(ej+UV)x7*cWT?R7&xX-A2+hxx~XcN7@f zdVK5*C=v*ICJ-XHlR0<74uOs(g-;J16;swfJ56xXbTyCj)h+Iy-=|O4={3xo{O3lF z+4YO|v!7Sm%|Bm1`OemBb*i3`AL`V9TKNValUQbOVqqq6rll~*SBT!~trrMdJ$M7ZYCE0yy+*Tg>!;gRQ7 zaA=q>eW61_P@P9$K~INZ;UNZAFjuF6!TzH8g^r3w2F72Cy80LF1@%EH@)roRX*9SU z;ofrS6BDD9;C%K(3erP+7+bPG%Mmca8y&>*96< z$kk|IU}O?;0Fqol>ls)DfFu(KkYr@x5Lm###KI8(Q~+c%5>$g>)Pw&F6$du#a`ydn zAhDGHX@yOl=chACp}%ic*LxNne)K4>>b<_HXVrUu&u^Y}MV0?&ZFVdQ&MBb@06tIBWdHyG literal 0 HcmV?d00001 diff --git a/data/themes/flip_base_shad.png b/data/themes/flip_base_shad.png new file mode 100644 index 0000000000000000000000000000000000000000..056997776a4b3f1d7bdf20f688063576aa88856e GIT binary patch literal 826 zcmeAS@N?(olHy`uVBq!ia0vp^5kS0xgAGWguxsi9DaPU;cPEB*=VV?2Ic!PZ?k)`f zL2$v|<&%LToCO|{#S9GG!XV7ZFl&wkP>{XE)7O>#2B#pqy!f0`zqbN~BuiW)N}Tg^ zb5rw57@Uhz6H8K46v{J8G8EiBeFMT9`NSC*n5KHVIEGZ*dVBp~-mL%uhl|Uq3VPOfZc5I-Oi!Qh=BH-GMooef@AC|nq%x~DDvU*V#v-n1_YmL>? zH-ZcA#|n3|d>0X}$z(R?->MH3Kba-4eZS4eNM`>7YGp;7S1OPHi#-~(L$KW7lkbeR zNsGF_oc_i)Z>N}D>zx~>=U3~n=G_zc^u=5H?{eLI{3>sO@ z8d=3|u!uz@2!m0hZvtElCJYio5=K{wYyz56WD`I(Au9#ihiodcQZg;u)%e=NY~L>a z9gb@saoFtBvYaa%!<_y=|mMKD7%3@&PA?uH+vo9@eM2qlYH_y zWg2)t@XlbAH29kML-Czh1;=jZh-;b!#s`n@D3sfwf57OS@Xuea3ufNo{b2m2@1=hI zrH#$oKmKH~VO*Uu%Q&|_Iy7+$vs~lv4b`9jWHqN6t_)5PylmZn{!!fec5k0IitC<# zi;nnq?sp-dNMQ{B-xH~GR=r;OVDZW`Z1=wJ|G)9Y-}@i9u4*?+ZmfEL6PSt_JYD@< J);T3K0RUR;Mh^f0 literal 0 HcmV?d00001 diff --git a/data/themes/flip_pmb.png b/data/themes/flip_pmb.png new file mode 100644 index 0000000000000000000000000000000000000000..de14fa5ee5abfb3d35e82a57c00a056e7fc96259 GIT binary patch literal 709 zcmeAS@N?(olHy`uVBq!ia0vp^0U*r51|<6gKdl8)jKx9jP7LeL$-D$|*pj^6T^Rm@ z;DWu&Cj&(|3p^r=85p>QL70(Y)*K0-AbW|YuPgfvP9b(hwxwM8SAas2C9V-A&iT2y zsd*&~&PAz-C8;S2<(VZJ3hti10pX2&;tUK-3Z5>GAr-gYUbD@96~J)pC z;et%NB;K*M`|(+ITCuoj?3=K0-fcvQVdttyf7b z|FibrehnKVc;@;&PuO!e&w0`khi`j6y>_n4cZ13@Nrwn?k8TKPx#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOS` z2Ou(?rK%tR000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000AbNklBRv( zNF+@N2azBQ(#V)lCasyhZFYCs>5sAK=KD z(sfE&{{;C8$5`1trk6vfZN>FMd0 zhK7c34-XHdlY`33%W-~w{#AH-db)mjdHKZ7%e@nwPUnrF>$8!!Y0=274kv0wln~21pa3iExAokN_!~2u*||On?*t(nM$?9ASz8 z39x|9K$-|UkN^pg7io$e$d?E^kN_!~2+u%{Fac5oNE2ZP(uFB@AOX@ucm`4&VFDyT zng~S`;Rq8T0a7#(ng~aj04V~biO@ti!W01#AWh`IFcDX_$yHTVId4!=Q2|jDQCnLJ zpU;Pmjt=zn^q{1q2ojg6MM8yg$8_uJp!$KKvv+Vw~zf@m~aco*r? z(o#%LPFm({Z*S*ZH`RGJJ3E^;Kh;{MGxNi|L^?Y=E!VHFuXCt*@^`mSt1? z;^G3Eo13Qi;NW0kyhN(2t8HIc|JLZ}s413ACJ_th5lUVD2xT3cHSV}y5hb}ZLxYHISTJ2p0Eip63v ztgNj3`YcIO$_}^NeQyRZ9*<*sdfGC_@Av0bySKL&Ua!{_|NU*8$~@}o>d@EM_pt%0 zs)}$pjPCAk93355=JxmZ=e38+q@K00001b5ch_0Itp) z=>Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOS_ z1|$;E(26wx000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}0008JZzzYeSPZvl2>hj02;Yy~Rog;0d&9>j^9oX6v_xy1Y2^+>E!TGR5qsdHC&{@lGv^Oy5MnxI@r0#TZ$nY-m22=}T6krJj4 zysixbU1?+>0i=Yd*9V20vb6A?hk~!t$XNo> zBHbDgQ3;~(9ga zGJfw2bjHswN?S^JhcqTvH);xS?JE?ubE#?I3{0x-Hn&tF+6VqA5OISbIsh{h=?x`Z zYTrwH2PMXpu9v<$$2RT0K`334HsHi_=eQE-gvDCq3+R2V7Q`Bf*7N{NQ5Zdd1AviI zHroW?Kp)r^M9wM^0$Bkd6X_iiX_}z~3=*CRq&+yrG0? z8%da^tVGz2sRxm1ObdAMEqw>zgs-mjfbZ5mEf3!4F~P5X3xqrwFGJ(a)Lzz&8N@e8>*39l=`~F7F( z_mAz5-WT5c?uC%Dd;oay7#)I2hgD>Gix~Oev#`Ho7RJ&&czoVHJ~LLp1i20#xPc5j sW8j#|m%B{K(no;O2c9<&7+klsPtxW(p{{dE$^ZZW07*qoM6N<$f+{zVod5s; literal 0 HcmV?d00001 diff --git a/data/themes/flip_t.png b/data/themes/flip_t.png new file mode 100644 index 0000000000000000000000000000000000000000..74ed50d91dd8767d6b5b518d54bf7b0e5318293b GIT binary patch literal 442 zcmeAS@N?(olHy`uVBq!ia0vp^0U*r51|<6gKdl8)jKx9jP7LeL$-D$|*pj^6T^Rm@ z;DWu&Cj&(|3p^r=85p>QL70(Y)*K0-AbW|YuPgg4PB~#So|s&5XP_xoo-U3d6}R5r z+33scD8lxz{<^e90ee|s07r|6BS)))zXLm;UPPs*j8aSOrYDE*ixeDuv3G9t%Mw-h zs`vb!^TJkN)%!8g@R)@RU%cnM=0hCx^9N^-k(8y9Xv5m7t*szhs$z@I> zP@#Z^lG=wyUxOb?##}D{c+P>z^@#5gu4W+Z;*!wHsS@C#S8}841kb z1$&oI28wVNctjR6FmMZlFeAgPITAoY_7YEDSN0p6Oe}(i6V{2o0}4r&xJHyX=jZ08 z=9Mrw7o{eaq^2m8XO?6rxO@5rgg5eu1Fhonba4#vIDU4TV_u5^kL!HrBdffRtaE>m zV(WkYaA=yL&?A=3op1AIa2aw6X)HagHfjH#{rlg#bnLdCsn2A0{f=srn(_7m6KjUH;H}u6xJYm0gc^>6Yss_IkQ(P4R)vAxe{+mhI-t5D|=J?b2O% zrHq+FafyV}iC-Mj&!;^5$lc;PM{eSE>y;(hBAznXNNd!3WC z@lJ`O@Y;C?PpADW+kWlU*1u1<%WG=?{g`NJS-d;p_G_KPA5T~Ad8>86{oV1`>;??% VQ9s!CJ^}_EgQu&X%Q~loCIGkFun7PF literal 0 HcmV?d00001 diff --git a/data/themes/frame_2.png b/data/themes/frame_2.png new file mode 100644 index 0000000000000000000000000000000000000000..0fef1e9a9b7eae8d8c4bfe166caabc6eb173dced GIT binary patch literal 676 zcmV;V0$crwP)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOS$ z1Qr_vR7(E<000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}00061NklB&SeV0Pq5E3o8G!0nflo1H``hJzdw#Af%WQ zz}tofuZBek35f&}*&fjdt)UP|@r~27A?23y^8lgQdoBYthE%@Jt<1uw$au0JudR>~;aOP4_Sm96w{-B6>@?SqI%t+$@D*7lv0O#?GxFcT3@q ziO47e9bL}cRfER@&_ja*;2#DU-c%0}4}b&U5dq{b4F2ARA`j)lS(hucZv3ae3(~$K}bE-@?zYpL8kWP_~&{xg)IiZ zwis9uYxL(9gWQy!9K|=3f)$)t(Dwo~88Bj_H-!_3h)67Qs<|K@23CW~se!a?jC*bD zb>YHBZegP)4YVQLMVllRlV=Bm+4h^FS)vQy#~xb%pO}*XG0H~1k4K(UOlEIb(lUNe z@sXKGVPQV7u}3GFVLqUlF}>y5W*JJWxNM(mnL=~9R(dCAE_?x~RL1#H=9&Kh0000< KMNUMnLSTXv(h@)b literal 0 HcmV?d00001 diff --git a/data/themes/group_index.png b/data/themes/group_index.png new file mode 100644 index 0000000000000000000000000000000000000000..7df068040c384ed4f834bdd106e289469634b7bd GIT binary patch literal 217 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 WsQ5TT?+@J&2WY71Dwil)h5ipb`gn-| literal 0 HcmV?d00001 diff --git a/data/themes/hoversel_entry_bg.png b/data/themes/hoversel_entry_bg.png new file mode 100644 index 0000000000000000000000000000000000000000..ec8b31d31af7730419687fe877202eb01bbe4457 GIT binary patch literal 782 zcmV+p1M&QcP)Px#24YJ`L;wH)0002_L%V+f000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOb< z2?{Zm9U?OT000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}0007MNklVAE1?I?r<-~jLj;5UF@5x`FXp8&i9_(FK? zVuqlBNKlc1MkU1<#KxFuOnp2F9{~Pzy!Y_~z!~MGm5!TntRyx%2Ax|GUU{GQefR%J z>8TPKeNeIWk)vHD@|G={@m@=aqKKvL1SoR1N$D1`UK)gKctF4`Xm!HtA4DOX$&ZSS zFg~CKIV=>MVr>pdi*TKA%Pb)G5ASkAHnLEhB4vV)7O~o+I^@k`OF*J7lj-_Zmtmrh zb|K5Yie&vC`-RX2q~0p^#$9a01Y5t}q_AfeYK~2c5T4;K10(WD`ui@#mDo-qs&n70 zh`oqsC2O4DYG7D{Cnuh)W&)ncfY)if$d3svSr%deOkShEEs$rCj|%WeGx<9V%Yf>D ziSHNWn{=ON1Y|?N=^$w)Rt3z+4>J2gm(m)riuUN3iMZ9mun_3u+k$PF{7!Slwot@% zB4Cg_1WyTAwE}maZL;*X<^YYpMgEv%;bx&G>zS}9p!9j8INfR{z>EHAkUy;GYX%@5 z4i}zh^4zt8VLeNL7Vo)WAy>d^2AbjF7g{r2S;+E#GAwjDQL70(Y)*K0-AbW|YuPgfvE>SiixtTk5y#WeImbgZgIOpf) zrskC}I2WZRmZYXAlxLP?D7bt2281{Ai8C-T9rko_45_&FcFya(*$yHt>^$3Y!uOth z`P)7|d#mr#88>DuwXZRYozS>dRwCr=M1ez3KBbnO+vItSdqs%WRIk!>Rl)C*PxRNW zUlsk_OuKpUzEB7K7%7>PEFa{q-3(;6@!`9!nsQC~!J&8hj8DpJ)%LKjVVF`DQkI{{ z!_z0+usPP9^M$)L`-ZY}ZzYSpXD#z*=quYeIK@ z^2423VO7yT&Ni0DZa!en#>*hBbX@9y;)}M~&km>-KAFxaKYMZUy|Y#G&Tuxc7CsTb z#yNx0{kgNYbi^?gmk-CJO4MY+pIcpJp31A&RiSL}&1V_FH--7B0}|Dcm59WH$^Bm) z|MXrGkIM%GH$(A04aUO};jS`wxTb5crX9GbnKYkSn*nHltri!9pG)5+|07EtADr}X z66a5r2dn2^|Mn|_UoO2#lwls@AGQxk-?uT?O}41Jwe!IKhKmW@*1`W07O0yTDl9Qum zule@-Z#mnIyzRfmVvH>3ooNhR(~#&iRWgSscx80ah0QMRPNr`Q6Y}PtVTr$a@Y#vo zTco^JJUcQmUnQhdX778R04LMF$NyTiHkL}fpCt9@LVWVQ-CKZW%WANnYAjkH1EnmA z*}WXLZh&!Nl8jdmWhHLi@G(hYre$l|i+kP^jtZ(KC@=Jq`RV2~^-N*C(^QL3y)9Z3 zA3tn)C2pPn=BweqhwmPq+rc9B|3Q`0*T+X>&NI|KY;0NepE1rb*Jz7F@oCHRAp#b0 z7bXYzR!uX1xNWvwg7LRa#})IqFRZjYb#0D~#sag2y?0u|ZYvxwJX0*VDrlwL+WmUn W8#sKv-qHo8c?M5cKbLh*2~7Zuf^)$D literal 0 HcmV?d00001 diff --git a/data/themes/icon_arrow_down.png b/data/themes/icon_arrow_down.png new file mode 100644 index 0000000000000000000000000000000000000000..899373f6e29a619caa7978d15bdf384c683cfda6 GIT binary patch literal 866 zcmV-o1D*VdP)Px#24YJ`L;&0X+yLCZuzQRE000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOV~ z2Q?krwlf3(000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}0008LNkl3~&3NtVW$fRN_t{^LM3rXd|tSY(4BC?XKASS^9L1fIJ#$0$P(Xx-y z^l+fRx2mhF=nI;sPSZ5?gHlQCz;mDg zG{)oc*CgWQa=AA^8yEn8W>)8;EAY-2XD*l98;wR^l7yGf=lAYi(w-~L3-1c}4UB+6 zKA(S^AiQ^G)s2n8l^3M#CXzBYksMG3UIDwq;qcQc;}r^pec&7L1LzpU3opR*6YfM4 zpbNBs1M>!}iuVCHFrT$+KKrHZGJeVr>GaG>tN}Z~?qD$ZxJr2I>+4gz>B<|~e!k4} zq_Ogde(~mcRP#ja_xnqYSS%KO-Bo1cwqxt5l>D|0!3^z8j<5g0T>BlTzF9dS`m+rj~7DR+}w-}FG|2r5aY&+ z8qkV(baXTq;?~wy?09hi27>4cUR;1y#KXfwE8_O{wljEf0{TL94KHp$8{+F$t954r zqS+F7n~4Eu@LU0W2(bdxfucFy=Vr{T%k8X6?07B# z&LU=jEH|@>FU_%Ez>wQn6({gq1Du}EbUJp8+xf*yv+AsaJ_5XZPP2pU(?M@s!gCeS s>)ftUN-3q3Qc5YMlu}A5rIhm5f24|j#J4cudH?_b07*qoM6N<$f-jMU%>V!Z literal 0 HcmV?d00001 diff --git a/data/themes/icon_arrow_down_left.png b/data/themes/icon_arrow_down_left.png new file mode 100644 index 0000000000000000000000000000000000000000..2f1d2ed5116379ad336b18942c6ae6ed2a31b05b GIT binary patch literal 1992 zcmV;(2RHbMP)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2igh} z5*8tVg22lF000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000LgNkl>4u)Tw({b<&w==0Vhm5e!IzIILmzrD2)f_0|1HT$qLZ6P7{dd05zg zVIB-P1SR^?vZ8`7zU09W5JxkKYp-2hRp+t~p3c_v^riZeiak?bD7w1qa=JeKyPaQE z1EorpD)rlyQSf+FFXYz(kQV%7S+{Q8n!j`B&KUrv{*07%obQKngCJPAckkX`-oAbN zuSTQsB>->MA<_cJF`Lb1<<+ZKRmRw#FJ8R(_pPn1F95i+46!JH1ONk2IXE~7g%F18 zx_??*Tl?GQ=H?dwoLPlfC_u)Tdw6*00x*9xG zAP9o5Ha0fCSzcbQX?UMJ#3Ey$;+!kfG>H(R69$oe6+*zWto28a9(}jDx%vB9u*9Nc zAT&AE4R2Q6xhQ}~F07Oygbu;tOLP0S3(FSr97gg!(mU&LQE{ug%tpprb&F? zuV!n(ZfoqUODW+v&ia!lPrhGXUjF=3gjl2tD@v()@#00~x-J1g`nm5cK`g3_A$lxA zDeVbtRv{Ku#sGklQi`put^Fv9l*&+=Wr&5kFaUDt(j~8xji+FVC!U=PoysxB=;h0o zL(8)ILK+3)r%>Vy9kkVIO*DY#c?2KZ_j3Twudc5CuF+_GD}?x28Ivt%27T6%VHjvO zn?F2${P-U?Zru1cfHnZpYPHlf0ePM`nFV^D2c^{5OSks-_fyU}y33e6mY97nrR-U3 zd!9!o`M%j@7`)sr?EC&y02+ot>-GAA{$eDL>-O4~ec!9t_I-b1h`#SnHwIQJm5JR! z2%+A+dzW&~M~Z)gVq(7rM5R(0J0^~Dt#s5APw2vOdwcsJj$=7!CNju%`&nZzcdk?_ zBU|FAhB9&%4uW8!tiQ3bF=yL09X1mg2CjR1KZrpPkmJ0zvC5br2*$EN#u!;zT5>3* zx!rWoetEk%K@beJ#BmK{>^d+E!;z2SoQsDKA09+eguFA6VV~vg;)G#Hrg<$>DWtqQPHXNw)n>x{{QTgFHzBlMuh$&MA%k3amLN{O8#6yY-`4^OA+T-R$OA5K5;->(^2E!Nx5^O9cj+FeE$6T`y@$nl_YsvTqg;! z=%=&P-rioM+gWN-h=XEXQ8BSlfRs{Nuh&0w9H;M0WE$Cd+$pXCiqa=4oaeXLc_7*%)JeeLb)&E7wdU55&BQ=C~3|(f5UM z_Uu`YF*cHg<$;(dVdU9wRER~FF{;sM97IusJk5k6V`4u`ynFZVH2`)$R)s!b2|#ep z(@|V(T!_8m-=L;!KX<-*_3GCT9z3{;j}HfslK|NHR+2F$Zr;3Eb6ppN5Mo&tbaNGq zF*uF`N+~F%ux%TrX@U>}(==h*HV7dw3@*At}_IOj>4rm>V#3L!Y> zye))Cl~PF4H0GSgdcTx&-j-5wDW%lg674NXnx<{XasIHny872fqp^Y>|88XkS)c@v za?byI`}XboYin!&+}qp3g$oxxmr}}|ot?L*PoEA>ojMi1eED)ej$^U1vT~}~Y_@lI zcMr~;J6EezD$dT%&X2Zjv-9WAfA;3ho2F%1sbyIv03=D08iqkF%VKdHrvQ{~+m=#F zq-iQBrG{l$MifN}Aq1}LT1k=!rIavDlTk`Z9LFi8l(?>INGaQvWwmRy8V|$pgHp=r zWr0OKkV64j00ICD`qjY4e`^u|iGFVah_%()8hoOUHS{*3-=_e$-jC>QopBOvJ=`j-{m~ztw7~_wV0}#l=O#Fbwkg^=oe1HWn8b>EYpF{Nclg*2>CC+xPwdJbU)+ zCwzSVhMxpLlDRlXFHHYmmhI1I$9CnOJi4ACk-~y4LfaJA3hij;CGw4LVL~U_!sj zlXBr+N|h>As#K{`rAn15RjO2}Ql(1$ a2K7JFw^zWSWzDnz0000Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2igh} z5*#E72i(p8000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000HdNkl@qAF5p2nt*fDk>cK4}cpI z*Mvj)Ax<2SK%BTl;@|^qk;*ky4n>?&615>wTOr5ZU(*A-?qcj#E%AESeP7A)Tfg;s z{n5M8>mEEbEY zfIBM-Y=D;lkO8m*K(SOReY~)+aO&W}gI}1Yxil~^@ZICbk6#0D+U>?7#_;+96pO{; zo~u`{P9Hve_;X#?``kRoTh(f{?U7i< z&20e;UAuPe#N6E6mzHHAV0mC>uGMNk>AL>?)2B~20NDTMAkq}x{QUf>GiT16ux%Se zREGxuLI?t2r&6i5yKdA0{v$j9VCMHA0wBk6D9jU$CA=Us|DBoHvqCql>$`|6yhext z7xs@6iVJITg%q?~U@LGT*W_EO4kM)9Tr{MW64A*sITZwcOp69~SOJibpUpQ2Ftz4Lh5OCqx z1d%Af^T&3rRtu&vkp~zhco0G)gDxF)7w#Cm79fMbDC&uH)Zl@Lh?z|+9>=n@lE6(=q~n8GnX%4 zo|>7NnT=Y&Xx5=hM4U>c{1&&4xv++}o$=Ls_wJoMe*E~HZQH(!_zQ3R*ME9vT)+0v zTQ!?|Z@<7b>zx}y-dxlDT6Cz2R4QenLk*Vx3AzBRa=HA~=;-Lz03fA=<2Wp(Bq0QB z+a@A{rfG0pmt5E7L?QuZhU>ZzLXeaauImyrL(??)H+(crBO-$1I7CE{Qr5qxX&Q(K zwr!IT!k;654geg-VIc&Wrs+S<1tEk0;0hsL?cTlHL&0|V*%_wTQiN+tc+v12=zmXFMdxix)3` zfAHYJ>r0m|l?=ns?%cVva^S#$?4d)42A(~8w*LJ2^EVeRTo~Tk+OlulxbbRkZf?iX zqeqKUN(do1nM~TcuA7eItQ=X3s?lrm=+M$VfH9>XvUBPXTwkDtru z^Yytxp^)_gpY+bZqm>A?cyAo@2mUs1!}$jv^XE=l-M=mM=s)b&j$>c-Px#24YJ`L;&0X+yLCZuzQRE000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOV~ z2Q?}B0>`lc000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}0008mNkl41`>bPwZFa=BAcl&a34W$Q}Yc4q{Ewl%vSl(AzQV%=^H&MNGM%K*q z|3M_gB9R{6AvO#GXlQ6?XlQ5>CujU0$Pn%L-ePeO;05=S1Mo&1IRFuWo%pI8(XkBA z0gwl92cQr|(NcV$7q8_A@I2lFfMOIyKgDYW0B_S;ZH|R_ZWxAN;y6Ye$H#yU0iMV6 z!Z3V(an3yemR5nxCcNEl_gPeTJoz;LSvof1ow&!;0GSPVK@cRBcaveJ<88Owb9kw~ z*L6(C%le|2sd$^sCbMO0T7ijpx?CJH4R5_(Yf+vF1t#L@c9F~!ywz%@Re3rWn24wA zGGV&oEtg9z%hR#IL_FQ!A~0R?7K??}<>>_Y3U5B28-b_85>CW3>BBkG32!!=8B<=? z1t#Lbz+pPzO{Y`i%FC+2L_8QgEK9t}WMXW2w=OUd4;Bo|0&hGX8(-e70AJyaMk8zR z(q6)ec(80(ig-Ek`yT*!zVBOA-Yp7b*zb%g`o3>nd1)4SymSl0;qckU^3pEwu*vZb zmQU*M1B=Dt<6)~=7Kf>TF@O-j3c%QP-A`2Db$Ahg0KgQ$F96?N*L|V_ubZ7Ha0uWB zfN!4XaVqfg3S)t|I8+GWtLJ%~3cP+P|AAO4l{f)PB9_Z#PD@w;A{8i!SgBMv6{rA_ z3Y0{wR;!!}RDehYN+Q;3HBJR8K%@dC5$p9jrveoqQh}0)jYfkLpd@0m+2pi@6(CZ9 zl8CKVi&KFL5UD^(#CE&QsXzsYRG=hcr_c>aEF`Up^Z2rbQj7YGdvjk@^_T>Px#24YJ`L;&0X+yLCZuzQRE000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOV~ z2Q@k8wb#`E000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}0009CNkl#5HjH;0ZnC4xIzt(g<0J;-s0X zPJdDfF^6V&yn-1~YKV!6iHV63oI-qaFJC*mzFB$0o{{~cmH=#jHJg&O|6pb+$W0=imAAo9T5PcfB25e^! z&StZFAPos(;&JT)uRs|BJ+16}p| zeen>*8t5V&qG$tM^?E(A5LEy)#?b9{MM4zc!r4fKsK!87olZv-L{$d5NP@Vw3Ilzl z-EP;5#o}B0v zm75q0K!B&Gr~1y$&PpK$(Zb6RSJ}=%8R+u(_*mcF-E}5*t%>+BF*pOW5LpZ~ZTl1@ zNCRCOjmCYYQmFxB7PE=}{QEFi12fsOq7j*&;ka))Yqj%rg*Ow;rZ_yl|b8bIF~7=ML-m%Y8cJK!Vm8TeuEMqK;G7XDTC_xG3K zb>pp^aCku&cyMr#8$9&}<_%A^frp2Oxx-UypcHs24LmwJ5(7`2fzsfqGVu8LSR6bx z21HVN*3O&h4&Bwyj1|4 zI0LV*uipV*SxgKB0naBu!(t*}VBy^WZ5FdCZel<^Jn%C!R{&nIm<%lgC40OFG+E55 z1Od+{K(_(oYhcrY8UiD0W)Sdv0n9>tZVOODKwE&uO=$n~4=E-lCgyMQ6B&~|baYFM Q#sB~S07*qoM6N<$f^$@h761SM literal 0 HcmV?d00001 diff --git a/data/themes/icon_arrow_up.png b/data/themes/icon_arrow_up.png new file mode 100644 index 0000000000000000000000000000000000000000..46584db71e53368550df4cb20bf0ed370df4ab2e GIT binary patch literal 776 zcmeAS@N?(olHy`uVBq!ia0vp^0U*r51|<6gKdl8)jKx9jP7LeL$-D$|*pj^6T^R0w z;JyvjJwOr80*}aI1_o|n5N2eUHAey{$X?><>&kwEOO)MIU@5!*PN0xviEBiObAE1a zYF-J0b5UwyNotBhd1gt5g1e`0KzJjcI0FMyvZsq|T3IY=D)_L{<&}OF~V5rqAwI;?kg>tO<+?7p8yF ze0@6dQ&YP3q8lyc7BX&uVr#-yUsLe9_aVnwMEb+G-+y0B6TO+ip_9YJM#ss*2l?Kzneq+xS8!C;3}U`M(9qL^lLxqj~6 zbSb{}iGp*vE7GQ15oXw~Q^ByH|LWD_{|cT7{^T*KuxHq@@BM!_&d)aQ)f-eB>?`D> zmM>zmVvu9JQgeU)!XuUQt}}07|FDWNG~~d0hE)tz48JPm7pLF-ut~yral(BD8OAk? zK8$BfAKdR}(C-bf&HOqyE+af)Prtxn;~oC(;@&Ol9~RHkyXV8*w&IKJ`%wS+cAbm& z9P>DMe%JbQZly0x)lPMrZ2qDzhLR>Ey6@DlityuYx_EgbFikRey85}Sb4q9e01DDh AdH?_b literal 0 HcmV?d00001 diff --git a/data/themes/icon_arrow_up_left.png b/data/themes/icon_arrow_up_left.png new file mode 100644 index 0000000000000000000000000000000000000000..711bef8760ca0cf93967e2fc77cc335814b07daf GIT binary patch literal 1695 zcmV;Q24MM#P)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2igh} z5*Z`u6ul?_000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000I0Nklfjz6o%h({S}iB$PfZWj06fFRToIWCbL74SP`NAh>9hv{(!Ej%0K9aHLFUr zWs~kAk+h72#DX$JL_tCcG*QOHB7Ro=Jo5>$7g3} zPY@9cAt0qB0NKdMhzP?lBO>xVk9b$a%6 zot&I(RVtO{*|TT2A3uKl+k*!Wwsg2KDYu;jaPHy5hj;JXx${k{)dB$czK832S3Ohg1AwJa-5lH}*7PoI7_KR>^w!vd+}c-Gq58p1FHGcyq(3`0^7 z5JeGo&l{X138m@Yki$_F?d>O}gzx*u)xJ5k1K0O|ermsbz13>{(r7e(oS&b6w||Tl zMFtUdM~}_S%zWXxF4TAGIN@IFyFcF7Rs_5-41cZH>-TH5+A|eE^a0G5EX%TfFDPH{ z)%H2z?d<6v$2tM# zXK0;1eR|xs?SbI+FYT3|7HWY)2mo-Vr>7@!fP(Nr+*Zx5eJXu~|zQ3}vviV=&6&^&?g}CR> zpRaUA;X&Z(a9bS!x#J?Nv9Ylc%d!S`Tix)A1V}24VF2w$qp|*}H0H1trUPE#V_-fP z_B_uPLLjfSlqFzj9|Khy<6gLMVX9Xeb68Maf>h6dvADSS?H~bTSY{$}V`C#o)AUH- z>2O<}E(`$4`ucive;PB0i|T@>D~<6kUAi>wx^C&==_+TD5JL1yVGg@ZC%nQfP*qgh zuU@@cmr|A z-6sr^eA+dL+v znd3O4qoboEaU2ib+;*5PkQFHMJkL=nO)1@0=NJe8(aV=F*SkHTS~hrvC(_FL{A#s2 zBBhMWIOb_hqyg}$Q>TRQ`<89nZm0DPLt&r{7RXy$TkR~%q9jS;vcoGn3TFV)ot>S( zHa9olyRPf17i*rCA=>H|0q}$nQvklK*Xut@DS2ya>yL{UFP>93(uV%`mxtB@89X7UlCDMtJVI*?t8ddS>3j1 pml0|qGu|D|O(TQD$jC^e{szqV6soFu_%;9l002ovPDHLkV1kzDFkS!v literal 0 HcmV?d00001 diff --git a/data/themes/icon_arrow_up_right.png b/data/themes/icon_arrow_up_right.png new file mode 100644 index 0000000000000000000000000000000000000000..7a9f495fc72eb31b31e7c7c5d90beb64d2b3427c GIT binary patch literal 2028 zcmV-P)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2igh} z5*q;yLY__l000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000L^Nkl9n#)Cb6%zLI^^~-_oWIXtlUEI^Q`zu*p zT~%GK{>-oH_p9z|AX21Aks?Kk6e&`qNRc8%iWDhQq)3q>MT!(DQlv*P%^a%~ez{EGn=c!ambar-%QmMq_@wiB*)2eBjs^d5!oldLq zc$`-%6_H3J_~786D3{AZQ52rZWCUYOt=H?kudh!{CX=FAEOK4f)l4QMY};0C+g68$ zhD2v)Coh-FYFAg6IxsLGs?{ndBK5$51430*wN|U~-rinOtJPEhLen&E7=|DsZknc= zN~P3fGRX^tf-*ET#LDGzpa9hk;AsG?`T6;zcfMMy)#3mW^?E%Iz|3Z|A4w@~0Qo|p z(An13*6zCQG60yS*_+Sjs{l&5T&`Q!bq&ChX_^8+Po+{R0H|lP*Ma(F#j97Z4#(qh#9}cw7K>R2 z4<58eM@L@+uv;~R82|yG{no8pzdUyA*zYt=>n9==0Aq~Vj4|QWbpS9$Q5XOak*jH% z0f2N}H;AZUS=O?y>w}7-#7xutH|IR2Y1)8o+e@zNmSVA(K}2L()*B&2LRHnIWm#DO zPAnEPT-U8stJQx1Kv!4S&rQ>uQxrwjG;PRnoE6hFzXc!}W2C&(o7vgf&rh5<@xtq0 zO91Ksx{e+_nz?@c`fo=@Mt-B~dXh25@Qxygh#J6=q9}eb08m3+YA7J@M|iKEpZ3}Y z08$i%5fO-pIOl%ZntILskWwzr&dz>%{P^)d1E>cvCo1azBmi=DcD8=@?Ab4$Jb5yq zX&PgU!N1=|3VzzVApr1i97MDxy-~fU^ncF*zy~R%e6Jp3j5VeKD5hy@y}iBaHk{Os zIT7EpaR6;IGczmw{ryflolXlOVryvskK=~v?bd7faeinXan9Q>UcC6l%a<>60Nfxf zkZ)2Z0Z^$_qUq`B6~i!iCX-2NnikvY=7NIQJbG-~UdUuJ)A#P(`v!p3N`TV)=MDf_ zDwP}`qG1?mUDrcniH+w{%KGcquO}Wqe*DTbP20PVKIdz_*Ic(v8-$)iqn?HD3n+nx=8j0I1afn<4t0qOd|FBBfTVS=(5q1_p3lO9T)K zOKfh#3v-m9;BDoFo99IGLIcNNg-lFLe4kFI`N+t~CtjS^O2X@d9un*zTSYo3r%UZN;`>%KJ-uwOAE@#jZa>HnhZIF=8yy|JUa3@e#Y!Y>5E#>iOvXAoIs)4x!x5Zz#1b1pnx?r}EEfNA=gysfh4p!0=q#}jq8APZ zy2UMMfI9}!TZs%TE-qGjdU|Meb#>1I+^IQ{T-RmO)6>hVtE+M^Ti}jClv2{<8NR6%&fNSH4sVbWRjP$Wy0I{i?may}JRT+$~!>S{-aFGcz;GgM)+W$jHbi{M&VyRTJpFe-Tc<9g}G7KZlImg`G-1y|=`K|H%h^~&(V4S`~<)+0Gzsg z`}QB+zI{ulPoF*tARclD85)S)0EPkl6u`$*Q&YdcdGqGays|*{O0!)KQ3Vk5EKYdy zUZG)_Qv`79{&Nqc|9yz>sbx?dz#f3;{}BTG$Yw8!MF=A8FZ~Dgh#L~2aFrwg0000< KMNUMnLSTZ)g1PSi literal 0 HcmV?d00001 diff --git a/data/themes/icon_chat.png b/data/themes/icon_chat.png new file mode 100644 index 0000000000000000000000000000000000000000..1fe8f63140206411ad1e23c26194d6a2b0cccde0 GIT binary patch literal 3221 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 Hu0mjf^}_?B literal 0 HcmV?d00001 diff --git a/data/themes/icon_clock.png b/data/themes/icon_clock.png new file mode 100644 index 0000000000000000000000000000000000000000..c89ae17dde0e6f1055ebec2b3d6f90646d2544cd GIT binary patch literal 4190 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 Hu0mjfa?vK$ literal 0 HcmV?d00001 diff --git a/data/themes/icon_delete.png b/data/themes/icon_delete.png new file mode 100644 index 0000000000000000000000000000000000000000..e0a635e5efff3e4bba3135291e701a1345b3e9b7 GIT binary patch literal 1628 zcmV-i2BZ0jP)miACUe2lhI?-eINDqnyD zSJVUC`x*EQP;Nc+R8>f&JtEO-wcBk=wNkQ660hSp@r*qjYu?O-+g z`0@K^=JCwy8Dm(ZJ~~Ygz;&z%w8WY~ORNdB#F{`$tO>M4x9I^a!t*?Dng5xV%)h** z$59YgHs*f+4QB4wG(~7*1kMrHA@_uhqLpFgG$IX<6-^f{qX{C7F^x2GqBfsDfBxlo zJbs{*>StMImT5_n91e%W-yS`B^bK$cI1g+VeR?Z>jt0qlXEYl9xGZUJYtNoN`vv$6 zxKNVl9Dy9iuw|RSySw{Unxo_J9qAUUy%4d z;8z`w&9m3e!gJYjnV2d1G?zNK0TmtBlzws__X42Ep0XE|} z{=@hEZGam$Zv1fn{{26J5SVbB6i&Q7(7k%~>PHVBKKuzFj^ki!YwISk4-A0WDc8@V zd`X)8#c3)gA{zpIrPQqQ#Vv&I`=4<9@>CT9E4y$(UWeTB{wugt{3;;zJTF_8M4OdJ zw~qC;6dwRbMXQ9mYvE<%ohx{Ud=g*zx$0VAxqPa5dF!Bol#?_6sjzWjy}7yhDe!R= zMZa!rY&aDY(=^rR&Yk-X=##r{OipAaRCeLQ?8-Ih7&uJRbX>KcrZJn%V)D%U7jQ`a zEE-rkfqIxo5U?r>gnwA!%otNSdo_(DNn-Mq%anZL zUD^7;!UByk#`C-kNR?7Yt|gSoWKynp(xO!+4`dW+qqPoQBd~DcQd6uwc#&@+X_`9c z!qe$=!ZCrhA!30_slYW0jG}0sz{V`l0LDcNEMj2F+oiLmAYy^D+03~ZI3ABn3#?5Z z2*to8Nk$U=tP)`uj%iB_oKC0CO=Cu*QG`GY6d^E*BIlCGU@%yWfwdr#M1ml2&V>&S z4oVj`G@V2SgMo7v*zfm6Tv#NDJbn7qISYL8;zfu+5|JR#+`W7EsEH5sHf?WjuZ)3K z(-;vK-re0*X_`(toz8m#{hc|KQnNUY%TK4xyD<4`BoylF%u$G`){|(E+aGAO)?v5X zy(rY*nPNJfiYPH)X@P})W&j+uz%qeU+Kn&|F$+x7)S1=DoRnql!eTK{Ywe5$7A|bP z3IRb2bV=4Pq%4sbD7ML5YwZky3u3AjL?+S{7AVlyN-&vB%4M9@Iv509I7t#`*27^K zMhL|~u_TftNg&kMnIjCt*2O?GnM|CCfk6-~x^QiXC6VcLI&y`;;cz%FWm!Qii3CC5 zj0+zg9*zra#7B&4ePUV#isKvu=VQI zs{_yTT787p7?WMTeEBA@1C&QAbX_q)%mM+EWm)StS|&*{<@m5-d$KTvpwQ`b&I|S_ z4oNK#&VWGQZ}(Q|LJPG17E;36h37<7lVw@!C9MT9)%viu=#hUH6qz`V#grJ3Ejr=E zHn$Tj&aTrB99+G9t!q%CfM8CJ0w4)DMFw~@v*r|9`6Dl0vE{(IlQiCWqlJn zl=|O{ysk`-{GfGA%~P5sL|nKy`fAAE>=F5Z1CGluwE>2_tVwxNJwc$_n^^ff%W6ie zfOVCklOS3@(4wB!s!%>`tvXpJ;mis!E?dfT)sU{$(s&6_*U{=vkS<_Npe5D>T4GJ0 aCH@A`iI)$>m}l$&00002?p zUk71ECym(^Ktah8*NBqf{Irtt#G+J&^73-M%)IR4Yo%NWgG%Y! zk3v!vEH^eJHY>Sy3N4yB!9;v_wpggH)kMRqwYM^-m)fnox+y1o=f8ieUxl1pu9VE< zRVh{azu`h4W9y0rrw|84tpx(20Vh%>^1BC$ghuX^Y?jdal-Vq-cgV_2c;lKGYUTbL zt=P1mY-O_gC>62&--CC;H*d4PKCShdG4{csyO#r8zq~voXfSix%gm{w=2E@Y2RJ{l zYCrkGIivV~ui}-z+TR|QG{%XzI+ms8v-2&?-QIZqfcmNa)tc?zR`(F)4YDT>$`lxtGNEX4Y4`N{u}Q8MHAGUofOqeDSYifH;;p)Nd+{@kF-Rq^2S3J6P^X5A}=B-lx}gH!|&F$!PZN_-SKr z|Nr>Cd-pDHI(Pfdoi}UNtl7hGk6C`>&qLxYHF-`GjfL|V?3v1~=AJtowt8#Wl0_DM z*4f$F=Nq>luztXNt@SxeP1>QYu{TV0j#@osv51R^sMxfB|Nk@FC(WsNf2Z`#sa*;Q z9~T^$e|)a6dV^+8-|;WUjvZTk^XAQ~j`zDC@3@?|-T33ZBF%e}7q}yBGz2_$w>`VO zrB7U3T%Nz^(Y0&WBD&dCFNv=!N?LvO*Qw6iw{Ooa+x@pm`-pPGjq}eLr=R-2!|%x5 zyLWr9UcEZ~#!WN*dzOoJ1A3l8e`ciAJgt4*l{=~;uSYAja|6=>S=Ap`1@Gveum388mw=>?7j((?R;p z5AiIyf@{-)ZH!*6_F8hTkM)EZyBcTpW;6Rvo*pSJ@8q>VCLG)Kqb~8xRMxN>pNzRY lx)Z|mI4kE!al&)le+fpzyi2?8p97W;44$rjF6*2UngDNG34j0q literal 0 HcmV?d00001 diff --git a/data/themes/icon_file.png b/data/themes/icon_file.png new file mode 100644 index 0000000000000000000000000000000000000000..371f1d08b51359e3688047ea4f0483cbf98675d3 GIT binary patch literal 2753 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 Z;7jt~Y~i8sZz2Ey002ovPDHLkV1gKenq~k1 literal 0 HcmV?d00001 diff --git a/data/themes/icon_refresh.png b/data/themes/icon_refresh.png new file mode 100644 index 0000000000000000000000000000000000000000..5ea70bfab3f2dcc59b0f6c0dbf3b44460dee50c5 GIT binary patch literal 5123 zcmWky1y~eK7+ykB-~gq&rArz-5jc(%B&1OqNePiW1SO@UTbiRmX*kLwj_wfY?vhmh z{db?;+1+Pno^NK}?|t8yi04``5+XVx002nfs!FrP&hePj|#`?S;NF5V~^zAJ>y{XT-0N|vhJ=vF)`{yIwn!iYGCDgj(3ORL!RG9a@q zX#LlE(Lt{!fzX9s7SYb=;?~{pr3~umR`3{eWpgL$vi!6%->b)%nE3j-?p|Cd!ZzEK zAT|B3D;^@9>sA`u9_Y^Kzy{yx9DZ~Rz*eSt)rtO5o_p{loo@Oo27~{jgy13 zv;4mSzA6TxM~_a(6~)o1MIn8Gq_!V$EOA&U6jy;B95(^eMmHsA=L1Y+Ugnti5bRMB zPa#oZ;zv@o(juOL>wCmh_i>i7SyIWCiycj*0g0G324EEk4OF z)u$qd&JQ0xm>hWfwUV-3KT^+Rgx+Pn`}KZ8a>@VfU3w9`S=>;_fh85_ zsB1qf*}@Zf0<7-t?nYW0DcI@$P{6TEP<+?{EIychJ!|re(pR>BD$!*PgRAo(3!rFl zniGX56h!{T9`XdDMbN-~yf_Ax&m$Z=vMgC^P- zd9*D4OG`{Vhp>j?cM!1t@lFVZc&_5p1Du1K1VG^CU|J=odUEvXwSQ(FPbLzXtdOzw ze)hn7XydH|4&MD-A=KU5x#xFa=FMK7}*Vj3=bKo~7*d)ieKuicenHFYf=#P@2 z(0TDB7GM=kt{9F)2IuAFy?zll)HSyZR+m06q@h?SJ1VWH_~X+T$2wvZk<`@w0Y*TM zMeyYAxckYH$B2B;q;};JuveoR!ybr2d5z^MM@hK+^udDy2)a#!E}ZI?MHf5QkvI{w zR1CX~jZF?It*A9;ue%^$OwTl|pOV%}QCa!N>epvs?e>|b%mqkwV}1RpyFe67C()7x za$Jh!6+?@|6Iu%k3zvp7B#(j!SQP*TAc2&Hm>iE3p_#z(RcJXWIoXBrN#LDHC?rXj z7baDpfHQlK39tikRa;(Oe%D@7jwQv4%dMS#xAd7_GEm>t)RYsh%R+OX*Su=xWh)+Z znzJ%QWSTUW5jy&5Jk@yj&5qOrAe12M}+q01&eNSI6vW zX=&Ft{pUn-iUhlRdu8>mOYMIB37q&~_$K&jQ=OuS{GyqVn?!!6=;vyFez`Q#Z`UpM zat>z5GzhKiZgE*e-b?k?J1-PzqzbQ)H4m}3VGSQ$`epkaHc8Hu8+n*oIE9f$I$^7b z31p@R8b0f=seyh?G)4=HiFs&%!`7vfuOdKf^b9o%&0wnR(ae&$2v95K%&_}CkP~>b z6Lx)l-C}HPobI)J|9G(2880mT>Iv26Me5I2Lj1(9qHFf|_j@momV%sCdm{F{JRXW6 z*2`z*7uTBS=jZF^oa*(WBx1=GRaqeReEj_W?tkyDGr;DCaqK7U!~jXal_2+1GjFps zFKdDwobwh^K#8Vlx%}n#@1UPMXK?ksdGtdZ<9H}3qJyUHXtCvzH3jq7JcXAJpg=7h zF@e)HF*P-H0myMx59(6$I{YEW^BPjP|MwF0FJP?MYwy%ELpvYNMvWuKg!q$e;sPHY z8ZvX>tQMdAeRq9k6A=*+WMO7zM!cLL=*}d6pD>kU&-Zm2p;a^pm7&@1Z)P<9xD3L& zBkGo=R%4jtn8=kiP!tE=gQO!ZEnWKP(IZri+Wjm4cJ(#%XOn`31}eb0dGcNbZjm9j zcE*s3nwpyT(OjKf?2s*cO?wXHLt|s({zE>4pKo5<`97qZ^W2pyEGn|C%j3~Vwo&&O z&Xh*s2xD~!1En(bi+lIZU(Es>K;y>sR!)$TzCIU5R9`>oU{ys zotH2ej1uwmW^2A&&2px&H8*$Jkd~H~jJ}w{Mig+m*qy3!{ndJH9X`POs?y9*Z`CKe z7)@fe)E*F&F6F+;YsT(ROvQioE-TSy>~{~1RUQxN&srNyqJ4c_)T&(1_1V^lh~GC= zO5nst?(vAi?S76IY|Iv0yT!PJHn@Q&lBm}mY^Eo<{|h$?M&N+$M&41_=69Jr-yU#l zoV^7vmlr|5)Y2O6Zl((x>U4{rwE+};eQ)%L$)DgLT8`Rpb2QwumUi_^aaB|#jYPiWh5 zb8tl0zHS-7VAR1;^w2?VXUHE+k!p$qr|8f0eB7Gp=e(>vu85+lp*Q93N59%KDx{R3 zLKuGh_<@>sk8r@emp2k?L?U-z7$qAC(?m;@=JD*O*=1idB2Z%<54AkGN2)f3`(mWz zcM`E#;7hTK=MBMt3MVJ0W<-r7)qT7)eoT2y%}I58gHM1fIp=6~P|W%HIex{gLc@aD z?P1GNApP6!MylYNv^K)+bcpYaL~0gkZ105U{%nnaN;c#KeF%b#DUhU48{ z@$fBx}Z>~mC9R)A>6S~-dJqWTl~*=0I=B^FU%+xmI#F`6u`f@ zh|WC~q(gM2idczyVY4FX@UVkpF7{@ET-g9U(_22HZ;BkYTn=SrWf`(EGIRn`l&^Zi z$#)1|=yrXK_;)opIH*C4mkdwvtoi!&tAJX}sxSQ@M`7^Ijc*PIoZ9Lj38JVH!yrv3 zAC=Fh#zHIOx$XSvFDyM;WPE)5G-PD!EF;xAaxX~uOFBLs9i0|V_;2pk%Z?yjj}uBz^qRS4TgU5|@<|&nFu40hBOvg0HKtiDMhq z-bcRzei3yJpSAMo-E_fO0LW9wY93a}3&pFOy(*!fmgATCjsF8oA-Y0ryOM z*5c8l>*z9jd@KMAz?;@wiXp>!)=zWdL(MFWtqc`s0<}a?31&l$&;yX{+BV*crWL~r zJLLPB9nzV*K$LY4$mD}q$&FZVBe_qx-{s)6Rk!)E(pR*a}r z%rkHA-#(NfA@mUFLhjQLG!3A#a0U{R_U_RH8`dmmHpsXS$6VMx;gZscZyVdI;kiu+SXp^_tI{KVwvSw&*xhBa zO22Sv4nW`O-+s<*Hj5r8t7=c@CcxIwf4uu0lG+8gWK!gH!@;@M2&dkl+<8llRy>0&OSMoi-od4K6}AlyqGxI+_V+yN}T>U z4-NU9%*)H`tz^aXKpCqr(Z<^Pr{tUIa`NrrtWRRo>oPzCENcxkRa=dwf_Xe@DVni8 zG6%CYR#6ey`8BQ8L{QAgh)_(j&?qq%Ya|;H5m7dD1TU#lxO3wzAxHw<<~}PQaZNL< zUzD8BVa=jr7&E}0eBmg?@PEtzjgT{#rubuZG`zeBBE&N29|Y^`>!+1k@=B3vJcazS zvbPP}!-2FrPp}XH*QXooDzQufJu7Y;9|3;>;2YNRyZzY{Ye&ajRkcSEDl9-plgAb* zO=>9n=OzLtX9&XBz`&r3hCNZ2s{h&dh6c(M%tJ#XqiYcvzO?A%N4=EVa`7j#Rj zQVck6937))sy_14dymAYq)6WVUT_W4d7!*`;hX>791jR1WxNq<#>9PpX(;`S$OagX ze8^XSCdZsqp|Afi7>WQBaIwL03V93koXO=hTK6ZI7*?8IQ-jHhKxU&vK>H`@ z8k|ugV&W8TPRw7wz8}&kl3s<>Nz5)24@u zd>z?hXXuRw6{iX_FwpEU|IML0S-|9XQ}>Fhh}PWErEFzzvBbc+5)gxfPuiNEovlC) zoL&2eQ{9T7kHMaxVh#@x)sIX}a3cr$vXI2og8p`(@okdG7-Di*OVs^VUtc>pIe7&p zO&}99a}IxGURhz`y+mC%27IIBd!F1ybNZfiY=x8Uz8AZ2@Go-)YU*CFSK%uJ?D3%o z2M1e{PP1+lS=WawZ0jve1g5l8OY1^HLMS~GliL(fF-7q7^&@8XY#baM(%jwMD?$8M z-WCRq-|6dFJUa!wHfTit+D?}n1x3cjhRy695M{E@DP(W;&wqbo=-Xya_ImP0347Gu z_XOuy;c7Vqb3w^Iw*Qp_-m`X++tfr08c|Cz--WwzGD#BI!pZAjen*Q>tkBV#{r&yr zZEbB)UNL%GssyYX8yhVtLKcC*;>Az$GJ!^(=!zm#)3bzvWNn4(bqfu%ujKjOs3kIG zovt4S>%1kEI+p7|NBhlgSx~0zyTdK8Ir}$nKokGOaj;mu(BS#=YV@q^>-APEEPK_j zt{|Q*S{4tH_A{~`Q9CyEbmtN2xzcm7n~b53=IriY8MV7+D-}#0VN8xXbMFo zbgJ{8n+sI7sLcQ~J}JXCM`$$~t@3(y$6lQyG!E3Ae}cTc^TkIE?CEFWoWZuSPU6e& zX|1vwe);ZsWp72q)7OjM_E)-dohIY6Y{v%^ARbUtYfA^*oTH8EY@OlS+OfoVA)s`} zD_Ny$UYd=Mjvfbz*$v;3c~V>9S$=&vV2cGMS^OM)0Mf;^ARph}Vry%wUAe@Wa$lSZ z4o1VDZJm3pNzM-hiRsg)ojvYr=!YaAnO3c?uI3_n1x*{FgCp>8wt#4eq8!sm)9n!o z1zDUb4}4kf@on5`R$0`Ip;#kFLEh$n`}dg&X6BNunDgnRzQwe%2gV#A?r^%^KL`4` z1}<)HZB;nD=`kxS>%@*H7tsd*o-kXeo)XTF+5RyfKC;y!?mYkPM=if(eqBokepFkR z0kE$#AndU@80^}5f@W6IVHk}v(5=HwuwUNsj$Q!Q8X;D_F#(+}4cfvyoY`Bf1lUSC zp*)efiHiFASAPP1+RRIk^Z9B5$wO;WF+OtH%?=Yq8rPRjKy+sabZIycMJ{Y$7pUJmYn9NB-u*vt#pDm^wUt5>^s?B_lUN5xjNjp z40c-RI5)Y)BFzljM$^h2;H8;amirI`B?Lf=v-U)LnL?9HBfv;6N`$m;4GI#t-Dos|y>}6|0R17pEhYXJr~@kzT`+8qStC zS)wM4y_d~GuztQX0Rx$^S5#E|;PBdn5!*Kop30RqnR@(FuBM)N9y@w? z{v5`M9nP%a-ze@lS@LLmaZQhgH56n%eSHT_&7m5z7H{WldB5Ko;AToC0bYnEm){og z%BA3fd0gP%Adxo9P$g{!8Iw9)GDey6zssE=N41{FM8`zkA0V+a%lWv?tp12XO_FJj za}EK6faW1t>7J|Q4f~4K3?rNuk=WJM)h}i{=p!c};9M|d8^VuC=f^O1T8_?4PI^{? zM}2MWsS_AUAvlLocEgztDwlP3(Nsc&^30QzS~!6efH!B$*c@$kfuCRZM252n59h!naX_Dn4E1H!Y-qHCNY%)Ns=<(mX5{Vk|9@KYEIRl26`mM6_zATH{oZKzu1lxy7Q&W+;Oz4EPWa-p7u1)kg|G@vBRy^QhW-vnT7R_tpD(j VQ&^&Ditk1{0FcE#T5Vm literal 0 HcmV?d00001 diff --git a/data/themes/icon_right_arrow.png b/data/themes/icon_right_arrow.png new file mode 100644 index 0000000000000000000000000000000000000000..6bbb2c6eaaff30f8e0e6d98e4a5ded40244708d0 GIT binary patch literal 1832 zcmV+@2iN$CP)B`E=0^lJa3-ADn z)8cIfV2IzoefyJRV`Jw;oQ1>T_VV)b*+9OY4eoS+kP`8Rg+ie-3l}b&158gB2q_b9 z*zoZ1*#!$0l%xv;JH&e$8ylaPiuiPdU`4#5&*)hrBO?c=Dn8vHSOwq#?ys$_EsaDX zfBqjKSWSPgzO+5NXwjldRaO5=078e85bOZ(Fz_r;R$5y6es6EDs%e@qDzeGp?%Y`LeRIxv7R=6@Xjs>@qtvw*ok z1+c8Ju&|-KyE{BSJ}%7o(9qDu^78U|seoWlBXU158N$5D5Q4#=X$Y#SrUZh04c!4k zadB}&Fc=I+qfueTRaL!|YzX$!oC1Wgu`yxBRaL$0^Z81X1;N&ekPspU+yrg_SAjvG z7wGQj=(xCe@#0Sh2M0&Yw3(Zm`%EAZ_`>J&JqhF>C*2IYDoctUIa^Iplni8~rUCaO zqc;Z%iA4TbvSdlsp+kqdfCvx;G$Dj$rLRe;3I0bWT&k$3 z*gZ5fbj?hgIXO8`@7}%pKxJj+(@bQ7I@|IUPb zn?TM9W5|eIJ$v@-I|T&=FPiDIrfH(7sj0Q5rsgz|3xts{6P^cB1;8*3(7L+1KFG_< zd)2J?`uh5|jT<+fL5ennTbcw@3BU!o`}+DCa&vRvGV`FOX=3x{&1d|6e+O_~_c3Hv zX~+yq$dV2~U#2nuPk(>^$JyE0Z<~$$mMvR4{C@whzz}jt9Y!v%H;@n#8vl@*%h3!V zv%kOpldP<)H_Y@?2qEh0>pT2@|1Urv@R#lb$nk%ji7ZISk_KS1_<@0eUDKvbt2Xnz zrfFj9)~)C2>go*fL7+$fJPcezUjY)0J|qc1ocKLnueZ`{({SOiFmMa2*gExpU2}dwax=#=gys-sT2=3Wx!gfL_AoZ0~EkLI5_x~%jGgHJ`f08a8f*2s0iuNcLDBjIQ$#>TX0ixP1D%3 zXU~P&+S(s*P&`;KiMarGK|#T`%a<>IK2-qC&CM5Aty<-{cte04ZMf&ppWocp*7nVv zekg=s@7}!^YierRNCWX;4*(6>;i%8&YdLxHWZUf`zi;2ZODk8dOdIiF9e^SJI#R%J zRaMm&Cr+IBIsS(&EiIQ;tXT0qX(S#j0MI+B0prNdUqK#Id#kIfTTY!i)ow(7|Ni}* z%akG5Q?J2^sf=*`P>*9Bgl7yh5k9D`v_?u z9&9`gD~jSme{m9d36i6`7YXDB63{3U#SBNqgN?^wA%r&R0>ronxQ-ki#`h>PGh(EH zct~DF$jAnxc5e&|!xOIJ+HFa@8`MDPx#32;bRa{vGf6951U69E94oEQKA00(qQO+^RT2oebzIT#?RYXATM8FWQhbVF}# zZDnqB07G(RVRU6=Aa`kWXdp*PO;A^X4i^9b1a3)0K~z}7)mT|>n>5~TqU|LpH20nnRO>?I@wLh3tlmw;j=0T2QxXhui5 zJdfi=0M(Zya5xFy|SDI5sn zM+S?RcuZX>whufA9RW6IwBpi|mdJ$3-fAtU*6^H&+YC(SXJbJ?TGm%WSSYe5*J>fx zh_NiS7>1GQM<_)ts6_cAEg{!MoQUm6XI&VaWT(0+^pa@>LOKp*K|F3gIgIHM*Wv@O zAv8vH9<=JeEajV1dU;c2Nddb{MXukHxZ12GSJP3GAZ*0?D)8W{t$VP34}6~yhA+3( zKdy>@WNItYhrVFB^@=xZOt#%je6W7CPlYFEDJxd*M2$d2Ycho;(x!1MknUJW8o;r& zzR%XP3U-QAqPxse)u9aEQ!CtCMi;$^R{5vBo>vD((RVRvQ^|AemsiVR5&D|Ckr9WY zw^N5)Yc6hoMh3PxStuoi)|p*4MO*BtIfrP`G^rv=>-PFKI^?_Et1Fj|ajStA0up0v zscHq-V&9WjvC15cv^-)~%K9D$d|pvA!&N%eb<`TSC~D4uwdi)-VlTnIXmHM! zPNs5+TkjaHpj+}zejVX}q!E8}z?|3S!3f=v&IcGM6i)q)0o9t^(k*#!G%r*aRc}5w z#`;w|E%bcu!%EcKeG&kSDY;bPhm2t(T6*h4m<{)p@Gfn;OsLUx`!o+c48OWl202<# z!d&fVjRVU-Ay(5BDmEoNwuz>!eYAbSGnx$N`b*=$G-I#TSL>bFBJz}&= zzRI@Aa>yq|&g-)m67aB>a>cCaPj`OSPHF+tJWaS*5eGy{4b}~vY_Mt*Nb4jWr?VG= zFsOv)al<@A$X;U~cS?{ghifJc1B6E%tE91Ay`P#XtptqYRWR+a9%=> z7B)#wb!eut5w^DB`sve*zUF_c*ds|yV@yXhx9XfLr%iGK9r7mLSQWv-SZT2a0E=(Y zG+=xRkIVaQm8k<`$YZAc7u%0;L8w%WnVJ4@T$S;^EDxvTv=*F6U-z+h2Uep-*lGf| z!pSpJsZfuB0k)AATZ$|jYdRiUxJROYeSCa;etuRLa2&_BDMWHRs5O3_JhF|oi`gXD rgCu+6I*ub&Px#32;bRa{vGf6951U69E94oEQKA00(qQO+^RV3JnbnE7oB_%K!iX8FWQhbVF}# zZDnqB07G(RVRU6=Aa`kWXdp*PO;A^X4i^9b1T#rQK~z}7wOC7X1t|=ZsJ{OlbBe6e zng#d=<|S1#^A<@r4aOf?Hc)yc03eC~`uFwq^#BAU>3v^)_`R@A~vg z`2PMLwwYQL>L?)zAV96J%3nc2Tnm>!M*8e4Vs(s?@PAlhd?%MdaJqVM{T|ml+TxqjdFG)$e1$&6OBqmcpl7sU7N9pZOvCSA`3Dkz9z{o{n5tl+c*)S%LT`C*zclsWKvS$@*az#^9 z!y0C=v4pYKKY^mp#a{ceWuX7b`_1RZvE%!OYAIMlT~wvz9En&IQB{~K2Tr~X6_9B7+yhR81vBI$!<62W1`bPHR8ud@DwttP z#uf14FRr_e94n2N&VI4&Z=y-6J&1vZ4ulwYHR(pMQ{ScpT`NI5w34p{ zigdjpLTQz&N!?lDJWo80>vg-5;tsUgKWULiel7=bQq3U*mHTc-=$bvdp?^6i3DmUT+4cb-lMa>Hw}R*Ig#}cSmajv?kmZ zeKxUbC+WfGC>u&nQIQIr5)Opt1o)NpZgW`9)thGPx#32;bRa{vGf6951U69E94oEQKA00(qQO+^RT2oeb!2f$i|fdBvi8FWQhbVF}# zZDnqB07G(RVRU6=Aa`kWXdp*PO;A^X4i^9b1ky=FK~z}7tyoEN+%OOWnEC%FeTzTf ziyJwxS4x^VRncLFqPX;m2FcIQ-vCJh0B~*GcK)Q1?fVHw$|UVAu?T!eYRSq?vCkV5MzqRi)P~#h|5MN<=k5<$Ft# zw3hFm-lB^tP8I+4Ne{RWOyYLpn}A}E3P|D+h5KCs*LHZbUMd)Ga-XL1|D@7X03d12 ziFb0xcvfIb9(Cn$cg=RUNNE4K`8lKNVlhF)`hg}*fwqnwj7xF5q1=0SQc6ZgCjK~t)>uqu zN<-Txfdm!w=JPUC=#edtr5-RNeI1YJ_^7Kk!hQcu5*MmJD}9uXt6aZM*xMg$Ct1!eFL0ejM<vIJ@M@mu=S2vVz>j1DsYqabZ)?$ce!&|^=kDbh84RnEOfp#l&=11x4L=j+z6 zi5{TJf>%)F(v(1zD5-@Iq1X!}yHJPAhQBa?Igk|Zjp>mZ`jw# zb=%I>Nq^Ml&F=<-baOfheB}{=k>4x ziC9ndfg%8dmM97mxptv-HxeeSe(n##jhn*T*=K{KwEd+#y#9Iyh9_{C0Fl=@gL$$F zr#Dg`(_tP>ShZQ~X1a%+PgS!p+}-DNdiLOoti*m#6&|n?ZESS*pz0%&2Vug01zEE^ z`n6nlM%B%;WLz_LrLJbS(=XV>6miz93ZWJi$u1J?dx<+FaloxK&~%9g2YG%xiETvf z8SuHY-2{(pd!{yy-mD*?Jf`2~k#5{A+}%aq^Q9F5dM2o~SGCwZJu|X7@@uPPS2${6 zrt_Zk4cfe+1+R~fkFT#UM%`X(9rxEHH>b@;j>%t=YyH~uaxlpix4SvfOk`1xwN|ni nuC;%Yz^%2UZ)eo=WRmSaNKGI2GJ{Ah00000NkvXXu0mjfzR-xy literal 0 HcmV?d00001 diff --git a/data/themes/ilist_2_h.png b/data/themes/ilist_2_h.png new file mode 100644 index 0000000000000000000000000000000000000000..6ab252e574a31e4eab2487ee50986a57752e66c4 GIT binary patch literal 1384 zcmV-u1(*7XP)Px#32;bRa{vGf6951U69E94oEQKA00(qQO+^RV3Jnbp6jCt`bN~PV8FWQhbVF}# zZDnqB07G(RVRU6=Aa`kWXdp*PO;A^X4i^9b1l37IK~z}7wOC7*+b|3RnB4!8vuiIf zi;2($KcZwgd3~?-VkVYli3C9sGJpU6B>@0Q{OjxM>+1;+kfbq&@`4ZbYYagWB>6n- z(}sow44gHcp_k=wN%z(`9gF zCMwi@v&@dm&=Itw$s~irGa1`Vf#lOCY3O4xPO)*8838fFB?a4zNmIRx!M5>sYtxT( z%Wv|({nc_Cl80MiOOBu^fzhHrW&xSdEs;Ng78MVV;Amwsxqws^?Tzhk{8*rKh=jt8 zRrpA@Qq8~GX>McoBnb&Ha4dC5vmLZ7Eo6d9?UyjTnn^>mKw+zH%=Gzy(q*uEj}~ui z=`R<`@{k=lMs!TB_)Hdc+Pv$UX}bUp$ZISIMM)qS$)*mJW&bcpByXOiGnD%gXU|Sjy zJ;H*J<(f;DH6iB@ln%FdXxrcI`Fq$kAt%>ln~*{l%RJjqOkJRc*xG&;Mwaw0p*+dhT4w8#%A%;2 zO-qVGV&!#}8G2$V>x&<*#*m@c>%|!@Ja2<+c|Oqt_jU$kv0GYlPN_Du%Ls0P*?MV% zj7V)t53WwV(uq-NmEJR?Y1V$!Z5}=)F@n7Fr)=LC!L4GKv(0gAYRVeyRnP=%ht;a@ z+n&`|I058Ucrn{*c0SFLk?1i>=|lpdCBRf>4oWWPWy)?E;i+I=$+gYzU9$@>oru}b zS$*uN@9H!#;Yw1KsyH0J>ijqxN~wo-{;vE&Jg#3+8bKY7IO5tpcbhxU)&tHYA(N)$ z2_&5>e&S2)$G?L;&LXY&Hi4cvTm@g0_4!7{rW#yhk#5f2&9qI3aSQSNspNTpUbhGR zooKD-a{av=LtEGJvz2u&SwBt0nQp2eHVQN-hT~A(S7x1qH(pnG4;0C-F5t%8N5T5V~m4BdH<13nzi=R^(F=% qz98*i15QABsn*@Ie{vcA^YsT_8Nw!>!1I;>0000#zZjbG*X;ZU6sI-gG!&dRqJ13zD~sZabE* zSg>Se%*~)n4bu5%4n)|#-g~^d^qaKwKS|cPHw$Kzveewz&wTlqqo>oV8A^r^uT~{0 zm4yD?bex-^Q20$}h?H(=#|DmT9h+^AeqYb Oox#)9&t;ucLK6U#|8=hb literal 0 HcmV?d00001 diff --git a/data/themes/ilist_item_shadow_h.png b/data/themes/ilist_item_shadow_h.png new file mode 100644 index 0000000000000000000000000000000000000000..fb21bc5affa2891848b80b129378fde64e167eb0 GIT binary patch literal 350 zcmeAS@N?(olHy`uVBq!ia0vp^AhrVs8<14~_-s3nVk{1FcVbv~PUa<$!&%@FSF~y3C>6$mL@9q-(ElElXBg?<5tYR3(v^cB;gt;N{1RiHDP` zPQ0+lH(Dmc*e|E4Bq{e(zTaN<(z}#^g)1ZvrOM9S*UEjsHFn*sy&^%qDGMSFERIQD r_4>*h@w~*0xBRn1o-cEm@`fdD^*)uY&(A9Yy~W_^>gTe~DWM4fhTwzZ literal 0 HcmV?d00001 diff --git a/data/themes/leftright.png b/data/themes/leftright.png new file mode 100644 index 0000000000000000000000000000000000000000..8188c19482e0170969de3757aac589524bc54424 GIT binary patch literal 1367 zcmV-d1*rOoP)Px#24YJ`L;wH)0002_L%V+f000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOb< z1rIIuadTY&000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000ECNkl;{0&GjevuVzC>0dwVH2KEp7SWHQ;75J%>#)v98ersb@3I?V+FfoTBOyaWJn zEf5Gyr_*W9jkj8@o;yUt{Iss?O08D2oW(Ei^PgdhO; zS5{V@Xqu)~DizCFG))T>Mg7zU^R6Linikx2HBHl2R#u*TE`$$&e|2^Bsj8~w6U@J- zC~Cfq=1&Uo-c4Us)$;1<>Qg&}&q>k+;AS?P0M7Zw)oxn0~QbS*3_+><2f z&`qD`c{v)5z63CA`#pwk0Ji`<3kHL4IF2j1krWDr51X5tkqekth|SH-NTE>p;HJxQ zTqzg~z5(#e_Sx;Wfhqe~oC^knZ#j-D6^lj7S+XpDWEf_+jUfnzVTNT{{^+L1aa^gt zzyB?Oxu#>AIOz%5WB2)7e}DfX$8m}*%a*h9`MgNe^hi6#X_}@-^7*{zrqg8pMbrN4 zJnb=m6e1J~EoL$q*AS8<9Wo3PJRO0Q?C+08j!@ zbKAHlp=Mts0QhTXXXp3X+1X!2QPeEULUZZ5ZlqEv!pkt1N~H*0*9|9^D2m$b?ChD$ zpB2a2DI5;JV_8-eMbQ#P(GmoqFf}#x9Kdyt}$W-bcAo$>MUS3J)bS(a5Ikx1jHJhOS9#}JJ@F+4gt z8loslT3cKD4Zyzu@*ZzPJY(q7ue*TS9n+Wz(REr23`EPw(4 zqlG(r1psNc-!}kq01mwLysrh(4*M~F#TL=ev%%~|>9$`Do3H*Q{^0VpxBwT;b%`&E Z{{YFFitqWf@(Ta}002ovPDHLkV1mlzaq$2E literal 0 HcmV?d00001 diff --git a/data/themes/map_item.png b/data/themes/map_item.png new file mode 100644 index 0000000000000000000000000000000000000000..9e9015921c316146dca1bad9419939e8422d63a6 GIT binary patch literal 3041 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 literal 0 HcmV?d00001 diff --git a/data/themes/map_item_1.png b/data/themes/map_item_1.png new file mode 100644 index 0000000000000000000000000000000000000000..da9b580c3776a388808cca2229a719fb6360a2b8 GIT binary patch literal 2669 zcmV-z3X=7SP)r^ihC2k( zgASbr%F(1lxI#N5r5w{1N?SfO%s^qLg;FT(bVvu9>A}D>FiA@Zk7NfRJINK2u`; zzY@`*oCzDQaW)M=L2V)*FIANESAC>&4T06y2edqRp+e}0FVJPSOQ`Y7(iqY5T`sYkpVx7V^7Nfp}_NSk$d^3rmLTHnal;u*}xHzoxP|tFlYqn zY5i#P(`S6Guf3(j0~=WYP1)@ho& zcPjlSH2@I>$yT-ditGP&o*Nm6@!8X!E|@ zwEC%fK`P?_aqa~V0DuT)-hmf?ZA+z8;QbdO^4WHs&;Zd^`HQ;7jh7aCR`3AGkT$QVsnugoHD%qpZSFhVy0|4f^a>2_MB7=5qyP-dPdVd`eg(hm7F#|+v*$?ZN-|GQ@ zv$wkW1tNpXRz7MIY~_IlyBM!{@c^5wb02DeK&|b9UQbb%lQM)k) zhy~@3U2xgY%81A`@Jv5{X;}FvC)&K*CTcUn07NX}rP8lE%darc?JItENVZCJmS0|n zh?kGoW`qHpSbWnt4R<*S3>I%SYD? zMawW|38u4pIZv?Ks~EvrdiUsZ24LWwpR-tng*g8Q5v>&f1WlvM2Q#2dv{sk_7j6dd zk{bcRHoE+C18kK-o;BqaUUUJ&3gYN;1^|F%S&wA%@(VZtz#=(;Wi6Qv&~-hjrxlp5 zZ+_W8dI}hhM?@Sk4F;z`ARcWuz5rc$LrDaIGusRp*p?q+$bdwDS59_c=L*S04^cXq z0)W2Z<%0$URk=s|e0O%?k(5KArDb*W4iWNz|)lsVh z!O_um!&gamhJ3p<0ATYcEkAU3yhA3F5RFIMUm9IElmSFUx~6o7%bKBU`BRu< zPJOzSSk|176Fq;-R6oK1BGQbsvcK(A8USQUN{gq`438K3Bw|};hWP4H+ zC0qHMuFBP`5EyRh%FW0y8F!oWPV1rHlM?e8=U()n_TL@1_k_C-uOU(oXWKukjX)xz zM8E&Ko{o2RB4Vuh%}t~#;pwZM1$147gYP~_CYIN0FWji@-gc9(KYIMzQwbhm8pq{D zoA(KayWtK!rMRk=ti$r!Ya!pu>Al?_!twpjQtgFzYb?vB4!nJTYa-gQhKPJq9cxTkk6FCpKC~50cq(mLD2X0uIq)nQx@Mfa z;=Z(|CFt<3NBr^r_E(fx;HNZ$)!Z3$DG ze+3ImE|~V%@kl##x4%Ww&493LiIyS^8>> z7phqFUrd7x0oBEP@Mou>_DY0g(Z!5{9JQ z1F9T^q#T4qq@7}YtsvQ}jnYM5){Dzl81YCOocwr8IOzM}SR&f-eIgpOwl{6 bZ@~WmP+WDwGsb#y00000NkvXXu0mjff-vdX literal 0 HcmV?d00001 diff --git a/data/themes/map_item_2.png b/data/themes/map_item_2.png new file mode 100644 index 0000000000000000000000000000000000000000..f92ebfac5d9f657a0b5a76b53d8345cbcd5800d2 GIT binary patch literal 2578 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 literal 0 HcmV?d00001 diff --git a/data/themes/outdent-top.png b/data/themes/outdent-top.png new file mode 100644 index 0000000000000000000000000000000000000000..b4f891d040fd76397cb113721d09b55cf261fac9 GIT binary patch literal 1913 zcmV-<2Zs2GP)Px#24YJ`L;wH)0002_L%V+f000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOb< z0u47jYW^Sq000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000KmNkl0|=JCWXJFE@k0ti;wK^q z&->xUYct2t*&+at>g!_w05WJ``k;=D_Os{CTn87PEkiIC0LLc+j|=B!fP(=UI?$v* z*ZcaTaBrfv9vLzuxIzf|O5l$^Cc(!q05v;q7HrSr!2z5ApqM@=z!?Bq-*1Z~m>rve zCQkx-1pbG2!~yu20P8AQZ~=VJx<{bvW&tk%Q2X|{MiltEd5Qo58Ds)}RykI|%|1&) z7ofn$MN52^zn)q33~Ud04Za4x8WMoA_yz!bZuj{x@wU@iaF+ot+j0d_@-hf%-hDj7zWiWBf6;L#Z~x)53cx2L`S1K>lY$7%9U_ znwAOdA_9;~@z6>0wDoJ?UwYdV;D`MGHe(&*?NTs~v$K5n`4lSX`to z=F+(6r)Tn?@$u0+P~h*;qHAMR}H-QsEWXNF8 zeR2UK0N?@{GP0fx?naJSq1X=`T*|w*@ZX%@Dw=2zmrKVgWSqfTso$92;c~I8cG8Ka2d` z)Ugf#&k(^{>sNwLL7L~)__h2W>E4SWz*}!GD%C?(5!{_puyzk<+<|_#ks5fefd&~u zL<~rR52M)OiUOQ<36?x|(guROKC=4a^sD3ly%^vi0I8gx2W8;n*Bk;gW35_E&`|+4 z?gj?IVg!8F@;w}eE?@*4Eu?BVQ5cT^GvILmeueEf3D8G@o~;$w?{C#9T?x$kZdeQ!=|ql?6U(>7pGX0;3LN(w z^8dTHtrMUH1OTG~%^`-hN*JV>QK}dPj}Vl8JcADen5=+QAh?;?LOn)P-%JvVIK1;5MCK4!`*L+JQP~Z%0DM9=fENhl5x{c+ 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 JE>p1%|39ABAq)Tj literal 0 HcmV?d00001 diff --git a/data/themes/radio2.png b/data/themes/radio2.png new file mode 100644 index 0000000000000000000000000000000000000000..b83e5527d3edf0518220526c580756fc2c149c67 GIT binary patch literal 4406 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 RU+|6tFw!&CrE0sx{|{{bMFIc- literal 0 HcmV?d00001 diff --git a/data/themes/radio_base.png b/data/themes/radio_base.png new file mode 100644 index 0000000000000000000000000000000000000000..d21940030513732358329db1627473ff3df084c4 GIT binary patch literal 3125 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 P00000NkvXXu0mjf5VFiE literal 0 HcmV?d00001 diff --git a/data/themes/sb_runnerh.png b/data/themes/sb_runnerh.png new file mode 100644 index 0000000000000000000000000000000000000000..a483ce8b1d6e625abe0db3c7c12f7714881c4eaf GIT binary patch literal 160 zcmeAS@N?(olHy`uVBq!ia0vp^0zk~n!3HE}ZR`&LQjEnx?oJHr&dIz4a@dl*-CY>| zgW!U_%O?XxI14-?iy0WWg+Z8+Vb&Z8pdfpRr>`sf4Gtj=CYHk!#YKQZ3Z5>GAsp9} y6BY;<7#SFx2ww1CQJI;U`SAb${~w<;Wn>WWXNkY@LufrvErX}4pUXO@geCxL7%B$< literal 0 HcmV?d00001 diff --git a/data/themes/sb_runnerv.png b/data/themes/sb_runnerv.png new file mode 100644 index 0000000000000000000000000000000000000000..cb2da6fc3a866b7d011c07db827d432dfef3e6e4 GIT binary patch literal 166 zcmeAS@N?(olHy`uVBq!ia0vp^%s?!_!3HERXC3VVQjEnx?oJHr&dIz4a@dl*-CY>| zgW!U_%O?XxI14-?iy0WWg+Z8+Vb&Z8pdfpRr>`sf4Gtj=Mmf=Yd)ESm)I41rLpZJ{ zCp0irvH^jc#Pk3E|MU6qcqCjX{s&}EXl!g`WLPcBUcNv>s0^rs!PC{xWt~$(69D=U BER8<0#)^t}M27>k44ofy`glX(f`uqAoByDx`7I;J!Gca%qgD@k*tT_@uLG}_)Usv{<9HN}8EVpMe`~V7xd%8G=a9mGL oNl18*sK8|K@Bjb(b0u0CdYYLh8*bu!160D`>FVdQ&MBb@02v!6_y7O^ literal 0 HcmV?d00001 diff --git a/data/themes/separator_v.png b/data/themes/separator_v.png new file mode 100644 index 0000000000000000000000000000000000000000..cd1b0182a75b88399db25405ea8e8d09dce2522a GIT binary patch literal 96 zcmeAS@N?(olHy`uVBq!ia0vp^OhC-V!3HGfJ?-}dQY^(zo*^7SP{WbZ0pyE&x;Tb# rTu)9&NObP0l+XkKx*Zr| literal 0 HcmV?d00001 diff --git a/data/themes/shad_circ.png b/data/themes/shad_circ.png new file mode 100644 index 0000000000000000000000000000000000000000..e344e5c7b6f5555aa692139ef8f2d6b11df47bbf GIT binary patch literal 1521 zcmVPx#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOV- z2Q3<9y0N?f000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}000F{Nklu%&A423b_{oi=-{%Iu^`EqPXrqhCiCYeo>%(n-8!AU8nop#y>H~P@~;RA5* z_4%&=eCm4q+kOyjJeGeFNP6@6pBlpaX#gqsZ?q8{KM9f^Iv*__i$LJTW8V%CffU_G zAx8JNL8Lc;qniQplOXA4c+z$jW)vC%0uJZ!P;SYgi@=kBY1^m@XT{Y47zslb1!+NCQXmDDNeVP+ z--Cz%>;pua;EmhkagwFApqW71g8B-eyh!&{sLgp@`P*4>Gei<#hE>=W)aMP~xnIh5 z73M?Bk?sP(@BVTW+#O3FR$*IEUrBG z5+EW9oWXgjVr7b81E#COwo!ea3ZvuR8NzO{mZV zIIC|Qrk9{PRzNb40T<`NY%(F^14_`EVN5)LlFP!%aIHdoOo9@_t!;$og>Z;L(F_Ss z3ZhAU61X}z&eegJhS-AZ9M&<>Xv6|o6$N%>&Xd4t5Up?#NhbXF9U6&b6Q$%h*4p=) z0=4hQb95j?v=nHCcw2@rfuO5mSUe*`fC4q;b>q4nSULy~;}s)lMMkJEr(tebenHk|##VUK(K<99N3Lu(fMUt@IoEnYAGxwBkwd`pWfLj8J zh$_AWAZ;nE+6C~>wp{?dIy^RxVNgr+4QrKG2{ zZ>6NFkTqr{8zaH9t}D&0OY>p_K}i92q&`JTf_7o}j-i>RK&!uiA^1>k%cU4av131oKLFz4BepdUpq!_1&yi%cvkg!|THAEV_`P!g(%xDT>n6 zhc0U(3iNzLB%;|egssJAX$Yg!z{&W+L1^kl=^Bx142fKH!u2h(E09Vt;CldpD*GAh7$~^8xu_`%n*4> zQCT(45rC}tcSsb1CK0x~F=*{vS33tg(CFZ8FW$MzzLu@8&bmD- z`^(^V{~+&t=jCG?&wE~fxAFYv1&lXb=ez>+2VC#hy@dANL-^MM%-#=|(@s0>wDtB6 XePo=MsxSw{00000NkvXXu0mjfqm#V* literal 0 HcmV?d00001 diff --git a/data/themes/shadow.png b/data/themes/shadow.png new file mode 100644 index 0000000000000000000000000000000000000000..5dc92ccfe4091eabd53c88a0f4ae818e0fcf99c5 GIT binary patch literal 1030 zcmeAS@N?(olHy`uVBq!ia0vp^`+>NNgAGXjj-4$5q!^2X+?^QKos)S95(ej@)Wnk16ovB4k_-iRPv3y>Mm}){2IfRh7srr_TW@a!=3h>eXnT0PH#6Yn z7EV8bj^@Ar|Fhb9UY{CtQKh&1liROptYYat+m4iaPMdqgi@$3Bx92Jh4EC+>>h0v0 z8U0x?WB0Q==L8Hszi3xJo__Sc>dqB^7gfIXJ0NrT{?&gwD{H^_U6?OXH~)$2=C5ZR z4$L`pU+t#J?QN0`lON|Fj#u01RTTSsDPzL2hxV$KKA!@9n=l*n?EDmeW$Hhzldo0s zv+84+H)Kq6Fi8FL`-A+XJ8F?v(|4==nf&yZSM-_8H@hm2a~;KSx}w zU!`{4RA6=$+lyO_FZK)9l|MQ4U+?65&wFY=RZlKm%5NO`Y0cyszoOvx_9{EQi|(6P zW!=1Nn*Hy!RKs@9d+I;e-V?Vk?)bkl$)C0Uvd!$WWciAI+b{c8Y5!aA`-l6Zar2M; z*FM&+4bl7jT|RY};m2}z<_#-8>udj-{wQ7Tqy6=dn||56eE#F#5&I4D4c%!1->N?v zm;T9&%31&A?!neSYku&{xAf;4Ox;}dMcUS0_oH&1fPIJj5&lQ)ADe$T{!t)?+fS@Q zR8xt!09hYV4*THzMftq^zKsV%&gE^A|Hxi;_S>B|lb3w9PdM~r{_NcH6ppryANk!u zajz1oUb*VL_@nekKgzE@-u3H_49}s+@P7+C|7B0o_k1_`&ei9qtMUXuk+AMp&6?}C zo2?JN__6(~E5B#n~ literal 0 HcmV?d00001 diff --git a/data/themes/shelf_inset.png b/data/themes/shelf_inset.png new file mode 100644 index 0000000000000000000000000000000000000000..bb1989dd78cc08b7221b52ecf5e76631d1ae7325 GIT binary patch literal 509 zcmeAS@N?(olHy`uVBq!ia0vp^N+8U^1|+TAxeoy;#^NA%Cx&(BWL^R}Y)RhkEPx#32;bRa{vGf6951U69E94oEQKA00(qQO+^RU0tf^cG~zc{_y7O^8FWQhbVF}# zZDnqB07G(RVRU6=Aa`kWXdp*PO;A^X4i^9b0Zd6mK~y-)eUwpl10f6pHNO98a>40` zZOSHTd07HPYfG{Tuh)y`D9GDE_b&06oE>mc1fTrNl~+;$O)C2UIY%a_h766G68AeM;)rRIEhqpH8o~G?i9uR*8g!I+l6#zN z^B#gP5&SEamBN<_n;`46(rlxS8QPz2vw%Gvj>s|5$=7vt%xrO8LW4I6qr*}D?zwyG zpHlTJWEyMSmJRQ;R9_9ZDPzQ)4=mlyG~tloB&1bNMLVSzaT6TWqvM`;=+NiOHC(Cu zb6HPp3Ei5%O%q1WP;>6ls?F_@4d0jubK`Z4h@f7T)3wn^x~b!3HGr&QzEKDaPU;cPEB*=VV?2Ih+L^k;M!Q z+`=Ht$S`Y;1W=H@#M9T6{U#F!i5(ej@)Wnk16ovB4 zk_-iRPv3y>Mm}+%qS>A?-l++mqoRZ)(oIZR>}#%pD#qVh$K9Xo4vmNS$lG< z_ya>-mhdK}sRx)Ixofz&tYi0fXD5!(ojwzmtdf8C&UB}QK;!u-m%2ON{Mr{E>pOj~ z;pU5H=AAhc^7YM$=XZQ_jd%{P?$~owLO!`?`(ukuS0+W@ZfmvnIg0EFQFbo(xUHx3vIVCg! E0MRX_2LJ#7 literal 0 HcmV?d00001 diff --git a/data/themes/sl_bt2_0_1.png b/data/themes/sl_bt2_0_1.png new file mode 100644 index 0000000000000000000000000000000000000000..5db1c7cdf5f29c6e9854623c23dc51953d091632 GIT binary patch literal 466 zcmeAS@N?(olHy`uVBq!ia0vp^{6MV0!3HGH>L{%QQjEnx?oJHr&dIz4a@dl*-CY>| zgW!U_%O?XxI14-?iy0WWg+Z8+Vb&Z8pdfpRr>`sfO(qTwQBk2+=lg*|k|nMYCC>S| zxv6<249-QVi6yBi3gww484B*6z5(HleBwZ>bUj@hLo80eox0cSh=YimztQBIEsWCL zd)m%#?By2AdgBse9ylB`4u5S7nZvw zyvHQATvO+CX-SmGxGlEz{`>iBw@NP+NtF1fAt1PG-QrbR+it&YX3ClOy#Ly*=(S%L zC9s^{q;h(bbi(om<_n^(A5+%uoh|HhfcFE_9<2rJQ3(Z2zXJ`f@%&&DNq#Q(qTz7J zh3|i5elTu1rTaIsu_NHRY2>t6=H1B`4DX9M^DH?ay20;qNW<3M%ir1B^vzy*fI<9# z>I4SU4}3L#)@l~uPKJZSX-}^z1_N667+Z0yro-KHIlWX*& z5`pZV$iD#`57mQ0Lj{GL9KL>ddE;+ge9H3(wvC zT3gR=kzjVf^nvlR8U~gh4EGwsAIJ)D+Z?^+#Ab3_C}z%P;RS3K{o0(CcY9wZXGv*= js(pBV{{XE)7O>#CKCsTkn}F$5`UnOWQl7;iF1B# zZfaf$gL6@8Vo7R>LV0FMhJw4NZ$Nk>pEyv_PEQxd5Rc<;Cm-ZJWWeJ(Uyl)p-61xT;&gP!@k`JNvo= zt}c1Pf{q6SZ~STaDQD5^6m#VUdthz%+ORWOY~QRt*hUM+3M@$U(C$3S5|z;T@LDf# zy37athN*cA%IY>5raL9upLBZug-88psz>LCnGcpOSL{7(`y?kRvuWjW7i%J(n nx7p0wJ$=sQ-FMd8EoWaYpzHc~TE<$SCm1|k{an^LB{Ts5Hq3tE literal 0 HcmV?d00001 diff --git a/data/themes/sl_bt2_2.png b/data/themes/sl_bt2_2.png new file mode 100644 index 0000000000000000000000000000000000000000..061ac29d85311917ee8538c545b0adeae7b34d43 GIT binary patch literal 286 zcmeAS@N?(olHy`uVBq!ia0vp^hCr;q!3HFEi%n1hQjEnx?oJHr&dIz4a@dl*-CY>| zgW!U_%O?XxI14-?iy0WWg+Z8+Vb&Z8pdfpRr>`sfO(qTwVW#8BZ_fdRBuiW)N}Tg^ zb5rw57@Uhz6H8K46v{J8G8EiBeFMT9`NV;WDm`5sLn02py`sq1V8GM*@Ze4h?m3d3 z4huHiHu+${VYE?U+JRI5RYkqi?p@nfcy247hJTQL=I$*2S01l)yO$`6C#`v~(AqQj z-JuxI<7>Vb@0#hPI`_S9OUIuh?kzDK`HC)EF8Iwmn6}~cS(e+K^M53AR5$Z7Ff=^( Y+r)V7Yqo}g7tj$5p00i_>zopr00$Ri@c;k- literal 0 HcmV?d00001 diff --git a/data/themes/sl_bt_0.png b/data/themes/sl_bt_0.png new file mode 100644 index 0000000000000000000000000000000000000000..8691b1957ac72d17acd9b5dcde193f0530a197d5 GIT binary patch literal 571 zcmV-B0>u4^P)Px#32;bRa{vGf6951U69E94oEQKA00(qQO+^RU0tg2U1%?^`j{pDw8FWQhbVF}# zZDnqB07G(RVRU6=Aa`kWXdp*PO;A^X4i^9b0jNntK~y-)m6gqI)G!c$KmWv8c2zDM zBHn_BfJ+awSDus$>Z?Qw5~!7swlvYMY{%xnxJtGO4I^2$m6^|;8P7y97j-c&Nxqn8 zMjEhyk@XrN10xWDRA36IfVaT6iQ?MmMej=N6ms$vaJK<49d}}90BYbpFcbx))asZ( z2C=J44E9>g_lEn7RF0X_iNP19uHTK0{6*GrB066B;^ zz60I>C*T+Gd+7%1AMdATCc2 literal 0 HcmV?d00001 diff --git a/data/themes/sl_bt_1.png b/data/themes/sl_bt_1.png new file mode 100644 index 0000000000000000000000000000000000000000..a29f65c286a4f3b7472dd6e023eb6a6a62533f52 GIT binary patch literal 249 zcmeAS@N?(olHy`uVBq!ia0vp^fut`Q!saSD68YBuiW)N}Tg^b5rw57@Uhz6H8K46v{J8 zG8EiBeFMT9`NV;W(mY)pLp08xJ-?B+!GOo*;`@$J4T%O-i5aRHGg-K#RF-pDISM(o ztBUtMT5kMjsSkVk{DzOI&l$puXUlsiFW9QGV)Ajuf=n%AhxuZnmW{ffceb?2Y&u=J nlcoGZR)_gA&iDyIv$#9w6&ed$NnV%-w2{Hn)z4*}Q$iB}47E!F literal 0 HcmV?d00001 diff --git a/data/themes/sl_bt_2.png b/data/themes/sl_bt_2.png new file mode 100644 index 0000000000000000000000000000000000000000..96bd19134ff893cdeaee9610b824dbf1a073971b GIT binary patch literal 246 zcmeAS@N?(olHy`uVBq!ia0vp^fVYF;p`# z)oI~LOi8ghcHqE)p7Rr?yZriNY3DpoIP-*eP1~LYZQdQGPgqU&IEzjXu=lwjJc(tZ iW^_lQNKca@H^Z9Ko{Yv?qOL&e7(8A5T-G@yGywqUZBIe~ literal 0 HcmV?d00001 diff --git a/data/themes/sl_bt_3.png b/data/themes/sl_bt_3.png new file mode 100644 index 0000000000000000000000000000000000000000..8be95f545cb380539645d1863b5a0fa32757aaad GIT binary patch literal 570 zcmV-A0>%A_P)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2ign= z5DzwUQfhYq0013nR9JLFZ*6U5Zgc_CX>@2HM@dakWG-a~0004z zNklZ42C~@6BH5z1r-!rg988+5|10ri4YXrfpdUF1QG?0SynI)8gDcS zyV1s#3;SF9U-=)Q2-%Xnn2N}B2t-6$&@|^f1>Q#{ z?pQ?DHg|z?&f|6+0aR57L)x`cN{Zd;Jv>DUVyLmild$PEAZsKzw81PfGgn9>OBzE9O@T%2j;-zDyRc6 zxB4IFT#~{X71#pyfCJ!YHk;k4Dk-IQg(u*-1pM>T4$$FbGP!S>=G>a+tAI{JEPx#24YJ`L;wH)0002_L%V+f000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iXD$ z3=JKbBX>9e000?uMObu0Z*6U5Zgc=ca%Ew3Wn>_CX>@2HM@dakSAh-}0008mNkltY6um3Kl1EffFuABz@FP!RaF2y1NfBdS}FaX8)KIlL?ZG6;3t4r0BI$p1uY}q z0c?42DSrT*0o?NajoPbWuT=xU3$s%uGmyox2cvLL zH__41PJKJg;dY{TdM^F$Vx$&`1+hD#-VCVN0HiG-%#4~B#0n!^c89G<^DUq*JHd&D z(J|9T_glqW(E##T(Vm%LMC>t>8fIcp>8Ob;GipT4fIQJMV^-{m-lN_==7|;Is-w%QfYmTl^DOof>p3kTH8V|V#=7X<5Vtp89Z*AN zLM7g$hL>5kqFFpun9*5gYMzxUfz9(EjBW$1y-6z!d73I9;AmyaM4p*E&uZyN8>Yn! zkWn+~fEm5T)d_Ms%M2=U!81X0o?*bHb<~@*^U_|-&`#Lb(e0qcj0GnZQ6Ij-=mEehnZEJp2<%s9ZdJ`|)5@ipB9*Mvsp3yVe2)jB8X7n&G zGmDIBCv*l$1*Dn-olY?N5Y3Ey5RpIJ<(zdjX7r^9{^nQ{fPixb9Px#32;bRa{vGf6951U69E94oEQKA00(qQO+^RU0tp8%4B*I_ZU6uP8FWQhbVF}# zZDnqB07G(RVRU6=Aa`kWXdp*PO;A^X4i^9b0hmcdK~y-)b(Bkz<1h?E-$U{Khv^Gq z7L*)!y2guCOba4Dl>GVm;rBDqew9$aN~fZZwM z(o?L^(IB=xJe-4j@G>#G=CFbxP@}bLzyuqpE(I7CY3boQE)r2GG6x`5j-ajW0tk!= z4^3Q+Xxgf!l<|u68Z^O*#B1bDNKku7ECbMry+-R2k#t0kV`$eeJsr9qCwl$@SO~{y zRARguPY)}ZWH-KJAp_=73`mlzG8?=D(N(7bNWwN<0lR8n5}+k+v}^kDdbaUq6bi1O z-u*3(IlYQj?LbcNQo$XjP0=c?qmfp2qwx6EGhXT}^`?-}ZXBMdvC+;WM$VUsDPZkd z;^6u#+E$qZ;?Z#8xQ7ibgE^`JTJMm*Pi{OT;fYL!Tn|0zFR$(tZsWQ6vzaf6JsqC` z{Y-R03i%xO=Vy%NaNWfV5(ej@)Wnk16ovB4 zk_-iRPv3y>Mm}+%qM4p9jv*e$-%dNoby$JNVZNWn-O9Ub{~rJQx$5@G=75apu}Pe} zPrO*Vf#aacJ`GMmre4vKdIm|21IzYxcT8F0#y0N&cf^(JjLEEBa_3et$26{FTJ0vr z%+Qk3vwdP#`wg!}tOY;Xj2X`AJgUEP@b^LOm+|Lc7d%^cjFG*L@kzz$rR#U<%}QU) sI_X^AUd|WaGXq@M4xEzR!T69lN?#_yc=kzSpd%SPUHx3vIVCg!0CT5m$p8QV literal 0 HcmV?d00001 diff --git a/data/themes/slv_units.png b/data/themes/slv_units.png new file mode 100644 index 0000000000000000000000000000000000000000..d935b3baaac7a8fbc2b642922a7f4065093cb5b9 GIT binary patch literal 812 zcmV+{1JnG8P)Px#32;bRa{vGf6951U69E94oEQKA00(qQO+^RU0tpBo7rwV4OaK4?8FWQhbVF}# zZDnqB07G(RVRU6=Aa`kWXdp*PO;A^X4i^9b0+~rfK~z}7)mdG0)G!QO*>VnO;Sckh zd4f`g>)E_G9i5P5=a{<$&19zaN4nmuR<=v9g8-nlhCPFb2te!4RiprT#{Q8z7SbK; zfTq5vx-;+r+-Z_3g(Z1|23Bf$(hxP z+Xg_gos7Ad=+9dihe%HTpQIvXQdE00n6{X;{+KmZ_vxS0Eq0g#pMO-;S;k38&5=S27HYk(-YS)kJ4@x4m!KRtN(S(x%D%M?kZq&> zt?}K4`kVjN#$Z;8K9M3XNs`z|zlFKVZn6Nkm1x?RouX;v|mo61;Pmi=n z_Npfbj#4_~|FYMJiq%Y%S>U9AKL;K?0~ixt9qoOJD1!-MItTG;6e@3g zb%4{XtK`o3t@c+9Few;kk(70C>qpI2lx!`?yDHm7c zS!DC`hRsqMNXD{7Z*!IevBhGYor<~orze$};xanAjW%2)Y`N$JwSX^T@aLU1zKBOA zX=6hsOF#K6N-8sZ>@?WFd%t^DSp=5sF`k4>7Q@H)2o}JlT&@_;dWA&vHM*3!bG#V} z$i4lYak)P^iS|oy2)Ji7A)PFMGl1U!h>cReUJJa4>jAnGI2u&mbARL|6={vvzM2;R z-vIpFQ6}rcE&yHu{OH)KPR=S=Mju%2$o4Go_3OV11yp@=B`YQ$;QCD};jKUCHSfsT q))I~tYqGxoBZ~%iA4dXy6@LIx9>A5|p=|L00000QL70(Y)*K0-AbW|YuPgga4q1L{p3r^AUjcwc6x=<11Hv2m#DP``d%8G=Se)KEX`|PX00Gze*@}}cXJ~P@jyZQdClx^O*633Q4wlL4}=R0iBvt){a?`NmTwXc7@P20@KkhA@Edg$NE zdCx@|1O#jD+lNNkax~58aB$H${V6WSM} zPp>!i-}^E6@)muD9GT-ctM<;*j=#U{?dxs1ic61VZLLb}k=359;`vFV<$wXtiA`@Z z=L^V&hEC-_%%I2;bA9U+S)J3n9?fB9uz3D4F4FJvm&T3>U<~WwH+9S44$rjF6*2UngI6GuR8z$ literal 0 HcmV?d00001 diff --git a/data/themes/sp_bt_r.png b/data/themes/sp_bt_r.png new file mode 100644 index 0000000000000000000000000000000000000000..bef2c54130b4f17b32a129e6638d24158f9a1c1d GIT binary patch literal 369 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`jKx9jP7LeL$-D$|*pj^6T^Rm@ z;DWu&Cj&(|3p^r=85p>QL70(Y)*K0-AbW|YuPgga4q1L{=A(?as)0h1C9V-A&iT2y zsd*&~&PAz-C8;S2<(VZJ3hti10pX2&;y^`bJY5_^EKYBoWXRPVAmH+S`A4B9i6YME zw_n*jMK3)SxYgB~^xpDPgvR|-hYm5fOyJ;Zy2TNHS4P3L;ONWr8QZNHs!wjxIs4hB z_0{ytCV#J#o@HbZn7Fpcy019@w%G1QXW`CF}hOJYUL+y$?H?Odfb z=egwUWt9N|D)+xH&YV>cDW-G!lb56A(ZWA2E+S4mmGk~Dkol)-aO_0zgeHZK76B8M z!v=cMeJj!;-Rc+T-k#mAqVD-g&0mt?fQj$f(pc7S*ThZICvADP^xq_)zZg7S{an^L HB{Ts5jIoQ( literal 0 HcmV?d00001 diff --git a/data/themes/thumb_shadow.png b/data/themes/thumb_shadow.png new file mode 100644 index 0000000000000000000000000000000000000000..8e666708f86ef5eb9357a015530b8f278cd6155a GIT binary patch literal 1087 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 literal 0 HcmV?d00001 diff --git a/data/themes/toolbar_separator_v.png b/data/themes/toolbar_separator_v.png new file mode 100644 index 0000000000000000000000000000000000000000..cb2da6fc3a866b7d011c07db827d432dfef3e6e4 GIT binary patch literal 166 zcmeAS@N?(olHy`uVBq!ia0vp^%s?!_!3HERXC3VVQjEnx?oJHr&dIz4a@dl*-CY>| zgW!U_%O?XxI14-?iy0WWg+Z8+Vb&Z8pdfpRr>`sf4Gtj=Mmf=Yd)ESm)I41rLpZJ{ zCp0irvH^jc#Pk3E|MU6qcqCjX{s&}EXl!g`WLPcBUcNv>s0^rs!PC{xWt~$(69D=U BEY98V;rIo4AyWyw>+ zs7x+X?WnY~ayxo5jAbp05{XF{XZ;)JeV+I8KJVxGyuZEA^C=0y`|9eL=>Pzri}Uj# zs5I*rH)yG*YaDV|C6EknT<``J=o{jSReocdUwDS<{`D`adD~R|N^A$QVPH^dJeV0n zqX3zinGOjl)Qs4eG>Sti?PS$F$_xNBmvKJm;H>J8S9@sVhmDK$y>u9RpHwg?M;?GO z`Re6KEWz6KE>(_XmX+cexga^av}T%ny|m3r9pXEJ&}5}VE)aLzc1 zp6+9K)=Hl4UYwLUFs*U(sA4GeQ6WEWe7^?S=+*2eVcsD5`(q^$>#OPe1kV1F3CJf+ z37pWWxle3%4x@4+?&z)QZDQt+8%D&~peF9SXc&k|^GPvFprAikee1hvSlV7Gw@S`n zmb>YhYtRb$f%R>4c($h^CHzRl9cEt(41r@pgj9ig%}6@&X1hB&0!*rgukVyBC*E}i zQpP`yx2v1uv`z?i_YhJHT(rvT49&-kz-jrVvos~fzT@? z{X`IuJzh%=0#|qK6MREAgf<|HBiV}t-Rdh|^;u2Bc1HGc4?^XGZwH=qCl*tg-6iho zLavw>qPEI#2-xB(!Vflt!NcJD{6vG#=@9AW#})P>(!1BbxDFpDDpOT5n1F-fM;z@&5y+o;``U*?~C7qZdevYyHoIK#|+e@ zRP)`^*Uu{SE-x>q0zcIP)H@DW%<3Hfrx((swYJIB%1M@}VC~dcRXa}0&;9xRt7GaU z-_>0qxvWd#XWgYM=Ot17ot|oR^##X*fm7CwLl<75Tm4^s?JCtfID;BkS`sH6?$m#g zggo?e={r<{vOx|-T3s<;wm#~ijHiU-8~%O2YyNCfj9U%cUbNAzGp5YjgTuw@!(8gK z_I7aR{*0aPt)Ofl6E>SbbB|RrVoP_>1cgx3&x^s1PR+2s$qi58Bx5>#f)_k7$L8h! zFe!nWu2J-NCxe^y_C{GkoiP`+`lO@6GgVOiL#|`Ixm!|MECK-~mSF_X>Y`-@w#C-yTL*C86gnEaXbl7RRzcc4& zl`zs}ro7>fwsf$g6D!-}7R8Kg`@q7`UNcJB9VhHf&UI+tD|$*ktLo*TseKUN#QiU+ z!Ftt-cSuNx>C#tvc5#(u?~9owipm0eKxSbJiQx+{PaiU@oITO}dw%}+)y0_ysZ+J? zxoaTm>al%hWqRrUQ||q){QPx`7E;d%5{Z;|n=_jUzzQ5kjdM5sW}#i@g~)(NAzoV2 zK;k8}YPBpTMJz%M42bSkkNmNtAExxX*6`5gd?SbBP@U1DDr}mr^q`qAs`ctS%WO=V z-~8?7rsg1!jggb{T|7cw7mmSuvv|!r10#uB-RkOCPrAPEZ&Ff9nJU; DeSG%l literal 0 HcmV?d00001 diff --git a/data/themes/tooltip-corner-bottom-left-tip.png b/data/themes/tooltip-corner-bottom-left-tip.png new file mode 100644 index 0000000000000000000000000000000000000000..f60787b3e9589ab3ff88b1645207790682f797b4 GIT binary patch literal 440 zcmeAS@N?(olHy`uVBq!ia0vp^d?3uh1|;P@bT0xa#^NA%Cx&(BWL^R}Y)RhkE)4%c zaKYZ?lYt_f1s;*bK<(E-n9)gNb_Gz7y~NYkmHiec55JaPL)f`rKq1-8kcblJ{M_8s zyb>Unfx)>bHL)Z$MWH;iBtya7(>EYRFO?l=9lxiGV~EE2xf3>e9dQtGeSe#CCTHV` zklB|Gol{#YKSA%HPKU1xOZ~z7AB@FrXHF5YS8VlFc&XFktEH&rmhyPBkdwomiic&- zKU7SgA^BK9FyBo2&s5fbGmk#GwebD#^_yKapT5l6I%%`((kqc7uHSSfc6{s1kYqWy zN4`}+y-XC%ZKf;69oX?|U}wNAh(hS6e1(`BIsZ-)5{c{6`j cUJu>R=&4g`kh1(w2Pn)uUHx3vIVCg!0M*E_CjbBd literal 0 HcmV?d00001 diff --git a/data/themes/tooltip-corner-bottom-right-tip.png b/data/themes/tooltip-corner-bottom-right-tip.png new file mode 100644 index 0000000000000000000000000000000000000000..4d715f38d9ee9a991358c52f4a08bf36abc7042f GIT binary patch literal 441 zcmeAS@N?(olHy`uVBq!ia0vp^d?3uh1|;P@bT0xa#^NA%Cx&(BWL^R}Y)RhkE)4%c zaKYZ?lYt_f1s;*bK<(E-n9)gNb_Gz7y~NYkmHiec55Kmdi0damppa~4NJNQqer|4R zUI~!Pz~Eeznpl#WqEMb$lA+-4=^K!um&y*bPQcT}F+}71)Jq$^jyMRgJ*YQo%dsig zY<4dbP0l+XkKh7_uy literal 0 HcmV?d00001 diff --git a/data/themes/tooltip-corner-top-left-tip.png b/data/themes/tooltip-corner-top-left-tip.png new file mode 100644 index 0000000000000000000000000000000000000000..3f74c585c1999acd7ad65b8e33fa1915b79801e3 GIT binary patch literal 452 zcmeAS@N?(olHy`uVBq!ia0vp^d?3uh1|;P@bT0xa#^NA%Cx&(BWL^R}Y)RhkE)4%c zaKYZ?lYt_f1s;*bK<(E-n9)gNb_Gz7y~NYkmHiec55G3snjhhgKq1-8kcblJ{M_8s zyb>Unfx)>bHL)Z$MWH;iBtya7(>EYRFO?l=owTQmV~EE2sh2i-IVDOQ`}qI5_&nkC z3+q*nw{6Qi7JE*F<=s7p@<&Ps7e3^Xe8kG)>#AXKWl=>*ck-j~6}G-jj#HkurdPDf z^Y7Wiwu8a0A==ZDRgJGHLAGsS`MJBy(+_m2{Np-MDA6W=_+h}>Fz>BVxq_}2FIj%i zS)0qWe7}>Y#dEpaZ?|pI37(cJ)$8Up$)!-{x7X558q-g&cNB$b@C*Z+#W zOEa3e;_}NC7c*+YR$sMLaBvekHpBS&oy!RZ9p7xvFg7fiem3p%wfEmOSs24shhBPH zcD;4s_kU`>ms1ltYsGy*^Q6pZ%S994 zg_*acPrhB);n=lkh34r`A2;wbc`9`++V}qV^uUB^sR}z)f7)^NJg&HJa`y85+X@9c pW47hqw(Do>USy&A(@M%_S^n1Blly19m#+r}pr@;!%Q~loCIIg;x~KpE literal 0 HcmV?d00001 diff --git a/data/themes/tooltip-edge-bottom-tip.png b/data/themes/tooltip-edge-bottom-tip.png new file mode 100644 index 0000000000000000000000000000000000000000..49fd2b032fda446dd0d42c8808fe3f6bfa34f34a GIT binary patch literal 471 zcmeAS@N?(olHy`uVBq!ia0vp^d?3uh1|;P@bT0xa#^NA%Cx&(BWL^R}Y)RhkE)4%c zaKYZ?lYt_f1s;*bK<(E-n9)gNb_Gz7y~NYkmHiec55I}P)Ur2yKq1-8kcblJ{M_8s zyb>Unfx)>bHL)Z$MWH;iBtya7(>EYRFO?l=ot~$QV~EE2xo0{e(ANIdm?l$WSDGuy=$eU>&3qrCS8XOY`ClU&WqEV z-mKB}ip^7^?cvp|tRNVL)8@SQmTTKpgoPPA_8lwyBgk^_`^xNn@7Hg; z{Z{xSi#5w6hJfio>(Vz%P7PvTfB${3*H6v^x4!S^_VmzXe_K{P+4b|!IajkvSsy6g zmUCb*UmB#zd$@pq_uY5lOM@y;m;G1p6zO)|e=}#9m!_YZ@U3lY8Sl((WmwlDkYypW z>1tM{;*rnypK07lJYOgit2bSk;kvlh_XcR#%=`79(Lu_pjz!~m5hzGKUHx3v IIVCg!0HCqH8vpTWd~ZP>FMGaqH(@=(tfWa4g$x@H{aa*M&2yl zVy)=AoJA8Zy^`A9vczVGT88i%l~4tiH71Qe7`VR6R0^JzmU+gz=J>H@(Ve?_YR;bd z)AqCNAVWhR>#-kqKJPid@BLN1^xg)O=X(U41dQ`#890`HX)NB?yXeKb*H(Gg-r8PR z8$Uv8$9Jxj>K-zzw9D zezT$c_BMIVrRO~-U0Ahh&dr>*V=ZSTqB#{aWR5RZEWQds`kkA8%UjwKBZr!YZB9p0k#TDL%2t;Ms94Du3DKm!Y?}743}q zm&?%5?8KoObZWgt-~RT*hPfY3sPF$^^ZsznC;2@abGu9Tf4&C_O;1-pmvv4FO#ng1 B#qajnsGE}=k6tKU*29~ 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 + DaveMDS Andreoli + + Supported Browsers: + ie7, opera9, konqueror4 and firefox3 + + Please use a different file for ie6, ie5, etc. hacks. +*/ + + +/* Necessary to place the footer at the bottom of the page */ +html, body { + height: 100%; + margin: 0px; + padding: 0px; +} + +#container { + min-height: 100%; + height: auto !important; + height: 100%; + margin: 0 auto -53px; +} + +#footer, #push { + height: 53px; +} + + +* html #container { + height: 100%; +} + +/* Prevent floating elements overflowing containers */ +.clear { + clear: both; + width: 0px; + height: 0px; +} + +/* Flexible & centered layout from 750 to 960 pixels */ +.layout { + max-width: 960px; + min-width: 760px; + margin-left: auto; + margin-right: auto; +} + +body { + /*font-family: Lucida Grande, Helvetica, sans-serif;*/ + font-family: "Bitstream Vera","Vera","Trebuchet MS",Trebuchet,Tahoma,sans-serif +} + +/* Prevent design overflowing the viewport in small resolutions */ +#container { + padding-right: 17px; + padding-left: 17px; + background-image: url(head_bg.png); + background-repeat: repeat-x; +} + +/****************************/ +/* Top main menu */ +/****************************/ +#header_logo { + background-image : url(logo.png); + width : 61px; +} + +#header_logo a { + position : absolute; + border : 0px; + background-color : transparent; + top : 0px; + width : 60px; + height : 60px; +} + +#header_menu { + background-image : url(header_menu_background.png); + font : normal 10pt verdana,'Bitstream Vera Sans',helvetica,arial,sans-serif; + text-align : right; +} + +#header_last { + background-image : url(header_menu_background_last.png); + width : 15px; +} + +td.nav_passive { + background : url(header_menu_unselected_background.png) 0 0 no-repeat; + height : 63px; + font-family : "Bitstream Vera","Vera","Trebuchet MS",Trebuchet,Tahoma,sans-serif; + font-size : 11px; + padding : 20px 10px 20px 10px; + vertical-align : middle; +} + +td.nav_active { + background : url(header_menu_current_background.png) 0 0 no-repeat; + height : 63px; + color : #646464; + font-family : "Bitstream Vera","Vera","Trebuchet MS",Trebuchet,Tahoma,sans-serif; + font-size : 11px; + font-weight : bold; + padding : 20px 10px 20px 10px; + vertical-align : middle; +} + +#header_menu a { + display : block; + text-decoration : none; + cursor : pointer; + color : #cdcdcd; +} + + + +#header { + width: 100%; + height: 102px; +} + +#header h1 { + width: 63px; + height: 63px; + position: absolute; + margin: 0px; +} + +#header h1 span { + display: none; +} + +#header h2 { + display: none; +} + +/* .menu-container is used to set properties common to .menu and .submenu */ +#header .menu-container { +} + +#header .menu-container ul { + list-style-type: none; + list-style-position: inside; + margin: 0; +} + +#header .menu-container li { + display: block; + float: right; +} + +#header .menu { + height: 63px; + display: block; + background-image: url(menu_bg.png); + background-repeat: repeat-x; +} + +#header .menu ul { + height: 100%; + display: block; + background-image: url(menu_bg_last.png); + background-repeat: no-repeat; + background-position: top right; + padding-right: 17px; +} + +#header .menu li { + height: 100%; + text-align: center; + background-image: url(menu_bg_unsel.png); + background-repeat: no-repeat; +} + +#header .menu a { + height: 100%; + display: block; + color: #cdcdcd; + text-decoration: none; + font-size: 10pt; + line-height: 59px; + text-align: center; + padding: 0px 15px 0px 15px; +} + +#header .menu li:hover { + background-image: url(menu_bg_hover.png); + background-repeat: no-repeat; +} + +#header .menu li:hover a { + color: #FFFFFF; +} + +#header .menu li.current { + background-image: url(menu_bg_current.png); + background-repeat: no-repeat; +} + +#header .menu li.current a { + color: #646464; +} + + +/* Hide all the submenus but the current */ +#header .submenu ul { + display: none; +} + +#header .submenu .current { + display: block; +} + +#header .submenu { + font: bold 10px verdana,'Bitstream Vera Sans',helvetica,arial,sans-serif; + margin-top: 10px; +} + +#header .submenu a { + color: #888888; + text-decoration: none; + font-size: 0.9em; + line-height: 15px; + padding:0px 5px 0px 5px; +} + +#header .submenu a:hover { + color: #444444; +} + +#header .submenu li { + border-left: 1px solid #DDDDDD; +} + +#header .submenu li:last-child { + border-left: 0; +} + +#header .doxytitle { + position: absolute; + font-size: 1.8em; + font-weight: bold; + color: #444444; + line-height: 35px; +} + +#header small { + font-size: 0.4em; +} + +#footer { + background-image: url(foot_bg.png); + width: 100%; +} + +#footer table { + width: 100%; + text-align: center; + white-space: nowrap; + padding: 5px 30px 5px 30px; + font-size: 0.8em; + font-family: "Bitstream Vera","Vera","Trebuchet MS",Trebuchet,Tahoma,sans-serif; + color: #888888; +} + +#footer td.copyright { + width: 100%; +} + diff --git a/doc/elementary.dox.in b/doc/elementary.dox.in new file mode 100644 index 0000000..f91c12e --- /dev/null +++ b/doc/elementary.dox.in @@ -0,0 +1,62 @@ +/** +@file elementary.dox +@brief Elementary Widget Library +*/ + +/** +@mainpage Elementary +@image html elementary.png +@version @PACKAGE_VERSION@ +@author Carsten Haitzler +@author Gustavo Sverzut Barbieri +@author Cedric Bail +@author Vincent Torri +@author Daniel Kolesa +@author Jaime Thomas +@author Swisscom - http://www.swisscom.ch/ +@author Christopher Michael +@author Marco Trevisan (Treviño) +@author Michael Bouchaud +@author Jonathan Atton (Watchwolf) +@author Brian Wang +@author Mike Blumenkrantz (zmike) +@author Samsung Electronics +@author Samsung SAIT +@author Brett Nash +@author Bruno Dilly +@author Rafael Fonseca +@author Chuneon Park +@author Woohyun Jung +@author Jaehwan Kim +@author Wonguk Jeong +@author Leandro A. F. Pereira +@author Helen Fornazier +@author Gustavo Lima Chaves +@author Fabiano Fidêncio +@author Tiago Falcão +@author Otavio Pontes +@author Viktor Kojouharov +@author Daniel Juyung Seo (SeoZ) +@date 2008-2010 + +@section intro What is Elementary? + +This is a VERY SIMPLE toolkit. It is not meant for writing extensive desktop +applications (yet). Small simple ones with simple needs. + +It is meant to make the programmers work almost brainless but give them lots +of flexibility. + +License: LGPL v2 (see COPYING in the base of Elementary's source). This +applies to all files in the source here. + +Acknowledgements: There is a lot that goes into making a widget set, and +they don't happen out of nothing. It's like trying to make everyone +everywhere happy, regardless of age, gender, race or nationality - and +that is really tough. So thanks to people and organisations behind this, +aslisted in the Authors section above. + +@verbatim +Pants +@endverbatim +*/ diff --git a/doc/foot.html b/doc/foot.html new file mode 100644 index 0000000..d43cf8f --- /dev/null +++ b/doc/foot.html @@ -0,0 +1,18 @@ + +

    + + + + + + + + + + + diff --git a/doc/head.html b/doc/head.html new file mode 100644 index 0000000..7e20e6d --- /dev/null +++ b/doc/head.html @@ -0,0 +1,68 @@ + + + $title + + + + + + + + + + + + + + +
    + + + +
    +
    diff --git a/doc/img/edoxy.css b/doc/img/edoxy.css new file mode 100644 index 0000000..311ca23 --- /dev/null +++ b/doc/img/edoxy.css @@ -0,0 +1,486 @@ +/* + * This file contain a custom doxygen style to match e.org graphics + */ + + + +/* BODY,H1,H2,H3,H4,H5,H6,P,CENTER,TD,TH,UL,DL,DIV { + font-family: Geneva, Arial, Helvetica, sans-serif; +}*/ +BODY, TD { + font-size: 12px; +} +H1 { + text-align: center; + font-size: 160%; +} +H2 { + font-size: 120%; +} +H3 { + font-size: 100%; +} +CAPTION { + font-weight: bold +} +DIV.qindex { + width: 100%; + background-color: #e8eef2; + border: 1px solid #84b0c7; + text-align: center; + margin: 2px; + padding: 2px; + line-height: 140%; +} +DIV.navpath { + width: 100%; + background-color: #e8eef2; + border: 1px solid #84b0c7; + text-align: center; + margin: 2px; + padding: 2px; + line-height: 140%; +} +DIV.navtab { + background-color: #e8eef2; + border: 1px solid #84b0c7; + text-align: center; + margin: 2px; + margin-right: 15px; + padding: 2px; +} +TD.navtab { + font-size: 70%; +} +A.qindex { + text-decoration: none; + font-weight: bold; + color: #1A419D; +} +A.qindex:visited { + text-decoration: none; + font-weight: bold; + color: #1A419D +} +A.qindex:hover { + text-decoration: none; + background-color: #ddddff; +} +A.qindexHL { + text-decoration: none; + font-weight: bold; + background-color: #6666cc; + color: #ffffff; + border: 1px double #9295C2; +} +A.qindexHL:hover { + text-decoration: none; + background-color: #6666cc; + color: #ffffff; +} +A.qindexHL:visited { + text-decoration: none; + background-color: #6666cc; + color: #ffffff +} +A.el { + text-decoration: none; + font-weight: bold +} +A.elRef { + font-weight: bold +} +A.code:link { + text-decoration: none; + font-weight: normal; + color: #0000FF +} +A.code:visited { + text-decoration: none; + font-weight: normal; + color: #0000FF +} +A.codeRef:link { + font-weight: normal; + color: #0000FF +} +A.codeRef:visited { + font-weight: normal; + color: #0000FF +} +A:hover, A:visited:hover { + text-decoration: none; + /* background-color: #f2f2ff; */ + color: #000055; +} +A.anchor { + color: #000; +} +DL.el { + margin-left: -1cm +} +.fragment { + font-family: monospace, fixed; + font-size: 95%; +} +PRE.fragment { + border: 1px solid #CCCCCC; + background-color: #f5f5f5; + margin-top: 4px; + margin-bottom: 4px; + margin-left: 2px; + margin-right: 8px; + padding-left: 6px; + padding-right: 6px; + padding-top: 4px; + padding-bottom: 4px; +} +DIV.ah { + background-color: black; + font-weight: bold; + color: #ffffff; + margin-bottom: 3px; + margin-top: 3px +} + +DIV.groupHeader { + margin-left: 16px; + margin-top: 12px; + margin-bottom: 6px; + font-weight: bold; +} +DIV.groupText { + margin-left: 16px; + font-style: italic; + font-size: 90% +} +/*BODY { + background: white; + color: black; + margin-right: 20px; + margin-left: 20px; +}*/ +TD.indexkey { + background-color: #e8eef2; + font-weight: bold; + padding-right : 10px; + padding-top : 2px; + padding-left : 10px; + padding-bottom : 2px; + margin-left : 0px; + margin-right : 0px; + margin-top : 2px; + margin-bottom : 2px; + border: 1px solid #CCCCCC; +} +TD.indexvalue { + background-color: #e8eef2; + font-style: italic; + padding-right : 10px; + padding-top : 2px; + padding-left : 10px; + padding-bottom : 2px; + margin-left : 0px; + margin-right : 0px; + margin-top : 2px; + margin-bottom : 2px; + border: 1px solid #CCCCCC; +} +TR.memlist { + background-color: #f0f0f0; +} +P.formulaDsp { + text-align: center; +} +IMG.formulaDsp { +} +IMG.formulaInl { + vertical-align: middle; +} +SPAN.keyword { color: #008000 } +SPAN.keywordtype { color: #604020 } +SPAN.keywordflow { color: #e08000 } +SPAN.comment { color: #800000 } +SPAN.preprocessor { color: #806020 } +SPAN.stringliteral { color: #002080 } +SPAN.charliteral { color: #008080 } +SPAN.vhdldigit { color: #ff00ff } +SPAN.vhdlchar { color: #000000 } +SPAN.vhdlkeyword { color: #700070 } +SPAN.vhdllogic { color: #ff0000 } + +.mdescLeft { + padding: 0px 8px 4px 8px; + font-size: 80%; + font-style: italic; + background-color: #FAFAFA; + border-top: 1px none #E0E0E0; + border-right: 1px none #E0E0E0; + border-bottom: 1px none #E0E0E0; + border-left: 1px none #E0E0E0; + margin: 0px; +} +.mdescRight { + padding: 0px 8px 4px 8px; + font-size: 80%; + font-style: italic; + background-color: #FAFAFA; + border-top: 1px none #E0E0E0; + border-right: 1px none #E0E0E0; + border-bottom: 1px none #E0E0E0; + border-left: 1px none #E0E0E0; + margin: 0px; +} +.memItemLeft { + padding: 1px 0px 0px 8px; + margin: 4px; + border-top-width: 1px; + border-right-width: 1px; + border-bottom-width: 1px; + border-left-width: 1px; + border-top-color: #E0E0E0; + border-right-color: #E0E0E0; + border-bottom-color: #E0E0E0; + border-left-color: #E0E0E0; + border-top-style: solid; + border-right-style: none; + border-bottom-style: none; + border-left-style: none; + background-color: #FAFAFA; + font-size: 80%; +} +.memItemRight { + padding: 1px 8px 0px 8px; + margin: 4px; + border-top-width: 1px; + border-right-width: 1px; + border-bottom-width: 1px; + border-left-width: 1px; + border-top-color: #E0E0E0; + border-right-color: #E0E0E0; + border-bottom-color: #E0E0E0; + border-left-color: #E0E0E0; + border-top-style: solid; + border-right-style: none; + border-bottom-style: none; + border-left-style: none; + background-color: #FAFAFA; + font-size: 80%; +} +.memTemplItemLeft { + padding: 1px 0px 0px 8px; + margin: 4px; + border-top-width: 1px; + border-right-width: 1px; + border-bottom-width: 1px; + border-left-width: 1px; + border-top-color: #E0E0E0; + border-right-color: #E0E0E0; + border-bottom-color: #E0E0E0; + border-left-color: #E0E0E0; + border-top-style: none; + border-right-style: none; + border-bottom-style: none; + border-left-style: none; + background-color: #FAFAFA; + font-size: 80%; +} +.memTemplItemRight { + padding: 1px 8px 0px 8px; + margin: 4px; + border-top-width: 1px; + border-right-width: 1px; + border-bottom-width: 1px; + border-left-width: 1px; + border-top-color: #E0E0E0; + border-right-color: #E0E0E0; + border-bottom-color: #E0E0E0; + border-left-color: #E0E0E0; + border-top-style: none; + border-right-style: none; + border-bottom-style: none; + border-left-style: none; + background-color: #FAFAFA; + font-size: 80%; +} +.memTemplParams { + padding: 1px 0px 0px 8px; + margin: 4px; + border-top-width: 1px; + border-right-width: 1px; + border-bottom-width: 1px; + border-left-width: 1px; + border-top-color: #E0E0E0; + border-right-color: #E0E0E0; + border-bottom-color: #E0E0E0; + border-left-color: #E0E0E0; + border-top-style: solid; + border-right-style: none; + border-bottom-style: none; + border-left-style: none; + color: #606060; + background-color: #FAFAFA; + font-size: 80%; +} +.search { + color: #003399; + font-weight: bold; +} +FORM.search { + margin-bottom: 0px; + margin-top: 0px; +} +INPUT.search { + font-size: 75%; + color: #000080; + font-weight: normal; + background-color: #e8eef2; +} +TD.tiny { + font-size: 75%; +} +a { + color: #1A41A8; +} +a:visited { + color: #2A3798; +} +.dirtab { + padding: 4px; + border-collapse: collapse; + border: 1px solid #84b0c7; +} +TH.dirtab { + background: #e8eef2; + font-weight: bold; +} +HR { + height: 1px; + border: none; + border-top: 1px solid black; +} + +/* Style for detailed member documentation */ +.memtemplate { + font-size: 80%; + color: #606060; + font-weight: normal; + margin-left: 3px; +} +.memnav { + background-color: #eeeeee; + border: 1px solid #dddddd; + text-align: center; + margin: 2px; + margin-right: 15px; + padding: 2px; +} +.memitem { + padding: 4px; + background-color: #eeeeee; + border-width: 1px; + border-style: solid; + border-color: #dddddd; + -moz-border-radius: 4px 4px 4px 4px; +} +.memname { + white-space: nowrap; + font-weight: bold; + color: #ffffff; +} +.memdoc{ + padding-left: 10px; +} +.memproto { + background-color: #111111; + width: 100%; + border-width: 1px; + border-style: solid; + border-color: #000000; + font-weight: bold; + -moz-border-radius: 4px 4px 4px 4px; +} +.paramkey { + text-align: right; + color: #ffffff; +} +.paramtype { + white-space: nowrap; + color: #aaaaaa; +} +.paramname { + color: #ff0000; + font-style: italic; + white-space: nowrap; +} +/* End Styling for detailed member documentation */ + +/* for the tree view */ +.ftvtree { + font-family: sans-serif; + margin:0.5em; +} +/* these are for tree view when used as main index */ +.directory { + font-size: 9pt; + font-weight: bold; +} +.directory h3 { + margin: 0px; + margin-top: 1em; + font-size: 11pt; +} + +/* The following two styles can be used to replace the root node title */ +/* with an image of your choice. Simply uncomment the next two styles, */ +/* specify the name of your image and be sure to set 'height' to the */ +/* proper pixel height of your image. */ + +/* .directory h3.swap { */ +/* height: 61px; */ +/* background-repeat: no-repeat; */ +/* background-image: url("yourimage.gif"); */ +/* } */ +/* .directory h3.swap span { */ +/* display: none; */ +/* } */ + +.directory > h3 { + margin-top: 0; +} +.directory p { + margin: 0px; + white-space: nowrap; +} +.directory div { + display: none; + margin: 0px; +} +.directory img { + vertical-align: -30%; +} +/* these are for tree view when not used as main index */ +.directory-alt { + font-size: 100%; + font-weight: bold; +} +.directory-alt h3 { + margin: 0px; + margin-top: 1em; + font-size: 11pt; +} +.directory-alt > h3 { + margin-top: 0; +} +.directory-alt p { + margin: 0px; + white-space: nowrap; +} +.directory-alt div { + display: none; + margin: 0px; +} +.directory-alt img { + vertical-align: -30%; +} + diff --git a/doc/img/elementary.png b/doc/img/elementary.png new file mode 100644 index 0000000000000000000000000000000000000000..79754891f19704929cf6198da9c17f7f12a7601b GIT binary patch literal 7313 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 GLK6Ub>Mc;VkfoEM{Qf z76xHPhFNnYfP(BLp1!W^H+WcuRXD>A=l%i;Wq7(chG?8W+i%Esz<`6f_y7NWHH!5o z63R1{^0cb0vMSkFaE_%x<+7O{*?Xs&Ff%xKT5jO&GtAqcqoa~}b>qg&H07ky z617wnX2HUfTT*8{kPx#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iOZ8 z6%`IG`XD&~00I3;L_t(o!^Kz8j>8}fODg_+AF{uksuh}hxC0rJP`W$mkkHl^jB%XM z>f`Y+`Dtd>`gxwMmr`2KIk$cshdiH8N#}XW6$o}5WA?p%5)sKc%eHO9fR!#HlFUqU z&XQ6Z1~3DUmCHm#rjx?$lu|lm24QA+Eh4g2CJ}X<;QbGo;J_$CohD|s1Tu}z3KIrH zRtpQ8-Z|UyQP4caCB~&Z3QG0mMzcQLYIcQ!(sFW-xf9knF@|(?iY~XAOhHzd%#8OD2m>x}XSSsVf@;^obfpX48<@ZgFF$M4@xtjbM#B=Ojp!9yfFNKXj22K7STvD?00000NkvXXu0mjfB76)l literal 0 HcmV?d00001 diff --git a/doc/img/header_menu_current_background.png b/doc/img/header_menu_current_background.png new file mode 100644 index 0000000000000000000000000000000000000000..de97c9268e4ac68310c8b92d6ab6bd8a245611da GIT binary patch literal 1200 zcmV;h1W)^kP)002J-1^@s6XaB>y00001b5ch_0Itp) z=>Px#32;bRa{vGf6951U69E94oEQKA00(qQO+^RT3Fc5TrKj#zpOzs?z2=A0p@aw&u*pMn|G)ug+?Vh;0+zHe5dVLoF=!DBW&zJ?E zp99|S_j0@4%Io#|xG+sqdB5NP{rn5Cj%O+78UIn|DpKcsK9>`B2V6JsOB3oD&r;4a z{-e%Sw9ela{A&{jdu5*U-Tgr1~ zQc-ZvZCmQQrCnTG+COg8zWQ3Lv1sjNIKQPlR|Xsq_}(oT0MbDS91lPg3>xeBFKokrh3I+f~!N36>5GNtP zFb=56FWNP#oK=?bNEQ~!rtXW9X1GX=k~FL`OjOeF$R)LGB-wAZi(5xddgID^{pUl5 z$!2zVWE!iC5c%CAFL=jfl{TW1M$7Wjcr9z}SyPKmlC20r0B}G6Q80PClsJ^eQ9Rdb zuHflIJ5saoBdvW)J5o7`LrQ$sb0li*FS@pt^@$vLe#kJ^<1ntHwKLacEE8!V_VYY{ z^jk0Fa-9o0ILfhhgnDcg*`~%yk#UNgFLkMLQ1xp&>oHLMt>=krgKLZ9aoj&)eVyWk z+VI9yb#%knV zBgOT1iW^1q->g9a$6utrxv^4Ql-s5#yS%xS5>LwpJyaYZ1w-06F426k%%gi2p;YTL zn*Zi$*TU&q<}Gq{z5F%GPa}Dt9$}k233)sorIb>h&nNZ+VE-)`LNtIN1b_p=0f8Pk zSwvore6GJZg3A%uh&UU`%8A$z3ApNcvGym`^9BW5y;mkO7OVYaI#wj=im2;bzSt*w z8j*3rXhhk-tiA%ik?Y6P7yM_$}>d^Cl%aa8a!%A!J=gv)gqCjA%RAmjShY zk&jin$jBj)wrhPzE#o_v^@kLW;DnK~k;Uxogc+{8mlL+=3tKP%4hR4$2Lynj z95C}RO)LJ$<@I?2i7h|tH#%lcU&}tk-(ol0<1_foFDdWsgqjV%=7cRA;M<%KLNw4f z2!R6vT{&RuTk7799C>JZ4;!>{ThW;;ZOYD_SA%VO2ZR&C3B68;Eg1NXEf@e0gaF^` zfS#=57JO;X{zkCF($|*uL^8|wn48N;fkQ7R9I3CpA0+QRH%LYRy5b)R!`g7p731Il O0000002J-1^@s6XaB>y00001b5ch_0Itp) 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 +Vendor: %{?_vendorinfo:%{_vendorinfo}}%{!?_vendorinfo:The Enlightenment Project (http://www.enlightenment.org/)} +Distribution: %{?_distribution:%{_distribution}}%{!?_distribution:%{_vendor}} +#BuildSuggests: xorg-x11-devel, vim-enhanced +BuildRequires: evas-devel +Requires: evas +BuildRoot: %{_tmppath}/%{name}-%{version}-root + +%description +Elementary is a widget set. It is a new-style of widget set much more canvas +object based than anything else. Why not ETK? Why not EWL? Well they both +tend to veer away from the core of Evas, Ecore and Edje a lot to build their +own worlds. Also I wanted something focused on embedded devices - +specifically small touchscreens. Unlike GTK+ and Qt, 75% of the "widget set" +is already embodied in a common core - Ecore, Edje, Evas etc. So this +fine-grained library splitting means all of this is shared, just a new +widget "personality" is on top. And that is... Elementary, my dear watson. +Elementary. + +%package devel +Summary: Elementary headers, static libraries, documentation and test programs +Group: System Environment/Libraries +Requires: %{name} = %{version}, %{name}-bin = %{version} +Requires: evas-devel + +%description devel +Headers, static libraries, test programs and documentation for Elementary + +%package bin +Summary: Elementary file compiler/decompiler suite +Group: System Environment/Libraries +Requires: %{name} = %{version} +Requires: elementary + +%description bin +Elmementary programs + +%prep +%setup -q + +%build +%{configure} --prefix=%{_prefix} +%{__make} %{?_smp_mflags} %{?mflags} + +%install +%{__make} %{?mflags_install} DESTDIR=$RPM_BUILD_ROOT install +test -x `which doxygen` && sh gendoc || : + +%post +/sbin/ldconfig || : + +%postun +/sbin/ldconfig || : + +%clean +test "x$RPM_BUILD_ROOT" != "x/" && rm -rf $RPM_BUILD_ROOT + +%files +%defattr(-, root, root) +%doc AUTHORS COPYING README +%{_libdir}/libelementary*.so.* + +%files devel +%defattr(-, root, root) +%doc doc/html +%{_libdir}/*.so +%{_libdir}/*.la +%{_libdir}/*.a +%{_libdir}/edje/*.so +%{_libdir}/edje/*.la +%{_libdir}/elementary/modules/test_entry/*/module.* +%{_libdir}/pkgconfig/* +%{_includedir}/*.h +%{_includedir}/elementary/*.h + +%files bin +%defattr(-, root, root) +%{_bindir}/* +%{_datadir}/applications/*.desktop +%{_datadir}/elementary/config/*.cfg +%{_datadir}/elementary/config/default/* +%{_datadir}/elementary/config/illume/* +%{_datadir}/elementary/config/standard/* +%{_datadir}/elementary/edje_externals/* +%{_datadir}/elementary/images/* +%{_datadir}/elementary/objects/* +%{_datadir}/elementary/themes/* +%{_datadir}/icons/elementary.png + +%changelog diff --git a/m4/ac_attribute.m4 b/m4/ac_attribute.m4 new file mode 100644 index 0000000..23479a9 --- /dev/null +++ b/m4/ac_attribute.m4 @@ -0,0 +1,47 @@ +dnl Copyright (C) 2004-2008 Kim Woelders +dnl Copyright (C) 2008 Vincent Torri +dnl That code is public domain and can be freely used or copied. +dnl Originally snatched from somewhere... + +dnl Macro for checking if the compiler supports __attribute__ + +dnl Usage: AC_C___ATTRIBUTE__ +dnl call AC_DEFINE for HAVE___ATTRIBUTE__ and __UNUSED__ +dnl if the compiler supports __attribute__, HAVE___ATTRIBUTE__ is +dnl defined to 1 and __UNUSED__ is defined to __attribute__((unused)) +dnl otherwise, HAVE___ATTRIBUTE__ is not defined and __UNUSED__ is +dnl defined to nothing. + +AC_DEFUN([AC_C___ATTRIBUTE__], +[ + +AC_MSG_CHECKING([for __attribute__]) + +AC_CACHE_VAL([ac_cv___attribute__], + [AC_TRY_COMPILE( + [ +#include + +int func(int x); +int foo(int x __attribute__ ((unused))) +{ + exit(1); +} + ], + [], + [ac_cv___attribute__="yes"], + [ac_cv___attribute__="no"] + )]) + +AC_MSG_RESULT($ac_cv___attribute__) + +if test "x${ac_cv___attribute__}" = "xyes" ; then + AC_DEFINE([HAVE___ATTRIBUTE__], [1], [Define to 1 if your compiler has __attribute__]) + AC_DEFINE([__UNUSED__], [__attribute__((unused))], [Macro declaring a function argument to be unused]) + else + AC_DEFINE([__UNUSED__], [], [Macro declaring a function argument to be unused]) +fi + +]) + +dnl End of ac_attribute.m4 diff --git a/m4/efl_binary.m4 b/m4/efl_binary.m4 new file mode 100644 index 0000000..c774688 --- /dev/null +++ b/m4/efl_binary.m4 @@ -0,0 +1,71 @@ +dnl Copyright (C) 2010 Vincent Torri +dnl That code is public domain and can be freely used or copied. + +dnl Macro that check if a binary is built or not + +dnl Usage: EFL_ENABLE_BIN(binary) +dnl Call AC_SUBST(BINARY_PRG) (BINARY is the uppercase of binary, - being transformed into _) +dnl Define have_binary (- is transformed into _) +dnl Define conditional BUILD_BINARY (BINARY is the uppercase of binary, - being transformed into _) + +AC_DEFUN([EFL_ENABLE_BIN], +[ + +m4_pushdef([UP], m4_translit([[$1]], [-a-z], [_A-Z]))dnl +m4_pushdef([DOWN], m4_translit([[$1]], [-A-Z], [_a-z]))dnl + +have_[]m4_defn([DOWN])="yes" + +dnl configure option + +AC_ARG_ENABLE([$1], + [AC_HELP_STRING([--disable-$1], [disable building of ]DOWN)], + [ + if test "x${enableval}" = "xyes" ; then + have_[]m4_defn([DOWN])="yes" + else + have_[]m4_defn([DOWN])="no" + fi + ]) + +AC_MSG_CHECKING([whether to build ]DOWN[ binary]) +AC_MSG_RESULT([$have_[]m4_defn([DOWN])]) + +if test "x$have_[]m4_defn([DOWN])" = "xyes"; then + UP[]_PRG=DOWN[${EXEEXT}] +fi + +AC_SUBST(UP[]_PRG) + +AM_CONDITIONAL(BUILD_[]UP, test "x$have_[]m4_defn([DOWN])" = "xyes") + +AS_IF([test "x$have_[]m4_defn([DOWN])" = "xyes"], [$2], [$3]) + +]) + + +dnl Macro that check if a binary is built or not + +dnl Usage: EFL_WITH_BIN(package, binary, default_value) +dnl Call AC_SUBST(_binary) (_binary is the lowercase of binary, - being transformed into _ by default, or the value set by the user) + +AC_DEFUN([EFL_WITH_BIN], +[ + +m4_pushdef([DOWN], m4_translit([[$2]], [-A-Z], [_a-z]))dnl + +dnl configure option + +AC_ARG_WITH([$2], + [AC_HELP_STRING([--with-$2=PATH], [specify a specific path to ]DOWN[ @<:@default=$3@:>@])], + [_efl_with_binary=${withval}], + [_efl_with_binary=$(pkg-config --variable=prefix $1)/bin/$3]) + +DOWN=${_efl_with_binary} +AC_MSG_NOTICE(DOWN[ set to ${_efl_with_binary}]) + +with_binary_[]m4_defn([DOWN])=${_efl_with_binary} + +AC_SUBST(DOWN) + +]) diff --git a/m4/efl_doxygen.m4 b/m4/efl_doxygen.m4 new file mode 100644 index 0000000..dd6bc3e --- /dev/null +++ b/m4/efl_doxygen.m4 @@ -0,0 +1,99 @@ +dnl Copyright (C) 2008 Vincent Torri +dnl That code is public domain and can be freely used or copied. + +dnl Macro that check if doxygen is available or not. + +dnl EFL_CHECK_DOXYGEN([ACTION-IF-FOUND [, ACTION-IF-NOT-FOUND]]) +dnl Test for the doxygen program +dnl Defines efl_doxygen +dnl Defines the automake conditionnal EFL_BUILD_DOC +dnl +AC_DEFUN([EFL_CHECK_DOXYGEN], +[ + +dnl +dnl Disable the build of the documentation +dnl +AC_ARG_ENABLE([doc], + [AC_HELP_STRING( + [--disable-doc], + [Disable documentation build @<:@default=enabled@:>@])], + [ + if test "x${enableval}" = "xyes" ; then + efl_enable_doc="yes" + else + efl_enable_doc="no" + fi + ], + [efl_enable_doc="yes"]) + +AC_MSG_CHECKING([whether to build documentation]) +AC_MSG_RESULT([${efl_enable_doc}]) + +if test "x${efl_enable_doc}" = "xyes" ; then + +dnl +dnl Specify the file name, without path +dnl + + efl_doxygen="doxygen" + + AC_ARG_WITH([doxygen], + [AC_HELP_STRING( + [--with-doxygen=FILE], + [doxygen program to use @<:@default=doxygen@:>@])], +dnl +dnl Check the given doxygen program. +dnl + [efl_doxygen=${withval} + AC_CHECK_PROG([efl_have_doxygen], + [${efl_doxygen}], + [yes], + [no]) + if test "x${efl_have_doxygen}" = "xno" ; then + echo "WARNING:" + echo "The doxygen program you specified:" + echo "${efl_doxygen}" + echo "was not found. Please check the path and make sure " + echo "the program exists and is executable." + AC_MSG_WARN([no doxygen detected. Documentation will not be built]) + fi + ], + [AC_CHECK_PROG([efl_have_doxygen], + [${efl_doxygen}], + [yes], + [no]) + if test "x${efl_have_doxygen}" = "xno" ; then + echo "WARNING:" + echo "The doxygen program was not found in your execute path." + echo "You may have doxygen installed somewhere not covered by your path." + echo "" + echo "If this is the case make sure you have the packages installed, AND" + echo "that the doxygen program is in your execute path (see your" + echo "shell manual page on setting the \$PATH environment variable), OR" + echo "alternatively, specify the program to use with --with-doxygen." + AC_MSG_WARN([no doxygen detected. Documentation will not be built]) + fi + ]) +fi + +dnl +dnl Substitution +dnl +AC_SUBST([efl_doxygen]) + +if ! test "x${efl_have_doxygen}" = "xyes" ; then + efl_enable_doc="no" +fi + +AM_CONDITIONAL(EFL_BUILD_DOC, test "x${efl_enable_doc}" = "xyes") + +if test "x${efl_enable_doc}" = "xyes" ; then + m4_default([$1], [:]) +else + m4_default([$2], [:]) +fi + +]) + +dnl End of doxygen.m4 diff --git a/m4/efl_threads.m4 b/m4/efl_threads.m4 new file mode 100644 index 0000000..33d15a3 --- /dev/null +++ b/m4/efl_threads.m4 @@ -0,0 +1,206 @@ +dnl Copyright (C) 2010 Vincent Torri +dnl rwlock code added by Mike Blumenkrantz +dnl This code is public domain and can be freely used or copied. + +dnl Macro that check if POSIX or Win32 threads library is available or not. + +dnl Usage: EFL_CHECK_THREADS(ACTION-IF-FOUND [, ACTION-IF-NOT-FOUND]) +dnl Call AC_SUBST(EFL_PTHREAD_CFLAGS) +dnl Call AC_SUBST(EFL_PTHREAD_LIBS) +dnl Defines EFL_HAVE_POSIX_THREADS or EFL_HAVE_WIN32_THREADS, and EFL_HAVE_THREADS + +AC_DEFUN([EFL_CHECK_THREADS], +[ + +dnl configure option + +AC_ARG_ENABLE([posix-threads], + [AC_HELP_STRING([--disable-posix-threads], [enable POSIX threads code @<:@default=auto@:>@])], + [ + if test "x${enableval}" = "xyes" ; then + _efl_enable_posix_threads="yes" + else + _efl_enable_posix_threads="no" + fi + ], + [_efl_enable_posix_threads="auto"]) + +AC_MSG_CHECKING([whether to build POSIX threads code]) +AC_MSG_RESULT([${_efl_enable_posix_threads}]) + +AC_ARG_ENABLE([win32-threads], + [AC_HELP_STRING([--disable-win32-threads], [enable Win32 threads code @<:@default=no@:>@])], + [ + if test "x${enableval}" = "xyes" ; then + _efl_enable_win32_threads="yes" + else + _efl_enable_win32_threads="no" + fi + ], + [_efl_enable_win32_threads="no"]) + +AC_MSG_CHECKING([whether to build Windows threads code]) +AC_MSG_RESULT([${_efl_enable_win32_threads}]) + +dnl +dnl * no + no +dnl * yes + no : win32: error, other : pthread +dnl * yes + yes : win32 : wthread, other : pthread +dnl * no + yes : win32 : wthread, other : error + +if test "x${_efl_enable_posix_threads}" = "xyes" && test "x${_efl_enable_win32_threads}" = "xyes" ; then + case "$host_os" in + mingw*) + _efl_enable_posix_threads=no + ;; + *) + _efl_enable_win32_threads=no + ;; + esac +fi + +if test "x${_efl_enable_win32_threads}" = "xyes" ; then + case "$host_os" in + mingw*) + ;; + *) + AC_MSG_ERROR([Win32 threads support requested but non Windows system found.]) + ;; + esac +fi + +if test "x${_efl_enable_posix_threads}" = "xyes" ; then + case "$host_os" in + mingw*) + AC_MSG_ERROR([POSIX threads support requested but Windows system found.]) + ;; + *) + ;; + esac +fi + +dnl check if the compiler supports POSIX threads + +case "$host_os" in + mingw*) + ;; + solaris*) + _efl_threads_cflags="-mt" + _efl_threads_libs="-mt" + ;; + *) + _efl_threads_cflags="-pthread" + _efl_threads_libs="-pthread" + ;; +esac + +_efl_have_posix_threads="no" +_efl_have_win32_threads="no" + +if test "x${_efl_enable_posix_threads}" = "xyes" || test "x${_efl_enable_posix_threads}" = "xauto" ; then + + SAVE_CFLAGS=${CFLAGS} + CFLAGS="${CFLAGS} ${_efl_threads_cflags}" + SAVE_LIBS=${LIBS} + LIBS="${LIBS} ${_efl_threads_libs}" + AC_LINK_IFELSE( + [AC_LANG_PROGRAM([[ +#include + ]], + [[ +pthread_t id; +id = pthread_self(); + ]])], + [_efl_have_posix_threads="yes"], + [_efl_have_posix_threads="no"]) + CFLAGS=${SAVE_CFLAGS} + LIBS=${SAVE_LIBS} + +fi + +AC_MSG_CHECKING([whether system support POSIX threads]) +AC_MSG_RESULT([${_efl_have_posix_threads}]) +if test "$x{_efl_enable_posix_threads}" = "xyes" && test "x${_efl_have_posix_threads}" = "xno"; then + AC_MSG_ERROR([POSIX threads support requested but not found.]) +fi + +EFL_PTHREAD_CFLAGS="" +EFL_PTHREAD_LIBS="" +if test "x${_efl_have_posix_threads}" = "xyes" ; then + EFL_PTHREAD_CFLAGS=${_efl_threads_cflags} + EFL_PTHREAD_LIBS=${_efl_threads_libs} +fi + +AC_SUBST(EFL_PTHREAD_CFLAGS) +AC_SUBST(EFL_PTHREAD_LIBS) + +_efl_enable_debug_threads="no" +AC_ARG_ENABLE([debug-threads], + [AC_HELP_STRING([--enable-debug-threads], [disable assert when you forgot to call eina_threads_init])], + [_efl_enable_debug_threads="${enableval}"]) + +have_debug_threads="no" +if test "x${_efl_have_posix_threads}" = "xyes" -a "x${_efl_enable_debug_threads}" = "xyes"; then + have_debug_threads="yes" + AC_DEFINE([EFL_DEBUG_THREADS], [1], [Assert when forgot to call eina_threads_init]) +fi + +if test "x${_efl_have_posix_threads}" = "xyes" ; then + AC_DEFINE([EFL_HAVE_POSIX_THREADS], [1], [Define to mention that POSIX threads are supported]) +fi + +if test "x${_efl_enable_win32_threads}" = "xyes" ; then + _efl_have_win32_threads="yes" + AC_DEFINE([EFL_HAVE_WIN32_THREADS], [1], [Define to mention that Win32 threads are supported]) +fi + +if test "x${_efl_have_posix_threads}" = "xyes" || test "x${_efl_have_win32_threads}" = "xyes" ; then + AC_DEFINE([EFL_HAVE_THREADS], [1], [Define to mention that POSIX or Win32 threads are supported]) +fi + +AS_IF([test "x$_efl_have_posix_threads" = "xyes" || test "x$_efl_have_win32_threads" = "xyes"], [$1], [$2]) +]) + +dnl Usage: EFL_CHECK_SPINLOCK(ACTION-IF-FOUND [, ACTION-IF-NOT-FOUND]) +dnl Defines EFL_HAVE_POSIX_THREADS_SPINLOCK +AC_DEFUN([EFL_CHECK_SPINLOCK], +[ + +dnl check if the compiler supports pthreads spinlock + +_efl_have_posix_threads_spinlock="no" + +if test "x${_efl_have_posix_threads}" = "xyes" ; then + + SAVE_CFLAGS=${CFLAGS} + CFLAGS="${CFLAGS} ${EFL_PTHREAD_CFLAGS}" + SAVE_LIBS=${LIBS} + LIBS="${LIBS} ${EFL_PTHREAD_LIBS}" + AC_LINK_IFELSE( + [AC_LANG_PROGRAM([[ +#include + ]], + [[ +pthread_spinlock_t lock; +int res; +res = pthread_spin_init(&lock, PTHREAD_PROCESS_PRIVATE); + ]])], + [_efl_have_posix_threads_spinlock="yes"], + [_efl_have_posix_threads_spinlock="no"]) + CFLAGS=${SAVE_CFLAGS} + LIBS=${SAVE_LIBS} + +fi + +AC_MSG_CHECKING([whether to build POSIX threads spinlock code]) +AC_MSG_RESULT([${_efl_have_posix_threads_spinlock}]) +if test "x${_efl_enable_posix_threads}" = "xyes" && test "x${_efl_have_posix_threads_spinlock}" = "xno" ; then + AC_MSG_WARN([POSIX threads support requested but spinlocks are not supported]) +fi + +if test "x${_efl_have_posix_threads_spinlock}" = "xyes" ; then + AC_DEFINE([EFL_HAVE_POSIX_THREADS_SPINLOCK], [1], [Define to mention that POSIX threads spinlocks are supported]) +fi +AS_IF([test "x$_efl_have_posix_threads_spinlock" = "xyes"], [$1], [$2]) +]) + diff --git a/src/.cvsignore b/src/.cvsignore new file mode 100644 index 0000000..282522d --- /dev/null +++ b/src/.cvsignore @@ -0,0 +1,2 @@ +Makefile +Makefile.in diff --git a/src/Makefile.am b/src/Makefile.am new file mode 100644 index 0000000..be7ccd9 --- /dev/null +++ b/src/Makefile.am @@ -0,0 +1,4 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +SUBDIRS = lib bin modules edje_externals diff --git a/src/bin/.cvsignore b/src/bin/.cvsignore new file mode 100644 index 0000000..a25cf77 --- /dev/null +++ b/src/bin/.cvsignore @@ -0,0 +1,7 @@ +.deps +.libs +Makefile +Makefile.in +rage +raged +rage_thumb diff --git a/src/bin/Makefile.am b/src/bin/Makefile.am new file mode 100644 index 0000000..e01dc3c --- /dev/null +++ b/src/bin/Makefile.am @@ -0,0 +1,133 @@ +AUTOMAKE_OPTIONS = 1.4 foreign + +MAINTAINERCLEANFILES = Makefile.in + +AM_CPPFLAGS = \ +-I$(top_srcdir) \ +-I$(top_srcdir)/src/lib \ +-I$(top_builddir)/src/lib \ +-I$(top_srcdir)/src/bin \ +-DPACKAGE_DATA_DIR=\"$(datadir)/$(PACKAGE)\" \ +@ELEMENTARY_CFLAGS@ \ +@ELEMENTARY_X_CFLAGS@ \ +@ELEMENTARY_FB_CFLAGS@ \ +@ELEMENTARY_WIN32_CFLAGS@ \ +@ELEMENTARY_WINCE_CFLAGS@ \ +@ELEMENTARY_EDBUS_CFLAGS@ \ +@ELEMENTARY_EFREET_CFLAGS@ \ +@ELEMENTARY_EWEATHER_CFLAGS@ \ +@ELEMENTARY_ETHUMB_CFLAGS@ + +if ELEMENTARY_WINDOWS_BUILD +AM_CPPFLAGS += -DELEMENTARY_BUILD +endif + +bin_PROGRAMS = @ELEMENTARY_TEST_PRG@ @ELEMENTARY_CONFIG_PRG@ +if BUILD_QUICKLAUNCH +bin_PROGRAMS += elementary_quicklaunch elementary_run elementary_testql +endif + +EXTRA_PROGRAMS = elementary_test elementary_config + +elementary_test_SOURCES = \ +test.c \ +test_bg.c \ +test_icon.c \ +test_box.c \ +test_button.c \ +test_transit.c \ +test_fileselector_button.c \ +test_fileselector_entry.c \ +test_toggle.c \ +test_table.c \ +test_gengrid.c \ +test_clock.c \ +test_layout.c \ +test_hover.c \ +test_entry.c \ +test_anchorview.c \ +test_anchorblock.c \ +test_toolbar.c \ +test_hoversel.c \ +test_list.c \ +test_inwin.c \ +test_scaling.c \ +test_slider.c \ +test_actionslider.c \ +test_genlist.c \ +test_check.c \ +test_pager.c \ +test_radio.c \ +test_win_state.c \ +test_progressbar.c \ +test_fileselector.c \ +test_separator.c \ +test_scroller.c \ +test_spinner.c \ +test_index.c \ +test_photocam.c \ +test_photo.c \ +test_thumb.c \ +test_icon_desktops.c \ +test_notify.c \ +test_slideshow.c \ +test_menu.c \ +test_panel.c \ +test_panes.c \ +test_map.c \ +test_weather.c \ +test_flip.c \ +test_label.c \ +test_conform.c \ +test_multi.c \ +test_floating.c \ +test_launcher.c \ +test_anim.c \ +test_calendar.c \ +test_tooltip.c \ +test_cursor.c \ +test_focus.c \ +test_focus2.c \ +test_flipselector.c \ +test_diskselector.c \ +test_colorselector.c \ +test_ctxpopup.c \ +test_bubble.c \ +test_store.c + +elementary_test_LDADD = $(top_builddir)/src/lib/libelementary.la @ELEMENTARY_EWEATHER_LIBS@ @my_libs@ +elementary_test_LDFLAGS = + +elementary_config_SOURCES = \ +config.c + +elementary_config_LDADD = $(top_builddir)/src/lib/libelementary.la @ELEMENTARY_EWEATHER_LIBS@ +elementary_config_LDFLAGS = + +if BUILD_QUICKLAUNCH +elementary_quicklaunch_SOURCES = quicklaunch.c +elementary_quicklaunch_LDADD = $(top_builddir)/src/lib/libelementary.la @ELEMENTARY_EWEATHER_LIBS@ +elementary_quicklaunch_LDFLAGS = + +if BUILD_RUN +elementary_run_SOURCES = run.c +elementary_run_LDADD = +elementary_run_LDFLAGS = +endif + +## This is how to build a quicklanch capable app +# build the shared lib version - libtool produces a .a and .la file as well +# as a .so - these get put in libdir ($PREIFX/lib) as elementary_testql.so +# etc. - this is where elementary will expect to find the .so's for +# quicklaunch apps. +elementary_testqldir = $(libdir) +elementary_testql_LTLIBRARIES = elementary_testql.la +elementary_testql_la_SOURCES = $(elementary_test_SOURCES) +elementary_testql_la_LIBADD = $(top_builddir)/src/lib/libelementary.la +elementary_testql_la_CFLAGS = +elementary_testql_la_LDFLAGS = -module -avoid-version -no-undefined +elementary_testql_SOURCES = $(elementary_test_SOURCES) +elementary_testql_LDADD = $(top_builddir)/src/lib/libelementary.la +elementary_testql_CFLAGS = -DELM_LIB_QUICKLAUNCH=1 +elementary_testql_LDFLAGS = +endif diff --git a/src/bin/config.c b/src/bin/config.c new file mode 100644 index 0000000..8bc8ed4 --- /dev/null +++ b/src/bin/config.c @@ -0,0 +1,3019 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +typedef struct _Theme Theme; +typedef struct _Fonts_Data Fonts_Data; +typedef struct _Elm_Text_Class_Data Elm_Text_Class_Data; +typedef struct _Elm_Font_Size_Data Elm_Font_Size_Data; + +struct _Theme +{ + const char *label; + const char *name; + const char *path; + Eina_Bool in_search_path; +}; + +static Theme *tsel = NULL; +static Eina_List *themes = NULL; + +struct _Elm_Text_Class_Data +{ + const char *name; + const char *desc; + const char *font; + const char *style; + Evas_Font_Size size; +}; + +struct _Elm_Font_Size_Data +{ + const char *size_str; + Evas_Font_Size size; +}; + +struct _Fonts_Data +{ + Eina_List *text_classes; + + Eina_Hash *font_hash; + Eina_List *font_px_list; + Eina_List *font_scale_list; + + const char *cur_font; + const char *cur_style; + double cur_size; +}; + +#define ELM_LIST_DISABLE(list) \ + do \ + { \ + const Eina_List *l = elm_list_items_get(list); \ + if (l) \ + { \ + elm_list_item_show(eina_list_data_get(l)); \ + elm_object_disabled_set(list, EINA_TRUE); \ + } \ + } \ + while (0) + +#define ELM_LIST_ENABLE(list) \ + do \ + { \ + elm_object_disabled_set(list, EINA_FALSE); \ + } \ + while (0) + +#define LABEL_FRAME_ADD(label) \ + do \ + { \ + pd = elm_frame_add(win); \ + evas_object_size_hint_weight_set(pd, EVAS_HINT_EXPAND, 0.0); \ + evas_object_size_hint_align_set(pd, EVAS_HINT_FILL, 0.5); \ + elm_object_style_set(pd, "pad_medium"); \ + elm_box_pack_end(bx, pd); \ + evas_object_show(pd); \ + \ + lb = elm_label_add(win); \ + evas_object_size_hint_weight_set(lb, EVAS_HINT_EXPAND, 0.0); \ + evas_object_size_hint_align_set(lb, EVAS_HINT_FILL, 0.5); \ + elm_label_label_set(lb, label); \ + elm_frame_content_set(pd, lb); \ + evas_object_show(lb); \ + } \ + while (0) + +static int quiet = 0; +static int interactive = 1; + +static const char *theme_set = NULL; +static const char *finger_size_set = NULL; +static const char *scale_set = NULL; +static Fonts_Data fdata = {NULL, NULL, NULL, NULL, NULL, NULL, 0.0}; + +static void +_font_styles_list_sel(void *data __UNUSED__, + Evas_Object *obj, + void *event_info); + +static void +config_exit(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Elm_Text_Class_Data *tc_data; + Elm_Font_Size_Data *sd; + + EINA_LIST_FREE(fdata.text_classes, tc_data) + { + eina_stringshare_del(tc_data->name); + eina_stringshare_del(tc_data->desc); + eina_stringshare_del(tc_data->font); + eina_stringshare_del(tc_data->style); + free(tc_data); + } + + elm_font_available_hash_del(fdata.font_hash); + + EINA_LIST_FREE(fdata.font_px_list, sd) + { + eina_stringshare_del(sd->size_str); + free(sd); + } + + EINA_LIST_FREE(fdata.font_scale_list, sd) + { + eina_stringshare_del(sd->size_str); + free(sd); + } + + if (fdata.cur_font) eina_stringshare_del(fdata.cur_font); + if (fdata.cur_style) eina_stringshare_del(fdata.cur_style); + + elm_config_save(); + elm_exit(); /* exit the program's main loop that runs in elm_run() */ +} + +static void +sb_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Eina_Bool val = elm_check_state_get(obj); + Eina_Bool sb = elm_scroll_bounce_enabled_get(); + + if (val == sb) return; + elm_scroll_bounce_enabled_all_set(val); + + /*TODO: enable/disable subordinate sliders (make 'em support it 1st)*/ +} + +static void +bf_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +bf_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double bf = elm_scroll_bounce_friction_get(); + double val = elm_slider_value_get(obj); + + if (bf == val) return; + elm_scroll_bounce_friction_all_set(val); +} + +static void +ps_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +ps_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double ps = elm_scroll_page_scroll_friction_get(); + double val = elm_slider_value_get(obj); + + if (ps == val) return; + elm_scroll_page_scroll_friction_all_set(val); +} + +static void +bis_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +bis_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double bis = elm_scroll_bring_in_scroll_friction_get(); + double val = elm_slider_value_get(obj); + + if (bis == val) return; + elm_scroll_bring_in_scroll_friction_all_set(val); +} + +static void +zf_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +zf_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double zf = elm_scroll_zoom_friction_get(); + double val = elm_slider_value_get(obj); + + if (zf == val) return; + elm_scroll_zoom_friction_all_set(val); +} + +static void +ts_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Eina_Bool val = elm_check_state_get(obj); + Eina_Bool sb = elm_scroll_bounce_enabled_get(); + + if (val == sb) return; + elm_scroll_thumbscroll_enabled_all_set(val); + + /*TODO: enable/disable subordinate sliders (make 'em support it 1st)*/ +} + +static void +tst_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +tst_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double tst = elm_scroll_thumbscroll_threshold_get(); + double val = elm_slider_value_get(obj); + + if (tst == val) return; + elm_scroll_thumbscroll_threshold_all_set(val); +} + +static void +tsmt_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +tsmt_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double tsmt = elm_scroll_thumbscroll_momentum_threshold_get(); + double val = elm_slider_value_get(obj); + + if (tsmt == val) return; + elm_scroll_thumbscroll_momentum_threshold_all_set(val); +} + +static void +tsf_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +tsf_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double tsf = elm_scroll_thumbscroll_friction_get(); + double val = elm_slider_value_get(obj); + + if (tsf == val) return; + elm_scroll_thumbscroll_friction_all_set(val); +} + +static void +tsbf_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +tsbf_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double tsbf = elm_scroll_thumbscroll_border_friction_get(); + double val = elm_slider_value_get(obj); + + if (tsbf == val) return; + elm_scroll_thumbscroll_border_friction_all_set(val); +} + +static void +cf_enable(void *data, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Eina_Bool cf = elm_cache_flush_enmabled_get(); + Eina_Bool val = elm_check_state_get(obj); + + if (cf == val) return; + elm_object_disabled_set((Evas_Object *)data, !val); + elm_cache_flush_enabled_all_set(val); +} + +static void +cf_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 5.0))) / 5.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +cf_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double cf = elm_cache_flush_interval_get(); + double val = elm_slider_value_get(obj); + + if (cf == val) return; + elm_cache_flush_interval_all_set(val); +} + +static void +fc_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +fc_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double font_cache = elm_font_cache_get(); + double val = elm_slider_value_get(obj); + + if (font_cache == val) return; + elm_font_cache_all_set(val * 1024); +} + +static void +ic_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +ic_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double image_cache = elm_image_cache_get(); + double val = elm_slider_value_get(obj); + + if (image_cache == val) return; + elm_image_cache_all_set(val * 1024); +} + +static void +sc_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 10.0))) / 10.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +sc_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double scale = elm_scale_get(); + double val = elm_slider_value_get(obj); + + if (scale == val) return; + elm_scale_all_set(val); +} + +static void +fs_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 5.0))) / 5.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +fs_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double fs = elm_finger_size_get(); + double val = elm_slider_value_get(obj); + + if (fs == val) return; + elm_finger_size_all_set(val); +} + +static void +efc_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 5.0))) / 5.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +efc_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double efc = elm_edje_file_cache_get(); + double val = elm_slider_value_get(obj); + + if (efc == val) return; + elm_edje_file_cache_all_set(val); +} + +static void +ecc_round(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + double v; + + v = ((double)((int)(val * 5.0))) / 5.0; + if (v != val) elm_slider_value_set(obj, v); +} + +static void +ecc_change(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + double ecc = elm_edje_collection_cache_get(); + double val = elm_slider_value_get(obj); + + if (ecc == val) return; + elm_edje_collection_cache_all_set(val); +} + +static void +_status_basic(Evas_Object *win, + Evas_Object *bx0) +{ + Evas_Object *lb, *fr; + + fr = elm_frame_add(win); + evas_object_size_hint_weight_set(fr, 1.0, 1.0); + elm_frame_label_set(fr, "Information"); + elm_box_pack_end(bx0, fr); + evas_object_show(fr); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "Applying configuration change" + ); + elm_frame_content_set(fr, lb); + evas_object_show(lb); +} + +static void +_status_config(Evas_Object *win, + Evas_Object *bx0) +{ + Evas_Object *lb, *pd, *bx, *fr, *sl, *sp; + + fr = elm_frame_add(win); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_label_set(fr, "Sizing"); + elm_box_pack_end(bx0, fr); + evas_object_show(fr); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, 0.5); + + LABEL_FRAME_ADD("Scale"); + + sl = elm_slider_add(win); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.2f"); + elm_slider_indicator_format_set(sl, "%1.2f"); + elm_slider_min_max_set(sl, 0.25, 5.0); + elm_slider_value_set(sl, elm_scale_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", sc_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", sc_change, NULL); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + LABEL_FRAME_ADD("Finger Size
    "); + + sl = elm_slider_add(win); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.0f"); + elm_slider_indicator_format_set(sl, "%1.0f"); + elm_slider_min_max_set(sl, 5, 200); + elm_slider_value_set(sl, elm_finger_size_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", fs_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", fs_change, NULL); + + // FIXME: add theme selector (basic mode and advanced for fallbacks) + // FIXME: save config + // FIXME: profile selector / creator etc. + elm_frame_content_set(fr, bx); + evas_object_show(bx); +} + +static void +_flip_to(Evas_Object *win, + const char *name) +{ + Evas_Object *wid, *pager; + wid = evas_object_data_get(win, name); + pager = evas_object_data_get(win, "pager"); + elm_pager_content_promote(pager, wid); +} + +static void +_cf_sizing(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + _flip_to(data, "sizing"); +} + +static void +_cf_themes(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + _flip_to(data, "themes"); +} + +static void +_cf_fonts(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + _flip_to(data, "fonts"); +} + +static void +_cf_profiles(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + _flip_to(data, "profiles"); +} + +static void +_cf_scrolling(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + _flip_to(data, "scrolling"); +} + +static void +_cf_rendering(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + _flip_to(data, "rendering"); +} + +static void +_cf_caches(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + _flip_to(data, "caches"); +} + +const char * +_elm_theme_current_get(const char *theme_search_order) +{ + const char *ret; + const char *p; + + if (!theme_search_order) + return NULL; + + for (p = theme_search_order;; p++) + { + if ((*p == ':') || (!*p)) + { + if (p > theme_search_order) + { + char *n = malloc(p - theme_search_order + 1); + if (!n) + return NULL; + + strncpy(n, theme_search_order, p - theme_search_order); + n[p - theme_search_order] = 0; + ret = eina_stringshare_add(n); + free(n); + break; + } + } + } + + return ret; +} + +static void +_font_overlay_set_all(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *win, *fclasses, *fnames, *fstyles, *fsizes; + Elm_Text_Class_Data *tc_data, *tc; + Elm_List_Item *it; + Eina_List *l; + + win = data; + + fclasses = evas_object_data_get(win, "font_classes_list"); + it = elm_list_selected_item_get(fclasses); + if (!it) return; + tc_data = elm_list_item_data_get(it); + + fnames = evas_object_data_get(win, "font_names_list"); + fstyles = evas_object_data_get(win, "font_styles_list"); + fsizes = evas_object_data_get(win, "font_sizes_list"); + + EINA_LIST_FOREACH(fdata.text_classes, l, tc) + { + eina_stringshare_replace(&tc->font, tc_data->font); + eina_stringshare_replace(&tc->style, tc_data->style); + tc->size = tc_data->size; + } + + elm_config_save(); +} + +static void +_font_overlay_reset(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *win, *fclasses, *fnames, *fstyles, *fsizes; + Elm_Text_Class_Data *tc_data; + Elm_List_Item *it; + + win = data; + + fclasses = evas_object_data_get(win, "font_classes_list"); + it = elm_list_selected_item_get(fclasses); + if (!it) return; + tc_data = elm_list_item_data_get(it); + + fnames = evas_object_data_get(win, "font_names_list"); + fstyles = evas_object_data_get(win, "font_styles_list"); + fsizes = evas_object_data_get(win, "font_sizes_list"); + + elm_font_overlay_unset(tc_data->name); + + eina_stringshare_replace(&fdata.cur_font, NULL); + eina_stringshare_replace(&tc_data->font, NULL); + eina_stringshare_replace(&fdata.cur_style, NULL); + eina_stringshare_replace(&tc_data->style, NULL); + fdata.cur_size = 0.0; + tc_data->size = 0.0; + + ELM_LIST_DISABLE(fnames); + ELM_LIST_DISABLE(fstyles); + ELM_LIST_DISABLE(fsizes); + + elm_config_save(); +} + +static void +_font_overlay_reset_all(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *win, *fclasses, *fnames, *fstyles, *fsizes; + Elm_Text_Class_Data *tc_data; + Elm_List_Item *it; + Eina_List *l; + + win = data; + eina_stringshare_replace(&fdata.cur_font, NULL); + eina_stringshare_replace(&fdata.cur_style, NULL); + fdata.cur_size = 0.0; + + EINA_LIST_FOREACH(fdata.text_classes, l, tc_data) + { + elm_font_overlay_unset(tc_data->name); + + eina_stringshare_replace(&tc_data->font, NULL); + eina_stringshare_replace(&tc_data->style, NULL); + tc_data->size = 0.0; + } + + fclasses = evas_object_data_get(win, "font_classes_list"); + fnames = evas_object_data_get(win, "font_names_list"); + fstyles = evas_object_data_get(win, "font_styles_list"); + fsizes = evas_object_data_get(win, "font_sizes_list"); + + it = elm_list_selected_item_get(fclasses); + if (it) elm_list_item_selected_set(it, EINA_FALSE); + + ELM_LIST_DISABLE(fnames); + ELM_LIST_DISABLE(fstyles); + ELM_LIST_DISABLE(fsizes); + + elm_config_save(); +} + +static void +_font_overlay_change(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Elm_Text_Class_Data *tc_data; + Eina_List *l; + + EINA_LIST_FOREACH(fdata.text_classes, l, tc_data) + { + if (tc_data->font) + { + const char *name; + + name = elm_font_fontconfig_name_get(tc_data->font, + tc_data->style); + elm_font_overlay_set(tc_data->name, name, + tc_data->size ? tc_data->size : -100); + elm_font_fontconfig_name_free(name); + } + else + elm_font_overlay_unset(tc_data->name); + } + + elm_config_save(); + elm_font_overlay_all_apply(); + + /* TODO: apply hinting */ +} + +static void +_profile_change_do(Evas_Object *win, + const char *profile) +{ + int flush_interval, font_c, image_c, edje_file_c, edje_col_c, ts_threshould; + double scale, s_bounce_friction, ts_momentum_threshold, ts_friction, + ts_border_friction, page_friction, bring_in_friction, zoom_friction; + const char *curr_theme, *curr_engine; + const Eina_List *l_items, *l; + Eina_Bool s_bounce, ts; + Elm_List_Item *it; + Elm_Theme *th; + int fs; + + elm_profile_all_set(profile); + + scale = elm_scale_get(); + fs = elm_finger_size_get(); + flush_interval = elm_cache_flush_interval_get(); + font_c = elm_font_cache_get(); + image_c = elm_image_cache_get(); + edje_file_c = elm_edje_file_cache_get(); + edje_col_c = elm_edje_collection_cache_get(); + + s_bounce = elm_scroll_bounce_enabled_get(); + s_bounce_friction = elm_scroll_bounce_friction_get(); + ts = elm_scroll_thumbscroll_enabled_get(); + ts_threshould = elm_scroll_thumbscroll_threshold_get(); + ts_momentum_threshold = elm_scroll_thumbscroll_momentum_threshold_get(); + ts_friction = elm_scroll_thumbscroll_friction_get(); + ts_border_friction = elm_scroll_thumbscroll_border_friction_get(); + page_friction = elm_scroll_page_scroll_friction_get(); + bring_in_friction = elm_scroll_bring_in_scroll_friction_get(); + zoom_friction = elm_scroll_zoom_friction_get(); + + /* gotta update root windows' atoms */ + elm_scale_all_set(scale); + elm_slider_value_set(evas_object_data_get(win, "scale_slider"), scale); + elm_finger_size_all_set(fs); + elm_slider_value_set(evas_object_data_get(win, "fs_slider"), fs); + + elm_cache_flush_interval_all_set(flush_interval); + elm_slider_value_set(evas_object_data_get(win, + "cache_flush_interval_slider"), + flush_interval); + elm_font_cache_all_set(font_c); + elm_slider_value_set(evas_object_data_get(win, "font_cache_slider"), + font_c / 1024.0); + elm_image_cache_all_set(image_c); + elm_slider_value_set(evas_object_data_get(win, "image_cache_slider"), + image_c / 1024.0); + elm_edje_file_cache_all_set(edje_file_c); + elm_slider_value_set(evas_object_data_get(win, "edje_file_cache_slider"), + edje_file_c); + elm_edje_collection_cache_all_set(edje_col_c); + elm_slider_value_set(evas_object_data_get(win, + "edje_collection_cache_slider"), + edje_col_c); + + elm_scroll_bounce_enabled_all_set(s_bounce); + elm_check_state_set(evas_object_data_get(win, "scroll_bounce_check"), + s_bounce); + elm_scroll_bounce_friction_all_set(s_bounce_friction); + elm_slider_value_set(evas_object_data_get(win, "bounce_friction_slider"), + s_bounce_friction); + elm_scroll_thumbscroll_enabled_all_set(ts); + elm_check_state_set(evas_object_data_get(win, "thumbscroll_check"), ts); + elm_scroll_thumbscroll_threshold_all_set(ts_threshould); + elm_slider_value_set(evas_object_data_get(win, + "thumbscroll_threshold_slider"), + ts_threshould); + elm_scroll_thumbscroll_momentum_threshold_all_set(ts_momentum_threshold); + elm_slider_value_set(evas_object_data_get(win, + "ts_momentum_threshold_slider"), + ts_momentum_threshold); + elm_scroll_thumbscroll_friction_all_set(ts_friction); + elm_slider_value_set(evas_object_data_get(win, + "thumbscroll_friction_slider"), + ts_friction); + elm_scroll_thumbscroll_border_friction_all_set(ts_border_friction); + elm_slider_value_set(evas_object_data_get(win, "ts_border_friction_slider"), + ts_border_friction); + elm_scroll_page_scroll_friction_all_set(page_friction); + elm_slider_value_set(evas_object_data_get(win, + "page_scroll_friction_slider"), + page_friction); + elm_scroll_bring_in_scroll_friction_all_set(bring_in_friction); + elm_slider_value_set(evas_object_data_get(win, + "bring_in_scroll_friction_slider"), + bring_in_friction); + elm_scroll_zoom_friction_all_set(zoom_friction); + elm_slider_value_set(evas_object_data_get(win, + "zoom_scroll_friction_slider"), + zoom_friction); + + curr_theme = _elm_theme_current_get(elm_theme_get(NULL)); + elm_theme_all_set(curr_theme); + + th = elm_theme_new(); + elm_theme_set(th, curr_theme); + elm_object_theme_set(evas_object_data_get(win, "theme_preview"), th); + elm_theme_free(th); + eina_stringshare_del(curr_theme); + + curr_engine = elm_engine_current_get(); + l_items = elm_list_items_get(evas_object_data_get(win, "engines_list")); + EINA_LIST_FOREACH(l_items, l, it) + { + if (!strcmp(elm_list_item_data_get(it), curr_engine)) + { + elm_list_item_selected_set(it, EINA_TRUE); + break; + } + } +} + +static void +_engine_use(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *li; + const char *selection; + + li = data; + selection = elm_list_item_data_get(elm_list_selected_item_get(li)); + + if (!strcmp(elm_engine_current_get(), selection)) + return; + + elm_engine_set(selection); + elm_config_save(); /* make sure new engine has its data dir */ +} + +static void +_profile_use(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *li; + const char *selection; + const char *profile; + + li = data; + selection = elm_list_item_data_get(elm_list_selected_item_get(li)); + profile = elm_profile_current_get(); + + if (!profile) + { + fprintf(stderr, "No profile currently set!\n"); /* FIXME: log domain */ + return; + } + + if (!strcmp(profile, selection)) + return; + + elm_config_save(); /* dump config into old profile's data dir */ + elm_profile_set(selection); /* just here to update info for getters below */ + + _profile_change_do(elm_object_top_widget_get(li), selection); + elm_config_save(); /* make sure new profile has its data dir */ +} + +static void +_btn_todo(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + printf("To be done!\n"); +} + +static void +_profile_reset(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + const char *selection, *curr; + const char *pdir; + Evas_Object *li; + + li = data; + selection = elm_list_item_data_get(elm_list_selected_item_get(li)); + curr = elm_profile_current_get(); + + elm_config_save(); /* dump config into old profile's data dir */ + + pdir = elm_profile_dir_get(selection, EINA_TRUE); + if (!pdir) + return; + + ecore_file_recursive_rm(pdir); + elm_profile_dir_free(pdir); + + elm_config_reload(); + + _profile_change_do(elm_object_top_widget_get(li), curr); + elm_config_save(); /* make sure new profile has its data dir */ +} + +static void +_theme_use(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + const char *defth; + char *newth; + Theme *t = tsel; + + if (!t) return; + defth = elm_theme_get(NULL); + newth = malloc(strlen(defth) + 1 + strlen(t->name) + 1); + if (newth) + { + char *rest; + + newth[0] = 0; + rest = strchr(defth, ':'); + if (!rest) + strcpy(newth, t->name); + else + { + strcpy(newth, t->name); + strcat(newth, rest); + } + elm_theme_all_set(newth); + free(newth); + } +} + +static void +_theme_sel(void *data, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Theme *t = data; + Evas_Object *win = elm_object_top_widget_get(obj); + Evas_Object *sample = evas_object_data_get(win, "theme_preview"); + Elm_Theme *th; + const char *defth; + char *newth; + + tsel = t; + defth = elm_theme_get(NULL); + newth = malloc(strlen(defth) + 1 + strlen(t->name) + 1); + th = elm_theme_new(); + if (newth) + { + char *rest; + + newth[0] = 0; + rest = strchr(defth, ':'); + if (!rest) + strcpy(newth, t->name); + else + { + strcpy(newth, t->name); + strcat(newth, rest); + } + elm_theme_set(th, newth); + free(newth); + } + elm_object_theme_set(sample, th); + elm_theme_free(th); +} + +/*static void + _theme_browse(void *data, Evas_Object *obj, void *event_info) + { + printf("not implemented\n"); + }*/ + +static void +_status_config_sizing(Evas_Object *win, + Evas_Object *pager) +{ + Evas_Object *lb, *pd, *bx, *sl, *sp; + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, 0.5); + + LABEL_FRAME_ADD("Scale"); + + sl = elm_slider_add(win); + evas_object_data_set(win, "scale_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.2f"); + elm_slider_indicator_format_set(sl, "%1.2f"); + elm_slider_min_max_set(sl, 0.25, 5.0); + elm_slider_value_set(sl, elm_scale_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", sc_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", sc_change, NULL); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + LABEL_FRAME_ADD("Finger Size
    "); + + sl = elm_slider_add(win); + evas_object_data_set(win, "fs_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.0f"); + elm_slider_indicator_format_set(sl, "%1.0f"); + elm_slider_min_max_set(sl, 5, 200); + elm_slider_value_set(sl, elm_finger_size_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", fs_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", fs_change, NULL); + + evas_object_data_set(win, "sizing", bx); + + elm_pager_content_push(pager, bx); +} + +static Evas_Object * +_sample_theme_new(Evas_Object *win) +{ + Evas_Object *base, *bg, *bt, *ck, *rd, *rdg, *sl, *fr, *li, *rc, *sp; + + base = elm_table_add(win); + evas_object_size_hint_weight_set(base, 1.0, 1.0); + evas_object_size_hint_align_set(base, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, 1.0, 1.0); + evas_object_size_hint_align_set(bg, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(base, bg, 0, 0, 2, 5); + evas_object_show(bg); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button"); + elm_table_pack(base, bt, 0, 0, 1, 1); + evas_object_show(bt); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Check"); + elm_table_pack(base, ck, 0, 1, 1, 1); + evas_object_show(ck); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, 0); + elm_radio_label_set(rd, "Radio 1"); + elm_table_pack(base, rd, 1, 0, 1, 1); + evas_object_show(rd); + rdg = rd; + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, 1); + elm_radio_label_set(rd, "Radio 2"); + elm_radio_group_add(rd, rdg); + elm_table_pack(base, rd, 1, 1, 1, 1); + evas_object_show(rd); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + evas_object_size_hint_weight_set(sp, 1.0, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_table_pack(base, sp, 0, 2, 2, 1); + evas_object_show(sp); + + sl = elm_slider_add(win); + elm_slider_label_set(sl, "Slider"); + elm_slider_span_size_set(sl, 120); + elm_slider_min_max_set(sl, 1, 10); + elm_slider_value_set(sl, 4); + evas_object_size_hint_weight_set(sl, 1.0, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(base, sl, 0, 3, 2, 1); + evas_object_show(sl); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Frame"); + elm_table_pack(base, fr, 0, 4, 2, 1); + evas_object_size_hint_weight_set(fr, 1.0, 1.0); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(fr); + + li = elm_list_add(win); + evas_object_size_hint_weight_set(li, 1.0, 1.0); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(fr, li); + evas_object_show(li); + + elm_list_item_append(li, "List Item 1", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Second Item", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Third Item", NULL, NULL, NULL, NULL); + elm_list_go(li); + + rc = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(rc, 160, 120); + elm_table_pack(base, rc, 0, 4, 2, 1); + + return base; +} + +static void +_status_config_themes(Evas_Object *win, + Evas_Object *pager) +{ + Evas_Object *tb, *rc, *sc, *sp, *li, *pd, *fr, *bt, *sample; + Eina_List *list, *l; + char *th, *s, *ext; + + tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, 1.0, 1.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + rc = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(rc, 0, 130); + elm_table_pack(tb, rc, 0, 0, 1, 1); + + rc = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(rc, 0, 200); + elm_table_pack(tb, rc, 0, 1, 1, 1); + + ///////////////////////////////////////////// + + pd = elm_frame_add(win); + elm_object_style_set(pd, "pad_medium"); + evas_object_size_hint_weight_set(pd, 1.0, 1.0); + evas_object_size_hint_align_set(pd, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, pd, 0, 0, 1, 1); + evas_object_show(pd); + + li = elm_list_add(win); + evas_object_size_hint_weight_set(li, 1.0, 1.0); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(pd, li); + evas_object_show(li); + + list = elm_theme_name_available_list_new(); + EINA_LIST_FOREACH(list, l, th) + { + Theme *t; + + t = calloc(1, sizeof(Theme)); + t->name = eina_stringshare_add(th); + s = elm_theme_list_item_path_get(th, &(t->in_search_path)); + if (s) + { + t->path = eina_stringshare_add(s); + free(s); + } + if (t->in_search_path) + { + s = strdup(th); + if (s) + { + s[0] = toupper(s[0]); + t->label = eina_stringshare_add(s); + free(s); + } + else + t->label = eina_stringshare_add(s); + } + else + { + s = strdup(ecore_file_file_get(th)); + if (s) + { + s[0] = toupper(s[0]); + ext = strrchr(s, '.'); + if (ext) *ext = 0; + t->label = eina_stringshare_add(s); + free(s); + } + else + t->label = eina_stringshare_add(s); + } + themes = eina_list_append(themes, t); + elm_list_item_append(li, t->label, NULL, NULL, _theme_sel, t); + } + elm_theme_name_available_list_free(list); + + elm_list_go(li); + + pd = elm_frame_add(win); + elm_object_style_set(pd, "pad_medium"); + evas_object_size_hint_weight_set(pd, 1.0, 1.0); + evas_object_size_hint_align_set(pd, 0.9, 0.9); + elm_table_pack(tb, pd, 0, 0, 1, 1); + evas_object_show(pd); + + /* FIXME: not implemented yet + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _theme_browse, win); + elm_button_label_set(bt, "Browse..."); + evas_object_size_hint_weight_set(bt, 1.0, 1.0); + evas_object_size_hint_align_set(bt, 0.9, 0.9); + elm_frame_content_set(pd, bt); + evas_object_show(bt); + */ + pd = elm_frame_add(win); + elm_object_style_set(pd, "pad_medium"); + evas_object_size_hint_weight_set(pd, 1.0, 0.0); + evas_object_size_hint_align_set(pd, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, pd, 0, 1, 1, 1); + evas_object_show(pd); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Preview"); + evas_object_size_hint_weight_set(fr, 1.0, 1.0); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(pd, fr); + evas_object_show(fr); + + sc = elm_scroller_add(win); + elm_scroller_bounce_set(sc, 0, 0); + evas_object_size_hint_weight_set(sc, 1.0, 1.0); + evas_object_size_hint_align_set(sc, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(fr, sc); + evas_object_show(sc); + + sample = _sample_theme_new(win); + elm_scroller_content_set(sc, sample); + evas_object_show(sample); + evas_object_data_set(win, "theme_preview", sample); + + ///////////////////////////////////////////// + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + evas_object_size_hint_weight_set(sp, 1.0, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_table_pack(tb, sp, 0, 2, 1, 1); + evas_object_show(sp); + + pd = elm_frame_add(win); + elm_object_style_set(pd, "pad_medium"); + evas_object_size_hint_weight_set(pd, 0.0, 0.0); + evas_object_size_hint_align_set(pd, 0.5, 0.5); + elm_table_pack(tb, pd, 0, 3, 1, 1); + evas_object_show(pd); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _theme_use, win); + elm_button_label_set(bt, "Use Theme"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_frame_content_set(pd, bt); + evas_object_show(bt); + + evas_object_data_set(win, "themes", tb); + elm_pager_content_push(pager, tb); +} + +static void +_font_preview_update(Evas_Object *win) +{ + Evas_Font_Size sz; + const char *name; + + if (!fdata.cur_font) + return; + + name = elm_font_fontconfig_name_get(fdata.cur_font, fdata.cur_style); + sz = fdata.cur_size; + + if (sz < 0) + sz = (-sz * 10) / 100; + if (sz == 0) + sz = 10; + + edje_object_text_class_set(evas_object_data_get(win, "font_preview"), + "font_preview", name, sz); + + elm_font_fontconfig_name_free(name); +} + +static void +_font_classes_list_sel(void *data __UNUSED__, + Evas_Object *obj, + void *event_info) +{ + const Eina_List *f_names_items, *l; + Elm_Text_Class_Data *tc_data; + Evas_Object *f_names_list; + Elm_List_Item *it; + + tc_data = elm_list_item_data_get(event_info); + + f_names_list = evas_object_data_get(elm_object_top_widget_get(obj), + "font_names_list"); + ELM_LIST_ENABLE(f_names_list); + + f_names_items = elm_list_items_get(f_names_list); + + EINA_LIST_FOREACH(f_names_items, l, it) + { + const char *l; + + l = elm_list_item_label_get(it); + + if (tc_data->font && !strcmp(l, tc_data->font)) + { + elm_list_item_selected_set(it, EINA_TRUE); + elm_list_item_show(it); + break; + } + } +} + +static void +_font_names_list_sel(void *data __UNUSED__, + Evas_Object *obj, + void *event_info) +{ + Evas_Object *style_list, *cls_list, *sizes_list, *win; + const char *style, *sel_font; + Elm_Text_Class_Data *tc_data; + Elm_List_Item *it, *fc_it; + Elm_Font_Properties *efp; + const Eina_List *l; + + it = event_info; + sel_font = elm_list_item_label_get(it); + + win = elm_object_top_widget_get(obj); + style_list = evas_object_data_get(win, "font_styles_list"); + cls_list = evas_object_data_get(win, "font_classes_list"); + sizes_list = evas_object_data_get(win, "font_sizes_list"); + + fc_it = elm_list_selected_item_get(cls_list); + if (!fc_it) return; /* should not happen, fonts list disabled in + * this case */ + + eina_stringshare_replace(&fdata.cur_font, sel_font); + + tc_data = elm_list_item_data_get(fc_it); + if (tc_data->font) eina_stringshare_del(tc_data->font); + if (fdata.cur_font) tc_data->font = eina_stringshare_ref(fdata.cur_font); + + /* load styles list */ + efp = eina_hash_find(fdata.font_hash, sel_font); + + ELM_LIST_ENABLE(style_list); + elm_list_clear(style_list); + + evas_event_freeze(evas_object_evas_get(style_list)); + edje_freeze(); + + it = NULL; + + EINA_LIST_FOREACH(efp->styles, l, style) + { + Elm_List_Item *i; + + i = elm_list_item_append(style_list, style, NULL, NULL, + _font_styles_list_sel, NULL); + + if (tc_data->style && (!strcmp(style, tc_data->style))) + it = i; + } + + elm_list_go(style_list); + + edje_thaw(); + evas_event_thaw(evas_object_evas_get(style_list)); + + if (it) + elm_list_item_selected_set(it, EINA_TRUE); + + _font_preview_update(win); +} + +static void +_font_styles_list_sel(void *data __UNUSED__, + Evas_Object *obj, + void *event_info) +{ + Evas_Object *fc_list, *fs_list, *win; + Elm_Text_Class_Data *tc_data; + const Eina_List *l; + Elm_List_Item *it; + + win = elm_object_top_widget_get(obj); + fc_list = evas_object_data_get(win, "font_classes_list"); + fs_list = evas_object_data_get(win, "font_sizes_list"); + + it = elm_list_selected_item_get(fc_list); + if (!it) return; /* should not happen */ + + eina_stringshare_replace(&fdata.cur_style, + elm_list_item_label_get(event_info)); + ELM_LIST_ENABLE(fs_list); + + tc_data = elm_list_item_data_get(it); + eina_stringshare_del(tc_data->style); + tc_data->style = eina_stringshare_ref(fdata.cur_style); + + evas_event_freeze(evas_object_evas_get(fs_list)); + edje_freeze(); + + EINA_LIST_FOREACH(elm_list_items_get(fs_list), l, it) + { + Elm_Font_Size_Data *sdata; + + sdata = elm_list_item_data_get(it); + elm_list_item_selected_set(l->data, EINA_FALSE); + + if (tc_data->size == sdata->size) + { + elm_list_item_selected_set(it, EINA_TRUE); + elm_list_item_show(it); + break; + } + } + + edje_thaw(); + evas_event_thaw(evas_object_evas_get(fs_list)); + + _font_preview_update(win); +} + +static void +_font_sizes_list_sel(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Elm_Text_Class_Data *tc_data; + Evas_Object *fc_list, *win; + Elm_Font_Size_Data *sd; + Elm_List_Item *it; + + win = elm_object_top_widget_get(obj); + fc_list = evas_object_data_get(win, "font_classes_list"); + + it = elm_list_selected_item_get(fc_list); + if (!it) return; /* should not happen */ + + sd = elm_list_item_data_get(event_info); + fdata.cur_size = sd->size; + + tc_data = elm_list_item_data_get(it); + tc_data->size = fdata.cur_size; + + _font_preview_update(win); +} + +static void +_fstyle_list_unselect_cb(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Evas_Object *sizes_list, *win; + + if (elm_list_selected_item_get(obj)) return; + + win = elm_object_top_widget_get(obj); + + sizes_list = evas_object_data_get(win, "font_sizes_list"); + ELM_LIST_DISABLE(sizes_list); +} + +static void +_fc_list_unselect_cb(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Evas_Object *font_names_list, *styles_list, *sizes_list, *win; + + if (elm_list_selected_item_get(obj)) return; + + win = elm_object_top_widget_get(obj); + + font_names_list = evas_object_data_get(win, "font_names_list"); + ELM_LIST_DISABLE(font_names_list); + + styles_list = evas_object_data_get(win, "font_styles_list"); + ELM_LIST_DISABLE(styles_list); + + sizes_list = evas_object_data_get(win, "font_sizes_list"); + ELM_LIST_DISABLE(sizes_list); +} + +static void +_font_classes_list_load(Evas_Object *li) +{ + Elm_Text_Class_Data *tc_data; + Eina_List *l; + Evas *evas; + + evas = evas_object_evas_get(li); + evas_event_freeze(evas); + edje_freeze(); + + EINA_LIST_FOREACH(fdata.text_classes, l, tc_data) + elm_list_item_append(li, tc_data->desc, NULL, NULL, + _font_classes_list_sel, tc_data); + + evas_object_smart_callback_add(li, "unselected", _fc_list_unselect_cb, + NULL); + + elm_list_go(li); + edje_thaw(); + evas_event_thaw(evas); +} + +static void +_fonts_data_fill(Evas *evas) +{ + const Eina_List *fo_list, *text_classes, *l; + Elm_Text_Class_Data *tc_data; + Elm_Font_Size_Data *sd; + Elm_Font_Overlay *efo; + Eina_List *evas_fonts; + Elm_Text_Class *etc; + int i; + + evas_fonts = evas_font_available_list(evas); + fdata.font_hash = elm_font_available_hash_add(evas_fonts); + evas_font_available_list_free(evas, evas_fonts); + + text_classes = elm_text_classes_list_get(); + fo_list = elm_font_overlay_list_get(); + + EINA_LIST_FOREACH(text_classes, l, etc) + { + const Eina_List *ll; + + tc_data = calloc(1, sizeof(*tc_data)); + tc_data->name = eina_stringshare_add(etc->name); + tc_data->desc = eina_stringshare_add(etc->desc); + + EINA_LIST_FOREACH(fo_list, ll, efo) + { + if (strcmp(tc_data->name, efo->text_class)) + continue; + + if (efo->font) + { + Elm_Font_Properties *efp; + + efp = elm_font_properties_get(efo->font); + if (efp) + { + tc_data->font = eina_stringshare_add(efp->name); + /* we're sure we recorded with only 1 style selected */ + tc_data->style = eina_stringshare_add(efp->styles->data); + elm_font_properties_free(efp); + } + } + tc_data->size = efo->size; + } + + fdata.text_classes = eina_list_append(fdata.text_classes, tc_data); + } + + elm_text_classes_list_free(text_classes); + + /* FIXME: hinting later */ + /* fdata.hinting = e_config->font_hinting; */ + + sd = calloc(1, sizeof(Elm_Font_Size_Data)); + sd->size_str = eina_stringshare_add("Tiny"); + sd->size = -50; + fdata.font_scale_list = eina_list_append(fdata.font_scale_list, sd); + + sd = calloc(1, sizeof(Elm_Font_Size_Data)); + sd->size_str = eina_stringshare_add("Small"); + sd->size = -80; + fdata.font_scale_list = eina_list_append(fdata.font_scale_list, sd); + + sd = calloc(1, sizeof(Elm_Font_Size_Data)); + sd->size_str = eina_stringshare_add("Normal"); + sd->size = -100; + fdata.font_scale_list = eina_list_append(fdata.font_scale_list, sd); + + sd = calloc(1, sizeof(Elm_Font_Size_Data)); + sd->size_str = eina_stringshare_add("Big"); + sd->size = -150; + fdata.font_scale_list = eina_list_append(fdata.font_scale_list, sd); + + sd = calloc(1, sizeof(Elm_Font_Size_Data)); + sd->size_str = eina_stringshare_add("Really Big"); + sd->size = -190; + fdata.font_scale_list = eina_list_append(fdata.font_scale_list, sd); + + sd = calloc(1, sizeof(Elm_Font_Size_Data)); + sd->size_str = eina_stringshare_add("Huge"); + sd->size = -250; + fdata.font_scale_list = eina_list_append(fdata.font_scale_list, sd); + + for (i = 5; i < 51; i++) + { + char str[16]; + + str[0] = 0; + snprintf(str, sizeof(str), "%d pixels", i); + + sd = calloc(1, sizeof(Elm_Font_Size_Data)); + sd->size_str = eina_stringshare_add(str); + sd->size = i; + fdata.font_px_list = eina_list_append(fdata.font_px_list, sd); + } +} + +static int +_font_sort_cb(const void *data1, + const void *data2) +{ + if (!data1) return 1; + if (!data2) return -1; + return strcmp(data1, data2); +} + +static void +_font_sizes_list_load(Evas_Object *size_list) +{ + Elm_Font_Size_Data *size_data; + Eina_List *l; + Evas *evas; + + evas = evas_object_evas_get(size_list); + evas_event_freeze(evas); + edje_freeze(); + + EINA_LIST_FOREACH(fdata.font_scale_list, l, size_data) + elm_list_item_append(size_list, size_data->size_str, NULL, NULL, + _font_sizes_list_sel, size_data); + + EINA_LIST_FOREACH(fdata.font_px_list, l, size_data) + elm_list_item_append(size_list, size_data->size_str, NULL, NULL, + _font_sizes_list_sel, size_data); + + elm_list_go(size_list); + edje_thaw(); + evas_event_thaw(evas); +} + +static void +_fnames_list_unselect_cb(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Evas_Object *styles_list, *sizes_list, *win; + + if (elm_list_selected_item_get(obj)) return; + + win = elm_object_top_widget_get(obj); + + styles_list = evas_object_data_get(win, "font_styles_list"); + ELM_LIST_DISABLE(styles_list); + + sizes_list = evas_object_data_get(win, "font_sizes_list"); + ELM_LIST_DISABLE(sizes_list); +} + +static Eina_Bool +_font_list_fill(const Eina_Hash *hash __UNUSED__, + const void *key __UNUSED__, + void *data, + void *fdata) +{ + Elm_Font_Properties *efp; + Eina_List **flist; + + flist = fdata; + efp = data; + + *flist = eina_list_append(*flist, efp->name); + + return EINA_TRUE; +} + +static void +_font_names_list_load(Evas_Object *flist) +{ + Eina_List *l, *names_list = NULL; + const char *font; + Evas *evas; + + evas = evas_object_evas_get(flist); + evas_event_freeze(evas); + edje_freeze(); + + eina_hash_foreach(fdata.font_hash, _font_list_fill, &names_list); + names_list = eina_list_sort(names_list, eina_list_count(names_list), + _font_sort_cb); + + EINA_LIST_FOREACH(names_list, l, font) + elm_list_item_append(flist, font, NULL, NULL, _font_names_list_sel, NULL); + + EINA_LIST_FREE(names_list, font) ; + + evas_object_smart_callback_add(flist, "unselected", + _fnames_list_unselect_cb, NULL); + + elm_list_go(flist); + + edje_thaw(); + evas_event_thaw(evas); +} + +static void +_status_config_fonts(Evas_Object *win, + Evas_Object *pager) +{ + Evas_Object *base, *fr, *li, *rc, *preview, *sp, *pd, *bt, *bx; + char buf[PATH_MAX]; + + _fonts_data_fill(evas_object_evas_get(win)); + + base = elm_table_add(win); + evas_object_size_hint_weight_set(base, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(base, EVAS_HINT_FILL, EVAS_HINT_FILL); + + /* yeah, dummy rectangles are ugly as hell, but no good way yet of + fixing sizes */ + rc = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(rc, 70, 170); + elm_table_pack(base, rc, 1, 0, 1, 1); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Font Class"); + elm_table_pack(base, fr, 0, 0, 1, 2); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(fr); + + /* FIXME: no multiselection for this list, for now */ + li = elm_list_add(win); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(fr, li); + evas_object_show(li); + + evas_object_data_set(win, "font_classes_list", li); + _font_classes_list_load(li); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Font"); + elm_table_pack(base, fr, 1, 0, 1, 2); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(fr); + + li = elm_list_add(win); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(fr, li); + evas_object_show(li); + + evas_object_data_set(win, "font_names_list", li); + _font_names_list_load(li); + ELM_LIST_DISABLE(li); + + rc = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(rc, 70, 130); + elm_table_pack(base, rc, 1, 2, 1, 1); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Style"); + elm_table_pack(base, fr, 0, 2, 1, 1); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(fr); + ELM_LIST_DISABLE(li); + + li = elm_list_add(win); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(fr, li); + evas_object_show(li); + + evas_object_data_set(win, "font_styles_list", li); + evas_object_smart_callback_add(li, "unselected", _fstyle_list_unselect_cb, + NULL); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Size"); + elm_table_pack(base, fr, 1, 2, 1, 1); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(fr); + + li = elm_list_add(win); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(fr, li); + evas_object_show(li); + + evas_object_data_set(win, "font_sizes_list", li); + _font_sizes_list_load(li); + ELM_LIST_DISABLE(li); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(base, bx, 0, 3, 2, 1); + evas_object_show(bx); + + /* FIXME: what to do here? dedicated widget? some new entry API set? */ + snprintf(buf, sizeof(buf), "%s/objects/font_preview.edj", PACKAGE_DATA_DIR); + preview = elm_layout_add(win); + elm_layout_file_set(preview, buf, "font_preview"); + elm_layout_text_set(preview, "elm.text", "Preview Text — 我真的会写中文"); + evas_object_size_hint_weight_set(preview, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(preview, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(preview); + + elm_box_pack_end(bx, preview); + evas_object_data_set(win, "font_preview", elm_layout_edje_get(preview)); + + ///////////////////////////////////////////// + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, EINA_TRUE); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_table_pack(base, sp, 0, 4, 2, 1); + evas_object_show(sp); + + pd = elm_frame_add(win); + elm_object_style_set(pd, "pad_medium"); + evas_object_size_hint_weight_set(pd, 0.0, 0.0); + evas_object_size_hint_align_set(pd, 0.5, 0.5); + elm_table_pack(base, pd, 0, 5, 2, 1); + evas_object_show(pd); + + bx = elm_box_add(win); + elm_box_horizontal_set(bx, EINA_TRUE); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(bx); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _font_overlay_set_all, win); + elm_button_label_set(bt, "Set to All"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _font_overlay_reset, win); + elm_button_label_set(bt, "Reset"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _font_overlay_reset_all, win); + elm_button_label_set(bt, "Reset All"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _font_overlay_change, win); + elm_button_label_set(bt, "Apply"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + elm_frame_content_set(pd, bx); + + evas_object_data_set(win, "fonts", base); + + elm_pager_content_push(pager, base); +} + +static void +_engines_list_item_del_cb(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + free(data); +} + +static void +_profiles_list_item_del_cb(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + free(data); +} + +static void +_profiles_list_selected_cb(void *data, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + const char *cur_profile = NULL; + const char *sel_profile, *pdir; + Eina_Bool cur_selected; + const char *prof_name; + char buf[PATH_MAX]; + Evas_Object *en; +#ifdef ELM_EFREET + Efreet_Desktop *desk = NULL; +#endif + + sel_profile = data; + if (!sel_profile) + return; + + cur_profile = elm_profile_current_get(); + cur_selected = !strcmp(cur_profile, sel_profile); + + pdir = elm_profile_dir_get(sel_profile, EINA_FALSE); +#ifdef ELM_EFREET + snprintf(buf, sizeof(buf), "%s/profile.desktop", pdir); + desk = efreet_desktop_new(buf); + if ((desk) && (desk->name)) prof_name = desk->name; + else +#endif + prof_name = cur_profile; + + if (!pdir) + elm_object_disabled_set(evas_object_data_get(obj, "prof_reset_btn"), + EINA_TRUE); + else + { + elm_object_disabled_set(evas_object_data_get(obj, "prof_del_btn"), + EINA_TRUE); + elm_object_disabled_set(evas_object_data_get(obj, "prof_reset_btn"), + EINA_FALSE); + elm_object_disabled_set(evas_object_data_get(obj, "prof_use_btn"), + EINA_FALSE); + elm_profile_dir_free(pdir); + } + + snprintf(buf, sizeof(buf), "Selected profile: %s
    ", + prof_name); + elm_label_label_set(evas_object_data_get(obj, "prof_name_lbl"), buf); + + en = evas_object_data_get(obj, "prof_desc_entry"); +#ifdef ELM_EFREET + if (desk) elm_scrolled_entry_entry_set(en, desk->comment); + else +#endif + elm_scrolled_entry_entry_set(en, "Unknown"); + +#ifdef ELM_EFREET + if (desk) efreet_desktop_free(desk); +#endif +} + +static void +_profiles_list_fill(Evas_Object *l_widget, + Eina_List *p_names) +{ + const char *cur_profile = NULL; + const char *profile; + void *sel_it = NULL; + Eina_List *l; + + if (!p_names) + return; + + elm_list_clear(l_widget); + + cur_profile = elm_profile_current_get(); + + EINA_LIST_FOREACH(p_names, l, profile) + { +#ifdef ELM_EFREET + Efreet_Desktop *desk = NULL; +#endif + const char *label, *ext, *pdir; + char buf[PATH_MAX]; + Elm_List_Item *it; + Evas_Object *ic; + + pdir = elm_profile_dir_get(profile, EINA_FALSE); + label = profile; + +#ifdef ELM_EFREET + snprintf(buf, sizeof(buf), "%s/profile.desktop", pdir); + desk = efreet_desktop_new(buf); + if ((desk) && (desk->name)) label = desk->name; +#endif + + buf[0] = 0; + if (pdir) snprintf(buf, sizeof(buf), "%s/icon.edj", pdir); +#ifdef ELM_EFREET + if ((desk) && (desk->icon) && (pdir)) + snprintf(buf, sizeof(buf), "%s/%s", pdir, desk->icon); +#endif + ic = elm_icon_add(l_widget); + ext = strrchr(buf, '.'); + if (ext) + { + if (!strcmp(ext, ".edj")) elm_icon_file_set(ic, buf, "icon"); + else elm_icon_file_set(ic, buf, NULL); + } + + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, + 1, 1); + evas_object_show(ic); + + it = elm_list_item_append(l_widget, label, ic, NULL, + _profiles_list_selected_cb, strdup(profile)); + elm_list_item_del_cb_set(it, _profiles_list_item_del_cb); + if (cur_profile && !strcmp(profile, cur_profile)) + sel_it = it; + + elm_profile_dir_free(pdir); + +#ifdef ELM_EFREET + if (desk) efreet_desktop_free(desk); +#endif + } + + if (sel_it) elm_list_item_selected_set(sel_it, EINA_TRUE); + elm_list_go(l_widget); +} + +static void +_profiles_list_unselect_cb(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + if (elm_list_selected_item_get(obj)) return; + elm_object_disabled_set(evas_object_data_get(obj, "prof_del_btn"), + EINA_TRUE); + elm_object_disabled_set(evas_object_data_get(obj, "prof_reset_btn"), + EINA_TRUE); + elm_object_disabled_set(evas_object_data_get(obj, "prof_use_btn"), + EINA_TRUE); +} + +static void +_status_config_profiles(Evas_Object *win, + Evas_Object *pager) +{ + Evas_Object *li, *bx, *fr_bx1, *fr_bx2, *btn_bx, *fr, *lb, *en, *sp, *pd, + *bt; + Eina_List *profs; + Evas *evas; + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + + fr_bx1 = elm_box_add(win); + evas_object_size_hint_weight_set(fr_bx1, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr_bx1, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_homogenous_set(fr_bx1, EINA_TRUE); + evas_object_show(fr_bx1); + + fr_bx2 = elm_box_add(win); + evas_object_size_hint_weight_set(fr_bx2, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr_bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(fr_bx2); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Available Profiles"); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(fr, fr_bx1); + elm_box_pack_end(bx, fr); + evas_object_show(fr); + + li = elm_list_add(win); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_smart_callback_add(li, "unselected", _profiles_list_unselect_cb, + NULL); + + profs = elm_profile_list_get(); + + evas_object_show(li); + elm_box_pack_end(fr_bx2, li); + + lb = elm_label_add(win); + evas_object_size_hint_weight_set(lb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(lb, EVAS_HINT_FILL, 0.5); + + evas_object_show(lb); + + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_editable_set(en, EINA_FALSE); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(en); + + evas_object_data_set(li, "prof_name_lbl", lb); + evas_object_data_set(li, "prof_desc_entry", en); + + elm_box_pack_end(fr_bx2, lb); + elm_box_pack_end(fr_bx1, fr_bx2); + elm_box_pack_end(fr_bx1, en); + + ///////////////////////////////////////////// + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, EINA_TRUE); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + pd = elm_frame_add(win); + elm_object_style_set(pd, "pad_medium"); + evas_object_size_hint_weight_set(pd, 0.0, 0.0); + evas_object_size_hint_align_set(pd, 0.5, 0.5); + elm_box_pack_end(bx, pd); + evas_object_show(pd); + + btn_bx = elm_box_add(win); + elm_box_horizontal_set(btn_bx, EINA_TRUE); + evas_object_size_hint_weight_set(btn_bx, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(btn_bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(btn_bx); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _profile_use, li); + elm_button_label_set(bt, "Use"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(btn_bx, bt); + evas_object_show(bt); + + evas_object_data_set(li, "prof_use_btn", bt); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _btn_todo, NULL); /* TODO */ + elm_button_label_set(bt, "Delete"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(btn_bx, bt); + evas_object_show(bt); + + evas_object_data_set(li, "prof_del_btn", bt); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _profile_reset, li); + elm_button_label_set(bt, "Reset"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(btn_bx, bt); + evas_object_show(bt); + + evas_object_data_set(li, "prof_reset_btn", bt); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _btn_todo, NULL); /* TODO */ + elm_button_label_set(bt, "Add new"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(btn_bx, bt); + evas_object_show(bt); + + elm_frame_content_set(pd, btn_bx); + + evas = evas_object_evas_get(li); + evas_event_freeze(evas); + edje_freeze(); + + _profiles_list_fill(li, profs); + + elm_profile_list_free(profs); + + edje_thaw(); + evas_event_thaw(evas); + + evas_object_data_set(win, "profiles", bx); + elm_pager_content_push(pager, bx); +} + +static void +_status_config_scrolling(Evas_Object *win, + Evas_Object *pager) +{ + Evas_Object *lb, *pd, *bx, *sl, *sp, *ck, *sc; + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, 0.5); + + sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(sc, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_scroller_bounce_set(sc, EINA_FALSE, EINA_TRUE); + evas_object_show(sc); + elm_scroller_content_set(sc, bx); + + ck = elm_check_add(win); + elm_object_tooltip_text_set(ck, "Set whether scrollers should bounce
    " + "when they reach their viewport's edge
    " + "during a scroll"); + elm_check_label_set(ck, "Enable scroll bounce"); + evas_object_data_set(win, "scroll_bounce_check", ck); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(ck, EVAS_HINT_FILL, 0.5); + elm_check_state_set(ck, elm_scroll_bounce_enabled_get()); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + evas_object_smart_callback_add(ck, "changed", sb_change, NULL); + + LABEL_FRAME_ADD("Scroll bounce friction"); + + sl = elm_slider_add(win); + elm_object_tooltip_text_set(sl, "This is the amount of inertia a
    " + "scroller will impose at bounce animations"); + evas_object_data_set(win, "bounce_friction_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.2f"); + elm_slider_indicator_format_set(sl, "%1.2f"); + elm_slider_min_max_set(sl, 0.0, 4.0); + elm_slider_value_set(sl, elm_scroll_bounce_friction_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", bf_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", bf_change, NULL); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, EINA_TRUE); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + ck = elm_check_add(win); + elm_object_tooltip_text_set(ck, "Set whether scrollers should be
    " + "draggable from any point in their views"); + elm_check_label_set(ck, "Enable thumb scroll"); + evas_object_data_set(win, "thumbscroll_check", ck); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(ck, EVAS_HINT_FILL, 0.5); + elm_check_state_set(ck, elm_scroll_thumbscroll_enabled_get()); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + evas_object_smart_callback_add(ck, "changed", ts_change, NULL); + + LABEL_FRAME_ADD("Thumb scroll threshold"); + + sl = elm_slider_add(win); + elm_object_tooltip_text_set(sl, "This is the number of pixels one should
    " + "travel while dragging a scroller's view
    " + "to actually trigger scrolling"); + evas_object_data_set(win, "thumbscroll_threshold_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.0f pixels"); + elm_slider_indicator_format_set(sl, "%1.0f"); + elm_slider_min_max_set(sl, 8.0, 50.0); + elm_slider_value_set(sl, elm_scroll_thumbscroll_threshold_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", tst_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", tst_change, NULL); + + LABEL_FRAME_ADD("Thumb scroll momentum threshold"); + + sl = elm_slider_add(win); + elm_object_tooltip_text_set(sl, "This is the minimum speed of mouse
    " + "cursor movement which will trigger
    " + "list self scrolling animation after a
    " + "mouse up event (pixels/second)"); + evas_object_data_set(win, "ts_momentum_threshold_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.0f pixels/s"); + elm_slider_indicator_format_set(sl, "%1.0f"); + elm_slider_min_max_set(sl, 10.0, 200.0); + elm_slider_value_set(sl, elm_scroll_thumbscroll_momentum_threshold_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", tsmt_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", tsmt_change, + NULL); + + LABEL_FRAME_ADD("Thumb scroll friction"); + + sl = elm_slider_add(win); + elm_object_tooltip_text_set(sl, "This is the amount of inertia a
    " + "scroller will impose at self scrolling
    " + "animations"); + evas_object_data_set(win, "thumbscroll_friction_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.1f"); + elm_slider_indicator_format_set(sl, "%1.1f"); + elm_slider_min_max_set(sl, 0.0, 15.0); + elm_slider_value_set(sl, elm_scroll_thumbscroll_friction_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", tsf_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", tsf_change, NULL); + + LABEL_FRAME_ADD("Thumb scroll border friction"); + + sl = elm_slider_add(win); + elm_object_tooltip_text_set(sl, "This is the amount of lag between your
    " + "actual mouse cursor dragging movement
    " + "and a scroller's view movement itself,
    " + "while pushing it into bounce state
    " + "manually"); + evas_object_data_set(win, "ts_border_friction_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.2f"); + elm_slider_indicator_format_set(sl, "%1.2f"); + elm_slider_min_max_set(sl, 0.0, 1.0); + elm_slider_value_set(sl, elm_scroll_thumbscroll_border_friction_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", tsbf_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", tsbf_change, NULL); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, EINA_TRUE); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + LABEL_FRAME_ADD("Page scroll friction"); + + sl = elm_slider_add(win); + elm_object_tooltip_text_set(sl, "This is the amount of inertia a
    " + "paged scroller will impose at
    " + "page fitting animations"); + evas_object_data_set(win, "page_scroll_friction_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.1f"); + elm_slider_indicator_format_set(sl, "%1.1f"); + elm_slider_min_max_set(sl, 0.0, 5.0); + elm_slider_value_set(sl, elm_scroll_page_scroll_friction_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", ps_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", ps_change, NULL); + + LABEL_FRAME_ADD("Bring in scroll friction"); + + sl = elm_slider_add(win); + elm_object_tooltip_text_set(sl, "This is the amount of inertia a
    " + "scroller will impose at region bring
    " + "animations"); + evas_object_data_set(win, "bring_in_scroll_friction_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.1f"); + elm_slider_indicator_format_set(sl, "%1.1f"); + elm_slider_min_max_set(sl, 0.0, 5.0); + elm_slider_value_set(sl, elm_scroll_bring_in_scroll_friction_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", bis_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", bis_change, NULL); + + LABEL_FRAME_ADD("Zoom scroll friction"); + + sl = elm_slider_add(win); + elm_object_tooltip_text_set(sl, "This is the amount of inertia
    " + "scrollers will impose at animations
    " + "triggered by Elementary widgets'
    " + "zooming API"); + evas_object_data_set(win, "zoom_scroll_friction_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.1f"); + elm_slider_indicator_format_set(sl, "%1.1f"); + elm_slider_min_max_set(sl, 0.0, 5.0); + elm_slider_value_set(sl, elm_scroll_zoom_friction_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", zf_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", zf_change, NULL); + + evas_object_data_set(win, "scrolling", sc); + + elm_pager_content_push(pager, sc); +} + +static char * +_engine_name_prettify(const char *engine) +{ + char *ret, *ptr; + + ret = strdup(engine); + ret[0] -= 0x20; + + while ((ptr = strpbrk(ret, "_"))) + { + *ptr = ' '; + } + + return ret; +} + +/* FIXME! ideally, we would trim elm_config.c's _elm_engines list at + build time, making a getter for is as in ecore-evas. */ +static Eina_Bool +_elm_engine_supported(const char *engine) +{ + const char *engines[] = { + "software_x11", + "fb", + "directfb", + "software_16_x11", + "software_8_x11", + "xrender_x11", + "opengl_x11", + "software_gdi", + "software_16_wince_gdi", + "sdl", + "software_16_sdl", + "opengl_sdl", + NULL + }; + + unsigned int i; + + for (i = 0; engines[i]; i++) + { +#define ENGINE_COMPARE(name) (!strcmp(engines[i], name)) + if (ENGINE_COMPARE(engine)) + return EINA_TRUE; +#undef ENGINE_COMPARE + } + + return EINA_FALSE; +} + +static void +_engines_list_fill(Evas_Object *l_widget, + Eina_List *e_names) +{ + const char *engine, *cur_engine; + void *sel_it = NULL; + Eina_List *l; + + if (!e_names) + return; + + cur_engine = elm_engine_current_get(); + + EINA_LIST_FOREACH(e_names, l, engine) + { + const char *label; + Elm_List_Item *it; + + if (!_elm_engine_supported(engine)) + continue; + + label = _engine_name_prettify(engine); + + it = elm_list_item_append(l_widget, label, NULL, NULL, NULL, + strdup(engine)); + elm_list_item_del_cb_set(it, _engines_list_item_del_cb); + free((void *)label); + + if (!strcmp(cur_engine, engine)) + sel_it = it; + } + + if (sel_it) elm_list_item_selected_set(sel_it, EINA_TRUE); + elm_list_go(l_widget); +} + +static void +_status_config_rendering(Evas_Object *win, + Evas_Object *pager) +{ + Evas_Object *li, *bx, *fr, *sp, *pd, *bt; + Eina_List *engines; + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Available Engines"); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, fr); + evas_object_show(fr); + + li = elm_list_add(win); + elm_frame_content_set(fr, li); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + + engines = ecore_evas_engines_get(); + _engines_list_fill(li, engines); + ecore_evas_engines_free(engines); + + evas_object_show(li); + evas_object_data_set(win, "engines_list", li); + + ///////////////////////////////////////////// + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, EINA_TRUE); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + pd = elm_frame_add(win); + elm_object_style_set(pd, "pad_medium"); + evas_object_size_hint_weight_set(pd, 0.0, 0.0); + evas_object_size_hint_align_set(pd, 0.5, 0.5); + elm_box_pack_end(bx, pd); + evas_object_show(pd); + + bt = elm_button_add(win); + evas_object_smart_callback_add(bt, "clicked", _engine_use, li); + elm_button_label_set(bt, "Use Engine"); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_frame_content_set(pd, bt); + evas_object_show(bt); + + evas_object_data_set(win, "rendering", bx); + elm_pager_content_push(pager, bx); +} + +static void +_status_config_caches(Evas_Object *win, + Evas_Object *pager) +{ + Evas_Object *lb, *pd, *bx, *sl, *sp, *ck; + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, 0.5); + + LABEL_FRAME_ADD("Cache Flush Interval (8 ticks pre second)"); + + sl = elm_slider_add(win); + evas_object_data_set(win, "cache_flush_interval_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.0f ticks"); + elm_slider_indicator_format_set(sl, "%1.0f"); + elm_slider_min_max_set(sl, 8.0, 4096.0); + elm_slider_value_set(sl, elm_cache_flush_interval_get()); + elm_object_disabled_set(sl, !elm_cache_flush_enmabled_get()); + + ck = elm_check_add(win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(ck, EVAS_HINT_FILL, 0.5); + elm_check_label_set(ck, "Enable Flushing"); + elm_check_state_set(ck, elm_cache_flush_enmabled_get()); + evas_object_smart_callback_add(ck, "changed", cf_enable, sl); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", cf_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", cf_change, NULL); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + LABEL_FRAME_ADD("Font Cache Size"); + + sl = elm_slider_add(win); + evas_object_data_set(win, "font_cache_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.1f MB"); + elm_slider_indicator_format_set(sl, "%1.1f"); + elm_slider_min_max_set(sl, 0.0, 4.0); + elm_slider_value_set(sl, (double)elm_font_cache_get() / 1024.0); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", fc_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", fc_change, NULL); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + LABEL_FRAME_ADD("Image Cache Size"); + + sl = elm_slider_add(win); + evas_object_data_set(win, "image_cache_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.0f MB"); + elm_slider_indicator_format_set(sl, "%1.0f"); + elm_slider_min_max_set(sl, 0, 32); + elm_slider_value_set(sl, (double)elm_image_cache_get() / 1024.0); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", ic_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", ic_change, NULL); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + LABEL_FRAME_ADD("Number of Edje Files to Cache"); + + sl = elm_slider_add(win); + evas_object_data_set(win, "edje_file_cache_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.0f files"); + elm_slider_indicator_format_set(sl, "%1.0f"); + elm_slider_min_max_set(sl, 0, 32); + elm_slider_value_set(sl, elm_edje_file_cache_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", efc_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", efc_change, NULL); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + LABEL_FRAME_ADD("Number of Edje Collections to Cache"); + + sl = elm_slider_add(win); + evas_object_data_set(win, "edje_collection_cache_slider", sl); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + elm_slider_span_size_set(sl, 120); + elm_slider_unit_format_set(sl, "%1.0f collections"); + elm_slider_indicator_format_set(sl, "%1.0f"); + elm_slider_min_max_set(sl, 0, 128); + elm_slider_value_set(sl, elm_edje_collection_cache_get()); + elm_box_pack_end(bx, sl); + evas_object_show(sl); + + evas_object_smart_callback_add(sl, "changed", ecc_round, NULL); + evas_object_smart_callback_add(sl, "delay,changed", ecc_change, NULL); + + evas_object_data_set(win, "caches", bx); + + elm_pager_content_push(pager, bx); +} + +static void +_status_config_full(Evas_Object *win, + Evas_Object *bx0) +{ + Evas_Object *tb, *pager; + Elm_Toolbar_Item *sizing, *it; + + tb = elm_toolbar_add(win); + elm_toolbar_menu_parent_set(tb, win); + elm_toolbar_homogenous_set(tb, 0); + evas_object_size_hint_weight_set(tb, 1.0, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + sizing = elm_toolbar_item_append(tb, "zoom-fit-best", "Sizing", + _cf_sizing, win); + elm_toolbar_item_priority_set(sizing, 100); + + it = elm_toolbar_item_append(tb, "preferences-desktop-theme", "Theme", + _cf_themes, win); + elm_toolbar_item_priority_set(it, 90); + + elm_toolbar_item_append(tb, "preferences-desktop-font", "Fonts", + _cf_fonts, win); + + it = elm_toolbar_item_append(tb, "system-users", "Profiles", + _cf_profiles, win); + elm_toolbar_item_priority_set(it, 90); + + elm_toolbar_item_append(tb, "system-run", "Scrolling", _cf_scrolling, win); + elm_toolbar_item_append(tb, "video-display", "Rendering", + _cf_rendering, win); + elm_toolbar_item_append(tb, "appointment-new", "Caches", _cf_caches, win); + + elm_box_pack_end(bx0, tb); + evas_object_show(tb); + + pager = elm_pager_add(win); + evas_object_size_hint_align_set(pager, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(pager, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_data_set(win, "pager", pager); + + _status_config_themes(win, pager); + _status_config_fonts(win, pager); + _status_config_profiles(win, pager); + _status_config_rendering(win, pager); + _status_config_scrolling(win, pager); + _status_config_caches(win, pager); + _status_config_sizing(win, pager); + + // FIXME uncomment after flip style fix, please + //elm_object_style_set(pager, "flip"); + elm_toolbar_item_selected_set(sizing, EINA_TRUE); + elm_box_pack_end(bx0, pager); + evas_object_show(pager); +} + +static void +status_win(void) +{ + Evas_Object *win, *bg, *bx0; + + win = elm_win_add(NULL, "main", ELM_WIN_BASIC); + elm_win_title_set(win, "Elementary Config"); + + evas_object_smart_callback_add(win, "delete,request", config_exit, NULL); + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, 1.0, 1.0); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + bx0 = elm_box_add(win); + evas_object_size_hint_weight_set(bx0, 1.0, 1.0); + elm_win_resize_object_add(win, bx0); + evas_object_show(bx0); + + if (!interactive) _status_basic(win, bx0); + else if (0) + _status_config(win, bx0); + else _status_config_full(win, bx0); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} + +static Eina_Bool +_exit_timer(void *data __UNUSED__) +{ + elm_exit(); + return ECORE_CALLBACK_CANCEL; +} + +/* this is your elementary main function - it MUST be called IMMEDIATELY + * after elm_init() and MUST be passed argc and argv, and MUST be called + * elm_main and not be static - must be a visible symbol with EAPI infront */ +EAPI int +elm_main(int argc, + char **argv) +{ + int i; + + for (i = 1; i < argc; i++) + { + if (!strcmp(argv[i], "-h")) + { + printf("Usage:\n" + " -h This help\n" + " -q Quiet mode (dont show window)\n" + " -t THEME Set theme to THEME (ELM_THEME spec)\n" + " -f SIZE Set finger size to SIZE pixels\n" + " -s SCALE Set scale factor to SCALE\n" + ); + } + else if (!strcmp(argv[i], "-q")) + { + quiet = 1; + interactive = 0; + } + else if ((!strcmp(argv[i], "-t")) && (i < argc - 1)) + { + i++; + theme_set = argv[i]; + interactive = 0; + } + else if ((!strcmp(argv[i], "-f")) && (i < argc - 1)) + { + i++; + finger_size_set = argv[i]; + interactive = 0; + } + else if ((!strcmp(argv[i], "-s")) && (i < argc - 1)) + { + i++; + scale_set = argv[i]; + interactive = 0; + } + } + /* put here any init code specific to this app like parsing args, etc. */ + if (!quiet) + { +#ifdef ELM_EFREET + elm_need_efreet(); +#endif + status_win(); /* create main window */ + if (!interactive) + ecore_timer_add(2.0, _exit_timer, NULL); + } + if (!interactive) + { + if (theme_set) + { + elm_theme_all_set(theme_set); + } + if (finger_size_set) + { + elm_finger_size_all_set(atoi(finger_size_set)); + } + if (scale_set) + { + elm_scale_all_set(atof(scale_set)); + } + if (quiet) + { + elm_exit(); + } + } + elm_run(); /* and run the program now and handle all events, etc. */ + /* if the mainloop that elm_run() runs exists, we exit the app */ + elm_shutdown(); /* clean up and shut down */ + /* exit code */ + return 0; +} + +#endif +/* All emelentary apps should use this. Put it right after elm_main() */ +ELM_MAIN() diff --git a/src/bin/quicklaunch.c b/src/bin/quicklaunch.c new file mode 100644 index 0000000..50f26ec --- /dev/null +++ b/src/bin/quicklaunch.c @@ -0,0 +1,297 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static double restart_time = 0.0; + +#define LENGTH_OF_SOCKADDR_UN(s) (strlen((s)->sun_path) + (size_t)(((struct sockaddr_un *)NULL)->sun_path)) + +static struct sigaction old_sigint; +static struct sigaction old_sigterm; +static struct sigaction old_sigquit; +static struct sigaction old_sigalrm; +static struct sigaction old_sigusr1; +static struct sigaction old_sigusr2; +static struct sigaction old_sighup; +static struct sigaction old_sigchld; +static struct sigaction old_sigsegv; +static struct sigaction old_sigill; +static struct sigaction old_sigfpe; +static struct sigaction old_sigbus; +static struct sigaction old_sigabrt; +static int _log_dom = -1; + +#define CRITICAL(...) EINA_LOG_DOM_CRIT(_log_dom, __VA_ARGS__) +#define ERR(...) EINA_LOG_DOM_ERR(_log_dom, __VA_ARGS__) +#define WRN(...) EINA_LOG_DOM_WARN(_log_dom, __VA_ARGS__) +#define INF(...) EINA_LOG_DOM_INFO(_log_dom, __VA_ARGS__) +#define DBG(...) EINA_LOG_DOM_DBG(_log_dom, __VA_ARGS__) + +static void +post_fork(void *data __UNUSED__) +{ + sigaction(SIGINT, &old_sigint, NULL); + sigaction(SIGTERM, &old_sigterm, NULL); + sigaction(SIGQUIT, &old_sigquit, NULL); + sigaction(SIGALRM, &old_sigalrm, NULL); + sigaction(SIGUSR1, &old_sigusr1, NULL); + sigaction(SIGUSR2, &old_sigusr2, NULL); + sigaction(SIGHUP, &old_sighup, NULL); + sigaction(SIGCHLD, &old_sigchld, NULL); + sigaction(SIGSEGV, &old_sigsegv, NULL); + sigaction(SIGILL, &old_sigill, NULL); + sigaction(SIGFPE, &old_sigfpe, NULL); + sigaction(SIGBUS, &old_sigbus, NULL); + sigaction(SIGABRT, &old_sigabrt, NULL); + if ((_log_dom > -1) && (_log_dom != EINA_LOG_DOMAIN_GLOBAL)) + { + eina_log_domain_unregister(_log_dom); + _log_dom = -1; + } +} + +static void +child_handler(int x __UNUSED__, siginfo_t *info __UNUSED__, void *data __UNUSED__) +{ + int status; + while (waitpid(-1, &status, WNOHANG) > 0); +} + +static void +crash_handler(int x __UNUSED__, siginfo_t *info __UNUSED__, void *data __UNUSED__) +{ + double t; + + ERR("crash detected. restarting."); + t = ecore_time_get(); + if ((t - restart_time) <= 2.0) + { + CRITICAL("crash too fast - less than 2 seconds. abort restart"); + exit(-1); + } + ecore_app_restart(); +} + +static void +handle_run(int fd, unsigned long bytes) +{ + unsigned char *buf = NULL; + int i; + char **argv = NULL; + char *cwd; + int argc; + + buf = alloca(bytes); + if (read(fd, buf, bytes) < 0) + { + close(fd); + return; + } + close(fd); + argc = ((unsigned long *)(buf))[0]; + argv = (char **)(&(((unsigned long *)(buf))[1])); + for (i = 0; i < argc; i++) argv[i] = (char *)(buf + (unsigned long)argv[i]); + cwd = argv[argc - 1] + strlen(argv[argc - 1]) + 1; + elm_quicklaunch_prepare(argc, argv); + elm_quicklaunch_fork(argc, argv, cwd, post_fork, NULL); + elm_quicklaunch_cleanup(); +} + +int +main(int argc, char **argv) +{ + int sock, socket_unix_len; + struct stat st; + struct sockaddr_un socket_unix; + struct linger lin; + char buf[PATH_MAX]; + struct sigaction action; + + if (!eina_init()) + { + fprintf(stderr, "ERROR: failed to init eina."); + exit(-1); + } + _log_dom = eina_log_domain_register + ("elementary_quicklaunch", EINA_COLOR_CYAN); + if (_log_dom < 0) + { + EINA_LOG_ERR("could not register elementary_quicklaunch log domain."); + _log_dom = EINA_LOG_DOMAIN_GLOBAL; + } + + if (!getenv("DISPLAY")) + { + CRITICAL("DISPLAY env var not set"); + exit(-1); + } + snprintf(buf, sizeof(buf), "/tmp/elm-ql-%i", getuid()); + if (stat(buf, &st) < 0) mkdir(buf, S_IRUSR | S_IWUSR | S_IXUSR); + snprintf(buf, sizeof(buf), "/tmp/elm-ql-%i/%s", getuid(), getenv("DISPLAY")); + unlink(buf); + sock = socket(AF_UNIX, SOCK_STREAM, 0); + if (sock < 0) + { + CRITICAL("cannot create socket for socket for '%s': %s", + buf, strerror(errno)); + exit(-1); + } + if (fcntl(sock, F_SETFD, FD_CLOEXEC) < 0) + { + CRITICAL("cannot set close on exec socket for '%s' (fd=%d): %s", + buf, sock, strerror(errno)); + exit(-1); + } + lin.l_onoff = 1; + lin.l_linger = 0; + if (setsockopt(sock, SOL_SOCKET, SO_LINGER, &lin, sizeof(struct linger)) < 0) + { + CRITICAL("cannot set linger for socket for '%s' (fd=%d): %s", + buf, sock, strerror(errno)); + exit(-1); + } + socket_unix.sun_family = AF_UNIX; + strncpy(socket_unix.sun_path, buf, sizeof(socket_unix.sun_path)); + socket_unix_len = LENGTH_OF_SOCKADDR_UN(&socket_unix); + if (bind(sock, (struct sockaddr *)&socket_unix, socket_unix_len) < 0) + { + CRITICAL("cannot bind socket for '%s' (fd=%d): %s", + buf, sock, strerror(errno)); + exit(-1); + } + if (listen(sock, 4096) < 0) + { + CRITICAL("listen(sock=%d, 4096): %s", sock, strerror(errno)); + exit(-1); + } + elm_quicklaunch_mode_set(EINA_TRUE); + elm_quicklaunch_init(argc, argv); + restart_time = ecore_time_get(); + + memset(&action, 0, sizeof(struct sigaction)); + action.sa_handler = SIG_DFL; + action.sa_sigaction = NULL; + action.sa_flags = SA_RESTART | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGINT, &action, &old_sigint); + + action.sa_handler = SIG_DFL; + action.sa_sigaction = NULL; + action.sa_flags = SA_RESTART | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGTERM, &action, &old_sigterm); + + action.sa_handler = SIG_DFL; + action.sa_sigaction = NULL; + action.sa_flags = SA_RESTART | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGQUIT, &action, &old_sigquit); + + action.sa_handler = SIG_DFL; + action.sa_sigaction = NULL; + action.sa_flags = SA_RESTART | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGALRM, &action, &old_sigalrm); + + action.sa_handler = SIG_DFL; + action.sa_sigaction = NULL; + action.sa_flags = SA_RESTART | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGUSR1, &action, &old_sigusr1); + + action.sa_handler = SIG_DFL; + action.sa_sigaction = NULL; + action.sa_flags = SA_RESTART | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGUSR2, &action, &old_sigusr2); + + action.sa_handler = SIG_DFL; + action.sa_sigaction = NULL; + action.sa_flags = SA_RESTART | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGHUP, &action, &old_sighup); + + action.sa_handler = NULL; + action.sa_sigaction = child_handler; + action.sa_flags = SA_RESTART | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGCHLD, &action, &old_sigchld); + + action.sa_handler = NULL; + action.sa_sigaction = crash_handler; + action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGSEGV, &action, &old_sigsegv); + + action.sa_handler = NULL; + action.sa_sigaction = crash_handler; + action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGILL, &action, &old_sigill); + + action.sa_handler = NULL; + action.sa_sigaction = crash_handler; + action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGFPE, &action, &old_sigfpe); + + action.sa_handler = NULL; + action.sa_sigaction = crash_handler; + action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGBUS, &action, &old_sigbus); + + action.sa_handler = NULL; + action.sa_sigaction = crash_handler; + action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO; + sigemptyset(&action.sa_mask); + sigaction(SIGABRT, &action, &old_sigabrt); + + for (;;) + { + int fd; + struct sockaddr_un client; + socklen_t len; + + elm_quicklaunch_sub_init(argc, argv); + elm_quicklaunch_seed(); + len = sizeof(struct sockaddr_un); + fd = accept(sock, (struct sockaddr *)&client, &len); + if (fd >= 0) + { + unsigned long bytes; + int num; + + num = read(fd, &bytes, sizeof(unsigned long)); + if (num == sizeof(unsigned long)) + { + ecore_app_args_set(argc, (const char **)argv); + handle_run(fd, bytes); + } + } + while (elm_quicklaunch_sub_shutdown() > 0); + } + elm_quicklaunch_shutdown(); + + if ((_log_dom > -1) && (_log_dom != EINA_LOG_DOMAIN_GLOBAL)) + { + eina_log_domain_unregister(_log_dom); + _log_dom = -1; + } + eina_shutdown(); + + return 0; +} diff --git a/src/bin/run.c b/src/bin/run.c new file mode 100644 index 0000000..ebd9833 --- /dev/null +++ b/src/bin/run.c @@ -0,0 +1,160 @@ +#include "elementary_config.h" +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#ifdef HAVE_ALLOCA_H +# include +#endif + +#define LENGTH_OF_SOCKADDR_UN(s) (strlen((s)->sun_path) + (size_t)(((struct sockaddr_un *)NULL)->sun_path)) + +int +main(int argc, char **argv) +{ + int sock, socket_unix_len, i; + struct sockaddr_un socket_unix; + char buf[PATH_MAX]; + struct stat st; + char *exe; + int we_are_elementary_run = 0; + char *disp; + char *cwd; + + int sargc, slen; + unsigned char *sbuf = NULL, *pos; + char **sargv = NULL; + + if (!getcwd(buf, sizeof(buf) - 1)) + { + fprintf(stderr, "elementary_quicklaunch: currect working dir too big.\n"); + exit(-1); + } + cwd = strdup(buf); + if (!(disp = getenv("DISPLAY"))) + { + fprintf(stderr, "elementary_quicklaunch: DISPLAY env var not set\n"); + exit(-1); + } + snprintf(buf, sizeof(buf), "/tmp/elm-ql-%i/%s", getuid(), disp); + if ((sock = socket(AF_UNIX, SOCK_STREAM, 0)) < 0) + { + perror("elementary_quicklaunch: socket(AF_UNIX, SOCK_STREAM, 0)"); + exit(-1); + } + socket_unix.sun_family = AF_UNIX; + strncpy(socket_unix.sun_path, buf, sizeof(socket_unix.sun_path)); + socket_unix_len = LENGTH_OF_SOCKADDR_UN(&socket_unix); + if (connect(sock, (struct sockaddr *)&socket_unix, socket_unix_len) < 0) + { + perror("elementary_quicklaunch: connect(sock, (struct sockaddr *)&socket_unix, socket_unix_len)"); + printf("elementary_quicklaunch: cannot connect to socket '%s'\n", buf); + exit(1); + } + exe = argv[0]; + if (!(((exe[0] == '/')) || + ((exe[0] == '.') && (exe[1] == '/')) || + ((exe[0] == '.') && (exe[1] == '.') && (exe[2] == '/')))) + { + char *path = getenv("PATH"); + int exelen = strlen(argv[0]); + if (path) + { + const char *p, *pp; + + p = path; + pp = p; + exe = NULL; + for (;;) + { + if ((*p == ':') || (!*p)) + { + unsigned int len; + + len = p - pp; + if (len < (sizeof(buf) - exelen - 3)) + { + strncpy(buf, pp, len); + strcpy(buf + len, "/"); + strcpy(buf + len + 1, argv[0]); + if (!access(buf, R_OK | X_OK)) + { + exe = buf; + break; + } + if (!*p) break; + p++; + pp = p; + } + } + else + { + if (!*p) break; + p++; + } + } + } + } + if (exe) + { + if (!lstat(exe, &st)) + { + if (S_ISLNK(st.st_mode)) + { + char buf2[PATH_MAX]; + + ssize_t len = readlink(exe, buf2, sizeof(buf2) - 1); + if (len >= 0) + { + char *p; + buf2[len] = 0; + p = strrchr(buf2, '/'); + if (p) p++; + else p = buf2; + if (!strncasecmp(p, "elementary_run", 14)) + we_are_elementary_run = 1; + } + } + } + } + if (we_are_elementary_run) + { + sargc = argc; + sargv = argv; + } + else + { + sargc = argc - 1; + sargv = &(argv[1]); + } + slen = sizeof(unsigned long) + sizeof(unsigned long); + for (i = 0; i < sargc; i++) + { + slen += sizeof(unsigned long); + slen += strlen(sargv[i]) + 1; + } + slen += strlen(cwd) + 1; + sbuf = alloca(slen); + ((unsigned long *)(sbuf))[0] = slen - sizeof(unsigned long); + ((unsigned long *)(sbuf))[1] = sargc; + pos = (unsigned char *)(&((((unsigned long *)(sbuf))[2 + sargc]))); + for (i = 0; i < sargc; i++) + { + ((unsigned long *)(sbuf))[2 + i] = + (unsigned long)pos - ((unsigned long)sbuf + sizeof(unsigned long)); + strcpy((char *)pos, sargv[i]); + pos += strlen(sargv[i]) + 1; + } + strcpy((char *)pos, cwd); + if (write(sock, sbuf, slen) < 0) + printf("elementary_quicklaunch: cannot write to socket '%s'\n", buf); + close(sock); + return 0; +} diff --git a/src/bin/test.c b/src/bin/test.c new file mode 100644 index 0000000..e195fbe --- /dev/null +++ b/src/bin/test.c @@ -0,0 +1,419 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +/* all tests prototypes */ +void test_bg_plain(void *data, Evas_Object *obj, void *event_info); +void test_bg_image(void *data, Evas_Object *obj, void *event_info); +void test_bg_options(void *data, Evas_Object *obj, void *event_info); +void test_icon(void *data, Evas_Object *obj, void *event_info); +void test_box_vert(void *data, Evas_Object *obj, void *event_info); +void test_box_vert2(void *data, Evas_Object *obj, void *event_info); +void test_box_horiz(void *data, Evas_Object *obj, void *event_info); +void test_box_transition(void *data, Evas_Object *obj, void *event_info); +void test_button(void *data, Evas_Object *obj, void *event_info); +void test_transit(void *data, Evas_Object *obj, void *event_info); +void test_transit2(void *data, Evas_Object *obj, void *event_info); +void test_transit3(void *data, Evas_Object *obj, void *event_info); +void test_transit4(void *data, Evas_Object *obj, void *event_info); +void test_transit5(void *data, Evas_Object *obj, void *event_info); +void test_transit6(void *data, Evas_Object *obj, void *event_info); +void test_transit7(void *data, Evas_Object *obj, void *event_info); +void test_transit8(void *data, Evas_Object *obj, void *event_info); +void test_fileselector_button(void *data, Evas_Object *obj, void *event_info); +void test_fileselector_entry(void *data, Evas_Object *obj, void *event_info); +void test_toggle(void *data, Evas_Object *obj, void *event_info); +void test_clock(void *data, Evas_Object *obj, void *event_info); +void test_clock2(void *data, Evas_Object *obj, void *event_info); +void test_check(void *data, Evas_Object *obj, void *event_info); +void test_radio(void *data, Evas_Object *obj, void *event_info); +void test_layout(void *data, Evas_Object *obj, void *event_info); +void test_hover(void *data, Evas_Object *obj, void *event_info); +void test_hover2(void *data, Evas_Object *obj, void *event_info); +void test_entry(void *data, Evas_Object *obj, void *event_info); +void test_entry_scrolled(void *data, Evas_Object *obj, void *event_info); +void test_entry3(void *data, Evas_Object *obj, void *event_info); +void test_entry4(void *data, Evas_Object *obj, void *event_info); +void test_entry5(void *data, Evas_Object *obj, void *event_info); +void test_entry_notepad(void *data, Evas_Object *obj, void *event_info); +void test_anchorview(void *data, Evas_Object *obj, void *event_info); +void test_anchorblock(void *data, Evas_Object *obj, void *event_info); +void test_toolbar(void *data, Evas_Object *obj, void *event_info); +void test_toolbar2(void *data, Evas_Object *obj, void *event_info); +void test_toolbar3(void *data, Evas_Object *obj, void *event_info); +void test_toolbar4(void *data, Evas_Object *obj, void *event_info); +void test_toolbar5(void *data, Evas_Object *obj, void *event_info); +void test_hoversel(void *data, Evas_Object *obj, void *event_info); +void test_list(void *data, Evas_Object *obj, void *event_info); +void test_list_horizontal(void *data, Evas_Object *obj, void *event_info); +void test_list2(void *data, Evas_Object *obj, void *event_info); +void test_list3(void *data, Evas_Object *obj, void *event_info); +void test_list4(void *data, Evas_Object *obj, void *event_info); +void test_list5(void *data, Evas_Object *obj, void *event_info); +void test_inwin(void *data, Evas_Object *obj, void *event_info); +void test_inwin2(void *data, Evas_Object *obj, void *event_info); +void test_scaling(void *data, Evas_Object *obj, void *event_info); +void test_scaling2(void *data, Evas_Object *obj, void *event_info); +void test_slider(void *data, Evas_Object *obj, void *event_info); +void test_actionslider(void *data, Evas_Object *obj, void *event_info); +void test_genlist(void *data, Evas_Object *obj, void *event_info); +void test_genlist2(void *data, Evas_Object *obj, void *event_info); +void test_genlist3(void *data, Evas_Object *obj, void *event_info); +void test_genlist4(void *data, Evas_Object *obj, void *event_info); +void test_genlist5(void *data, Evas_Object *obj, void *event_info); +void test_genlist6(void *data, Evas_Object *obj, void *event_info); +void test_genlist7(void *data, Evas_Object *obj, void *event_info); +void test_genlist8(void *data, Evas_Object *obj, void *event_info); +void test_genlist9(void *data, Evas_Object *obj, void *event_info); +void test_table(void *data, Evas_Object *obj, void *event_info); +void test_gengrid(void *data, Evas_Object *obj, void *event_info); +void test_gengrid2(void *data, Evas_Object *obj, void *event_info); +void test_pager(void *data, Evas_Object *obj, void *event_info); +void test_pager_slide(void *data, Evas_Object *obj, void *event_info); +void test_win_state(void *data, Evas_Object *obj, void *event_info); +void test_win_state2(void *data, Evas_Object *obj, void *event_info); +void test_progressbar(void *data, Evas_Object *obj, void *event_info); +void test_fileselector(void *data, Evas_Object *obj, void *event_info); +void test_separator(void *data, Evas_Object *obj, void *event_info); +void test_scroller(void *data, Evas_Object *obj, void *event_info); +void test_scroller2(void *data, Evas_Object *obj, void *event_info); +void test_spinner(void *data, Evas_Object *obj, void *event_info); +void test_index(void *data, Evas_Object *obj, void *event_info); +void test_index2(void *data, Evas_Object *obj, void *event_info); +void test_photocam(void *data, Evas_Object *obj, void *event_info); +void test_photo(void *data, Evas_Object *obj, void *event_info); +void test_thumb(void *data, Evas_Object *obj, void *event_info); +void test_icon_desktops(void *data, Evas_Object *obj, void *event_info); +void test_notify(void *data, Evas_Object *obj, void *event_info); +void test_slideshow(void *data, Evas_Object *obj, void *event_info); +void test_menu(void *data, Evas_Object *obj, void *event_info); +void test_panel(void *data, Evas_Object *obj, void *event_info); +void test_panes(void *data, Evas_Object *obj, void *event_info); +void test_calendar(void *data, Evas_Object *obj, void *event_info); +void test_calendar2(void *data, Evas_Object *obj, void *event_info); +void test_map(void *data, Evas_Object *obj, void *event_info); +void test_weather(void *data, Evas_Object *obj, void *event_info); +void test_flip(void *data, Evas_Object *obj, void *event_info); +void test_flip2(void *data, Evas_Object *obj, void *event_info); +void test_flip3(void *data, Evas_Object *obj, void *event_info); +void test_label(void *data, Evas_Object *obj, void *event_info); +void test_conformant(void *data, Evas_Object *obj, void *event_info); +void test_conformant2(void *data, Evas_Object *obj, void *event_info); +void test_multi(void *data, Evas_Object *obj, void *event_info); +void test_floating(void *data, Evas_Object *obj, void *event_info); +void test_launcher(void *data, Evas_Object *obj, void *event_info); +void test_launcher2(void *data, Evas_Object *obj, void *event_info); +void test_launcher3(void *data, Evas_Object *obj, void *event_info); +void test_anim(void *data, Evas_Object *obj, void *event_info); +void test_tooltip(void *data, Evas_Object *obj, void *event_info); +void test_tooltip2(void *data, Evas_Object *obj, void *event_info); +void test_cursor(void *data, Evas_Object *obj, void *event_info); +void test_cursor2(void *data, Evas_Object *obj, void *event_info); +void test_cursor3(void *data, Evas_Object *obj, void *event_info); +void test_focus(void *data, Evas_Object *obj, void *event_info); +void test_focus2(void *data, Evas_Object *obj, void *event_info); +void test_flipselector(void *data, Evas_Object *obj, void *event_info); +void test_diskselector(void *data, Evas_Object *obj, void *event_info); +void test_colorselector(void *data, Evas_Object *obj, void *event_info); +void test_ctxpopup(void *data, Evas_Object *obj, void *event_info); +void test_bubble(void *data, Evas_Object *obj, void *event_info); +void test_store(void *data, Evas_Object *obj, void *event_info); + +struct elm_test +{ + const char *name; + void (*cb)(void *, Evas_Object *, void *); +}; + +static int +elm_test_sort(const void *pa, const void *pb) +{ + const struct elm_test *a = pa, *b = pb; + return strcasecmp(a->name, b->name); +} + +static void +elm_test_add(Eina_List **p_list, const char *name, void (*cb)(void *, Evas_Object *, void *)) +{ + struct elm_test *t = malloc(sizeof(struct elm_test)); + t->name = name; + t->cb = cb; + *p_list = eina_list_sorted_insert(*p_list, elm_test_sort, t); +} + +static void +my_win_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + /* called when my_win_main is requested to be deleted */ + elm_exit(); /* exit the program's main loop that runs in elm_run() */ +} + +static void +index_changed(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + elm_list_item_show(event_info); +} + +static void +my_win_main(char *autorun) +{ + Evas_Object *win, *bg, *bx0, *lb, *li, *idx, *fr; + Eina_List *tests, *l; + struct elm_test *t; + + /* 1 create an elm window - it returns an evas object. this is a little + * special as the object lives in the canvas that is inside the window + * so what is returned is really inside the window, but as you manipulate + * the evas object returned - the window will respond. elm_win makes sure + * of that so you can blindly treat it like any other evas object + * pretty much, just as long as you know it has special significance */ + /* the first parameter is a "parent" window - eg for a dialog you want to + * have a main window it is related to, here it is NULL meaning there + * is no parent. "main" is the name of the window - used by the window + * manager for identifying the window uniquely amongst all the windows + * within this application (and all instances of the application). the + * type is a basic window (the final parameter) */ + win = elm_win_add(NULL, "main", ELM_WIN_BASIC); + /* set the title of the window - this is in the titlebar */ + elm_win_title_set(win, "Elementary Tests"); + + /* set a callback on the window when "delete,request" is emitted as + * a callback. when this happens my_win_del() is called and the + * data pointer (first param) is passed the final param here (in this + * case it is NULL). This is how you can pass specific things to a + * callback like objects or data layered on top */ + evas_object_smart_callback_add(win, "delete,request", my_win_del, NULL); + + /* add a background to our window. this just uses the standard theme set + * background. without a background, you could make a window seem + * transparent with elm_win_alpha_set(win, 1); for example. if you have + * a compositor running this will make the window able to be + * semi-transparent and any space not filled by object/widget pixels will + * be transparent or translucent based on alpha. if you do not have a + * comnpositor running this should fall back to using shaped windows + * (which have a mask). both these features will be slow and rely on + * a lot more resources, so only use it if you need it. */ + bg = elm_bg_add(win); + /* set weight to 1.0 x 1.0 == expand in both x and y direction */ + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + /* tell the window that this object is to be resized along with the window. + * also as a result this object will be one of several objects that + * controls the minimum/maximum size of the window */ + elm_win_resize_object_add(win, bg); + /* and show the background */ + evas_object_show(bg); + + /* add a box layout widget to the window */ + bx0 = elm_box_add(win); + /* allow base box (bx0) to expand in x and y */ + evas_object_size_hint_weight_set(bx0, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + /* tell the window that the box affects window size and also will be + * resized when the window is */ + elm_win_resize_object_add(win, bx0); + evas_object_show(bx0); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Information"); + elm_box_pack_end(bx0, fr); + evas_object_show(fr); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "Please select a test from the list below
    " + "by clicking the test button to show the
    " + "test window."); + elm_frame_content_set(fr, lb); + evas_object_show(lb); + + li = elm_list_add(win); + elm_list_always_select_mode_set(li, 1); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx0, li); + evas_object_show(li); + + idx = elm_index_add(win); + evas_object_smart_callback_add(idx, "delay,changed", index_changed, NULL); + evas_object_size_hint_weight_set(idx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, idx); + evas_object_show(idx); + + tests = NULL; +#define ADD_TEST(name_, cb_) elm_test_add(&tests, name_, cb_) + ADD_TEST("Bg Plain", test_bg_plain); + ADD_TEST("Bg Image", test_bg_image); + ADD_TEST("Bg Options", test_bg_options); + ADD_TEST("Icon Transparent", test_icon); + ADD_TEST("Box Vert", test_box_vert); + ADD_TEST("Box Vert 2", test_box_vert2); + ADD_TEST("Box Horiz", test_box_horiz); + ADD_TEST("Box Transition", test_box_transition); + ADD_TEST("Buttons", test_button); + ADD_TEST("Transit", test_transit); + ADD_TEST("Transit 2", test_transit2); + ADD_TEST("Transit 3", test_transit3); + ADD_TEST("Transit 4", test_transit4); + ADD_TEST("Transit 5", test_transit5); + ADD_TEST("Transit 6", test_transit6); + ADD_TEST("Transit 7", test_transit7); + ADD_TEST("Transit 8", test_transit8); + ADD_TEST("File Selector Button", test_fileselector_button); + ADD_TEST("File Selector Entry", test_fileselector_entry); + ADD_TEST("Toggles", test_toggle); + ADD_TEST("Table", test_table); + ADD_TEST("Clock", test_clock); + ADD_TEST("Clock 2", test_clock2); + ADD_TEST("Layout", test_layout); + ADD_TEST("Hover", test_hover); + ADD_TEST("Hover 2", test_hover2); + ADD_TEST("Entry", test_entry); + ADD_TEST("Entry Scrolled", test_entry_scrolled); + ADD_TEST("Entry 3", test_entry3); + ADD_TEST("Entry 4", test_entry4); + ADD_TEST("Entry 5", test_entry5); + ADD_TEST("Entry Notepad", test_entry_notepad); + ADD_TEST("Anchorview", test_anchorview); + ADD_TEST("Anchorblock", test_anchorblock); + ADD_TEST("Toolbar", test_toolbar); + ADD_TEST("Toolbar 2", test_toolbar2); + ADD_TEST("Toolbar 3", test_toolbar3); + ADD_TEST("Toolbar 4", test_toolbar4); + ADD_TEST("Toolbar 5", test_toolbar5); + ADD_TEST("Hoversel", test_hoversel); + ADD_TEST("List", test_list); + ADD_TEST("List - Horizontal", test_list_horizontal); + ADD_TEST("List 2", test_list2); + ADD_TEST("List 3", test_list3); + ADD_TEST("List 4", test_list4); + ADD_TEST("List 5", test_list5); + ADD_TEST("Inwin", test_inwin); + ADD_TEST("Inwin 2", test_inwin2); + ADD_TEST("Scaling", test_scaling); + ADD_TEST("Scaling 2", test_scaling2); + ADD_TEST("Slider", test_slider); + ADD_TEST("Actionslider", test_actionslider); + ADD_TEST("Genlist", test_genlist); + ADD_TEST("Genlist 2", test_genlist2); + ADD_TEST("Genlist 3", test_genlist3); + ADD_TEST("Genlist 4", test_genlist4); + ADD_TEST("Genlist 5", test_genlist5); + ADD_TEST("Genlist 7", test_genlist7); + ADD_TEST("Genlist Tree", test_genlist6); + ADD_TEST("Genlist Group", test_genlist8); + ADD_TEST("Genlist Group Tree", test_genlist9); + ADD_TEST("GenGrid", test_gengrid); + ADD_TEST("GenGrid 2", test_gengrid2); + ADD_TEST("Checks", test_check); + ADD_TEST("Radios", test_radio); + ADD_TEST("Pager", test_pager); + ADD_TEST("Pager Slide", test_pager_slide); + ADD_TEST("Window States", test_win_state); + ADD_TEST("Window States 2", test_win_state2); + ADD_TEST("Progressbar", test_progressbar); + ADD_TEST("File Selector", test_fileselector); + ADD_TEST("Separator", test_separator); + ADD_TEST("Scroller", test_scroller); + ADD_TEST("Scroller 2", test_scroller2); + ADD_TEST("Spinner", test_spinner); + ADD_TEST("Index", test_index); + ADD_TEST("Index 2", test_index2); + ADD_TEST("Photocam", test_photocam); + ADD_TEST("Photo", test_photo); + ADD_TEST("Thumb", test_thumb); + ADD_TEST("Icon Desktops", test_icon_desktops); + ADD_TEST("Notify", test_notify); + ADD_TEST("Slideshow", test_slideshow); + ADD_TEST("Menu", test_menu); + ADD_TEST("Panel", test_panel); + ADD_TEST("Panes", test_panes); + ADD_TEST("Map", test_map); + ADD_TEST("Weather", test_weather); + ADD_TEST("Flip", test_flip); + ADD_TEST("Flip 2", test_flip2); + ADD_TEST("Flip 3", test_flip3); + ADD_TEST("Label", test_label); + ADD_TEST("Conformant", test_conformant); + ADD_TEST("Conformant 2", test_conformant2); + ADD_TEST("Multi Touch", test_multi); + ADD_TEST("Floating Objects", test_floating); + ADD_TEST("Launcher", test_launcher); + ADD_TEST("Launcher 2", test_launcher2); + ADD_TEST("Launcher 3", test_launcher3); + ADD_TEST("Animation", test_anim); + ADD_TEST("Calendar", test_calendar); + ADD_TEST("Calendar 2", test_calendar2); + ADD_TEST("Tooltip", test_tooltip); + ADD_TEST("Tooltip2", test_tooltip2); + ADD_TEST("Cursor", test_cursor); + ADD_TEST("Cursor 2", test_cursor2); + ADD_TEST("Cursor 3", test_cursor3); + ADD_TEST("Focus", test_focus); + ADD_TEST("Focus 2", test_focus2); + ADD_TEST("Flip Selector", test_flipselector); + ADD_TEST("Disk Selector", test_diskselector); + ADD_TEST("Color Selector", test_colorselector); + ADD_TEST("Ctxpopup", test_ctxpopup); + ADD_TEST("Bubble", test_bubble); + ADD_TEST("Store", test_store); +#undef ADD_TEST + + if (autorun) + { + EINA_LIST_FOREACH(tests, l, t) + if ((t->name) && (t->cb) && (!strcmp(t->name, autorun))) + t->cb(NULL, NULL, NULL); + } + + if (tests) + { + char last_letter = 0; + EINA_LIST_FREE(tests, t) + { + Elm_List_Item *it; + it = elm_list_item_append(li, t->name, NULL, NULL, t->cb, NULL); + if (last_letter != t->name[0]) + { + char letter[2] = {t->name[0], '\0'}; + elm_index_item_append(idx, letter, it); + last_letter = t->name[0]; + } + free(t); + } + elm_index_item_go(idx, 0); + } + + elm_list_go(li); + + /* set an initial window size */ + evas_object_resize(win, 320, 480); + /* show the window */ + evas_object_show(win); +} + +/* this is your elementary main function - it MUSt be called IMMEDIATELY + * after elm_init() and MUSt be passed argc and argv, and MUST be called + * elm_main and not be static - must be a visible symbol with EAPI infront */ +EAPI int +elm_main(int argc, char **argv) +{ + char *autorun = NULL; + + /* if called with a single argument try to autorun a test with + * the same name as the given param + * ex: elementary_test "Box Vert 2" */ + if (argc == 2) + autorun = argv[1]; + + /* put here any init specific to this app like parsing args etc. */ + my_win_main(autorun); /* create main window */ + elm_run(); /* and run the program now and handle all events etc. */ + /* if the mainloop that elm_run() runs exist - we exit the app */ + elm_shutdown(); /* clean up and shut down */ + /* exit code */ + return 0; +} +#endif +/* all emeentary apps should use this. but it right after elm_main() */ +ELM_MAIN() diff --git a/src/bin/test_actionslider.c b/src/bin/test_actionslider.c new file mode 100644 index 0000000..973f532 --- /dev/null +++ b/src/bin/test_actionslider.c @@ -0,0 +1,131 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void _pos_selected_cb(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + printf("Selection: %s\n", (char *)event_info); + printf("Label selected: %s\n", elm_actionslider_selected_label_get(obj)); +} + +static void +_position_change_magnetic_cb(void *data __UNUSED__, Evas_Object * obj, void *event_info) +{ + if (!strcmp((char *)event_info, "left")) + elm_actionslider_magnet_pos_set(obj, ELM_ACTIONSLIDER_LEFT); + else if (!strcmp((char *)event_info, "right")) + elm_actionslider_magnet_pos_set(obj, ELM_ACTIONSLIDER_RIGHT); +} + +static void +_magnet_enable_disable_cb(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + if (!strcmp((char *)event_info, "left")) + elm_actionslider_magnet_pos_set(obj, ELM_ACTIONSLIDER_CENTER); + else if (!strcmp((char *)event_info, "right")) + elm_actionslider_magnet_pos_set(obj, ELM_ACTIONSLIDER_NONE); +} + +void +test_actionslider(void *data __UNUSED__, Evas_Object * obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *ms; + + win = elm_win_add(NULL, "actionslider", ELM_WIN_BASIC); + elm_win_title_set(win, "Actionslider"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, 0); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, 0); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + ms = elm_actionslider_add(win); + evas_object_size_hint_weight_set(ms, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(ms, EVAS_HINT_FILL, 0); + elm_actionslider_indicator_pos_set(ms, ELM_ACTIONSLIDER_RIGHT); + elm_actionslider_magnet_pos_set(ms, ELM_ACTIONSLIDER_RIGHT); + elm_actionslider_labels_set(ms, "Snooze", NULL, "Stop"); + elm_actionslider_enabled_pos_set(ms, ELM_ACTIONSLIDER_LEFT | + ELM_ACTIONSLIDER_RIGHT); + evas_object_smart_callback_add(ms, "pos_changed", + _position_change_magnetic_cb, NULL); + evas_object_smart_callback_add(ms, "selected", _pos_selected_cb, NULL); + evas_object_show(ms); + elm_box_pack_end(bx, ms); + + ms = elm_actionslider_add(win); + evas_object_size_hint_weight_set(ms, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(ms, EVAS_HINT_FILL, 0); + elm_actionslider_indicator_pos_set(ms, ELM_ACTIONSLIDER_CENTER); + elm_actionslider_magnet_pos_set(ms, ELM_ACTIONSLIDER_CENTER); + elm_actionslider_labels_set(ms, "Snooze", NULL, "Stop"); + elm_actionslider_enabled_pos_set(ms, ELM_ACTIONSLIDER_LEFT | + ELM_ACTIONSLIDER_RIGHT); + evas_object_smart_callback_add(ms, "selected", _pos_selected_cb, NULL); + evas_object_show(ms); + elm_box_pack_end(bx, ms); + + ms = elm_actionslider_add(win); + elm_object_style_set(ms, "bar"); + evas_object_size_hint_weight_set(ms, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(ms, EVAS_HINT_FILL, 0); + elm_actionslider_indicator_pos_set(ms, ELM_ACTIONSLIDER_LEFT); + elm_actionslider_magnet_pos_set(ms, ELM_ACTIONSLIDER_CENTER| + ELM_ACTIONSLIDER_RIGHT); + elm_actionslider_enabled_pos_set(ms, ELM_ACTIONSLIDER_CENTER | + ELM_ACTIONSLIDER_RIGHT); + elm_actionslider_labels_set(ms, NULL, "Accept", "Reject"); + evas_object_smart_callback_add(ms, "selected", _pos_selected_cb, NULL); + evas_object_show(ms); + elm_box_pack_end(bx, ms); + + ms = elm_actionslider_add(win); + elm_object_style_set(ms, "bar"); + evas_object_size_hint_weight_set(ms, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(ms, EVAS_HINT_FILL, 0); + elm_actionslider_indicator_pos_set(ms, ELM_ACTIONSLIDER_LEFT); + elm_actionslider_magnet_pos_set(ms, ELM_ACTIONSLIDER_LEFT); + elm_actionslider_labels_set(ms, NULL, "Accept", "Reject"); + elm_actionslider_indicator_label_set(ms, "Go"); + evas_object_smart_callback_add(ms, "pos_changed", + _position_change_magnetic_cb, NULL); + evas_object_smart_callback_add(ms, "selected", _pos_selected_cb, NULL); + evas_object_show(ms); + elm_box_pack_end(bx, ms); + + + ms = elm_actionslider_add(win); + evas_object_size_hint_weight_set(ms, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(ms, EVAS_HINT_FILL, 0); + elm_actionslider_indicator_pos_set(ms, ELM_ACTIONSLIDER_LEFT); + elm_actionslider_magnet_pos_set(ms, ELM_ACTIONSLIDER_ALL); + elm_actionslider_labels_set(ms, "Left", "Center", "Right"); + elm_actionslider_indicator_label_set(ms, "Go"); + evas_object_smart_callback_add(ms, "selected", _pos_selected_cb, NULL); + evas_object_show(ms); + elm_box_pack_end(bx, ms); + + ms = elm_actionslider_add(win); + evas_object_size_hint_weight_set(ms, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(ms, EVAS_HINT_FILL, 0); + elm_actionslider_indicator_pos_set(ms, ELM_ACTIONSLIDER_CENTER); + elm_actionslider_magnet_pos_set(ms, ELM_ACTIONSLIDER_CENTER); + elm_actionslider_labels_set(ms, "Enable", "Magnet", "Disable"); + evas_object_smart_callback_add(ms, "pos_changed", + _magnet_enable_disable_cb, NULL); + evas_object_smart_callback_add(ms, "selected", _pos_selected_cb, NULL); + evas_object_show(ms); + elm_box_pack_end(bx, ms); + + evas_object_resize(win, 320, 400); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_anchorblock.c b/src/bin/test_anchorblock.c new file mode 100644 index 0000000..89c7f83 --- /dev/null +++ b/src/bin/test_anchorblock.c @@ -0,0 +1,243 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void +_print_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("bubble clicked\n"); +} + +static void +my_anchorblock_bt(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *av = data; + elm_anchorblock_hover_end(av); +} + +static void +my_anchorblock_anchor(void *data, Evas_Object *obj, void *event_info) +{ + Evas_Object *av = data; + Elm_Entry_Anchorblock_Info *ei = event_info; + Evas_Object *bt, *bx; + + bt = elm_button_add(obj); + elm_button_label_set(bt, ei->name); + elm_hover_content_set(ei->hover, "middle", bt); + evas_object_show(bt); + + // hints as to where we probably should put hover contents (buttons etc.). + if (ei->hover_top) + { + bx = elm_box_add(obj); + bt = elm_button_add(obj); + elm_button_label_set(bt, "Top 1"); + elm_box_pack_end(bx, bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorblock_bt, av); + evas_object_show(bt); + bt = elm_button_add(obj); + elm_button_label_set(bt, "Top 2"); + elm_box_pack_end(bx, bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorblock_bt, av); + evas_object_show(bt); + bt = elm_button_add(obj); + elm_button_label_set(bt, "Top 3"); + elm_box_pack_end(bx, bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorblock_bt, av); + evas_object_show(bt); + elm_hover_content_set(ei->hover, "top", bx); + evas_object_show(bx); + } + if (ei->hover_bottom) + { + bt = elm_button_add(obj); + elm_button_label_set(bt, "Bot"); + elm_hover_content_set(ei->hover, "bottom", bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorblock_bt, av); + evas_object_show(bt); + } + if (ei->hover_left) + { + bt = elm_button_add(obj); + elm_button_label_set(bt, "Left"); + elm_hover_content_set(ei->hover, "left", bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorblock_bt, av); + evas_object_show(bt); + } + if (ei->hover_right) + { + bt = elm_button_add(obj); + elm_button_label_set(bt, "Right"); + elm_hover_content_set(ei->hover, "right", bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorblock_bt, av); + evas_object_show(bt); + } +} + +static void +my_anchorblock_edge_left(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("left\n"); +} + +static void +my_anchorblock_edge_right(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("right\n"); +} + +static void +my_anchorblock_edge_top(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("top\n"); +} + +static void +my_anchorblock_edge_bottom(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("bottom\n"); +} + +static void +my_anchorblock_scroll(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Coord x, y, w, h, vw, vh; + + elm_scroller_region_get(obj, &x, &y, &w, &h); + elm_scroller_child_size_get(obj, &vw, &vh); + printf("scroll %ix%i +%i+%i in %ix%i\n", w, h, x, y, vw, vh); +} + +void +test_anchorblock(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *av, *sc, *bx, *bb, *ic; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "anchorblock", ELM_WIN_BASIC); + elm_win_title_set(win, "Anchorblock"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, sc); + + evas_object_smart_callback_add(sc, "edge_left", my_anchorblock_edge_left, NULL); + evas_object_smart_callback_add(sc, "edge_right", my_anchorblock_edge_right, NULL); + evas_object_smart_callback_add(sc, "edge_top", my_anchorblock_edge_top, NULL); + evas_object_smart_callback_add(sc, "edge_bottom", my_anchorblock_edge_bottom, NULL); + evas_object_smart_callback_add(sc, "scroll", my_anchorblock_scroll, NULL); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_HORIZONTAL, 1, 1); + + bb = elm_bubble_add(win); + elm_bubble_label_set(bb, "Message 3"); + elm_bubble_info_set(bb, "10:32 4/11/2008"); + elm_bubble_icon_set(bb, ic); + evas_object_smart_callback_add(bb, "clicked", _print_clicked, NULL); + evas_object_show(ic); + evas_object_size_hint_weight_set(bb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bb, EVAS_HINT_FILL, EVAS_HINT_FILL); + av = elm_anchorblock_add(win); + elm_anchorblock_hover_style_set(av, "popout"); + elm_anchorblock_hover_parent_set(av, win); + elm_anchorblock_text_set(av, + "Hi there. This is the most recent message in the " + "list of messages. It has one +61 432 1234 " + "(phone number) to click on."); + evas_object_smart_callback_add(av, "anchor,clicked", + my_anchorblock_anchor, av); + elm_bubble_content_set(bb, av); + evas_object_show(av); + elm_box_pack_end(bx, bb); + evas_object_show(bb); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + + bb = elm_bubble_add(win); + elm_bubble_label_set(bb, "Message 2"); + elm_bubble_info_set(bb, "7:16 27/10/2008"); + elm_bubble_icon_set(bb, ic); + evas_object_smart_callback_add(bb, "clicked", _print_clicked, NULL); + evas_object_show(ic); + evas_object_size_hint_weight_set(bb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bb, EVAS_HINT_FILL, EVAS_HINT_FILL); + av = elm_anchorblock_add(win); + elm_anchorblock_hover_style_set(av, "popout"); + elm_anchorblock_hover_parent_set(av, win); + elm_anchorblock_text_set(av, + "Hey what are you doing? This is the second last message " + "Hi there. This is the most recent message in the " + "list. It's a longer one so it can wrap more and " + "contains a John contact " + "link in it to test popups on links. The idea is that " + "all SMS's are scanned for things that look like phone " + "numbers or names that are in your contacts list, and " + "if they are, they become clickable links that pop up " + "a menus of obvious actions to perform on this piece " + "of information. This of course can be later explicitly " + "done by links maybe running local apps or even being " + "web URL's too that launch the web browser and point it " + "to that URL. "); + evas_object_smart_callback_add(av, "anchor,clicked", my_anchorblock_anchor, av); + elm_bubble_content_set(bb, av); + evas_object_show(av); + elm_box_pack_end(bx, bb); + evas_object_show(bb); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_HORIZONTAL, 1, 1); + + bb = elm_bubble_add(win); + elm_bubble_label_set(bb, "Message 1"); + elm_bubble_info_set(bb, "20:47 18/6/2008"); + elm_bubble_icon_set(bb, ic); + evas_object_smart_callback_add(bb, "clicked", _print_clicked, NULL); + evas_object_show(ic); + evas_object_size_hint_weight_set(bb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + av = elm_anchorblock_add(win); + elm_anchorblock_hover_style_set(av, "popout"); + elm_anchorblock_hover_parent_set(av, win); + elm_anchorblock_text_set(av, "This is a short message. "); + evas_object_smart_callback_add(av, "anchor,clicked", + my_anchorblock_anchor, av); + elm_bubble_content_set(bb, av); + evas_object_show(av); + elm_box_pack_end(bx, bb); + evas_object_show(bb); + + elm_scroller_content_set(sc, bx); + evas_object_show(bx); + + evas_object_show(sc); + + evas_object_resize(win, 320, 300); + + elm_object_focus(win); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_anchorview.c b/src/bin/test_anchorview.c new file mode 100644 index 0000000..9d79664 --- /dev/null +++ b/src/bin/test_anchorview.c @@ -0,0 +1,108 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +static void +my_anchorview_bt(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *av = data; + elm_anchorview_hover_end(av); +} + +static void +my_anchorview_anchor(void *data, Evas_Object *obj, void *event_info) +{ + Evas_Object *av = data; + Elm_Entry_Anchorview_Info *ei = event_info; + Evas_Object *bt, *bx; + + bt = elm_button_add(obj); + elm_button_label_set(bt, ei->name); + elm_hover_content_set(ei->hover, "middle", bt); + evas_object_show(bt); + + // hints as to where we probably should put hover contents (buttons etc.). + if (ei->hover_top) + { + bx = elm_box_add(obj); + bt = elm_button_add(obj); + elm_button_label_set(bt, "Top 1"); + elm_box_pack_end(bx, bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorview_bt, av); + evas_object_show(bt); + bt = elm_button_add(obj); + elm_button_label_set(bt, "Top 2"); + elm_box_pack_end(bx, bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorview_bt, av); + evas_object_show(bt); + bt = elm_button_add(obj); + elm_button_label_set(bt, "Top 3"); + elm_box_pack_end(bx, bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorview_bt, av); + evas_object_show(bt); + elm_hover_content_set(ei->hover, "top", bx); + evas_object_show(bx); + } + if (ei->hover_bottom) + { + bt = elm_button_add(obj); + elm_button_label_set(bt, "Bot"); + elm_hover_content_set(ei->hover, "bottom", bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorview_bt, av); + evas_object_show(bt); + } + if (ei->hover_left) + { + bt = elm_button_add(obj); + elm_button_label_set(bt, "Left"); + elm_hover_content_set(ei->hover, "left", bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorview_bt, av); + evas_object_show(bt); + } + if (ei->hover_right) + { + bt = elm_button_add(obj); + elm_button_label_set(bt, "Right"); + elm_hover_content_set(ei->hover, "right", bt); + evas_object_smart_callback_add(bt, "clicked", my_anchorview_bt, av); + evas_object_show(bt); + } +} + +void +test_anchorview(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *av; + + win = elm_win_add(NULL, "anchorview", ELM_WIN_BASIC); + elm_win_title_set(win, "Anchorview"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + av = elm_anchorview_add(win); + elm_anchorview_hover_style_set(av, "popout"); + elm_anchorview_hover_parent_set(av, win); + elm_anchorview_text_set(av, + "This is an entry widget in this window that
    " + "uses markup like this for styling and
    " + "formatting like this, as well as
    " + "links in the text, so enter text
    " + "in here to edit it. By the way, links are
    " + "called Anchors so you will need
    " + "to refer to them this way. "); + evas_object_size_hint_weight_set(av, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_smart_callback_add(av, "anchor,clicked", my_anchorview_anchor, av); + elm_win_resize_object_add(win, av); + evas_object_show(av); + + evas_object_resize(win, 320, 300); + + elm_object_focus(win); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_anim.c b/src/bin/test_anim.c new file mode 100644 index 0000000..2601ef4 --- /dev/null +++ b/src/bin/test_anim.c @@ -0,0 +1,113 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static const char *names[] = +{ + "bub1", "sh1", + "bub2", "sh2", + "bub3", "sh3", +}; + +static void +_del(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Ecore_Animator *ani = evas_object_data_get(win, "animator"); + + ecore_animator_del(ani); +} + +static Eina_Bool +anim(void *data) +{ + Evas_Object *win = data; + Evas_Object *bub, *sh; + Evas_Coord x, y, w, h, vw, vh; + double t, xx, yy, zz, r, fac; + double lx, ly; + unsigned int i; + + evas_output_viewport_get(evas_object_evas_get(win), 0, 0, &vw, &vh); + r = 48; + t = ecore_loop_time_get(); + fac = 2.0 / (double)((sizeof(names) / sizeof(char *) / 2)); + evas_pointer_canvas_xy_get(evas_object_evas_get(win), &x, &y); + lx = x; + ly = y; + + for (i = 0; i < (sizeof(names) / sizeof(char *) / 2); i++) + { + bub = evas_object_data_get(win, names[i * 2]); + sh = evas_object_data_get(win, names[(i * 2) + 1]); + zz = (((2 + sin(t * 6 + (M_PI * (i * fac)))) / 3) * 64) * 2; + xx = (cos(t * 4 + (M_PI * (i * fac))) * r) * 2; + yy = (sin(t * 6 + (M_PI * (i * fac))) * r) * 2; + + w = zz; + h = zz; + x = (vw / 2) + xx - (w / 2); + y = (vh / 2) + yy - (h / 2); + + evas_object_move(bub, x, y); + evas_object_resize(bub, w, h); + + x = x - ((lx - (x + (w / 2))) / 4); + y = y - ((ly - (y + (h / 2))) / 4); + + evas_object_move(sh, x, y); + evas_object_resize(sh, w, h); + } + return ECORE_CALLBACK_RENEW; +} + +void +test_anim(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bub, *sh; + Ecore_Animator *ani; + char buf[PATH_MAX]; + unsigned int i; + + win = elm_win_add(NULL, "animation", ELM_WIN_BASIC); + elm_win_title_set(win, "Animation"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/rock_01.jpg", PACKAGE_DATA_DIR); + elm_bg_file_set(bg, buf, NULL); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + snprintf(buf, sizeof(buf), "%s/images/bubble_sh.png", PACKAGE_DATA_DIR); + for (i = 0; i < (sizeof(names) / sizeof(char *) / 2); i++) + { + sh = evas_object_image_filled_add(evas_object_evas_get(win)); + evas_object_image_file_set(sh, buf, NULL); + evas_object_resize(sh, 64, 64); + evas_object_show(sh); + evas_object_data_set(win, names[(i * 2) + 1], sh); + } + + snprintf(buf, sizeof(buf), "%s/images/bubble.png", PACKAGE_DATA_DIR); + for (i = 0; i < (sizeof(names) / sizeof(char *) / 2); i++) + { + bub = evas_object_image_filled_add(evas_object_evas_get(win)); + evas_object_image_file_set(bub, buf, NULL); + evas_object_resize(bub, 64, 64); + evas_object_show(bub); + evas_object_data_set(win, names[(i * 2)], bub); + } + + evas_object_resize(win, 480, 800); + evas_object_show(win); + + ani = ecore_animator_add(anim, win); + evas_object_data_set(win, "animator", ani); + + evas_object_event_callback_add(win, EVAS_CALLBACK_DEL, _del, win); +} +#endif diff --git a/src/bin/test_bg.c b/src/bin/test_bg.c new file mode 100644 index 0000000..a30b870 --- /dev/null +++ b/src/bin/test_bg.c @@ -0,0 +1,211 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void +_cb_radio_changed(void *data, Evas_Object *obj, void *event __UNUSED__) +{ + Evas_Object *o_bg = data; + + elm_bg_option_set(o_bg, elm_radio_value_get((Evas_Object *)obj)); +} + +static void +_cb_overlay_changed(void *data, Evas_Object *obj, void *event __UNUSED__) +{ + Evas_Object *o_bg = data; + + if (elm_check_state_get(obj)) + { + Evas_Object *parent, *over; + char buff[PATH_MAX]; + + snprintf(buff, sizeof(buff), "%s/objects/test.edj", PACKAGE_DATA_DIR); + parent = elm_object_parent_widget_get(o_bg); + over = edje_object_add(evas_object_evas_get(parent)); + edje_object_file_set(over, buff, "bg_overlay"); + elm_bg_overlay_set(o_bg, over); + } + else + elm_bg_overlay_set(o_bg, NULL); +} + +static void +_cb_color_changed(void *data, Evas_Object *obj, void *event __UNUSED__) +{ + Evas_Object *o_bg = data; + double val = 0.0; + + val = elm_spinner_value_get(obj); + if (val == 1.0) + elm_bg_color_set(o_bg, 255, 255, 255); + else if (val == 2.0) + elm_bg_color_set(o_bg, 255, 0, 0); + else if (val == 3.0) + elm_bg_color_set(o_bg, 0, 0, 255); + else if (val == 4.0) + elm_bg_color_set(o_bg, 0, 255, 0); +} + +void +test_bg_plain(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg; + + win = elm_win_add(NULL, "bg-plain", ELM_WIN_BASIC); + elm_win_title_set(win, "Bg Plain"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + /* allow bg to expand in x & y */ + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + /* set size hints. a minimum size for the bg. this should propagate back + * to the window thus limiting its size based off the bg as the bg is one + * of the window's resize objects. */ + evas_object_size_hint_min_set(bg, 160, 160); + /* and set a maximum size. not needed very often. normally used together + * with evas_object_size_hint_min_set() at the same size to make a + * window not resizable */ + evas_object_size_hint_max_set(bg, 640, 640); + /* and now just resize the window to a size you want. normally widgets + * will determine the initial size though */ + evas_object_resize(win, 320, 320); + /* and show the window */ + evas_object_show(win); +} + +void +test_bg_image(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "bg-image", ELM_WIN_BASIC); + elm_win_title_set(win, "Bg Image"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + elm_bg_file_set(bg, buf, NULL); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + evas_object_size_hint_min_set(bg, 160, 160); + evas_object_size_hint_max_set(bg, 640, 640); + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +void +test_bg_options(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg; + Evas_Object *box, *hbox, *o_bg; + Evas_Object *rd, *rdg; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "bg-options", ELM_WIN_BASIC); + elm_win_title_set(win, "Bg Options"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + box = elm_box_add(win); + evas_object_size_hint_weight_set(box, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, box); + evas_object_show(box); + + o_bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + elm_bg_file_set(o_bg, buf, NULL); + evas_object_size_hint_weight_set(o_bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(o_bg, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(box, o_bg); + evas_object_show(o_bg); + + hbox = elm_box_add(win); + elm_box_horizontal_set(hbox, EINA_TRUE); + evas_object_size_hint_weight_set(hbox, EVAS_HINT_EXPAND, EVAS_HINT_FILL); + evas_object_size_hint_align_set(hbox, EVAS_HINT_FILL, EVAS_HINT_FILL); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, ELM_BG_OPTION_CENTER); + elm_radio_label_set(rd, "Center"); + evas_object_size_hint_weight_set(rd, EVAS_HINT_EXPAND, EVAS_HINT_FILL); + evas_object_smart_callback_add(rd, "changed", _cb_radio_changed, o_bg); + elm_box_pack_end(hbox, rd); + evas_object_show(rd); + rdg = rd; + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, ELM_BG_OPTION_SCALE); + elm_radio_group_add(rd, rdg); + elm_radio_label_set(rd, "Scale"); + evas_object_size_hint_weight_set(rd, EVAS_HINT_EXPAND, EVAS_HINT_FILL); + evas_object_smart_callback_add(rd, "changed", _cb_radio_changed, o_bg); + elm_box_pack_end(hbox, rd); + evas_object_show(rd); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, ELM_BG_OPTION_STRETCH); + elm_radio_group_add(rd, rdg); + elm_radio_label_set(rd, "Stretch"); + evas_object_size_hint_weight_set(rd, EVAS_HINT_EXPAND, EVAS_HINT_FILL); + evas_object_smart_callback_add(rd, "changed", _cb_radio_changed, o_bg); + elm_box_pack_end(hbox, rd); + evas_object_show(rd); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, ELM_BG_OPTION_TILE); + elm_radio_group_add(rd, rdg); + elm_radio_label_set(rd, "Tile"); + evas_object_size_hint_weight_set(rd, EVAS_HINT_EXPAND, EVAS_HINT_FILL); + evas_object_smart_callback_add(rd, "changed", _cb_radio_changed, o_bg); + elm_box_pack_end(hbox, rd); + evas_object_show(rd); + + elm_radio_value_set(rdg, ELM_BG_OPTION_SCALE); + + rd = elm_check_add(win); + elm_check_label_set(rd, "Show Overlay"); + evas_object_size_hint_weight_set(rd, EVAS_HINT_EXPAND, EVAS_HINT_FILL); + evas_object_smart_callback_add(rd, "changed", _cb_overlay_changed, o_bg); + elm_box_pack_end(hbox, rd); + evas_object_show(rd); + + /* color choices ... this is ghetto, but we don't have a 'colorpicker' + * widget yet :( */ + rd = elm_spinner_add(win); + elm_object_style_set(rd, "vertical"); + elm_spinner_min_max_set(rd, 1, 4); + elm_spinner_label_format_set(rd, "%.0f"); + elm_spinner_editable_set(rd, EINA_FALSE); + elm_spinner_special_value_add(rd, 1, "White"); + elm_spinner_special_value_add(rd, 2, "Red"); + elm_spinner_special_value_add(rd, 3, "Blue"); + elm_spinner_special_value_add(rd, 4, "Green"); + evas_object_size_hint_weight_set(rd, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(rd, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_smart_callback_add(rd, "changed", _cb_color_changed, o_bg); + elm_box_pack_end(hbox, rd); + evas_object_show(rd); + + elm_box_pack_end(box, hbox); + evas_object_show(hbox); + + evas_object_size_hint_min_set(bg, 160, 160); + evas_object_size_hint_max_set(bg, 640, 640); + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_box.c b/src/bin/test_box.c new file mode 100644 index 0000000..abdbfd4 --- /dev/null +++ b/src/bin/test_box.c @@ -0,0 +1,280 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_box_vert(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *ic; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "box-vert", ELM_WIN_BASIC); + elm_win_title_set(win, "Box Vert"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.5); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.0, 0.5); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, EVAS_HINT_EXPAND, 0.5); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + evas_object_show(win); +} + +static void +_del_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + elm_box_unpack(data, obj); + evas_object_move(obj, 0, 0); + evas_object_color_set(obj, 128, 64, 0, 128); +// evas_object_del(obj); +} + +void +test_box_vert2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bt; + + win = elm_win_add(NULL, "box-vert2", ELM_WIN_BASIC); + elm_win_title_set(win, "Box Vert 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, 0.0, 0.0); + evas_object_show(bx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 1"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_smart_callback_add(bt, "clicked", _del_cb, bx); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 2"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_smart_callback_add(bt, "clicked", _del_cb, bx); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 3"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_smart_callback_add(bt, "clicked", _del_cb, bx); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 4"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_smart_callback_add(bt, "clicked", _del_cb, bx); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 5"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_smart_callback_add(bt, "clicked", _del_cb, bx); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + evas_object_show(win); +} + +void +test_box_horiz(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *ic; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "box-horiz", ELM_WIN_BASIC); + elm_win_title_set(win, "Box Horiz"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_box_horizontal_set(bx, 1); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.5); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.0); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.0, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + evas_object_show(win); +} + +typedef struct +{ + Eina_List *transitions; + Evas_Object *box; + Evas_Object_Box_Layout last_layout; +} Transitions_Data; + +static void +_test_box_transition_change(void *data) +{ + Transitions_Data *tdata = data; + Elm_Box_Transition *layout_data; + Evas_Object_Box_Layout next_layout; + + if (!data) return; + next_layout = eina_list_data_get(tdata->transitions); + layout_data = elm_box_transition_new(2.0, tdata->last_layout, + NULL, NULL, next_layout, NULL, NULL, + _test_box_transition_change, tdata); + elm_box_layout_set(tdata->box, elm_box_layout_transition, layout_data, elm_box_transition_free); + tdata->last_layout = next_layout; + + tdata->transitions = eina_list_demote_list(tdata->transitions, tdata->transitions); +} + +static void +_win_del(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Transitions_Data *tdata = data; + elm_box_layout_set(tdata->box, evas_object_box_layout_horizontal, NULL, NULL); + free(data); +} + +void +test_box_transition(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bt; + Transitions_Data *tdata; + + win = elm_win_add(NULL, "box-transition", ELM_WIN_BASIC); + elm_win_title_set(win, "Box Transition"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, 1.0, 1.0); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, 1.0, 1.0); + + evas_object_show(bx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 1"); + evas_object_size_hint_weight_set(bt, 1.0, 1.0); + evas_object_size_hint_align_set(bt, -1.0, -1.0); + evas_object_smart_callback_add(bt, "clicked", _del_cb, bx); + elm_box_pack_end(bx, bt); + evas_object_resize(bt, 100, 100); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 2"); + evas_object_size_hint_weight_set(bt, 1.0, 1.0); + evas_object_size_hint_align_set(bt, -1.0, -1.0); + evas_object_smart_callback_add(bt, "clicked", _del_cb, bx); + elm_box_pack_end(bx, bt); + evas_object_resize(bt, 100, 100); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 3"); + evas_object_size_hint_weight_set(bt, 1.0, 1.0); + evas_object_size_hint_align_set(bt, -1.0, -1.0); + evas_object_smart_callback_add(bt, "clicked", _del_cb, bx); + elm_box_pack_end(bx, bt); + evas_object_resize(bt, 100, 100); + evas_object_show(bt); + + tdata = calloc(1, sizeof(Transitions_Data)); + tdata->box = bx; + tdata->last_layout = evas_object_box_layout_horizontal; + tdata->transitions = eina_list_append(tdata->transitions, + evas_object_box_layout_vertical); + tdata->transitions = eina_list_append(tdata->transitions, + evas_object_box_layout_horizontal); + tdata->transitions = eina_list_append(tdata->transitions, + evas_object_box_layout_stack); + tdata->transitions = eina_list_append(tdata->transitions, + evas_object_box_layout_homogeneous_vertical); + tdata->transitions = eina_list_append(tdata->transitions, + evas_object_box_layout_homogeneous_horizontal); + tdata->transitions = eina_list_append(tdata->transitions, + evas_object_box_layout_flow_vertical); + tdata->transitions = eina_list_append(tdata->transitions, + evas_object_box_layout_flow_horizontal); + tdata->transitions = eina_list_append(tdata->transitions, + evas_object_box_layout_stack); + + evas_object_resize(win, 300, 300); + evas_object_resize(bx, 300, 300); + evas_object_smart_callback_add(win, "delete,request", _win_del, tdata); + evas_object_show(win); + elm_box_layout_set(bx, evas_object_box_layout_horizontal, NULL, NULL); + _test_box_transition_change(tdata); +} +#endif diff --git a/src/bin/test_bubble.c b/src/bin/test_bubble.c new file mode 100644 index 0000000..f8f7904 --- /dev/null +++ b/src/bin/test_bubble.c @@ -0,0 +1,81 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void +_print_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("bubble clicked\n"); +} + +void +test_bubble(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *ic, *bb, *ct; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "box-vert", ELM_WIN_BASIC); + elm_win_title_set(win, "Bubble"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_HORIZONTAL, 1, 1); + + bb = elm_bubble_add(win); + elm_bubble_label_set(bb, "Message 1"); + elm_bubble_info_set(bb, "Corner: bottom_right"); + elm_bubble_icon_set(bb, ic); + elm_bubble_corner_set(bb, "bottom_right"); + evas_object_smart_callback_add(bb, "clicked", _print_clicked, NULL); + evas_object_show(ic); + evas_object_size_hint_weight_set(bb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + ct = elm_label_add(win); + elm_label_label_set(ct, + "\"The future of the art: R or G or B?\", by Rusty"); + elm_bubble_content_set(bb, ct); + + elm_box_pack_end(bx, bb); + evas_object_show(bb); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_HORIZONTAL, 1, 1); + + bb = elm_bubble_add(win); + elm_bubble_label_set(bb, "Message 2"); + elm_bubble_info_set(bb, "10:32 4/11/2008"); + elm_bubble_icon_set(bb, ic); + evas_object_smart_callback_add(bb, "clicked", _print_clicked, NULL); + evas_object_show(ic); + evas_object_size_hint_weight_set(bb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + ct = elm_label_add(win); + elm_label_label_set(ct, "Corner: base (top-left)"); + elm_bubble_content_set(bb, ct); + + elm_box_pack_end(bx, bb); + evas_object_show(bb); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_button.c b/src/bin/test_button.c new file mode 100644 index 0000000..caf9a05 --- /dev/null +++ b/src/bin/test_button.c @@ -0,0 +1,174 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +static void +_bt_repeated(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + static int count; + char buf[16]; + + snprintf(buf, sizeof(buf), "count=%d", count++); + if (count >= 10000) + count = 0; + elm_button_label_set(obj, buf); +} + +static void +_bt_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + int param = (int)(data); + + printf("clicked event on Button:%d\n", param); +} + +static void +_bt_unpressed(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + int param = (int)(data); + + printf("unpressed event on Button:%d\n", param); +} + +void +test_button(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *scr, *bx, *ic, *bt; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "buttons", ELM_WIN_BASIC); + elm_win_title_set(win, "Buttons"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + scr = elm_scroller_add(win); + elm_scroller_bounce_set(scr, EINA_FALSE, EINA_TRUE); + elm_scroller_policy_set(scr, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_AUTO); + elm_win_resize_object_add(win, scr); + evas_object_show(scr); + evas_object_size_hint_weight_set(scr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_scroller_content_set(scr, bx); + evas_object_show(bx); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + bt = elm_button_add(win); + elm_button_label_set(bt, "Icon sized to button"); + elm_button_icon_set(bt, ic); + evas_object_smart_callback_add(bt, "clicked", _bt_clicked, (void *)1); + evas_object_smart_callback_add(bt, "unpressed", _bt_unpressed, (void *)1); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_show(ic); + + ic = elm_icon_add(bx); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + bt = elm_button_add(win); + elm_button_label_set(bt, "Icon no scale"); + elm_button_icon_set(bt, ic); + evas_object_smart_callback_add(bt, "clicked", _bt_clicked, (void *)2); + evas_object_smart_callback_add(bt, "unpressed", _bt_unpressed, (void *)2); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + bt = elm_button_add(win); + elm_button_label_set(bt, "Disabled Button"); + elm_button_icon_set(bt, ic); + elm_object_disabled_set(bt, 1); + evas_object_smart_callback_add(bt, "clicked", _bt_clicked, (void *)3); + evas_object_smart_callback_add(bt, "unpressed", _bt_unpressed, (void *)3); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + bt = elm_button_add(win); + elm_button_icon_set(bt, ic); + elm_object_disabled_set(bt, 1); + evas_object_smart_callback_add(bt, "clicked", _bt_clicked, (void *)4); + evas_object_smart_callback_add(bt, "unpressed", _bt_unpressed, (void *)4); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_show(ic); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Label Only"); + evas_object_smart_callback_add(bt, "clicked", _bt_clicked, (void *)5); + evas_object_smart_callback_add(bt, "unpressed", _bt_unpressed, (void *)5); + elm_box_pack_end(bx, bt); + evas_object_smart_callback_add(bt, "repeated", _bt_repeated, NULL); + elm_button_autorepeat_set(bt, 1); + elm_button_autorepeat_initial_timeout_set(bt, 2.0); + elm_button_autorepeat_gap_timeout_set(bt, 0.5); + evas_object_show(bt); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + bt = elm_button_add(win); + elm_button_icon_set(bt, ic); + evas_object_smart_callback_add(bt, "clicked", _bt_clicked, (void *)6); + evas_object_smart_callback_add(bt, "unpressed", _bt_unpressed, (void *)6); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_show(ic); + + bt = elm_button_add(win); + elm_object_style_set(bt, "anchor"); + elm_button_label_set(bt, "Anchor style"); + evas_object_smart_callback_add(bt, "clicked", _bt_clicked, (void *)7); + evas_object_smart_callback_add(bt, "unpressed", _bt_unpressed, (void *)7); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + bt = elm_button_add(win); + elm_object_style_set(bt, "anchor"); + elm_button_icon_set(bt, ic); + evas_object_smart_callback_add(bt, "clicked", _bt_clicked, (void *)8); + evas_object_smart_callback_add(bt, "unpressed", _bt_unpressed, (void *)8); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + bt = elm_button_add(win); + elm_object_style_set(bt, "anchor"); + elm_button_icon_set(bt, ic); + elm_object_disabled_set(bt, 1); + evas_object_smart_callback_add(bt, "clicked", _bt_clicked, (void *)9); + evas_object_smart_callback_add(bt, "unpressed", _bt_unpressed, (void *)9); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_show(ic); + evas_object_resize(win, 320, 480); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_calendar.c b/src/bin/test_calendar.c new file mode 100644 index 0000000..9259692 --- /dev/null +++ b/src/bin/test_calendar.c @@ -0,0 +1,181 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +/* A simple test, just displaying calendar in it's default state */ +void +test_calendar(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *cal; + + win = elm_win_add(NULL, "calendar", ELM_WIN_BASIC); + elm_win_title_set(win, "Calendar"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + cal = elm_calendar_add(win); + elm_win_resize_object_add(win, cal); + evas_object_size_hint_weight_set(cal, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(cal); + + evas_object_show(win); +} + +void +_print_cal_info(Evas_Object *cal, Evas_Object *en) +{ + char info[1024]; + double interval; + int year_min, year_max; + Eina_Bool sel_enabled; + const char **wds; + struct tm stime; + + if (!elm_calendar_selected_time_get(cal, &stime)) + return; + + interval = elm_calendar_interval_get(cal); + elm_calendar_min_max_year_get(cal, &year_min, &year_max); + sel_enabled = elm_calendar_day_selection_enabled_get(cal); + wds = elm_calendar_weekdays_names_get(cal); + + snprintf(info, sizeof(info), + " Day: %i, Mon: %i, Year %i, WeekDay: %i
    " + " Interval: %0.2f, Year_Min: %i, Year_Max %i, Sel Enabled : %i
    " + " Weekdays: %s, %s, %s, %s, %s, %s, %s
    ", + stime.tm_mday, stime.tm_mon, stime.tm_year + 1900, stime.tm_wday, + interval, year_min, year_max, sel_enabled, + wds[0], wds[1], wds[2], wds[3], wds[4], wds[5], wds[6]); + + elm_entry_entry_set(en, info); +} + +static void +_print_cal_info_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + _print_cal_info(obj, data); +} + +static char * +_format_month_year(struct tm *stime) +{ + char buf[32]; + if (!strftime(buf, sizeof(buf), "%b %y", stime)) return NULL; + return strdup(buf); +} + +/* A test intended to cover all the calendar api and much use cases as + possible */ +void +test_calendar2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bxh, *cal, *cal2, *cal3, *en; + Elm_Calendar_Mark *mark; + struct tm selected_time; + time_t current_time; + const char *weekdays[] = + { + "Sunday", "Monday", "Tuesday", "Wednesday", + "Thursday", "Friday", "Saturday" + }; + + win = elm_win_add(NULL, "calendar", ELM_WIN_BASIC); + elm_win_title_set(win, "Calendar 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + bxh = elm_box_add(win); + elm_box_horizontal_set(bxh, EINA_TRUE); + evas_object_size_hint_weight_set(bxh, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bxh, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(bxh); + elm_box_pack_end(bx, bxh); + + cal = elm_calendar_add(win); + evas_object_size_hint_weight_set(cal, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(cal, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(cal); + elm_box_pack_end(bx, cal); + + cal2 = elm_calendar_add(win); + evas_object_size_hint_weight_set(cal2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(cal2, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_calendar_day_selection_enabled_set(cal2, EINA_FALSE); + evas_object_show(cal2); + elm_box_pack_end(bxh, cal2); + + cal3 = elm_calendar_add(win); + evas_object_size_hint_weight_set(cal3, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(cal3, EVAS_HINT_FILL, EVAS_HINT_FILL); + current_time = time(NULL) + 34 * 84600; + localtime_r(¤t_time, &selected_time); + elm_calendar_selected_time_set(cal3, &selected_time); + current_time = time(NULL) + 1 * 84600; + localtime_r(¤t_time, &selected_time); + elm_calendar_mark_add(cal3, "checked", &selected_time, ELM_CALENDAR_UNIQUE); + elm_calendar_marks_clear(cal3); + current_time = time(NULL); + localtime_r(¤t_time, &selected_time); + elm_calendar_mark_add(cal3, "checked", &selected_time, ELM_CALENDAR_DAILY); + elm_calendar_mark_add(cal3, "holiday", &selected_time, ELM_CALENDAR_DAILY); + elm_calendar_marks_draw(cal3); + evas_object_show(cal3); + elm_box_pack_end(bxh, cal3); + + en = elm_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(en); + elm_box_pack_end(bx, en); + elm_entry_editable_set(en, EINA_FALSE); + evas_object_show(win); + + elm_calendar_weekdays_names_set(cal, weekdays); + elm_calendar_interval_set(cal, 0.4); + elm_calendar_format_function_set(cal, _format_month_year); + elm_calendar_min_max_year_set(cal, 2010, 2020); + + current_time = time(NULL) + 4 * 84600; + localtime_r(¤t_time, &selected_time); + elm_calendar_mark_add(cal, "holiday", &selected_time, ELM_CALENDAR_ANNUALLY); + + current_time = time(NULL) + 1 * 84600; + localtime_r(¤t_time, &selected_time); + elm_calendar_mark_add(cal, "checked", &selected_time, ELM_CALENDAR_UNIQUE); + + current_time = time(NULL) - 363 * 84600; + localtime_r(¤t_time, &selected_time); + elm_calendar_mark_add(cal, "checked", &selected_time, ELM_CALENDAR_MONTHLY); + + current_time = time(NULL) - 5 * 84600; + localtime_r(¤t_time, &selected_time); + mark = elm_calendar_mark_add(cal, "holiday", &selected_time, + ELM_CALENDAR_WEEKLY); + + current_time = time(NULL) + 1 * 84600; + localtime_r(¤t_time, &selected_time); + elm_calendar_mark_add(cal, "holiday", &selected_time, ELM_CALENDAR_WEEKLY); + + elm_calendar_mark_del(mark); + elm_calendar_marks_draw(cal); + + _print_cal_info(cal, en); + evas_object_smart_callback_add(cal, "changed", _print_cal_info_cb, en); +} + +#endif diff --git a/src/bin/test_check.c b/src/bin/test_check.c new file mode 100644 index 0000000..6d41324 --- /dev/null +++ b/src/bin/test_check.c @@ -0,0 +1,83 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_check(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *ic, *ck; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "check", ELM_WIN_BASIC); + elm_win_title_set(win, "Checks"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + ck = elm_check_add(win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, EVAS_HINT_FILL, 0.5); + elm_check_label_set(ck, "Icon sized to check"); + elm_check_icon_set(ck, ic); + elm_check_state_set(ck, 1); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + ck = elm_check_add(win); + elm_check_label_set(ck, "Icon no scale"); + elm_check_icon_set(ck, ic); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + evas_object_show(ic); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Label Only"); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + ck = elm_check_add(win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, EVAS_HINT_FILL, 0.5); + elm_check_label_set(ck, "Disabled check"); + elm_check_icon_set(ck, ic); + elm_check_state_set(ck, 1); + elm_box_pack_end(bx, ck); + elm_object_disabled_set(ck, 1); + evas_object_show(ck); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + ck = elm_check_add(win); + elm_check_icon_set(ck, ic); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + evas_object_show(ic); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_clock.c b/src/bin/test_clock.c new file mode 100644 index 0000000..b8b4a84 --- /dev/null +++ b/src/bin/test_clock.c @@ -0,0 +1,146 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_clock(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *ck; + unsigned int digedit; + + win = elm_win_add(NULL, "clock", ELM_WIN_BASIC); + elm_win_title_set(win, "Clock"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + ck = elm_clock_add(win); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + ck = elm_clock_add(win); + elm_clock_show_am_pm_set(ck, 1); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + ck = elm_clock_add(win); + elm_clock_show_seconds_set(ck, 1); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + ck = elm_clock_add(win); + elm_clock_show_seconds_set(ck, 1); + elm_clock_show_am_pm_set(ck, 1); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + ck = elm_clock_add(win); + elm_clock_show_seconds_set(ck, 1); + elm_clock_show_am_pm_set(ck, 0); + elm_clock_time_set(ck, 23, 59, 57); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + ck = elm_clock_add(win); + elm_clock_edit_set(ck, 1); + elm_clock_show_seconds_set(ck, 1); + elm_clock_show_am_pm_set(ck, 1); + elm_clock_time_set(ck, 10, 11, 12); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + ck = elm_clock_add(win); + elm_clock_show_seconds_set(ck, 1); + elm_clock_edit_set(ck, 1); + digedit = ELM_CLOCK_HOUR_UNIT | ELM_CLOCK_MIN_UNIT | ELM_CLOCK_SEC_UNIT; + elm_clock_digit_edit_set(ck, digedit); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + evas_object_show(win); +} + +static void +_edit_bt_clicked(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *ck = data; + + if (!elm_clock_edit_get(ck)) { + elm_button_label_set(obj, "Done"); + elm_clock_edit_set(ck, 1); + return; + } + elm_button_label_set(obj, "Edit"); + elm_clock_edit_set(ck, 0); +} + +static void +_hmode_bt_clicked(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *ck = data; + + if (!elm_clock_show_am_pm_get(ck)) { + elm_button_label_set(obj, "24h"); + elm_clock_show_am_pm_set(ck, 1); + return; + } + elm_button_label_set(obj, "12h"); + elm_clock_show_am_pm_set(ck, 0); +} + +void +test_clock2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *hbx, *ck, *bt; + + win = elm_win_add(NULL, "clock", ELM_WIN_BASIC); + elm_win_title_set(win, "Clock 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + ck = elm_clock_add(win); + elm_clock_show_seconds_set(ck, 1); + elm_clock_show_am_pm_set(ck, 1); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + hbx = elm_box_add(win); + evas_object_size_hint_weight_set(hbx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_horizontal_set(hbx, EINA_TRUE); + elm_box_pack_end(bx, hbx); + evas_object_show(hbx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Edit"); + evas_object_smart_callback_add(bt, "clicked", _edit_bt_clicked, ck); + elm_box_pack_end(hbx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "24h"); + evas_object_smart_callback_add(bt, "clicked", _hmode_bt_clicked, ck); + elm_box_pack_end(hbx, bt); + evas_object_show(bt); + + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_colorselector.c b/src/bin/test_colorselector.c new file mode 100644 index 0000000..0833703 --- /dev/null +++ b/src/bin/test_colorselector.c @@ -0,0 +1,97 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void +_colorselector_clicked_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *re = data; + int r, g, b, a; + + elm_colorselector_color_get(obj, &r, &g, &b, &a); + printf("Current Color [r=%d g=%d b=%d a=%d]\n",r, g, b, a); + + /* Fix Alpha pre multiplication by edje */ + r = (r * a) / 255; + g = (g * a) / 255; + b = (b * a) / 255; + + evas_object_color_set(re, r, g, b, a); +} + +void +test_colorselector(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *cp, *fr, *ly, *re; + char buf[PATH_MAX]; + int r, g, b, a; + + win = elm_win_add(NULL, "colorselector", ELM_WIN_BASIC); + elm_win_title_set(win, "Color Selector"); + elm_win_autodel_set(win, EINA_TRUE); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_color_set(bg, 255, 255, 255, 255); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + fr = elm_frame_add(win); + evas_object_size_hint_weight_set(fr, 1.0, 0.5); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_label_set(fr, "Color View"); + elm_box_pack_end(bx, fr); + evas_object_show(fr); + + ly = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/colorpreview.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly, buf, "main"); + evas_object_size_hint_align_set(ly, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_frame_content_set(fr, ly); + evas_object_show(ly); + + re = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_show(re); + elm_layout_content_set(ly, "ColorPreview", re); + + fr = elm_frame_add(win); + evas_object_size_hint_weight_set(fr, 1.0, 0); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, 0); + elm_frame_label_set(fr, "Color Selector"); + elm_box_pack_end(bx, fr); + evas_object_show(fr); + + cp = elm_colorselector_add(win); + + a = 180; + r = 255; + g = 160; + b = 132; + + elm_colorselector_color_set(cp, r, g, b, a); + evas_object_size_hint_weight_set(cp, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(cp, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_frame_content_set(fr, cp); + evas_object_show(cp); + evas_object_smart_callback_add(cp, "changed", _colorselector_clicked_cb, re); + + elm_colorselector_color_get(cp, &r, &g, &b, &a); + /* Fix Alpha pre multiplication by edje */ + r = (r * a) / 255; + g = (g * a) / 255; + b = (b * a) / 255; + evas_object_color_set(re, r, g, b, a); + + evas_object_resize(win, 320, 480); + evas_object_show(win); + +} +#endif diff --git a/src/bin/test_conform.c b/src/bin/test_conform.c new file mode 100644 index 0000000..9beafe8 --- /dev/null +++ b/src/bin/test_conform.c @@ -0,0 +1,205 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +void +test_conformant(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event __UNUSED__) +{ + Evas_Object *win, *bg, *conform, *btn, *bx, *en; + + win = elm_win_add(NULL, "conformant", ELM_WIN_BASIC); + elm_win_title_set(win, "Conformant"); + elm_win_autodel_set(win, 1); + elm_win_conformant_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + conform = elm_conformant_add(win); + elm_win_resize_object_add(win, conform); + evas_object_size_hint_weight_set(conform, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(conform); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_single_line_set(en, 1); + elm_scrolled_entry_bounce_set(en, 1, 0); + elm_scrolled_entry_entry_set(en, "This is the top entry here"); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + evas_object_show(en); + elm_box_pack_end(bx, en); + + btn = elm_button_add(win); + elm_button_label_set(btn, "Test Conformant"); + evas_object_size_hint_weight_set(btn, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(btn, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, btn); + evas_object_show(btn); + + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_single_line_set(en, 1); + elm_scrolled_entry_bounce_set(en, 1, 0); + elm_scrolled_entry_entry_set(en, "This is the middle entry here"); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + evas_object_show(en); + elm_box_pack_end(bx, en); + + btn = elm_button_add(win); + elm_button_label_set(btn, "Test Conformant"); + evas_object_size_hint_weight_set(btn, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(btn, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, btn); + evas_object_show(btn); + + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_bounce_set(en, 0, 1); + elm_scrolled_entry_entry_set(en, + "This is a multi-line entry at the bottom
    " + "This can contain more than 1 line of text and be " + "scrolled around to allow for entering of lots of " + "content. It is also to test to see that autoscroll " + "moves to the right part of a larger multi-line " + "text entry that is inside of a scroller than can be " + "scrolled around, thus changing the expected position " + "as well as cursor changes updating auto-scroll when " + "it is enabled."); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(en); + elm_box_pack_end(bx, en); + + elm_conformant_content_set(conform, bx); + evas_object_show(bx); + + evas_object_resize(win, 240, 240); + evas_object_show(win); +} + +static void +popobj(void *data, Evas_Object *obj __UNUSED__, void *event __UNUSED__) +{ + elm_pager_content_pop(data); +} + +void +test_conformant2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event __UNUSED__) +{ + Evas_Object *win, *bg, *conform, *btn, *bx, *en, *pg; + + win = elm_win_add(NULL, "conformant2", ELM_WIN_BASIC); + elm_win_title_set(win, "Conformant 2"); + elm_win_autodel_set(win, 1); + elm_win_conformant_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_single_line_set(en, 1); + elm_scrolled_entry_bounce_set(en, 1, 0); + elm_scrolled_entry_entry_set(en, "This is the top entry here"); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, en); + evas_object_show(en); + + btn = elm_button_add(win); + elm_object_focus_allow_set(btn, 0); + elm_button_label_set(btn, "Delete Below"); + evas_object_size_hint_weight_set(btn, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(btn, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, btn); + evas_object_show(btn); + + pg = elm_pager_add(win); + evas_object_size_hint_weight_set(pg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(pg, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, pg); + evas_object_show(pg); + + evas_object_smart_callback_add(btn, "clicked", popobj, pg); + + conform = elm_conformant_add(win); + evas_object_size_hint_weight_set(conform, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(conform, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_pager_content_push(pg, conform); + evas_object_show(conform); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_bounce_set(en, 0, 1); + elm_scrolled_entry_entry_set(en, "This entry and button below get deleted."); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(en); + elm_box_pack_end(bx, en); + + btn = elm_button_add(win); + elm_object_focus_allow_set(btn, 0); + elm_button_label_set(btn, "Delete this bottom bit 1"); + evas_object_size_hint_weight_set(btn, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(btn, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, btn); + evas_object_show(btn); + + evas_object_smart_callback_add(btn, "clicked", popobj, pg); + + elm_conformant_content_set(conform, bx); + evas_object_show(bx); + + conform = elm_conformant_add(win); + evas_object_size_hint_weight_set(conform, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(conform, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_pager_content_push(pg, conform); + evas_object_show(conform); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_bounce_set(en, 0, 1); + elm_scrolled_entry_entry_set(en, "This entry and button below get deleted."); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(en); + elm_box_pack_end(bx, en); + + btn = elm_button_add(win); + elm_object_focus_allow_set(btn, 0); + elm_button_label_set(btn, "Delete this bottom bit 2"); + evas_object_size_hint_weight_set(btn, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(btn, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, btn); + evas_object_show(btn); + + evas_object_smart_callback_add(btn, "clicked", popobj, pg); + + elm_conformant_content_set(conform, bx); + evas_object_show(bx); + + evas_object_resize(win, 240, 480); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_ctxpopup.c b/src/bin/test_ctxpopup.c new file mode 100644 index 0000000..1c4e0b8 --- /dev/null +++ b/src/bin/test_ctxpopup.c @@ -0,0 +1,178 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void +_ctxpopup_item_cb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("ctxpopup item selected: %s\n", + elm_ctxpopup_item_label_get(event_info)); +} + +#define ITEM_NEW(_hov, _label, _icon) \ + if(_icon) \ + { \ + ic = elm_icon_add(obj); \ + elm_icon_standard_set(ic, _icon); \ + elm_icon_scale_set(ic, EINA_FALSE, EINA_FALSE); \ + } \ + else \ + ic = NULL; \ + it = elm_ctxpopup_item_append(_hov, _label, ic, _ctxpopup_item_cb, NULL); \ + +static void +_list_item_cb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *ctxpopup, *ic; + Elm_Ctxpopup_Item *it; + Evas_Coord x,y; + + ctxpopup = elm_ctxpopup_add(obj); + + ITEM_NEW(ctxpopup, "Go to home folder", "home"); + ITEM_NEW(ctxpopup, "Save file", "file"); + ITEM_NEW(ctxpopup, "Delete file", "delete"); + ITEM_NEW(ctxpopup, "Navigate to folder", "folder"); + elm_ctxpopup_item_disabled_set(it, EINA_TRUE); + ITEM_NEW(ctxpopup, "Edit entry", "edit"); + ITEM_NEW(ctxpopup, "Set date and time", "clock"); + elm_ctxpopup_item_disabled_set(it, EINA_TRUE); + + evas_pointer_output_xy_get(evas_object_evas_get(obj), &x, &y); + evas_object_size_hint_max_set(ctxpopup, 240, 240); + evas_object_move(ctxpopup, x, y); + evas_object_show(ctxpopup); +} + +static void +_list_item_cb2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *ctxpopup, *ic; + Elm_Ctxpopup_Item *it; + Evas_Coord x,y; + + ctxpopup = elm_ctxpopup_add(obj); + + ITEM_NEW(ctxpopup, NULL, "home"); + ITEM_NEW(ctxpopup, NULL, "file"); + ITEM_NEW(ctxpopup, NULL, "delete"); + ITEM_NEW(ctxpopup, NULL, "folder"); + ITEM_NEW(ctxpopup, NULL, "edit"); + elm_ctxpopup_item_disabled_set(it, EINA_TRUE); + ITEM_NEW(ctxpopup, NULL, "clock"); + + evas_pointer_output_xy_get(evas_object_evas_get(obj), &x, &y); + evas_object_size_hint_max_set(ctxpopup, 240, 240); + evas_object_move(ctxpopup, x, y); + evas_object_show(ctxpopup); +} + +static void +_list_item_cb3(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *ctxpopup, *ic; + Elm_Ctxpopup_Item *it; + Evas_Coord x,y; + + ctxpopup = elm_ctxpopup_add(obj); + + ITEM_NEW(ctxpopup, "Eina", NULL); + ITEM_NEW(ctxpopup, "Eet", NULL); + ITEM_NEW(ctxpopup, "Evas", NULL); + ITEM_NEW(ctxpopup, "Ecore", NULL); + elm_ctxpopup_item_disabled_set(it, EINA_TRUE); + ITEM_NEW(ctxpopup, "Embryo", NULL); + ITEM_NEW(ctxpopup, "Edje", NULL); + + evas_pointer_output_xy_get(evas_object_evas_get(obj), &x, &y); + evas_object_move(ctxpopup, x, y); + evas_object_show(ctxpopup); +} + +static void +_list_item_cb4(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *ctxpopup, *ic; + Elm_Ctxpopup_Item *it; + Evas_Coord x,y; + + ctxpopup = elm_ctxpopup_add(obj); + elm_ctxpopup_horizontal_set(ctxpopup, EINA_TRUE); + + ITEM_NEW(ctxpopup, NULL, "home"); + ITEM_NEW(ctxpopup, NULL, "file"); + ITEM_NEW(ctxpopup, NULL, "delete"); + ITEM_NEW(ctxpopup, NULL, "folder"); + ITEM_NEW(ctxpopup, NULL, "edit"); + ITEM_NEW(ctxpopup, NULL, "clock"); + + evas_pointer_output_xy_get(evas_object_evas_get(obj), &x, &y); + evas_object_size_hint_max_set(ctxpopup, 240, 240); + evas_object_move(ctxpopup, x, y); + evas_object_show(ctxpopup); +} + + +static void +_list_item_cb5(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *ctxpopup, *btn; + Evas_Coord x,y; + + btn = elm_button_add(obj); + elm_button_label_set(btn, "Enlightenment"); + evas_object_size_hint_min_set(btn, 150, 150); + + ctxpopup = elm_ctxpopup_add(obj); + elm_ctxpopup_content_set(ctxpopup, btn); + + evas_pointer_output_xy_get(evas_object_evas_get(obj), &x, &y); + evas_object_move(ctxpopup, x, y); + evas_object_show(ctxpopup); +} + + +static void _list_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + elm_list_item_selected_set(event_info, EINA_FALSE); +} + +void +test_ctxpopup(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *list; + + win = elm_win_add(NULL, "Contexual Popup", ELM_WIN_BASIC); + elm_win_title_set(win, "Contextual Popup"); + elm_win_autodel_set(win, EINA_TRUE); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + list = elm_list_add(win); + elm_win_resize_object_add(win, list); + elm_list_mode_set(list, ELM_LIST_COMPRESS); + evas_object_smart_callback_add(list, "selected", _list_clicked, NULL); + +#undef ITEM_NEW + elm_list_item_append(list, "Ctxpopup with icons and labels", NULL, NULL, + _list_item_cb, NULL); + elm_list_item_append(list, "Ctxpopup with icons only", NULL, NULL, + _list_item_cb2, NULL); + elm_list_item_append(list, "Ctxpopup with labels only", NULL, NULL, + _list_item_cb3, NULL); + elm_list_item_append(list, "Ctxpopup at horizontal mode", NULL, NULL, + _list_item_cb4, NULL); + elm_list_item_append(list, "Ctxpopup with user content", NULL, NULL, + _list_item_cb5, NULL); + evas_object_show(list); + elm_list_go(list); + + evas_object_resize(win, 400, 400); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_cursor.c b/src/bin/test_cursor.c new file mode 100644 index 0000000..f45c552 --- /dev/null +++ b/src/bin/test_cursor.c @@ -0,0 +1,397 @@ +#include +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +typedef struct _Testitem +{ + Elm_Gengrid_Item *item; + const char *path; + int mode; + int onoff; +} Testitem; + +static Elm_Gengrid_Item_Class gic; + +char * +grd_lbl_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + const Testitem *ti = data; + char buf[256]; + snprintf(buf, sizeof(buf), "Photo %s", ti->path); + return strdup(buf); +} + +Evas_Object * +grd_icon_get(void *data, Evas_Object *obj, const char *part) +{ + const Testitem *ti = data; + if (!strcmp(part, "elm.swallow.icon")) + { + Evas_Object *icon = elm_bg_add(obj); + elm_bg_file_set(icon, ti->path, NULL); + evas_object_size_hint_aspect_set(icon, EVAS_ASPECT_CONTROL_VERTICAL, + 1, 1); + evas_object_show(icon); + return icon; + } + return NULL; +} + +static Elm_Genlist_Item_Class itct; + +static void +glt_exp(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + Evas_Object *gl = elm_genlist_item_genlist_get(it); + int val = (int)(long)elm_genlist_item_data_get(it); + Elm_Genlist_Item *it1, *it2, *it3; + + val *= 10; + it1 = elm_genlist_item_append(gl, &itct, (void *)(long)(val + 1), it, + ELM_GENLIST_ITEM_NONE, NULL, NULL); + it2 = elm_genlist_item_append(gl, &itct, (void *)(long)(val + 2), it, + ELM_GENLIST_ITEM_NONE, NULL, NULL); + it3 = elm_genlist_item_append(gl, &itct, (void *)(long)(val + 3), it, + ELM_GENLIST_ITEM_SUBITEMS, NULL, NULL); + + elm_genlist_item_cursor_set(it1, ELM_CURSOR_HAND2); + elm_genlist_item_cursor_set(it2, ELM_CURSOR_HAND2); + elm_genlist_item_cursor_set(it3, ELM_CURSOR_HAND1); + +} + +static void +glt_con(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_subitems_clear(it); +} + +static void +glt_exp_req(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, 1); +} + +static void +glt_con_req(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, 0); +} + +char * +glt_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + char buf[256]; + snprintf(buf, sizeof(buf), "Item mode %i", (int)(long)data); + return strdup(buf); +} + +void +test_cursor(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bt, *list, *entry, *ck; + Elm_List_Item *lit; + + win = elm_win_add(NULL, "cursor", ELM_WIN_BASIC); + elm_win_title_set(win, "Cursor"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + elm_object_cursor_set(bg, ELM_CURSOR_CIRCLE); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + ck = elm_clock_add(win); + elm_object_cursor_set(ck, ELM_CURSOR_CLOCK); + elm_box_pack_end(bx, ck); + evas_object_show(ck); + + bt = elm_button_add(win); + elm_object_cursor_set(bt, ELM_CURSOR_COFFEE_MUG); + elm_button_label_set(bt, "Coffee Mug"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_object_cursor_set(bt, ELM_CURSOR_CLOCK); + elm_button_label_set(bt, "Cursor unset"); + elm_object_cursor_unset(bt); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + list = elm_list_add(win); + elm_box_pack_end(bx, list); + evas_object_size_hint_weight_set(list, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(list, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_object_cursor_set(list, ELM_CURSOR_WATCH); + lit = elm_list_item_append(list, "watch over list | hand1", NULL, NULL, NULL, + NULL); + elm_list_item_cursor_set(lit, ELM_CURSOR_HAND1); + lit = elm_list_item_append(list, "watch over list | hand2", NULL, NULL, NULL, + NULL); + elm_list_item_cursor_set(lit, ELM_CURSOR_HAND2); + elm_list_go(list); + evas_object_show(list); + + entry = elm_scrolled_entry_add(win); + elm_scrolled_entry_entry_set(entry, "Xterm cursor"); + elm_scrolled_entry_single_line_set(entry, EINA_TRUE); + evas_object_size_hint_weight_set(entry, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_fill_set(entry, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, entry); + evas_object_show(entry); + elm_object_cursor_set(entry, ELM_CURSOR_XTERM); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} + +void +test_cursor2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *o, *grid, *gl; + Elm_Genlist_Item *it1, *it2, *it3; + Elm_Toolbar_Item *tit; + Elm_List_Item *lit; + char buf[PATH_MAX]; + static Testitem ti[144]; + int i, n; + const char *img[9] = + { + "panel_01.jpg", + "plant_01.jpg", + "rock_01.jpg", + "rock_02.jpg", + "sky_01.jpg", + "sky_02.jpg", + "sky_03.jpg", + "sky_04.jpg", + "wood_01.jpg", + }; + + win = elm_win_add(NULL, "cursor", ELM_WIN_BASIC); + elm_win_title_set(win, "Cursor 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + o = elm_toolbar_add(win); + elm_toolbar_homogenous_set(o, 0); + evas_object_size_hint_weight_set(o, 0.0, 0.0); + evas_object_size_hint_align_set(o, EVAS_HINT_FILL, 0.0); + tit = elm_toolbar_item_append(o, NULL, "Bogosity", NULL, NULL); + elm_toolbar_item_cursor_set(tit, ELM_CURSOR_BOGOSITY); + tit = elm_toolbar_item_append(o, NULL, "Unset", NULL, NULL); + elm_toolbar_item_cursor_set(tit, ELM_CURSOR_BOGOSITY); + elm_toolbar_item_cursor_unset(tit); + tit = elm_toolbar_item_append(o, NULL, "Xterm", NULL, NULL); + elm_toolbar_item_cursor_set(tit, ELM_CURSOR_XTERM); + elm_box_pack_end(bx, o); + evas_object_show(o); + + o = elm_list_add(win); + elm_box_pack_end(bx, o); + evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(o, EVAS_HINT_FILL, EVAS_HINT_FILL); + lit = elm_list_item_append(o, "cursor bogosity", NULL, NULL, NULL, NULL); + elm_list_item_cursor_set(lit, ELM_CURSOR_BOGOSITY); + lit = elm_list_item_append(o, "cursor unset", NULL, NULL, NULL, NULL); + elm_list_item_cursor_set(lit, ELM_CURSOR_BOGOSITY); + elm_list_item_cursor_unset(lit); + lit = elm_list_item_append(o, "cursor xterm", NULL, NULL, NULL, NULL); + elm_list_item_cursor_set(lit, ELM_CURSOR_XTERM); + elm_list_go(o); + evas_object_show(o); + + gl = elm_genlist_add(win); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(gl); + + itct.item_style = "default"; + itct.func.label_get = glt_label_get; + + it1 = elm_genlist_item_append(gl, &itct, (void *) 1, NULL, + ELM_GENLIST_ITEM_SUBITEMS, NULL, NULL); + it2 = elm_genlist_item_append(gl, &itct, (void *) 2, NULL, + ELM_GENLIST_ITEM_SUBITEMS, NULL, NULL); + it3 = elm_genlist_item_append(gl, &itct, (void *) 3, NULL, + ELM_GENLIST_ITEM_NONE, NULL, NULL); + + elm_genlist_item_cursor_set(it1, ELM_CURSOR_HAND1); + elm_genlist_item_cursor_set(it2, ELM_CURSOR_HAND1); + elm_genlist_item_cursor_set(it3, ELM_CURSOR_CROSS); + + evas_object_smart_callback_add(gl, "expand,request", glt_exp_req, gl); + evas_object_smart_callback_add(gl, "contract,request", glt_con_req, gl); + evas_object_smart_callback_add(gl, "expanded", glt_exp, gl); + evas_object_smart_callback_add(gl, "contracted", glt_con, gl); + + elm_box_pack_end(bx, gl); + + grid = elm_gengrid_add(win); + elm_gengrid_item_size_set(grid, 130, 130); + elm_gengrid_horizontal_set(grid, EINA_FALSE); + elm_gengrid_multi_select_set(grid, EINA_TRUE); + evas_object_size_hint_weight_set(grid, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(grid, EVAS_HINT_FILL, EVAS_HINT_FILL); + + gic.item_style = "default"; + gic.func.label_get = grd_lbl_get; + gic.func.icon_get = grd_icon_get; + + n = 0; + for (i = 0; i < 3 * 3; i++) + { + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, img[n]); + n = (n + 1) % 9; + ti[i].mode = i; + ti[i].path = eina_stringshare_add(buf); + ti[i].item = elm_gengrid_item_append(grid, &gic, &(ti[i]), NULL, NULL); + if (n % 2) + elm_gengrid_item_cursor_set(ti[i].item, ELM_CURSOR_HAND1); + else + elm_gengrid_item_cursor_set(ti[i].item, ELM_CURSOR_CLOCK); + if (!(i % 5)) + elm_gengrid_item_selected_set(ti[i].item, EINA_TRUE); + } + elm_box_pack_end(bx, grid); + evas_object_show(grid); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} + +void +test_cursor3(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *o; + Elm_List_Item *lit; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "cursor", ELM_WIN_BASIC); + elm_win_title_set(win, "Cursor 3"); + elm_win_autodel_set(win, 1); + + snprintf(buf, sizeof(buf), "%s/objects/cursors.edj", PACKAGE_DATA_DIR); + elm_theme_extension_add(NULL, buf); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + o = elm_button_add(win); + elm_object_cursor_set(o, ELM_CURSOR_HAND1); + elm_object_cursor_engine_only_set(o, EINA_FALSE); + elm_button_label_set(o, "hand1"); + elm_box_pack_end(bx, o); + evas_object_show(o); + + o = elm_button_add(win); + elm_object_cursor_set(o, ELM_CURSOR_HAND2); + elm_button_label_set(o, "hand2 x"); + elm_box_pack_end(bx, o); + evas_object_show(o); + + o = elm_button_add(win); + elm_object_cursor_set(o, ELM_CURSOR_HAND2); + elm_object_cursor_engine_only_set(o, EINA_FALSE); + elm_button_label_set(o, "hand2"); + elm_box_pack_end(bx, o); + evas_object_show(o); + + o = elm_button_add(win); + elm_object_cursor_set(o, "hand3"); + elm_object_cursor_engine_only_set(o, EINA_FALSE); + elm_button_label_set(o, "hand3"); + elm_box_pack_end(bx, o); + evas_object_show(o); + + o = elm_button_add(win); + elm_object_cursor_set(o, "hand3"); + elm_object_cursor_engine_only_set(o, EINA_FALSE); + elm_object_cursor_style_set(o, "transparent"); + elm_button_label_set(o, "hand3 transparent"); + elm_box_pack_end(bx, o); + evas_object_show(o); + + o = elm_button_add(win); + elm_object_cursor_set(o, "hand3"); + elm_object_cursor_engine_only_set(o, EINA_FALSE); + elm_object_cursor_unset(o); + elm_button_label_set(o, "unset"); + elm_box_pack_end(bx, o); + evas_object_show(o); + + o = elm_button_add(win); + elm_object_cursor_set(o, "hand4"); + elm_button_label_set(o, "not existent"); + elm_box_pack_end(bx, o); + evas_object_show(o); + + elm_cursor_engine_only_set(0); + o = elm_button_add(win); + elm_object_cursor_set(o, "hand2"); + elm_button_label_set(o, "hand 2 engine only config false"); + elm_box_pack_end(bx, o); + evas_object_show(o); + + elm_cursor_engine_only_set(1); + o = elm_button_add(win); + elm_object_cursor_set(o, "hand2"); + elm_button_label_set(o, "hand 2 engine only config true"); + elm_box_pack_end(bx, o); + evas_object_show(o); + + o = elm_list_add(win); + elm_box_pack_end(bx, o); + evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(o, EVAS_HINT_FILL, EVAS_HINT_FILL); + lit = elm_list_item_append(o, "cursor hand2 x", NULL, NULL, NULL, NULL); + elm_list_item_cursor_set(lit, ELM_CURSOR_HAND2); + lit = elm_list_item_append(o, "cursor hand2", NULL, NULL, NULL, NULL); + elm_list_item_cursor_set(lit, ELM_CURSOR_HAND2); + elm_list_item_cursor_engine_only_set(lit, EINA_FALSE); + lit = elm_list_item_append(o, "cursor hand3", NULL, NULL, NULL, NULL); + elm_list_item_cursor_set(lit, "hand3"); + elm_list_item_cursor_engine_only_set(lit, EINA_FALSE); + lit = elm_list_item_append(o, "cursor hand3 transparent", NULL, NULL, + NULL, NULL); + elm_list_item_cursor_set(lit, "hand3"); + elm_list_item_cursor_style_set(lit, "transparent"); + elm_list_item_cursor_engine_only_set(lit, EINA_FALSE); + elm_list_go(o); + evas_object_show(o); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_diskselector.c b/src/bin/test_diskselector.c new file mode 100644 index 0000000..9312c2b --- /dev/null +++ b/src/bin/test_diskselector.c @@ -0,0 +1,131 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void +_disk_sel(void *data __UNUSED__, Evas_Object * obj __UNUSED__, void *event_info) +{ + Elm_Diskselector_Item *it = event_info; + printf("Equinox: %s\n", elm_diskselector_item_label_get(it)); +} + +static void +_disk_next(void *data __UNUSED__, Evas_Object * obj __UNUSED__, void *event_info) +{ + Elm_Diskselector_Item *next, *prev, *it = event_info; + prev = elm_diskselector_item_prev_get(it); + next = elm_diskselector_item_next_get(it); + printf("Prev: %s, Next: %s\n", elm_diskselector_item_label_get(prev), + elm_diskselector_item_label_get(next)); +} + +static void +_print_disk_info_cb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Diskselector_Item *it = event_info; + printf("Selected label: %s\n", elm_diskselector_item_label_get(it)); +} + +static Evas_Object * +_disk_create(Evas_Object *win, Eina_Bool round) +{ + Elm_Diskselector_Item *it; + Evas_Object *di; + + di = elm_diskselector_add(win); + + elm_diskselector_item_append(di, "January", NULL, NULL, NULL); + elm_diskselector_item_append(di, "February", NULL, _disk_next, NULL); + elm_diskselector_item_append(di, "March", NULL, _disk_sel, NULL); + elm_diskselector_item_append(di, "April", NULL, NULL, NULL); + elm_diskselector_item_append(di, "May", NULL, NULL, NULL); + elm_diskselector_item_append(di, "June", NULL, NULL, NULL); + elm_diskselector_item_append(di, "July", NULL, NULL, NULL); + it = elm_diskselector_item_append(di, "August", NULL, NULL, NULL); + elm_diskselector_item_append(di, "September", NULL, _disk_sel, NULL); + elm_diskselector_item_append(di, "October", NULL, NULL, NULL); + elm_diskselector_item_append(di, "November", NULL, NULL, NULL); + elm_diskselector_item_append(di, "December", NULL, NULL, NULL); + + elm_diskselector_item_selected_set(it, EINA_TRUE); + elm_diskselector_round_set(di, round); + + return di; +} + +void +test_diskselector(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *disk, *ic; + Elm_Diskselector_Item *it; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "diskselector", ELM_WIN_BASIC); + elm_win_title_set(win, "Disk Selector"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bg, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(bx); + + disk = _disk_create(win, EINA_TRUE); + evas_object_size_hint_weight_set(disk, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(disk, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, disk); + evas_object_show(disk); + evas_object_smart_callback_add(disk, "selected", _print_disk_info_cb, NULL); + it = elm_diskselector_selected_item_get(disk); + elm_diskselector_item_selected_set(it, EINA_FALSE); + + disk = _disk_create(win, EINA_FALSE); + evas_object_size_hint_weight_set(disk, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(disk, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, disk); + evas_object_show(disk); + evas_object_smart_callback_add(disk, "selected", _print_disk_info_cb, NULL); + it = elm_diskselector_first_item_get(disk); + it = elm_diskselector_item_next_get(it); + elm_diskselector_item_selected_set(it, EINA_TRUE); + + disk = _disk_create(win, EINA_FALSE); + evas_object_size_hint_weight_set(disk, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(disk, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, disk); + evas_object_show(disk); + evas_object_smart_callback_add(disk, "selected", _print_disk_info_cb, NULL); + elm_diskselector_side_label_lenght_set(disk, 4); + + disk = elm_diskselector_add(win); + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 1, 1); + elm_diskselector_item_append(disk, "Sunday", ic, NULL, NULL); + elm_diskselector_item_append(disk, "Monday", NULL, NULL, NULL); + elm_diskselector_item_append(disk, "Tuesday", NULL, NULL, NULL); + elm_diskselector_item_append(disk, "Wednesday", NULL, NULL, NULL); + elm_diskselector_item_append(disk, "Thursday", NULL, NULL, NULL); + elm_diskselector_item_append(disk, "Friday", NULL, NULL, NULL); + elm_diskselector_item_append(disk, "Saturday", NULL, NULL, NULL); + elm_diskselector_round_set(disk, EINA_TRUE); + evas_object_size_hint_weight_set(disk, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(disk, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, disk); + evas_object_show(disk); + evas_object_smart_callback_add(disk, "selected", _print_disk_info_cb, NULL); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_entry.c b/src/bin/test_entry.c new file mode 100644 index 0000000..0d44331 --- /dev/null +++ b/src/bin/test_entry.c @@ -0,0 +1,1644 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +static void +my_entry_bt_1(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_entry_entry_set(en, ""); +} + +static void +my_entry_bt_2(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + const char *s = elm_entry_entry_get(en); + printf("ENTRY:\n"); + if (s) printf("%s\n", s); + printf("ENTRY PLAIN UTF8:\n"); + if (s) + { + s = elm_entry_markup_to_utf8(s); + if (s) + { + printf("%s\n", s); + free((char *)s); + } + } +} + +static void +my_entry_bt_3(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + const char *s = elm_entry_selection_get(en); + printf("SELECTION:\n"); + if (s) printf("%s\n", s); + printf("SELECTION PLAIN UTF8:\n"); + if (s) + { + s = elm_entry_markup_to_utf8(s); + if (s) + { + printf("%s\n", s); + free((char *)s); + } + } +} + +static void +my_entry_bt_4(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_entry_entry_insert(en, "Insert some BOLD text"); +} + +void +test_entry(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bx2, *bt, *en; + char buf[4096]; + + win = elm_win_add(NULL, "entry", ELM_WIN_BASIC); + elm_win_title_set(win, "Entry"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + en = elm_entry_add(win); + elm_entry_line_wrap_set(en, 0); + snprintf(buf, sizeof(buf), + "This is an entry widget in this window that
    " + "uses markup like this for styling and
    " + "formatting like this, as well as
    " + "links in the text, so enter text
    " + "in here to edit it. By the way, links are
    " + "called Anchors so you will need
    " + "to refer to them this way.
    " + "
    " + + "Also you can stick in items with (relsize + ascent): " + "" + " (full) " + "" + " (to the left)
    " + + "Also (size + ascent): " + "" + " (full) " + "" + " (before this)
    " + + "And as well (absize + ascent): " + "" + " (full) " + "" + " or even paths to image files on disk too like: " + "" + " ... end." + , PACKAGE_DATA_DIR + ); + elm_entry_entry_set(en, buf); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, en); + evas_object_show(en); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Clear"); + evas_object_smart_callback_add(bt, "clicked", my_entry_bt_1, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Print"); + evas_object_smart_callback_add(bt, "clicked", my_entry_bt_2, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Selection"); + evas_object_smart_callback_add(bt, "clicked", my_entry_bt_3, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Insert"); + evas_object_smart_callback_add(bt, "clicked", my_entry_bt_4, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + elm_object_focus(en); + evas_object_show(win); +} + +static void +my_scrolled_entry_bt_1(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_entry_set(en, ""); +} + +static void +my_scrolled_entry_bt_2(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + const char *s = elm_scrolled_entry_entry_get(en); + printf("ENTRY:\n"); + if (s) printf("%s\n", s); + printf("ENTRY PLAIN UTF8:\n"); + if (s) + { + s = elm_entry_markup_to_utf8(s); + if (s) + { + printf("%s\n", s); + free((char *)s); + } + } +} + +static void +my_scrolled_entry_bt_3(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + const char *s = elm_scrolled_entry_selection_get(en); + printf("SELECTION:\n"); + if (s) printf("%s\n", s); + printf("SELECTION PLAIN UTF8:\n"); + if (s) + { + s = elm_entry_markup_to_utf8(s); + if (s) + { + printf("%s\n", s); + free((char *)s); + } + } +} + +static void +my_scrolled_entry_bt_4(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_entry_insert(en, "Insert some BOLD text"); +} + +static void +my_scrolled_entry_bt_5(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + const char *s = elm_scrolled_entry_entry_get(en); + printf("PASSWORD: '%s'\n", s ? s : ""); +} + +static void +scrolled_anchor_test(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_entry_insert(en, "ANCHOR CLICKED"); +} + +void +test_entry_scrolled(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bx2, *bt, *en, *en_p, *sp; + static Elm_Entry_Filter_Accept_Set digits_filter_data, digits_filter_data2; + static Elm_Entry_Filter_Limit_Size limit_filter_data, limit_filter_data2; + + win = elm_win_add(NULL, "entry-scrolled", ELM_WIN_BASIC); + elm_win_title_set(win, "Entry Scrolled"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + /* disabled entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_entry_set(en, "Disabled entry"); + elm_scrolled_entry_single_line_set(en, 1); + elm_object_disabled_set(en, 1); + evas_object_show(en); + elm_box_pack_end(bx, en); + + /* password entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_password_set(en, 1); + elm_scrolled_entry_single_line_set(en, 1); + elm_scrolled_entry_entry_set(en, "Access denied, give up!"); + elm_object_disabled_set(en, 1); + evas_object_show(en); + elm_box_pack_end(bx, en); + + /* multi-line disable entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_ON, ELM_SCROLLER_POLICY_ON); + elm_object_disabled_set(en, 1); + elm_scrolled_entry_context_menu_item_add(en, "Hello", NULL, ELM_ICON_NONE, NULL, NULL); + elm_scrolled_entry_context_menu_item_add(en, "World", NULL, ELM_ICON_NONE, NULL, NULL); + elm_scrolled_entry_entry_set(en, + "Multi-line disabled entry widget :)
    " + "We can use markup like this for styling and
    " + "formatting like this, as well as
    " + "links in the text," + "but it won't be editable or clickable."); + evas_object_show(en); + elm_box_pack_end(bx, en); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + /* Single line selected entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_entry_set(en, "This is a single line"); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_single_line_set(en, 1); + elm_scrolled_entry_select_all(en); + evas_object_show(en); + elm_box_pack_end(bx, en); + + /* Only digits entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_entry_set(en, "01234"); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_single_line_set(en, 1); + evas_object_show(en); + elm_box_pack_end(bx, en); + + digits_filter_data.accepted = "0123456789"; + digits_filter_data.rejected = NULL; + elm_scrolled_entry_text_filter_append(en, elm_entry_filter_accept_set, &digits_filter_data); + + /* No digits entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_entry_set(en, "No numbers here"); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_single_line_set(en, 1); + evas_object_show(en); + elm_box_pack_end(bx, en); + + digits_filter_data2.accepted = NULL; + digits_filter_data2.rejected = "0123456789"; + elm_scrolled_entry_text_filter_append(en, elm_entry_filter_accept_set, &digits_filter_data2); + + /* Size limited entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_entry_set(en, "Just 20 chars"); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_single_line_set(en, 1); + evas_object_show(en); + elm_box_pack_end(bx, en); + + limit_filter_data.max_char_count = 20; + limit_filter_data.max_byte_count = 0; + elm_scrolled_entry_text_filter_append(en, elm_entry_filter_limit_size, &limit_filter_data); + + /* Byte size limited entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_entry_set(en, "And now only 30 bytes"); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_single_line_set(en, 1); + evas_object_show(en); + elm_box_pack_end(bx, en); + + limit_filter_data2.max_char_count = 0; + limit_filter_data2.max_byte_count = 30; + elm_scrolled_entry_text_filter_append(en, elm_entry_filter_limit_size, &limit_filter_data2); + + /* Single line password entry */ + en_p = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en_p, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en_p, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_scrollbar_policy_set(en_p, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_entry_set(en_p, "Password here"); + elm_scrolled_entry_single_line_set(en_p, 1); + elm_scrolled_entry_password_set(en_p, 1); + evas_object_show(en_p); + elm_box_pack_end(bx, en_p); + + /* scrolled entry with icon/end widgets*/ + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_single_line_set(en, 1); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + bt = elm_icon_add(win); + elm_icon_standard_set(bt, "home"); + evas_object_size_hint_min_set(bt, 48, 48); + evas_object_color_set(bt, 255, 0, 0, 128); + evas_object_show(bt); + elm_scrolled_entry_icon_set(en, bt); + bt = elm_icon_add(win); + elm_icon_standard_set(bt, "delete"); + evas_object_color_set(bt, 255, 0, 0, 128); + evas_object_size_hint_min_set(bt, 48, 48); + evas_object_show(bt); + elm_scrolled_entry_end_set(en, bt); + elm_scrolled_entry_entry_set(en, "scrolled entry with icon and end objects"); + evas_object_show(en); + elm_box_pack_end(bx, en); + + /* markup scrolled entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_ON, ELM_SCROLLER_POLICY_ON); + elm_scrolled_entry_entry_set(en, + "This is an entry widget in this window that
    " + "uses markup like this for styling and
    " + "formatting like this, as well as
    " + "links in the text, so enter text
    " + "in here to edit it. By them way, links are
    " + "called Anchors so you will need
    " + "to refer to them this way. At the end here is a really long " + "line to test line wrapping to see if it works. But just in " + "case this line is not long enough I will add more here to " + "really test it out, as Elementary really needs some " + "good testing to see if entry widgets work as advertised."); + evas_object_smart_callback_add(en, "anchor,clicked", scrolled_anchor_test, en); + evas_object_show(en); + elm_box_pack_end(bx, en); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Clear"); + evas_object_smart_callback_add(bt, "clicked", my_scrolled_entry_bt_1, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Print"); + evas_object_smart_callback_add(bt, "clicked", my_scrolled_entry_bt_2, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Print pwd"); + evas_object_smart_callback_add(bt, "clicked", my_scrolled_entry_bt_5, en_p); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Selection"); + evas_object_smart_callback_add(bt, "clicked", my_scrolled_entry_bt_3, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Insert"); + evas_object_smart_callback_add(bt, "clicked", my_scrolled_entry_bt_4, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 300); + + elm_object_focus(win); + evas_object_show(win); +} + +static void +my_ent_bt_clr(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_entry_set(en, ""); +} + +static void +my_ent_bt_pri(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + const char *s = elm_scrolled_entry_entry_get(en); + printf("ENTRY:\n"); + if (s) printf("%s\n", s); + printf("ENTRY PLAIN UTF8:\n"); + if (s) + { + s = elm_entry_markup_to_utf8(s); + if (s) + { + printf("%s\n", s); + free((char *)s); + } + } +} + +static void +my_ent_bt_sel(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + const char *s = elm_scrolled_entry_selection_get(en); + printf("SELECTION:\n"); + if (s) printf("%s\n", s); + printf("SELECTION PLAIN UTF8:\n"); + if (s) + { + s = elm_entry_markup_to_utf8(s); + if (s) + { + printf("%s\n", s); + free((char *)s); + } + } +} + +static void +my_ent_bt_all(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_select_all(en); +} + +static void +my_ent_bt_non(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_select_none(en); +} + +static void +my_ent_bt_ins(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_entry_insert(en, "Insert text"); +} + +static void +my_ent_bt_lef(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_prev(en); +} + +static void +my_ent_bt_rig(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_next(en); +} + +static void +my_ent_bt_up_(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_up(en); +} + +static void +my_ent_bt_dow(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_down(en); +} + +static void +my_ent_bt_beg(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_begin_set(en); +} + +static void +my_ent_bt_end(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_end_set(en); +} + +static void +my_ent_bt_lbe(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_line_begin_set(en); +} + +static void +my_ent_bt_len(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_line_end_set(en); +} + +static void +my_ent_bt_sbe(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_selection_begin(en); +} + +static void +my_ent_bt_sen(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_cursor_selection_end(en); +} + +static void +my_ent_bt_fmt(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + printf("IS FORMAT: %i\n", + (int)elm_scrolled_entry_cursor_is_format_get(en)); +} + +static void +my_ent_bt_vfm(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + printf("IS VISIBLE FORMAT %i\n", + (int)elm_scrolled_entry_cursor_is_visible_format_get(en)); +} + +static void +my_ent_bt_chr(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + printf("CHAR '%s'\n", elm_scrolled_entry_cursor_content_get(en)); +} + +static void +my_ent_bt_cut(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_selection_cut(en); +} + +static void +my_ent_bt_cop(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_selection_copy(en); +} + +static void +my_ent_bt_pas(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_selection_paste(en); +} + +void +test_entry3(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bx2, *bt, *en; + + win = elm_win_add(NULL, "entry3", ELM_WIN_BASIC); + elm_win_title_set(win, "Entry 3"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + /* Single line selected entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_entry_set(en, "This is a single line"); + elm_scrolled_entry_single_line_set(en, 1); + elm_box_pack_end(bx, en); + evas_object_show(en); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Clr"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_clr, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Pri"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_pri, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Sel"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_sel, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "All"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_all, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Non"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_non, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Ins"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_ins, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Lef"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_lef, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rig"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_rig, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Up "); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_up_, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Dow"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_dow, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Beg"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_beg, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "End"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_end, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "LBe"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_lbe, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "LEn"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_len, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "SBe"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_sbe, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "SEn"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_sen, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Fmt"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_fmt, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "VFm"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_vfm, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Chr"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_chr, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Cut"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_cut, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Cop"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_cop, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Pas"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_pas, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + /* markup scrolled entry */ + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_scrolled_entry_entry_set(en, + "This is an entry widget in this window that
    " + "uses markup like this for styling and
    " + "formatting like this, as well as
    " + "links in the text, so enter text
    " + "in here to edit it. By them way, links are
    " + "called Anchors so you will need
    " + "to refer to them this way. At the end here is a really long " + "line to test line wrapping to see if it works. But just in " + "case this line is not long enough I will add more here to " + "really test it out, as Elementary really needs some " + "good testing to see if entry widgets work as advertised." + ); + evas_object_smart_callback_add(en, "anchor,clicked", scrolled_anchor_test, en); + elm_box_pack_end(bx, en); + evas_object_show(en); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Clr"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_clr, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Pri"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_pri, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Sel"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_sel, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "All"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_all, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Non"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_non, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Ins"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_ins, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Lef"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_lef, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rig"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_rig, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Up "); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_up_, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Dow"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_dow, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Beg"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_beg, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "End"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_end, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "LBe"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_lbe, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "LEn"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_len, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "SBe"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_sbe, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "SEn"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_sen, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Fmt"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_fmt, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "VFm"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_vfm, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Chr"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_chr, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Cut"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_cut, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Cop"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_cop, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Pas"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_pas, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 480); + + elm_object_focus(win); + evas_object_show(win); +} + +void +test_entry4(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *ly, *en; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "entry4", ELM_WIN_BASIC); + elm_win_title_set(win, "Entry 4"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + ly = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/test.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly, buf, "layout"); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, ly); + evas_object_show(ly); + + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_entry_set(en, "This is a single line"); + elm_scrolled_entry_single_line_set(en, 1); + elm_layout_content_set(ly, "element1", en); + evas_object_show(en); + + en = elm_entry_add(win); + elm_entry_line_wrap_set(en, 0); + elm_entry_entry_set(en, + "This is an entry widget
    " + "that uses markup
    " + "like this and has
    " + "no scroller, so you can
    " + "use it more flexibly."); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_layout_content_set(ly, "element2", en); + evas_object_show(en); + + en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_scrolled_entry_entry_set(en, + "This is an entry widget in this window that
    " + "uses markup like this for styling and
    " + "formatting like this, as well as
    " + "links in the text, so enter text
    " + "in here to edit it. By them way, links are
    " + "called Anchors so you will need
    " + "to refer to them this way. At the end here is a really long " + "line to test line wrapping to see if it works. But just in " + "case this line is not long enough I will add more here to " + "really test it out, as Elementary really needs some " + "good testing to see if entry widgets work as advertised." + ); + evas_object_smart_callback_add(en, "anchor,clicked", scrolled_anchor_test, en); + elm_layout_content_set(ly, "element3", en); + evas_object_show(en); + + evas_object_show(win); +} + +void +test_entry5(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bx2, *bt, *en; + + win = elm_win_add(NULL, "entry5", ELM_WIN_BASIC); + elm_win_title_set(win, "Entry 5"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_line_char_wrap_set(en, 1); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_scrolled_entry_entry_set(en, + "This is an entry widget in this window that " + "uses markup like this for styling and " + "formatting like this, as well as " + "to refer to them this way. At the end here is a really long " + "line to test line wrapping to see if it works. But just in " + "case this line is not long enough I will add more here to " + "really test it out, as Elementary really needs some " + "good testing to see if entry widgets work as advertised." + ); + evas_object_smart_callback_add(en, "anchor,clicked", scrolled_anchor_test, en); + elm_box_pack_end(bx, en); + evas_object_show(en); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Clr"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_clr, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Pri"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_pri, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Sel"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_sel, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "All"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_all, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Non"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_non, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Ins"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_ins, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Lef"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_lef, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rig"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_rig, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Up "); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_up_, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Dow"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_dow, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Beg"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_beg, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "End"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_end, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "LBe"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_lbe, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "LEn"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_len, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "SBe"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_sbe, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "SEn"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_sen, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Fmt"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_fmt, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "VFm"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_vfm, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Chr"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_chr, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Cut"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_cut, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Cop"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_cop, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Pas"); + evas_object_smart_callback_add(bt, "clicked", my_ent_bt_pas, en); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_propagate_events_set(bt, 0); + elm_object_focus_allow_set(bt, 0); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 480); + + elm_object_focus(win); + evas_object_show(win); +} + +static void +_scrolled_entry_clear(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *en = data; + elm_scrolled_entry_entry_set(en, ""); +} + +void +test_entry_notepad(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bx2, *bt, *np; + + win = elm_win_add(NULL, "entry-notepad", ELM_WIN_BASIC); + elm_win_title_set(win, "Entry Notepad"); + elm_win_autodel_set(win, EINA_TRUE); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + np = elm_scrolled_entry_add(win); + elm_scrolled_entry_file_set(np, "note.txt", ELM_TEXT_FORMAT_PLAIN_UTF8); + evas_object_size_hint_weight_set(np, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(np, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, np); + evas_object_show(np); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, EINA_TRUE); + elm_box_homogenous_set(bx2, EINA_TRUE); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Clear"); + evas_object_smart_callback_add(bt, "clicked", _scrolled_entry_clear, np); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 300); + + elm_object_focus(win); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_fileselector.c b/src/bin/test_fileselector.c new file mode 100644 index 0000000..9a18756 --- /dev/null +++ b/src/bin/test_fileselector.c @@ -0,0 +1,210 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +static void +my_fileselector_done(void *data, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + /* event_info conatin the full path of the selected file + * or NULL if none is selected or cancel is pressed */ + const char *selected = event_info; + + if (selected) + printf("Selected file: %s\n", selected); + else + evas_object_del(data); /* delete the test window */ +} + +static void +my_fileselector_selected(void *data __UNUSED__, + Evas_Object *obj, + void *event_info) +{ + /* event_info conatin the full path of the selected file */ + const char *selected = event_info; + printf("Selected file: %s\n", selected); + + /* or you can query the selection */ + printf("or: %s\n", elm_fileselector_selected_get(obj)); +} + +static void +_is_save_clicked(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + printf("Toggle Is save\n"); + if (elm_fileselector_is_save_get(fs)) + elm_fileselector_is_save_set(fs, EINA_FALSE); + else + elm_fileselector_is_save_set(fs, EINA_TRUE); +} + +static void +_folder_only_clicked(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + printf("Toggle Folder only\n"); + if (elm_fileselector_folder_only_get(fs)) + elm_fileselector_folder_only_set(fs, EINA_FALSE); + else + elm_fileselector_folder_only_set(fs, EINA_TRUE); +} + +static void +_expandable_clicked(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + printf("Toggle Expandable\n"); + if (elm_fileselector_expandable_get(fs)) + elm_fileselector_expandable_set(fs, EINA_FALSE); + else + elm_fileselector_expandable_set(fs, EINA_TRUE); +} + +static void +_sel_get_clicked(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + printf("Get Selected: %s\n", elm_fileselector_selected_get(fs)); +} + +static void +_path_get_clicked(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + printf("Get Path: %s\n", elm_fileselector_path_get(fs)); +} + +static void +_mode_cycle_clicked(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + Elm_Fileselector_Mode mode; + + mode = (elm_fileselector_mode_get(fs) + 1) % ELM_FILESELECTOR_LAST; + elm_fileselector_mode_set(fs, mode); + + printf("Setting mode to: %d\n", mode); +} + +void +test_fileselector(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *win, *fs, *bg, *vbox, *hbox, *bt, *sep; + + /* Set the locale according to the system pref. + * If you dont do so the file selector will order the files list in + * a case sensitive manner + */ + setlocale(LC_ALL, ""); + + win = elm_win_add(NULL, "fileselector", ELM_WIN_BASIC); + elm_win_title_set(win, "File Selector"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + vbox = elm_box_add(win); + elm_win_resize_object_add(win, vbox); + evas_object_size_hint_weight_set(vbox, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(vbox); + + fs = elm_fileselector_add(win); + /* enable the fs file name entry */ + elm_fileselector_is_save_set(fs, EINA_TRUE); + /* make the file list a tree with dir expandable in place */ + elm_fileselector_expandable_set(fs, EINA_FALSE); + /* start the fileselector in the home dir */ + elm_fileselector_path_set(fs, getenv("HOME")); + /* allow fs to expand in x & y */ + evas_object_size_hint_weight_set(fs, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fs, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(vbox, fs); + evas_object_show(fs); // TODO fix this is the widget + + /* the 'done' cb is called when the user press ok/cancel */ + evas_object_smart_callback_add(fs, "done", my_fileselector_done, win); + /* the 'selected' cb is called when the user click on a file/dir */ + evas_object_smart_callback_add(fs, "selected", my_fileselector_selected, + win); + + /* test buttons */ + sep = elm_separator_add(win); + elm_separator_horizontal_set(sep, EINA_TRUE); + elm_box_pack_end(vbox, sep); + evas_object_show(sep); + + hbox = elm_box_add(win); + elm_box_horizontal_set(hbox, EINA_TRUE); + elm_box_pack_end(vbox, hbox); + evas_object_show(hbox); + + bt = elm_check_add(win); + elm_check_label_set(bt, "is save"); + elm_check_state_set(bt, elm_fileselector_is_save_get(fs)); + evas_object_smart_callback_add(bt, "changed", _is_save_clicked, fs); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + bt = elm_check_add(win); + elm_check_label_set(bt, "folder only"); + elm_check_state_set(bt, elm_fileselector_folder_only_get(fs)); + evas_object_smart_callback_add(bt, "changed", _folder_only_clicked, fs); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + bt = elm_check_add(win); + elm_check_label_set(bt, "expandable"); + elm_check_state_set(bt, elm_fileselector_expandable_get(fs)); + evas_object_smart_callback_add(bt, "changed", _expandable_clicked, fs); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + hbox = elm_box_add(win); + elm_box_horizontal_set(hbox, EINA_TRUE); + elm_box_pack_end(vbox, hbox); + evas_object_show(hbox); + + bt = elm_button_add(win); + elm_button_label_set(bt, "selected get"); + evas_object_smart_callback_add(bt, "clicked", _sel_get_clicked, fs); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "path get"); + evas_object_smart_callback_add(bt, "clicked", _path_get_clicked, fs); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "mode cycle"); + evas_object_smart_callback_add(bt, "clicked", _mode_cycle_clicked, fs); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + evas_object_resize(win, 240, 350); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_fileselector_button.c b/src/bin/test_fileselector_button.c new file mode 100644 index 0000000..00c8d07 --- /dev/null +++ b/src/bin/test_fileselector_button.c @@ -0,0 +1,147 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif + +#ifndef ELM_LIB_QUICKLAUNCH +static void +_file_chosen(void *data, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Evas_Object *entry = data; + const char *file = event_info; + if (file) + { + elm_entry_entry_set(entry, file); + printf("File chosen: %s\n", file); + } + else + printf("File selection canceled.\n"); +} + +static void +_inwin_mode_toggle(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs_bt = data; + Eina_Bool value = elm_fileselector_button_inwin_mode_get(fs_bt); + elm_fileselector_button_inwin_mode_set(fs_bt, !value); + printf("Inwin mode set to: %s\n", value ? "false" : "true"); +} + +static void +_current_sel_toggle(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs_bt = data; + Eina_Bool value = elm_fileselector_button_is_save_get(fs_bt); + elm_fileselector_button_is_save_set(fs_bt, !value); + printf("Current selection editable entry set to: %s\n", + value ? "false" : "true"); +} + +static void +_folder_only_toggle(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs_bt = data; + Eina_Bool value = elm_fileselector_button_folder_only_get(fs_bt); + elm_fileselector_button_folder_only_set(fs_bt, !value); + printf("Folder only flag set to: %s\n", value ? "false" : "true"); +} + +static void +_expandable_toggle(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs_bt = data; + Eina_Bool value = elm_fileselector_button_expandable_get(fs_bt); + elm_fileselector_button_expandable_set(fs_bt, !value); + printf("Expandable flag set to: %s\n", value ? "false" : "true"); +} + +void +test_fileselector_button(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *vbox, *hbox, *ic, *bt, *fs_bt, *en, *lb; + + win = elm_win_add(NULL, "fileselector button", ELM_WIN_BASIC); + elm_win_title_set(win, "File Selector Button"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + vbox = elm_box_add(win); + elm_win_resize_object_add(win, vbox); + evas_object_size_hint_weight_set(vbox, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(vbox); + + /* file selector button */ + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "file"); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + fs_bt = elm_fileselector_button_add(win); + elm_fileselector_button_label_set(fs_bt, "Select a file"); + elm_fileselector_button_icon_set(fs_bt, ic); + + elm_box_pack_end(vbox, fs_bt); + evas_object_show(fs_bt); + evas_object_show(ic); + + /* attribute setting buttons */ + hbox = elm_box_add(win); + elm_box_horizontal_set(hbox, EINA_TRUE); + elm_box_pack_end(vbox, hbox); + evas_object_show(hbox); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Toggle current selection text entry"); + evas_object_smart_callback_add(bt, "clicked", _current_sel_toggle, fs_bt); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Toggle inwin mode"); + evas_object_smart_callback_add(bt, "clicked", _inwin_mode_toggle, fs_bt); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Toggle folder only mode"); + evas_object_smart_callback_add(bt, "clicked", _folder_only_toggle, fs_bt); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Toggle expandable mode"); + evas_object_smart_callback_add(bt, "clicked", _expandable_toggle, fs_bt); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Last selection:"); + elm_box_pack_end(vbox, lb); + evas_object_show(lb); + + en = elm_entry_add(win); + elm_entry_line_wrap_set(en, EINA_FALSE); + elm_entry_editable_set(en, EINA_FALSE); + evas_object_smart_callback_add(fs_bt, "file,chosen", _file_chosen, en); + elm_box_pack_end(vbox, en); + evas_object_show(en); + + evas_object_resize(win, 400, 400); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_fileselector_entry.c b/src/bin/test_fileselector_entry.c new file mode 100644 index 0000000..0359dd5 --- /dev/null +++ b/src/bin/test_fileselector_entry.c @@ -0,0 +1,159 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif + +#ifndef ELM_LIB_QUICKLAUNCH +static void +_file_chosen(void *data, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Evas_Object *entry = data; + char *file = event_info; + elm_entry_entry_set(entry, file); + printf("File chosen: %s\n", file); +} + +static void +_inwin_mode_toggle(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs_en = data; + Eina_Bool value = elm_fileselector_entry_inwin_mode_get(fs_en); + elm_fileselector_entry_inwin_mode_set(fs_en, !value); + printf("Inwin mode set to: %s\n", value ? "false" : "true"); +} + +static void +_folder_only_toggle(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs_en = data; + Evas_Object *ic = elm_fileselector_entry_button_icon_get(fs_en); + Eina_Bool value = elm_fileselector_entry_folder_only_get(fs_en); + elm_fileselector_entry_folder_only_set(fs_en, !value); + printf("Folder only flag set to: %s\n", value ? "false" : "true"); + if (!value) + { + elm_icon_standard_set(ic, "folder"); + elm_fileselector_entry_button_label_set(fs_en, "Select a folder"); + } + else + { + elm_icon_standard_set(ic, "file"); + elm_fileselector_entry_button_label_set(fs_en, "Select a file"); + } +} + +static void +_expandable_toggle(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs_en = data; + Eina_Bool value = elm_fileselector_entry_expandable_get(fs_en); + elm_fileselector_entry_expandable_set(fs_en, !value); + printf("Expandable flag set to: %s\n", value ? "false" : "true"); +} + +static void +_disabled_toggle(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs_en = data; + Eina_Bool value = elm_object_disabled_get(fs_en); + elm_object_disabled_set(fs_en, !value); + printf("Disabled flag set to: %s\n", value ? "false" : "true"); +} + +void +test_fileselector_entry(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *vbox, *hbox, *ic, *bt, *fs_en, *en, *lb; + + win = elm_win_add(NULL, "fileselector entry", ELM_WIN_BASIC); + elm_win_title_set(win, "File Selector Entry"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + vbox = elm_box_add(win); + evas_object_size_hint_weight_set(vbox, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, vbox); + evas_object_show(vbox); + + /* file selector entry */ + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "file"); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + fs_en = elm_fileselector_entry_add(win); + elm_fileselector_entry_button_label_set(fs_en, "Select a file"); + elm_fileselector_entry_button_icon_set(fs_en, ic); + evas_object_size_hint_weight_set(fs_en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(fs_en, EVAS_HINT_FILL, EVAS_HINT_FILL); + + elm_box_pack_end(vbox, fs_en); + evas_object_show(fs_en); + evas_object_show(ic); + + /* attribute setting buttons */ + hbox = elm_box_add(win); + elm_box_horizontal_set(hbox, EINA_TRUE); + elm_box_pack_end(vbox, hbox); + evas_object_show(hbox); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Toggle inwin mode"); + evas_object_smart_callback_add(bt, "clicked", _inwin_mode_toggle, fs_en); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Toggle folder only mode"); + evas_object_smart_callback_add(bt, "clicked", _folder_only_toggle, fs_en); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Toggle expandable mode"); + evas_object_smart_callback_add(bt, "clicked", _expandable_toggle, fs_en); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Last selection:"); + elm_box_pack_end(vbox, lb); + evas_object_show(lb); + + hbox = elm_box_add(win); + elm_box_horizontal_set(hbox, EINA_TRUE); + elm_box_pack_end(vbox, hbox); + evas_object_show(hbox); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Toggle disabled"); + evas_object_smart_callback_add(bt, "clicked", _disabled_toggle, fs_en); + elm_box_pack_end(hbox, bt); + evas_object_show(bt); + + en = elm_entry_add(win); + elm_entry_line_wrap_set(en, EINA_FALSE); + elm_entry_editable_set(en, EINA_FALSE); + evas_object_smart_callback_add(fs_en, "file,chosen", _file_chosen, en); + elm_box_pack_end(vbox, en); + evas_object_show(en); + + evas_object_resize(win, 400, 500); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_flip.c b/src/bin/test_flip.c new file mode 100644 index 0000000..74f850f --- /dev/null +++ b/src/bin/test_flip.c @@ -0,0 +1,494 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +void +my_fl_1(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_ROTATE_Y_CENTER_AXIS); +} + +void +my_fl_2(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_ROTATE_X_CENTER_AXIS); +} + +void +my_fl_3(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_ROTATE_XZ_CENTER_AXIS); +} + +void +my_fl_4(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_ROTATE_YZ_CENTER_AXIS); +} + +void +my_fl_5(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_CUBE_LEFT); +} + +void +my_fl_6(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_CUBE_RIGHT); +} + +void +my_fl_7(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_CUBE_UP); +} + +void +my_fl_8(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_CUBE_DOWN); +} + +void +test_flip(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bx2, *fl, *o, *bt, *ly; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "flip", ELM_WIN_BASIC); + elm_win_title_set(win, "Flip"); + elm_win_focus_highlight_enabled_set(win, EINA_TRUE); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + fl = elm_flip_add(win); + evas_object_size_hint_align_set(fl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(fl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, fl); + + o = elm_bg_add(win); + evas_object_size_hint_align_set(o, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, "sky_01.jpg"); + elm_bg_file_set(o, buf, NULL); + elm_flip_content_front_set(fl, o); + evas_object_show(o); + + ly = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/test.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly, buf, "layout"); + evas_object_size_hint_align_set(ly, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_flip_content_back_set(fl, ly); + evas_object_show(ly); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 1"); + elm_layout_content_set(ly, "element1", bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 2"); + elm_layout_content_set(ly, "element2", bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 3"); + elm_layout_content_set(ly, "element3", bt); + evas_object_show(bt); + + evas_object_show(fl); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + + bt = elm_button_add(win); + elm_button_label_set(bt, "1"); + evas_object_smart_callback_add(bt, "clicked", my_fl_1, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "2"); + evas_object_smart_callback_add(bt, "clicked", my_fl_2, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "3"); + evas_object_smart_callback_add(bt, "clicked", my_fl_3, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "4"); + evas_object_smart_callback_add(bt, "clicked", my_fl_4, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + + bt = elm_button_add(win); + elm_button_label_set(bt, "5"); + evas_object_smart_callback_add(bt, "clicked", my_fl_5, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "6"); + evas_object_smart_callback_add(bt, "clicked", my_fl_6, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "7"); + evas_object_smart_callback_add(bt, "clicked", my_fl_7, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "8"); + evas_object_smart_callback_add(bt, "clicked", my_fl_8, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} + +void +test_flip2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bx2, *fl, *o, *bt, *tb, *li, *en; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "flip2", ELM_WIN_BASIC); + elm_win_title_set(win, "Flip 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, "sky_01.jpg"); + elm_bg_file_set(bg, buf, NULL); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + fl = elm_flip_add(win); + evas_object_size_hint_align_set(fl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(fl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, fl); + + o = elm_box_add(win); + evas_object_size_hint_align_set(o, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + tb = elm_toolbar_add(win); + elm_toolbar_homogenous_set(tb, 0); + evas_object_size_hint_weight_set(tb, 0.0, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, 0.0); + + elm_toolbar_item_append(tb, "arrow_left", "Hello", NULL, NULL); + elm_toolbar_item_append(tb, "arrow_right", "Out", NULL, NULL); + elm_toolbar_item_append(tb, "home", "There", NULL, NULL); + elm_toolbar_item_append(tb, "refresh", "World", NULL, NULL); + + elm_box_pack_end(o, tb); + evas_object_show(tb); + + li = elm_list_add(win); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + elm_list_item_append(li, "This is a list", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Second item", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "3rd", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Fourth", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Number five is alive!", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "The quick brown fox jumps over the lazy dog", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Booyah", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "And another item", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "More of them", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Get with it", NULL, NULL, NULL, NULL); + + elm_list_go(li); + + elm_box_pack_end(o, li); + evas_object_show(li); + + elm_flip_content_front_set(fl, o); + evas_object_show(o); + + en = elm_scrolled_entry_add(win); + elm_scrolled_entry_line_wrap_set(en, EINA_FALSE); + snprintf(buf, sizeof(buf), + "This is an entry widget in this window that
    " + "uses markup like this for styling and
    " + "formatting like this, as well as
    " + "links in the text, so enter text
    " + "in here to edit it. By the way, links are
    " + "called Anchors so you will need
    " + "to refer to them this way.
    " + "
    " + + "Also you can stick in items with (relsize + ascent): " + "" + " (full) " + "" + " (to the left)
    " + + "Also (size + ascent): " + "" + " (full) " + "" + " (before this)
    " + + "And as well (absize + ascent): " + "" + " (full) " + "" + " or even paths to image files on disk too like: " + "" + " ... end." + , PACKAGE_DATA_DIR + ); + elm_scrolled_entry_entry_set(en, buf); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + elm_flip_content_back_set(fl, en); + evas_object_show(en); + + evas_object_show(fl); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + + bt = elm_button_add(win); + elm_button_label_set(bt, "1"); + evas_object_smart_callback_add(bt, "clicked", my_fl_1, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "2"); + evas_object_smart_callback_add(bt, "clicked", my_fl_2, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "3"); + evas_object_smart_callback_add(bt, "clicked", my_fl_3, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "4"); + evas_object_smart_callback_add(bt, "clicked", my_fl_4, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "5"); + evas_object_smart_callback_add(bt, "clicked", my_fl_5, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "6"); + evas_object_smart_callback_add(bt, "clicked", my_fl_6, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} + +void +test_flip3(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bx2, *fl, *fl_f, *fl_b, *o, *bt, *fr; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "flip flip", ELM_WIN_BASIC); + elm_win_title_set(win, "Flip Flip"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + fl = elm_flip_add(win); + evas_object_size_hint_align_set(fl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(fl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, fl); + evas_object_show(fl); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Front"); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_flip_content_front_set(fl, fr); + evas_object_show(fr); + + fl_f = elm_flip_add(win); + evas_object_size_hint_align_set(fl_f, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(fl_f, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_frame_content_set(fr, fl_f); + evas_object_show(fl_f); + + o = elm_bg_add(win); + evas_object_size_hint_align_set(o, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, "sky_01.jpg"); + elm_bg_file_set(o, buf, NULL); + elm_flip_content_front_set(fl_f, o); + evas_object_show(o); + + o = elm_bg_add(win); + evas_object_size_hint_align_set(o, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, "sky_02.jpg"); + elm_bg_file_set(o, buf, NULL); + elm_flip_content_back_set(fl_f, o); + evas_object_show(o); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Back"); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_flip_content_back_set(fl, fr); + evas_object_show(fr); + + fl_b = elm_flip_add(win); + evas_object_size_hint_align_set(fl_b, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(fl_b, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_frame_content_set(fr, fl_b); + evas_object_show(fl_b); + + o = elm_bg_add(win); + evas_object_size_hint_align_set(o, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, "sky_03.jpg"); + elm_bg_file_set(o, buf, NULL); + elm_flip_content_front_set(fl_b, o); + evas_object_show(o); + + o = elm_bg_add(win); + evas_object_size_hint_align_set(o, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, "sky_04.jpg"); + elm_bg_file_set(o, buf, NULL); + elm_flip_content_back_set(fl_b, o); + evas_object_show(o); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Main Flip"); + evas_object_smart_callback_add(bt, "clicked", my_fl_6, fl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Front Flip"); + evas_object_smart_callback_add(bt, "clicked", my_fl_6, fl_f); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Back Flip"); + evas_object_smart_callback_add(bt, "clicked", my_fl_6, fl_b); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_flipselector.c b/src/bin/test_flipselector.c new file mode 100644 index 0000000..5ab4cda --- /dev/null +++ b/src/bin/test_flipselector.c @@ -0,0 +1,115 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +void +_sel_cb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Flipselector_Item *it; + + it = event_info; + printf("label of selected item is: %s\n", elm_flipselector_item_label_get(it)); +} + +void +_unsel_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Flipselector_Item *it; + Evas_Object *fp = data; + it = elm_flipselector_selected_item_get(fp); + elm_flipselector_item_selected_set(it, EINA_FALSE); +} + +void +_third_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Flipselector_Item *it; + Evas_Object *fp = data; + it = elm_flipselector_first_item_get(fp); + it = elm_flipselector_item_next_get(it); + it = elm_flipselector_item_next_get(it); + elm_flipselector_item_selected_set(it, EINA_TRUE); +} + +void +_underflow_cb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("underflow!\n"); +} + +void +_overflow_cb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("overflow!\n"); +} + +void +test_flipselector(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + char buf[8]; + unsigned int i; + Evas_Object *win, *bg, *bx, *fp, *bt; + static const char *lbl[] = { + "Elementary", + "Evas", + "Eina", + "Edje", + "Eet", + "Ecore", + "Efreet", + "Edbus" + }; + + win = elm_win_add(NULL, "flipselector", ELM_WIN_BASIC); + elm_win_title_set(win, "Flip Selector"); + elm_win_autodel_set(win, EINA_TRUE); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + fp = elm_flipselector_add(win); + evas_object_size_hint_weight_set(fp, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_smart_callback_add(fp, "selected", _sel_cb, NULL); + evas_object_smart_callback_add(fp, "underflowed", _overflow_cb, NULL); + evas_object_smart_callback_add(fp, "overflowed", _underflow_cb, NULL); + for (i = 0; i < sizeof(lbl)/sizeof(char *); i++) + elm_flipselector_item_append(fp, lbl[i], NULL, NULL); + elm_box_pack_end(bx, fp); + evas_object_show(fp); + + fp = elm_flipselector_add(win); + evas_object_smart_callback_add(fp, "underflowed", _overflow_cb, NULL); + evas_object_smart_callback_add(fp, "overflowed", _underflow_cb, NULL); + evas_object_size_hint_weight_set(fp, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + for (i = 1990; i < 2099; i++) + { + snprintf(buf, 8, "%d", i); + elm_flipselector_item_append(fp, buf, _sel_cb, NULL); + } + elm_box_pack_end(bx, fp); + evas_object_show(fp); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Select 1992"); + evas_object_smart_callback_add(bt, "clicked", _third_cb, fp); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Unselect year"); + evas_object_smart_callback_add(bt, "clicked", _unsel_cb, fp); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_floating.c b/src/bin/test_floating.c new file mode 100644 index 0000000..96764d6 --- /dev/null +++ b/src/bin/test_floating.c @@ -0,0 +1,109 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +typedef struct _Testitem +{ + Elm_Genlist_Item *item; + int mode; + int onoff; +} Testitem; + + +static Elm_Genlist_Item_Class itc1; +static char *glf_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + char buf[256]; + snprintf(buf, sizeof(buf), "Item # %i", (int)(long)data); + return strdup(buf); +} + +static Evas_Object *glf_icon_get(void *data __UNUSED__, Evas_Object *obj, const char *part __UNUSED__) +{ + char buf[PATH_MAX]; + Evas_Object *ic = elm_icon_add(obj); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + return ic; +} +static Eina_Bool glf_state_get(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + return EINA_FALSE; +} +static void glf_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__) +{ +} + +static void +gl_sel(void *data, Evas_Object *obj, void *event_info) +{ + printf("sel item data [%p] on genlist obj [%p], item pointer [%p]\n", data, obj, event_info); +} + +static Eina_Bool +anim(void *data) +{ + Evas_Object *gl = data; + Evas_Coord x, y; + + y = 0; + x = (sin(ecore_loop_time_get()) * 500); + evas_object_move(gl, x, y); + return ECORE_CALLBACK_RENEW; +} + +static void +_del(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Ecore_Animator *ani = data; + + ecore_animator_del(ani); +} + +void +test_floating(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl; + int i; + Ecore_Animator *ani; + + win = elm_win_add(NULL, "floating", ELM_WIN_BASIC); + elm_win_title_set(win, "Floaating"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + gl = elm_genlist_add(win); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_move(gl, 800, 0); + evas_object_resize(gl, 480, 800); + evas_object_show(gl); + + itc1.item_style = "default"; + itc1.func.label_get = glf_label_get; + itc1.func.icon_get = glf_icon_get; + itc1.func.state_get = glf_state_get; + itc1.func.del = glf_del; + + for (i = 0; i < 20; i++) + { + elm_genlist_item_append(gl, &itc1, + (void *)(long)i/* item data */, + NULL/* parent */, + ELM_GENLIST_ITEM_NONE, + gl_sel/* func */, + (void *)(long)(i * 10)/* func data */); + } + evas_object_resize(win, 480, 800); + evas_object_show(win); + + ani = ecore_animator_add(anim, gl); + evas_object_event_callback_add(win, EVAS_CALLBACK_DEL, _del, ani); +} +#endif diff --git a/src/bin/test_focus.c b/src/bin/test_focus.c new file mode 100644 index 0000000..7227d6d --- /dev/null +++ b/src/bin/test_focus.c @@ -0,0 +1,376 @@ +/* Test for Focus Chain Linear*/ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static Eina_Bool +_event(void *data __UNUSED__, Evas_Object *obj __UNUSED__, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type == EVAS_CALLBACK_KEY_DOWN) + printf ("Key Down:"); + else if (type == EVAS_CALLBACK_KEY_UP) + printf ("Key Up:"); + else + return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + printf("%s\n", ev->key); + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; +} + +static void +_on_key_down(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *einfo __UNUSED__) +{ + //Evas_Event_Key_Down *event = einfo; + //printf("%s %p Key %s Parent %p\n", evas_object_type_get(obj), + // obj, event->keyname, evas_object_smart_parent_get(obj)); +} + +static void +_disable(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *bt = data; + elm_object_disabled_set(bt, EINA_TRUE); +} + +static void +_enable(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *bt = data; + elm_object_disabled_set(bt, EINA_FALSE); +} + +static inline void +my_show(Evas_Object *obj) +{ + evas_object_event_callback_add(obj, EVAS_CALLBACK_KEY_DOWN, + _on_key_down, NULL); + evas_object_show(obj); +} + +void +test_focus(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win; + unsigned int i, j; + + win = elm_win_add(NULL, "focus", ELM_WIN_BASIC); + elm_win_title_set(win, "Focus"); + elm_win_focus_highlight_enabled_set(win, EINA_TRUE); + evas_object_resize(win, 800, 600); + elm_object_event_callback_add(win, _event, NULL); + elm_win_autodel_set(win, EINA_TRUE); + my_show(win); + + { + Evas_Object *bg; + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + my_show(bg); + } + + Evas_Object *mainbx = elm_box_add(win); + elm_box_horizontal_set(mainbx, EINA_TRUE); + elm_win_resize_object_add(win, mainbx); + evas_object_size_hint_weight_set(mainbx, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + my_show(mainbx); + + { //First Col + Evas_Object *bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + elm_box_pack_end(mainbx, bx); + my_show(bx); + + { + Evas_Object *lb = elm_label_add(win); + elm_label_label_set(lb, + "Use Tab and Shift+Tab" + ); + evas_object_size_hint_weight_set(lb, 0.0, 0.0); + evas_object_size_hint_align_set(lb, EVAS_HINT_FILL, + EVAS_HINT_FILL); + elm_box_pack_end(bx, lb); + my_show(lb); + } + + { + Evas_Object *tg = elm_toggle_add(win); + elm_toggle_states_labels_set(tg, "Yes", "No"); + elm_box_pack_end(bx, tg); + my_show(tg); + } + + { + Evas_Object *en = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_entry_set(en, "This is a single line"); + elm_scrolled_entry_single_line_set(en, 1); + elm_box_pack_end(bx, en); + my_show(en); + } + + { + Evas_Object *bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, EINA_TRUE); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx2, 0.0, 0.0); + elm_box_pack_end(bx, bx2); + + for (i = 2; i; i--) + { + Evas_Object *bt; + bt = elm_button_add(win); + elm_button_label_set(bt, "Box"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + if (i%2) + elm_object_disabled_set(bt, EINA_TRUE); + elm_box_pack_end(bx2, bt); + my_show(bt); + } + + { + Evas_Object *sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(sc, EVAS_HINT_FILL, + EVAS_HINT_FILL); + elm_scroller_bounce_set(sc, 1, 1); + elm_scroller_content_min_limit(sc, 1, 1); + elm_box_pack_end(bx2, sc); + my_show(sc); + + { + Evas_Object *bt; + bt = elm_button_add(win); + elm_button_label_set(bt, "Scroller"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + elm_object_event_callback_add(bt, _event, NULL); + elm_scroller_content_set(sc, bt); + my_show(bt); + elm_object_event_callback_del(bt, _event, NULL); + } + } + + my_show(bx2); + } + + { + Evas_Object *bt; + bt = elm_button_add(win); + elm_button_label_set(bt, "Box"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + elm_box_pack_end(bx, bt); + my_show(bt); + } + + { + Evas_Object *bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, EINA_TRUE); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx2, 0.0, 0.0); + elm_box_pack_end(bx, bx2); + my_show(bx2); + + for (i = 2; i; i--) + { + Evas_Object *bx3 = elm_box_add(win); + evas_object_size_hint_align_set(bx3, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx3, 0.0, 0.0); + elm_box_pack_end(bx2, bx3); + my_show(bx3); + + for (j = 3; j; j--) + { + Evas_Object *bt; + bt = elm_button_add(win); + elm_button_label_set(bt, "Box"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + elm_box_pack_end(bx3, bt); + my_show(bt); + } + } + + { + Evas_Object *sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(sc, EVAS_HINT_FILL, + EVAS_HINT_FILL); + elm_scroller_bounce_set(sc, 0, 1); + elm_scroller_content_min_limit(sc, 1, 0); + elm_box_pack_end(bx2, sc); + my_show(sc); + + Evas_Object *bx3 = elm_box_add(win); + evas_object_size_hint_align_set(bx3, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx3, 0.0, 0.0); + elm_scroller_content_set(sc, bx3); + my_show(bx3); + + for (i = 5; i; i--) + { + Evas_Object *bt; + bt = elm_button_add(win); + elm_button_label_set(bt, "BX Scroller"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + elm_box_pack_end(bx3, bt); + my_show(bt); + } + } + } + } + + {//Second Col + char buf[PATH_MAX]; + Evas_Object *ly = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/test.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly, buf, "twolines"); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + elm_box_pack_end(mainbx, ly); + my_show(ly); + + { + Evas_Object *bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, EINA_TRUE); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx2, 0.0, 0.0); + elm_layout_content_set(ly, "element1", bx2); + my_show(bx2); + + for (i = 3; i; i--) + { + Evas_Object *bt; + bt = elm_button_add(win); + elm_button_label_set(bt, "Layout"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + elm_box_pack_end(bx2, bt); + my_show(bt); + elm_object_focus_custom_chain_prepend(bx2, bt, NULL); + } + } + + { + Evas_Object *bx2 = elm_box_add(win); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bx2, 0.0, 0.0); + elm_layout_content_set(ly, "element2", bx2); + my_show(bx2); + + { + Evas_Object *bt; + bt = elm_button_add(win); + elm_button_label_set(bt, "Disable"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_smart_callback_add(bt, "clicked", _disable, bt); + my_show(bt); + elm_object_focus_custom_chain_prepend(bx2, bt, NULL); + + Evas_Object *bt2; + bt2 = elm_button_add(win); + elm_button_label_set(bt2, "Enable"); + evas_object_size_hint_align_set(bt2, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt2, 0.0, 0.0); + elm_box_pack_end(bx2, bt2); + evas_object_smart_callback_add(bt2, "clicked", _enable, bt); + my_show(bt2); + elm_object_focus_custom_chain_append(bx2, bt2, NULL); + } + + } + } + + {//Third Col + Evas_Object *bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + elm_box_pack_end(mainbx, bx); + my_show(bx); + + { + Evas_Object *fr = elm_frame_add(win); + elm_frame_label_set(fr, "Frame"); + elm_box_pack_end(bx, fr); + evas_object_show(fr); + + { + Evas_Object *tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_frame_content_set(fr, tb); + my_show(tb); + for (j = 0; j < 1; j++) + for (i = 0; i < 2; i++) + { + Evas_Object *bt; + bt = elm_button_add(win); + elm_button_label_set(bt, "Table"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_table_pack(tb, bt, i, j, 1, 1); + my_show(bt); + } + } + } + + { + Evas_Object *fr = elm_bubble_add(win); + elm_bubble_label_set(fr, "Bubble"); + evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, + EVAS_HINT_FILL); + elm_box_pack_end(bx, fr); + evas_object_show(fr); + + { + Evas_Object *tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_bubble_content_set(fr, tb); + my_show(tb); + for (j = 0; j < 2; j++) + for (i = 0; i < 1; i++) + { + Evas_Object *bt; + bt = elm_button_add(win); + elm_button_label_set(bt, "Table"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_table_pack(tb, bt, i, j, 1, 1); + my_show(bt); + } + } + } + } +} +#endif diff --git a/src/bin/test_focus2.c b/src/bin/test_focus2.c new file mode 100644 index 0000000..5191a26 --- /dev/null +++ b/src/bin/test_focus2.c @@ -0,0 +1,151 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void +_focus_in(void *data __UNUSED__, Evas *e __UNUSED__, void *event_info) +{ + const char *type = evas_object_type_get(event_info); + if ((type) && (!strcmp(type, "elm_widget"))) + type = elm_object_widget_type_get(event_info); + printf("Evas_Object focus in: %p %s\n", event_info, type); +} + +static void +_focus_out(void *data __UNUSED__, Evas *e __UNUSED__, void *event_info) +{ + const char *type = evas_object_type_get(event_info); + if ((type) && (!strcmp(type, "elm_widget"))) + type = elm_object_widget_type_get(event_info); + printf("Evas_Object focus out: %p %s\n", event_info, type); +} + +static void +_focus_obj(void *data, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *newfocus = data; + const char *type = evas_object_type_get(newfocus); + if ((type) && (!strcmp(type, "elm_widget"))) + type = elm_object_widget_type_get(newfocus); + printf("elm_object_focus(%p) %s\n", newfocus, type); + elm_object_focus(newfocus); +} + +static void +_focus_layout_part(void *data, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *ed = elm_layout_edje_get(data); + + Evas_Object *newfocus = (Evas_Object *)edje_object_part_object_get(ed, "sky"); + const char *type = evas_object_type_get(newfocus); + printf("evas_object_focus_set(%p, 1) %s\n", newfocus, type); + evas_object_focus_set(newfocus, EINA_TRUE);; +} + + +void +test_focus2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *ly, *bt, *en, *bt1; + + win = elm_win_add(NULL, "focus2", ELM_WIN_BASIC); + elm_win_title_set(win, "Focus2"); + elm_win_autodel_set(win, 1); + elm_win_focus_highlight_enabled_set(win, EINA_TRUE); + + evas_event_callback_add + (evas_object_evas_get(win), EVAS_CALLBACK_CANVAS_OBJECT_FOCUS_IN, + _focus_in, NULL); + evas_event_callback_add + (evas_object_evas_get(win), EVAS_CALLBACK_CANVAS_OBJECT_FOCUS_OUT, + _focus_out, NULL); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + +#define PARENT bx /* this is broken, but should work */ +//#define PARENT win + + en = elm_scrolled_entry_add(PARENT); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_entry_set(en, "Scrolled Entry that should get focus"); + elm_scrolled_entry_single_line_set(en, 1); + evas_object_show(en); + elm_box_pack_end(bx, en); + + bt = elm_button_add(PARENT); + elm_button_label_set(bt, "Give focus to scrolled entry"); + evas_object_smart_callback_add(bt, "clicked", _focus_obj, en); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + ly = elm_layout_add(PARENT); + elm_layout_file_set(ly, PACKAGE_DATA_DIR"/objects/test.edj", "layout"); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, ly); + evas_object_show(ly); + + bt1 = bt = elm_button_add(ly); + elm_button_label_set(bt, "Button 1"); + elm_layout_content_set(ly, "element1", bt); + + en = elm_scrolled_entry_add(ly); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_scrollbar_policy_set(en, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_entry_set(en, "Scrolled Entry that should get focus"); + elm_scrolled_entry_single_line_set(en, 1); + elm_layout_content_set(ly, "element2", en); + + bt = elm_button_add(ly); + elm_button_label_set(bt, "Button 2"); + elm_layout_content_set(ly, "element3", bt); + + bt = elm_button_add(PARENT); + elm_button_label_set(bt, "Give focus to layout"); + evas_object_smart_callback_add(bt, "clicked", _focus_obj, ly); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(PARENT); + elm_button_label_set(bt, "Give focus to layout part"); + evas_object_smart_callback_add(bt, "clicked", _focus_layout_part, ly); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(PARENT); + elm_button_label_set(bt, "Give focus to layout 'Button 1'"); + evas_object_smart_callback_add(bt, "clicked", _focus_obj, bt1); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(PARENT); + elm_button_label_set(bt, "Give focus to layout 'Entry'"); + evas_object_smart_callback_add(bt, "clicked", _focus_obj, en); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + evas_object_resize(win, 400, 400); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_gengrid.c b/src/bin/test_gengrid.c new file mode 100644 index 0000000..f5c6b14 --- /dev/null +++ b/src/bin/test_gengrid.c @@ -0,0 +1,357 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +typedef struct _Testitem +{ + Elm_Gengrid_Item *item; + const char *path; + int mode; + int onoff; +} Testitem; + +static const char *img[9] = +{ + "panel_01.jpg", + "plant_01.jpg", + "rock_01.jpg", + "rock_02.jpg", + "sky_01.jpg", + "sky_02.jpg", + "sky_03.jpg", + "sky_04.jpg", + "wood_01.jpg", +}; + +static Elm_Gengrid_Item_Class gic; + +static void +_horizontal_grid(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *grid = data; + elm_gengrid_horizontal_set(grid, elm_check_state_get(obj)); +} + +static void +grid_drag_up(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("Drag up: %p\n", event_info); +} + +static void +grid_drag_right(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("Drag right: %p\n", event_info); +} + +static void +grid_drag_down(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("Drag down: %p\n", event_info); +} + +static void +grid_drag_left(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("Drag left: %p\n", event_info); +} + +static void +grid_drag_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("Drag stop: %p\n", event_info); +} + +static void +grid_selected(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("Selected: %p\n", event_info); +} + +static void +grid_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("Clicked: %p\n", event_info); +} + +static void +grid_longpress(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("longpress %p\n", event_info); +} + +static void +grid_item_check_changed(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Testitem *ti = data; + ti->onoff = elm_check_state_get(obj); + printf("item %p onoff = %i\n", ti, ti->onoff); +} + +char * +grid_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + const Testitem *ti = data; + char buf[256]; + snprintf(buf, sizeof(buf), "Photo %s", ti->path); + return strdup(buf); +} + +Evas_Object * +grid_icon_get(void *data, Evas_Object *obj, const char *part) +{ + const Testitem *ti = data; + if (!strcmp(part, "elm.swallow.icon")) + { + + Evas_Object *icon = elm_bg_add(obj); + elm_bg_file_set(icon, ti->path, NULL); + evas_object_size_hint_aspect_set(icon, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + evas_object_show(icon); + return icon; + } + else if (!strcmp(part, "elm.swallow.end")) + { + Evas_Object *ck; + ck = elm_check_add(obj); + evas_object_propagate_events_set(ck, 0); + elm_check_state_set(ck, ti->onoff); + evas_object_smart_callback_add(ck, "changed", grid_item_check_changed, data); + evas_object_show(ck); + return ck; + } + return NULL; +} + +Eina_Bool +grid_state_get(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + return EINA_FALSE; +} + +void +grid_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__) +{ +} + +static void +grid_sel(void *data, Evas_Object *obj, void *event_info) +{ + printf("sel item data [%p] on grid obj [%p], pointer [%p]\n", data, obj, event_info); +} + +void +test_gengrid(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *grid; + static Testitem ti[144]; + int i, n; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "grid", ELM_WIN_BASIC); + elm_win_title_set(win, "Grid"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + grid = elm_gengrid_add(win); + elm_gengrid_item_size_set(grid, 150, 150); + elm_gengrid_horizontal_set(grid, EINA_FALSE); + elm_gengrid_multi_select_set(grid, EINA_TRUE); + evas_object_smart_callback_add(grid, "selected", grid_selected, NULL); + evas_object_smart_callback_add(grid, "clicked", grid_clicked, NULL); + evas_object_smart_callback_add(grid, "longpressed", grid_longpress, NULL); + evas_object_smart_callback_add(grid, "drag,start,up", grid_drag_up, NULL); + evas_object_smart_callback_add(grid, "drag,start,right", grid_drag_right, NULL); + evas_object_smart_callback_add(grid, "drag,start,down", grid_drag_down, NULL); + evas_object_smart_callback_add(grid, "drag,start,left", grid_drag_left, NULL); + evas_object_smart_callback_add(grid, "drag,stop", grid_drag_stop, NULL); + evas_object_size_hint_weight_set(grid, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + gic.item_style = "default"; + gic.func.label_get = grid_label_get; + gic.func.icon_get = grid_icon_get; + gic.func.state_get = grid_state_get; + gic.func.del = grid_del; + + n = 0; + for (i = 0; i < 12 * 12; i++) + { + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, img[n]); + n = (n + 1) % 9; + ti[i].mode = i; + ti[i].path = eina_stringshare_add(buf); + ti[i].item = elm_gengrid_item_append(grid, &gic, &(ti[i]), grid_sel, NULL); + if (!(i % 5)) + elm_gengrid_item_selected_set(ti[i].item, EINA_TRUE); + } + + evas_object_show(grid); + elm_win_resize_object_add(win, grid); + + evas_object_resize(win, 600, 600); + evas_object_show(win); +} + +static void +_before_bt_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Testitem *ti; + Evas_Object *grid = data; + Elm_Gengrid_Item *sel; + char buf[PATH_MAX]; + + sel = elm_gengrid_selected_item_get(grid); + if (!sel) + return; + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, img[rand() % 9]); + ti = malloc(sizeof(*ti)); + ti->mode = 0; + ti->path = eina_stringshare_add(buf); + ti->item = elm_gengrid_item_insert_before(grid, &gic, ti, sel, grid_sel, + NULL); +} + +static void +_after_bt_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Testitem *ti; + Evas_Object *grid = data; + Elm_Gengrid_Item *sel; + char buf[PATH_MAX]; + + sel = elm_gengrid_selected_item_get(grid); + if (!sel) + return; + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, img[rand() % 9]); + ti = malloc(sizeof(*ti)); + ti->mode = 0; + ti->path = eina_stringshare_add(buf); + ti->item = elm_gengrid_item_insert_after(grid, &gic, ti, sel, grid_sel, + NULL); +} + +static void +_prepend_bt_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Testitem *ti; + Evas_Object *grid = data; + char buf[PATH_MAX]; + + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, img[rand() % 9]); + ti = malloc(sizeof(*ti)); + ti->mode = 0; + ti->path = eina_stringshare_add(buf); + ti->item = elm_gengrid_item_prepend(grid, &gic, ti, grid_sel, NULL); +} + +static void +_append_bt_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Testitem *ti; + Evas_Object *grid = data; + char buf[PATH_MAX]; + + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, img[rand() % 9]); + ti = malloc(sizeof(*ti)); + ti->mode = 0; + ti->path = eina_stringshare_add(buf); + ti->item = elm_gengrid_item_append(grid, &gic, ti, grid_sel, NULL); +} + +static void +_size_changed(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *grid = data; + int size = elm_spinner_value_get(obj); + elm_gengrid_item_size_set(grid, size, size); +} + +void +test_gengrid2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *grid, *bx, *hbx, *bt, *ck; + + win = elm_win_add(NULL, "grid2", ELM_WIN_BASIC); + elm_win_title_set(win, "Grid2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + grid = elm_gengrid_add(win); + elm_gengrid_item_size_set(grid, 150, 150); + elm_gengrid_horizontal_set(grid, EINA_FALSE); + elm_gengrid_multi_select_set(grid, EINA_FALSE); + evas_object_smart_callback_add(grid, "selected", grid_selected, NULL); + evas_object_size_hint_weight_set(grid, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_min_set(grid, 600, 500); + elm_box_pack_end(bx, grid); + evas_object_show(grid); + + hbx = elm_box_add(win); + evas_object_size_hint_weight_set(hbx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_horizontal_set(hbx, EINA_TRUE); + elm_box_pack_end(bx, hbx); + evas_object_show(hbx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Append"); + evas_object_smart_callback_add(bt, "clicked", _append_bt_clicked, grid); + elm_box_pack_end(hbx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Prepend"); + evas_object_smart_callback_add(bt, "clicked", _prepend_bt_clicked, grid); + elm_box_pack_end(hbx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Insert before"); + evas_object_smart_callback_add(bt, "clicked", _before_bt_clicked, grid); + elm_box_pack_end(hbx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Insert after"); + evas_object_smart_callback_add(bt, "clicked", _after_bt_clicked, grid); + elm_box_pack_end(hbx, bt); + evas_object_show(bt); + + bt = elm_spinner_add(win); + elm_spinner_min_max_set(bt, 10, 1024); + elm_spinner_value_set(bt, 150); + elm_spinner_label_format_set(bt, "Item size: %.0f"); + evas_object_smart_callback_add(bt, "changed", _size_changed, grid); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(hbx, bt); + evas_object_show(bt); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Horizontal Mode"); + evas_object_smart_callback_add(ck, "changed", _horizontal_grid, grid); + elm_box_pack_end(hbx, ck); + evas_object_show(ck); + + gic.item_style = "default"; + gic.func.label_get = grid_label_get; + gic.func.icon_get = grid_icon_get; + gic.func.state_get = grid_state_get; + gic.func.del = grid_del; + + evas_object_resize(win, 600, 600); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_genlist.c b/src/bin/test_genlist.c new file mode 100644 index 0000000..4f95890 --- /dev/null +++ b/src/bin/test_genlist.c @@ -0,0 +1,1631 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +/* Hint: + * In this example some calls to elm_genlist_item_append() are used which give the + * value of an int as 'item data' and 'func data' after casting into (void*). For + * sure this works only on architectures where sizeof(int)==sizeof(void*). + * For real world usage you should hold a data structure or value in your + * application and then give only a pointer to this data as data pointer. + */ + +typedef struct _Testitem +{ + Elm_Genlist_Item *item; + int mode; + int onoff; +} Testitem; + + +static Elm_Genlist_Item_Class itc1; +char *gl_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + char buf[256]; + snprintf(buf, sizeof(buf), "Item # %i", (int)(long)data); + return strdup(buf); +} + +Evas_Object *gl_icon_get(void *data __UNUSED__, Evas_Object *obj, const char *part) +{ + char buf[PATH_MAX]; + Evas_Object *ic = elm_icon_add(obj); + if (!strcmp(part, "elm.swallow.end")) + snprintf(buf, sizeof(buf), "%s/images/bubble.png", PACKAGE_DATA_DIR); + else + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + return ic; +} +Eina_Bool gl_state_get(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + return EINA_FALSE; +} +void gl_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__) +{ +} + +static void +gl_sel(void *data, Evas_Object *obj, void *event_info) +{ + printf("sel item data [%p] on genlist obj [%p], item pointer [%p]\n", data, obj, event_info); +} + +static void +_move(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Object *gl = data; + Evas_Event_Mouse_Move *ev = event_info; + int where = 0; + Elm_Genlist_Item *gli; + gli = elm_genlist_at_xy_item_get(gl, ev->cur.canvas.x, ev->cur.canvas.y, &where); + if (gli) + printf("over %p, where %i\n", elm_genlist_item_data_get(gli), where); + else + printf("over none, where %i\n", where); +} + +static void +_bt50_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_genlist_item_bring_in(data); +} + +static void +_bt1500_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_genlist_item_middle_bring_in(data); +} + +static void +_gl_selected(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("selected: %p\n", event_info); +} + +static void +_gl_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("clicked: %p\n", event_info); +} + +static void +_gl_longpress(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("longpress %p\n", event_info); +} + +void +test_genlist(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *bt_50, *bt_1500, *bx; + Evas_Object *over; + Elm_Genlist_Item *gli; + int i; + + win = elm_win_add(NULL, "genlist", ELM_WIN_BASIC); + elm_win_title_set(win, "Genlist"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + gl = elm_genlist_add(win); + evas_object_smart_callback_add(gl, "selected", _gl_selected, NULL); + evas_object_smart_callback_add(gl, "clicked", _gl_clicked, NULL); + evas_object_smart_callback_add(gl, "longpressed", _gl_longpress, NULL); + // FIXME: This causes genlist to resize the horiz axis very slowly :( + // Reenable this and resize the window horizontally, then try to resize it back + //elm_genlist_horizontal_mode_set(gl, ELM_LIST_LIMIT); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, gl); + evas_object_show(gl); + + over = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_color_set(over, 0, 0, 0, 0); + evas_object_event_callback_add(over, EVAS_CALLBACK_MOUSE_MOVE, _move, gl); + evas_object_repeat_events_set(over, 1); + evas_object_show(over); + evas_object_size_hint_weight_set(over, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, over); + + itc1.item_style = "default"; + itc1.func.label_get = gl_label_get; + itc1.func.icon_get = gl_icon_get; + itc1.func.state_get = gl_state_get; + itc1.func.del = gl_del; + + bt_50 = elm_button_add(win); + elm_button_label_set(bt_50, "Go to 50"); + evas_object_show(bt_50); + elm_box_pack_end(bx, bt_50); + + bt_1500 = elm_button_add(win); + elm_button_label_set(bt_1500, "Go to 1500"); + evas_object_show(bt_1500); + elm_box_pack_end(bx, bt_1500); + + for (i = 0; i < 2000; i++) + { + gli = elm_genlist_item_append(gl, &itc1, + (void *)(long)i/* item data */, + NULL/* parent */, + ELM_GENLIST_ITEM_NONE, + gl_sel/* func */, + (void *)(long)(i * 10)/* func data */); + if (i == 50) + evas_object_smart_callback_add(bt_50, "clicked", _bt50_cb, gli); + else if (i == 1500) + evas_object_smart_callback_add(bt_1500, "clicked", _bt1500_cb, gli); + } + evas_object_resize(win, 480, 800); + evas_object_show(win); +} + +/*************/ + +static void +my_gl_clear(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *gl = data; + elm_genlist_clear(gl); +} + +static void +my_gl_add(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *gl = data; + static int i = 0; + + itc1.item_style = "default"; + itc1.func.label_get = gl_label_get; + itc1.func.icon_get = gl_icon_get; + itc1.func.state_get = gl_state_get; + itc1.func.del = gl_del; + + elm_genlist_item_append(gl, &itc1, + (void *)(long)i/* item data */, + NULL/* parent */, + ELM_GENLIST_ITEM_NONE, + gl_sel/* func */, + (void *)(long)(i * 10)/* func data */); + i++; +} + +static void +my_gl_insert_before(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *gl = data; + static int i = 0; + Elm_Genlist_Item *gli_selected; + + itc1.item_style = "default"; + itc1.func.label_get = gl_label_get; + itc1.func.icon_get = gl_icon_get; + itc1.func.state_get = gl_state_get; + itc1.func.del = gl_del; + + gli_selected = elm_genlist_selected_item_get(gl); + if(!gli_selected) + { + printf("no item selected\n"); + return ; + } + + elm_genlist_item_insert_before(gl, &itc1, + (void *)(long)i/* item data */, + NULL/* parent */, + gli_selected /* item before */, + ELM_GENLIST_ITEM_NONE, + gl_sel/* func */, + (void *)(long)(i * 10)/* func data */); + i++; +} + +static void +my_gl_insert_after(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *gl = data; + static int i = 0; + Elm_Genlist_Item *gli_selected; + + itc1.item_style = "default"; + itc1.func.label_get = gl_label_get; + itc1.func.icon_get = gl_icon_get; + itc1.func.state_get = gl_state_get; + itc1.func.del = gl_del; + + gli_selected = elm_genlist_selected_item_get(gl); + if(!gli_selected) + { + printf("no item selected\n"); + return ; + } + + elm_genlist_item_insert_after(gl, &itc1, + (void *)(long)i/* item data */, + NULL/* parent */, + gli_selected /* item after */, + ELM_GENLIST_ITEM_NONE, + gl_sel/* func */, + (void *)(long)(i * 10)/* func data */); + i++; +} + +static void +my_gl_del(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *gl = data; + Elm_Genlist_Item *gli = elm_genlist_selected_item_get(gl); + if (!gli) + { + printf("no item selected\n"); + return; + } + elm_genlist_item_del(gli); +} + +static void +my_gl_disable(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *gl = data; + Elm_Genlist_Item *gli = elm_genlist_selected_item_get(gl); + if (!gli) + { + printf("no item selected\n"); + return; + } + elm_genlist_item_disabled_set(gli, 1); + elm_genlist_item_selected_set(gli, 0); + elm_genlist_item_update(gli); +} + +static void +my_gl_update_all(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *gl = data; + int i = 0; + Elm_Genlist_Item *it = elm_genlist_first_item_get(gl); + while (it) + { + elm_genlist_item_update(it); + printf("%i\n", i); + i++; + it = elm_genlist_item_next_get(it); + } +} + +static void +my_gl_first(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *gl = data; + Elm_Genlist_Item *gli = elm_genlist_first_item_get(gl); + if (!gli) return; + elm_genlist_item_show(gli); + elm_genlist_item_selected_set(gli, 1); +} + +static void +my_gl_last(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *gl = data; + Elm_Genlist_Item *gli = elm_genlist_last_item_get(gl); + if (!gli) return; + elm_genlist_item_show(gli); + elm_genlist_item_selected_set(gli, 1); +} + +static Eina_Bool +my_gl_flush_delay(void *data __UNUSED__) +{ + elm_all_flush(); + return ECORE_CALLBACK_CANCEL; +} + +static void +my_gl_flush(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + ecore_timer_add(1.2, my_gl_flush_delay, NULL); +} + +void +test_genlist2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *bx, *bx2, *bx3, *bt; + Elm_Genlist_Item *gli[10]; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "genlist-2", ELM_WIN_BASIC); + elm_win_title_set(win, "Genlist 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + elm_bg_file_set(bg, buf, NULL); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + gl = elm_genlist_add(win); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(gl); + + itc1.item_style = "default"; + itc1.func.label_get = gl_label_get; + itc1.func.icon_get = gl_icon_get; + itc1.func.state_get = gl_state_get; + itc1.func.del = gl_del; + + gli[0] = elm_genlist_item_append(gl, &itc1, + (void *)1001/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + (void *)1001/* func data */); + gli[1] = elm_genlist_item_append(gl, &itc1, + (void *)1002/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + (void *)1002/* func data */); + gli[2] = elm_genlist_item_append(gl, &itc1, + (void *)1003/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + (void *)1003/* func data */); + gli[3] = elm_genlist_item_prepend(gl, &itc1, + (void *)1004/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + (void *)1004/* func data */); + gli[4] = elm_genlist_item_prepend(gl, &itc1, + (void *)1005/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + (void *)1005/* func data */); + gli[5] = elm_genlist_item_insert_before(gl, &itc1, + (void *)1006/* item data */, NULL/* parent */, gli[2]/* rel */, ELM_GENLIST_ITEM_NONE, + gl_sel/* func */, (void *)1006/* func data */); + gli[6] = elm_genlist_item_insert_after(gl, &itc1, + (void *)1007/* item data */, NULL/* parent */, gli[2]/* rel */, ELM_GENLIST_ITEM_NONE, + gl_sel/* func */, (void *)1007/* func data */); + + elm_box_pack_end(bx, gl); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "/\\"); + evas_object_smart_callback_add(bt, "clicked", my_gl_first, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "\\/"); + evas_object_smart_callback_add(bt, "clicked", my_gl_last, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "#"); + evas_object_smart_callback_add(bt, "clicked", my_gl_disable, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "U"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update_all, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "X"); + evas_object_smart_callback_add(bt, "clicked", my_gl_clear, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "+"); + evas_object_smart_callback_add(bt, "clicked", my_gl_add, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "-"); + evas_object_smart_callback_add(bt, "clicked", my_gl_del, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx3 = elm_box_add(win); + elm_box_horizontal_set(bx3, 1); + elm_box_homogenous_set(bx3, 1); + evas_object_size_hint_weight_set(bx3, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx3, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "+ before"); + evas_object_smart_callback_add(bt, "clicked", my_gl_insert_before, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx3, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "+ after"); + evas_object_smart_callback_add(bt, "clicked", my_gl_insert_after, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx3, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Flush"); + evas_object_smart_callback_add(bt, "clicked", my_gl_flush, gl); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx3, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx3); + evas_object_show(bx3); + + + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +/*************/ + +static Elm_Genlist_Item_Class itc2; +char *gl2_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + const Testitem *tit = data; + char buf[256]; + snprintf(buf, sizeof(buf), "Item mode %i", tit->mode); + return strdup(buf); +} +Evas_Object *gl2_icon_get(void *data, Evas_Object *obj, const char *part) +{ + const Testitem *tit = data; + char buf[PATH_MAX]; + Evas_Object *ic = elm_icon_add(obj); + if (!strcmp(part, "elm.swallow.icon")) + { + if (!(tit->mode & 0x3)) + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + else if ((tit->mode & 0x3) == 1) + snprintf(buf, sizeof(buf), "%s/images/logo.png", PACKAGE_DATA_DIR); + else if ((tit->mode & 0x3) == 2) + snprintf(buf, sizeof(buf), "%s/images/panel_01.jpg", PACKAGE_DATA_DIR); + else if ((tit->mode & 0x3) == 3) + snprintf(buf, sizeof(buf), "%s/images/rock_01.jpg", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + } + else if (!strcmp(part, "elm.swallow.end")) + { + if (!(tit->mode & 0x3)) + snprintf(buf, sizeof(buf), "%s/images/sky_01.jpg", PACKAGE_DATA_DIR); + else if ((tit->mode & 0x3) == 1) + snprintf(buf, sizeof(buf), "%s/images/sky_02.jpg", PACKAGE_DATA_DIR); + else if ((tit->mode & 0x3) == 2) + snprintf(buf, sizeof(buf), "%s/images/sky_03.jpg", PACKAGE_DATA_DIR); + else if ((tit->mode & 0x3) == 3) + snprintf(buf, sizeof(buf), "%s/images/sky_04.jpg", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + } + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + return ic; +} +Eina_Bool gl2_state_get(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + return EINA_FALSE; +} +void gl2_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__) +{ +} + +static void +my_gl_update(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Testitem *tit = data; + tit->mode++; + elm_genlist_item_update(tit->item); +} + +void +test_genlist3(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *bx, *bx2, *bt; + static Testitem tit[3]; + + win = elm_win_add(NULL, "genlist-3", ELM_WIN_BASIC); + elm_win_title_set(win, "Genlist 3"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + gl = elm_genlist_add(win); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(gl); + + itc2.item_style = "default"; + itc2.func.label_get = gl2_label_get; + itc2.func.icon_get = gl2_icon_get; + itc2.func.state_get = gl2_state_get; + itc2.func.del = gl2_del; + + tit[0].mode = 0; + tit[0].item = elm_genlist_item_append(gl, &itc2, + &(tit[0])/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + NULL/* func data */); + tit[1].mode = 1; + tit[1].item = elm_genlist_item_append(gl, &itc2, + &(tit[1])/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + NULL/* func data */); + tit[2].mode = 2; + tit[2].item = elm_genlist_item_append(gl, &itc2, + &(tit[2])/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + NULL/* func data */); + + elm_box_pack_end(bx, gl); + evas_object_show(bx); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[1]"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[0])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[2]"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[1])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[3]"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[2])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +/*************/ + +static void +my_gl_item_check_changed(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Testitem *tit = data; + tit->onoff = elm_check_state_get(obj); + printf("item %p onoff = %i\n", tit, tit->onoff); +} + +static Elm_Genlist_Item_Class itc3; +char *gl3_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + const Testitem *tit = data; + char buf[256]; + snprintf(buf, sizeof(buf), "Item mode %i", tit->mode); + return strdup(buf); +} +Evas_Object *gl3_icon_get(void *data, Evas_Object *obj, const char *part) +{ + const Testitem *tit = data; + if (!strcmp(part, "elm.swallow.icon")) + { + Evas_Object *lb; + + lb = elm_label_add(obj); + elm_label_line_wrap_set(lb, 1); + elm_label_wrap_width_set(lb, 201); + elm_label_label_set(lb, "ashj ascjscjh n asjkl hcjlh ls hzshnn zjh sh zxjcjsnd h dfw sdv edev efe fwefvv vsd cvs ws wf fvwf wd fwe f we wef we wfe rfwewef wfv wswf wefg sdfws w wsdcfwcf wsc vdv sdsd sdcd cv wsc sdcv wsc d sdcdcsd sdcdsc wdvd sdcsd wscxcv wssvd sd"); + evas_object_show(lb); + return lb; + } + else if (!strcmp(part, "elm.swallow.end")) + { + Evas_Object *ck; + ck = elm_check_add(obj); + evas_object_propagate_events_set(ck, 0); + elm_check_state_set(ck, tit->onoff); + evas_object_smart_callback_add(ck, "changed", my_gl_item_check_changed, data); + evas_object_show(ck); + return ck; + } + return NULL; +} +Eina_Bool gl3_state_get(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + return EINA_FALSE; +} +void gl3_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__) +{ +} + +void +test_genlist4(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *bx, *bx2, *bt; + static Testitem tit[3]; + + win = elm_win_add(NULL, "genlist-4", ELM_WIN_BASIC); + elm_win_title_set(win, "Genlist 4"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + gl = elm_genlist_add(win); + elm_genlist_multi_select_set(gl, 1); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(gl); + + itc3.item_style = "default"; + itc3.func.label_get = gl3_label_get; + itc3.func.icon_get = gl3_icon_get; + itc3.func.state_get = gl3_state_get; + itc3.func.del = gl3_del; + + tit[0].mode = 0; + tit[0].item = elm_genlist_item_append(gl, &itc3, + &(tit[0])/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + NULL/* func data */); + tit[1].mode = 1; + tit[1].item = elm_genlist_item_append(gl, &itc3, + &(tit[1])/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + NULL/* func data */); + tit[2].mode = 2; + tit[2].item = elm_genlist_item_append(gl, &itc3, + &(tit[2])/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + NULL/* func data */); + + elm_box_pack_end(bx, gl); + evas_object_show(bx); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[1]"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[0])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[2]"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[1])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[3]"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[2])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + + +/*************/ +static void +my_gl_item_check_changed2(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Testitem *tit = data; + tit->onoff = elm_check_state_get(obj); + printf("item %p onoff = %i\n", tit, tit->onoff); +} + +static Elm_Genlist_Item_Class itc5; +char *gl5_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part) +{ + const Testitem *tit = data; + char buf[256]; + if (!strcmp(part, "elm.text")) + { + snprintf(buf, sizeof(buf), "Item mode %i", tit->mode); + } + else if (!strcmp(part, "elm.text.sub")) + { + snprintf(buf, sizeof(buf), "%i bottles on the wall", tit->mode); + } + return strdup(buf); +} +Evas_Object *gl5_icon_get(void *data, Evas_Object *obj, const char *part) +{ + const Testitem *tit = data; + char buf[PATH_MAX]; + if (!strcmp(part, "elm.swallow.icon")) + { + Evas_Object *bx = elm_box_add(obj); + Evas_Object *ic; + elm_box_horizontal_set(bx, 1); + ic = elm_icon_add(obj); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_show(ic); + elm_box_pack_end(bx, ic); + ic = elm_icon_add(obj); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_show(ic); + elm_box_pack_end(bx, ic); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + return bx; + } + else if (!strcmp(part, "elm.swallow.end")) + { + Evas_Object *ck; + ck = elm_check_add(obj); + evas_object_propagate_events_set(ck, 0); + elm_check_state_set(ck, tit->onoff); + evas_object_smart_callback_add(ck, "changed", my_gl_item_check_changed2, data); + evas_object_show(ck); + return ck; + } + return NULL; +} +Eina_Bool gl5_state_get(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + return EINA_FALSE; +} +void gl5_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__) +{ +} + +static void +item_drag_up(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag up\n"); +} + +static void +item_drag_down(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag down\n"); +} + +static void +item_drag_left(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag left\n"); +} + +static void +item_drag_right(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag right\n"); +} + +static void +scroll_top(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Top edge!\n"); +} + +static void +scroll_bottom(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Bottom edge!\n"); +} + +static void +scroll_left(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Left edge!\n"); +} + +static void +scroll_right(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Right edge!\n"); +} + +static void +item_drag(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag\n"); +} + +static void +item_drag_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag stop\n"); +} + +static void +item_longpress(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("longpress\n"); +} + +void +test_genlist5(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *bx, *bx2, *bt; + static Testitem tit[3]; + + win = elm_win_add(NULL, "genlist-5", ELM_WIN_BASIC); + elm_win_title_set(win, "Genlist 5"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + gl = elm_genlist_add(win); + elm_genlist_always_select_mode_set(gl, 1); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(gl); + itc5.item_style = "double_label"; + itc5.func.label_get = gl5_label_get; + itc5.func.icon_get = gl5_icon_get; + itc5.func.state_get = gl5_state_get; + itc5.func.del = gl5_del; + + tit[0].mode = 0; + tit[0].item = elm_genlist_item_append(gl, &itc5, + &(tit[0])/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + NULL/* func data */); + tit[1].mode = 1; + tit[1].item = elm_genlist_item_append(gl, &itc5, + &(tit[1])/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + NULL/* func data */); + tit[2].mode = 2; + tit[2].item = elm_genlist_item_append(gl, &itc5, + &(tit[2])/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl_sel/* func */, + NULL/* func data */); + + elm_box_pack_end(bx, gl); + evas_object_show(bx); + + evas_object_smart_callback_add(gl, "drag,start,up", item_drag_up, NULL); + evas_object_smart_callback_add(gl, "drag,start,down", item_drag_down, NULL); + evas_object_smart_callback_add(gl, "drag,start,left", item_drag_left, NULL); + evas_object_smart_callback_add(gl, "drag,start,right", item_drag_right, NULL); + evas_object_smart_callback_add(gl, "scroll,edge,top", scroll_top, NULL); + evas_object_smart_callback_add(gl, "scroll,edge,bottom", scroll_bottom, NULL); + evas_object_smart_callback_add(gl, "scroll,edge,left", scroll_left, NULL); + evas_object_smart_callback_add(gl, "scroll,edge,right", scroll_right, NULL); + evas_object_smart_callback_add(gl, "drag", item_drag, NULL); + evas_object_smart_callback_add(gl, "drag,stop", item_drag_stop, NULL); + evas_object_smart_callback_add(gl, "longpressed", item_longpress, NULL); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[1]"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[0])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[2]"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[1])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[3]"); + evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[2])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +/*************/ + +static Elm_Genlist_Item_Class itc4; + +static void +gl4_sel(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = (Elm_Genlist_Item *)event_info; + int depth = 0; + + depth = elm_genlist_item_expanded_depth_get(it); + printf("expanded depth for selected item is %d\n", depth); + +} +static void +gl4_exp(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + Evas_Object *gl = elm_genlist_item_genlist_get(it); + int val = (int)(long)elm_genlist_item_data_get(it); + val *= 10; + elm_genlist_item_append(gl, &itc4, + (void *)(long)(val + 1)/* item data */, it/* parent */, + ELM_GENLIST_ITEM_NONE, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc4, + (void *)(long)(val + 2)/* item data */, it/* parent */, + ELM_GENLIST_ITEM_NONE, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc4, + (void *)(long)(val + 3)/* item data */, it/* parent */, + ELM_GENLIST_ITEM_SUBITEMS, gl4_sel/* func */, + NULL/* func data */); +} +static void +gl4_con(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_subitems_clear(it); +} + +static void +gl4_exp_req(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, 1); +} +static void +gl4_con_req(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, 0); +} + +char *gl4_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + char buf[256]; + snprintf(buf, sizeof(buf), "Item mode %i", (int)(long)data); + return strdup(buf); +} +Evas_Object *gl4_icon_get(void *data __UNUSED__, Evas_Object *obj, const char *part) +{ + char buf[PATH_MAX]; + if (!strcmp(part, "elm.swallow.icon")) + { + Evas_Object *ic = elm_icon_add(obj); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + evas_object_show(ic); + return ic; + } + else if (!strcmp(part, "elm.swallow.end")) + { + Evas_Object *ck; + ck = elm_check_add(obj); + evas_object_show(ck); + return ck; + } + return NULL; +} +Eina_Bool gl4_state_get(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + return EINA_FALSE; +} +void gl4_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__) +{ +} + +void +test_genlist6(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *bx, *bx2, *bt; + + win = elm_win_add(NULL, "genlist-tree", ELM_WIN_BASIC); + elm_win_title_set(win, "Genlist Tree"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + gl = elm_genlist_add(win); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(gl); + + itc4.item_style = "default"; + itc4.func.label_get = gl4_label_get; + itc4.func.icon_get = gl4_icon_get; + itc4.func.state_get = gl4_state_get; + itc4.func.del = gl4_del; + + elm_genlist_item_append(gl, &itc4, + (void *)1/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_SUBITEMS, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc4, + (void *)2/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_SUBITEMS, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc4, + (void *)3/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_NONE, gl4_sel/* func */, + NULL/* func data */); + + evas_object_smart_callback_add(gl, "expand,request", gl4_exp_req, gl); + evas_object_smart_callback_add(gl, "contract,request", gl4_con_req, gl); + evas_object_smart_callback_add(gl, "expanded", gl4_exp, gl); + evas_object_smart_callback_add(gl, "contracted", gl4_con, gl); + + elm_box_pack_end(bx, gl); + evas_object_show(bx); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[1]"); +// evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[0])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[2]"); +// evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[1])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "[3]"); +// evas_object_smart_callback_add(bt, "clicked", my_gl_update, &(tit[2])); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +/*************/ + +struct genlist7_data +{ + Evas_Object *win, *pager; +}; + +static Elm_Genlist_Item_Class itc7; +static void +gl_sel7(void *data, Evas_Object *obj, void *event_info) +{ + if (!event_info) return; + elm_genlist_item_item_class_update(event_info, &itc7); + printf("sel item data [%p] on genlist obj [%p], item pointer [%p], new item style [%s] \n", data, obj, event_info, itc7.item_style); +} + +static void +test_genlist7_back_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + struct genlist7_data *info = data; + if (!info) return; + + elm_pager_content_pop(info->pager); +} + +static void +test_genlist7_swipe(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + struct genlist7_data *info = data; + Evas_Object *box, *entry, *button; + char item_data[] = "Just a simple test"; + + if ((!event_info) || (!data)) return; + + box = elm_box_add(info->win); + elm_box_homogenous_set(box, 0); + evas_object_size_hint_weight_set(box, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(box, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(box); + + entry = elm_scrolled_entry_add(info->win); + elm_scrolled_entry_editable_set(entry, EINA_FALSE); + elm_scrolled_entry_entry_set(entry, item_data); + evas_object_size_hint_weight_set(entry, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(entry, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(entry); + + button = elm_button_add(info->win); + elm_button_label_set(button, "back"); + evas_object_size_hint_weight_set(button, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(button, EVAS_HINT_FILL, 0); + evas_object_smart_callback_add(button, "clicked", test_genlist7_back_cb, + info); + evas_object_show(button); + + elm_box_pack_start(box, entry); + elm_box_pack_end(box, button); + + elm_pager_content_push(info->pager, box); +} + +void +test_genlist7(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *pager; + static struct genlist7_data info; + static Testitem tit[3]; + + win = elm_win_add(NULL, "genlist-7", ELM_WIN_BASIC); + elm_win_title_set(win, "Genlist 7"); + elm_win_autodel_set(win, 1); + info.win = win; + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + pager = elm_pager_add(win); + elm_win_resize_object_add(win, pager); + evas_object_size_hint_weight_set(pager, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(pager, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(pager); + info.pager = pager; + + gl = elm_genlist_add(win); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_smart_callback_add(gl, "swipe", test_genlist7_swipe, &info); + evas_object_show(gl); + elm_pager_content_push(pager, gl); + + itc2.item_style = "default"; + itc2.func.label_get = gl2_label_get; + itc2.func.icon_get = gl2_icon_get; + itc2.func.state_get = gl2_state_get; + itc2.func.del = gl2_del; + + itc7.item_style = "double_label"; + itc7.func.label_get = gl5_label_get; + itc7.func.icon_get = gl5_icon_get; + itc7.func.state_get = gl5_state_get; + itc7.func.del = gl5_del; + + tit[0].mode = 0; + tit[0].item = elm_genlist_item_append(gl, &itc2, + &(tit[0])/* item data */, NULL/* parent */, + ELM_GENLIST_ITEM_NONE, gl_sel7/* func */, + NULL/* func data */); + tit[1].mode = 1; + tit[1].item = elm_genlist_item_append(gl, &itc2, + &(tit[1])/* item data */, NULL/* parent */, + ELM_GENLIST_ITEM_NONE, gl_sel7/* func */, + NULL/* func data */); + tit[2].mode = 2; + tit[2].item = elm_genlist_item_append(gl, &itc2, + &(tit[2])/* item data */, NULL/* parent */, + ELM_GENLIST_ITEM_NONE, gl_sel7/* func */, + NULL/* func data */); + + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +/*************/ + +static Elm_Genlist_Item_Class itc_group; +char *gl8_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + char buf[256]; + snprintf(buf, sizeof(buf), "Group Index # %i (Item # %i)", (int)((long)data / 10), (int)(long)data); + return strdup(buf); +} + +static void +_bt_show_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_genlist_item_top_show(data); + //elm_genlist_item_show(data); + //elm_genlist_item_middle_show(data); +} +static void +_bt_bring_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_genlist_item_top_bring_in(data); + //elm_genlist_item_bring_in(data); + //elm_genlist_item_middle_bring_in(data); +} + +void +test_genlist8(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *bt[8], *bx, *bx2, *bx3; + Elm_Genlist_Item *gli = NULL, *git = NULL; + int i, bt_count, bt_num; + + win = elm_win_add(NULL, "genlist-group", ELM_WIN_BASIC); + elm_win_title_set(win, "Genlist Group"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + gl = elm_genlist_add(win); + evas_object_smart_callback_add(gl, "selected", _gl_selected, NULL); + evas_object_smart_callback_add(gl, "clicked", _gl_clicked, NULL); + evas_object_smart_callback_add(gl, "longpressed", _gl_longpress, NULL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, gl); + evas_object_show(gl); + + itc1.item_style = "default"; + itc1.func.label_get = gl_label_get; + itc1.func.icon_get = gl_icon_get; + itc1.func.state_get = gl_state_get; + itc1.func.del = gl_del; + + itc_group.item_style = "group_index"; + itc_group.func.label_get = gl8_label_get; + itc_group.func.icon_get = NULL; + itc_group.func.state_get = NULL; + itc_group.func.del = gl_del; + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, EINA_TRUE); + elm_box_homogenous_set(bx2, EINA_TRUE); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt_num = 0; + bt[bt_num] = elm_button_add(win); + elm_button_label_set(bt[bt_num], "Show 0"); + evas_object_size_hint_align_set(bt[bt_num], EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt[bt_num], EVAS_HINT_EXPAND, 0.0); + evas_object_show(bt[bt_num]); + elm_box_pack_end(bx2, bt[bt_num]); + + bt[++bt_num] = elm_button_add(win); + elm_button_label_set(bt[bt_num], "Show 26"); + evas_object_size_hint_align_set(bt[bt_num], EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt[bt_num], EVAS_HINT_EXPAND, 0.0); + evas_object_show(bt[bt_num]); + elm_box_pack_end(bx2, bt[bt_num]); + + bt[++bt_num] = elm_button_add(win); + elm_button_label_set(bt[bt_num], "Show 101"); + evas_object_size_hint_align_set(bt[bt_num], EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt[bt_num], EVAS_HINT_EXPAND, 0.0); + evas_object_show(bt[bt_num]); + elm_box_pack_end(bx2, bt[bt_num]); + + bt[++bt_num] = elm_button_add(win); + elm_button_label_set(bt[bt_num], "Show 480"); + evas_object_size_hint_align_set(bt[bt_num], EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt[bt_num], EVAS_HINT_EXPAND, 0.0); + evas_object_show(bt[bt_num]); + elm_box_pack_end(bx2, bt[bt_num]); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx3 = elm_box_add(win); + elm_box_horizontal_set(bx3, EINA_TRUE); + elm_box_homogenous_set(bx3, EINA_TRUE); + evas_object_size_hint_weight_set(bx3, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx3, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt[++bt_num] = elm_button_add(win); + elm_button_label_set(bt[bt_num], "Bring top 0"); + evas_object_size_hint_align_set(bt[bt_num], EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt[bt_num], EVAS_HINT_EXPAND, 0.0); + evas_object_show(bt[bt_num]); + elm_box_pack_end(bx3, bt[bt_num]); + + bt[++bt_num] = elm_button_add(win); + elm_button_label_set(bt[bt_num], "Bring top 31"); + evas_object_size_hint_align_set(bt[bt_num], EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt[bt_num], EVAS_HINT_EXPAND, 0.0); + evas_object_show(bt[bt_num]); + elm_box_pack_end(bx3, bt[bt_num]); + + bt[++bt_num] = elm_button_add(win); + elm_button_label_set(bt[bt_num], "Bring top 239"); + evas_object_size_hint_align_set(bt[bt_num], EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt[bt_num], EVAS_HINT_EXPAND, 0.0); + evas_object_show(bt[bt_num]); + elm_box_pack_end(bx3, bt[bt_num]); + + bt[++bt_num] = elm_button_add(win); + elm_button_label_set(bt[bt_num], "Bring top 477"); + evas_object_size_hint_align_set(bt[bt_num], EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt[bt_num], EVAS_HINT_EXPAND, 0.0); + evas_object_show(bt[bt_num]); + elm_box_pack_end(bx3, bt[bt_num]); + + elm_box_pack_end(bx, bx3); + evas_object_show(bx3); + + bt_count = 0; + for (i = 0; i < 500; i++) + { + if (!(i % 10)) + { + gli = git = elm_genlist_item_append(gl, &itc_group, + (void *)(long)i/* item data */, + NULL/* parent */, + ELM_GENLIST_ITEM_GROUP, + gl_sel/* func */, + (void *)(long)(i * 10)/* func data */); + } + else if (git) + { + gli = elm_genlist_item_append(gl, &itc1, + (void *)(long)i/* item data */, + git/* parent */, + ELM_GENLIST_ITEM_NONE, + gl_sel/* func */, + (void *)(long)(i * 10)/* func data */); + } + //elm_genlist_item_display_only_set(gli, EINA_TRUE); + switch (i) + { + case 0: + evas_object_smart_callback_add(bt[0], "clicked", _bt_show_cb, gli); + evas_object_smart_callback_add(bt[4], "clicked", _bt_bring_cb, gli); + break; + case 26: + evas_object_smart_callback_add(bt[1], "clicked", _bt_show_cb, gli); + break; + case 31: + evas_object_smart_callback_add(bt[5], "clicked", _bt_bring_cb, gli); + break; + case 101: + evas_object_smart_callback_add(bt[2], "clicked", _bt_show_cb, gli); + break; + case 239: + evas_object_smart_callback_add(bt[6], "clicked", _bt_bring_cb, gli); + break; + case 477: + evas_object_smart_callback_add(bt[7], "clicked", _bt_bring_cb, gli); + break; + case 480: + evas_object_smart_callback_add(bt[3], "clicked", _bt_show_cb, gli); + break; + } + } + + evas_object_resize(win, 480, 800); + evas_object_show(win); +} + +/*************/ + +static void +gl9_exp(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + Evas_Object *gl = elm_genlist_item_genlist_get(it); + int val = (int)(long)elm_genlist_item_data_get(it); + val *= 10; + elm_genlist_item_append(gl, &itc1, + (void *)(long)(val + 1)/* item data */, it/* parent */, + ELM_GENLIST_ITEM_NONE, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc1, + (void *)(long)(val + 2)/* item data */, it/* parent */, + ELM_GENLIST_ITEM_NONE, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc1, + (void *)(long)(val + 3)/* item data */, it/* parent */, + ELM_GENLIST_ITEM_SUBITEMS, gl4_sel/* func */, + NULL/* func data */); +} +static void +gl9_con(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_subitems_clear(it); +} + +static void +gl9_exp_req(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, EINA_TRUE); +} +static void +gl9_con_req(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, EINA_FALSE); +} + +void +test_genlist9(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *bx; + Elm_Genlist_Item *git; + + win = elm_win_add(NULL, "genlist-group-tree", ELM_WIN_BASIC); + elm_win_title_set(win, "Genlist Group Tree"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + gl = elm_genlist_add(win); + evas_object_smart_callback_add(gl, "selected", _gl_selected, NULL); + evas_object_smart_callback_add(gl, "clicked", _gl_clicked, NULL); + evas_object_smart_callback_add(gl, "longpressed", _gl_longpress, NULL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, gl); + evas_object_show(gl); + + itc1.item_style = "default"; + itc1.func.label_get = gl_label_get; + itc1.func.icon_get = gl_icon_get; + itc1.func.state_get = gl_state_get; + itc1.func.del = gl_del; + + itc_group.item_style = "group_index"; + itc_group.func.label_get = gl8_label_get; + itc_group.func.icon_get = NULL; + itc_group.func.state_get = NULL; + itc_group.func.del = gl_del; + + git = elm_genlist_item_append(gl, &itc_group, + (void *)0/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_GROUP, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc1, + (void *)1/* item data */, git/* parent */, ELM_GENLIST_ITEM_SUBITEMS, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc1, + (void *)2/* item data */, git/* parent */, ELM_GENLIST_ITEM_NONE, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc1, + (void *)3/* item data */, git/* parent */, ELM_GENLIST_ITEM_SUBITEMS, gl4_sel/* func */, + NULL/* func data */); + git = elm_genlist_item_append(gl, &itc_group, + (void *)4/* item data */, NULL/* parent */, ELM_GENLIST_ITEM_GROUP, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc1, + (void *)5/* item data */, git/* parent */, ELM_GENLIST_ITEM_SUBITEMS, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc1, + (void *)6/* item data */, git/* parent */, ELM_GENLIST_ITEM_NONE, gl4_sel/* func */, + NULL/* func data */); + elm_genlist_item_append(gl, &itc1, + (void *)7/* item data */, git/* parent */, ELM_GENLIST_ITEM_SUBITEMS, gl4_sel/* func */, + NULL/* func data */); + + evas_object_smart_callback_add(gl, "expand,request", gl9_exp_req, gl); + evas_object_smart_callback_add(gl, "contract,request", gl9_con_req, gl); + evas_object_smart_callback_add(gl, "expanded", gl9_exp, gl); + evas_object_smart_callback_add(gl, "contracted", gl9_con, gl); + + evas_object_resize(win, 480, 800); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_hover.c b/src/bin/test_hover.c new file mode 100644 index 0000000..f4b597c --- /dev/null +++ b/src/bin/test_hover.c @@ -0,0 +1,172 @@ +#include +#include +#ifndef ELM_LIB_QUICKLAUNCH +static void +my_hover_bt(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *hv = data; + + evas_object_show(hv); +} + +void +test_hover(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bt, *hv, *ic; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "hover", ELM_WIN_BASIC); + elm_win_title_set(win, "Hover"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + hv = elm_hover_add(win); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button"); + evas_object_smart_callback_add(bt, "clicked", my_hover_bt, hv); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + elm_hover_parent_set(hv, win); + elm_hover_target_set(hv, bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Popup"); + elm_hover_content_set(hv, "middle", bt); + evas_object_show(bt); + + bx = elm_box_add(win); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Top 1"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + bt = elm_button_add(win); + elm_button_label_set(bt, "Top 2"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + bt = elm_button_add(win); + elm_button_label_set(bt, "Top 3"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + evas_object_show(bx); + elm_hover_content_set(hv, "top", bx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Bottom"); + elm_hover_content_set(hv, "bottom", bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Left"); + elm_hover_content_set(hv, "left", bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Right"); + elm_hover_content_set(hv, "right", bt); + evas_object_show(bt); + + evas_object_size_hint_min_set(bg, 160, 160); + evas_object_size_hint_max_set(bg, 640, 640); + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +void +test_hover2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bt, *hv, *ic; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "hover2", ELM_WIN_BASIC); + elm_win_title_set(win, "Hover 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + hv = elm_hover_add(win); + elm_object_style_set(hv, "popout"); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button"); + evas_object_smart_callback_add(bt, "clicked", my_hover_bt, hv); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + elm_hover_parent_set(hv, win); + elm_hover_target_set(hv, bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Popup"); + elm_hover_content_set(hv, "middle", bt); + evas_object_show(bt); + + bx = elm_box_add(win); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + bt = elm_button_add(win); + elm_button_label_set(bt, "Top 1"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + bt = elm_button_add(win); + elm_button_label_set(bt, "Top 2"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + bt = elm_button_add(win); + elm_button_label_set(bt, "Top 3"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_show(bx); + elm_hover_content_set(hv, "top", bx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Bot"); + elm_hover_content_set(hv, "bottom", bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Left"); + elm_hover_content_set(hv, "left", bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Right"); + elm_hover_content_set(hv, "right", bt); + evas_object_show(bt); + + evas_object_size_hint_min_set(bg, 160, 160); + evas_object_size_hint_max_set(bg, 640, 640); + evas_object_resize(win, 320, 320); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_hoversel.c b/src/bin/test_hoversel.c new file mode 100644 index 0000000..40b68e2 --- /dev/null +++ b/src/bin/test_hoversel.c @@ -0,0 +1,109 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_hoversel(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bt, *ic; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "hoversel", ELM_WIN_BASIC); + elm_win_title_set(win, "Hoversel"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + bt = elm_hoversel_add(win); + elm_hoversel_hover_parent_set(bt, win); + elm_hoversel_label_set(bt, "Labels"); + elm_hoversel_item_add(bt, "Item 1", NULL, ELM_ICON_NONE, NULL, NULL); + elm_hoversel_item_add(bt, "Item 2", NULL, ELM_ICON_NONE, NULL, NULL); + elm_hoversel_item_add(bt, "Item 3", NULL, ELM_ICON_NONE, NULL, NULL); + elm_hoversel_item_add(bt, "Item 4 - Long Label Here", NULL, ELM_ICON_NONE, NULL, NULL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_hoversel_add(win); + elm_hoversel_hover_parent_set(bt, win); + elm_hoversel_label_set(bt, "Some Icons"); + elm_hoversel_item_add(bt, "Item 1", NULL, ELM_ICON_NONE, NULL, NULL); + elm_hoversel_item_add(bt, "Item 2", NULL, ELM_ICON_NONE, NULL, NULL); + elm_hoversel_item_add(bt, "Item 3", "home", ELM_ICON_STANDARD, NULL, NULL); + elm_hoversel_item_add(bt, "Item 4", "close", ELM_ICON_STANDARD, NULL, NULL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_hoversel_add(win); + elm_hoversel_hover_parent_set(bt, win); + elm_hoversel_label_set(bt, "All Icons"); + elm_hoversel_item_add(bt, "Item 1", "apps", ELM_ICON_STANDARD, NULL, NULL); + elm_hoversel_item_add(bt, "Item 2", "arrow_down", ELM_ICON_STANDARD, NULL, NULL); + elm_hoversel_item_add(bt, "Item 3", "home", ELM_ICON_STANDARD, NULL, NULL); + elm_hoversel_item_add(bt, "Item 4", "close", ELM_ICON_STANDARD, NULL, NULL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_hoversel_add(win); + elm_hoversel_hover_parent_set(bt, win); + elm_hoversel_label_set(bt, "All Icons"); + elm_hoversel_item_add(bt, "Item 1", "apps", ELM_ICON_STANDARD, NULL, NULL); + snprintf(buf, sizeof(buf), "%s/images/sky_02.jpg", PACKAGE_DATA_DIR); + elm_hoversel_item_add(bt, "Item 2", buf, ELM_ICON_FILE, NULL, NULL); + elm_hoversel_item_add(bt, "Item 3", "home", ELM_ICON_STANDARD, NULL, NULL); + elm_hoversel_item_add(bt, "Item 4", "close", ELM_ICON_STANDARD, NULL, NULL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_hoversel_add(win); + elm_hoversel_hover_parent_set(bt, win); + elm_hoversel_label_set(bt, "Disabled Hoversel"); + elm_hoversel_item_add(bt, "Item 1", "apps", ELM_ICON_STANDARD, NULL, NULL); + elm_hoversel_item_add(bt, "Item 2", "close", ELM_ICON_STANDARD, NULL, NULL); + elm_object_disabled_set(bt, 1); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_hoversel_add(win); + elm_hoversel_hover_parent_set(bt, win); + elm_hoversel_label_set(bt, "Icon + Label"); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/sky_03.jpg", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_hoversel_icon_set(bt, ic); + evas_object_show(ic); + + elm_hoversel_item_add(bt, "Item 1", "apps", ELM_ICON_STANDARD, NULL, NULL); + elm_hoversel_item_add(bt, "Item 2", "arrow_down", ELM_ICON_STANDARD, NULL, NULL); + elm_hoversel_item_add(bt, "Item 3", "home", ELM_ICON_STANDARD, NULL, NULL); + elm_hoversel_item_add(bt, "Item 4", "close", ELM_ICON_STANDARD, NULL, NULL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + evas_object_size_hint_align_set(bt, 0.5, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + evas_object_resize(win, 320, 300); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_icon.c b/src/bin/test_icon.c new file mode 100644 index 0000000..966171b --- /dev/null +++ b/src/bin/test_icon.c @@ -0,0 +1,37 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +static void +icon_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("clicked!\n"); +} + +void +test_icon(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *ic; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "icon-transparent", ELM_WIN_BASIC); + elm_win_title_set(win, "Icon Transparent"); + elm_win_autodel_set(win, 1); + elm_win_alpha_set(win, 1); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + elm_icon_no_scale_set(ic, 1); + evas_object_size_hint_weight_set(ic, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(ic, 0.5, 0.5); + elm_win_resize_object_add(win, ic); + evas_object_show(ic); + + evas_object_smart_callback_add(ic, "clicked", icon_clicked, NULL); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_icon_desktops.c b/src/bin/test_icon_desktops.c new file mode 100644 index 0000000..afc300a --- /dev/null +++ b/src/bin/test_icon_desktops.c @@ -0,0 +1,128 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +static Elm_Genlist_Item_Class it_desk; + +static char * +desk_gl_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ +#ifdef ELM_EFREET + Efreet_Desktop *d = (Efreet_Desktop *)data; + return strdup(d->name); +#else + return NULL; + (void)data; +#endif +} +static Evas_Object * +desk_gl_icon_get(void *data, Evas_Object *obj, const char *part) +{ + // FIXME: elm_icon should grok this +#ifdef ELM_EFREET + Efreet_Desktop *d = (Efreet_Desktop *)data; + const char *path; + Evas_Object *ic; + ic = elm_icon_add(obj); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + if (!(!strcmp(part, "elm.swallow.icon"))) return ic; + if (!d->icon) return ic; + path = efreet_icon_path_find(getenv("E_ICON_THEME"), d->icon, 48); + if (!path) + { + path = efreet_icon_path_find("default", d->icon, 48); + if (!path) + { + path = efreet_icon_path_find("hicolor", d->icon, 48); + if (!path) + { + path = efreet_icon_path_find("gnome", d->icon, 48); + if (!path) + { + path = efreet_icon_path_find("Human", d->icon, 48); + } + } + } + } + if (path) + { + elm_icon_file_set(ic, path, NULL); + return ic; + } + return ic; +#else + return NULL; + (void)data; + (void)obj; + (void)part; +#endif +} +static void +desk_gl_del(void *data, Evas_Object *obj __UNUSED__) +{ +#ifdef ELM_EFREET + Efreet_Desktop *d = (Efreet_Desktop *)data; + efreet_desktop_free(d); +#else + return; + (void)data; +#endif +} + +#ifdef ELM_EFREET +static void +desktop_sel(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("sel\n"); +} +#endif + +void +test_icon_desktops(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl; +#ifdef ELM_EFREET + Eina_List *desktops; +#endif + + win = elm_win_add(NULL, "icon_desktops", ELM_WIN_BASIC); + elm_win_title_set(win, "Icon Desktops"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + it_desk.item_style = "default"; + it_desk.func.label_get = desk_gl_label_get; + it_desk.func.icon_get = desk_gl_icon_get; + it_desk.func.state_get = NULL; + it_desk.func.del = desk_gl_del; + + gl = elm_genlist_add(win); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, gl); + evas_object_show(gl); + +#ifdef ELM_EFREET + if (elm_need_efreet()) + { + desktops = efreet_util_desktop_name_glob_list("*"); + if (desktops) + { + Efreet_Desktop *d; + + EINA_LIST_FREE(desktops, d) + elm_genlist_item_append(gl, &it_desk, d, + NULL, ELM_GENLIST_ITEM_NONE, + desktop_sel, NULL); + } + } +#endif + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_index.c b/src/bin/test_index.c new file mode 100644 index 0000000..442496c --- /dev/null +++ b/src/bin/test_index.c @@ -0,0 +1,255 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +static Elm_Genlist_Item_Class itci; +char *gli_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part __UNUSED__) +{ + char buf[256]; + int j = (long)data; + snprintf(buf, sizeof(buf), "%c%c", + 'A' + ((j >> 4) & 0xf), + 'a' + ((j ) & 0xf) + ); + return strdup(buf); +} + +void +index_changed2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + // called on a change but delayed in case multiple changes happen in a + // short timespan + elm_genlist_item_top_bring_in(event_info); +} + +void +index_changed(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + // this is calld on every change, no matter how often + // elm_genlist_item_bring_in(event_info); +} + +void +index_selected(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + // called on final select + elm_genlist_item_top_bring_in(event_info); +} + +void +test_index(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *id; + Elm_Genlist_Item *it; + int i, j; + + win = elm_win_add(NULL, "index", ELM_WIN_BASIC); + elm_win_title_set(win, "Index"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + gl = elm_genlist_add(win); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, gl); + evas_object_show(gl); + + id = elm_index_add(win); + evas_object_size_hint_weight_set(id, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, id); + + evas_object_show(id); + + itci.item_style = "default"; + itci.func.label_get = gli_label_get; + itci.func.icon_get = NULL; + itci.func.state_get = NULL; + itci.func.del = NULL; + + j = 0; + for (i = 0; i < 100; i++) + { + it = elm_genlist_item_append(gl, &itci, + (void *)(long)j/* item data */, + NULL/* parent */, ELM_GENLIST_ITEM_NONE, + NULL/* func */, NULL/* func data */); + if (!(j & 0xf)) + { + char buf[32]; + + snprintf(buf, sizeof(buf), "%c", 'A' + ((j >> 4) & 0xf)); + elm_index_item_append(id, buf, it); + } + j += 2; + } + evas_object_smart_callback_add(id, "delay,changed", index_changed2, NULL); + evas_object_smart_callback_add(id, "changed", index_changed, NULL); + evas_object_smart_callback_add(id, "selected", index_selected, NULL); + elm_index_item_go(id, 0); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} + +/***********/ + +typedef struct _Test_Index2_Elements +{ + Evas_Object *entry, *lst, *id; +} Test_Index2_Elements; + +void +test_index2_del(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + /* FIXME it won't be called if elm_test main window is closed */ + free(data); +} + +int +test_index2_cmp(const void *data1, const void *data2) +{ + const char *label1, *label2; + const Elm_List_Item *it1 = data1; + const Elm_List_Item *it2 = data2; + + label1 = elm_list_item_label_get(it1); + label2 = elm_list_item_label_get(it2); + + return strcasecmp(label1, label2); +} + +int +test_index2_icmp(const void *data1, const void *data2) +{ + const char *label1, *label2; + const Elm_Index_Item *it1 = data1; + const Elm_Index_Item *it2 = data2; + + label1 = elm_index_item_letter_get(it1); + label2 = elm_index_item_letter_get(it2); + + return strcasecmp(label1, label2); +} + +void +test_index2_it_add(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Test_Index2_Elements *gui = data; + Elm_List_Item *it; + const char *label; + char letter[2]; + + label = elm_scrolled_entry_entry_get(gui->entry); + snprintf(letter, sizeof(letter), "%c", label[0]); + it = elm_list_item_sorted_insert(gui->lst, label, NULL, NULL, NULL, NULL, + test_index2_cmp); + elm_index_item_sorted_insert(gui->id, letter, it, test_index2_icmp, + test_index2_cmp); + elm_list_go(gui->lst); + /* FIXME it's not showing the recently added item */ + elm_list_item_show(it); +} + +void +test_index2_it_del(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Test_Index2_Elements *gui = data; + const char *label, *label_next; + Elm_List_Item *it, *it_next; + + it = elm_list_selected_item_get(obj); + it_next = elm_list_item_next(it); + + if (!it_next) + { + elm_index_item_del(gui->id, it); + elm_list_item_del(it); + return; + } + + label = elm_list_item_label_get(it); + label_next = elm_list_item_label_get(it_next); + + if (label[0] == label_next[0]) + { + Elm_Index_Item *iit; + iit = elm_index_item_find(gui->id, it); + elm_index_item_data_set(iit, it_next); + } + else + elm_index_item_del(gui->id, it); + + elm_list_item_del(it); +} + +void +test_index2_id_changed(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + elm_list_item_show(event_info); +} + +void +test_index2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *box, *bt; + Test_Index2_Elements *gui; + + gui = malloc(sizeof(*gui)); + + win = elm_win_add(NULL, "sorted-index-list", ELM_WIN_BASIC); + elm_win_title_set(win, "Sorted Index and List"); + evas_object_smart_callback_add(win, "delete-request", test_index2_del, gui); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + box = elm_box_add(win); + evas_object_size_hint_weight_set(box, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, box); + evas_object_show(box); + + gui->id = elm_index_add(win); + evas_object_size_hint_weight_set(gui->id, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, gui->id); + evas_object_smart_callback_add(gui->id, "delay,changed", + test_index2_id_changed, NULL); + evas_object_show(gui->id); + + gui->entry = elm_scrolled_entry_add(win); + elm_scrolled_entry_entry_set(gui->entry, "Label"); + elm_scrolled_entry_single_line_set(gui->entry, EINA_TRUE); + evas_object_size_hint_weight_set(gui->entry, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_fill_set(gui->entry, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(box, gui->entry); + evas_object_show(gui->entry); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Add"); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(box, bt); + evas_object_smart_callback_add(bt, "clicked", test_index2_it_add, gui); + evas_object_show(bt); + + gui->lst = elm_list_add(win); + elm_box_pack_end(box, gui->lst); + evas_object_size_hint_weight_set(gui->lst, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(gui->lst, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_smart_callback_add(gui->lst, "selected", test_index2_it_del, + gui); + elm_list_go(gui->lst); + evas_object_show(gui->lst); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_inwin.c b/src/bin/test_inwin.c new file mode 100644 index 0000000..8a95071 --- /dev/null +++ b/src/bin/test_inwin.c @@ -0,0 +1,71 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_inwin(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *inwin, *lb; + + win = elm_win_add(NULL, "inwin", ELM_WIN_BASIC); + elm_win_title_set(win, "Inwin"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + inwin = elm_win_inwin_add(win); + evas_object_show(inwin); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "This is an \"inwin\" - a window in a
    " + "window. This is handy for quick popups
    " + "you want centered, taking over the window
    " + "until dismissed somehow. Unlike hovers they
    " + "don't hover over their target."); + elm_win_inwin_content_set(inwin, lb); + evas_object_show(lb); + + evas_object_resize(win, 320, 240); + evas_object_show(win); +} + +void +test_inwin2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *inwin, *lb; + + win = elm_win_add(NULL, "inwin", ELM_WIN_BASIC); + elm_win_title_set(win, "Inwin"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + inwin = elm_win_inwin_add(win); + elm_object_style_set(inwin, "minimal_vertical"); + evas_object_show(inwin); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "This is an \"inwin\" - a window in a
    " + "window. This is handy for quick popups
    " + "you want centered, taking over the window
    " + "until dismissed somehow. Unlike hovers they
    " + "don't hover over their target.
    " + "
    " + "This inwin style compacts itself vertically
    " + "to the size of its contents minimum size."); + elm_win_inwin_content_set(inwin, lb); + evas_object_show(lb); + + evas_object_resize(win, 320, 240); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_label.c b/src/bin/test_label.c new file mode 100644 index 0000000..d26841e --- /dev/null +++ b/src/bin/test_label.c @@ -0,0 +1,78 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +void +test_label(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *lb; + + win = elm_win_add(NULL, "label", ELM_WIN_BASIC); + elm_win_title_set(win, "Label"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "This is a small label" + ); + evas_object_size_hint_weight_set(lb, 0.0, 0.0); + evas_object_size_hint_align_set(lb, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "This is a larger label with newlines
    " + "to make it bigger, bit it won't expand or wrap
    " + "just be a block of text that can't change its
    " + "formatting as it's fixed based on text
    " + ); + evas_object_size_hint_weight_set(lb, 0.0, 0.0); + evas_object_size_hint_align_set(lb, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + lb = elm_label_add(win); + elm_label_line_wrap_set(lb, 1); + elm_label_label_set(lb, + "" + "This is more text designed to line-wrap here as " + "This object is resized horizontally. As it is " + "resized vertically though, nothing should change. " + "The amount of space allocated vertically should " + "change as horizontal size changes." + "" + ); + evas_object_size_hint_weight_set(lb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(lb, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "This small label set to wrap" + ); + evas_object_size_hint_weight_set(lb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(lb, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + evas_object_resize(win, 320, 300); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_launcher.c b/src/bin/test_launcher.c new file mode 100644 index 0000000..f99626a --- /dev/null +++ b/src/bin/test_launcher.c @@ -0,0 +1,922 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void +mode_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Evas_Object *mb; + Eina_List *mbs, *l; + + mbs = evas_object_data_get(win, "mbs"); + EINA_LIST_FOREACH(mbs, l, mb) + { + if (elm_mapbuf_enabled_get(mb)) + elm_mapbuf_enabled_set(mb, 0); + else + elm_mapbuf_enabled_set(mb, 1); + } +} + +static void +full_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + elm_win_fullscreen_set(win, !elm_win_fullscreen_get(win)); +} + +static void +alpha_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Evas_Object *mb; + Eina_List *mbs, *l; + + mbs = evas_object_data_get(win, "mbs"); + EINA_LIST_FOREACH(mbs, l, mb) + { + elm_mapbuf_alpha_set(mb, elm_check_state_get(obj)); + } +} + +static void +smooth_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Evas_Object *mb; + Eina_List *mbs, *l; + + mbs = evas_object_data_get(win, "mbs"); + EINA_LIST_FOREACH(mbs, l, mb) + { + elm_mapbuf_smooth_set(mb, elm_check_state_get(obj)); + } +} + +static void +close_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_del(data); +} + +static Eina_Bool +tim_cb(void *data) +{ + Evas_Object *tb, *sc, *mb; + Eina_List *list, *l; + + evas_object_data_del(data, "timer"); + tb = evas_object_data_get(data, "tb"); + sc = evas_object_data_get(data, "sc"); + elm_object_scroll_freeze_push(sc); + evas_object_data_set(data, "dragging", (void *)(long)(1)); + evas_object_color_set(data, 255, 255, 255, 255); + list = (Eina_List *)evas_object_data_get + (elm_object_top_widget_get(data), "mbs"); + EINA_LIST_FOREACH(list, l, mb) + evas_object_color_set(mb, 128, 128, 128, 128); + elm_table_unpack(tb, data); + return EINA_FALSE; +} + +static void +ic_del_cb(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Ecore_Timer *tim; + + tim = evas_object_data_get(obj, "timer"); + if (tim) + { + evas_object_data_del(obj, "timer"); + ecore_timer_del(tim); + } +} + +static void +ic_down_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Down *ev = event_info; + Ecore_Timer *tim; + Evas_Coord x, y, w, h; + + evas_object_color_set(data, 128, 0, 0, 128); + + tim = evas_object_data_get(obj, "timer"); + if (tim) evas_object_data_del(obj, "timer"); + tim = ecore_timer_add(1.0, tim_cb, obj); + evas_object_data_set(obj, "timer", tim); + + evas_object_geometry_get(data, &x, &y, &w, &h); + evas_object_data_set(obj, "x", (void *)(long)(ev->canvas.x)); + evas_object_data_set(obj, "y", (void *)(long)(ev->canvas.y)); + evas_object_data_set(obj, "px", (void *)(long)(x)); + evas_object_data_set(obj, "py", (void *)(long)(y)); + + if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK) + { + printf("double click %p\n", obj); + } +} + +static void +ic_up_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Up *ev = event_info; + Ecore_Timer *tim; + + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return; + evas_object_color_set(data, 255, 255, 255, 255); + tim = evas_object_data_get(obj, "timer"); + if (tim) + { + evas_object_data_del(obj, "timer"); + ecore_timer_del(tim); + } + if (evas_object_data_get(obj, "dragging")) + { + Evas_Object *tb, *sc, *mb; + Eina_List *list, *l; + int tbx, tby; + + evas_object_data_del(obj, "dragging"); + tb = evas_object_data_get(obj, "tb"); + sc = evas_object_data_get(obj, "sc"); + elm_object_scroll_freeze_pop(sc); + tbx = (int)(long)evas_object_data_get(obj, "tbx"); + tby = (int)(long)evas_object_data_get(obj, "tby"); + elm_table_pack(tb, obj, tbx, tby, 1, 1); + list = (Eina_List *)evas_object_data_get + (elm_object_top_widget_get(obj), "mbs"); + EINA_LIST_FOREACH(list, l, mb) + evas_object_color_set(mb, 255, 255, 255, 255); + } +} + +static void +ic_move_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Move *ev = event_info; + if (evas_object_data_get(obj, "dragging")) + { + Evas_Coord x, y, px, py; + + x = (Evas_Coord)(long)evas_object_data_get(obj, "x"); + y = (Evas_Coord)(long)evas_object_data_get(obj, "y"); + px = (Evas_Coord)(long)evas_object_data_get(obj, "px"); + py = (Evas_Coord)(long)evas_object_data_get(obj, "py"); + evas_object_move(obj, + px + ev->cur.canvas.x - x, + py + ev->cur.canvas.y - y); + } + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + { + Ecore_Timer *tim; + + tim = evas_object_data_get(obj, "timer"); + if (tim) + { + evas_object_data_del(obj, "timer"); + ecore_timer_del(tim); + } + evas_object_color_set(data, 255, 255, 255, 255); + return; + } +} + +void +test_launcher(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *sc, *tb, *pad, *bt, *ic, *lb, *tb2, *mb, *ck, *bx, *bx2; + int i, j, k, n, m; + char buf[PATH_MAX]; + const char *names[] = + { + "Hello", "World", "Spam", "Egg", + "Ham", "Good", "Bad", "Milk", + "Smell", "Of", "Sky", "Gold", + "Hole", "Pig", "And", "Calm" + }; + Eina_List *mbs = NULL; + + win = elm_win_add(NULL, "launcher", ELM_WIN_BASIC); + elm_win_title_set(win, "Launcher"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/sky_04.jpg", PACKAGE_DATA_DIR); + elm_bg_file_set(bg, buf, NULL); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_box_homogenous_set(bx, 1); + elm_box_horizontal_set(bx, 1); + + sc = elm_scroller_add(win); + elm_scroller_bounce_set(sc, 1, 0); + elm_scroller_policy_set(sc, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(sc, EVAS_HINT_FILL, EVAS_HINT_FILL); + + n = 0; m = 0; + for (k = 0 ; k < 8; k++) + { + tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, 0.0, 0.0); + evas_object_size_hint_align_set(tb, 0.5, 0.5); + + pad = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(pad, 470, 4); + evas_object_size_hint_weight_set(pad, 0.0, 0.0); + evas_object_size_hint_align_set(pad, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, pad, 1, 0, 5, 1); + + pad = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(pad, 470, 4); + evas_object_size_hint_weight_set(pad, 0.0, 0.0); + evas_object_size_hint_align_set(pad, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, pad, 1, 11, 5, 1); + + pad = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(pad, 4, 4); + evas_object_size_hint_weight_set(pad, 0.0, 0.0); + evas_object_size_hint_align_set(pad, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, pad, 0, 1, 1, 10); + + pad = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(pad, 4, 4); + evas_object_size_hint_weight_set(pad, 0.0, 0.0); + evas_object_size_hint_align_set(pad, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, pad, 6, 1, 1, 10); + + mb = elm_mapbuf_add(win); + elm_mapbuf_content_set(mb, tb); + evas_object_show(tb); + + for (j = 0; j < 5; j++) + { + for (i = 0; i < 5; i++) + { + ic = elm_icon_add(win); + elm_object_scale_set(ic, 0.5); + snprintf(buf, sizeof(buf), "%s/images/icon_%02i.png", PACKAGE_DATA_DIR, n); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_weight_set(ic, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ic, 0.5, 0.5); + elm_table_pack(tb, ic, 1 + i, 1 + (j * 2), 1, 1); + evas_object_show(ic); + + lb = elm_label_add(win); + elm_object_style_set(lb, "marker"); + elm_label_label_set(lb, names[m]); + evas_object_size_hint_weight_set(lb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(lb, 0.5, 0.5); + elm_table_pack(tb, lb, 1 + i, 1 + (j * 2) + 1, 1, 1); + evas_object_show(lb); + + evas_object_event_callback_add(ic, EVAS_CALLBACK_DEL, ic_del_cb, ic); + + evas_object_event_callback_add(ic, EVAS_CALLBACK_MOUSE_DOWN, ic_down_cb, ic); + evas_object_event_callback_add(ic, EVAS_CALLBACK_MOUSE_UP, ic_up_cb, ic); + evas_object_event_callback_add(ic, EVAS_CALLBACK_MOUSE_MOVE, ic_move_cb, ic); + + evas_object_data_set(ic, "lb", lb); + evas_object_data_set(ic, "tb", tb); + evas_object_data_set(ic, "sc", sc); + evas_object_data_set(ic, "bx", bx); + evas_object_data_set(ic, "mb", mb); + evas_object_data_set(ic, "tbx", (void *)(long)(1 + i)); + evas_object_data_set(ic, "tby", (void *)(long)(1 + (j * 2))); + + n++; if (n > 23) n = 0; + m++; if (m > 15) m = 0; + } + } + + elm_box_pack_end(bx, mb); + evas_object_show(mb); + + mbs = eina_list_append(mbs, mb); + } + + // fixme: free mbs + evas_object_data_set(win, "mbs", mbs); + + bx2 = elm_box_add(win); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_horizontal_set(bx2, 0); + elm_win_resize_object_add(win, bx2); + evas_object_show(bx2); + + elm_scroller_content_set(sc, bx); + evas_object_show(bx); + + elm_scroller_page_relative_set(sc, 1.0, 1.0); + evas_object_show(sc); + + tb2 = elm_table_add(win); + evas_object_size_hint_weight_set(tb2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_fill_set(tb2, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx2, tb2); + + elm_box_pack_end(bx2, sc); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Map"); + elm_check_state_set(ck, 0); + evas_object_smart_callback_add(ck, "changed", mode_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.05, 0.99); + elm_table_pack(tb2, ck, 0, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "A"); + elm_check_state_set(ck, 1); + evas_object_smart_callback_add(ck, "changed", alpha_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.20, 0.99); + elm_table_pack(tb2, ck, 1, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Smo"); + elm_check_state_set(ck, 1); + evas_object_smart_callback_add(ck, "changed", smooth_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.40, 0.99); + elm_table_pack(tb2, ck, 2, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "FS"); + elm_check_state_set(ck, 0); + evas_object_smart_callback_add(ck, "changed", full_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.5, 0.99); + elm_table_pack(tb2, ck, 3, 0, 1, 1); + evas_object_show(ck); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", close_cb, win); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.95, 0.99); + elm_table_pack(tb2, bt, 4, 0, 1, 1); + evas_object_show(bt); + + evas_object_show(tb2); + + evas_object_resize(win, 480, 800); + evas_object_show(win); +} + +void +test_launcher2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *sc, *bt, *tb2, *mb, *ck, *bx, *ly; + int k; + char buf[PATH_MAX]; + Eina_List *mbs = NULL; + + win = elm_win_add(NULL, "launcher", ELM_WIN_BASIC); + elm_win_title_set(win, "Launcher"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/sky_03.jpg", PACKAGE_DATA_DIR); + elm_bg_file_set(bg, buf, NULL); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_box_homogenous_set(bx, 1); + elm_box_horizontal_set(bx, 1); + + for (k = 0 ; k < 8; k++) + { + ly = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/test.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly, buf, "layout"); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 1"); + elm_layout_content_set(ly, "element1", bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 2"); + elm_layout_content_set(ly, "element2", bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 3"); + elm_layout_content_set(ly, "element3", bt); + evas_object_show(bt); + + mb = elm_mapbuf_add(win); + elm_mapbuf_content_set(mb, ly); + evas_object_show(ly); + + elm_box_pack_end(bx, mb); + evas_object_show(mb); + + mbs = eina_list_append(mbs, mb); + } + + // fixme: free mbs + evas_object_data_set(win, "mbs", mbs); + + sc = elm_scroller_add(win); + elm_scroller_bounce_set(sc, 1, 0); + elm_scroller_policy_set(sc, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, sc); + + elm_scroller_content_set(sc, bx); + evas_object_show(bx); + + elm_scroller_page_relative_set(sc, 1.0, 1.0); + evas_object_show(sc); + + tb2 = elm_table_add(win); + evas_object_size_hint_weight_set(tb2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, tb2); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Map"); + elm_check_state_set(ck, 0); + evas_object_smart_callback_add(ck, "changed", mode_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.05, 0.99); + elm_table_pack(tb2, ck, 0, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "A"); + elm_check_state_set(ck, 1); + evas_object_smart_callback_add(ck, "changed", alpha_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.20, 0.99); + elm_table_pack(tb2, ck, 1, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Smo"); + elm_check_state_set(ck, 1); + evas_object_smart_callback_add(ck, "changed", smooth_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.40, 0.99); + elm_table_pack(tb2, ck, 2, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "FS"); + elm_check_state_set(ck, 0); + evas_object_smart_callback_add(ck, "changed", full_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.5, 0.99); + elm_table_pack(tb2, ck, 3, 0, 1, 1); + evas_object_show(ck); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", close_cb, win); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.95, 0.99); + elm_table_pack(tb2, bt, 4, 0, 1, 1); + evas_object_show(bt); + + evas_object_show(tb2); + + evas_object_resize(win, 480, 800); + evas_object_show(win); +} + +static void +l3_mode_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Evas_Object *mb; + Eina_List *mbs, *l; + + mbs = evas_object_data_get(win, "mbs"); + EINA_LIST_FOREACH(mbs, l, mb) + { + if (elm_mapbuf_enabled_get(mb)) + elm_mapbuf_enabled_set(mb, 0); + else + elm_mapbuf_enabled_set(mb, 1); + } +} + +static void +l3_full_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + elm_win_fullscreen_set(win, !elm_win_fullscreen_get(win)); +} + +static void +l3_alpha_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Evas_Object *mb; + Eina_List *mbs, *l; + + mbs = evas_object_data_get(win, "mbs"); + EINA_LIST_FOREACH(mbs, l, mb) + { + elm_mapbuf_alpha_set(mb, elm_check_state_get(obj)); + } +} + +static void +l3_smooth_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Evas_Object *mb; + Eina_List *mbs, *l; + + mbs = evas_object_data_get(win, "mbs"); + EINA_LIST_FOREACH(mbs, l, mb) + { + elm_mapbuf_smooth_set(mb, elm_check_state_get(obj)); + } +} + +static void +l3_hidden_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Evas_Object *mb; + Eina_List *mbs, *l; + + mbs = evas_object_data_get(win, "mbs"); + EINA_LIST_FOREACH(mbs, l, mb) + { + if (evas_object_visible_get(mb)) evas_object_hide(mb); + else evas_object_show(mb); + } +} + +static void +l3_close_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_del(data); +} + +static Eina_Bool +l3_tim_cb(void *data) +{ + Evas_Object *ly, *ly2, *sc, *mb; + Eina_List *list, *l; + char buf[256]; + int slx, sly; + + evas_object_data_del(data, "timer"); + ly = evas_object_data_get(data, "ly"); + ly2 = evas_object_data_get(data, "ly2"); + sc = evas_object_data_get(data, "sc"); + elm_object_scroll_freeze_push(sc); + evas_object_data_set(data, "dragging", (void *)(long)1); + evas_object_color_set(data, 255, 255, 255, 255); + list = (Eina_List *)evas_object_data_get + (elm_object_top_widget_get(data), "mbs"); + EINA_LIST_FOREACH(list, l, mb) + evas_object_color_set(mb, 128, 128, 128, 128); + slx = (int)(long)evas_object_data_get(data, "slx"); + sly = (int)(long)evas_object_data_get(data, "sly"); + snprintf(buf, sizeof(buf), "slot.%i.%i", slx, sly); + elm_layout_content_unset(ly, buf); + edje_object_signal_emit(elm_layout_edje_get(ly2), "drag", "app"); + return EINA_FALSE; +} + +static void +l3_ic_del_cb(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Ecore_Timer *tim; + + tim = evas_object_data_get(obj, "timer"); + if (tim) + { + evas_object_data_del(obj, "timer"); + ecore_timer_del(tim); + } +} + +static void +l3_ic_down_cb(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Down *ev = event_info; + Ecore_Timer *tim; + Evas_Coord x, y, w, h; + Evas_Object *ly2; + + tim = evas_object_data_get(obj, "timer"); + if (tim) evas_object_data_del(obj, "timer"); + tim = ecore_timer_add(1.0, l3_tim_cb, obj); + evas_object_data_set(obj, "timer", tim); + + ly2 = evas_object_data_get(obj, "ly2"); + evas_object_geometry_get(ly2, &x, &y, &w, &h); + evas_object_data_set(obj, "x", (void *)(long)(ev->canvas.x)); + evas_object_data_set(obj, "y", (void *)(long)(ev->canvas.y)); + evas_object_data_set(obj, "px", (void *)(long)(x)); + evas_object_data_set(obj, "py", (void *)(long)(y)); + + edje_object_signal_emit(elm_layout_edje_get(ly2), "click", "app"); + + if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK) + { + printf("double click %p\n", obj); + } +} + +static void +l3_ic_up_cb(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Up *ev = event_info; + Ecore_Timer *tim; + Evas_Object *ly2; + + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return; + + ly2 = evas_object_data_get(obj, "ly2"); + tim = evas_object_data_get(obj, "timer"); + if (tim) + { + evas_object_data_del(obj, "timer"); + ecore_timer_del(tim); + } + if (evas_object_data_get(obj, "dragging")) + { + Evas_Object *ly, *sc, *mb; + Eina_List *list, *l; + int slx, sly; + char buf[256]; + + evas_object_data_del(obj, "dragging"); + ly = evas_object_data_get(obj, "ly"); + sc = evas_object_data_get(obj, "sc"); + elm_object_scroll_freeze_pop(sc); + slx = (int)(long)evas_object_data_get(obj, "slx"); + sly = (int)(long)evas_object_data_get(obj, "sly"); + snprintf(buf, sizeof(buf), "slot.%i.%i", slx, sly); + elm_layout_content_set(ly, buf, ly2); + list = (Eina_List *)evas_object_data_get + (elm_object_top_widget_get(obj), "mbs"); + EINA_LIST_FOREACH(list, l, mb) + evas_object_color_set(mb, 255, 255, 255, 255); + edje_object_signal_emit(elm_layout_edje_get(ly2), "drop", "app"); + } + else + edje_object_signal_emit(elm_layout_edje_get(ly2), "unclick", "app"); +} + +static void +l3_ic_move_cb(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Move *ev = event_info; + Evas_Object *ly2; + + ly2 = evas_object_data_get(obj, "ly2"); + + if (evas_object_data_get(obj, "dragging")) + { + Evas_Coord x, y, px, py; + + x = (Evas_Coord)(long)evas_object_data_get(obj, "x"); + y = (Evas_Coord)(long)evas_object_data_get(obj, "y"); + px = (Evas_Coord)(long)evas_object_data_get(obj, "px"); + py = (Evas_Coord)(long)evas_object_data_get(obj, "py"); + evas_object_move(ly2, + px + ev->cur.canvas.x - x, + py + ev->cur.canvas.y - y); + } + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + { + Ecore_Timer *tim; + + tim = evas_object_data_get(obj, "timer"); + if (tim) + { + evas_object_data_del(obj, "timer"); + ecore_timer_del(tim); + } + edje_object_signal_emit(elm_layout_edje_get(ly2), "cancel", "app"); + return; + } +} + +void +test_launcher3(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *sc, *tb, *pad, *bt, *ic, *tb2, *mb, *ck, *bx, *bx2, *ly, *ly2; + int i, j, k, n, m; + char buf[PATH_MAX]; + const char *names[] = + { + "Hello", "World", "Spam", "Egg", + "Ham", "Good", "Bad", "Milk", + "Smell", "Of", "Sky", "Gold", + "Hole", "Pig", "And", "Calm" + }; + Eina_List *mbs = NULL; + + win = elm_win_add(NULL, "launcher", ELM_WIN_BASIC); + elm_win_title_set(win, "Launcher"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/sky_04.jpg", PACKAGE_DATA_DIR); + elm_bg_file_set(bg, buf, NULL); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_homogenous_set(bx, 1); + elm_box_horizontal_set(bx, 1); + + sc = elm_scroller_add(win); + elm_scroller_bounce_set(sc, 1, 0); + elm_scroller_policy_set(sc, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(sc, EVAS_HINT_FILL, EVAS_HINT_FILL); + + n = 0; m = 0; + for (k = 0 ; k < 8; k++) + { + tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + pad = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(pad, 450, 10); + elm_table_pack(tb, pad, 1, 0, 1, 1); + + pad = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(pad, 450, 10); + elm_table_pack(tb, pad, 1, 2, 1, 1); + + pad = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(pad, 10, 450); + elm_table_pack(tb, pad, 0, 1, 1, 1); + + pad = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(pad, 10, 450); + elm_table_pack(tb, pad, 2, 1, 1, 1); + + mb = elm_mapbuf_add(win); + mbs = eina_list_append(mbs, mb); + + elm_mapbuf_content_set(mb, tb); + evas_object_show(tb); + elm_box_pack_end(bx, mb); + evas_object_show(mb); + + ly = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/test.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly, buf, "launcher_page"); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ly, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, ly, 1, 1, 1, 1); + evas_object_show(ly); + + for (j = 0; j < 4; j++) + { + for (i = 0; i < 4; i++) + { + ly2 = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/test.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly2, buf, "launcher_icon"); + evas_object_size_hint_weight_set(ly2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ly2, EVAS_HINT_FILL, EVAS_HINT_FILL); + edje_object_part_text_set(elm_layout_edje_get(ly2), "label", names[m]); + + ic = elm_icon_add(win); + elm_object_scale_set(ic, 0.5); + snprintf(buf, sizeof(buf), "%s/images/icon_%02i.png", PACKAGE_DATA_DIR, n); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_weight_set(ic, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ic, 0.5, 0.5); + elm_layout_content_set(ly2, "slot", ic); + evas_object_show(ic); + + evas_object_event_callback_add(ic, EVAS_CALLBACK_DEL, l3_ic_del_cb, ic); + + evas_object_event_callback_add(ic, EVAS_CALLBACK_MOUSE_DOWN, l3_ic_down_cb, ic); + evas_object_event_callback_add(ic, EVAS_CALLBACK_MOUSE_UP, l3_ic_up_cb, ic); + evas_object_event_callback_add(ic, EVAS_CALLBACK_MOUSE_MOVE, l3_ic_move_cb, ic); + + evas_object_data_set(ic, "ly", ly); + evas_object_data_set(ic, "ly2", ly2); + evas_object_data_set(ic, "sc", sc); + evas_object_data_set(ic, "bx", bx); + evas_object_data_set(ic, "mb", mb); + evas_object_data_set(ic, "slx", (void *)(long)(i)); + evas_object_data_set(ic, "sly", (void *)(long)(j)); + + snprintf(buf, sizeof(buf), "slot.%i.%i", i, j); + elm_layout_content_set(ly, buf, ly2); + evas_object_show(ly2); + + n++; if (n > 23) n = 0; + m++; if (m > 15) m = 0; + } + } + } + + // fixme: free mbs + evas_object_data_set(win, "mbs", mbs); + + bx2 = elm_box_add(win); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_horizontal_set(bx2, 0); + elm_win_resize_object_add(win, bx2); + evas_object_show(bx2); + + elm_scroller_content_set(sc, bx); + evas_object_show(bx); + + elm_scroller_page_relative_set(sc, 1.0, 1.0); + evas_object_show(sc); + + tb2 = elm_table_add(win); + evas_object_size_hint_weight_set(tb2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_fill_set(tb2, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx2, tb2); + + elm_box_pack_end(bx2, sc); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Map"); + elm_check_state_set(ck, 0); + evas_object_smart_callback_add(ck, "changed", l3_mode_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.05, 0.99); + elm_table_pack(tb2, ck, 0, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "A"); + elm_check_state_set(ck, 1); + evas_object_smart_callback_add(ck, "changed", l3_alpha_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.20, 0.99); + elm_table_pack(tb2, ck, 1, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Smo"); + elm_check_state_set(ck, 1); + evas_object_smart_callback_add(ck, "changed", l3_smooth_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.40, 0.99); + elm_table_pack(tb2, ck, 2, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "FS"); + elm_check_state_set(ck, 0); + evas_object_smart_callback_add(ck, "changed", l3_full_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.5, 0.99); + elm_table_pack(tb2, ck, 3, 0, 1, 1); + evas_object_show(ck); + + ck = elm_check_add(win); + elm_check_label_set(ck, "Hid"); + elm_check_state_set(ck, 0); + evas_object_smart_callback_add(ck, "changed", l3_hidden_cb, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.5, 0.99); + elm_table_pack(tb2, ck, 4, 0, 1, 1); + evas_object_show(ck); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", l3_close_cb, win); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.95, 0.99); + elm_table_pack(tb2, bt, 5, 0, 1, 1); + evas_object_show(bt); + + evas_object_show(tb2); + + evas_object_resize(win, 480, 800); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_layout.c b/src/bin/test_layout.c new file mode 100644 index 0000000..21beec3 --- /dev/null +++ b/src/bin/test_layout.c @@ -0,0 +1,83 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +#include + +static void +_clicked_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + elm_layout_text_set(data, "text", elm_button_label_get(obj)); +} + +void +test_layout(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *box, *ly, *bt; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "layout", ELM_WIN_BASIC); + elm_win_title_set(win, "Layout"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + box = elm_box_add(win); + evas_object_size_hint_weight_set(box, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(box, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_win_resize_object_add(win, box); + evas_object_show(box); + + ly = elm_layout_add(win); + elm_layout_theme_set(ly, "layout", "application", "titlebar"); + elm_layout_label_set(ly, "Some title"); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ly, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(box, ly); + evas_object_show(ly); + + bt = elm_icon_add(win); + elm_icon_standard_set(bt, "chat"); + evas_object_size_hint_min_set(bt, 20, 20); + elm_layout_icon_set(ly, bt); + + bt = elm_icon_add(win); + elm_icon_standard_set(bt, "close"); + evas_object_size_hint_min_set(bt, 20, 20); + elm_layout_end_set(ly, bt); + + ly = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/test.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly, buf, "layout"); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(box, ly); + //elm_win_resize_object_add(win, ly); + evas_object_show(ly); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 1"); + elm_layout_content_set(ly, "element1", bt); + evas_object_smart_callback_add(bt, "clicked", _clicked_cb, ly); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 2"); + elm_layout_content_set(ly, "element2", bt); + evas_object_smart_callback_add(bt, "clicked", _clicked_cb, ly); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 3"); + elm_layout_content_set(ly, "element3", bt); + evas_object_smart_callback_add(bt, "clicked", _clicked_cb, ly); + evas_object_show(bt); + + elm_layout_part_cursor_set(ly, "text", ELM_CURSOR_WATCH); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_list.c b/src/bin/test_list.c new file mode 100644 index 0000000..e4137e2 --- /dev/null +++ b/src/bin/test_list.c @@ -0,0 +1,758 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +static void +my_show_it(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_list_item_show(data); +} + +static void +scroll_top(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Top edge!\n"); +} + +static void +scroll_bottom(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Bottom edge!\n"); +} + +static void +scroll_left(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Left edge!\n"); +} + +static void +scroll_right(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Right edge!\n"); +} + +void +test_list(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *li, *ic, *ic2, *bx, *tb2, *bt; + char buf[PATH_MAX]; + Elm_List_Item *it1, *it2, *it3, *it4, *it5; + + win = elm_win_add(NULL, "list", ELM_WIN_BASIC); + elm_win_title_set(win, "List"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + li = elm_list_add(win); + elm_win_resize_object_add(win, li); + elm_list_mode_set(li, ELM_LIST_LIMIT); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 1, 1); + it1 = elm_list_item_append(li, "Hello", ic, NULL, NULL, NULL); + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_scale_set(ic, 0, 0); + elm_icon_file_set(ic, buf, NULL); + elm_list_item_append(li, "world", ic, NULL, NULL, NULL); + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "edit"); + elm_icon_scale_set(ic, 0, 0); + elm_list_item_append(li, ".", ic, NULL, NULL, NULL); + + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "delete"); + elm_icon_scale_set(ic, 0, 0); + ic2 = elm_icon_add(win); + elm_icon_standard_set(ic2, "clock"); + elm_icon_scale_set(ic2, 0, 0); + it2 = elm_list_item_append(li, "How", ic, ic2, NULL, NULL); + + bx = elm_box_add(win); + elm_box_horizontal_set(bx, 1); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.5); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.0); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.0, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + elm_list_item_append(li, "are", bx, NULL, NULL, NULL); + + elm_list_item_append(li, "you", NULL, NULL, NULL, NULL); + it3 = elm_list_item_append(li, "doing", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "out", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "there", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "today", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "?", NULL, NULL, NULL, NULL); + it4 = elm_list_item_append(li, "Here", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "are", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "some", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "more", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "items", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Is this label long enough?", NULL, NULL, NULL, NULL); + it5 = elm_list_item_append(li, "Maybe this one is even longer so we can test long long items.", NULL, NULL, NULL, NULL); + + elm_list_go(li); + + evas_object_show(li); + + tb2 = elm_table_add(win); + evas_object_size_hint_weight_set(tb2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, tb2); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Hello"); + evas_object_smart_callback_add(bt, "clicked", my_show_it, it1); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.5); + elm_table_pack(tb2, bt, 0, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "How"); + evas_object_smart_callback_add(bt, "clicked", my_show_it, it2); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.5); + elm_table_pack(tb2, bt, 0, 1, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "doing"); + evas_object_smart_callback_add(bt, "clicked", my_show_it, it3); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.5); + elm_table_pack(tb2, bt, 0, 2, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Here"); + evas_object_smart_callback_add(bt, "clicked", my_show_it, it4); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.5); + elm_table_pack(tb2, bt, 0, 3, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Maybe this..."); + evas_object_smart_callback_add(bt, "clicked", my_show_it, it5); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.5); + elm_table_pack(tb2, bt, 0, 4, 1, 1); + evas_object_show(bt); + + evas_object_show(tb2); + + evas_object_resize(win, 320, 300); + evas_object_show(win); + + evas_object_smart_callback_add(li, "scroll,edge,top", scroll_top, NULL); + evas_object_smart_callback_add(li, "scroll,edge,bottom", scroll_bottom, NULL); + evas_object_smart_callback_add(li, "scroll,edge,left", scroll_left, NULL); + evas_object_smart_callback_add(li, "scroll,edge,right", scroll_right, NULL); +} + +void +test_list_horizontal(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *li, *ic, *ic2, *bx, *tb2, *bt; + char buf[PATH_MAX]; + Elm_List_Item *it1, *it2, *it3, *it4; + + win = elm_win_add(NULL, "list", ELM_WIN_BASIC); + elm_win_title_set(win, "List"); + elm_win_autodel_set(win, EINA_TRUE); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + li = elm_list_add(win); + elm_list_horizontal_set(li, EINA_TRUE); + elm_list_mode_set(li, ELM_LIST_LIMIT); + elm_win_resize_object_add(win, li); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 1, 1); + it1 = elm_list_item_append(li, "Hello", ic, NULL, NULL, NULL); + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_scale_set(ic, 0, 0); + elm_icon_file_set(ic, buf, NULL); + elm_list_item_append(li, "world", ic, NULL, NULL, NULL); + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "edit"); + elm_icon_scale_set(ic, 0, 0); + elm_list_item_append(li, ".", ic, NULL, NULL, NULL); + + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "delete"); + elm_icon_scale_set(ic, 0, 0); + ic2 = elm_icon_add(win); + elm_icon_standard_set(ic2, "clock"); + elm_icon_scale_set(ic2, 0, 0); + it2 = elm_list_item_append(li, "How", ic, ic2, NULL, NULL); + + bx = elm_box_add(win); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.5); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.0); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + elm_list_item_append(li, "are", bx, NULL, NULL, NULL); + + elm_list_item_append(li, "you", NULL, NULL, NULL, NULL); + it3 = elm_list_item_append(li, "doing", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "out", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "there", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "today", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "?", NULL, NULL, NULL, NULL); + + it4 = elm_list_item_append(li, "And", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "here", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "we", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "are", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "done", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "with", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "items.", NULL, NULL, NULL, NULL); + + elm_list_go(li); + + evas_object_show(li); + + tb2 = elm_table_add(win); + evas_object_size_hint_weight_set(tb2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, tb2); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Hello"); + evas_object_smart_callback_add(bt, "clicked", my_show_it, it1); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.5, 0.9); + elm_table_pack(tb2, bt, 0, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "How"); + evas_object_smart_callback_add(bt, "clicked", my_show_it, it2); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.5, 0.9); + elm_table_pack(tb2, bt, 1, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "doing"); + evas_object_smart_callback_add(bt, "clicked", my_show_it, it3); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.5, 0.9); + elm_table_pack(tb2, bt, 2, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "And"); + evas_object_smart_callback_add(bt, "clicked", my_show_it, it4); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.5, 0.9); + elm_table_pack(tb2, bt, 3, 0, 1, 1); + evas_object_show(bt); + + evas_object_show(tb2); + + evas_object_resize(win, 320, 300); + evas_object_show(win); +} + +/***********/ + +static void +my_li2_clear(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_list_clear(data); +} + +static void +my_li2_sel(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_List_Item *it = elm_list_selected_item_get(obj); + elm_list_item_selected_set(it, 0); +// elm_list_item_selected_set(event_info, 0); +} + +void +test_list2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *li, *ic, *ic2, *bx, *bx2, *bt; + char buf[PATH_MAX]; + Elm_List_Item *it; + + win = elm_win_add(NULL, "list-2", ELM_WIN_BASIC); + elm_win_title_set(win, "List 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + elm_bg_file_set(bg, buf, NULL); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + li = elm_list_add(win); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_list_mode_set(li, ELM_LIST_LIMIT); +// elm_list_multi_select_set(li, 1); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + it = elm_list_item_append(li, "Hello", ic, NULL, my_li2_sel, NULL); + elm_list_item_selected_set(it, 1); + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_scale_set(ic, 0, 0); + elm_icon_file_set(ic, buf, NULL); + elm_list_item_append(li, "world", ic, NULL, NULL, NULL); + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "edit"); + elm_icon_scale_set(ic, 0, 0); + elm_list_item_append(li, ".", ic, NULL, NULL, NULL); + + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "delete"); + elm_icon_scale_set(ic, 0, 0); + ic2 = elm_icon_add(win); + elm_icon_standard_set(ic2, "clock"); + elm_icon_scale_set(ic2, 0, 0); + elm_list_item_append(li, "How", ic, ic2, NULL, NULL); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.5); + elm_box_pack_end(bx2, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.0); + elm_box_pack_end(bx2, ic); + evas_object_show(ic); + elm_list_item_append(li, "are", bx2, NULL, NULL, NULL); + + elm_list_item_append(li, "you", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "doing", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "out", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "there", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "today", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "?", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Here", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "are", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "some", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "more", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "items", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Longer label.", NULL, NULL, NULL, NULL); + + elm_list_go(li); + + elm_box_pack_end(bx, li); + evas_object_show(li); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Clear"); + evas_object_smart_callback_add(bt, "clicked", my_li2_clear, li); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 300); + evas_object_show(win); +} + +/***********/ + +static void +_bt_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("button was clicked\n"); +} + +static void +_it_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("item was clicked\n"); +} + +void +test_list3(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *li, *ic, *ic2, *bx; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "list-3", ELM_WIN_BASIC); + elm_win_title_set(win, "List 3"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + li = elm_list_add(win); + elm_win_resize_object_add(win, li); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_list_mode_set(li, ELM_LIST_COMPRESS); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_scale_set(ic, 0, 0); + elm_icon_file_set(ic, buf, NULL); + ic2 = elm_button_add(win); + elm_button_label_set(ic2, "Click me"); + evas_object_smart_callback_add(ic2, "clicked", _bt_clicked, NULL); + evas_object_propagate_events_set(ic2, 0); + elm_list_item_append(li, "Hello", ic, ic2, _it_clicked, NULL); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_scale_set(ic, 0, 0); + elm_icon_file_set(ic, buf, NULL); + ic2 = elm_button_add(win); + elm_button_label_set(ic2, "Click me"); + evas_object_smart_callback_add(ic2, "clicked", _bt_clicked, NULL); + elm_list_item_append(li, "world", ic, ic2, _it_clicked, NULL); + + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "edit"); + elm_icon_scale_set(ic, 0, 0); + elm_list_item_append(li, ".", ic, NULL, NULL, NULL); + + ic = elm_icon_add(win); + elm_icon_standard_set(ic, "delete"); + elm_icon_scale_set(ic, 0, 0); + ic2 = elm_icon_add(win); + elm_icon_standard_set(ic2, "clock"); + elm_icon_scale_set(ic2, 0, 0); + elm_list_item_append(li, "How", ic, ic2, NULL, NULL); + + bx = elm_box_add(win); + elm_box_horizontal_set(bx, 1); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.5); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.5, 0.0); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_size_hint_align_set(ic, 0.0, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, ic); + evas_object_show(ic); + + elm_list_item_append(li, "are", bx, NULL, NULL, NULL); + elm_list_item_append(li, "you", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "doing", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "out", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "there", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "today", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "?", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Here", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "are", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "some", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "more", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "items", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Is this label long enough?", NULL, NULL, NULL, NULL); + elm_list_item_append(li, "Maybe this one is even longer so we can test long long items.", NULL, NULL, NULL, NULL); + + elm_list_go(li); + + evas_object_show(li); + + evas_object_resize(win, 320, 300); + evas_object_show(win); +} + +/////////////////////////////////////////////////////////////////////////////////////// + +struct Pginfo { + Evas_Object *pager, *win; +}; + +static void +test_list4_back_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + struct Pginfo *info = data; + if (!info) return; + + elm_pager_content_pop(info->pager); +} + +static void +test_list4_swipe(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Object *box, *entry, *button; + struct Pginfo *info = data; + char *item_data; + if ((!event_info) || (!data)) return; + + item_data = elm_list_item_data_get(event_info); + + box = elm_box_add(info->win); + elm_box_horizontal_set(box, 0); + elm_box_homogenous_set(box, 0); + evas_object_size_hint_weight_set(box, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(box, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(box); + + entry = elm_scrolled_entry_add(info->win); + elm_scrolled_entry_editable_set(entry, EINA_FALSE); + elm_scrolled_entry_entry_set(entry, item_data); + evas_object_size_hint_weight_set(entry, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(entry, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(entry); + + button = elm_button_add(info->win); + elm_button_label_set(button, "back"); + evas_object_size_hint_weight_set(button, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(button, EVAS_HINT_FILL, 0); + evas_object_smart_callback_add(button, "clicked", test_list4_back_cb, info); + evas_object_show(button); + + elm_box_pack_start(box, entry); + elm_box_pack_end(box, button); + + elm_pager_content_push(info->pager, box); +} + +void +test_list4(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *li, *ic, *ic2, *pager; + static struct Pginfo info = {NULL, NULL}; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "list-4", ELM_WIN_BASIC); + elm_win_title_set(win, "List 4"); + elm_win_autodel_set(win, 1); + info.win = win; + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + pager = elm_pager_add(win); + elm_win_resize_object_add(win, pager); + evas_object_size_hint_weight_set(pager, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(pager, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(pager); + info.pager = pager; + + li = elm_list_add(win); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_list_mode_set(li, ELM_LIST_COMPRESS); + evas_object_smart_callback_add(li, "swipe", test_list4_swipe, &info); + elm_pager_content_push(pager, li); + + static char pf_data[] = "Pink Floyd were formed in 1965, and originally consisted of university" \ + "students Roger Waters, Nick Mason, Richard Wright, and Syd Barrett. The group were a popular"\ + "fixture on London's underground music scene, and under Barrett's leadership released two "\ + "charting singles, \"Arnold Layne\" and \"See Emily Play\", and a successful debut album, "\ + "ThePiper at the Gates of Dawn. In 1968, guitarist and singer David Gilmour joined the "\ + "line-up. Barrett was soon removed, due to his increasingly erratic behaviour. Following "\ + "Barrett's departure, bass player and singer Roger Waters became the band's lyricist and "\ + "conceptual leader, with Gilmour assuming lead guitar and much of the vocals. With this "\ + "line-up, Floyd went on to achieve worldwide critical and commercial success with the "\ + "conceptalbums The Dark Side of the Moon, Wish You Were Here, Animals, and The Wall."; + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/mystrale.jpg", PACKAGE_DATA_DIR); + elm_icon_scale_set(ic, 0, 0); + elm_icon_file_set(ic, buf, NULL); + elm_list_item_append(li, "Pink Floyd", ic, NULL, NULL, &pf_data); + + static char ds_data[] = "Dire Straits were a British rock band, formed by Mark Knopfler "\ + "(lead vocals and lead guitar), his younger brother David Knopfler (rhythm guitar and "\ + "backing vocals), John Illsley (bass guitar and backing vocals), and Pick Withers (drums "\ + "and percussion), and managed by Ed Bicknell, active between 1977 and 1995. Although the "\ + "band was formed in an era when punk rock was at the forefront, Dire Straits played a more " + "bluesy style, albeit with a stripped-down sound that appealed to audiences weary of the "\ + "overproduced stadium rock of the 1970s.[citation needed] In their early days, Mark and "\ + "David requested that pub owners turn down their sound so that patrons could converse "\ + "while the band played, an indication of their unassuming demeanor. Despite this oddly "\ + "self-effacing approach to rock and roll, Dire Straits soon became hugely successful, with "\ + "their first album going multi-platinum globally."; + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/mystrale_2.jpg", PACKAGE_DATA_DIR); + elm_icon_scale_set(ic, 0, 0); + elm_icon_file_set(ic, buf, NULL); + elm_list_item_append(li, "Dire Straits", ic, NULL, NULL, &ds_data); + + static char uh_data[] = "Uriah Heep are an English hard rock band. The band released several "\ + "commercially successful albums in the 1970s such as Uriah Heep Live (1973), but their "\ + "audience declined by the 1980s, to the point where they became essentially a cult band in "\ + "the United States and United Kingdom. Uriah Heep maintain a significant following in "\ + "Germany, the Netherlands, Scandinavia, the Balkans, Japan and Russia, where they still "\ + "perform at stadium-sized venues."; + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/icon_17.png", PACKAGE_DATA_DIR); + elm_icon_scale_set(ic, 1, 1); + elm_icon_file_set(ic, buf, NULL); + elm_list_item_append(li, "Uriah Heep", ic, NULL, NULL, &uh_data); + + static char r_data[] = "Rush is a Canadian rock band formed in August 1968, in the Willowdale "\ + "neighbourhood of Toronto, Ontario. The band is composed of bassist, keyboardist, and lead "\ + "vocalist Geddy Lee, guitarist Alex Lifeson, and drummer and lyricist Neil Peart. The band "\ + "and its membership went through a number of re-configurations between 1968 and 1974, "\ + "achieving their current form when Peart replaced original drummer John Rutsey in July 1974, "\ + "two weeks before the group's first United States tour."; + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/icon_21.png", PACKAGE_DATA_DIR); + elm_icon_scale_set(ic, 0, 0); + elm_icon_file_set(ic, buf, NULL); + ic2 = elm_icon_add(win); + elm_icon_standard_set(ic2, "clock"); + elm_icon_scale_set(ic2, 0, 0); + elm_list_item_append(li, "Rush", ic, ic2, NULL, &r_data); + + elm_list_go(li); + + evas_object_show(li); + evas_object_resize(win, 320, 300); + evas_object_show(win); +} + +///////////////////////////////////////////////////////////////////////////////////////// +struct list5_data_cb { + Evas_Object *win, *list; +}; + +static void +test_list5_item_del(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_list_item_del(data); +} + +static void +test_list5_swipe(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Object *button; + struct list5_data_cb *info = elm_list_item_data_get(event_info); + + if (elm_list_item_end_get(event_info)) return; + + button = elm_button_add(info->win); + elm_button_label_set(button, "delete"); + evas_object_propagate_events_set(button, 0); + evas_object_smart_callback_add(button, "clicked", test_list5_item_del, + event_info); + elm_list_item_end_set(event_info, button); +} + +void +test_list5(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *li; + static struct list5_data_cb info; + + win = elm_win_add(NULL, "list-5", ELM_WIN_BASIC); + elm_win_title_set(win, "List 5"); + elm_win_autodel_set(win, 1); + info.win = win; + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + li = elm_list_add(win); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_list_mode_set(li, ELM_LIST_COMPRESS); + evas_object_smart_callback_add(li, "swipe", test_list5_swipe, NULL); + elm_win_resize_object_add(win, li); + evas_object_show(li); + info.list = li; + + elm_list_item_append(li, "Network", NULL, NULL, NULL, &info); + elm_list_item_append(li, "Audio", NULL, NULL, NULL, &info); + + elm_list_go(li); + evas_object_resize(win, 320, 300); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_map.c b/src/bin/test_map.c new file mode 100644 index 0000000..c3a3f24 --- /dev/null +++ b/src/bin/test_map.c @@ -0,0 +1,604 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +typedef struct Marker_Data +{ + const char *file; +} Marker_Data; + + +static Elm_Map_Marker_Class *itc1, *itc2, *itc_parking; +static Elm_Map_Group_Class *itc_group1, *itc_group2, *itc_group_parking; + +static Evas_Object *rect; +static int nb_elts; + +Marker_Data data1 = {PACKAGE_DATA_DIR"/images/logo.png"}; +Marker_Data data2 = {PACKAGE_DATA_DIR"/images/logo_small.png"}; +Marker_Data data3 = {PACKAGE_DATA_DIR"/images/panel_01.jpg"}; +Marker_Data data4 = {PACKAGE_DATA_DIR"/images/plant_01.jpg"}; +Marker_Data data5 = {PACKAGE_DATA_DIR"/images/rock_01.jpg"}; +Marker_Data data6 = {PACKAGE_DATA_DIR"/images/rock_02.jpg"}; +Marker_Data data7 = {PACKAGE_DATA_DIR"/images/sky_01.jpg"}; +Marker_Data data8 = {PACKAGE_DATA_DIR"/images/sky_02.jpg"}; +Marker_Data data9 = {PACKAGE_DATA_DIR"/images/sky_03.jpg"}; +Marker_Data data10 = {PACKAGE_DATA_DIR"/images/sky_03.jpg"}; +Marker_Data data11= {PACKAGE_DATA_DIR"/images/wood_01.jpg"}; + +Marker_Data data_parking= {PACKAGE_DATA_DIR"/images/parking.png"}; + +static void +my_map_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("clicked\n"); +} + +static void +my_map_press(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("press\n"); +} + +static void +my_map_longpressed(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("longpressed\n"); +} + +static void +my_map_clicked_double(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("clicked,double\n"); +} + +static void +my_map_load_detail(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("load,detail\n"); +} + +static void +my_map_loaded_detail(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("loaded,detail\n"); +} + +static void +my_map_zoom_start(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("zoom,start\n"); +} + +static void +my_map_zoom_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("zoom,stop\n"); +} + +static void +my_map_zoom_change(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("zoom,change\n"); +} + +static void +my_map_anim_start(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("anim,start\n"); +} + +static void +my_map_anim_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("anim,stop\n"); +} + +static void +my_map_drag_start(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag,start\n"); +} + +static void +my_map_drag_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag_stop\n"); +} + +static void +my_map_scroll(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + double lon, lat; + elm_map_geo_region_get(obj, &lon, &lat); + printf("scroll longitude : %f latitude : %f\n", lon, lat); +} + +static void +my_map_downloaded(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + int try_num, finish_num; + elm_map_utils_downloading_status_get(data, &try_num, &finish_num); + printf("downloaded : %d / %d\n", finish_num, try_num); +} + +static void +my_bt_show_reg(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Eina_Bool b = elm_map_paused_get(data); + elm_map_paused_set(data, EINA_TRUE); + elm_map_zoom_mode_set(data, ELM_MAP_ZOOM_MODE_MANUAL); + elm_map_geo_region_show(data, 2.352, 48.857); + elm_map_zoom_set(data, 18); + elm_map_paused_set(data, b); +} + +static void +my_bt_bring_reg(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_geo_region_bring_in(data, 2.352, 48.857); +} + +static void +my_bt_zoom_in(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + double zoom; + + zoom = elm_map_zoom_get(data); + zoom += 1; + elm_map_zoom_mode_set(data, ELM_MAP_ZOOM_MODE_MANUAL); + if (zoom >= (1.0 / 32.0)) elm_map_zoom_set(data, zoom); +} + +static void +my_bt_zoom_out(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + double zoom; + + zoom = elm_map_zoom_get(data); + zoom -= 1; + elm_map_zoom_mode_set(data, ELM_MAP_ZOOM_MODE_MANUAL); + if (zoom <= 256.0) elm_map_zoom_set(data, zoom); +} + +static void +my_bt_pause(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_paused_set(data, !elm_map_paused_get(data)); +} + +static void +my_bt_markers_pause(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_paused_markers_set(data, !elm_map_paused_markers_get(data)); +} + +static void +my_bt_zoom_fit(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_zoom_mode_set(data, ELM_MAP_ZOOM_MODE_AUTO_FIT); +} + +static void +my_bt_zoom_fill(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_zoom_mode_set(data, ELM_MAP_ZOOM_MODE_AUTO_FILL); +} + +static void +my_bt_source_mapnik(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_source_set(data, ELM_MAP_SOURCE_MAPNIK); +} + +static void +my_bt_source_osmarender(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_source_set(data, ELM_MAP_SOURCE_OSMARENDER); +} + +static void +my_bt_source_cyclemap(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_source_set(data, ELM_MAP_SOURCE_CYCLEMAP); +} + +static void +my_bt_source_maplint(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_source_set(data, ELM_MAP_SOURCE_MAPLINT); +} + +static void +my_bt_source_module(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_map_source_set(data, ELM_MAP_SOURCE_MODULE); +} + +static void +my_bt_add(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + int i; + Elm_Map_Group_Class *g_clas; + Elm_Map_Marker_Class *m_clas; + Marker_Data *d = &data7; + + for(i =0; i<1000; i++) + { + d = &data7; + + int r1 = rand() % (180*2*100); + if(r1<=180) r1 = -r1; + else r1 = r1 - 180*100; + + int r2 = rand() % (85*2*100); + if(r2<=85) r2 = -r2; + else r2 = r2 - 85*100; + + int style = rand() % 3; + if(!style) + m_clas = itc1; + else if(style == 1) + m_clas = itc2; + else + { + m_clas = itc_parking; + d = &data_parking; + } + + style = rand() % 2; + if (!style) + g_clas = itc_group1; + else + g_clas = itc_group2; + + elm_map_marker_add(data, r1/100., r2/100., m_clas, g_clas, d); + } + nb_elts+=1000; + printf("nb elements: %d\n", nb_elts); +} + +static Evas_Object * +_marker_get(Evas_Object *obj, Elm_Map_Marker *marker __UNUSED__, void *data) +{ + Marker_Data *d = data; + + Evas_Object *bx = elm_box_add(obj); + evas_object_show(bx); + + if(d == &data3) + { + Evas_Object *icon = elm_icon_add(obj); + elm_icon_file_set(icon, d->file, NULL); + evas_object_show(icon); + + Evas_Object *o = elm_button_add(obj); + elm_button_icon_set(o, icon); + evas_object_show(o); + elm_box_pack_end(bx, o); + } + else + { + Evas_Object *o = evas_object_image_add(evas_object_evas_get(obj)); + evas_object_image_file_set(o, d->file, NULL); + evas_object_image_filled_set(o, EINA_TRUE); + evas_object_size_hint_min_set(o, 64, 64); + evas_object_show(o); + elm_box_pack_end(bx, o); + + Evas_Object *lbl = elm_label_add(obj); + elm_label_label_set(lbl, "Wolves Go !"); + evas_object_show(lbl); + elm_box_pack_end(bx, lbl); + } + + return bx; +} + +static Evas_Object * +_icon_get(Evas_Object *obj, Elm_Map_Marker *marker __UNUSED__, void *data) +{ + Marker_Data *d = data; + + Evas_Object *icon = elm_icon_add(obj); + elm_icon_file_set(icon, d->file, NULL); + evas_object_show(icon); + + return icon; +} + +static Evas_Object * +_group_icon_get(Evas_Object *obj, void *data) +{ + char *file = data; + + Evas_Object *icon = elm_icon_add(obj); + elm_icon_file_set(icon, file, NULL); + evas_object_show(icon); + + return icon; +} + +static void +_map_mouse_wheel_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Object *map = data; + Evas_Event_Mouse_Wheel *ev = (Evas_Event_Mouse_Wheel*) event_info; + int zoom; + //unset the mouse wheel + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + + zoom = elm_map_zoom_get(map); + + if (ev->z > 0) + zoom--; + else + zoom++; + + elm_map_zoom_mode_set(map, ELM_MAP_ZOOM_MODE_MANUAL); + if ((zoom >= 0) && (zoom <= 18)) elm_map_zoom_set(map, zoom); +} + +static void +_map_move_resize_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + int x,y,w,h; + + evas_object_geometry_get(data,&x,&y,&w,&h); + evas_object_resize(rect,w,h); + evas_object_move(rect,x,y); +} + +void +test_map(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *map, *tb2, *bt, *bx; + + win = elm_win_add(NULL, "map", ELM_WIN_BASIC); + elm_win_title_set(win, "Map"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + map = elm_map_add(win); + if (map) + { + srand( time(NULL) ); + + evas_object_size_hint_weight_set(map, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, map); + evas_object_data_set(map, "window", win); + + // + itc1 = elm_map_marker_class_new(map); + elm_map_marker_class_get_cb_set(itc1, _marker_get); + elm_map_marker_class_del_cb_set(itc1, NULL); + + itc2 = elm_map_marker_class_new(map); + elm_map_marker_class_get_cb_set(itc2, _marker_get); + elm_map_marker_class_del_cb_set(itc2, NULL); + elm_map_marker_class_style_set(itc2, "radio2"); + + itc_parking = elm_map_marker_class_new(map); + elm_map_marker_class_get_cb_set(itc_parking, _marker_get); + elm_map_marker_class_del_cb_set(itc_parking, NULL); + elm_map_marker_class_icon_cb_set(itc_parking, _icon_get); + elm_map_marker_class_style_set(itc_parking, "empty"); + // + + // + itc_group1 = elm_map_group_class_new(map); + elm_map_group_class_data_set(itc_group1, (void *)PACKAGE_DATA_DIR"/images/plant_01.jpg"); + + itc_group2 = elm_map_group_class_new(map); + elm_map_group_class_style_set(itc_group2, "radio2"); + elm_map_group_class_zoom_displayed_set(itc_group1, 3); + + itc_group_parking = elm_map_group_class_new(map); + elm_map_group_class_icon_cb_set(itc_group_parking, _group_icon_get); + elm_map_group_class_data_set(itc_group_parking, (void *)PACKAGE_DATA_DIR"/images/parking.png"); + elm_map_group_class_style_set(itc_group_parking, "empty"); + elm_map_group_class_zoom_displayed_set(itc_group_parking, 5); + // + + + rect = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_color_set(rect, 0, 0, 0, 0); + evas_object_repeat_events_set(rect,1); + evas_object_show(rect); + evas_object_event_callback_add(rect, EVAS_CALLBACK_MOUSE_WHEEL, + _map_mouse_wheel_cb, map); + evas_object_raise(rect); + + evas_object_event_callback_add(map, EVAS_CALLBACK_RESIZE, + _map_move_resize_cb, map); + evas_object_event_callback_add(map, EVAS_CALLBACK_MOVE, + _map_move_resize_cb, map); + + elm_map_marker_add(map, 2.352, 48.857, itc1, itc_group1, &data1); + elm_map_marker_add(map, 2.355, 48.857, itc1, itc_group1, &data3); + elm_map_marker_add(map, 3, 48.857, itc2, itc_group1, &data2); + elm_map_marker_add(map, 2.352, 49, itc2, itc_group1, &data1); + + elm_map_marker_add(map, 7.31451, 48.857127, itc1, itc_group1, &data10); + elm_map_marker_add(map, 7.314704, 48.857119, itc1, itc_group1, &data4); + elm_map_marker_add(map, 7.314704, 48.857119, itc2, itc_group1, &data5); + elm_map_marker_add(map, 7.31432, 48.856785, itc2, itc_group1, &data6); + elm_map_marker_add(map, 7.3148, 48.85725, itc1, itc_group2, &data7); + elm_map_marker_add(map, 7.316445, 48.8572210000694, itc1, itc_group1, &data8); + elm_map_marker_add(map, 7.316527000125, 48.85609, itc2, itc_group2, &data9); + elm_map_marker_add(map, 7.3165409990833, 48.856078, itc2, itc_group1, &data11); + elm_map_marker_add(map, 7.319812, 48.856561, itc2, itc_group2, &data10); + + nb_elts = 13; + + evas_object_smart_callback_add(map, "clicked", my_map_clicked, win); + evas_object_smart_callback_add(map, "press", my_map_press, win); + evas_object_smart_callback_add(map, "longpressed", my_map_longpressed, win); + evas_object_smart_callback_add(map, "clicked,double", my_map_clicked_double, win); + evas_object_smart_callback_add(map, "load,detail", my_map_load_detail, win); + evas_object_smart_callback_add(map, "loaded,detail", my_map_loaded_detail, win); + evas_object_smart_callback_add(map, "zoom,start", my_map_zoom_start, win); + evas_object_smart_callback_add(map, "zoom,stop", my_map_zoom_stop, win); + evas_object_smart_callback_add(map, "zoom,change", my_map_zoom_change, win); + evas_object_smart_callback_add(map, "scroll,anim,start", my_map_anim_start, win); + evas_object_smart_callback_add(map, "scroll,anim,stop", my_map_anim_stop, win); + evas_object_smart_callback_add(map, "scroll,drag,start", my_map_drag_start, win); + evas_object_smart_callback_add(map, "scroll,drag,stop", my_map_drag_stop, win); + evas_object_smart_callback_add(map, "scroll", my_map_scroll, win); + evas_object_smart_callback_add(map, "downloaded", my_map_downloaded, map); + + evas_object_show(map); + + tb2 = elm_table_add(win); + evas_object_size_hint_weight_set(tb2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, tb2); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Z -"); + evas_object_smart_callback_add(bt, "clicked", my_bt_zoom_out, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.1, 0.1); + elm_table_pack(tb2, bt, 0, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Add 1000 markers"); + evas_object_smart_callback_add(bt, "clicked", my_bt_add, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.5, 0.1); + elm_table_pack(tb2, bt, 1, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Z +"); + evas_object_smart_callback_add(bt, "clicked", my_bt_zoom_in, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.1); + elm_table_pack(tb2, bt, 2, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Show Paris"); + evas_object_smart_callback_add(bt, "clicked", my_bt_show_reg, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.1, 0.5); + elm_table_pack(tb2, bt, 0, 1, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Bring Paris"); + evas_object_smart_callback_add(bt, "clicked", my_bt_bring_reg, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.5); + elm_table_pack(tb2, bt, 2, 1, 1, 1); + evas_object_show(bt); + + // + bx = elm_box_add(win); + evas_object_show(bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, 0.1, 0.9); + elm_table_pack(tb2, bx, 0, 2, 1, 1); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Pause On/Off"); + evas_object_smart_callback_add(bt, "clicked", my_bt_pause, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.1, 0.9); + evas_object_show(bt); + elm_box_pack_end(bx, bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Markers pause On/Off"); + evas_object_smart_callback_add(bt, "clicked", my_bt_markers_pause, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.1, 0.9); + evas_object_show(bt); + elm_box_pack_end(bx, bt); + // + + // + bx = elm_box_add(win); + evas_object_show(bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, 0.5, 0.9); + elm_table_pack(tb2, bx, 1, 2, 1, 1); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Fit"); + evas_object_smart_callback_add(bt, "clicked", my_bt_zoom_fit, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.5, 0.9); + evas_object_show(bt); + elm_box_pack_end(bx, bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Fill"); + evas_object_smart_callback_add(bt, "clicked", my_bt_zoom_fill, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.5, 0.9); + evas_object_show(bt); + elm_box_pack_end(bx, bt); + // + + // + bx = elm_box_add(win); + evas_object_show(bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, 1.0, 0.9); + elm_table_pack(tb2, bx, 2, 2, 1, 1); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Mapnik"); + evas_object_smart_callback_add(bt, "clicked", my_bt_source_mapnik, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 1.0, 0.9); + evas_object_show(bt); + elm_box_pack_end(bx, bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Osmarender"); + evas_object_smart_callback_add(bt, "clicked", my_bt_source_osmarender, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 1.0, 0.9); + evas_object_show(bt); + elm_box_pack_end(bx, bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Cycle Map"); + evas_object_smart_callback_add(bt, "clicked", my_bt_source_cyclemap, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 1.0, 0.9); + evas_object_show(bt); + elm_box_pack_end(bx, bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Maplint"); + evas_object_smart_callback_add(bt, "clicked", my_bt_source_maplint, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 1.0, 0.9); + evas_object_show(bt); + elm_box_pack_end(bx, bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Module"); + evas_object_smart_callback_add(bt, "clicked", my_bt_source_module, map); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 1.0, 0.9); + evas_object_show(bt); + elm_box_pack_end(bx, bt); + // + + evas_object_show(tb2); + } + + evas_object_resize(win, 800, 800); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_menu.c b/src/bin/test_menu.c new file mode 100644 index 0000000..544ad09 --- /dev/null +++ b/src/bin/test_menu.c @@ -0,0 +1,115 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static Evas_Object *win, *bg, *menu, *rect; + +static void +_show(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Down *ev = event_info; + elm_menu_move(data, ev->canvas.x, ev->canvas.y); + evas_object_show(data); +} + +static void +_populate_4(Elm_Menu_Item *item) +{ + Elm_Menu_Item *item2; + + elm_menu_item_add(menu, item, "go-bottom", "menu 2", NULL, NULL); + elm_menu_item_add(menu, item, "go-first", "menu 3", NULL, NULL); + elm_menu_item_separator_add(menu, item); + item2 = elm_menu_item_add(menu, item, "go-last", "Disabled item", NULL, NULL); + elm_menu_item_disabled_set(item2, 1); + item2 = elm_menu_item_add(menu, item, "go-next", "Disabled item", NULL, NULL); + elm_menu_item_disabled_set(item2, 1); + item2 = elm_menu_item_add(menu, item, "go-up", "Disabled item", NULL, NULL); + elm_menu_item_disabled_set(item2, 1); +} + +static void +_populate_3(Elm_Menu_Item *item) +{ + Elm_Menu_Item *item2; + + elm_menu_item_add(menu, item, "media-eject", "menu 2", NULL, NULL); + elm_menu_item_add(menu, item, "media-playback-start", "menu 3", NULL, NULL); + elm_menu_item_separator_add(menu,item); + item2 = elm_menu_item_add(menu, item, "media-playback-stop", "Disabled item", NULL, NULL); + elm_menu_item_disabled_set(item2, 1); +} + +static void +_populate_2(Elm_Menu_Item *item) +{ + Elm_Menu_Item *item2, *item3; + + elm_menu_item_add(menu, item, "system-reboot", "menu 2", NULL, NULL); + item2 = elm_menu_item_add(menu, item, "system-shutdown", "menu 3", NULL, NULL); + + _populate_3(item2); + + elm_menu_item_separator_add(menu,item); + elm_menu_item_separator_add(menu,item); + elm_menu_item_separator_add(menu,item); + elm_menu_item_separator_add(menu,item); + elm_menu_item_separator_add(menu,item); + elm_menu_item_separator_add(menu,item); + elm_menu_item_separator_add(menu,item); + + item2 = elm_menu_item_add(menu, item, "system-lock-screen", "menu 2", NULL, NULL); + elm_menu_item_separator_add(menu,item); + + item3 = elm_menu_item_add(menu, item, "system-run", "Disabled item", NULL, NULL); + elm_menu_item_disabled_set(item3, 1); + + _populate_4(item2); +} + +static void +_populate_1(Elm_Menu_Item *item) +{ + Elm_Menu_Item *item2; + + item2 = elm_menu_item_add(menu, item, "object-rotate-left", "menu 1", NULL, NULL); + + _populate_2(item2); +} + +void +test_menu(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Menu_Item *item; + + win = elm_win_add(NULL, "Menu", ELM_WIN_BASIC); + elm_win_title_set(win, "Menu"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + rect = evas_object_rectangle_add(evas_object_evas_get(win)); + elm_win_resize_object_add(win, rect); + evas_object_color_set(rect, 0, 0, 0, 0); + evas_object_show(rect); + + menu = elm_menu_add(win); + elm_menu_item_add(menu, NULL, NULL, "first item", NULL, NULL); + + item = elm_menu_item_add(menu, NULL, "mail-reply-all", "second item", NULL, NULL); + _populate_1(item); + + elm_menu_item_add(menu, item, "window-new", "sub menu", NULL, NULL); + + evas_object_event_callback_add(rect, EVAS_CALLBACK_MOUSE_DOWN, _show, menu); + + evas_object_resize(win, 350, 200); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_multi.c b/src/bin/test_multi.c new file mode 100644 index 0000000..45fe59d --- /dev/null +++ b/src/bin/test_multi.c @@ -0,0 +1,135 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +#define IND_NUM 20 + +static Evas_Object *indicator[IND_NUM]; + +static void +_mouse_down(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Down *ev = event_info; + + if (ev->button != 1) return; + printf("MOUSE: down @ %4i %4i\n", ev->canvas.x, ev->canvas.y); + evas_object_move(indicator[0], ev->canvas.x, ev->canvas.y); + evas_object_resize(indicator[0], 1, 1); + evas_object_show(indicator[0]); +} + +static void +_mouse_up(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Up *ev = event_info; + if (ev->button != 1) return; + printf("MOUSE: up @ %4i %4i\n", ev->canvas.x, ev->canvas.y); + evas_object_hide(indicator[0]); +} + +static void +_mouse_move(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Move *ev = event_info; + printf("MOUSE: move @ %4i %4i\n", ev->cur.canvas.x, ev->cur.canvas.y); + evas_object_move(indicator[0], ev->cur.canvas.x, ev->cur.canvas.y); + evas_object_resize(indicator[0], 1, 1); +} + +static void +_multi_down(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info) +{ + Evas_Event_Multi_Down *ev = event_info; + printf("MULTI: down @ %4i %4i | dev: %i\n", ev->canvas.x, ev->canvas.y, ev->device); + if (ev->device >= IND_NUM) return; + evas_object_move(indicator[ev->device], ev->canvas.x, ev->canvas.y); + evas_object_resize(indicator[ev->device], 1, 1); + evas_object_show(indicator[ev->device]); +} + +static void +_multi_up(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info) +{ + Evas_Event_Multi_Up *ev = event_info; + printf("MULTI: up @ %4i %4i | dev: %i\n", ev->canvas.x, ev->canvas.y, ev->device); + if (ev->device >= IND_NUM) return; + evas_object_hide(indicator[ev->device]); +} + +static void +_multi_move(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info) +{ + Evas_Event_Multi_Move *ev = event_info; + printf("MULTI: move @ %4i %4i | dev: %i\n", ev->cur.canvas.x, + ev->cur.canvas.y, ev->device); + if (ev->device >= IND_NUM) return; + evas_object_move(indicator[ev->device], ev->cur.canvas.x, ev->cur.canvas.y); + evas_object_resize(indicator[ev->device], 1, 1); +} + +void +my_bt_rot(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + elm_win_rotation_set(win, elm_win_rotation_get(win) + 90); +} + +void +test_multi(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *r, *bx, *bt; + int i; + + win = elm_win_add(NULL, "bg-plain", ELM_WIN_BASIC); + elm_win_title_set(win, "Bg Plain"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + r = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_weight_set(r, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_color_set(r, 0, 0, 0, 0); + elm_win_resize_object_add(win, r); + evas_object_show(r); + + for (i = 0; i < IND_NUM; i++) + { + char buf[PATH_MAX]; + + snprintf(buf, sizeof(buf), "%s/objects/multip.edj", PACKAGE_DATA_DIR); + indicator[i] = edje_object_add(evas_object_evas_get(win)); + edje_object_file_set(indicator[i], buf, "point"); + } + + evas_object_event_callback_add(r, EVAS_CALLBACK_MOUSE_DOWN, _mouse_down, win); + evas_object_event_callback_add(r, EVAS_CALLBACK_MOUSE_UP, _mouse_up, win); + evas_object_event_callback_add(r, EVAS_CALLBACK_MOUSE_MOVE, _mouse_move, win); + evas_object_event_callback_add(r, EVAS_CALLBACK_MULTI_DOWN, _multi_down, win); + evas_object_event_callback_add(r, EVAS_CALLBACK_MULTI_UP, _multi_up, win); + evas_object_event_callback_add(r, EVAS_CALLBACK_MULTI_MOVE, _multi_move, win); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rotate"); + evas_object_smart_callback_add(bt, "clicked", my_bt_rot, win); + evas_object_size_hint_align_set(bt, 0.0, 0.0); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + evas_object_size_hint_min_set(bg, 160, 160); + evas_object_resize(win, 480, 800); + + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_notify.c b/src/bin/test_notify.c new file mode 100644 index 0000000..bd107ad --- /dev/null +++ b/src/bin/test_notify.c @@ -0,0 +1,307 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void +_bt(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *notify = data; + evas_object_show(notify); +} + +static void +_bt_close(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *notify = data; + evas_object_hide(notify); +} + +static void +_bt_timer_close(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *notify = data; + elm_notify_timeout_set(notify, 2.0); +} + +static void +_notify_timeout(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Notify timed out!\n"); +} + +static void +_notify_block(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("Notify block area clicked!!\n"); +} + +void +test_notify(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *tb, *notify, *bt, *lb; + + win = elm_win_add(NULL, "Notify", ELM_WIN_BASIC); + elm_win_title_set(win, "Notify"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + tb = elm_table_add(win); + elm_win_resize_object_add(win, tb); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(tb); + + notify = elm_notify_add(win); + evas_object_size_hint_weight_set(notify, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + bx = elm_box_add(win); + elm_notify_content_set(notify, bx); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, "This position is the default."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", _bt_close, notify); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Top"); + evas_object_smart_callback_add(bt, "clicked", _bt, notify); + elm_table_pack(tb, bt, 1, 0, 1, 1); + evas_object_show(bt); + + notify = elm_notify_add(win); + elm_notify_repeat_events_set(notify, EINA_FALSE); + evas_object_size_hint_weight_set(notify, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_notify_orient_set(notify, ELM_NOTIFY_ORIENT_BOTTOM); + elm_notify_timeout_set(notify, 5.0); + evas_object_smart_callback_add(notify, "timeout", _notify_timeout, NULL); + evas_object_smart_callback_add(notify, "block,clicked", _notify_block, NULL); + + bx = elm_box_add(win); + elm_notify_content_set(notify, bx); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Bottom position. This notify use a timeout of 5 sec.
    " + "The events outside the window are blocked."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", _bt_close, notify); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Bottom"); + evas_object_smart_callback_add(bt, "clicked", _bt, notify); + elm_table_pack(tb, bt, 1, 2, 1, 1); + evas_object_show(bt); + + notify = elm_notify_add(win); + evas_object_size_hint_weight_set(notify, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_notify_orient_set(notify, ELM_NOTIFY_ORIENT_LEFT); + elm_notify_timeout_set(notify, 10.0); + evas_object_smart_callback_add(notify, "timeout", _notify_timeout, NULL); + + bx = elm_box_add(win); + elm_notify_content_set(notify, bx); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Left position. This notify use a timeout of 10 sec."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", _bt_close, notify); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Left"); + evas_object_smart_callback_add(bt, "clicked", _bt, notify); + elm_table_pack(tb, bt, 0, 1, 1, 1); + evas_object_show(bt); + + notify = elm_notify_add(win); + evas_object_size_hint_weight_set(notify, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_notify_orient_set(notify, ELM_NOTIFY_ORIENT_CENTER); + elm_notify_timeout_set(notify, 10); + elm_notify_timeout_set(notify, 10.0); + evas_object_smart_callback_add(notify, "timeout", _notify_timeout, NULL); + + bx = elm_box_add(win); + elm_notify_content_set(notify, bx); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Center position. This notify use a timeout of 10 sec."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", _bt_close, notify); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Center"); + evas_object_smart_callback_add(bt, "clicked", _bt, notify); + elm_table_pack(tb, bt, 1, 1, 1, 1); + evas_object_show(bt); + + notify = elm_notify_add(win); + evas_object_size_hint_weight_set(notify, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_notify_orient_set(notify, ELM_NOTIFY_ORIENT_RIGHT); + + bx = elm_box_add(win); + elm_notify_content_set(notify, bx); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Right position."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", _bt_close, notify); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Right"); + evas_object_smart_callback_add(bt, "clicked", _bt, notify); + elm_table_pack(tb, bt, 2, 1, 1, 1); + evas_object_show(bt); + + notify = elm_notify_add(win); + evas_object_size_hint_weight_set(notify, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_notify_orient_set(notify, ELM_NOTIFY_ORIENT_TOP_LEFT); + + bx = elm_box_add(win); + elm_notify_content_set(notify, bx); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Top Left position."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", _bt_close, notify); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Top Left"); + evas_object_smart_callback_add(bt, "clicked", _bt, notify); + elm_table_pack(tb, bt, 0, 0, 1, 1); + evas_object_show(bt); + + notify = elm_notify_add(win); + evas_object_size_hint_weight_set(notify, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_notify_orient_set(notify, ELM_NOTIFY_ORIENT_TOP_RIGHT); + + bx = elm_box_add(win); + elm_notify_content_set(notify, bx); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Top Right position."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", _bt_close, notify); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Top Right"); + evas_object_smart_callback_add(bt, "clicked", _bt, notify); + elm_table_pack(tb, bt, 2, 0, 1, 1); + evas_object_show(bt); + + notify = elm_notify_add(win); + evas_object_size_hint_weight_set(notify, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_notify_orient_set(notify, ELM_NOTIFY_ORIENT_BOTTOM_LEFT); + + bx = elm_box_add(win); + elm_notify_content_set(notify, bx); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Bottom Left position."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", _bt_close, notify); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Bottom Left"); + evas_object_smart_callback_add(bt, "clicked", _bt, notify); + elm_table_pack(tb, bt, 0, 2, 1, 1); + evas_object_show(bt); + + notify = elm_notify_add(win); + evas_object_size_hint_weight_set(notify, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_notify_orient_set(notify, ELM_NOTIFY_ORIENT_BOTTOM_RIGHT); + + bx = elm_box_add(win); + elm_notify_content_set(notify, bx); + elm_box_horizontal_set(bx, 1); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, "Bottom Right position."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close in 2s"); + evas_object_smart_callback_add(bt, "clicked", _bt_timer_close, notify); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Bottom Right"); + evas_object_smart_callback_add(bt, "clicked", _bt, notify); + elm_table_pack(tb, bt, 2, 2, 1, 1); + evas_object_show(bt); + + evas_object_show(win); + evas_object_resize(win, 300, 350); +} + +#endif + diff --git a/src/bin/test_pager.c b/src/bin/test_pager.c new file mode 100644 index 0000000..3324da6 --- /dev/null +++ b/src/bin/test_pager.c @@ -0,0 +1,330 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +typedef struct _Pginfo Pginfo; + +struct _Pginfo +{ + Evas_Object *win, *pager, *pg1, *pg2, *pg3, *pg4; +}; + +static void +my_pager_1(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Pginfo *info = data; + elm_pager_content_promote(info->pager, info->pg2); +} + +static void +my_pager_2(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Pginfo *info = data; + elm_pager_content_promote(info->pager, info->pg3); +} + +static void +my_pager_3(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Pginfo *info = data; + elm_pager_content_promote(info->pager, info->pg4); +} + + +static void +my_pager_4(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Pginfo *info = data; + elm_pager_content_promote(info->pager, info->pg1); +} + + +static void +my_pager_pop(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Pginfo *info = data; + elm_pager_content_pop(info->pager); +} + +struct style_tuple { + const char *label; + const char *name; +}; +static const struct style_tuple styles[] = { + { "Default", "default"}, + { "Slide", "slide"}, + { "Slide Invisible", "slide_invisible"}, + { "Fade", "fade"}, + { "Fade Translucide", "fade_translucide"}, + { "Fade Invisible", "fade_invisible"}, + { "Flip", "flip"}, +}; + +static void +_style(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *pg = data; + elm_object_style_set(pg, styles[elm_radio_value_get(obj)].name); +} + +void +test_pager(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *pg, *bx, *lb, *bt; + static Pginfo info; + + win = elm_win_add(NULL, "pager", ELM_WIN_BASIC); + elm_win_title_set(win, "Pager"); + elm_win_focus_highlight_enabled_set(win, EINA_TRUE); + elm_win_autodel_set(win, 1); + info.win = win; + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + pg = elm_pager_add(win); + evas_object_size_hint_weight_set(pg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, pg); + evas_object_show(pg); + + info.pager = pg; + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "This is page 1 in a pager stack.
    " + "
    " + "So what is a pager stack? It is a stack
    " + "of pages that hold widgets in it. The
    " + "pages can be pushed and popped on and
    " + "off the stack, activated and otherwise
    " + "activated if already in the stack
    " + "(activated means promoted to the top of
    " + "the stack).
    " + "
    " + "The theme may define the animation how
    " + "show and hide of pages. Select one theme style:"); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + unsigned int i = 0; + Evas_Object *rdg = NULL, *rd; + for (i = 0; i < (sizeof(styles) / sizeof(struct style_tuple)); i++) + { + rd = elm_radio_add(win); + elm_radio_label_set(rd, styles[i].label); + elm_radio_state_value_set(rd, i); + if (rdg) + elm_radio_group_add(rd, rdg); + else + rdg = rd; + evas_object_smart_callback_add(rd, "changed", _style, pg); + elm_box_pack_end(bx, rd); + evas_object_show(rd); + } + elm_radio_value_set(rd, 0); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Flip to 2"); + evas_object_smart_callback_add(bt, "clicked", my_pager_1, &info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Popme"); + evas_object_smart_callback_add(bt, "clicked", my_pager_pop, &info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + elm_pager_content_push(pg, bx); + info.pg1 = bx; + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "This is page 2 in a pager stack.
    " + "
    " + "This is just like the previous page in
    " + "the pager stack." + ); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Flip to 3"); + evas_object_smart_callback_add(bt, "clicked", my_pager_2, &info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Popme"); + evas_object_smart_callback_add(bt, "clicked", my_pager_pop, &info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + elm_pager_content_push(pg, bx); + info.pg2 = bx; + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "This is page 3 in a pager stack.
    " + "
    " + "This is just like the previous page in
    " + "the pager stack."); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Flip to 1"); + evas_object_smart_callback_add(bt, "clicked", my_pager_3, &info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Popme"); + evas_object_smart_callback_add(bt, "clicked", my_pager_pop, &info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + elm_pager_content_push(pg, bx); + info.pg3 = bx; + + Evas_Object *ly, *ly2; + char buf[4096]; + + ly = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/test.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly, buf, "test/layout"); + evas_object_size_hint_weight_set(ly, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(ly); + + ly2 = elm_layout_add(win); + snprintf(buf, sizeof(buf), "%s/objects/test.edj", PACKAGE_DATA_DIR); + elm_layout_file_set(ly2, buf, "layout2"); + evas_object_size_hint_weight_set(ly2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + //elm_win_resize_object_add(win, ly2); + evas_object_show(ly2); + + + + + bt = elm_button_add(win); + elm_button_label_set(bt, "Flip to 1"); + evas_object_smart_callback_add(bt, "clicked", my_pager_4, &info); + elm_layout_content_set(ly2, "element1", bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Popme"); + evas_object_smart_callback_add(bt, "clicked", my_pager_pop, &info); + evas_object_show(bt); + elm_layout_content_set(ly2, "element2", bt); + + elm_layout_content_set(ly, "swallow", ly2); + evas_object_show(ly); + + elm_pager_content_push(pg, ly); + info.pg4 = ly2; + + + evas_object_show(win); +} + +static void +my_pager_push(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Pginfo *info = data; + Evas_Object *bx, *bt, *lb; + static int count = 2; + char buf[32]; + + bx = elm_box_add(info->win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + lb = elm_label_add(info->win); + snprintf(buf, sizeof(buf), "This is page %d in the slide pager

    ", count++); + elm_label_label_set(lb, buf); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(info->win); + elm_button_label_set(bt, "Push a new page"); + evas_object_smart_callback_add(bt, "clicked", my_pager_push, info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(info->win); + elm_button_label_set(bt, "Go back (pop)"); + evas_object_smart_callback_add(bt, "clicked", my_pager_pop, info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + elm_pager_content_push(info->pager, bx); +} + +void +test_pager_slide(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *pg, *bx, *lb, *bt; + static Pginfo info; + + win = elm_win_add(NULL, "pager", ELM_WIN_BASIC); + elm_win_title_set(win, "Pager Slide"); + elm_win_focus_highlight_enabled_set(win, EINA_TRUE); + elm_win_autodel_set(win, 1); + info.win = win; + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + pg = elm_pager_add(win); + elm_win_resize_object_add(win, pg); + elm_object_style_set(pg, "slide"); + evas_object_show(pg); + info.pager = pg; + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + lb = elm_label_add(win); + elm_label_label_set(lb, + "This is page 1 in a slide pager.
    " + "
    " + "The slide pager style is useful for browsing
    " + "a hierarchy of objects, as it makes clear
    " + "the direction of the browse.
    " + "This is the 'slide' style, also available
    " + "a fully transparent style named 'slide_invisble'.
    " + "
    "); + elm_box_pack_end(bx, lb); + evas_object_show(lb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Push a new page"); + evas_object_smart_callback_add(bt, "clicked", my_pager_push, &info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Go back (pop)"); + evas_object_smart_callback_add(bt, "clicked", my_pager_pop, &info); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + elm_pager_content_push(pg, bx); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_panel.c b/src/bin/test_panel.c new file mode 100644 index 0000000..aa0493a --- /dev/null +++ b/src/bin/test_panel.c @@ -0,0 +1,264 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static Elm_Genlist_Item_Class itc; + +static void _bstatus(void *data, Evas_Object *obj, void *event_info); +static void _tstatus(void *data, Evas_Object *obj, void *event_info); +static char *_label_get(void *data, Evas_Object *obj, const char *source); +static Evas_Object *_icon_get(void *data, Evas_Object *obj, const char *source); +static Eina_Bool _state_get(void *data, Evas_Object *obj, const char *source); +static void _item_del(void *data, Evas_Object *obj); +static void _fill_list(Evas_Object *obj); +static Eina_Bool _dir_has_subs(const char *path); + +static void +_tstatus(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Toolbar_Item *sel; + const char *status; + + if (elm_panel_hidden_get((Evas_Object*)data)) + status = "hidden"; + else + status = "shown"; + printf("The top panel is currently %s\n", status); + sel = elm_toolbar_selected_item_get(obj); + elm_toolbar_item_selected_set(sel, EINA_FALSE); +} + +static void +_bstatus(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Toolbar_Item *sel; + const char *status; + + if (elm_panel_hidden_get((Evas_Object*)data)) + status = "hidden"; + else + status = "shown"; + printf("The bottom panel is currently %s\n", status); + sel = elm_toolbar_selected_item_get(obj); + elm_toolbar_item_selected_set(sel, EINA_FALSE); +} + +static char * +_label_get(void *data, Evas_Object *obj __UNUSED__, const char *source __UNUSED__) +{ + return strdup(ecore_file_file_get(data)); +} + +static Evas_Object * +_icon_get(void *data, Evas_Object *obj, const char *source) +{ + if (!strcmp(source, "elm.swallow.icon")) + { + Evas_Object *ic; + + ic = elm_icon_add(obj); + if (ecore_file_is_dir((char *)data)) + elm_icon_standard_set(ic, "folder"); + else + elm_icon_standard_set(ic, "file"); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + evas_object_show(ic); + return ic; + } + return NULL; +} + +static Eina_Bool +_state_get(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const char *source __UNUSED__) +{ + return EINA_FALSE; +} + +static void +_item_del(void *data, Evas_Object *obj __UNUSED__) +{ + eina_stringshare_del(data); +} + +static void +_fill_list(Evas_Object *obj) +{ + DIR *d; + struct dirent *de; + Eina_List *dirs = NULL, *l; + char *real; + + if (!(d = opendir(getenv("HOME")))) return; + while ((de = readdir(d))) + { + char buff[PATH_MAX]; + + if (de->d_name[0] == '.') continue; + snprintf(buff, sizeof(buff), "%s/%s", getenv("HOME"), de->d_name); + if (!ecore_file_is_dir(buff)) continue; + real = ecore_file_realpath(buff); + dirs = eina_list_append(dirs, real); + } + closedir(d); + + dirs = eina_list_sort(dirs, eina_list_count(dirs), EINA_COMPARE_CB(strcoll)); + + EINA_LIST_FOREACH(dirs, l, real) + { + Eina_Bool result = EINA_FALSE; + + result = _dir_has_subs(real); + if (!result) + elm_genlist_item_append(obj, &itc, eina_stringshare_add(real), + NULL, ELM_GENLIST_ITEM_NONE, NULL, NULL); + else + elm_genlist_item_append(obj, &itc, eina_stringshare_add(real), + NULL, ELM_GENLIST_ITEM_SUBITEMS, + NULL, NULL); + free(real); + } + eina_list_free(dirs); +} + +static Eina_Bool +_dir_has_subs(const char *path) +{ + DIR *d; + struct dirent *de; + Eina_Bool result = EINA_FALSE; + + if (!path) return result; + if (!(d = opendir(path))) return result; + while ((de = readdir(d))) + { + char buff[PATH_MAX]; + + if (de->d_name[0] == '.') continue; + snprintf(buff, sizeof(buff), "%s/%s", path, de->d_name); + if (ecore_file_is_dir(buff)) + { + result = EINA_TRUE; + break; + } + } + closedir(d); + return result; +} + +void +test_panel(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *panel, *bx, *vbx, *toolbar; + Evas_Object *list; + + win = elm_win_add(NULL, "panel", ELM_WIN_BASIC); + elm_win_title_set(win, "Panel"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + vbx = elm_box_add(win); + elm_win_resize_object_add(win, vbx); + evas_object_size_hint_weight_set(vbx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(vbx, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(vbx); + + bx = elm_box_add(win); + elm_box_horizontal_set(bx, EINA_TRUE); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(bx); + + panel = elm_panel_add(win); + elm_panel_orient_set(panel, ELM_PANEL_ORIENT_TOP); + evas_object_size_hint_weight_set(panel, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(panel, EVAS_HINT_FILL, EVAS_HINT_FILL); + + toolbar = elm_toolbar_add(win); + elm_toolbar_homogenous_set(toolbar, 0); + elm_toolbar_mode_shrink_set(toolbar, ELM_TOOLBAR_SHRINK_NONE); + evas_object_size_hint_weight_set(toolbar, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(toolbar, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(toolbar); + + elm_toolbar_item_append(toolbar, "home", "Hello", _tstatus, panel); + + elm_panel_content_set(panel, toolbar); + elm_box_pack_end(vbx, panel); + evas_object_show(panel); + + panel = elm_panel_add(win); + elm_panel_orient_set(panel, ELM_PANEL_ORIENT_LEFT); + evas_object_size_hint_weight_set(panel, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(panel, 0, EVAS_HINT_FILL); + + itc.item_style = "default"; + itc.func.label_get = _label_get; + itc.func.icon_get = _icon_get; + itc.func.state_get = _state_get; + itc.func.del = _item_del; + + list = elm_genlist_add(win); + evas_object_size_hint_min_set(list, 100, -1); + evas_object_size_hint_weight_set(list, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(list, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(list); + + elm_panel_content_set(panel, list); + + elm_box_pack_end(bx, panel); + evas_object_show(panel); + + _fill_list(list); + + panel = elm_panel_add(win); + elm_panel_orient_set(panel, ELM_PANEL_ORIENT_RIGHT); + evas_object_size_hint_weight_set(panel, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(panel, 1, EVAS_HINT_FILL); + elm_panel_hidden_set(panel, EINA_TRUE); + + list = elm_genlist_add(win); + evas_object_size_hint_min_set(list, 100, -1); + evas_object_size_hint_weight_set(list, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(list, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(list); + + elm_panel_content_set(panel, list); + + elm_box_pack_end(bx, panel); + evas_object_show(panel); + + _fill_list(list); + + elm_box_pack_end(vbx, bx); + + panel = elm_panel_add(win); + elm_panel_orient_set(panel, ELM_PANEL_ORIENT_BOTTOM); + evas_object_size_hint_weight_set(panel, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(panel, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_panel_hidden_set(panel, EINA_TRUE); + + toolbar = elm_toolbar_add(win); + elm_toolbar_homogenous_set(toolbar, 0); + elm_toolbar_mode_shrink_set(toolbar, ELM_TOOLBAR_SHRINK_NONE); + evas_object_size_hint_weight_set(toolbar, EVAS_HINT_EXPAND, 0); + evas_object_size_hint_align_set(toolbar, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(toolbar); + + elm_toolbar_item_append(toolbar, "home", "Hello", _bstatus, panel); + + elm_panel_content_set(panel, toolbar); + elm_box_pack_end(vbx, panel); + evas_object_show(panel); + + evas_object_resize(win, 320, 400); + evas_object_show(win); +} + + +#endif diff --git a/src/bin/test_panes.c b/src/bin/test_panes.c new file mode 100644 index 0000000..b0800d6 --- /dev/null +++ b/src/bin/test_panes.c @@ -0,0 +1,118 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static double size = 0.0; + +static void +_press(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("press\n"); +} + +static void +_unpress(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + printf("unpress, size : %f\n", elm_panes_content_left_size_get(obj)); +} + +static void +_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("clicked\n"); +} + + +static void +_clicked_double(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + printf("clicked double\n"); + if(elm_panes_content_left_size_get(obj) > 0) + { + size = elm_panes_content_left_size_get(obj); + elm_panes_content_left_size_set(obj, 0.0); + } + else + elm_panes_content_left_size_set(obj, size); +} + + +void +test_panes(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *panes, *panes_h, *bt; + + win = elm_win_add(NULL, "panes", ELM_WIN_BASIC); + elm_win_title_set(win, "Panes"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_focus_highlight_enabled_set(win, EINA_TRUE); + evas_object_show(bg); + + panes = elm_panes_add(win); + elm_win_resize_object_add(win, panes); + evas_object_size_hint_weight_set(panes, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(panes, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(panes); + + evas_object_smart_callback_add(panes, "clicked", _clicked, panes); + evas_object_smart_callback_add(panes, "clicked,double", _clicked_double, panes); + + evas_object_smart_callback_add(panes, "press", _press, panes); + evas_object_smart_callback_add(panes, "unpress", _unpress, panes); + + + // + bt = elm_button_add(win); + elm_button_label_set(bt, "Left"); + evas_object_size_hint_weight_set(bt, 1.0, 1.0); + evas_object_size_hint_align_set(bt, -1.0, -1.0); + evas_object_show(bt); + elm_panes_content_left_set(panes, bt); + // + + // + panes_h = elm_panes_add(win); + elm_panes_horizontal_set(panes_h, EINA_TRUE); + evas_object_size_hint_weight_set(panes_h, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(panes_h, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(panes_h); + + evas_object_smart_callback_add(panes_h, "clicked", _clicked, panes_h); + evas_object_smart_callback_add(panes_h, "clicked,double", _clicked_double, panes_h); + + evas_object_smart_callback_add(panes_h, "press", _press, panes_h); + evas_object_smart_callback_add(panes_h, "unpress", _unpress, panes_h); + elm_panes_content_right_set(panes, panes_h); + // + + // + bt = elm_button_add(win); + elm_button_label_set(bt, "Up"); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(bt); + elm_panes_content_left_set(panes_h, bt); + // + + // + bt = elm_button_add(win); + elm_button_label_set(bt, "Down"); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(bt); + elm_panes_content_right_set(panes_h, bt); + // + + + evas_object_resize(win, 320, 400); + evas_object_show(win); +} + + +#endif diff --git a/src/bin/test_photo.c b/src/bin/test_photo.c new file mode 100644 index 0000000..1658f30 --- /dev/null +++ b/src/bin/test_photo.c @@ -0,0 +1,104 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static void drop_cb(void *mydata, Evas_Object *obj, void *evdata); +static void drag_stop_cb(void *mydata, Evas_Object *obj, void *evdata); +static void drag_start_cb(void *mydata, Evas_Object *obj, void *evdata); + +void +test_photo(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *sc, *tb, *ph; + int i, j, n; + char buf[PATH_MAX]; + const char *img[9] = + { + "panel_01.jpg", + "mystrale.jpg", + "mystrale_2.jpg", + "rock_02.jpg", + "sky_01.jpg", + "sky_02.jpg", + "sky_03.jpg", + "sky_04.jpg", + "wood_01.jpg" + }; + + win = elm_win_add(NULL, "photo", ELM_WIN_BASIC); + elm_win_title_set(win, "Photo"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + n = 0; + for (j = 0; j < 12; j++) + { + for (i = 0; i < 12; i++) + { + ph = elm_photo_add(win); + snprintf(buf, sizeof(buf), "%s/images/%s", + PACKAGE_DATA_DIR, img[n]); + n++; + if (n >= 9) n = 0; + elm_photo_size_set(ph, 80); + elm_photo_file_set(ph, buf); + elm_photo_editable_set(ph, 1); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_smart_callback_add(ph, "drop", + drop_cb, NULL); + evas_object_smart_callback_add(ph, "drag,start", + drag_start_cb, NULL); + evas_object_smart_callback_add(ph, "drag,stop", + drag_stop_cb, NULL); + + if((n == 2) || (n == 3)) { + elm_photo_fill_inside_set(ph, EINA_TRUE); + elm_object_style_set(ph, "shadow"); + } + elm_table_pack(tb, ph, i, j, 1, 1); + evas_object_show(ph); + } + } + + sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, sc); + + elm_scroller_content_set(sc, tb); + evas_object_show(tb); + evas_object_show(sc); + + evas_object_resize(win, 300, 300); + evas_object_show(win); +} + +/* Never called, elm_photo never call "drop" smart cb */ +static void +drop_cb(void *mydata __UNUSED__, Evas_Object *obj, void *evdata __UNUSED__){ + printf("Drop on obj %p\n", obj); +} + +static void +drag_start_cb(void *mydata __UNUSED__, Evas_Object *obj __UNUSED__, void *evdata __UNUSED__){ + +} + +static void +drag_stop_cb(void *mydata __UNUSED__, Evas_Object *obj __UNUSED__, void *evdata __UNUSED__){ + +} + +/* vim:set ts=8 sw=3 sts=3 expandtab cino=>5n-2f0^-2{2(0W1st0 :*/ +#endif diff --git a/src/bin/test_photocam.c b/src/bin/test_photocam.c new file mode 100644 index 0000000..97891f5 --- /dev/null +++ b/src/bin/test_photocam.c @@ -0,0 +1,342 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +static Evas_Object *rect; + +static void +my_ph_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("clicked\n"); +} + +static void +my_ph_press(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("press\n"); +} + +static void +my_ph_longpressed(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("longpressed\n"); +} + +static void +my_ph_clicked_double(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("clicked,double\n"); +} + +static void +my_ph_load(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("load\n"); +} + +static void +my_ph_loaded(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("loaded\n"); +} + +static void +my_ph_load_details(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("load,details\n"); +} + +static void +my_ph_loaded_details(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("loaded,details\n"); +} + +static void +my_ph_zoom_start(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("zoom,start\n"); +} + +static void +my_ph_zoom_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("zoom,stop\n"); +} + +static void +my_ph_zoom_change(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("zoom,change\n"); +} + +static void +my_ph_anim_start(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("anim,start\n"); +} + +static void +my_ph_anim_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("anim,stop\n"); +} + +static void +my_ph_drag_start(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag,start\n"); +} + +static void +my_ph_drag_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + printf("drag_stop\n"); +} + +static void +my_ph_scroll(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + int x, y, w, h; + elm_photocam_region_get(obj, &x, &y, &w, &h); + printf("scroll %i %i %ix%i\n", x, y, w, h); +} + +static void +my_bt_open(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Object *ph = data; + const char *file = event_info; + + if (file) + elm_photocam_file_set(ph, file); +} + +static void +my_bt_show_reg(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_photocam_image_region_show(data, 30, 50, 500, 300); +} + +static void +my_bt_bring_reg(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) + +{ + elm_photocam_image_region_bring_in(data, 800, 300, 500, 300); +} + +static void +my_bt_zoom_in(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + double zoom; + + zoom = elm_photocam_zoom_get(data); + zoom -= 0.5; + elm_photocam_zoom_mode_set(data, ELM_PHOTOCAM_ZOOM_MODE_MANUAL); + if (zoom >= (1.0 / 32.0)) elm_photocam_zoom_set(data, zoom); +} + +static void +my_bt_zoom_out(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + double zoom; + + zoom = elm_photocam_zoom_get(data); + zoom += 0.5; + elm_photocam_zoom_mode_set(data, ELM_PHOTOCAM_ZOOM_MODE_MANUAL); + if (zoom <= 256.0) elm_photocam_zoom_set(data, zoom); +} + +static void +my_bt_pause(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_photocam_paused_set(data, !elm_photocam_paused_get(data)); +} + +static void +my_bt_zoom_fit(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_photocam_zoom_mode_set(data, ELM_PHOTOCAM_ZOOM_MODE_AUTO_FIT); +} + +static void +my_bt_zoom_fill(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_photocam_zoom_mode_set(data, ELM_PHOTOCAM_ZOOM_MODE_AUTO_FILL); +} + +static void +_photocam_mouse_wheel_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Object *photocam = data; + Evas_Event_Mouse_Wheel *ev = (Evas_Event_Mouse_Wheel*) event_info; + int zoom; + double val; + //unset the mouse wheel + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + + zoom = elm_photocam_zoom_get(photocam); + if ((ev->z>0) && (zoom == 1)) return; + + if (ev->z > 0) + zoom /= 2; + else + zoom *= 2; + + val = 1; + int _zoom = zoom; + while(_zoom>1) + { + _zoom /= 2; + val++; + } + + elm_photocam_zoom_mode_set(photocam, ELM_PHOTOCAM_ZOOM_MODE_MANUAL); + if (zoom >= 1) elm_photocam_zoom_set(photocam, zoom); +} + +static void +_photocam_move_resize_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + int x,y,w,h; + + evas_object_geometry_get(data,&x,&y,&w,&h); + evas_object_resize(rect,w,h); + evas_object_move(rect,x,y); +} + +void +test_photocam(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *ph, *tb2, *bt; + // these were just testing - use the "select photo" browser to select one + const char *img[5] = + { + "/home/raster/t1.jpg", // 5 mpixel + "/home/raster/t2.jpg", // 18 mpixel + "/home/raster/t3.jpg", // 39 mpixel + "/home/raster/t4.jpg", // 192 mpixel + "/home/raster/t5.jpg" // 466 mpixel + }; + + win = elm_win_add(NULL, "photocam", ELM_WIN_BASIC); + elm_win_title_set(win, "Photocam"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + ph = elm_photocam_add(win); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, ph); + evas_object_data_set(ph, "window", win); + + rect = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_color_set(rect, 0, 0, 0, 0); + evas_object_repeat_events_set(rect,1); + evas_object_show(rect); + evas_object_event_callback_add(rect, EVAS_CALLBACK_MOUSE_WHEEL, _photocam_mouse_wheel_cb, ph); + evas_object_raise(rect); + + evas_object_event_callback_add(ph, EVAS_CALLBACK_RESIZE, _photocam_move_resize_cb, ph); + evas_object_event_callback_add(ph, EVAS_CALLBACK_MOVE, _photocam_move_resize_cb, ph); + + evas_object_smart_callback_add(ph, "clicked", my_ph_clicked, win); + evas_object_smart_callback_add(ph, "press", my_ph_press, win); + evas_object_smart_callback_add(ph, "longpressed", my_ph_longpressed, win); + evas_object_smart_callback_add(ph, "clicked,double", my_ph_clicked_double, win); + evas_object_smart_callback_add(ph, "load", my_ph_load, win); + evas_object_smart_callback_add(ph, "loaded", my_ph_loaded, win); + evas_object_smart_callback_add(ph, "load,details", my_ph_load_details, win); + evas_object_smart_callback_add(ph, "loaded,details", my_ph_loaded_details, win); + evas_object_smart_callback_add(ph, "zoom,start", my_ph_zoom_start, win); + evas_object_smart_callback_add(ph, "zoom,stop", my_ph_zoom_stop, win); + evas_object_smart_callback_add(ph, "zoom,change", my_ph_zoom_change, win); + evas_object_smart_callback_add(ph, "scroll,anim,start", my_ph_anim_start, win); + evas_object_smart_callback_add(ph, "scroll,anim,stop", my_ph_anim_stop, win); + evas_object_smart_callback_add(ph, "scroll,drag,start", my_ph_drag_start, win); + evas_object_smart_callback_add(ph, "scroll,drag,stop", my_ph_drag_stop, win); + evas_object_smart_callback_add(ph, "scroll", my_ph_scroll, win); + + elm_photocam_file_set(ph, img[1]); + + evas_object_show(ph); + + tb2 = elm_table_add(win); + evas_object_size_hint_weight_set(tb2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, tb2); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Z -"); + evas_object_smart_callback_add(bt, "clicked", my_bt_zoom_out, ph); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.1, 0.1); + elm_table_pack(tb2, bt, 0, 0, 1, 1); + evas_object_show(bt); + + bt = elm_fileselector_button_add(win); + elm_fileselector_button_label_set(bt, "Select Photo"); + evas_object_smart_callback_add(bt, "file,chosen", my_bt_open, ph); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.5, 0.1); + elm_table_pack(tb2, bt, 1, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Z +"); + evas_object_smart_callback_add(bt, "clicked", my_bt_zoom_in, ph); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.1); + elm_table_pack(tb2, bt, 2, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Show 30,50 500x300"); + evas_object_smart_callback_add(bt, "clicked", my_bt_show_reg, ph); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.1, 0.5); + elm_table_pack(tb2, bt, 0, 1, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Bring 800,300 500x300"); + evas_object_smart_callback_add(bt, "clicked", my_bt_bring_reg, ph); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.5); + elm_table_pack(tb2, bt, 2, 1, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Pause On/Off"); + evas_object_smart_callback_add(bt, "clicked", my_bt_pause, ph); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.1, 0.9); + elm_table_pack(tb2, bt, 0, 2, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Fit"); + evas_object_smart_callback_add(bt, "clicked", my_bt_zoom_fit, ph); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.5, 0.9); + elm_table_pack(tb2, bt, 1, 2, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Fill"); + evas_object_smart_callback_add(bt, "clicked", my_bt_zoom_fill, ph); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.9); + elm_table_pack(tb2, bt, 2, 2, 1, 1); + evas_object_show(bt); + + evas_object_show(tb2); + + evas_object_resize(win, 800, 800); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_progressbar.c b/src/bin/test_progressbar.c new file mode 100644 index 0000000..198b63c --- /dev/null +++ b/src/bin/test_progressbar.c @@ -0,0 +1,205 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +typedef struct Progressbar +{ + Evas_Object *pb1; + Evas_Object *pb2; + Evas_Object *pb3; + Evas_Object *pb4; + Evas_Object *pb5; + Evas_Object *pb6; + Evas_Object *pb7; + Eina_Bool run; + Ecore_Timer *timer; +} Progressbar; + +static Progressbar _test_progressbar; + +static Eina_Bool +_my_progressbar_value_set (void *data __UNUSED__) +{ + double progress; + + progress = elm_progressbar_value_get (_test_progressbar.pb1); + if (progress < 1.0) progress += 0.0123; + else progress = 0.0; + elm_progressbar_value_set(_test_progressbar.pb1, progress); + elm_progressbar_value_set(_test_progressbar.pb4, progress); + elm_progressbar_value_set(_test_progressbar.pb3, progress); + elm_progressbar_value_set(_test_progressbar.pb6, progress); + if (progress < 1.0) return ECORE_CALLBACK_RENEW; + _test_progressbar.run = 0; + return ECORE_CALLBACK_CANCEL; +} + +static void +my_progressbar_test_start(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_progressbar_pulse(_test_progressbar.pb2, EINA_TRUE); + elm_progressbar_pulse(_test_progressbar.pb5, EINA_TRUE); + elm_progressbar_pulse(_test_progressbar.pb7, EINA_TRUE); + if (!_test_progressbar.run) + { + _test_progressbar.timer = ecore_timer_add(0.1, _my_progressbar_value_set, NULL); + _test_progressbar.run = EINA_TRUE; + } +} + +static void +my_progressbar_test_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_progressbar_pulse(_test_progressbar.pb2, EINA_FALSE); + elm_progressbar_pulse(_test_progressbar.pb5, EINA_FALSE); + elm_progressbar_pulse(_test_progressbar.pb7, EINA_FALSE); + if (_test_progressbar.run) + { + ecore_timer_del(_test_progressbar.timer); + _test_progressbar.run = EINA_FALSE; + } +} + +static void +my_progressbar_destroy(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + my_progressbar_test_stop(NULL, NULL, NULL); + evas_object_del(obj); +} + +void +test_progressbar(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *pb, *bx, *hbx, *bt, *bt_bx, *ic1, *ic2; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "progressbar", ELM_WIN_BASIC); + elm_win_title_set(win, "Progressbar"); + evas_object_smart_callback_add(win, "delete,request", + my_progressbar_destroy, NULL); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + pb = elm_progressbar_add(win); + evas_object_size_hint_weight_set(pb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(pb, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, pb); +// elm_progressbar_horizontal_set(pb, EINA_TRUE); +// elm_progressbar_label_set(pb, "Progression %"); +// elm_progressbar_unit_format_set(pb, NULL); + evas_object_show(pb); + _test_progressbar.pb1 = pb; + + pb = elm_progressbar_add(win); + evas_object_size_hint_align_set(pb, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(pb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_progressbar_label_set(pb, "Infinite bounce"); + elm_progressbar_pulse_set(pb, EINA_TRUE); + elm_box_pack_end(bx, pb); + evas_object_show(pb); + _test_progressbar.pb2 = pb; + + ic1 = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic1, buf, NULL); + evas_object_size_hint_aspect_set(ic1, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + + pb = elm_progressbar_add(win); + elm_progressbar_label_set(pb, "Label"); + elm_progressbar_icon_set(pb, ic1); + elm_progressbar_inverted_set(pb, 1); + elm_progressbar_unit_format_set(pb, "%1.1f units"); + elm_progressbar_span_size_set(pb, 200); + evas_object_size_hint_align_set(pb, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(pb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, pb); + evas_object_show(ic1); + evas_object_show(pb); + _test_progressbar.pb3 = pb; + + hbx = elm_box_add(win); + elm_box_horizontal_set(hbx, EINA_TRUE); + evas_object_size_hint_weight_set(hbx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(hbx, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, hbx); + evas_object_show(hbx); + + pb = elm_progressbar_add(win); + elm_progressbar_horizontal_set(pb, EINA_FALSE); + evas_object_size_hint_align_set(pb, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(pb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(hbx, pb); + elm_progressbar_span_size_set(pb, 60); + elm_progressbar_label_set(pb, "percent"); + evas_object_show(pb); + _test_progressbar.pb4 = pb; + + pb = elm_progressbar_add(win); + elm_progressbar_horizontal_set(pb, EINA_FALSE); + evas_object_size_hint_align_set(pb, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(pb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_progressbar_span_size_set(pb, 80); + elm_progressbar_pulse_set(pb, EINA_TRUE); + elm_progressbar_unit_format_set(pb, NULL); + elm_progressbar_label_set(pb, "Infinite bounce"); + elm_box_pack_end(hbx, pb); + evas_object_show(pb); + _test_progressbar.pb5 = pb; + + ic2 = elm_icon_add(win); + elm_icon_file_set(ic2, buf, NULL); + evas_object_size_hint_aspect_set(ic2, EVAS_ASPECT_CONTROL_HORIZONTAL, 1, 1); + + pb = elm_progressbar_add(win); + elm_progressbar_horizontal_set(pb, EINA_FALSE); + elm_progressbar_label_set(pb, "Label"); + elm_progressbar_icon_set(pb, ic2); + elm_progressbar_inverted_set(pb, 1); + elm_progressbar_unit_format_set(pb, "%1.2f%%"); + elm_progressbar_span_size_set(pb, 200); + evas_object_size_hint_align_set(pb, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(pb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(hbx, pb); + evas_object_show(ic2); + evas_object_show(pb); + _test_progressbar.pb6 = pb; + + pb = elm_progressbar_add(win); + elm_object_style_set(pb, "wheel"); + elm_progressbar_label_set(pb, "Style: wheel"); + evas_object_size_hint_align_set(pb, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(pb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, pb); + evas_object_show(pb); + _test_progressbar.pb7 = pb; + + bt_bx = elm_box_add(win); + elm_box_horizontal_set(bt_bx, 1); + evas_object_size_hint_weight_set(bt_bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, bt_bx); + evas_object_show(bt_bx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Start"); + evas_object_smart_callback_add(bt, "clicked", my_progressbar_test_start, NULL); + elm_box_pack_end(bt_bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Stop"); + evas_object_smart_callback_add(bt, "clicked", my_progressbar_test_stop, NULL); + elm_box_pack_end(bt_bx, bt); + evas_object_show(bt); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_radio.c b/src/bin/test_radio.c new file mode 100644 index 0000000..6ee75ac --- /dev/null +++ b/src/bin/test_radio.c @@ -0,0 +1,102 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_radio(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *ic, *rd, *rdg; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "radio", ELM_WIN_BASIC); + elm_win_title_set(win, "Radios"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, 0); + evas_object_size_hint_weight_set(rd, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(rd, EVAS_HINT_FILL, 0.5); + elm_radio_label_set(rd, "Icon sized to radio"); + elm_radio_icon_set(rd, ic); + elm_box_pack_end(bx, rd); + evas_object_show(rd); + evas_object_show(ic); + rdg = rd; + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, 1); + elm_radio_group_add(rd, rdg); + elm_radio_label_set(rd, "Icon no scale"); + elm_radio_icon_set(rd, ic); + elm_box_pack_end(bx, rd); + evas_object_show(rd); + evas_object_show(ic); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, 2); + elm_radio_group_add(rd, rdg); + elm_radio_label_set(rd, "Label Only"); + elm_box_pack_end(bx, rd); + evas_object_show(rd); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, 3); + elm_radio_group_add(rd, rdg); + elm_radio_label_set(rd, "Disabled"); + elm_object_disabled_set(rd, 1); + elm_box_pack_end(bx, rd); + evas_object_show(rd); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, 4); + elm_radio_group_add(rd, rdg); + elm_radio_icon_set(rd, ic); + elm_box_pack_end(bx, rd); + evas_object_show(rd); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + + rd = elm_radio_add(win); + elm_radio_state_value_set(rd, 5); + elm_radio_group_add(rd, rdg); + elm_radio_icon_set(rd, ic); + elm_object_disabled_set(rd, 1); + elm_box_pack_end(bx, rd); + evas_object_show(rd); + evas_object_show(ic); + + elm_radio_value_set(rdg, 2); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_scaling.c b/src/bin/test_scaling.c new file mode 100644 index 0000000..aa396a7 --- /dev/null +++ b/src/bin/test_scaling.c @@ -0,0 +1,126 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_scaling(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bt; + + win = elm_win_add(NULL, "scaling", ELM_WIN_BASIC); + elm_win_title_set(win, "Scaling"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Scale: 0.5"); + elm_object_scale_set(bt, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Scale: 0.75"); + elm_object_scale_set(bt, 0.75); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Scale: 1.0"); + elm_object_scale_set(bt, 1.0); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Scale: 1.5"); + elm_object_scale_set(bt, 1.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Scale: 2.0"); + elm_object_scale_set(bt, 2.0); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Scale: 3.0"); + elm_object_scale_set(bt, 3.0); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +void +test_scaling2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *fr, *lb; + + win = elm_win_add(NULL, "scaling-2", ELM_WIN_BASIC); + elm_win_title_set(win, "Scaling 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + fr = elm_frame_add(win); + elm_object_scale_set(fr, 0.5); + elm_frame_label_set(fr, "Scale: 0.5"); + lb = elm_label_add(win); + elm_label_label_set(lb, + "Parent frame scale
    " + "is 0.5. Child should
    " + "inherit it."); + elm_frame_content_set(fr, lb); + evas_object_show(lb); + elm_box_pack_end(bx, fr); + evas_object_show(fr); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Scale: 1.0"); + lb = elm_label_add(win); + elm_label_label_set(lb, + "Parent frame scale
    " + "is 1.0. Child should
    " + "inherit it."); + elm_frame_content_set(fr, lb); + evas_object_show(lb); + elm_object_scale_set(fr, 1.0); + elm_box_pack_end(bx, fr); + evas_object_show(fr); + + fr = elm_frame_add(win); + elm_frame_label_set(fr, "Scale: 2.0"); + lb = elm_label_add(win); + elm_label_label_set(lb, + "Parent frame scale
    " + "is 2.0. Child should
    " + "inherit it."); + elm_frame_content_set(fr, lb); + evas_object_show(lb); + elm_object_scale_set(fr, 2.0); + elm_box_pack_end(bx, fr); + evas_object_show(fr); + + evas_object_resize(win, 320, 320); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_scroller.c b/src/bin/test_scroller.c new file mode 100644 index 0000000..7ad1d19 --- /dev/null +++ b/src/bin/test_scroller.c @@ -0,0 +1,266 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +my_bt_go_300_300(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_scroller_region_bring_in((Evas_Object *)data, 300, 300, 318, 318); +} + +void +my_bt_go_900_300(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_scroller_region_bring_in((Evas_Object *)data, 900, 300, 318, 318); +} + +void +my_bt_go_300_900(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_scroller_region_bring_in((Evas_Object *)data, 300, 900, 318, 318); +} + +void +my_bt_go_900_900(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_scroller_region_bring_in((Evas_Object *)data, 900, 900, 318, 318); +} + +void +test_scroller(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg2, *tb, *tb2, *bg, *sc, *bt; + int i, j, n; + char buf[PATH_MAX]; + const char *img[9] = + { + "panel_01.jpg", + "plant_01.jpg", + "rock_01.jpg", + "rock_02.jpg", + "sky_01.jpg", + "sky_02.jpg", + "sky_03.jpg", + "sky_04.jpg", + "wood_01.jpg" + }; + + win = elm_win_add(NULL, "scroller", ELM_WIN_BASIC); + elm_win_title_set(win, "Scroller"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + n = 0; + for (j = 0; j < 12; j++) + { + for (i = 0; i < 12; i++) + { + bg2 = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/%s", + PACKAGE_DATA_DIR, img[n]); + n++; + if (n >= 9) n = 0; + elm_bg_file_set(bg2, buf, NULL); + evas_object_size_hint_weight_set(bg2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bg2, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_min_set(bg2, 318, 318); + elm_table_pack(tb, bg2, i, j, 1, 1); + evas_object_show(bg2); + } + } + + sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, sc); + + elm_scroller_content_set(sc, tb); + evas_object_show(tb); + + elm_scroller_page_relative_set(sc, 1.0, 1.0); +// elm_scroller_page_size_set(sc, 200, 200); + evas_object_show(sc); + + tb2 = elm_table_add(win); + evas_object_size_hint_weight_set(tb2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, tb2); + + bt = elm_button_add(win); + elm_button_label_set(bt, "to 300 300"); + evas_object_smart_callback_add(bt, "clicked", my_bt_go_300_300, sc); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.1, 0.1); + elm_table_pack(tb2, bt, 0, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "to 900 300"); + evas_object_smart_callback_add(bt, "clicked", my_bt_go_900_300, sc); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.1); + elm_table_pack(tb2, bt, 1, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "to 300 900"); + evas_object_smart_callback_add(bt, "clicked", my_bt_go_300_900, sc); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.1, 0.9); + elm_table_pack(tb2, bt, 0, 1, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "to 900 900"); + evas_object_smart_callback_add(bt, "clicked", my_bt_go_900_900, sc); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, 0.9, 0.9); + elm_table_pack(tb2, bt, 1, 1, 1, 1); + evas_object_show(bt); + + evas_object_show(tb2); + + evas_object_resize(win, 320, 320); + evas_object_show(win); +} + +void +click_through(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + printf("click went through on %p\n", obj); +} + +void +test_scroller2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bt, *bx, *bx2, *bg, *sc, *tb, *tb2, *rc; + int i, j; + + win = elm_win_add(NULL, "scroller2", ELM_WIN_BASIC); + elm_win_title_set(win, "Scroller 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, 0.0); + + /* { */ + for (i = 0; i < 3; i++) + { + bt = elm_button_add(win); + elm_button_label_set(bt, "Vertical"); + evas_object_smart_callback_add(bt, "clicked", click_through, NULL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + } + /* } */ + + /* { */ + sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(sc, EVAS_HINT_FILL, 0.5); + elm_scroller_bounce_set(sc, 1, 0); + elm_scroller_content_min_limit(sc, 0, 1); + elm_box_pack_end(bx, sc); + evas_object_show(sc); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + + for (i = 0; i < 10; i++) + { + bt = elm_button_add(win); + elm_button_label_set(bt, "... Horizontal scrolling ..."); + evas_object_smart_callback_add(bt, "clicked", click_through, NULL); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + } + + elm_scroller_content_set(sc, bx2); + evas_object_show(bx2); + /* } */ + + /* { */ + for (i = 0; i < 3; i++) + { + bt = elm_button_add(win); + elm_button_label_set(bt, "Vertical"); + evas_object_smart_callback_add(bt, "clicked", click_through, NULL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + } + /* } */ + + /* { */ + tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + rc = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_size_hint_min_set(rc, 200, 120); + elm_table_pack(tb, rc, 0, 0, 1, 1); + + sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(sc, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, sc, 0, 0, 1, 1); + evas_object_show(sc); + + tb2 = elm_table_add(win); + + for (j = 0; j < 16; j++) + { + for (i = 0; i < 16; i++) + { + bt = elm_button_add(win); + elm_button_label_set(bt, "Both"); + evas_object_smart_callback_add(bt, "clicked", click_through, NULL); + elm_table_pack(tb2, bt, i, j, 1, 1); + evas_object_show(bt); + } + } + + elm_scroller_content_set(sc, tb2); + evas_object_show(tb2); + /* } */ + + for (i = 0; i < 24; i++) + { + bt = elm_button_add(win); + elm_button_label_set(bt, "Vertical"); + evas_object_smart_callback_add(bt, "clicked", click_through, NULL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, 0.5); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + } + + sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_scroller_bounce_set(sc, 0, 1); + elm_win_resize_object_add(win, sc); + elm_scroller_content_set(sc, bx); + evas_object_show(bx); + evas_object_show(sc); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_separator.c b/src/bin/test_separator.c new file mode 100644 index 0000000..4a5f0e9 --- /dev/null +++ b/src/bin/test_separator.c @@ -0,0 +1,74 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_separator(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx0, *bx, *bt, *sp; + + win = elm_win_add(NULL, "separators", ELM_WIN_BASIC); + elm_win_title_set(win, "Separators"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx0 = elm_box_add(win); + evas_object_size_hint_weight_set(bx0, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_horizontal_set(bx0, 1); + elm_win_resize_object_add(win, bx0); + evas_object_show(bx0); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx0, bx); + evas_object_show(bx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Left upper corner"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); // by default, separator is vertical, we must set it horizontal + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Left lower corner"); + elm_object_disabled_set(bt, 1); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + sp = elm_separator_add(win); // now we need vertical separator + elm_box_pack_end(bx0, sp); + evas_object_show(sp); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx0, bx); + evas_object_show(bx); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Right upper corner"); + elm_object_disabled_set(bt, 1); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + sp = elm_separator_add(win); + elm_separator_horizontal_set(sp, 1); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Right lower corner"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_slider.c b/src/bin/test_slider.c new file mode 100644 index 0000000..6488cda --- /dev/null +++ b/src/bin/test_slider.c @@ -0,0 +1,199 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +void +_change_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + double val = elm_slider_value_get(obj); + elm_slider_value_set(data, val); +} + +void +test_slider(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *sl, *ic, *sl1, *bx2; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "slider", ELM_WIN_BASIC); + elm_win_title_set(win, "Slider"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + + sl = elm_slider_add(win); + sl1 = sl; + elm_slider_label_set(sl, "Horizontal"); + elm_slider_icon_set(sl, ic); + elm_slider_unit_format_set(sl, "%1.1f units"); + elm_slider_span_size_set(sl, 120); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, sl); + evas_object_show(ic); + evas_object_show(sl); + + /* horizontal disable state */ + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + + sl = elm_slider_add(win); + elm_slider_label_set(sl, "Disabled"); + elm_slider_icon_set(sl, ic); + elm_slider_unit_format_set(sl, "%1.1f units"); + elm_slider_span_size_set(sl, 120); + elm_slider_min_max_set(sl, 50, 150); + elm_slider_value_set(sl, 80); + elm_object_disabled_set(sl, EINA_TRUE); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, sl); + evas_object_show(ic); + evas_object_show(sl); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + + sl = elm_slider_add(win); + elm_slider_label_set(sl, "Horizontal inverted"); + elm_slider_end_set(sl, ic); + elm_slider_span_size_set(sl, 80); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_slider_indicator_format_set(sl, "%3.0f"); + elm_slider_min_max_set(sl, 50, 150); + elm_slider_value_set(sl, 80); + elm_slider_inverted_set(sl, EINA_TRUE); + evas_object_size_hint_align_set(sl, 0.5, 0.5); + evas_object_size_hint_weight_set(sl, 0.0, 0.0); + elm_box_pack_end(bx, sl); + evas_object_show(ic); + evas_object_show(sl); + + /* label2 disable */ + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + + sl = elm_slider_add(win); + elm_slider_label_set(sl, "Disabled inverted"); + elm_slider_end_set(sl, ic); + elm_slider_span_size_set(sl, 80); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_slider_indicator_format_set(sl, "%3.0f"); + elm_slider_min_max_set(sl, 50, 150); + elm_slider_value_set(sl, 80); + elm_slider_inverted_set(sl, EINA_TRUE); + elm_object_disabled_set(sl, EINA_TRUE); + evas_object_size_hint_align_set(sl, 0.5, 0.5); + evas_object_size_hint_weight_set(sl, 0.0, 0.0); + elm_box_pack_end(bx, sl); + evas_object_show(ic); + evas_object_show(sl); + + sl = elm_slider_add(win); + elm_slider_indicator_show_set(sl, EINA_FALSE); + elm_slider_label_set(sl, "Scale doubled"); + elm_slider_unit_format_set(sl, "%3.0f units"); + elm_slider_span_size_set(sl, 40); + evas_object_size_hint_align_set(sl, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_slider_indicator_format_set(sl, "%3.0f"); + elm_slider_min_max_set(sl, 50, 150); + elm_slider_value_set(sl, 80); + elm_slider_inverted_set(sl, EINA_TRUE); + elm_object_scale_set(sl, 2.0); + elm_box_pack_end(bx, sl); + evas_object_show(ic); + evas_object_show(sl); + + bx2 = elm_box_add(win); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_horizontal_set(bx2, EINA_TRUE); + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_HORIZONTAL, 1, 1); + + sl = elm_slider_add(win); + elm_slider_icon_set(sl, ic); + elm_slider_label_set(sl, "Vertical inverted"); + elm_slider_inverted_set(sl, EINA_TRUE); + elm_slider_unit_format_set(sl, "units"); + elm_slider_span_size_set(sl, 60); + evas_object_size_hint_align_set(sl, 0.5, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(sl, 0.0, EVAS_HINT_EXPAND); + elm_slider_indicator_format_set(sl, "%1.1f"); + elm_slider_value_set(sl, 0.2); + elm_object_scale_set(sl, 1.0); + elm_slider_horizontal_set(sl, 0); + elm_box_pack_end(bx2, sl); + evas_object_show(ic); + evas_object_show(sl); + + evas_object_smart_callback_add(sl1, "changed", _change_cb, sl); + + sl = elm_slider_add(win); + elm_slider_label_set(sl, "Vertical"); + elm_slider_unit_format_set(sl, "units"); + elm_slider_span_size_set(sl, 60); + evas_object_size_hint_align_set(sl, 0.5, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(sl, 0.0, EVAS_HINT_EXPAND); + elm_slider_indicator_format_set(sl, "%1.1f"); + elm_slider_value_set(sl, 0.2); + elm_object_scale_set(sl, 1.0); + elm_slider_horizontal_set(sl, EINA_FALSE); + elm_box_pack_end(bx2, sl); + evas_object_show(ic); + evas_object_show(sl); + + /* vertical disable state */ + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_HORIZONTAL, 1, 1); + + sl = elm_slider_add(win); + elm_slider_icon_set(sl, ic); + elm_slider_label_set(sl, "Disabled vertical"); + elm_slider_inverted_set(sl, EINA_TRUE); + elm_slider_unit_format_set(sl, "units"); + elm_slider_span_size_set(sl, 100); + evas_object_size_hint_align_set(sl, 0.5, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(sl, 0.0, EVAS_HINT_EXPAND); + elm_slider_indicator_format_set(sl, "%1.1f"); + elm_slider_value_set(sl, 0.2); + elm_object_scale_set(sl, 1.0); + elm_slider_horizontal_set(sl, 0); + elm_object_disabled_set(sl, EINA_TRUE); + elm_box_pack_end(bx2, sl); + evas_object_show(ic); + evas_object_show(sl); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_slideshow.c b/src/bin/test_slideshow.c new file mode 100644 index 0000000..f337bfc --- /dev/null +++ b/src/bin/test_slideshow.c @@ -0,0 +1,215 @@ +#include +#include +#ifndef ELM_LIB_QUICKLAUNCH + +static Evas_Object *slideshow, *bt_start, *bt_stop; +static Elm_Slideshow_Item_Class itc; +static const char *img1 = PACKAGE_DATA_DIR"/images/logo.png"; +static const char *img2 = PACKAGE_DATA_DIR"/images/plant_01.jpg"; +static const char *img3 = PACKAGE_DATA_DIR"/images/rock_01.jpg"; +static const char *img4 = PACKAGE_DATA_DIR"/images/rock_02.jpg"; +static const char *img5 = PACKAGE_DATA_DIR"/images/sky_01.jpg"; +static const char *img6 = PACKAGE_DATA_DIR"/images/sky_04.jpg"; +static const char *img7 = PACKAGE_DATA_DIR"/images/wood_01.jpg"; +static const char *img8 = PACKAGE_DATA_DIR"/images/mystrale.jpg"; +static const char *img9 = PACKAGE_DATA_DIR"/images/mystrale_2.jpg"; + +static void +_notify_show(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_show(data); +} + +static void +_next(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_slideshow_next(data); +} + +static void +_previous(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_slideshow_previous(data); +} + +static void +_mouse_in(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_notify_timeout_set(data, 0.0); + evas_object_show(data); +} + + +static void +_mouse_out(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_notify_timeout_set(data, 3.0); +} + +static void +_hv_select(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + elm_slideshow_transition_set(slideshow, data); + elm_hoversel_label_set(obj, data); +} + +static void +_layout_select(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + elm_slideshow_layout_set(slideshow, data); + elm_hoversel_label_set(obj, data); +} + +static void +_start(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_slideshow_timeout_set(slideshow, elm_spinner_value_get(data)); + + elm_object_disabled_set(bt_start, EINA_TRUE); + elm_object_disabled_set(bt_stop, EINA_FALSE); +} + +static void +_stop(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_slideshow_timeout_set(slideshow, 0.0); + elm_object_disabled_set(bt_start, EINA_FALSE); + elm_object_disabled_set(bt_stop, EINA_TRUE); +} + +static void +_spin(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + if (elm_slideshow_timeout_get(slideshow) > 0) + elm_slideshow_timeout_set(slideshow, elm_spinner_value_get(data)); +} + +static Evas_Object * +_get(void *data, Evas_Object *obj) +{ + //Evas_Object *photo = elm_photocam_add(obj); + //elm_photocam_file_set(photo, data); + //elm_photocam_zoom_mode_set(photo, ELM_PHOTOCAM_ZOOM_MODE_AUTO_FIT); + + Evas_Object *photo = elm_photo_add(obj); + elm_photo_file_set(photo, data); + elm_photo_fill_inside_set(photo, EINA_TRUE); + elm_object_style_set(photo, "shadow"); + + return photo; +} + + + +void +test_slideshow(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *notify, *bx, *bt, *hv, *spin; + const Eina_List *l; + const char *transition, *layout; + + win = elm_win_add(NULL, "Slideshow", ELM_WIN_BASIC); + elm_win_title_set(win, "Slideshow"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + slideshow = elm_slideshow_add(win); + elm_slideshow_loop_set(slideshow, EINA_TRUE); + elm_win_resize_object_add(win, slideshow); + evas_object_size_hint_weight_set(slideshow, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(slideshow); + + itc.func.get = _get; + itc.func.del = NULL; + + elm_slideshow_item_add(slideshow, &itc, img1); + elm_slideshow_item_add(slideshow, &itc, img2); + elm_slideshow_item_add(slideshow, &itc, img3); + elm_slideshow_item_add(slideshow, &itc, img4); + elm_slideshow_item_add(slideshow, &itc, img9); + elm_slideshow_item_add(slideshow, &itc, img5); + elm_slideshow_item_add(slideshow, &itc, img6); + elm_slideshow_item_add(slideshow, &itc, img7); + elm_slideshow_item_add(slideshow, &itc, img8); + + notify = elm_notify_add(win); + elm_notify_orient_set(notify, ELM_NOTIFY_ORIENT_BOTTOM); + elm_win_resize_object_add(win, notify); + elm_notify_timeout_set(notify, 3.0); + + bx = elm_box_add(win); + elm_box_horizontal_set(bx, EINA_TRUE); + elm_notify_content_set(notify, bx); + evas_object_show(bx); + + evas_object_event_callback_add(bx, EVAS_CALLBACK_MOUSE_IN, _mouse_in, + notify); + evas_object_event_callback_add(bx, EVAS_CALLBACK_MOUSE_OUT, _mouse_out, + notify); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Previous"); + evas_object_smart_callback_add(bt, "clicked", _previous, slideshow); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Next"); + evas_object_smart_callback_add(bt, "clicked", _next, slideshow); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + hv = elm_hoversel_add(win); + elm_box_pack_end(bx, hv); + elm_hoversel_hover_parent_set(hv, win); + EINA_LIST_FOREACH(elm_slideshow_transitions_get(slideshow), l, transition) + elm_hoversel_item_add(hv, transition, NULL, 0, _hv_select, transition); + elm_hoversel_label_set(hv, eina_list_data_get(elm_slideshow_transitions_get(slideshow))); + evas_object_show(hv); + + hv = elm_hoversel_add(win); + elm_box_pack_end(bx, hv); + elm_hoversel_hover_parent_set(hv, win); + EINA_LIST_FOREACH(elm_slideshow_layouts_get(slideshow), l, layout) + elm_hoversel_item_add(hv, layout, NULL, 0, _layout_select, layout); + elm_hoversel_label_set(hv, elm_slideshow_layout_get(slideshow)); + evas_object_show(hv); + + spin = elm_spinner_add(win); + elm_spinner_label_format_set(spin, "%2.0f secs."); + evas_object_smart_callback_add(spin, "changed", _spin, spin); + elm_spinner_step_set(spin, 1); + elm_spinner_min_max_set(spin, 1, 30); + elm_spinner_value_set(spin, 3); + elm_box_pack_end(bx, spin); + evas_object_show(spin); + + bt = elm_button_add(win); + bt_start = bt; + elm_button_label_set(bt, "Start"); + evas_object_smart_callback_add(bt, "clicked", _start, spin); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + bt_stop = bt; + elm_button_label_set(bt, "Stop"); + evas_object_smart_callback_add(bt, "clicked", _stop, spin); + elm_box_pack_end(bx, bt); + elm_object_disabled_set(bt, EINA_TRUE); + evas_object_show(bt); + + evas_object_event_callback_add(slideshow, EVAS_CALLBACK_MOUSE_UP, + _notify_show, notify); + evas_object_event_callback_add(slideshow, EVAS_CALLBACK_MOUSE_MOVE, + _notify_show, notify); + + evas_object_resize(win, 500, 400); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_spinner.c b/src/bin/test_spinner.c new file mode 100644 index 0000000..39027ed --- /dev/null +++ b/src/bin/test_spinner.c @@ -0,0 +1,89 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_spinner(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *sp; + + win = elm_win_add(NULL, "spinner", ELM_WIN_BASIC); + elm_win_title_set(win, "Spinner"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + sp = elm_spinner_add(win); + elm_spinner_label_format_set(sp, "%1.1f units"); + elm_spinner_step_set(sp, 1.3); + elm_spinner_wrap_set(sp, 1); + elm_spinner_min_max_set(sp, -50.0, 250.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + sp = elm_spinner_add(win); + elm_spinner_label_format_set(sp, "Percentage %%%1.2f something"); + elm_spinner_step_set(sp, 5.0); + elm_spinner_wrap_set(sp, 1); + elm_spinner_min_max_set(sp, 0.0, 100.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + sp = elm_spinner_add(win); + elm_spinner_label_format_set(sp, "%1.1f units"); + elm_spinner_step_set(sp, 1.3); + elm_spinner_wrap_set(sp, 1); + elm_object_style_set (sp, "vertical"); + elm_spinner_min_max_set(sp, -50.0, 250.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + sp = elm_spinner_add(win); + elm_spinner_label_format_set(sp, "Disabled %.0f"); + elm_object_disabled_set(sp, 1); + elm_spinner_min_max_set(sp, -50.0, 250.0); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + sp = elm_spinner_add(win); + elm_spinner_min_max_set(sp, 1, 12); + elm_spinner_label_format_set(sp, "%.0f"); + elm_spinner_step_set(sp, 1.0); + elm_spinner_editable_set(sp, EINA_FALSE); + elm_spinner_special_value_add(sp, 1, "January"); + elm_spinner_special_value_add(sp, 2, "February"); + elm_spinner_special_value_add(sp, 3, "March"); + elm_spinner_special_value_add(sp, 4, "April"); + elm_spinner_special_value_add(sp, 5, "May"); + elm_spinner_special_value_add(sp, 6, "June"); + elm_spinner_special_value_add(sp, 7, "July"); + elm_spinner_special_value_add(sp, 8, "August"); + elm_spinner_special_value_add(sp, 9, "September"); + elm_spinner_special_value_add(sp, 10, "October"); + elm_spinner_special_value_add(sp, 11, "November"); + elm_spinner_special_value_add(sp, 12, "December"); + evas_object_size_hint_align_set(sp, EVAS_HINT_FILL, 0.5); + evas_object_size_hint_weight_set(sp, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, sp); + evas_object_show(sp); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_store.c b/src/bin/test_store.c new file mode 100644 index 0000000..64ce49d --- /dev/null +++ b/src/bin/test_store.c @@ -0,0 +1,268 @@ +#include + +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +typedef struct _My_Item My_Item; + +struct _My_Item +{ + char *from, *subject, *date, *head_content; +}; + +// callbacks just to see user interacting with genlist +static void +_st_selected(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("selected: %p\n", event_info); +} + +static void +_st_clicked(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("clicked: %p\n", event_info); +} + +static void +_st_longpress(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + printf("longpress %p\n", event_info); +} + +// store callbacks to handle loading/parsing/freeing of store items from src +static Elm_Genlist_Item_Class itc1 = +{ + "message", { NULL, NULL, NULL, NULL } +}; + +static const Elm_Store_Item_Mapping it1_mapping[] = +{ + { + ELM_STORE_ITEM_MAPPING_LABEL, + "elm.title.1", ELM_STORE_ITEM_MAPPING_OFFSET(My_Item, from), + { .empty = { + EINA_TRUE + } } }, + { + ELM_STORE_ITEM_MAPPING_LABEL, + "elm.title.2", ELM_STORE_ITEM_MAPPING_OFFSET(My_Item, subject), + { .empty = { + EINA_TRUE + } } }, + { + ELM_STORE_ITEM_MAPPING_LABEL, + "elm.text", ELM_STORE_ITEM_MAPPING_OFFSET(My_Item, head_content), + { .empty = { + EINA_TRUE + } } }, + { + ELM_STORE_ITEM_MAPPING_ICON, + "elm.swallow.icon", 0, + { .icon = { + 48, 48, + ELM_ICON_LOOKUP_THEME_FDO, + EINA_TRUE, EINA_FALSE, + EINA_TRUE, + EINA_FALSE, EINA_FALSE, + } } }, + { + ELM_STORE_ITEM_MAPPING_CUSTOM, + "elm.swallow.end", 0, + { .custom = { + NULL + } } }, + ELM_STORE_ITEM_MAPPING_END +}; + + +////// **** WARNING *********************************************************** +//// * This function runs inside a thread outside efl mainloop. Be careful! * +// ************************************************************************ +static Eina_Bool +_st_store_list(void *data __UNUSED__, Elm_Store_Item_Info *item_info) +{ + Elm_Store_Item_Info_Filesystem *info = (Elm_Store_Item_Info_Filesystem *)item_info; + int id; + char sort_id[7]; + + // create a sort id based on the filename itself assuming it is a numeric + // value like the id number in mh mail folders which is what this test + // uses as a data source + char *file = strrchr(info->path, '/'); + if (file) file++; + else file = info->path; + id = atoi(file); + sort_id[0] = ((id >> 30) & 0x3f) + 32; + sort_id[1] = ((id >> 24) & 0x3f) + 32; + sort_id[2] = ((id >> 18) & 0x3f) + 32; + sort_id[3] = ((id >> 12) & 0x3f) + 32; + sort_id[4] = ((id >> 6) & 0x3f) + 32; + sort_id[5] = ((id >> 0) & 0x3f) + 32; + sort_id[6] = 0; + info->base.sort_id = strdup(sort_id); + // choose the item genlist item class to use (only item style should be + // provided by the app, store will fill everything else in, so it also + // has to be writable + info->base.item_class = &itc1; // based on item info - return the item class wanted (only style field used - rest reset to internal funcs store sets up to get label/icon etc) + info->base.mapping = it1_mapping; + info->base.data = NULL; // if we can already parse and load all of item here and want to - set this + return EINA_TRUE; // return true to include this, false not to +} +// ************************************************************************ +//// * End of separate thread function. * +////// ************************************************************************ + +////// **** WARNING *********************************************************** +//// * This function runs inside a thread outside efl mainloop. Be careful! * +// ************************************************************************ +static void +_st_store_fetch(void *data __UNUSED__, Elm_Store_Item *sti) +{ + const char *path = elm_store_item_filesystem_path_get(sti); + My_Item *myit; + FILE *f; + char buf[4096], *p; + Eina_Bool have_content = EINA_FALSE; + char *content = NULL, *content_pos = NULL, *content_end = NULL; + + // if we already have my item data - skip + if (elm_store_item_data_get(sti)) return; + // open the mail file and parse it + f = fopen(path, "r"); + if (!f) return; + + // alloc my item in memory that holds data to show in the list + myit = calloc(1, sizeof(My_Item)); + if (!myit) + { + fclose(f); + return; + } + while (fgets(buf, sizeof(buf), f)) + { + if (!have_content) + { + if (!isblank(buf[0])) + { + // get key: From:, Subject: etc. + if (!strncmp(buf, "From:", 5)) + { + p = buf + 5; + while ((*p) && (isblank(*p))) p++; + p = strdup(p); + if (p) + { + myit->from = p; + p = strchr(p, '\n'); + if (p) *p = 0; + } + } + else if (!strncmp(buf, "Subject:", 8)) + { + p = buf + 8; + while ((*p) && (isblank(*p))) p++; + p = strdup(p); + if (p) + { + myit->subject = p; + p = strchr(p, '\n'); + if (p) *p = 0; + } + } + else if (!strncmp(buf, "Date:", 5)) + { + p = buf + 5; + while ((*p) && (isblank(*p))) p++; + p = strdup(p); + if (p) + { + myit->date = p; + p = strchr(p, '\n'); + if (p) *p = 0; + } + } + else if (buf[0] == '\n') // begin of content + have_content = EINA_TRUE; + } + } + else + { + // get first 320 bytes of content/body + if (!content) + { + content = calloc(1, 320); + content_pos = content; + content_end = content + 319; + } + strncat(content_pos, buf, content_end - content_pos - 1); + content_pos = content + strlen(content); + } + } + fclose(f); + myit->head_content = elm_entry_utf8_to_markup(content); + free(content); + elm_store_item_data_set(sti, myit); +} +// ************************************************************************ +//// * End of separate thread function. * +////// ************************************************************************ + +static void +_st_store_unfetch(void *data __UNUSED__, Elm_Store_Item *sti) +{ + My_Item *myit = elm_store_item_data_get(sti); + if (!myit) return; + if (myit->from) free(myit->from); + if (myit->subject) free(myit->subject); + if (myit->date) free(myit->date); + if (myit->head_content) free(myit->head_content); + free(myit); + elm_store_item_data_set(sti, NULL); +} + +void +test_store(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *gl, *bx; + + Elm_Store *st; + + win = elm_win_add(NULL, "store", ELM_WIN_BASIC); + elm_win_title_set(win, "Store"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + gl = elm_genlist_add(win); + elm_genlist_height_for_width_mode_set(gl, EINA_TRUE); + evas_object_smart_callback_add(gl, "selected", _st_selected, NULL); + evas_object_smart_callback_add(gl, "clicked", _st_clicked, NULL); + evas_object_smart_callback_add(gl, "longpressed", _st_longpress, NULL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, gl); + evas_object_show(gl); + + st = elm_store_filesystem_new(); + elm_store_list_func_set(st, _st_store_list, NULL); + elm_store_fetch_func_set(st, _st_store_fetch, NULL); + //elm_store_fetch_thread_set(st, EINA_FALSE); + elm_store_unfetch_func_set(st, _st_store_unfetch, NULL); + elm_store_sorted_set(st, EINA_TRUE); + elm_store_target_genlist_set(st, gl); + elm_store_filesystem_directory_set(st, "./store"); + + evas_object_resize(win, 480, 800); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_table.c b/src/bin/test_table.c new file mode 100644 index 0000000..dd0bb99 --- /dev/null +++ b/src/bin/test_table.c @@ -0,0 +1,69 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_table(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *tb, *bt; + + win = elm_win_add(NULL, "table", ELM_WIN_BASIC); + elm_win_title_set(win, "Table"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + tb = elm_table_add(win); + elm_win_resize_object_add(win, tb); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(tb); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 1"); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, bt, 0, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 2"); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, bt, 1, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 3"); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, bt, 2, 0, 1, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 4"); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, bt, 0, 1, 2, 1); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 5"); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, bt, 2, 1, 1, 3); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button 6"); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_table_pack(tb, bt, 0, 2, 2, 2); + evas_object_show(bt); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_thumb.c b/src/bin/test_thumb.c new file mode 100644 index 0000000..b6f2f9d --- /dev/null +++ b/src/bin/test_thumb.c @@ -0,0 +1,70 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_thumb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *sc, *tb, *th; + int i, j, n; + char buf[PATH_MAX]; + const char *img[9] = + { + "panel_01.jpg", + "plant_01.jpg", + "rock_01.jpg", + "rock_02.jpg", + "sky_01.jpg", + "sky_02.jpg", + "sky_03.jpg", + "sky_04.jpg", + "wood_01.jpg", + }; + + elm_need_ethumb(); + + win = elm_win_add(NULL, "thumb", ELM_WIN_BASIC); + elm_win_title_set(win, "Thumb"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + n = 0; + for (j = 0; j < 12; j++) + { + for (i = 0; i < 12; i++) + { + th = elm_thumb_add(win); + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, + img[n]); + n = (n + 1) % 9; + elm_thumb_file_set(th, buf, img[n]); + evas_object_size_hint_weight_set(th, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(th, EVAS_HINT_FILL, + EVAS_HINT_FILL); + elm_table_pack(tb, th, i, j, 1, 1); + elm_thumb_editable_set(th, EINA_TRUE); + evas_object_show(th); + } + } + + sc = elm_scroller_add(win); + evas_object_size_hint_weight_set(sc, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, sc); + + elm_scroller_content_set(sc, tb); + evas_object_show(tb); + evas_object_show(sc); + + evas_object_resize(win, 600, 600); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_toggle.c b/src/bin/test_toggle.c new file mode 100644 index 0000000..e8046f1 --- /dev/null +++ b/src/bin/test_toggle.c @@ -0,0 +1,87 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +void +test_toggle(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *ic, *tg; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "toggles", ELM_WIN_BASIC); + elm_win_title_set(win, "Toggles"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + + tg = elm_toggle_add(win); + evas_object_size_hint_weight_set(tg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(tg, EVAS_HINT_FILL, 0.5); + elm_toggle_label_set(tg, "Icon sized to toggle"); + elm_toggle_icon_set(tg, ic); + elm_toggle_state_set(tg, 1); + elm_toggle_states_labels_set(tg, "Yes", "No"); + elm_box_pack_end(bx, tg); + evas_object_show(tg); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + + tg = elm_toggle_add(win); + elm_toggle_label_set(tg, "Icon no scale"); + elm_toggle_icon_set(tg, ic); + elm_box_pack_end(bx, tg); + evas_object_show(tg); + evas_object_show(ic); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + + tg = elm_toggle_add(win); + elm_toggle_label_set(tg, "Icon no scale"); + elm_toggle_icon_set(tg, ic); + elm_object_disabled_set(tg, 1); + elm_box_pack_end(bx, tg); + evas_object_show(tg); + evas_object_show(ic); + + tg = elm_toggle_add(win); + elm_toggle_label_set(tg, "Label Only"); + elm_toggle_states_labels_set(tg, "Big long fun times label", + "Small long happy fun label"); + elm_box_pack_end(bx, tg); + evas_object_show(tg); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + + tg = elm_toggle_add(win); + elm_toggle_icon_set(tg, ic); + elm_box_pack_end(bx, tg); + evas_object_show(tg); + evas_object_show(ic); + + evas_object_show(win); +} +#endif diff --git a/src/bin/test_toolbar.c b/src/bin/test_toolbar.c new file mode 100644 index 0000000..ca46fa4 --- /dev/null +++ b/src/bin/test_toolbar.c @@ -0,0 +1,618 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +static void +tb_1(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), "%s/images/panel_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(data, buf); +} + +static void +tb_2(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), "%s/images/rock_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(data, buf); +} + +static void +tb_3(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), "%s/images/wood_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(data, buf); +} + +static void +tb_3a(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + tb_3(data, obj, event_info); + elm_toolbar_item_state_set(event_info, elm_toolbar_item_state_next(event_info)); +} + +static void +tb_3b(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + tb_3(data, obj, event_info); + elm_toolbar_item_state_unset(event_info); +} + +static void +tb_4(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), "%s/images/sky_03.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(data, buf); +} + +static void +tb_4a(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_toolbar_item_state_set(event_info, elm_toolbar_item_state_prev(event_info)); +} + +static void +tb_5(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_photo_file_set(data, NULL); +} + +void +test_toolbar(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *tb, *ph, *menu; + Evas_Object *ph1, *ph2, *ph3, *ph4; + Elm_Toolbar_Item *item; + Elm_Menu_Item *menu_item; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "toolbar", ELM_WIN_BASIC); + elm_win_title_set(win, "Toolbar"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + tb = elm_toolbar_add(win); + elm_toolbar_homogenous_set(tb, 0); + elm_toolbar_mode_shrink_set(tb, ELM_TOOLBAR_SHRINK_MENU); + evas_object_size_hint_weight_set(tb, 0.0, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, 0.0); + + ph1 = elm_photo_add(win); + ph2 = elm_photo_add(win); + ph3 = elm_photo_add(win); + ph4 = elm_photo_add(win); + + item = elm_toolbar_item_append(tb, "document-print", "Hello", tb_1, ph1); + elm_toolbar_item_disabled_set(item, EINA_TRUE); + elm_toolbar_item_priority_set(item, 100); + + item = elm_toolbar_item_append(tb, "folder-new", "World", tb_2, ph1); + elm_toolbar_item_priority_set(item, -100); + + item = elm_toolbar_item_append(tb, "object-rotate-right", "H", tb_3, ph4); + elm_toolbar_item_priority_set(item, 150); + + item = elm_toolbar_item_append(tb, "mail-send", "Comes", tb_4, ph4); + elm_toolbar_item_priority_set(item, 0); + + item = elm_toolbar_item_append(tb, "clock", "Elementary", tb_5, ph4); + elm_toolbar_item_priority_set(item, -200); + + item = elm_toolbar_item_append(tb, "refresh", "Menu", NULL, NULL); + elm_toolbar_item_menu_set(item, 1); + elm_toolbar_item_priority_set(item, -999999); + elm_toolbar_menu_parent_set(tb, win); + menu = elm_toolbar_item_menu_get(item); + + elm_menu_item_add(menu, NULL, "edit-cut", "Shrink", tb_3, ph4); + menu_item = elm_menu_item_add(menu, NULL, "edit-copy", "Mode", tb_4, ph4); + elm_menu_item_add(menu, menu_item, "edit-paste", "is set to", tb_4, ph4); + elm_menu_item_add(menu, NULL, "edit-delete", "Menu", tb_5, ph4); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + tb = elm_table_add(win); + //elm_table_homogenous_set(tb, 1); + evas_object_size_hint_weight_set(tb, 0.0, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + ph = ph1; + elm_photo_size_set(ph, 40); + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 0, 1, 1); + evas_object_show(ph); + + ph = ph2; + elm_photo_size_set(ph, 80); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 0, 1, 1); + evas_object_show(ph); + + ph = ph3; + elm_photo_size_set(ph, 20); + snprintf(buf, sizeof(buf), "%s/images/sky_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 1, 1, 1); + evas_object_show(ph); + + ph = ph4; + elm_photo_size_set(ph, 60); + snprintf(buf, sizeof(buf), "%s/images/sky_02.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 1, 1, 1); + evas_object_show(ph); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + evas_object_resize(win, 320, 300); + evas_object_show(win); +} + +void +test_toolbar2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *tb, *ph, *menu; + Evas_Object *ph1, *ph2, *ph3, *ph4; + Elm_Toolbar_Item *item; + Elm_Menu_Item *menu_item; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "toolbar", ELM_WIN_BASIC); + elm_win_title_set(win, "Toolbar"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + tb = elm_toolbar_add(win); + elm_toolbar_homogenous_set(tb, 0); + elm_toolbar_mode_shrink_set(tb, ELM_TOOLBAR_SHRINK_SCROLL); + evas_object_size_hint_weight_set(tb, 0.0, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, 0.0); + + ph1 = elm_photo_add(win); + ph2 = elm_photo_add(win); + ph3 = elm_photo_add(win); + ph4 = elm_photo_add(win); + + item = elm_toolbar_item_append(tb, "document-print", "Hello", tb_1, ph1); + elm_toolbar_item_disabled_set(item, EINA_TRUE); + elm_toolbar_item_priority_set(item, -100); + + item = elm_toolbar_item_append(tb, "folder-new", "World", tb_2, ph1); + elm_toolbar_item_priority_set(item, 100); + + item = elm_toolbar_item_append(tb, "object-rotate-right", "H", tb_3, ph4); + elm_toolbar_item_priority_set(item, -150); + + item = elm_toolbar_item_append(tb, "mail-send", "Comes", tb_4, ph4); + elm_toolbar_item_priority_set(item, -200); + + item = elm_toolbar_item_append(tb, "clock", "Elementary", tb_5, ph4); + elm_toolbar_item_priority_set(item, 0); + + item = elm_toolbar_item_append(tb, "refresh", "Menu", NULL, NULL); + elm_toolbar_item_menu_set(item, 1); + elm_toolbar_item_priority_set(item, -999999); + elm_toolbar_menu_parent_set(tb, win); + menu = elm_toolbar_item_menu_get(item); + + elm_menu_item_add(menu, NULL, "edit-cut", "Shrink", tb_3, ph4); + menu_item = elm_menu_item_add(menu, NULL, "edit-copy", "Mode", tb_4, ph4); + elm_menu_item_add(menu, menu_item, "edit-paste", "is set to", tb_4, ph4); + elm_menu_item_add(menu, NULL, "edit-delete", "Scroll", tb_5, ph4); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + tb = elm_table_add(win); + //elm_table_homogenous_set(tb, 1); + evas_object_size_hint_weight_set(tb, 0.0, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + ph = ph1; + elm_photo_size_set(ph, 40); + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 0, 1, 1); + evas_object_show(ph); + + ph = ph2; + elm_photo_size_set(ph, 80); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 0, 1, 1); + evas_object_show(ph); + + ph = ph3; + elm_photo_size_set(ph, 20); + snprintf(buf, sizeof(buf), "%s/images/sky_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 1, 1, 1); + evas_object_show(ph); + + ph = ph4; + elm_photo_size_set(ph, 60); + snprintf(buf, sizeof(buf), "%s/images/sky_02.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 1, 1, 1); + evas_object_show(ph); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + evas_object_resize(win, 320, 300); + evas_object_show(win); +} + +void +test_toolbar3(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *tb, *ph, *menu; + Evas_Object *ph1, *ph2, *ph3, *ph4; + Elm_Toolbar_Item *item; + Elm_Menu_Item *menu_item; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "toolbar", ELM_WIN_BASIC); + elm_win_title_set(win, "Toolbar"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + tb = elm_toolbar_add(win); + elm_toolbar_homogenous_set(tb, 0); + elm_toolbar_mode_shrink_set(tb, ELM_TOOLBAR_SHRINK_NONE); + evas_object_size_hint_weight_set(tb, 0.0, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, 0.0); + + ph1 = elm_photo_add(win); + ph2 = elm_photo_add(win); + ph3 = elm_photo_add(win); + ph4 = elm_photo_add(win); + + item = elm_toolbar_item_append(tb, "document-print", "Hello", tb_1, ph1); + elm_toolbar_item_disabled_set(item, EINA_TRUE); + elm_toolbar_item_priority_set(item, 0); + + item = elm_toolbar_item_append(tb, "folder-new", "World", tb_2, ph1); + elm_toolbar_item_priority_set(item, -200); + + item = elm_toolbar_item_append(tb, "object-rotate-right", "H", tb_3, ph4); + elm_toolbar_item_priority_set(item, 1); + + item = elm_toolbar_item_append(tb, "mail-send", "Comes", tb_4, ph4); + elm_toolbar_item_priority_set(item, -10); + + item = elm_toolbar_item_append(tb, "clock", "Elementary", tb_5, ph4); + elm_toolbar_item_priority_set(item, 50); + + item = elm_toolbar_item_append(tb, "refresh", "Menu", NULL, NULL); + elm_toolbar_item_menu_set(item, 1); + elm_toolbar_item_priority_set(item, 999999); + elm_toolbar_menu_parent_set(tb, win); + menu = elm_toolbar_item_menu_get(item); + + elm_menu_item_add(menu, NULL, "edit-cut", "Shrink", tb_3, ph4); + menu_item = elm_menu_item_add(menu, NULL, "edit-copy", "Mode", tb_4, ph4); + elm_menu_item_add(menu, menu_item, "edit-paste", "is set to", tb_4, ph4); + elm_menu_item_add(menu, NULL, "edit-delete", "None", tb_5, ph4); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + tb = elm_table_add(win); + //elm_table_homogenous_set(tb, 1); + evas_object_size_hint_weight_set(tb, 0.0, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + ph = ph1; + elm_photo_size_set(ph, 40); + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 0, 1, 1); + evas_object_show(ph); + + ph = ph2; + elm_photo_size_set(ph, 80); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 0, 1, 1); + evas_object_show(ph); + + ph = ph3; + elm_photo_size_set(ph, 20); + snprintf(buf, sizeof(buf), "%s/images/sky_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 1, 1, 1); + evas_object_show(ph); + + ph = ph4; + elm_photo_size_set(ph, 60); + snprintf(buf, sizeof(buf), "%s/images/sky_02.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 1, 1, 1); + evas_object_show(ph); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + evas_object_resize(win, 320, 300); + evas_object_show(win); +} + +/* The same test of toolbar, but using hide shrink mode instead of menu */ +void +test_toolbar4(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *tb, *ph, *menu; + Evas_Object *ph1, *ph2, *ph3, *ph4; + Elm_Toolbar_Item *item; + Elm_Menu_Item *menu_item; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "toolbar", ELM_WIN_BASIC); + elm_win_title_set(win, "Toolbar 4"); + elm_win_autodel_set(win, EINA_TRUE); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + tb = elm_toolbar_add(win); + elm_toolbar_homogenous_set(tb, 0); + elm_toolbar_mode_shrink_set(tb, ELM_TOOLBAR_SHRINK_HIDE); + evas_object_size_hint_weight_set(tb, 0.0, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, 0.0); + + ph1 = elm_photo_add(win); + ph2 = elm_photo_add(win); + ph3 = elm_photo_add(win); + ph4 = elm_photo_add(win); + + item = elm_toolbar_item_append(tb, "document-print", "Hello", tb_1, ph1); + elm_toolbar_item_disabled_set(item, EINA_TRUE); + elm_toolbar_item_priority_set(item, 100); + + item = elm_toolbar_item_append(tb, "folder-new", "World", tb_2, ph1); + elm_toolbar_item_priority_set(item, -100); + + item = elm_toolbar_item_append(tb, "object-rotate-right", "H", tb_3, ph4); + elm_toolbar_item_priority_set(item, 150); + + item = elm_toolbar_item_append(tb, "mail-send", "Comes", tb_4, ph4); + elm_toolbar_item_priority_set(item, 0); + + item = elm_toolbar_item_append(tb, "clock", "Elementary", tb_5, ph4); + elm_toolbar_item_priority_set(item, -200); + + item = elm_toolbar_item_append(tb, "refresh", "Menu", NULL, NULL); + elm_toolbar_item_menu_set(item, 1); + elm_toolbar_item_priority_set(item, -999999); + elm_toolbar_menu_parent_set(tb, win); + menu = elm_toolbar_item_menu_get(item); + + elm_menu_item_add(menu, NULL, "edit-cut", "Shrink", tb_3, ph4); + menu_item = elm_menu_item_add(menu, NULL, "edit-copy", "Mode", tb_4, ph4); + elm_menu_item_add(menu, menu_item, "edit-paste", "is set to", tb_4, ph4); + elm_menu_item_add(menu, NULL, "edit-delete", "Menu", tb_5, ph4); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + tb = elm_table_add(win); + evas_object_size_hint_weight_set(tb, 0.0, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + ph = ph1; + elm_photo_size_set(ph, 40); + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 0, 1, 1); + evas_object_show(ph); + + ph = ph2; + elm_photo_size_set(ph, 80); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 0, 1, 1); + evas_object_show(ph); + + ph = ph3; + elm_photo_size_set(ph, 20); + snprintf(buf, sizeof(buf), "%s/images/sky_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 1, 1, 1); + evas_object_show(ph); + + ph = ph4; + elm_photo_size_set(ph, 60); + snprintf(buf, sizeof(buf), "%s/images/sky_02.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 1, 1, 1); + evas_object_show(ph); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + evas_object_resize(win, 320, 300); + evas_object_show(win); +} + +/* Toolbar with multiple state buttons */ +void +test_toolbar5(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *tb, *ph, *menu; + Evas_Object *ph1, *ph2, *ph3, *ph4; + Elm_Toolbar_Item *item; + Elm_Menu_Item *menu_item; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "toolbar", ELM_WIN_BASIC); + elm_win_title_set(win, "Toolbar"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + tb = elm_toolbar_add(win); + elm_toolbar_homogenous_set(tb, 0); + elm_toolbar_mode_shrink_set(tb, ELM_TOOLBAR_SHRINK_MENU); + evas_object_size_hint_weight_set(tb, 0.0, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, 0.0); + elm_toolbar_no_select_mode_set(tb, EINA_TRUE); + + ph1 = elm_photo_add(win); + ph2 = elm_photo_add(win); + ph3 = elm_photo_add(win); + ph4 = elm_photo_add(win); + + item = elm_toolbar_item_append(tb, "document-print", "Hello", tb_1, ph1); + elm_toolbar_item_disabled_set(item, EINA_TRUE); + elm_toolbar_item_priority_set(item, 100); + + item = elm_toolbar_item_append(tb, PACKAGE_DATA_DIR"/images/icon_04.png", "World", tb_2, ph1); + elm_toolbar_item_priority_set(item, -100); + + item = elm_toolbar_item_append(tb, "object-rotate-right", "H", tb_3a, ph4); + elm_toolbar_item_state_add(item, "object-rotate-left", "H2", tb_3b, ph4); + elm_toolbar_item_priority_set(item, 150); + + item = elm_toolbar_item_append(tb, "mail-send", "Comes", tb_4a, ph4); + elm_toolbar_item_state_add(item, "emptytrash", "Comes2", tb_4a, ph4); + elm_toolbar_item_state_add(item, "trashcan_full", "Comes3", tb_4a, ph4); + elm_toolbar_item_priority_set(item, 0); + + item = elm_toolbar_item_append(tb, "clock", "Elementary", tb_5, ph4); + elm_toolbar_item_priority_set(item, -200); + + item = elm_toolbar_item_append(tb, "refresh", "Menu", NULL, NULL); + elm_toolbar_item_menu_set(item, 1); + elm_toolbar_item_priority_set(item, -999999); + elm_toolbar_menu_parent_set(tb, win); + menu = elm_toolbar_item_menu_get(item); + + elm_menu_item_add(menu, NULL, "edit-cut", "Shrink", tb_3, ph4); + menu_item = elm_menu_item_add(menu, NULL, "edit-copy", "Mode", tb_4, ph4); + elm_menu_item_add(menu, menu_item, "edit-paste", "is set to", tb_4, ph4); + elm_menu_item_add(menu, NULL, "edit-delete", "Menu", tb_5, ph4); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + tb = elm_table_add(win); + //elm_table_homogenous_set(tb, 1); + evas_object_size_hint_weight_set(tb, 0.0, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + + ph = ph1; + elm_photo_size_set(ph, 40); + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 0, 1, 1); + evas_object_show(ph); + + ph = ph2; + elm_photo_size_set(ph, 80); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 0, 1, 1); + evas_object_show(ph); + + ph = ph3; + elm_photo_size_set(ph, 20); + snprintf(buf, sizeof(buf), "%s/images/sky_01.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 0, 1, 1, 1); + evas_object_show(ph); + + ph = ph4; + elm_photo_size_set(ph, 60); + snprintf(buf, sizeof(buf), "%s/images/sky_02.jpg", PACKAGE_DATA_DIR); + elm_photo_file_set(ph, buf); + evas_object_size_hint_weight_set(ph, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ph, 0.5, 0.5); + elm_table_pack(tb, ph, 1, 1, 1, 1); + evas_object_show(ph); + + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + evas_object_resize(win, 320, 300); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_tooltip.c b/src/bin/test_tooltip.c new file mode 100644 index 0000000..1dabd1a --- /dev/null +++ b/src/bin/test_tooltip.c @@ -0,0 +1,550 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +typedef struct _Testitem +{ + Elm_Gengrid_Item *item; + const char *path; + int mode; + int onoff; +} Testitem; + +static Elm_Gengrid_Item_Class gic; + +char * +grdt_lbl_get(void *data, + Evas_Object *obj __UNUSED__, + const char *part __UNUSED__) +{ + const Testitem *ti = data; + char buf[256]; + snprintf(buf, sizeof(buf), "Photo %s", ti->path); + return strdup(buf); +} + +Evas_Object * +grdt_icon_get(void *data, + Evas_Object *obj, + const char *part) +{ + const Testitem *ti = data; + if (!strcmp(part, "elm.swallow.icon")) + { + Evas_Object *icon = elm_bg_add(obj); + elm_bg_file_set(icon, ti->path, NULL); + evas_object_size_hint_aspect_set(icon, + EVAS_ASPECT_CONTROL_VERTICAL, + 1, 1); + evas_object_show(icon); + return icon; + } + return NULL; +} + +static Elm_Genlist_Item_Class itct; + +static void +gltt_exp(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = event_info; + Evas_Object *gl = elm_genlist_item_genlist_get(it); + int val = (int)(long)elm_genlist_item_data_get(it); + Elm_Genlist_Item *it1, *it2, *it3; + + val *= 10; + it1 = elm_genlist_item_append(gl, &itct, (void *)(long)(val + 1), it, + ELM_GENLIST_ITEM_NONE, NULL, NULL); + it2 = elm_genlist_item_append(gl, &itct, (void *)(long)(val + 2), it, + ELM_GENLIST_ITEM_NONE, NULL, NULL); + it3 = elm_genlist_item_append(gl, &itct, (void *)(long)(val + 3), it, + ELM_GENLIST_ITEM_SUBITEMS, NULL, NULL); + + elm_genlist_item_tooltip_text_set(it1, "Testing A"); + elm_genlist_item_tooltip_text_set(it2, "Testing B"); + elm_genlist_item_tooltip_text_set(it3, "Testing C"); +} + +static void +gltt_con(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_subitems_clear(it); +} + +static void +gltt_exp_req(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, 1); +} + +static void +gltt_con_req(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, 0); +} + +char * +gltt_label_get(void *data, + Evas_Object *obj __UNUSED__, + const char *part __UNUSED__) +{ + char buf[256]; + snprintf(buf, sizeof(buf), "Item mode %i", (int)(long)data); + return strdup(buf); +} + +static Evas_Object * +_tt_item_icon(void *data __UNUSED__, + Evas_Object *obj, + void *item __UNUSED__) +{ + Evas_Object *ic = elm_icon_add(obj); + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", + PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_resize(ic, 64, 64); + return ic; +} + +static void +_tt_item_icon_del(void *data, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + // test to check for del_cb behavior! + printf("_tt_icon_del: data=%ld (== 456?), event_info=%p\n", + (long)data, event_info); +} + +static void +_tt_text_replace(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + static int count = 0; + char buf[64]; + snprintf(buf, sizeof(buf), "count=%d", count); + count++; + elm_object_tooltip_text_set(obj, buf); +} + +static void +_tt_timer_del(void *data __UNUSED__, + Evas *e __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Ecore_Timer *timer = evas_object_data_del(obj, "test-timer"); + if (!timer) return; + ecore_timer_del(timer); +} + +static Eina_Bool +_tt_text_replace_timer_cb(void *data) +{ + _tt_text_replace(NULL, data, NULL); + return EINA_TRUE; +} + +static void +_tt_text_replace_timed(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Ecore_Timer *timer = evas_object_data_get(obj, "test-timer"); + if (timer) + { + ecore_timer_del(timer); + evas_object_data_del(obj, "test-timer"); + elm_button_label_set(obj, "Simple text tooltip, click to start" + " changed timed"); + return; + } + + timer = ecore_timer_add(1.5, _tt_text_replace_timer_cb, obj); + evas_object_data_set(obj, "test-timer", timer); + elm_button_label_set(obj, "Simple text tooltip, click to stop changed" + " timed"); +} + +static Evas_Object * +_tt_icon(void *data __UNUSED__, + Evas_Object *obj) +{ + Evas_Object *ic = elm_icon_add(obj); + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", + PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_resize(ic, 64, 64); + return ic; +} + +static Evas_Object * +_tt_icon2(void *data __UNUSED__, + Evas_Object *obj) +{ + Evas_Object *ic = elm_icon_add(obj); + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), "%s/images/icon_00.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + elm_icon_scale_set(ic, 0, 0); + evas_object_resize(ic, 64, 64); + return ic; +} + +static void +_tt_icon_del(void *data, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + // test to check for del_cb behavior! + printf("_tt_icon_del: data=%ld (== 123?), event_info=%p\n", + (long)data, event_info); +} + +static Eina_Bool +_tt_icon_replace_timer_cb(void *data) +{ + static int current = 0; + + elm_object_tooltip_content_cb_set + (data, current ? _tt_icon2 : _tt_icon, NULL, NULL); + + current = !current; + return EINA_TRUE; +} + +static void +_tt_icon_replace_timed(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Ecore_Timer *timer = evas_object_data_get(obj, "test-timer"); + if (timer) + { + ecore_timer_del(timer); + evas_object_data_del(obj, "test-timer"); + elm_button_label_set(obj, "Icon tooltip, click to start changed" + " timed"); + return; + } + + timer = ecore_timer_add(1.5, _tt_icon_replace_timer_cb, obj); + evas_object_data_set(obj, "test-timer", timer); + elm_button_label_set(obj, "Icon tooltip, click to stop changed timed"); +} + +static Eina_Bool +_tt_style_replace_timer_cb(void *data) +{ + static int current = 0; + elm_object_tooltip_style_set(data, current ? NULL : "transparent"); + current = !current; + return EINA_TRUE; +} + +static void +_tt_style_replace_timed(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Ecore_Timer *timer = evas_object_data_get(obj, "test-timer"); + if (timer) + { + ecore_timer_del(timer); + evas_object_data_del(obj, "test-timer"); + elm_button_label_set(obj, "Icon tooltip style, click to start" + " changed timed"); + return; + } + + timer = ecore_timer_add(1.5, _tt_style_replace_timer_cb, obj); + evas_object_data_set(obj, "test-timer", timer); + elm_button_label_set(obj, "Icon tooltip style, click to stop changed" + " timed"); +} + +static void +_tt_visible_lock_toggle(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + static int locked = 0; + + locked = !locked; + if (locked) + { + elm_button_label_set(obj, "Locked tooltip visibility"); + elm_object_tooltip_text_set(obj, "This tooltip is locked" + " visible,
    click the button" + " to unlock!"); + elm_object_tooltip_show(obj); + } + else + { + elm_button_label_set(obj, "Unlocked tooltip visibility"); + elm_object_tooltip_text_set(obj, "This tooltip is unlocked" + " visible,
    click the button" + " to lock!"); + elm_object_tooltip_hide(obj); + } +} + +void +test_tooltip(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *tb, *bt, *se, *lst; + Elm_Toolbar_Item *ti; + Elm_List_Item *li; + + win = elm_win_add(NULL, "tooltip", ELM_WIN_BASIC); + elm_win_title_set(win, "Tooltip"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + tb = elm_toolbar_add(win); + elm_toolbar_homogenous_set(tb, 0); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, 0.0); + elm_box_pack_end(bx, tb); + evas_object_show(tb); + + ti = elm_toolbar_item_append(tb, NULL, "Open", NULL, NULL); + elm_toolbar_item_tooltip_text_set(ti, "Opens a file"); + + ti = elm_toolbar_item_append(tb, NULL, "Icon", NULL, NULL); + elm_toolbar_item_tooltip_content_cb_set + (ti, _tt_item_icon, (void *)456L, _tt_item_icon_del); + elm_toolbar_item_tooltip_style_set(ti, "transparent"); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Simple text tooltip"); + elm_object_tooltip_text_set(bt, "Simple text tooltip"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Simple text tooltip, click to change"); + elm_object_tooltip_text_set(bt, "Initial"); + evas_object_smart_callback_add(bt, "clicked", _tt_text_replace, NULL); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Simple text tooltip, click to start" + " changed timed"); + elm_object_tooltip_text_set(bt, "Initial"); + evas_object_smart_callback_add(bt, "clicked", _tt_text_replace_timed, + NULL); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_event_callback_add(bt, EVAS_CALLBACK_DEL, _tt_timer_del, + NULL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Icon tooltip"); + elm_object_tooltip_content_cb_set(bt, _tt_icon, (void *)123L, + _tt_icon_del); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Icon tooltip, click to start changed timed"); + elm_object_tooltip_content_cb_set(bt, _tt_icon, NULL, NULL); + evas_object_smart_callback_add(bt, "clicked", _tt_icon_replace_timed, + NULL); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_event_callback_add(bt, EVAS_CALLBACK_DEL, _tt_timer_del, + NULL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Transparent Icon tooltip"); + elm_object_tooltip_content_cb_set(bt, _tt_icon, NULL, NULL); + elm_object_tooltip_style_set(bt, "transparent"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Icon tooltip style, click to start changed" + " timed"); + elm_object_tooltip_content_cb_set(bt, _tt_icon, NULL, NULL); + evas_object_smart_callback_add(bt, "clicked", _tt_style_replace_timed, + NULL); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_event_callback_add(bt, EVAS_CALLBACK_DEL, _tt_timer_del, + NULL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Unlocked tooltip visibility"); + elm_object_tooltip_text_set(bt, "This tooltip is unlocked visible,
    " + " click the button to lock!"); + evas_object_smart_callback_add(bt, "clicked", _tt_visible_lock_toggle, + NULL); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + + se = elm_scrolled_entry_add(win); + evas_object_size_hint_weight_set(se, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(se, EVAS_HINT_FILL, 0.5); + elm_scrolled_entry_scrollbar_policy_set(se, ELM_SCROLLER_POLICY_OFF, + ELM_SCROLLER_POLICY_OFF); + elm_scrolled_entry_entry_set(se, "Hello, some scrolled entry here!"); + elm_object_tooltip_text_set(se, "Type something here!"); + elm_scrolled_entry_single_line_set(se, 1); + elm_box_pack_end(bx, se); + evas_object_show(se); + + lst = elm_list_add(win); + li = elm_list_item_append(lst, "Hello", NULL, NULL, NULL, NULL); + elm_list_item_tooltip_text_set(li, "Something useful here?"); + li = elm_list_item_append(lst, "Icon Tooltip", NULL, NULL, NULL, NULL); + elm_list_item_tooltip_content_cb_set(li, _tt_item_icon, NULL, NULL); + evas_object_size_hint_weight_set(lst, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(lst, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_min_set(lst, 100, 100); + elm_list_go(lst); + elm_box_pack_end(bx, lst); + evas_object_show(lst); + + evas_object_resize(win, 320, 580); + evas_object_show(win); +} + +void +test_tooltip2(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *grid, *gl; + Elm_Genlist_Item *it1, *it2, *it3; + static Testitem ti[144]; + int i, n; + char buf[PATH_MAX]; + const char *img[9] = + { + "panel_01.jpg", + "plant_01.jpg", + "rock_01.jpg", + "rock_02.jpg", + "sky_01.jpg", + "sky_02.jpg", + "sky_03.jpg", + "sky_04.jpg", + "wood_01.jpg", + }; + + win = elm_win_add(NULL, "tooltip2", ELM_WIN_BASIC); + elm_win_title_set(win, "Tooltip 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + grid = elm_gengrid_add(win); + elm_gengrid_item_size_set(grid, 100, 100); + elm_gengrid_horizontal_set(grid, EINA_FALSE); + elm_gengrid_multi_select_set(grid, EINA_TRUE); + evas_object_size_hint_align_set(grid, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(grid, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + + gic.item_style = "default"; + gic.func.label_get = grdt_lbl_get; + gic.func.icon_get = grdt_icon_get; + + n = 0; + for (i = 0; i < 9; i++) + { + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, + img[n]); + n++; + ti[i].mode = i; + ti[i].path = eina_stringshare_add(buf); + ti[i].item = elm_gengrid_item_append(grid, &gic, &(ti[i]), NULL, + NULL); + if (n % 2) + elm_gengrid_item_tooltip_text_set(ti[i].item, "Testing X"); + else + elm_gengrid_item_tooltip_text_set(ti[i].item, "Testing Y"); + if (!(i % 5)) + elm_gengrid_item_selected_set(ti[i].item, EINA_TRUE); + } + + elm_box_pack_end(bx, grid); + evas_object_show(grid); + + gl = elm_genlist_add(win); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + + itct.item_style = "default"; + itct.func.label_get = gltt_label_get; + + it1 = elm_genlist_item_append(gl, &itct, (void *)1, NULL, + ELM_GENLIST_ITEM_SUBITEMS, NULL, NULL); + it2 = elm_genlist_item_append(gl, &itct, (void *)2, NULL, + ELM_GENLIST_ITEM_SUBITEMS, NULL, NULL); + it3 = elm_genlist_item_append(gl, &itct, (void *)3, NULL, + ELM_GENLIST_ITEM_NONE, NULL, NULL); + + elm_genlist_item_tooltip_text_set(it1, "Testing 1"); + elm_genlist_item_tooltip_text_set(it2, "Testing 2"); + elm_genlist_item_tooltip_text_set(it3, "Testing 3"); + + evas_object_smart_callback_add(gl, "expand,request", gltt_exp_req, gl); + evas_object_smart_callback_add(gl, "contract,request", gltt_con_req, + gl); + evas_object_smart_callback_add(gl, "expanded", gltt_exp, gl); + evas_object_smart_callback_add(gl, "contracted", gltt_con, gl); + + elm_box_pack_end(bx, gl); + evas_object_show(gl); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} + +#endif diff --git a/src/bin/test_transit.c b/src/bin/test_transit.c new file mode 100644 index 0000000..0067fc5 --- /dev/null +++ b/src/bin/test_transit.c @@ -0,0 +1,524 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +typedef struct _Custom_Effect Custom_Effect; + +struct _Custom_Effect +{ + struct _size + { + Evas_Coord w, h; + } from, to; +}; + +static void +_custom_op(void *data, Elm_Transit *transit, double progress) +{ + if (!data) return; + Evas_Coord w, h; + Evas_Object *obj; + const Eina_List *elist; + + Custom_Effect *custom_effect = data; + const Eina_List *objs = elm_transit_objects_get(transit); + + if (progress < 0.5) + { + h = custom_effect->from.h + (custom_effect->to.h * progress * 2); + w = custom_effect->from.w; + } + else + { + h = custom_effect->from.h + custom_effect->to.h; + w = custom_effect->from.w + \ + (custom_effect->to.w * (progress - 0.5) * 2); + } + + EINA_LIST_FOREACH(objs, elist, obj) + evas_object_resize(obj, w, h); + +} + +static void * +_custom_context_new(Evas_Coord from_w, Evas_Coord from_h, Evas_Coord to_w, Evas_Coord to_h) +{ + Custom_Effect *custom_effect; + + custom_effect = calloc(1, sizeof(Custom_Effect)); + if (!custom_effect) return NULL; + + custom_effect->from.w = from_w; + custom_effect->from.h = from_h; + custom_effect->to.w = to_w - from_w; + custom_effect->to.h = to_h - from_h; + + return custom_effect; +} + +static void +_custom_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + free(data); +} + +static void +_transit_rotation_translation_color(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit *trans; + + trans = elm_transit_add(); + elm_transit_object_add(trans, obj); + elm_transit_auto_reverse_set(trans, EINA_TRUE); + elm_transit_repeat_times_set(trans, 2); + + /* Translation Effect */ + elm_transit_effect_translation_add(trans, -70.0, -150.0, 70.0, 150.0); + + /* Color Effect */ + elm_transit_effect_color_add(trans, 100, 255, 100, 255, 200, 50, 200, 50); + + /* Rotation Effect */ + elm_transit_effect_rotation_add(trans, 0.0, 135.0); + + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +static void +_transit_wipe(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit *trans; + + trans = elm_transit_add(); + elm_transit_object_add(trans, obj); + elm_transit_auto_reverse_set(trans, EINA_TRUE); + + elm_transit_effect_wipe_add(trans, + ELM_TRANSIT_EFFECT_WIPE_TYPE_HIDE, + ELM_TRANSIT_EFFECT_WIPE_DIR_RIGHT); + + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +static void +_transit_image_animation(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Eina_List *images = NULL; + char buf[PATH_MAX]; + Elm_Transit *trans; + Evas_Object *ic = data; + + snprintf(buf, sizeof(buf), "%s/images/icon_19.png", PACKAGE_DATA_DIR); + images = eina_list_append(images, eina_stringshare_add(buf)); + + snprintf(buf, sizeof(buf), "%s/images/icon_00.png", PACKAGE_DATA_DIR); + images = eina_list_append(images, eina_stringshare_add(buf)); + + snprintf(buf, sizeof(buf), "%s/images/icon_11.png", PACKAGE_DATA_DIR); + images = eina_list_append(images, eina_stringshare_add(buf)); + + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + images = eina_list_append(images, eina_stringshare_add(buf)); + + trans = elm_transit_add(); + elm_transit_object_add(trans, ic); + + elm_transit_effect_image_animation_add(trans, images); + + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +static void +_transit_resizing(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Transit *trans; + + trans = elm_transit_add(); + elm_transit_object_add(trans, obj); + + elm_transit_effect_resizing_add(trans, 100, 50, 300, 150); + + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +static void +_transit_flip(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit *trans; + Evas_Object *obj2 = data; + + trans = elm_transit_add(); + elm_transit_object_add(trans, obj); + elm_transit_object_add(trans, obj2); + + elm_transit_effect_flip_add(trans, ELM_TRANSIT_EFFECT_FLIP_AXIS_X, EINA_TRUE); + + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +static void +_transit_zoom(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Transit *trans; + + trans = elm_transit_add(); + elm_transit_object_add(trans, obj); + + elm_transit_effect_zoom_add(trans, 1.0, 3.0); + + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +static void +_transit_blend(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit *trans; + Evas_Object *obj2 = data; + + trans = elm_transit_add(); + elm_transit_object_add(trans, obj); + elm_transit_object_add(trans, obj2); + + elm_transit_effect_blend_add(trans); + + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +static void +_transit_fade(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit *trans; + Evas_Object *obj2 = data; + + trans = elm_transit_add(); + elm_transit_object_add(trans, obj); + elm_transit_object_add(trans, obj2); + + elm_transit_effect_fade_add(trans); + + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +static void +_transit_resizable_flip(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit *trans; + Evas_Object *obj2 = data; + + trans = elm_transit_add(); + elm_transit_object_add(trans, obj); + elm_transit_object_add(trans, obj2); + + elm_transit_effect_resizable_flip_add(trans, ELM_TRANSIT_EFFECT_FLIP_AXIS_Y, EINA_TRUE); + + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +/* Translation, Rotation, Color, Wipe, ImagemAnimation Effect */ +void +test_transit(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bx, *bt, *ic; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "transit", ELM_WIN_BASIC); + elm_win_title_set(win, "Transit"); + elm_win_autodel_set(win, EINA_TRUE); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_min_set(bx, 318, 318); + evas_object_show(bx); + + ic = elm_icon_add(win); + snprintf(buf, sizeof(buf), "%s/images/icon_11.png", PACKAGE_DATA_DIR); + elm_icon_file_set(ic, buf, NULL); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + + bt = elm_button_add(win); + elm_button_label_set(bt, "ImageAnimation Effect"); + elm_button_icon_set(bt, ic); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_show(ic); + evas_object_smart_callback_add(bt, "clicked", _transit_image_animation, ic); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Color, Rotation and Translation"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_smart_callback_add(bt, "clicked", + _transit_rotation_translation_color, NULL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Wipe Effect"); + elm_box_pack_end(bx, bt); + evas_object_show(bt); + evas_object_smart_callback_add(bt, "clicked", _transit_wipe, NULL); + + evas_object_show(win); +} + +/* Resizing Effect */ +void +test_transit2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bt; + + win = elm_win_add(NULL, "transit-2", ELM_WIN_BASIC); + elm_win_title_set(win, "Transit 2"); + elm_win_autodel_set(win, EINA_TRUE); + evas_object_resize(win, 400, 400); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Resizing Effect"); + evas_object_show(bt); + evas_object_move(bt, 50, 100); + evas_object_resize(bt, 100, 50); + evas_object_smart_callback_add(bt, "clicked", _transit_resizing, NULL); + + evas_object_show(win); +} + +/* Flip Effect */ +void +test_transit3(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bt, *bt2; + + win = elm_win_add(NULL, "transit-3", ELM_WIN_BASIC); + elm_win_title_set(win, "Transit 3"); + elm_win_autodel_set(win, EINA_TRUE); + evas_object_resize(win, 300, 300); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Front Button - Flip Effect"); + evas_object_show(bt); + evas_object_move(bt, 50, 50); + evas_object_resize(bt, 200, 200); + + bt2 = elm_button_add(win); + elm_button_label_set(bt2, "Back Button - Flip Effect"); + evas_object_move(bt2, 50, 50); + evas_object_resize(bt2, 200, 200); + + evas_object_show(win); + + evas_object_smart_callback_add(bt, "clicked", _transit_flip, bt2); + evas_object_smart_callback_add(bt2, "clicked", _transit_flip, bt); +} + +/* Zoom Effect */ +void +test_transit4(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bt; + + win = elm_win_add(NULL, "transit-4", ELM_WIN_BASIC); + elm_win_title_set(win, "Transit 4"); + elm_win_autodel_set(win, EINA_TRUE); + evas_object_resize(win, 300, 300); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Zoom Effect"); + evas_object_resize(bt, 100, 50); + evas_object_move(bt, 100, 125); + evas_object_show(bt); + + evas_object_smart_callback_add(bt, "clicked", _transit_zoom, NULL); + + evas_object_show(win); +} + +/* Blend Effect */ +void +test_transit5(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bt, *bt2, *ic; + + win = elm_win_add(NULL, "transit-5", ELM_WIN_BASIC); + elm_win_title_set(win, "Transit 5"); + elm_win_autodel_set(win, EINA_TRUE); + evas_object_resize(win, 300, 300); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + ic = elm_icon_add(win); + elm_icon_file_set(ic, PACKAGE_DATA_DIR"/images/rock_01.jpg", NULL); + evas_object_size_hint_max_set(ic, 50, 50); + + bt = elm_button_add(win); + elm_button_icon_set(bt, ic); + elm_button_label_set(bt, "Before Button - Blend Effect"); + evas_object_move(bt, 25, 125); + evas_object_resize(bt, 250, 50); + evas_object_show(bt); + + ic = elm_icon_add(win); + elm_icon_file_set(ic, PACKAGE_DATA_DIR"/images/rock_02.jpg", NULL); + evas_object_size_hint_max_set(ic, 50, 50); + + bt2 = elm_button_add(win); + elm_button_icon_set(bt2, ic); + elm_button_label_set(bt2, "After Button - Blend Effect"); + evas_object_move(bt2, 25, 125); + evas_object_resize(bt2, 250, 50); + + evas_object_show(win); + + evas_object_smart_callback_add(bt, "clicked", _transit_blend, bt2); + evas_object_smart_callback_add(bt2, "clicked", _transit_blend, bt); +} + +/* Fade Effect */ +void +test_transit6(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bt, *bt2, *ic; + + win = elm_win_add(NULL, "transit-6", ELM_WIN_BASIC); + elm_win_title_set(win, "Transit 6"); + elm_win_autodel_set(win, EINA_TRUE); + evas_object_resize(win, 300, 300); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + ic = elm_icon_add(win); + elm_icon_file_set(ic, PACKAGE_DATA_DIR"/images/rock_01.jpg", NULL); + evas_object_size_hint_max_set(ic, 50, 50); + + bt = elm_button_add(win); + elm_button_icon_set(bt, ic); + elm_button_label_set(bt, "Before Button - Fade Effect"); + evas_object_move(bt, 25, 125); + evas_object_resize(bt, 250, 50); + evas_object_show(bt); + + ic = elm_icon_add(win); + elm_icon_file_set(ic, PACKAGE_DATA_DIR"/images/rock_02.jpg", NULL); + evas_object_size_hint_max_set(ic, 50, 50); + + bt2 = elm_button_add(win); + elm_button_icon_set(bt2, ic); + elm_button_label_set(bt2, "After Button - Fade Effect"); + evas_object_move(bt2, 25, 125); + evas_object_resize(bt2, 250, 50); + + evas_object_show(win); + + evas_object_smart_callback_add(bt, "clicked", _transit_fade, bt2); + evas_object_smart_callback_add(bt2, "clicked", _transit_fade, bt); +} + +/* Resizable Flip Effect */ +void +test_transit7(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bt, *bt2; + + win = elm_win_add(NULL, "transit-7", ELM_WIN_BASIC); + elm_win_title_set(win, "Transit 7"); + elm_win_autodel_set(win, EINA_TRUE); + evas_object_resize(win, 400, 400); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Front Button - Resizable Flip Effect"); + evas_object_show(bt); + evas_object_move(bt, 50, 100); + evas_object_resize(bt, 250, 30); + + bt2 = elm_button_add(win); + elm_button_label_set(bt2, "Back Button - Resizable Flip Effect"); + evas_object_move(bt2, 50, 100); + evas_object_resize(bt2, 300, 200); + + evas_object_show(win); + + evas_object_smart_callback_add(bt, "clicked", _transit_resizable_flip, bt2); + evas_object_smart_callback_add(bt2, "clicked", _transit_resizable_flip, bt); +} + +/* Custom Effect */ +void +test_transit8(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *bt; + Elm_Transit *trans; + void *effect_context; + + win = elm_win_add(NULL, "transit-8", ELM_WIN_BASIC); + elm_win_title_set(win, "Transit 8"); + elm_win_autodel_set(win, EINA_TRUE); + evas_object_resize(win, 400, 400); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Button - Custom Effect"); + evas_object_show(bt); + evas_object_move(bt, 50, 100); + evas_object_resize(bt, 250, 150); + + evas_object_show(win); + + /* Adding Transit */ + trans = elm_transit_add(); + elm_transit_auto_reverse_set(trans, EINA_TRUE); + elm_transit_tween_mode_set(trans, ELM_TRANSIT_TWEEN_MODE_DECELERATE); + elm_transit_repeat_times_set(trans, -1); + effect_context = _custom_context_new(100, 100, 250, 250); + elm_transit_object_add(trans, bt); + elm_transit_effect_add(trans, + _custom_op, effect_context, + _custom_context_free); + elm_transit_duration_set(trans, 5.0); + elm_transit_go(trans); +} + +#endif diff --git a/src/bin/test_weather.c b/src/bin/test_weather.c new file mode 100644 index 0000000..536bd32 --- /dev/null +++ b/src/bin/test_weather.c @@ -0,0 +1,176 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH + +#ifdef HAVE_ELEMENTARY_EWEATHER +# include "EWeather_Smart.h" +#endif + +#ifdef HAVE_ELEMENTARY_EWEATHER +static Evas_Object *en, *hv, *fl; +static Evas_Object *weather[2]; +static int current = 0; +static Eina_Module *module[2]; + +static void +_first_city_cb(void *data __UNUSED__, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) +{ + if (!current) return; + current = 0; + elm_flip_go(fl, ELM_FLIP_ROTATE_YZ_CENTER_AXIS); +} + +static void +_second_city_cb(void *dat __UNUSED__, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) +{ + if (current) return; + current = 1; + elm_flip_go(fl, ELM_FLIP_ROTATE_XZ_CENTER_AXIS); +} + +static void _apply_cb(void *data __UNUSED__, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) +{ + EWeather *eweather = eweather_object_eweather_get(weather[current]); + + if (module[current]) + eweather_plugin_set(eweather, module[current]); + eweather_code_set(eweather, elm_entry_entry_get(en)); + printf("CURRENT %d %p %p\n", current, module[current], eweather); +} + +static void +_hover_select_cb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + EWeather *eweather = eweather_object_eweather_get(weather[0]); + module[0] = eweather_plugin_search(eweather, elm_hoversel_item_label_get(event_info)); + + eweather = eweather_object_eweather_get(weather[1]); + module[1] = eweather_plugin_search(eweather, elm_hoversel_item_label_get(event_info)); + printf("%p %p\n", module[0], module[1]); +} +#endif + +void +test_weather(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg; +#ifdef HAVE_ELEMENTARY_EWEATHER + Evas_Object *bx, *bx0, *bt; + EWeather *eweather; + Eina_Array_Iterator it; + Eina_Array *array; + Eina_Module *m; + unsigned int i; +#endif + + win = elm_win_add(NULL, "weather", ELM_WIN_BASIC); + elm_win_title_set(win, "Weather"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + +#ifdef HAVE_ELEMENTARY_EWEATHER + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bx); + + fl = elm_flip_add(win); + evas_object_size_hint_align_set(fl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(fl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_box_pack_end(bx, fl); + + current = 0; + + module[0] = NULL; + weather[0] = eweather_object_add(evas_object_evas_get(win)); + evas_object_size_hint_weight_set(weather[0], EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(weather[0], -1.0, -1.0); + elm_flip_content_front_set(fl, weather[0]); + evas_object_show(weather[0]); + + module[1] = NULL; + weather[1] = eweather_object_add(evas_object_evas_get(win)); + eweather = eweather_object_eweather_get(weather[1]); + evas_object_size_hint_weight_set(weather[1], EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(weather[1], -1.0, -1.0); + elm_flip_content_back_set(fl, weather[1]); + evas_object_show(weather[1]); + + evas_object_show(fl); + + // + bx0 = elm_box_add(win); + elm_box_horizontal_set(bx0, EINA_TRUE); + evas_object_size_hint_weight_set(bx0, 1.0, 0.0); + elm_box_pack_end(bx, bx0); + evas_object_show(bx0); + + bt = elm_button_add(win); + elm_button_label_set(bt, "First city"); + evas_object_show(bt); + elm_box_pack_end(bx0, bt); + evas_object_smart_callback_add(bt, "clicked", _first_city_cb, NULL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Second city"); + evas_object_show(bt); + elm_box_pack_end(bx0, bt); + evas_object_smart_callback_add(bt, "clicked", _second_city_cb, NULL); + // + + // + bx0 = elm_box_add(win); + elm_box_horizontal_set(bx0, EINA_TRUE); + evas_object_size_hint_weight_set(bx0, 1.0, 0.0); + elm_box_pack_end(bx, bx0); + evas_object_show(bx0); + + hv = elm_hoversel_add(win); + elm_hoversel_hover_parent_set(hv, win); + elm_hoversel_label_set(hv, "data source"); + evas_object_size_hint_weight_set(hv, 0.0, 0.0); + evas_object_size_hint_align_set(hv, 0.5, 0.5); + elm_box_pack_end(bx0, hv); + evas_object_show(hv); + + array = eweather_plugins_list_get(eweather); + + EINA_ARRAY_ITER_NEXT(array, i, m, it) + elm_hoversel_item_add(hv, eweather_plugin_name_get(eweather, i), NULL, ELM_ICON_NONE, _hover_select_cb, NULL); + + en = elm_entry_add(win); + elm_entry_line_wrap_set(en, 0); + elm_entry_single_line_set(en, EINA_TRUE); + elm_entry_entry_set(en, "Paris"); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx0, en); + evas_object_show(en); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Apply"); + evas_object_show(bt); + elm_box_pack_end(bx0, bt); + evas_object_smart_callback_add(bt, "clicked", _apply_cb, NULL); + // + + +#else + Evas_Object *lbl; + + lbl = elm_label_add(win); + elm_win_resize_object_add(win, lbl); + elm_label_label_set(lbl, "libeweather is required to display the forecast."); + evas_object_show(lbl); +#endif + + evas_object_resize(win, 244, 388); + evas_object_show(win); +} +#endif diff --git a/src/bin/test_win_state.c b/src/bin/test_win_state.c new file mode 100644 index 0000000..d6efacb --- /dev/null +++ b/src/bin/test_win_state.c @@ -0,0 +1,369 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifndef ELM_LIB_QUICKLAUNCH +typedef struct _Testitem +{ + Elm_Genlist_Item *item; + int mode, onoff; +} Testitem; + +static int rotate_with_resize = 0; + +static void +my_bt_38_alpha_on(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Evas_Object *bg = evas_object_data_get(win, "bg"); + evas_object_hide(bg); + elm_win_alpha_set(win, 1); +} + +static void +my_bt_38_alpha_off(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + Evas_Object *bg = evas_object_data_get(win, "bg"); + evas_object_show(bg); + elm_win_alpha_set(win, 0); +} + +static void +my_ck_38_resize(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ +// Evas_Object *win = data; + rotate_with_resize = elm_check_state_get(obj); +} + +static void +my_bt_38_rot_0(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + if (rotate_with_resize) + elm_win_rotation_with_resize_set(win, 0); + else + elm_win_rotation_set(win, 0); +} + +static void +my_bt_38_rot_90(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + if (rotate_with_resize) + elm_win_rotation_with_resize_set(win, 90); + else + elm_win_rotation_set(win, 90); +} + +static void +my_bt_38_rot_180(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + if (rotate_with_resize) + elm_win_rotation_with_resize_set(win, 180); + else + elm_win_rotation_set(win, 180); +} + +static void +my_bt_38_rot_270(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win = data; + if (rotate_with_resize) + elm_win_rotation_with_resize_set(win, 270); + else + elm_win_rotation_set(win, 270); +} + +static void +my_win_move(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Coord x, y; + elm_win_screen_position_get(obj, &x, &y); + printf("MOVE - win geom: %4i %4i\n", x, y); +} + +static void +_win_resize(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Coord w, h; + evas_object_geometry_get(obj, NULL, NULL, &w, &h); + printf("RESIZE - win geom: %4ix%4i\n", w, h); +} + +static void +_win_foc_in(void *data __UNUSED__, Evas *e __UNUSED__, void *event_info __UNUSED__) +{ + printf("FOC IN\n"); +} + +static void +_win_foc_out(void *data __UNUSED__, Evas *e __UNUSED__, void *event_info __UNUSED__) +{ + printf("FOC OUT\n"); +} + +static void +_close_win(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_del(data); +} + +void +test_win_state(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *sl, *bx, *bx2, *bt, *ck; + + win = elm_win_add(NULL, "window-state", ELM_WIN_BASIC); + elm_win_title_set(win, "Window States"); + evas_object_smart_callback_add(win, "moved", my_win_move, NULL); + evas_object_event_callback_add(win, EVAS_CALLBACK_RESIZE, _win_resize, NULL); + evas_event_callback_add(evas_object_evas_get(win), EVAS_CALLBACK_CANVAS_FOCUS_IN, _win_foc_in, NULL); + evas_event_callback_add(evas_object_evas_get(win), EVAS_CALLBACK_CANVAS_FOCUS_OUT, _win_foc_out, NULL); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + evas_object_data_set(win, "bg", bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_fill_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Alpha On"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_alpha_on, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Alpha Off"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_alpha_off, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + sl = elm_slider_add(win); + elm_slider_label_set(sl, "Test"); + elm_slider_span_size_set(sl, 100); + evas_object_size_hint_align_set(sl, 0.5, 0.5); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_slider_indicator_format_set(sl, "%3.0f"); + elm_slider_min_max_set(sl, 50, 150); + elm_slider_value_set(sl, 50); + elm_slider_inverted_set(sl, 1); + elm_box_pack_end(bx2, sl); + evas_object_show(sl); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + ck = elm_check_add(win); + elm_check_label_set(ck, "resize"); + elm_check_state_set(ck, rotate_with_resize); + evas_object_smart_callback_add(ck, "changed", my_ck_38_resize, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.02, 0.99); + evas_object_show(ck); + elm_box_pack_end(bx, ck); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_fill_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rot 0"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_rot_0, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rot 90"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_rot_90, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rot 180"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_rot_180, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rot 270"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_rot_270, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 280, 400); + evas_object_show(win); +} + +void +test_win_state2(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *win, *bg, *sl, *bx, *bx2, *bt, *ck; + char buf[PATH_MAX]; + + win = elm_win_add(NULL, "window-state2", ELM_WIN_BASIC); + elm_win_override_set(win, 1); + evas_object_smart_callback_add(win, "moved", my_win_move, NULL); + evas_object_event_callback_add(win, EVAS_CALLBACK_RESIZE, _win_resize, NULL); + elm_win_title_set(win, "Window States 2"); + elm_win_autodel_set(win, 1); + + bg = elm_bg_add(win); + snprintf(buf, sizeof(buf), "%s/images/sky_02.jpg", PACKAGE_DATA_DIR); + elm_bg_file_set(bg, buf, NULL); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + evas_object_data_set(win, "bg", bg); + + bx = elm_box_add(win); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(win, bx); + evas_object_show(bx); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_fill_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Alpha On"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_alpha_on, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Alpha Off"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_alpha_off, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, 0.0, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Close"); + evas_object_smart_callback_add(bt, "clicked", _close_win, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + sl = elm_slider_add(win); + elm_slider_label_set(sl, "Override Redirect"); + elm_slider_span_size_set(sl, 100); + evas_object_size_hint_align_set(sl, 0.5, 0.5); + evas_object_size_hint_weight_set(sl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_slider_indicator_format_set(sl, "%3.0f"); + elm_slider_min_max_set(sl, 50, 150); + elm_slider_value_set(sl, 50); + elm_slider_inverted_set(sl, 1); + elm_box_pack_end(bx2, sl); + evas_object_show(sl); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + ck = elm_check_add(win); + elm_check_label_set(ck, "resize"); + elm_check_state_set(ck, rotate_with_resize); + evas_object_smart_callback_add(ck, "changed", my_ck_38_resize, win); + evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(ck, 0.02, 0.99); + evas_object_show(ck); + elm_box_pack_end(bx, ck); + + bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); + elm_box_homogenous_set(bx2, 1); + evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_fill_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rot 0"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_rot_0, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rot 90"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_rot_90, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rot 180"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_rot_180, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + bt = elm_button_add(win); + elm_button_label_set(bt, "Rot 270"); + evas_object_smart_callback_add(bt, "clicked", my_bt_38_rot_270, win); + evas_object_size_hint_fill_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + elm_box_pack_end(bx2, bt); + evas_object_show(bt); + + elm_box_pack_end(bx, bx2); + evas_object_show(bx2); + + evas_object_resize(win, 320, 480); + evas_object_show(win); +} +#endif diff --git a/src/edje_externals/Makefile.am b/src/edje_externals/Makefile.am new file mode 100644 index 0000000..8d1b53d --- /dev/null +++ b/src/edje_externals/Makefile.am @@ -0,0 +1,61 @@ +MAINTAINERCLEANFILES = Makefile.in + +AM_CPPFLAGS = \ +-DELM_INTERAL_API_MDFGELQ=1 \ +-I. \ +-I$(top_builddir) \ +-I$(top_srcdir) \ +-I$(top_srcdir)/src/lib \ +-I$(top_builddir)/src/lib \ +-DPACKAGE_DATA_DIR=\"$(datadir)/$(PACKAGE)\" \ +-DPACKAGE_LIB_DIR=\"$(libdir)\" \ +@ELEMENTARY_CFLAGS@ \ +@ELEMENTARY_X_CFLAGS@ \ +@ELEMENTARY_FB_CFLAGS@ \ +@ELEMENTARY_WIN32_CFLAGS@ \ +@ELEMENTARY_WINCE_CFLAGS@ \ +@ELEMENTARY_EDBUS_CFLAGS@ \ +@ELEMENTARY_EFREET_CFLAGS@ \ +@ELEMENTARY_ETHUMB_CFLAGS@ + +if ELEMENTARY_WINDOWS_BUILD +AM_CPPFLAGS += -DELEMENTARY_BUILD +endif + +pkgdir = $(libdir)/edje/modules/elm/$(MODULE_EDJE) +pkg_LTLIBRARIES = module.la + +module_la_SOURCES = private.h \ +modules.inc \ +elm.c \ +elm_anchorblock.c \ +elm_anchorview.c \ +elm_bubble.c \ +elm_button.c \ +elm_check.c \ +elm_clock.c \ +elm_fileselector.c \ +elm_fileselector_button.c \ +elm_fileselector_entry.c \ +elm_genlist.c \ +elm_hoversel.c \ +elm_list.c \ +elm_map.c \ +elm_photocam.c \ +elm_progressbar.c \ +elm_radio.c \ +elm_scrolled_entry.c \ +elm_slider.c \ +elm_slideshow.c \ +elm_spinner.c \ +elm_thumb.c \ +elm_toggle.c \ +elm_toolbar.c \ +elm_notify.c \ +elm_panes.c \ +elm_label.c \ +elm_icon.c \ +elm_scroller.c + +module_la_LIBADD = $(top_builddir)/src/lib/libelementary.la +module_la_LDFLAGS = -no-undefined -module -avoid-version -shared -fPIC diff --git a/src/edje_externals/elm.c b/src/edje_externals/elm.c new file mode 100644 index 0000000..ccb6069 --- /dev/null +++ b/src/edje_externals/elm.c @@ -0,0 +1,300 @@ +#include "Elementary.h" +#include "private.h" + +int _elm_log_dom = -1; + +static int init_count = 0; + +void +external_elm_init(void) +{ + int argc = 0; + char **argv = NULL; + + init_count++; + printf("elm_real_init\n"); + if (init_count > 1) return; + ecore_app_args_get(&argc, &argv); + elm_init(argc, argv); +} + +static void +external_elm_shutdown(void) +{ + init_count--; + printf("elm_real_shutdown\n"); + if (init_count > 1) return; + elm_shutdown(); +} + +static void +_external_obj_del(void *data __UNUSED__, Evas *evas __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + evas_object_event_callback_del(obj, EVAS_CALLBACK_DEL, + _external_obj_del); + external_elm_shutdown(); +} + +void +external_signal(void *data __UNUSED__, Evas_Object *obj, const char *signal, const char *source) +{ + char *_signal = strdup(signal); + char *p = _signal; + Evas_Object *content; + + while((*p!='\0') && (*p!=']')) + p++; + + + if((*p=='\0') || (*(p+1)!=':')) + { + ERR("Invalid External Signal received: '%s' '%s'\n", signal, source); + free(_signal); + return ; + } + + *p = '\0'; + p+=2; //jump ']' and ':' + + Edje_External_Type *type = evas_object_data_get(obj, "Edje_External_Type"); + if (!type->content_get) + { + ERR("external type '%s' from module '%s' does not provide content_get()", + type->module_name, type->module); + free(_signal); + return ; + } + + content = type->content_get(type->data, obj, _signal); + free(_signal); + if(content) + edje_object_signal_emit(content, signal + (p - _signal), source); +} + +const char * +external_translate(void *data __UNUSED__, const char *orig) +{ + // in future, mark all params as translatable and use dgettext() + // with "elementary" text domain here. + return orig; +} + +typedef struct { + const char *emission; + const char *source; + Evas_Object *edje; +} Elm_External_Signals_Proxy_Context; + +static void +_external_signal_proxy_free_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_External_Signals_Proxy_Context *ctxt = data; + free(ctxt); +} + +static void +_external_signal_proxy_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_External_Signals_Proxy_Context *ctxt = data; + // TODO: Is it worth to check Evas_Smart_Cb_Description and do something + // TODO: with event_info given its description? + edje_object_signal_emit(ctxt->edje, ctxt->emission, ctxt->source); +} + +Eina_Bool +external_common_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "style")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_object_style_get(obj); + return EINA_TRUE; + } + } + return EINA_FALSE; +} + +Eina_Bool +external_common_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "style")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_object_style_set(obj, param->s); + return EINA_TRUE; + } + } + return EINA_FALSE; +} + +void +external_signals_proxy(Evas_Object *obj, Evas_Object *edje, const char *part_name) +{ + const Evas_Smart_Cb_Description **cls_descs, **inst_descs; + unsigned int cls_count, inst_count, total; + Elm_External_Signals_Proxy_Context *ctxt; + + evas_object_smart_callbacks_descriptions_get + (obj, &cls_descs, &cls_count, &inst_descs, &inst_count); + + total = cls_count + inst_count; + if (!total) return; + ctxt = malloc(sizeof(Elm_External_Signals_Proxy_Context) * total); + if (!ctxt) return; + evas_object_event_callback_add + (obj, EVAS_CALLBACK_DEL, _external_signal_proxy_free_cb, ctxt); + + for (; cls_count > 0; cls_count--, cls_descs++, ctxt++) + { + const Evas_Smart_Cb_Description *d = *cls_descs; + ctxt->emission = d->name; + ctxt->source = part_name; + ctxt->edje = edje; + evas_object_smart_callback_add + (obj, d->name, _external_signal_proxy_cb, ctxt); + } + + for (; inst_count > 0; inst_count--, inst_descs++, ctxt++) + { + const Evas_Smart_Cb_Description *d = *inst_descs; + ctxt->emission = d->name; + ctxt->source = part_name; + ctxt->edje = edje; + evas_object_smart_callback_add + (obj, d->name, _external_signal_proxy_cb, ctxt); + } + evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, + _external_obj_del, NULL); +} + +void +external_common_params_parse(void *mem, void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params *p; + const Eina_List *l; + Edje_External_Param *param; + + p = mem; + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "style")) + { + p->style = eina_stringshare_add(param->s); + break; + } + } +} + +void +external_common_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params *p; + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->style) + elm_object_style_set(obj, p->style); +} + +Evas_Object * +external_common_param_icon_get(Evas_Object *obj, const Edje_External_Param *p) +{ + Evas_Object *edje, *parent_widget, *icon; + const char *file; + + if ((!p) || (!p->s) || (p->type != EDJE_EXTERNAL_PARAM_TYPE_STRING)) + return NULL; + + edje = evas_object_smart_parent_get(obj); + edje_object_file_get(edje, &file, NULL); + + parent_widget = elm_widget_parent_widget_get(obj); + if (!parent_widget) + parent_widget = edje; + icon = elm_icon_add(parent_widget); + + if (elm_icon_file_set(icon, file, p->s)) + return icon; + if (elm_icon_standard_set(icon, p->s)) + return icon; + + evas_object_del(icon); + return NULL; +} + +void +external_common_icon_param_parse(Evas_Object **icon, Evas_Object *obj, const Eina_List *params) +{ + Edje_External_Param *p = edje_external_param_find(params, "icon"); + *icon = external_common_param_icon_get(obj, p); +} + +Evas_Object * +external_common_param_edje_object_get(Evas_Object *obj, const Edje_External_Param *p) +{ + Evas_Object *edje, *parent_widget, *ret; + const char *file; + + if ((!p) || (!p->s) || (p->type != EDJE_EXTERNAL_PARAM_TYPE_STRING)) + return NULL; + + edje = evas_object_smart_parent_get(obj); + edje_object_file_get(edje, &file, NULL); + + parent_widget = elm_widget_parent_widget_get(obj); + if (!parent_widget) + parent_widget = edje; + + ret = edje_object_add(evas_object_evas_get(parent_widget)); + + if (edje_object_file_set(ret, file, p->s)) + return ret; + + evas_object_del(ret); + return NULL; +} + +void +external_common_params_free(void *params) +{ + Elm_Params *p = params; + if (p->style) + eina_stringshare_del(p->style); +} + +#define DEFINE_TYPE(type_name) \ + extern const Edje_External_Type external_##type_name##_type; +#include "modules.inc" +#undef DEFINE_TYPE + +static Edje_External_Type_Info elm_external_types[] = +{ +#define DEFINE_TYPE(type_name) \ + {"elm/"#type_name, &external_##type_name##_type}, +#include "modules.inc" +#undef DEFINE_TYPE + {NULL, NULL} +}; + +static Eina_Bool +elm_mod_init(void) +{ + _elm_log_dom = eina_log_domain_register("elm-externals", EINA_COLOR_LIGHTBLUE); + edje_external_type_array_register(elm_external_types); + return EINA_TRUE; +} + +static void +elm_mod_shutdown(void) +{ + edje_external_type_array_unregister(elm_external_types); + eina_log_domain_unregister(_elm_log_dom); + _elm_log_dom = -1; + +} + +EINA_MODULE_INIT(elm_mod_init); +EINA_MODULE_SHUTDOWN(elm_mod_shutdown); diff --git a/src/edje_externals/elm_anchorblock.c b/src/edje_externals/elm_anchorblock.c new file mode 100644 index 0000000..1e04c37 --- /dev/null +++ b/src/edje_externals/elm_anchorblock.c @@ -0,0 +1,104 @@ +#include "private.h" + +typedef struct _Elm_Params_Anchorblock +{ + Elm_Params base; + const char *text; +} Elm_Params_Anchorblock; + +static void +external_anchorblock_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Anchorblock *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->text) + { + elm_anchorblock_text_set(obj, p->text); + } +} + +static Eina_Bool +external_anchorblock_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "text")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_anchorblock_text_set(obj, param->s); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_anchorblock_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "text")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_anchorblock_text_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_anchorblock_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Anchorblock *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = ELM_NEW(Elm_Params_Anchorblock); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "text")) + mem->text = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_anchorblock_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_anchorblock_params_free(void *params) +{ + Elm_Params_Anchorblock *mem = params; + + if (mem->text) + eina_stringshare_del(mem->text); + free(mem); +} + +static Edje_External_Param_Info external_anchorblock_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("text", "some text"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(anchorblock, "anchorblock") +DEFINE_EXTERNAL_TYPE_SIMPLE(anchorblock, "Anchorblock"); diff --git a/src/edje_externals/elm_anchorview.c b/src/edje_externals/elm_anchorview.c new file mode 100644 index 0000000..d74a09f --- /dev/null +++ b/src/edje_externals/elm_anchorview.c @@ -0,0 +1,104 @@ +#include "private.h" + +typedef struct _Elm_Params_Anchorview +{ + Elm_Params base; + const char *text; +} Elm_Params_Anchorview; + +static void +external_anchorview_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Anchorview *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->text) + { + elm_anchorview_text_set(obj, p->text); + } +} + +static Eina_Bool +external_anchorview_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "text")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_anchorview_text_set(obj, param->s); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_anchorview_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "text")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_anchorview_text_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_anchorview_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Anchorview *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = ELM_NEW(Elm_Params_Anchorview); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "text")) + mem->text = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_anchorview_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_anchorview_params_free(void *params) +{ + Elm_Params_Anchorview *mem = params; + + if (mem->text) + eina_stringshare_del(mem->text); + free(mem); +} + +static Edje_External_Param_Info external_anchorview_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("text", "some text"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(anchorview, "anchorview") +DEFINE_EXTERNAL_TYPE_SIMPLE(anchorview, "Anchorview"); diff --git a/src/edje_externals/elm_bubble.c b/src/edje_externals/elm_bubble.c new file mode 100644 index 0000000..1de2e82 --- /dev/null +++ b/src/edje_externals/elm_bubble.c @@ -0,0 +1,165 @@ +#include "private.h" + +typedef struct _Elm_Params_Bubble +{ + Elm_Params base; + const char *label; + Evas_Object *icon; + const char *info; + Evas_Object *content; /* part name whose obj is to be set as content */ +} Elm_Params_Bubble; + +static void +external_bubble_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Bubble *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) elm_bubble_label_set(obj, p->label); + if (p->icon) elm_bubble_icon_set(obj, p->icon); + if (p->info) elm_bubble_info_set(obj, p->info); + if (p->content) elm_bubble_content_set(obj, p->content); +} + +static Eina_Bool +external_bubble_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_bubble_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_bubble_icon_set(obj, icon); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "info")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_bubble_info_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "content")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *content = \ + external_common_param_edje_object_get(obj, param); + if ((strcmp(param->s, "")) && (!content)) return EINA_FALSE; + elm_bubble_content_set(obj, content); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_bubble_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_bubble_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "info")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_bubble_info_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "content")) + { + /* not easy to get content name back from live object */ + return EINA_FALSE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_bubble_params_parse(void *data __UNUSED__, Evas_Object *obj, const Eina_List *params) +{ + Elm_Params_Bubble *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Bubble)); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "info")) + mem->info = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "content")) + mem->content = external_common_param_edje_object_get(obj, param); + else if (!strcmp(param->name, "label")) + mem->label = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_bubble_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_bubble_params_free(void *params) +{ + Elm_Params_Bubble *mem = params; + + if (mem->info) + eina_stringshare_del(mem->info); + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_bubble_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_STRING("info"), + EDJE_EXTERNAL_PARAM_INFO_STRING("content"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(bubble, "bubble"); +DEFINE_EXTERNAL_TYPE_SIMPLE(bubble, "Bubble"); diff --git a/src/edje_externals/elm_button.c b/src/edje_externals/elm_button.c new file mode 100644 index 0000000..9e2f5c2 --- /dev/null +++ b/src/edje_externals/elm_button.c @@ -0,0 +1,125 @@ +#include "private.h" + +typedef struct _Elm_Params_Button +{ + Elm_Params base; + const char *label; + Evas_Object *icon; +} Elm_Params_Button; + +static void +external_button_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Button *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) + elm_button_label_set(obj, p->label); + if (p->icon) + elm_button_icon_set(obj, p->icon); +} + +static Eina_Bool +external_button_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_button_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_button_icon_set(obj, icon); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_button_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_button_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_button_params_parse(void *data __UNUSED__, Evas_Object *obj, const Eina_List *params) +{ + Elm_Params_Button *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = ELM_NEW(Elm_Params_Button); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "label")) + { + mem->label = eina_stringshare_add(param->s); + break; + } + } + + return mem; +} + +static Evas_Object *external_button_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_button_params_free(void *params) +{ + Elm_Params_Button *mem = params; + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_button_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(button, "button"); +DEFINE_EXTERNAL_TYPE_SIMPLE(button, "Button"); diff --git a/src/edje_externals/elm_check.c b/src/edje_externals/elm_check.c new file mode 100644 index 0000000..f9b3e8b --- /dev/null +++ b/src/edje_externals/elm_check.c @@ -0,0 +1,148 @@ +#include "private.h" + +typedef struct _Elm_Params_Check +{ + Elm_Params base; + const char *label; + Evas_Object *icon; + Eina_Bool state:1; + Eina_Bool state_exists:1; +} Elm_Params_Check; + +static void +external_check_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Check *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) + elm_check_label_set(obj, p->label); + if (p->icon) + elm_check_icon_set(obj, p->icon); + if (p->state_exists) + elm_check_state_set(obj, p->state); +} + +static Eina_Bool +external_check_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_check_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_check_icon_set(obj, icon); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "state")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_check_state_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_check_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_check_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "state")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_check_state_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_check_params_parse(void *data __UNUSED__, Evas_Object *obj, const Eina_List *params) +{ + Elm_Params_Check *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Check)); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "state")) + { + mem->state = !!param->i; + mem->state_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "label")) + mem->label = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_check_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_check_params_free(void *params) +{ + Elm_Params_Check *mem = params; + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_check_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_BOOL_FULL("state", 0, "unchecked", "checked"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(check, "check") +DEFINE_EXTERNAL_TYPE_SIMPLE(check, "Check") diff --git a/src/edje_externals/elm_clock.c b/src/edje_externals/elm_clock.c new file mode 100644 index 0000000..c4bf9d2 --- /dev/null +++ b/src/edje_externals/elm_clock.c @@ -0,0 +1,241 @@ +#include "private.h" + +typedef struct _Elm_Params_Clock +{ + Elm_Params base; + int hrs, min, sec; + Eina_Bool hrs_exists:1; + Eina_Bool min_exists:1; + Eina_Bool sec_exists:1; + Eina_Bool edit:1; + Eina_Bool ampm:1; + Eina_Bool seconds:1; +} Elm_Params_Clock; + +static void +external_clock_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Clock *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if ((p->hrs_exists) && (p->min_exists) && (p->sec_exists)) + elm_clock_time_set(obj, p->hrs, p->min, p->sec); + else if ((p->hrs_exists) || (p->min_exists) || (p->sec_exists)) + { + int hrs, min, sec; + elm_clock_time_get(obj, &hrs, &min, &sec); + if (p->hrs_exists) + hrs = p->hrs; + if (p->min_exists) + min = p->min; + if (p->sec_exists) + sec = p->sec; + elm_clock_time_set(obj, hrs, min, sec); + } + if (p->edit) + elm_clock_edit_set(obj, p->edit); + if (p->ampm) + elm_clock_show_am_pm_set(obj, p->ampm); + if (p->seconds) + elm_clock_show_seconds_set(obj, p->seconds); +} + +static Eina_Bool +external_clock_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "hours")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + int hrs, min, sec; + elm_clock_time_get(obj, &hrs, &min, &sec); + elm_clock_time_set(obj, param->d, min, sec); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "minutes")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + int hrs, min, sec; + elm_clock_time_get(obj, &hrs, &min, &sec); + elm_clock_time_set(obj, hrs, param->d, sec); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "seconds")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + int hrs, min, sec; + elm_clock_time_get(obj, &hrs, &min, &sec); + elm_clock_time_set(obj, hrs, min, param->d); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "editable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_clock_edit_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "am/pm")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_clock_show_am_pm_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "show seconds")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_clock_show_seconds_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_clock_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "hours")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + int hrs, min, sec; + elm_clock_time_get(obj, &hrs, &min, &sec); + param->i = hrs; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "minutes")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + int hrs, min, sec; + elm_clock_time_get(obj, &hrs, &min, &sec); + param->i = min; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "seconds")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + int hrs, min, sec; + elm_clock_time_get(obj, &hrs, &min, &sec); + param->i = sec; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "editable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_clock_edit_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "am/pm")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_clock_show_am_pm_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "show seconds")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_clock_show_seconds_get(obj); + return EINA_TRUE; + } + } + + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_clock_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Clock *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Clock)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "hours")) + { + mem->hrs = param->i; + mem->hrs_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "minutes")) + { + mem->min = param->i; + mem->min_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "seconds")) + { + mem->sec = param->i; + mem->sec_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "editable")) + mem->edit = !!param->i; + else if (!strcmp(param->name, "am/pm")) + mem->ampm = !!param->i; + else if (!strcmp(param->name, "show seconds")) + mem->seconds = !!param->i; + } + + return mem; +} + +static Evas_Object *external_clock_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_clock_params_free(void *params) +{ + Elm_Params_Clock *mem = params; + + free(mem); +} + +static Edje_External_Param_Info external_clock_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_INT("hours"), + EDJE_EXTERNAL_PARAM_INFO_INT("minutes"), + EDJE_EXTERNAL_PARAM_INFO_INT("seconds"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("editable"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("am/pm"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("show seconds"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(clock, "clock") +DEFINE_EXTERNAL_TYPE_SIMPLE(clock, "Clock") diff --git a/src/edje_externals/elm_fileselector.c b/src/edje_externals/elm_fileselector.c new file mode 100644 index 0000000..246698c --- /dev/null +++ b/src/edje_externals/elm_fileselector.c @@ -0,0 +1,185 @@ +#include + +#include "private.h" + +typedef struct _Elm_Params_Fileselector +{ + Elm_Params base; + Eina_Bool is_save:1; + Eina_Bool is_save_set:1; + Eina_Bool folder_only:1; + Eina_Bool folder_only_set:1; + Eina_Bool show_buttons:1; + Eina_Bool show_buttons_set:1; + Eina_Bool expandable:1; + Eina_Bool expandable_set:1; +} Elm_Params_Fileselector; + +static void +external_fileselector_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Fileselector *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if ((p->is_save_set) && (p->is_save)) + elm_fileselector_is_save_set(obj, p->is_save); + if (p->folder_only_set) + elm_fileselector_folder_only_set(obj, p->folder_only); + if (p->show_buttons_set) + elm_fileselector_buttons_ok_cancel_set(obj, p->show_buttons); + if (p->expandable_set) + elm_fileselector_expandable_set(obj, p->expandable); +} + +static Eina_Bool +external_fileselector_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "save")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_is_save_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "folder only")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_folder_only_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "show buttons")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_buttons_ok_cancel_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "expandable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_expandable_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_fileselector_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "save")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_is_save_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "folder only")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_folder_only_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "show buttons")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_buttons_ok_cancel_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "expandable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_expandable_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_fileselector_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Fileselector *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Fileselector)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "save")) + { + mem->is_save = !!param->i; + mem->is_save_set = EINA_TRUE; + } + else if (!strcmp(param->name, "folder only")) + { + mem->folder_only = !!param->i; + mem->folder_only_set = EINA_TRUE; + } + else if (!strcmp(param->name, "show buttons")) + { + mem->show_buttons = !!param->i; + mem->show_buttons_set = EINA_TRUE; + } + else if (!strcmp(param->name, "expandable")) + { + mem->expandable = !!param->i; + mem->expandable_set = EINA_TRUE; + } + } + + return mem; +} + +static Evas_Object *external_fileselector_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_fileselector_params_free(void *params) +{ + Elm_Params_Fileselector *mem = params; + free(mem); +} + +static Edje_External_Param_Info external_fileselector_params[] = + { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_BOOL("save"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("folder only"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("show buttons"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("expandable"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL + }; + +DEFINE_EXTERNAL_ICON_ADD(fileselector, "fileselector") +DEFINE_EXTERNAL_TYPE_SIMPLE(fileselector, "File Selector") + diff --git a/src/edje_externals/elm_fileselector_button.c b/src/edje_externals/elm_fileselector_button.c new file mode 100644 index 0000000..6782b54 --- /dev/null +++ b/src/edje_externals/elm_fileselector_button.c @@ -0,0 +1,252 @@ +#include "private.h" + +typedef struct _Elm_Params_fileselector_button +{ + Elm_Params base; + const char *label; + Evas_Object *icon; + + struct { + const char *path; + Eina_Bool is_save:1; + Eina_Bool is_save_set:1; + Eina_Bool folder_only:1; + Eina_Bool folder_only_set:1; + Eina_Bool expandable:1; + Eina_Bool expandable_set:1; + Eina_Bool inwin_mode:1; + Eina_Bool inwin_mode_set:1; + } fs; +} Elm_Params_fileselector_button; + +static void +external_fileselector_button_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_fileselector_button *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) + elm_fileselector_button_label_set(obj, p->label); + if (p->icon) elm_fileselector_button_icon_set(obj, p->icon); + if (p->fs.path) elm_fileselector_button_path_set(obj, p->fs.path); + if (p->fs.is_save_set) + elm_fileselector_button_is_save_set(obj, p->fs.is_save); + if (p->fs.folder_only_set) + elm_fileselector_button_folder_only_set(obj, p->fs.folder_only); + if (p->fs.expandable_set) + elm_fileselector_button_expandable_set(obj, p->fs.expandable); + if (p->fs.inwin_mode_set) + elm_fileselector_button_inwin_mode_set(obj, p->fs.inwin_mode); +} + +static Eina_Bool +external_fileselector_button_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_fileselector_button_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_fileselector_button_icon_set(obj, icon); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "path")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_fileselector_button_path_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "save")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_button_is_save_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "folder only")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_button_folder_only_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "expandable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_button_expandable_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "inwin mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_button_inwin_mode_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_fileselector_button_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_fileselector_button_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "path")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_fileselector_button_path_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "save")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_button_is_save_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "folder only")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_button_folder_only_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "expandable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_button_expandable_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "inwin mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_button_inwin_mode_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_fileselector_button_params_parse(void *data __UNUSED__, Evas_Object *obj, const Eina_List *params) +{ + Elm_Params_fileselector_button *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_fileselector_button)); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "path")) + mem->fs.path = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "save")) + { + mem->fs.is_save = !!param->i; + mem->fs.is_save_set = EINA_TRUE; + } + else if (!strcmp(param->name, "folder only")) + { + mem->fs.folder_only = !!param->i; + mem->fs.folder_only_set = EINA_TRUE; + } + else if (!strcmp(param->name, "expandable")) + { + mem->fs.expandable = !!param->i; + mem->fs.expandable_set = EINA_TRUE; + } + else if (!strcmp(param->name, "inwin mode")) + { + mem->fs.inwin_mode = !!param->i; + mem->fs.inwin_mode_set = EINA_TRUE; + } + else if (!strcmp(param->name, "label")) + mem->label = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_fileselector_button_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + + static void +external_fileselector_button_params_free(void *params) +{ + Elm_Params_fileselector_button *mem = params; + + if (mem->fs.path) + eina_stringshare_del(mem->fs.path); + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_fileselector_button_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_STRING("path"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("save"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("folder only"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("expandable"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("inwin mode"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(fileselector_button, "fileselector_button"); +DEFINE_EXTERNAL_TYPE_SIMPLE(fileselector_button, "File Selector Button"); diff --git a/src/edje_externals/elm_fileselector_entry.c b/src/edje_externals/elm_fileselector_entry.c new file mode 100644 index 0000000..2389b70 --- /dev/null +++ b/src/edje_externals/elm_fileselector_entry.c @@ -0,0 +1,252 @@ +#include "private.h" + +typedef struct _Elm_Params_fileselector_entry +{ + Elm_Params base; + const char *label; + Evas_Object *icon; + + struct { + const char *path; + Eina_Bool is_save:1; + Eina_Bool is_save_set:1; + Eina_Bool folder_only:1; + Eina_Bool folder_only_set:1; + Eina_Bool expandable:1; + Eina_Bool expandable_set:1; + Eina_Bool inwin_mode:1; + Eina_Bool inwin_mode_set:1; + } fs; +} Elm_Params_fileselector_entry; + +static void +external_fileselector_entry_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_fileselector_entry *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) + elm_fileselector_entry_button_label_set(obj, p->label); + if (p->icon) elm_fileselector_entry_button_icon_set(obj, p->icon); + if (p->fs.path) elm_fileselector_entry_selected_set(obj, p->fs.path); + if (p->fs.is_save_set) + elm_fileselector_entry_is_save_set(obj, p->fs.is_save); + if (p->fs.folder_only_set) + elm_fileselector_entry_folder_only_set(obj, p->fs.folder_only); + if (p->fs.expandable_set) + elm_fileselector_entry_expandable_set(obj, p->fs.expandable); + if (p->fs.inwin_mode_set) + elm_fileselector_entry_inwin_mode_set(obj, p->fs.inwin_mode); +} + +static Eina_Bool +external_fileselector_entry_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_fileselector_entry_button_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_fileselector_entry_button_icon_set(obj, icon); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "path")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_fileselector_entry_selected_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "save")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_entry_is_save_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "folder only")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_entry_folder_only_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "expandable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_entry_expandable_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "inwin mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_fileselector_entry_inwin_mode_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_fileselector_entry_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_fileselector_entry_button_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "path")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_fileselector_entry_selected_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "save")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_entry_is_save_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "folder only")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_entry_folder_only_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "expandable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_entry_expandable_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "inwin mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_fileselector_entry_inwin_mode_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_fileselector_entry_params_parse(void *data __UNUSED__, Evas_Object *obj, const Eina_List *params) +{ + Elm_Params_fileselector_entry *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_fileselector_entry)); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "path")) + mem->fs.path = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "save")) + { + mem->fs.is_save = !!param->i; + mem->fs.is_save_set = EINA_TRUE; + } + else if (!strcmp(param->name, "folder only")) + { + mem->fs.folder_only = !!param->i; + mem->fs.folder_only_set = EINA_TRUE; + } + else if (!strcmp(param->name, "expandable")) + { + mem->fs.expandable = !!param->i; + mem->fs.expandable_set = EINA_TRUE; + } + else if (!strcmp(param->name, "inwin mode")) + { + mem->fs.inwin_mode = !!param->i; + mem->fs.inwin_mode_set = EINA_TRUE; + } + else if (!strcmp(param->name, "label")) + mem->label = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_fileselector_entry_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + + static void +external_fileselector_entry_params_free(void *params) +{ + Elm_Params_fileselector_entry *mem = params; + + if (mem->fs.path) + eina_stringshare_del(mem->fs.path); + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_fileselector_entry_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_STRING("path"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("save"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("folder only"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("expandable"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("inwin mode"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(fileselector_entry, "fileselector_entry"); +DEFINE_EXTERNAL_TYPE_SIMPLE(fileselector_entry, "File Selector Entry"); diff --git a/src/edje_externals/elm_genlist.c b/src/edje_externals/elm_genlist.c new file mode 100644 index 0000000..41eaef8 --- /dev/null +++ b/src/edje_externals/elm_genlist.c @@ -0,0 +1,333 @@ +#include + +#include "private.h" + +typedef struct _Elm_Params_Genlist +{ + Elm_Params base; + const char *horizontal_mode; + Eina_Bool multi:1; + Eina_Bool multi_exists:1; + Eina_Bool always_select:1; + Eina_Bool always_select_exists:1; + Eina_Bool no_select:1; + Eina_Bool no_select_exists:1; + Eina_Bool compress:1; + Eina_Bool compress_exists:1; + Eina_Bool homogeneous:1; + Eina_Bool homogeneous_exists:1; + Eina_Bool h_bounce:1; + Eina_Bool h_bounce_exists:1; + Eina_Bool v_bounce:1; + Eina_Bool v_bounce_exists:1; +} Elm_Params_Genlist; + +static const char* list_horizontal_mode_choices[] = {"compress", "scroll", "limit", "expand", NULL}; + +static Elm_List_Mode +_list_horizontal_mode_setting_get(const char *horizontal_mode_str) +{ + unsigned int i; + + assert(sizeof(list_horizontal_mode_choices)/sizeof(list_horizontal_mode_choices[0]) == ELM_LIST_LAST + 1); + + for (i = 0; i < sizeof(list_horizontal_mode_choices); i++) + { + if (!strcmp(horizontal_mode_str, list_horizontal_mode_choices[i])) + return i; + } + return ELM_LIST_LAST; +} + +static void +external_genlist_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Genlist *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->horizontal_mode) + { + Elm_List_Mode set = _list_horizontal_mode_setting_get(p->horizontal_mode); + + if (set != ELM_LIST_LAST) + elm_genlist_horizontal_mode_set(obj, set); + } + if (p->multi_exists) + elm_genlist_multi_select_set(obj, p->multi); + if (p->always_select_exists) + elm_genlist_always_select_mode_set(obj, p->always_select); + if (p->no_select_exists) + elm_genlist_no_select_mode_set(obj, p->no_select); + if (p->compress_exists) + elm_genlist_compress_mode_set(obj, p->compress); + if (p->homogeneous_exists) + elm_genlist_homogeneous_set(obj, p->homogeneous); + if ((p->h_bounce_exists) && (p->v_bounce_exists)) + elm_genlist_bounce_set(obj, p->h_bounce, p->v_bounce); + else if ((p->h_bounce_exists) || (p->v_bounce_exists)) + { + Eina_Bool h_bounce, v_bounce; + + elm_genlist_bounce_get(obj, &h_bounce, &v_bounce); + if (p->h_bounce_exists) + elm_genlist_bounce_set(obj, p->h_bounce, v_bounce); + else + elm_genlist_bounce_set(obj, h_bounce, p->v_bounce); + } +} + +static Eina_Bool +external_genlist_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "horizontal mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_List_Mode set = _list_horizontal_mode_setting_get(param->s); + + if (set == ELM_LIST_LAST) return EINA_FALSE; + elm_genlist_horizontal_mode_set(obj, set); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "multi select")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_genlist_multi_select_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "always select")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_genlist_always_select_mode_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "no select")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_genlist_no_select_mode_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "compress")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_genlist_compress_mode_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "homogeneous")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_genlist_homogeneous_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "height bounce")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + Eina_Bool h_bounce, v_bounce; + elm_genlist_bounce_get(obj, &h_bounce, &v_bounce); + elm_genlist_bounce_set(obj, param->i, v_bounce); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "width bounce")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + Eina_Bool h_bounce, v_bounce; + elm_genlist_bounce_get(obj, &h_bounce, &v_bounce); + elm_genlist_bounce_set(obj, h_bounce, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_genlist_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "horizontal mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_List_Mode list_horizontal_mode_set = elm_genlist_horizontal_mode_get(obj); + + if (list_horizontal_mode_set == ELM_LIST_LAST) + return EINA_FALSE; + + param->s = list_horizontal_mode_choices[list_horizontal_mode_set]; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "multi select")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_genlist_multi_select_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "always select")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_genlist_always_select_mode_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "no select")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_genlist_no_select_mode_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "compress")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_genlist_compress_mode_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "homogeneous")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_genlist_homogeneous_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "height bounce")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + Eina_Bool h_bounce, v_bounce; + elm_genlist_bounce_get(obj, &h_bounce, &v_bounce); + param->i = h_bounce; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "width bounce")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + Eina_Bool h_bounce, v_bounce; + elm_genlist_bounce_get(obj, &h_bounce, &v_bounce); + param->i = v_bounce; + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_genlist_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Genlist *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = ELM_NEW(Elm_Params_Genlist); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "horizontal mode")) + mem->horizontal_mode = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "multi select")) + { + mem->multi = !!param->i; + mem->multi_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "always select")) + { + mem->always_select = !!param->i; + mem->always_select_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "no select")) + { + mem->no_select = !!param->i; + mem->no_select_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "compress")) + { + mem->compress = !!param->i; + mem->compress_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "homogeneous")) + { + mem->homogeneous = !!param->i; + mem->homogeneous_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "height bounce")) + { + mem->h_bounce = !!param->i; + mem->h_bounce_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "width bounce")) + { + mem->v_bounce = !!param->i; + mem->v_bounce_exists = EINA_TRUE; + } + } + + return mem; +} + +static Evas_Object *external_genlist_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_genlist_params_free(void *params) +{ + Elm_Params_Genlist *mem = params; + + if (mem->horizontal_mode) + eina_stringshare_del(mem->horizontal_mode); + + free(mem); +} + +static Edje_External_Param_Info external_genlist_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("horizontal mode", "scroll", list_horizontal_mode_choices), + EDJE_EXTERNAL_PARAM_INFO_BOOL("multi select"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("always select"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("no select"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("compress"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("homogeneous"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("height bounce"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("width bounce"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(genlist, "genlist"); +DEFINE_EXTERNAL_TYPE_SIMPLE(genlist, "Generic List"); diff --git a/src/edje_externals/elm_hoversel.c b/src/edje_externals/elm_hoversel.c new file mode 100644 index 0000000..de4bbec --- /dev/null +++ b/src/edje_externals/elm_hoversel.c @@ -0,0 +1,148 @@ +#include "private.h" + +typedef struct _Elm_Params_Hoversel +{ + Elm_Params base; + const char *label; + Evas_Object *icon; + Eina_Bool horizontal:1; + Eina_Bool horizontal_exists:1; +} Elm_Params_Hoversel; + +static void +external_hoversel_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Hoversel *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) + elm_hoversel_label_set(obj, p->label); + if (p->icon) + elm_hoversel_icon_set(obj, p->icon); + if (p->horizontal_exists) + elm_hoversel_horizontal_set(obj, p->horizontal); +} + +static Eina_Bool +external_hoversel_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_hoversel_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_hoversel_icon_set(obj, icon); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "horizontal")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_hoversel_horizontal_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_hoversel_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_hoversel_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "horizontal")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_hoversel_horizontal_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_hoversel_params_parse(void *data __UNUSED__, Evas_Object *obj, const Eina_List *params) +{ + Elm_Params_Hoversel *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Hoversel)); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "horizontal")) + { + mem->horizontal = !!param->i; + mem->horizontal_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "label")) + mem->label = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_hoversel_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + + static void +external_hoversel_params_free(void *params) +{ + Elm_Params_Hoversel *mem = params; + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_hoversel_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("horizontal"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(hoversel, "hoversel"); +DEFINE_EXTERNAL_TYPE_SIMPLE(hoversel, "Hoversel"); diff --git a/src/edje_externals/elm_icon.c b/src/edje_externals/elm_icon.c new file mode 100644 index 0000000..bce7a3e --- /dev/null +++ b/src/edje_externals/elm_icon.c @@ -0,0 +1,116 @@ +#include "private.h" + +typedef struct _Elm_Params_Icon +{ + Elm_Params base; + const char *icon; +} Elm_Params_Icon; + +static void +external_icon_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Icon *p; + Evas_Object *edje; + const char *file; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->icon) + { + edje = evas_object_smart_parent_get(obj); + edje_object_file_get(edje, &file, NULL); + + if (!elm_icon_file_set(obj, file, p->icon)) + elm_icon_standard_set(obj, p->icon); + } +} + +static Eina_Bool +external_icon_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + Evas_Object *edje; + const char *file; + + if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + edje = evas_object_smart_parent_get(obj); + edje_object_file_get(edje, &file, NULL); + + if (!elm_icon_file_set(obj, file, param->s)) + elm_icon_standard_set(obj, param->s); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_icon_param_get(void *data __UNUSED__, const Evas_Object *obj __UNUSED__, Edje_External_Param *param) +{ + if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_icon_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Icon *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = ELM_NEW(Elm_Params_Icon); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "icon")) + { + mem->icon = eina_stringshare_add(param->s); + } + } + + return mem; +} + +static Evas_Object *external_icon_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("no content"); + return NULL; +} + +static void +external_icon_params_free(void *params) +{ + Elm_Params_Icon *mem = params; + + if (mem->icon) + eina_stringshare_del(mem->icon); + external_common_params_free(params); +} + +static Edje_External_Param_Info external_icon_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(icon, "icon"); +DEFINE_EXTERNAL_TYPE_SIMPLE(icon, "Icon"); diff --git a/src/edje_externals/elm_label.c b/src/edje_externals/elm_label.c new file mode 100644 index 0000000..09f8970 --- /dev/null +++ b/src/edje_externals/elm_label.c @@ -0,0 +1,87 @@ +#include "private.h" + +typedef struct _Elm_Params_Label +{ + Elm_Params base; +} Elm_Params_Label; + +static void +external_label_state_set(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Label *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + //if (p->base.label) elm_label_label_set(obj, p->base.label); +} + +static Eina_Bool +external_label_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_label_label_set(obj, param->s); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_label_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_label_label_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_label_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params __UNUSED__) +{ + Elm_Params_Label *mem; + + mem = ELM_NEW(Elm_Params_Label); + if (!mem) + return NULL; + + return mem; +} + +static Evas_Object *external_label_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("no content"); + return NULL; +} + +static void +external_label_params_free(void *params) +{ + external_common_params_free(params); +} + +static Edje_External_Param_Info external_label_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(label, "label"); +DEFINE_EXTERNAL_TYPE_SIMPLE(label, "label"); diff --git a/src/edje_externals/elm_list.c b/src/edje_externals/elm_list.c new file mode 100644 index 0000000..1d81349 --- /dev/null +++ b/src/edje_externals/elm_list.c @@ -0,0 +1,305 @@ +#include + +#include "private.h" + +typedef struct _Elm_Params_List +{ + Elm_Params base; + const char *policy_h; + const char *policy_v; + const char *mode; + Eina_Bool h_mode : 1; + Eina_Bool h_mode_exists : 1; + Eina_Bool multi : 1; + Eina_Bool multi_exists : 1; + Eina_Bool always_select : 1; + Eina_Bool always_select_exists : 1; +} Elm_Params_List; + +#define CHOICE_GET(CHOICES, STR) \ + unsigned int i; \ + for (i = 0; i < sizeof(CHOICES); i++) \ + if (strcmp(STR, CHOICES[i]) == 0) \ + return i + +static const char *scroller_policy_choices[] = {"auto", "on", "off", NULL}; +static const char *list_mode_choices[] = {"compress", "scroll", "limit", + "expand", NULL}; + +static Elm_Scroller_Policy +_scroller_policy_choices_setting_get(const char *policy_str) +{ + assert(sizeof(scroller_policy_choices)/ + sizeof(scroller_policy_choices[0]) == ELM_SCROLLER_POLICY_LAST + 1); + CHOICE_GET(scroller_policy_choices, policy_str); + return ELM_SCROLLER_POLICY_LAST; +} + +static Elm_List_Mode +_list_mode_setting_get(const char *mode_str) +{ + assert(sizeof(list_mode_choices)/sizeof(list_mode_choices[0]) == + ELM_LIST_LAST + 1); + CHOICE_GET(list_mode_choices, mode_str); + return ELM_LIST_LAST; +} + +static void +external_list_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_List *p; + Elm_Scroller_Policy policy_h, policy_v; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->mode) + { + Elm_List_Mode set = _list_mode_setting_get(p->mode); + + if (set != ELM_LIST_LAST) + elm_list_mode_set(obj, set); + } + + if ((p->policy_h) && (p->policy_v)) + { + policy_h = _scroller_policy_choices_setting_get(p->policy_h); + policy_v = _scroller_policy_choices_setting_get(p->policy_v); + elm_list_scroller_policy_set(obj, policy_h, policy_v); + } + else if ((p->policy_h) || (p->policy_v)) + { + elm_list_scroller_policy_get(obj, &policy_h, &policy_v); + if (p->policy_h) + { + policy_h = _scroller_policy_choices_setting_get(p->policy_h); + elm_list_scroller_policy_set(obj, policy_h, policy_v); + } + else + { + policy_v = _scroller_policy_choices_setting_get(p->policy_v); + elm_list_scroller_policy_set(obj, policy_h, policy_v); + } + } + + if (p->h_mode_exists) + elm_list_horizontal_set(obj, p->h_mode); + if (p->multi_exists) + elm_list_multi_select_set(obj, p->multi); + if (p->always_select_exists) + elm_list_always_select_mode_set(obj, p->always_select); +} + +static Eina_Bool +external_list_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "list mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_List_Mode set = _list_mode_setting_get(param->s); + if (set == ELM_LIST_LAST) return EINA_FALSE; + elm_list_mode_set(obj, set); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "horizontal scroll")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Scroller_Policy h, v; + elm_list_scroller_policy_get(obj, &h, &v); + h = _scroller_policy_choices_setting_get(param->s); + if (h == ELM_SCROLLER_POLICY_LAST) return EINA_FALSE; + elm_list_scroller_policy_set(obj, h, v); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "vertical scroll")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Scroller_Policy h, v; + elm_list_scroller_policy_get(obj, &h, &v); + v = _scroller_policy_choices_setting_get(param->s); + if (v == ELM_SCROLLER_POLICY_LAST) return EINA_FALSE; + elm_list_scroller_policy_set(obj, h, v); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "horizontal mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_list_horizontal_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "multi-select mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_list_multi_select_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "always-select mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_list_always_select_mode_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_list_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "horizontal mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_list_horizontal_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "multi-select mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_list_multi_select_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "always-select mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_list_always_select_mode_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "horizontal scroll")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Scroller_Policy h, v; + elm_list_scroller_policy_get(obj, &h, &v); + + param->s = scroller_policy_choices[h]; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "vertical scroll")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Scroller_Policy h, v; + elm_list_scroller_policy_get(obj, &h, &v); + + param->s = scroller_policy_choices[v]; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "list mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_List_Mode m = elm_list_mode_get(obj); + + if (m == ELM_LIST_LAST) + return EINA_FALSE; + + param->s = list_mode_choices[m]; + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_list_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_List *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = ELM_NEW(Elm_Params_List); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "horizontal mode")) + { + mem->h_mode = param->i; + mem->h_mode_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "multi-select mode")) + { + mem->multi = param->i; + mem->multi_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "always-select mode")) + { + mem->always_select = param->i; + mem->always_select_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "horizontal scroll")) + mem->policy_h = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "vertical scroll")) + mem->policy_v = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "list mode")) + mem->mode = eina_stringshare_add(param->s); + } + return mem; +} + +static Evas_Object *external_list_content_get(void *data __UNUSED__, const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_list_params_free(void *params) +{ + Elm_Params_List *mem = params; + + if (mem->mode) + eina_stringshare_del(mem->mode); + if (mem->policy_h) + eina_stringshare_del(mem->policy_h); + if (mem->policy_v) + eina_stringshare_del(mem->policy_v); + + free(mem); +} + +static Edje_External_Param_Info external_list_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("list mode", "scroll", + list_mode_choices), + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("horizontal scroll", "auto", + scroller_policy_choices), + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("vertical scroll", "auto", + scroller_policy_choices), + EDJE_EXTERNAL_PARAM_INFO_BOOL("horizontal mode"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("multi-select mode"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("always-select mode"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(list, "list") +DEFINE_EXTERNAL_TYPE_SIMPLE(list, "List"); diff --git a/src/edje_externals/elm_map.c b/src/edje_externals/elm_map.c new file mode 100644 index 0000000..c5e8386 --- /dev/null +++ b/src/edje_externals/elm_map.c @@ -0,0 +1,207 @@ +#include + +#include "private.h" + +typedef struct _Elm_Params_Map +{ + Elm_Params base; + const char *map_source; + const char *zoom_mode; + double zoom; + Eina_Bool zoom_set:1; +} Elm_Params_Map; + +static const char *zoom_choices[] = {"manual", "auto fit", "auto fill", NULL}; + +static const char *source_choices[] = + {"Mapnik", "Osmarender", "Cycle Map", "Maplint", + "Custom 1", "Custom 2", "Custom 3", "Custom 4", + "Custom 5", "Custom 6", "Custom 7"}; + +static Elm_Map_Zoom_Mode +_zoom_mode_get(const char *map_src) +{ + unsigned int i; + + assert(sizeof(zoom_choices)/sizeof(zoom_choices[0]) == + ELM_MAP_ZOOM_MODE_LAST + 1); + + for (i = 0; i < sizeof(zoom_choices); i++) + if (!strcmp(map_src, zoom_choices[i])) return i; + + return ELM_MAP_ZOOM_MODE_LAST; +} + +static Elm_Map_Sources +_map_source_get(const char *map_src) +{ + unsigned int i; + + assert(sizeof(source_choices)/sizeof(source_choices[0]) == + ELM_MAP_SOURCE_LAST); + + for (i = 0; i < sizeof(source_choices); i++) + if (!strcmp(map_src, source_choices[i])) return i; + + return ELM_MAP_SOURCE_LAST; +} + +static void +external_map_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Map *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->map_source) + { + Elm_Map_Sources set = _map_source_get(p->map_source); + if (set == ELM_MAP_SOURCE_LAST) return; + elm_map_source_set(obj, set); + } + if (p->zoom_mode) + { + Elm_Map_Zoom_Mode set = _zoom_mode_get(p->zoom_mode); + if (set == ELM_MAP_ZOOM_MODE_LAST) return; + elm_map_zoom_mode_set(obj, set); + } + if (p->zoom_set) elm_map_zoom_set(obj, p->zoom); +} + +static Eina_Bool +external_map_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "map source")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Map_Sources set = _map_source_get(param->s); + if (set == ELM_MAP_SOURCE_LAST) return EINA_FALSE; + elm_map_source_set(obj, set); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "zoom mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Map_Zoom_Mode set = _zoom_mode_get(param->s); + if (set == ELM_MAP_ZOOM_MODE_LAST) return EINA_FALSE; + elm_map_zoom_mode_set(obj, set); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "zoom level")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + elm_map_zoom_set(obj, param->d); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_map_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "map source")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Map_Sources set = elm_map_source_get(obj); + if (set == ELM_MAP_SOURCE_LAST) return EINA_FALSE; + param->s = source_choices[set]; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "zoom mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Map_Zoom_Mode set = elm_map_zoom_mode_get(obj); + if (set == ELM_MAP_ZOOM_MODE_LAST) return EINA_FALSE; + param->s = zoom_choices[set]; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "zoom level")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + param->d = elm_map_zoom_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_map_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Map *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Map)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "map source")) + mem->map_source = eina_stringshare_add(param->s); + if (!strcmp(param->name, "zoom mode")) + mem->zoom_mode = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "zoom level")) + { + mem->zoom = param->d; + mem->zoom_set = EINA_TRUE; + } + } + + return mem; +} + +static Evas_Object *external_map_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_map_params_free(void *params) +{ + Elm_Params_Map *mem = params; + + if (mem->map_source) + eina_stringshare_del(mem->map_source); + if (mem->zoom_mode) + eina_stringshare_del(mem->zoom_mode); + free(mem); +} + +static Edje_External_Param_Info external_map_params[] = + { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("map source", "Mapnik", + source_choices), + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("zoom mode", "manual", zoom_choices), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("zoom level"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL + }; + +DEFINE_EXTERNAL_ICON_ADD(map, "map") +DEFINE_EXTERNAL_TYPE_SIMPLE(map, "Map") + diff --git a/src/edje_externals/elm_notify.c b/src/edje_externals/elm_notify.c new file mode 100644 index 0000000..3eab33a --- /dev/null +++ b/src/edje_externals/elm_notify.c @@ -0,0 +1,199 @@ +#include "private.h" +#include + + +typedef struct _Elm_Params_Notify Elm_Params_Notify; + +struct _Elm_Params_Notify { + Elm_Params base; + Evas_Object *content; /* part name whose obj is to be set as content */ + Eina_Bool repeat_events_exists; + Eina_Bool repeat_events; + Eina_Bool timeout_exists; + double timeout; + + const char *orient; +}; + + +static const char *orients[] = { + "top", + "center", + "bottom", + "left", + "right", + "top_left", + "top_right", + "bottom_left", + "bottom_right", + NULL +}; + +static Elm_Notify_Orient _orient_get(const char *orient) +{ + unsigned int i; + + assert(sizeof(orients)/sizeof(orients[0]) == + ELM_NOTIFY_ORIENT_LAST + 1); + + for (i = 0; i < sizeof(orients); i++) + if (!strcmp(orient, orients[i])) return i; + + return ELM_NOTIFY_ORIENT_LAST; +} + +static void external_notify_state_set(void *data __UNUSED__, + Evas_Object *obj, const void *from_params, + const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Notify *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->content) { + elm_notify_content_set(obj, p->content); + } + if (p->repeat_events_exists) + elm_notify_repeat_events_set(obj, p->repeat_events); + if (p->timeout_exists) + elm_notify_timeout_set(obj, p->timeout); + if (p->orient) + { + Elm_Notify_Orient set = _orient_get(p->orient); + if (set == ELM_NOTIFY_ORIENT_LAST) return; + elm_notify_orient_set(obj, set); + } +} + +static Eina_Bool external_notify_param_set(void *data __UNUSED__, + Evas_Object *obj, const Edje_External_Param *param) +{ + if ((!strcmp(param->name, "content")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING)) + { + Evas_Object *content = external_common_param_edje_object_get(obj, param); + if ((strcmp(param->s, "")) && (!content)) + return EINA_FALSE; + elm_notify_content_set(obj, content); + return EINA_TRUE; + } + else if ((!strcmp(param->name, "repeat_events")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL)) + { + elm_notify_repeat_events_set(obj, param->i); + return EINA_TRUE; + } + else if ((!strcmp(param->name, "timeout")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE)) + { + elm_notify_timeout_set(obj, param->d); + return EINA_TRUE; + } + else if ((!strcmp(param->name, "orient")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE)) + { + Elm_Notify_Orient set = _orient_get(param->s); + if (set == ELM_NOTIFY_ORIENT_LAST) return EINA_FALSE; + elm_notify_orient_set(obj, set); + return EINA_TRUE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool external_notify_param_get(void *data __UNUSED__, + const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "content")) + { + /* not easy to get content name back from live object */ + return EINA_FALSE; + } + else if ((!strcmp(param->name, "repeat_events")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL)) + { + param->i = elm_notify_repeat_events_get(obj); + return EINA_TRUE; + } + else if ((!strcmp(param->name, "timeout")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE)) + { + param->d = elm_notify_timeout_get(obj); + return EINA_TRUE; + } + else if ((!strcmp(param->name, "orient")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE)) + { + Elm_Notify_Orient set = elm_notify_orient_get(obj); + if (set == ELM_NOTIFY_ORIENT_LAST) return EINA_FALSE; + param->s = orients[set]; + return EINA_TRUE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * external_notify_params_parse(void *data __UNUSED__, Evas_Object *obj, + const Eina_List *params) { + Elm_Params_Notify *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Notify)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "content")) + mem->content = external_common_param_edje_object_get(obj, param); + else if (!strcmp(param->name, "timeout")) + { + mem->timeout = param->d; + mem->timeout_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "repeat_events")) + { + mem->repeat_events = param->i; + mem->repeat_events_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "orient")) + mem->orient = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_notify_content_get(void *data __UNUSED__, + const Evas_Object *obj, const char *content) +{ + if (!strcmp(content, "content")) + return elm_notify_content_get(obj); + + ERR("unknown content '%s'", content); + return NULL; +} + +static void external_notify_params_free(void *params) { + free(params); +} + +static Edje_External_Param_Info external_notify_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("content"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("repeat_events"), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("timeout"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(notify, "notify"); +DEFINE_EXTERNAL_TYPE_SIMPLE(notify, "Notify") +; diff --git a/src/edje_externals/elm_panes.c b/src/edje_externals/elm_panes.c new file mode 100644 index 0000000..a965d31 --- /dev/null +++ b/src/edje_externals/elm_panes.c @@ -0,0 +1,171 @@ +#include "private.h" +#include + + +typedef struct _Elm_Params_Panes Elm_Params_Panes; + +struct _Elm_Params_Panes { + Elm_Params base; + Evas_Object *content_left; + Evas_Object *content_right; + Eina_Bool is_horizontal; + Eina_Bool horizontal; + Eina_Bool is_left_size; + double left_size; +}; + +static void external_panes_state_set(void *data __UNUSED__, + Evas_Object *obj, const void *from_params, + const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Panes *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->content_left) + elm_panes_content_left_set(obj, p->content_left); + + if (p->content_right) + elm_panes_content_right_set(obj, p->content_right); + + if(p->is_left_size) + elm_panes_content_left_size_set(obj, p->left_size); + + if(p->is_horizontal) + elm_panes_horizontal_set(obj, p->horizontal); +} + +static Eina_Bool external_panes_param_set(void *data __UNUSED__, + Evas_Object *obj, const Edje_External_Param *param) +{ + if ((!strcmp(param->name, "content left")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING)) + { + Evas_Object *content = external_common_param_edje_object_get(obj, param); + if ((strcmp(param->s, "")) && (!content)) + return EINA_FALSE; + elm_panes_content_left_set(obj, content); + return EINA_TRUE; + } + else if ((!strcmp(param->name, "content right")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING)) + { + Evas_Object *content = external_common_param_edje_object_get(obj, param); + if ((strcmp(param->s, "")) && (!content)) + return EINA_FALSE; + elm_panes_content_right_set(obj, content); + return EINA_TRUE; + } + else if ((!strcmp(param->name, "horizontal")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL)) + { + elm_panes_horizontal_set(obj, param->i); + return EINA_TRUE; + } + else if ((!strcmp(param->name, "left size")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE)) + { + elm_panes_content_left_size_set(obj, param->d); + return EINA_TRUE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool external_panes_param_get(void *data __UNUSED__, + const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "content left")) + { + /* not easy to get content name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "content right")) + { + /* not easy to get content name back from live object */ + return EINA_FALSE; + } + else if ((!strcmp(param->name, "horizontal")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL)) + { + param->i = elm_panes_horizontal_get(obj); + return EINA_TRUE; + } + else if ((!strcmp(param->name, "left size")) + && (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE)) + { + param->d = elm_panes_content_left_size_get(obj); + return EINA_TRUE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * external_panes_params_parse(void *data __UNUSED__, Evas_Object *obj, + const Eina_List *params) { + Elm_Params_Panes *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Panes)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "content left")) + mem->content_left = external_common_param_edje_object_get(obj, param); + else if (!strcmp(param->name, "content right")) + mem->content_right = external_common_param_edje_object_get(obj, param); + else if (!strcmp(param->name, "horizontal")) + { + mem->is_horizontal = EINA_TRUE; + mem->horizontal = param->i; + } + else if (!strcmp(param->name, "left size")) + { + mem->is_left_size = EINA_TRUE; + mem->left_size = param->d; + } + } + + return mem; +} + +static Evas_Object *external_panes_content_get(void *data __UNUSED__, + const Evas_Object *obj, const char *content) +{ + if (!strcmp(content, "left")) + return elm_panes_content_left_get(obj); + else if (!strcmp(content, "right")) + return elm_panes_content_right_get(obj); + + ERR("unknown content '%s'", content); + + return NULL; +} + + +static void external_panes_params_free(void *params) { + free(params); +} + +static Edje_External_Param_Info external_panes_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("content left"), + EDJE_EXTERNAL_PARAM_INFO_STRING("content right"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("horizontal"), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("left size"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(panes, "panes"); +DEFINE_EXTERNAL_TYPE_SIMPLE(panes, "panes"); diff --git a/src/edje_externals/elm_photocam.c b/src/edje_externals/elm_photocam.c new file mode 100644 index 0000000..a38e708 --- /dev/null +++ b/src/edje_externals/elm_photocam.c @@ -0,0 +1,208 @@ +#include + +#include "private.h" + +typedef struct _Elm_Params_Photocam +{ + Elm_Params base; + const char *file; + double zoom; + const char *zoom_mode; + Eina_Bool paused:1; + Eina_Bool paused_exists:1; + Eina_Bool zoom_exists:1; +} Elm_Params_Photocam; + +static const char* choices[] = {"manual", "auto fit", "auto fill", NULL}; + +static Elm_Photocam_Zoom_Mode +_zoom_mode_setting_get(const char *zoom_mode_str) +{ + unsigned int i; + + assert(sizeof(choices)/sizeof(choices[0]) == ELM_PHOTOCAM_ZOOM_MODE_LAST + 1); + + for (i = 0; i < sizeof(choices); i++) + { + if (!strcmp(zoom_mode_str, choices[i])) + return i; + } + return ELM_PHOTOCAM_ZOOM_MODE_LAST; +} + +static void +external_photocam_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Photocam *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->file) + elm_photocam_file_set(obj, p->file); + if (p->zoom_exists) + elm_photocam_zoom_set(obj, p->zoom); + if (p->zoom_mode) + { + Elm_Photocam_Zoom_Mode set = _zoom_mode_setting_get(p->zoom_mode); + if (set == ELM_PHOTOCAM_ZOOM_MODE_LAST) return; + elm_photocam_zoom_mode_set(obj, set); + } + if (p->paused_exists) + elm_photocam_paused_set(obj, p->paused); +} + +static Eina_Bool +external_photocam_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "file")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_photocam_file_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "zoom")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + elm_photocam_zoom_set(obj, param->d); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "zoom mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Elm_Photocam_Zoom_Mode set = _zoom_mode_setting_get(param->s); + if (set == ELM_PHOTOCAM_ZOOM_MODE_LAST) return EINA_FALSE; + elm_photocam_zoom_mode_set(obj, set); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "paused")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_photocam_paused_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_photocam_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "file")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_photocam_file_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "zoom")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + param->d = elm_photocam_zoom_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "zoom mode")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Elm_Photocam_Zoom_Mode zoom_mode_set = elm_photocam_zoom_mode_get(obj); + + if (zoom_mode_set == ELM_PHOTOCAM_ZOOM_MODE_LAST) + return EINA_FALSE; + + param->s = choices[zoom_mode_set]; + return EINA_TRUE; + } + } + else if(!strcmp(param->name, "paused")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_photocam_paused_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_photocam_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Photocam *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Photocam)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "file")) + mem->file = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "zoom")) + { + mem->zoom = param->d; + mem->zoom_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "zoom mode")) + mem->zoom_mode = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "paused")) + { + mem->paused = !!param->i; + mem->paused_exists = EINA_TRUE; + } + } + + return mem; +} + +static Evas_Object *external_photocam_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_photocam_params_free(void *params) +{ + Elm_Params_Photocam *mem = params; + + if (mem->file) + eina_stringshare_del(mem->file); + if (mem->zoom_mode) + eina_stringshare_del(mem->zoom_mode); + free(mem); +} + +static Edje_External_Param_Info external_photocam_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("file"), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("zoom"), + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("zoom mode", "manual", choices), + EDJE_EXTERNAL_PARAM_INFO_BOOL("paused"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(photocam, "photocam"); +DEFINE_EXTERNAL_TYPE_SIMPLE(photocam, "Photocam"); diff --git a/src/edje_externals/elm_progressbar.c b/src/edje_externals/elm_progressbar.c new file mode 100644 index 0000000..d7bdee3 --- /dev/null +++ b/src/edje_externals/elm_progressbar.c @@ -0,0 +1,251 @@ +#include "private.h" + +typedef struct _Elm_Params_Progressbar +{ + Elm_Params base; + const char *label; + Evas_Object *icon; + const char *unit; + double value; + Evas_Coord span; + Eina_Bool value_exists:1; + Eina_Bool span_exists:1; + Eina_Bool inverted:1; + Eina_Bool inverted_exists:1; + Eina_Bool horizontal:1; + Eina_Bool horizontal_exists:1; +} Elm_Params_Progressbar; + +static void +external_progressbar_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Progressbar *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) + elm_progressbar_label_set(obj, p->label); + if (p->icon) + elm_progressbar_icon_set(obj, p->icon); + if (p->span_exists) + elm_progressbar_span_size_set(obj, p->span); + if (p->value_exists) + elm_progressbar_value_set(obj, p->value); + if (p->inverted_exists) + elm_progressbar_inverted_set(obj, p->inverted); + if (p->horizontal_exists) + elm_progressbar_horizontal_set(obj, p->horizontal); + if (p->unit) + elm_progressbar_unit_format_set(obj, p->unit); +} + +static Eina_Bool +external_progressbar_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_progressbar_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_progressbar_icon_set(obj, icon); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "value")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + elm_progressbar_value_set(obj, param->d); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "horizontal")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_progressbar_horizontal_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "inverted")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_progressbar_inverted_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "span")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + elm_progressbar_span_size_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "unit format")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_progressbar_unit_format_set(obj, param->s); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_progressbar_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_progressbar_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "value")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + param->d = elm_progressbar_value_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "horizontal")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_progressbar_horizontal_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "inverted")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_progressbar_inverted_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "span")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + param->i = elm_progressbar_span_size_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "unit format")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_progressbar_unit_format_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_progressbar_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Progressbar *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Progressbar)); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "span")) + { + mem->span = param->i; + mem->span_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "value")) + { + mem->value = param->d; + mem->value_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "inverted")) + { + mem->inverted = !!param->i; + mem->inverted_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "horizontal")) + { + mem->horizontal = !!param->i; + mem->horizontal_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "unit format")) + mem->unit = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "label")) + mem->label = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_progressbar_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_progressbar_params_free(void *params) +{ + Elm_Params_Progressbar *mem = params; + + if (mem->unit) + eina_stringshare_del(mem->unit); + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_progressbar_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("value"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("horizontal"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("inverted"), + EDJE_EXTERNAL_PARAM_INFO_INT("span"), + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("unit format", "%1.2f"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(progressbar, "progressbar") +DEFINE_EXTERNAL_TYPE_SIMPLE(progressbar, "Progressbar") diff --git a/src/edje_externals/elm_radio.c b/src/edje_externals/elm_radio.c new file mode 100644 index 0000000..1345122 --- /dev/null +++ b/src/edje_externals/elm_radio.c @@ -0,0 +1,176 @@ +#include "private.h" + +typedef struct _Elm_Params_Radio +{ + Elm_Params base; + const char *label; + Evas_Object *icon; + const char* group_name; + int value; + Eina_Bool value_exists:1; +} Elm_Params_Radio; + +static void +external_radio_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Radio *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) + elm_radio_label_set(obj, p->label); + if (p->icon) + elm_radio_icon_set(obj, p->icon); + if (p->value_exists) + elm_radio_state_value_set(obj, p->value); + if (p->group_name) + { + Evas_Object *ed = evas_object_smart_parent_get(obj); + Evas_Object *group = edje_object_part_swallow_get(ed, p->group_name); + elm_radio_group_add(obj, group); + } +} + +static Eina_Bool +external_radio_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_radio_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_radio_icon_set(obj, icon); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "value")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + elm_radio_value_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "group")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *ed = evas_object_smart_parent_get(obj); + Evas_Object *group = edje_object_part_swallow_get(ed, param->s); + elm_radio_group_add(obj, group); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_radio_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_radio_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "value")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + param->i = elm_radio_value_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "group")) + { + /* not easy to get group name back from live object */ + return EINA_FALSE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_radio_params_parse(void *data __UNUSED__, Evas_Object *obj, const Eina_List *params) +{ + Elm_Params_Radio *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Radio)); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "group")) + mem->group_name = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "value")) + { + mem->value = param->i; + mem->value_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "label")) + mem->label = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_radio_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_radio_params_free(void *params) +{ + Elm_Params_Radio *mem = params; + + if (mem->group_name) + eina_stringshare_del(mem->group_name); + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_radio_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_STRING("group"), + EDJE_EXTERNAL_PARAM_INFO_INT("value"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(radio, "radio") +DEFINE_EXTERNAL_TYPE_SIMPLE(radio, "Radio") diff --git a/src/edje_externals/elm_scrolled_entry.c b/src/edje_externals/elm_scrolled_entry.c new file mode 100644 index 0000000..266e0e1 --- /dev/null +++ b/src/edje_externals/elm_scrolled_entry.c @@ -0,0 +1,184 @@ +#include "private.h" + +typedef struct _Elm_Params_Entry +{ + Elm_Params base; + const char *text; + Eina_Bool text_set:1; + Eina_Bool editable:1; + Eina_Bool single:1; + Eina_Bool password:1; + Eina_Bool editable_exists:1; + Eina_Bool single_exists:1; + Eina_Bool password_exists:1; +} Elm_Params_Entry; + +static void +external_scrolled_entry_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Entry *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if ((!p->text_set) && (p->text)) + { + elm_scrolled_entry_entry_set(obj, p->text); + ((Elm_Params_Entry *)p)->text_set = EINA_TRUE; + } + if (p->editable_exists) + elm_scrolled_entry_editable_set(obj, p->editable); + if (p->single_exists) + elm_scrolled_entry_single_line_set(obj, p->single); + if (p->password_exists) + elm_scrolled_entry_password_set(obj, p->password); +} + +static Eina_Bool +external_scrolled_entry_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "text")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_scrolled_entry_entry_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "editable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_scrolled_entry_editable_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "single line")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_scrolled_entry_single_line_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "password")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_scrolled_entry_password_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_scrolled_entry_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "text")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_scrolled_entry_entry_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "editable")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_scrolled_entry_editable_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "single line")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_scrolled_entry_single_line_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "password")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_scrolled_entry_password_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_scrolled_entry_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Entry *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Entry)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "text")) + mem->text = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "single line")) + { + mem->single = !!param->i; + mem->single_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "password")) + { + mem->password = !!param->i; + mem->password_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "editable")) + { + mem->editable = param->i; + mem->editable_exists = EINA_TRUE; + } + } + + return mem; +} + +static Evas_Object *external_scrolled_entry_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_scrolled_entry_params_free(void *params) +{ + Elm_Params_Entry *mem = params; + + if (mem->text) + eina_stringshare_del(mem->text); + free(mem); +} + +static Edje_External_Param_Info external_scrolled_entry_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("text", "some text"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("editable"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("single line"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("password"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(scrolled_entry, "scrolled_entry") +DEFINE_EXTERNAL_TYPE_SIMPLE(scrolled_entry, "Entry"); diff --git a/src/edje_externals/elm_scroller.c b/src/edje_externals/elm_scroller.c new file mode 100644 index 0000000..ccec362 --- /dev/null +++ b/src/edje_externals/elm_scroller.c @@ -0,0 +1,104 @@ +#include "private.h" +#include + + +typedef struct _Elm_Params_Scroller Elm_Params_Scroller; + +struct _Elm_Params_Scroller { + Elm_Params base; + Evas_Object *content; +}; + + + +static void external_scroller_state_set(void *data __UNUSED__, + Evas_Object *obj, const void *from_params, + const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Scroller *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->content) { + elm_scroller_content_set(obj, p->content); + } +} + +static Eina_Bool external_scroller_param_set(void *data __UNUSED__, + Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "content") + && param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *content = external_common_param_edje_object_get(obj, param); + if ((strcmp(param->s, "")) && (!content)) + return EINA_FALSE; + elm_scroller_content_set(obj, content); + return EINA_TRUE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool external_scroller_param_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, Edje_External_Param *param) +{ + if (!strcmp(param->name, "content")) + { + /* not easy to get content name back from live object */ + return EINA_FALSE; + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * external_scroller_params_parse(void *data __UNUSED__, Evas_Object *obj, + const Eina_List *params) { + Elm_Params_Scroller *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = ELM_NEW(Elm_Params_Scroller); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "content")) + mem->content = external_common_param_edje_object_get(obj, param); + } + + return mem; +} + +static Evas_Object *external_scroller_content_get(void *data __UNUSED__, + const Evas_Object *obj, const char *content) +{ + if (!strcmp(content, "content")) + return elm_scroller_content_get(obj); + + ERR("unknown content '%s'", content); + return NULL; +} + +static void external_scroller_params_free(void *params) { + external_common_params_free(params); +} + +static Edje_External_Param_Info external_scroller_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("content"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(scroller, "scroller"); +DEFINE_EXTERNAL_TYPE_SIMPLE(scroller, "Scroller") +; diff --git a/src/edje_externals/elm_slider.c b/src/edje_externals/elm_slider.c new file mode 100644 index 0000000..b559400 --- /dev/null +++ b/src/edje_externals/elm_slider.c @@ -0,0 +1,339 @@ +#include "private.h" + +typedef struct _Elm_Params_Slider +{ + Elm_Params base; + const char *label; + Evas_Object *icon; + const char *indicator, *unit; + double min, max, value; + Eina_Bool min_exists:1; + Eina_Bool max_exists:1; + Eina_Bool value_exists:1; + Eina_Bool inverted:1; + Eina_Bool inverted_exists:1; + Eina_Bool span:1; + Eina_Bool span_exists:1; + Eina_Bool horizontal:1; + Eina_Bool horizontal_exists:1; +} Elm_Params_Slider; + +static void +external_slider_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Slider *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) + elm_slider_label_set(obj, p->label); + if (p->icon) + elm_slider_icon_set(obj, p->icon); + if (p->span_exists) + elm_slider_span_size_set(obj, p->span); + if ((p->min_exists) && (p->max_exists)) + elm_slider_min_max_set(obj, p->min, p->max); + else if ((p->min_exists) || (p->max_exists)) + { + double min, max; + elm_slider_min_max_get(obj, &min, &max); + if (p->min_exists) + elm_slider_min_max_set(obj, p->min, max); + else + elm_slider_min_max_set(obj, min, p->max); + } + if (p->value_exists) + elm_slider_value_set(obj, p->value); + if (p->inverted_exists) + elm_slider_inverted_set(obj, p->inverted); + if (p->horizontal_exists) + elm_slider_horizontal_set(obj, p->horizontal); + if (p->indicator) + elm_slider_indicator_format_set(obj, p->indicator); + if (p->unit) + elm_slider_unit_format_set(obj, p->unit); +} + +static Eina_Bool +external_slider_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_slider_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_slider_icon_set(obj, icon); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "min")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + double min, max; + elm_slider_min_max_get(obj, &min, &max); + elm_slider_min_max_set(obj, param->d, max); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "max")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + double min, max; + elm_slider_min_max_get(obj, &min, &max); + elm_slider_min_max_set(obj, min, param->d); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "value")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + elm_slider_value_set(obj, param->d); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "horizontal")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_slider_horizontal_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "inverted")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_slider_inverted_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "span")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + elm_slider_span_size_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "unit format")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_slider_unit_format_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "indicator format")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_slider_indicator_format_set(obj, param->s); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_slider_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_slider_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "min")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + double min, max; + elm_slider_min_max_get(obj, &min, &max); + param->d = min; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "max")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + double min, max; + elm_slider_min_max_get(obj, &min, &max); + param->d = max; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "value")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + param->d = elm_slider_value_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "horizontal")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_slider_horizontal_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "inverted")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_slider_inverted_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "span")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + param->i = elm_slider_span_size_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "unit format")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_slider_unit_format_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "indicator format")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_slider_indicator_format_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_slider_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Slider *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Slider)); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "span")) + { + mem->span = param->i; + mem->span_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "min")) + { + mem->min = param->d; + mem->min_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "max")) + { + mem->max = param->d; + mem->max_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "value")) + { + mem->value = param->d; + mem->value_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "inverted")) + { + mem->inverted = param->i; + mem->inverted_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "horizontal")) + { + mem->horizontal = param->i; + mem->horizontal_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "unit format")) + mem->unit = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "indicator format")) + mem->indicator = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "label")) + mem->label = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_slider_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_slider_params_free(void *params) +{ + Elm_Params_Slider *mem = params; + + if (mem->unit) + eina_stringshare_del(mem->unit); + if (mem->indicator) + eina_stringshare_del(mem->indicator); + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_slider_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("min"), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE_DEFAULT("max", 10.0), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("value"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("horizontal"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("inverted"), + EDJE_EXTERNAL_PARAM_INFO_INT("span"), + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("unit format", "%1.2f"), + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("indicator format", "%1.2f"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(slider, "slider") +DEFINE_EXTERNAL_TYPE_SIMPLE(slider, "Slider") diff --git a/src/edje_externals/elm_slideshow.c b/src/edje_externals/elm_slideshow.c new file mode 100644 index 0000000..913dfaa --- /dev/null +++ b/src/edje_externals/elm_slideshow.c @@ -0,0 +1,182 @@ +#include "private.h" + +typedef struct _Elm_Params_Slideshow +{ + Elm_Params base; + int timeout; + const char *transition; + const char *layout; + Eina_Bool loop:1; + Eina_Bool timeout_exists:1; + Eina_Bool loop_exists:1; +} Elm_Params_Slideshow; + +static const char *transitions[] = { "fade", "black_fade", "horizontal", + "vertical", "square", NULL}; +static const char *layout[] = { "fullscreen", "not_fullscreen", NULL}; + +static void +external_slideshow_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Slideshow *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->timeout_exists) + elm_slideshow_timeout_set(obj , p->timeout); + if (p->loop_exists) + elm_slideshow_loop_set(obj, p->loop); + if (p->transition) { + elm_slideshow_transition_set(obj, p->transition); + } + if (p->layout) { + elm_slideshow_layout_set(obj, p->layout); + } +} + +static Eina_Bool +external_slideshow_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "timeout")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + elm_slideshow_timeout_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "loop")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_slideshow_loop_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "transition")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_slideshow_transition_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "layout")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_slideshow_layout_set(obj, param->s); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_slideshow_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "timeout")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + param->i = elm_slideshow_timeout_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "loop")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_slideshow_loop_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "transition")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_slideshow_transition_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "layout")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_slideshow_layout_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_slideshow_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Slideshow *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Slideshow)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "timeout")) + { + mem->timeout = param->i; + mem->timeout_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "loop")) + { + mem->loop = param->i; + mem->loop_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "transition")) + { + mem->transition = param->s; + } + else if (!strcmp(param->name, "layout")) + { + mem->layout = param->s; + } + } + + return mem; +} + +static Evas_Object *external_slideshow_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_slideshow_params_free(void *params __UNUSED__) +{ + return; +} + +static Edje_External_Param_Info external_slideshow_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_INT("timeout"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("loop"), + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("transition", "fade", transitions), + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("layout", "fullscreen", layout), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(slideshow, "slideshow"); +DEFINE_EXTERNAL_TYPE_SIMPLE(slideshow, "Slideshow"); diff --git a/src/edje_externals/elm_spinner.c b/src/edje_externals/elm_spinner.c new file mode 100644 index 0000000..8978cb6 --- /dev/null +++ b/src/edje_externals/elm_spinner.c @@ -0,0 +1,244 @@ +#include "private.h" + +typedef struct _Elm_Params_Spinner +{ + Elm_Params base; + const char *label_format; + double min, max, step, value; + Eina_Bool min_exists:1; + Eina_Bool max_exists:1; + Eina_Bool step_exists:1; + Eina_Bool value_exists:1; + Eina_Bool wrap_exists:1; + Eina_Bool wrap:1; +} Elm_Params_Spinner; + +static void +external_spinner_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Spinner *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label_format) + elm_spinner_label_format_set(obj, p->label_format); + if ((p->min_exists) && (p->max_exists)) + elm_spinner_min_max_set(obj, p->min, p->max); + else if ((p->min_exists) || (p->max_exists)) + { + double min, max; + elm_spinner_min_max_get(obj, &min, &max); + if (p->min_exists) + elm_spinner_min_max_set(obj, p->min, max); + else + elm_spinner_min_max_set(obj, min, p->max); + } + if (p->step_exists) + elm_spinner_step_set(obj, p->step); + if (p->value_exists) + elm_spinner_value_set(obj, p->value); + if (p->wrap_exists) + elm_spinner_wrap_set(obj, p->wrap); +} + +static Eina_Bool +external_spinner_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label format")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_spinner_label_format_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "min")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + double min, max; + elm_spinner_min_max_get(obj, &min, &max); + elm_spinner_min_max_set(obj, param->d, max); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "max")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + double min, max; + elm_spinner_min_max_get(obj, &min, &max); + elm_spinner_min_max_set(obj, min, param->d); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "step")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + elm_spinner_step_set(obj, param->d); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "value")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + elm_spinner_value_set(obj, param->d); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "wrap")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_spinner_wrap_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_spinner_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label format")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_spinner_label_format_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "min")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + double min, max; + elm_spinner_min_max_get(obj, &min, &max); + param->d = min; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "max")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + double min, max; + elm_spinner_min_max_get(obj, &min, &max); + param->d = max; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "step")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + param->d = elm_spinner_step_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "value")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + param->d = elm_spinner_value_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "wrap")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_spinner_value_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_spinner_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Spinner *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Spinner)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "label format")) + mem->label_format = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "min")) + { + mem->min = param->d; + mem->min_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "max")) + { + mem->max = param->d; + mem->max_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "step")) + { + mem->step = param->d; + mem->step_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "value")) + { + mem->value = param->d; + mem->value_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "wrap")) + { + mem->wrap = param->i; + mem->wrap_exists = EINA_TRUE; + } + } + + return mem; +} + +static Evas_Object *external_spinner_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_spinner_params_free(void *params) +{ + Elm_Params_Spinner *mem = params; + + if (mem->label_format) + eina_stringshare_del(mem->label_format); + free(mem); +} + +static Edje_External_Param_Info external_spinner_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("label format", "%1.2f"), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("min"), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE_DEFAULT("max", 100.0), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE_DEFAULT("step", 1.0), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("value"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("wrap"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(spinner, "spinner") +DEFINE_EXTERNAL_TYPE_SIMPLE(spinner, "Spinner") diff --git a/src/edje_externals/elm_thumb.c b/src/edje_externals/elm_thumb.c new file mode 100644 index 0000000..412cd04 --- /dev/null +++ b/src/edje_externals/elm_thumb.c @@ -0,0 +1,146 @@ +#include + +#include "private.h" + +typedef struct _Elm_Params_Thumb +{ + Elm_Params base; + const char *animate; +} Elm_Params_Thumb; + +static const char* choices[] = {"loop", "start", "stop", NULL}; + +static Elm_Thumb_Animation_Setting +_anim_setting_get(const char *anim_str) +{ + unsigned int i; + + assert(sizeof(choices)/sizeof(choices[0]) == ELM_THUMB_ANIMATION_LAST + 1); + + for (i = 0; i < sizeof(choices); i++) + { + if (!strcmp(anim_str, choices[i])) + return i; + } + return ELM_THUMB_ANIMATION_LAST; +} + +static void +external_thumb_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Thumb *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->animate) + { + Elm_Thumb_Animation_Setting set = _anim_setting_get(p->animate); + if (set != ELM_THUMB_ANIMATION_LAST) + elm_thumb_animate_set(obj, set); + } +} + +static Eina_Bool +external_thumb_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "animate")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Thumb_Animation_Setting set = _anim_setting_get(param->s); + if (set == ELM_THUMB_ANIMATION_LAST) return EINA_FALSE; + elm_thumb_animate_set(obj, set); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_thumb_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "animate")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_CHOICE) + { + Elm_Thumb_Animation_Setting anim_set = elm_thumb_animate_get(obj); + + if (anim_set == ELM_THUMB_ANIMATION_LAST) + return EINA_FALSE; + + param->s = choices[anim_set]; + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_thumb_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Thumb *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Thumb)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "animate")) + mem->animate = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_thumb_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_thumb_params_free(void *params) +{ + Elm_Params_Thumb *mem = params; + + if (mem->animate) + eina_stringshare_del(mem->animate); + free(mem); +} + +static Edje_External_Param_Info external_thumb_params[] = + { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_CHOICE_FULL("animate", "loop", choices), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL + }; + +DEFINE_EXTERNAL_ICON_ADD(thumb, "thumb") + +static Evas_Object * +external_thumb_add(void *data __UNUSED__, Evas *evas __UNUSED__, Evas_Object *edje, const Eina_List *params __UNUSED__, const char *part_name) +{ + Evas_Object *parent, *obj; + external_elm_init(); + parent = elm_widget_parent_widget_get(edje); + if (!parent) parent = edje; + elm_need_ethumb(); /* extra command needed */ + obj = elm_thumb_add(parent); + external_signals_proxy(obj, edje, part_name); + return obj; +} +DEFINE_EXTERNAL_TYPE(thumb, "Thumbnail") diff --git a/src/edje_externals/elm_toggle.c b/src/edje_externals/elm_toggle.c new file mode 100644 index 0000000..5b28058 --- /dev/null +++ b/src/edje_externals/elm_toggle.c @@ -0,0 +1,212 @@ +#include + +#include "private.h" + +typedef struct _Elm_Params_Toggle +{ + Elm_Params base; + const char *label; + Evas_Object *icon; + const char *on, *off; + Eina_Bool state:1; + Eina_Bool state_exists:1; +} Elm_Params_Toggle; + +static void +external_toggle_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Toggle *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->label) + elm_toggle_label_set(obj, p->label); + if (p->icon) + elm_toggle_icon_set(obj, p->icon); + + if ((p->on) && (p->off)) + elm_toggle_states_labels_set(obj, p->on, p->off); + else if ((p->on) || (p->off)) + { + const char *on, *off; + elm_toggle_states_labels_get(obj, &on, &off); + if (p->on) + elm_toggle_states_labels_set(obj, p->on, off); + else + elm_toggle_states_labels_set(obj, on, p->off); + } + + if (p->state_exists) + elm_toggle_state_set(obj, p->state); +} + +static Eina_Bool +external_toggle_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + elm_toggle_label_set(obj, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + Evas_Object *icon = external_common_param_icon_get(obj, param); + if ((strcmp(param->s, "")) && (!icon)) return EINA_FALSE; + elm_toggle_icon_set(obj, icon); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "label on")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + const char *on, *off; + elm_toggle_states_labels_get(obj, &on, &off); + elm_toggle_states_labels_set(obj, param->s, off); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "label off")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + const char *on, *off; + elm_toggle_states_labels_get(obj, &on, &off); + elm_toggle_states_labels_set(obj, on, param->s); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "state")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + elm_toggle_state_set(obj, param->i); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_toggle_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "label")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + param->s = elm_toggle_label_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "icon")) + { + /* not easy to get icon name back from live object */ + return EINA_FALSE; + } + else if (!strcmp(param->name, "label on")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + const char *on, *off; + elm_toggle_states_labels_get(obj, &on, &off); + param->s = on; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "label off")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_STRING) + { + const char *on, *off; + elm_toggle_states_labels_get(obj, &on, &off); + param->s = off; + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "state")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_BOOL) + { + param->i = elm_toggle_state_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_toggle_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Toggle *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Toggle)); + if (!mem) + return NULL; + + external_common_icon_param_parse(&mem->icon, obj, params); + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "state")) { + mem->state = param->i; + mem->state_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "label on")) + mem->on = eina_stringshare_add(param->s); + else if (!strcmp(param->name, "label off")) + mem->off = eina_stringshare_add(param->s); + } + + return mem; +} + +static Evas_Object *external_toggle_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_toggle_params_free(void *params) +{ + Elm_Params_Toggle *mem = params; + + if (mem->on) + eina_stringshare_del(mem->on); + if (mem->off) + eina_stringshare_del(mem->off); + if (mem->label) + eina_stringshare_del(mem->label); + free(params); +} + +static Edje_External_Param_Info external_toggle_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_STRING("label"), + EDJE_EXTERNAL_PARAM_INFO_STRING("icon"), + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("label on", "ON"), + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("label off", "OFF"), + EDJE_EXTERNAL_PARAM_INFO_BOOL("state"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(toggle, "toggle") +DEFINE_EXTERNAL_TYPE_SIMPLE(toggle, "Toggle") diff --git a/src/edje_externals/elm_toolbar.c b/src/edje_externals/elm_toolbar.c new file mode 100644 index 0000000..18d5d84 --- /dev/null +++ b/src/edje_externals/elm_toolbar.c @@ -0,0 +1,129 @@ +#include "private.h" + +typedef struct _Elm_Params_Toolbar +{ + Elm_Params base; + int icon_size; + Eina_Bool icon_size_exists:1; + double align; + Eina_Bool align_exists:1; +} Elm_Params_Toolbar; + +static void +external_toolbar_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) +{ + const Elm_Params_Toolbar *p; + + if (to_params) p = to_params; + else if (from_params) p = from_params; + else return; + + if (p->icon_size_exists) + elm_toolbar_icon_size_set(obj, p->icon_size); + if (p->align_exists) + elm_toolbar_align_set(obj, p->align); +} + +static Eina_Bool +external_toolbar_param_set(void *data __UNUSED__, Evas_Object *obj, const Edje_External_Param *param) +{ + if (!strcmp(param->name, "icon_size")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + elm_toolbar_icon_size_set(obj, param->i); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "align")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + elm_toolbar_align_set(obj, param->d); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static Eina_Bool +external_toolbar_param_get(void *data __UNUSED__, const Evas_Object *obj, Edje_External_Param *param) +{ + if (!strcmp(param->name, "icon_size")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_INT) + { + param->i = elm_toolbar_icon_size_get(obj); + return EINA_TRUE; + } + } + else if (!strcmp(param->name, "align")) + { + if (param->type == EDJE_EXTERNAL_PARAM_TYPE_DOUBLE) + { + param->d = elm_toolbar_align_get(obj); + return EINA_TRUE; + } + } + + ERR("unknown parameter '%s' of type '%s'", + param->name, edje_external_param_type_str(param->type)); + + return EINA_FALSE; +} + +static void * +external_toolbar_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) +{ + Elm_Params_Toolbar *mem; + Edje_External_Param *param; + const Eina_List *l; + + mem = calloc(1, sizeof(Elm_Params_Toolbar)); + if (!mem) + return NULL; + + EINA_LIST_FOREACH(params, l, param) + { + if (!strcmp(param->name, "icon_size")) + { + mem->icon_size = param->i; + mem->icon_size_exists = EINA_TRUE; + } + else if (!strcmp(param->name, "align")) + { + mem->align = param->d; + mem->align_exists = EINA_TRUE; + } + } + + return mem; +} + +static Evas_Object *external_toolbar_content_get(void *data __UNUSED__, + const Evas_Object *obj __UNUSED__, const char *content __UNUSED__) +{ + ERR("No content."); + return NULL; +} + +static void +external_toolbar_params_free(void *params) +{ + Elm_Params_Toolbar *mem = params; + free(mem); +} + +static Edje_External_Param_Info external_toolbar_params[] = { + DEFINE_EXTERNAL_COMMON_PARAMS, + EDJE_EXTERNAL_PARAM_INFO_INT("icon_size"), + EDJE_EXTERNAL_PARAM_INFO_DOUBLE("align"), + EDJE_EXTERNAL_PARAM_INFO_SENTINEL +}; + +DEFINE_EXTERNAL_ICON_ADD(toolbar, "toolbar"); +DEFINE_EXTERNAL_TYPE_SIMPLE(toolbar, "Toolbar"); diff --git a/src/edje_externals/modules.inc b/src/edje_externals/modules.inc new file mode 100644 index 0000000..941fe95 --- /dev/null +++ b/src/edje_externals/modules.inc @@ -0,0 +1,28 @@ +DEFINE_TYPE(anchorblock) +DEFINE_TYPE(anchorview) +DEFINE_TYPE(bubble) +DEFINE_TYPE(button) +DEFINE_TYPE(check) +DEFINE_TYPE(clock) +DEFINE_TYPE(fileselector) +DEFINE_TYPE(fileselector_button) +DEFINE_TYPE(fileselector_entry) +DEFINE_TYPE(genlist) +DEFINE_TYPE(hoversel) +DEFINE_TYPE(list) +DEFINE_TYPE(map) +DEFINE_TYPE(photocam) +DEFINE_TYPE(progressbar) +DEFINE_TYPE(radio) +DEFINE_TYPE(scrolled_entry) +DEFINE_TYPE(slider) +DEFINE_TYPE(slideshow) +DEFINE_TYPE(spinner) +DEFINE_TYPE(thumb) +DEFINE_TYPE(toggle) +DEFINE_TYPE(toolbar) +DEFINE_TYPE(notify) +DEFINE_TYPE(panes) +DEFINE_TYPE(label) +DEFINE_TYPE(icon) +DEFINE_TYPE(scroller) diff --git a/src/edje_externals/private.h b/src/edje_externals/private.h new file mode 100644 index 0000000..6bf0274 --- /dev/null +++ b/src/edje_externals/private.h @@ -0,0 +1,118 @@ +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#include "Elementary.h" +#include "elm_priv.h" + +typedef struct { + const char *style; +} Elm_Params; + +void external_elm_init(void); +void external_signal(void *data, Evas_Object *obj, const char *signal, const char *source); +void external_signals_proxy(Evas_Object *obj, Evas_Object *edje, const char *part_name); +const char *external_translate(void *data, const char *orig); +void external_common_params_free(void *params); +void *external_common_params_parse_internal(size_t params_size, void *data, Evas_Object *obj, const Eina_List *params); +Evas_Object *external_common_param_icon_get(Evas_Object *obj, const Edje_External_Param *param); +Evas_Object *external_common_param_edje_object_get(Evas_Object *obj, const Edje_External_Param *p); +void external_common_icon_param_parse(Evas_Object **icon, Evas_Object *obj, const Eina_List *params); +Eina_Bool external_common_param_get(void *data, const Evas_Object *obj, Edje_External_Param *param); +Eina_Bool external_common_param_set(void *data, Evas_Object *obj, const Edje_External_Param *param); +void external_common_state_set(void *data, Evas_Object *obj, const void *from_params, const void *to_params, float pos); +void external_common_params_parse(void *mem, void *data, Evas_Object *obj, const Eina_List *params); + +#define DEFINE_EXTERNAL_TYPE(type_name, name) \ +static Eina_Bool \ +_external_##type_name##_param_set(void *data, Evas_Object *obj, const Edje_External_Param *param) \ +{ \ + if (external_common_param_set(data, obj, param)) \ + return EINA_TRUE; \ + return external_##type_name##_param_set(data, obj, param); \ +} \ +static Eina_Bool \ +_external_##type_name##_param_get(void *data, const Evas_Object *obj, Edje_External_Param *param) \ +{ \ + if (external_common_param_get(data, obj, param)) \ + return EINA_TRUE; \ + return external_##type_name##_param_get(data, obj, param); \ +} \ +static const char * \ +external_##type_name##_label_get(void *data __UNUSED__) \ +{ \ + return name; \ +} \ + \ +static void \ +_external_##type_name##_state_set(void *data __UNUSED__, Evas_Object *obj, const void *from_params, const void *to_params, float pos __UNUSED__) \ +{ \ + external_common_state_set(data, obj, from_params, to_params, pos); \ + external_##type_name##_state_set(data, obj, from_params, to_params, pos); \ +} \ + \ +static void * \ +_external_##type_name##_params_parse(void *data __UNUSED__, Evas_Object *obj __UNUSED__, const Eina_List *params) \ +{ \ + void *mem = external_##type_name##_params_parse(data, obj, params); \ + external_common_params_parse(mem, data, obj, params); \ + return mem; \ +} \ +static void \ +_external_##type_name##_params_free(void *params) \ +{ \ + external_common_params_free(params); \ + external_##type_name##_params_free(params); \ +} \ + \ +const Edje_External_Type external_##type_name##_type = {\ + .abi_version = EDJE_EXTERNAL_TYPE_ABI_VERSION, \ + .module = "elm", \ + .module_name = "Elementary", \ + .add = external_##type_name##_add, \ + .state_set = _external_##type_name##_state_set, \ + .signal_emit = external_signal, \ + .param_set = _external_##type_name##_param_set, \ + .param_get = _external_##type_name##_param_get, \ + .params_parse = _external_##type_name##_params_parse,\ + .params_free = _external_##type_name##_params_free, \ + .label_get = external_##type_name##_label_get, \ + .content_get = external_##type_name##_content_get, \ + .description_get = NULL, \ + .icon_add = external_##type_name##_icon_add, \ + .preview_add = NULL, \ + .translate = external_translate, \ + .parameters_info = external_##type_name##_params, \ + .data = NULL \ +}; + +#define DEFINE_EXTERNAL_TYPE_SIMPLE(type_name, name) \ +static Evas_Object * \ +external_##type_name##_add(void *data __UNUSED__, Evas *evas __UNUSED__, Evas_Object *edje, const Eina_List *params __UNUSED__, const char *part_name) \ +{ \ + Evas_Object *parent, *obj; \ + external_elm_init(); \ + parent = elm_widget_parent_widget_get(edje); \ + if (!parent) parent = edje; \ + obj = elm_##type_name##_add(parent); \ + external_signals_proxy(obj, edje, part_name); \ + return obj; \ +} \ + \ +DEFINE_EXTERNAL_TYPE(type_name, name) + +#define DEFINE_EXTERNAL_ICON_ADD(type_name, name) \ +Evas_Object * \ +external_##type_name##_icon_add(void *data __UNUSED__, Evas *e) { \ + Evas_Object *ic; \ + int w = 20, h = 10; \ + \ + ic = edje_object_add(e); \ + edje_object_file_set(ic, PACKAGE_DATA_DIR"/edje_externals/icons.edj", "ico_"name);\ + evas_object_size_hint_min_set(ic, w, h); \ + evas_object_size_hint_max_set(ic, w, h); \ + \ + return ic; \ +} + +#define DEFINE_EXTERNAL_COMMON_PARAMS \ + EDJE_EXTERNAL_PARAM_INFO_STRING_DEFAULT("style", "default") diff --git a/src/lib/Elementary.h.in b/src/lib/Elementary.h.in new file mode 100644 index 0000000..0ae22f3 --- /dev/null +++ b/src/lib/Elementary.h.in @@ -0,0 +1,2647 @@ +/* + * + * vim:ts=8:sw=3:sts=3:expandtab:cino=>5n-2f0^-2{2(0W1st0 + */ +#ifndef ELEMENTARY_H +#define ELEMENTARY_H + +/** + * @file Elementary.h + * @brief Elementary's API + * + * Elementary API. + */ + +@ELM_UNIX_DEF@ ELM_UNIX +@ELM_WIN32_DEF@ ELM_WIN32 +@ELM_WINCE_DEF@ ELM_WINCE +@ELM_EDBUS_DEF@ ELM_EDBUS +@ELM_EFREET_DEF@ ELM_EFREET +@ELM_ETHUMB_DEF@ ELM_ETHUMB +@ELM_DEBUG_DEF@ ELM_DEBUG +@ELM_ALLOCA_H_DEF@ ELM_ALLOCA_H +@ELM_LIBINTL_H_DEF@ ELM_LIBINTL_H + +/* Standard headers for standard system calls etc. */ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#ifdef ELM_UNIX +# include +# ifdef ELM_LIBINTL_H +# include +# endif +# include +# include +# include +#endif + +#ifdef ELM_ALLOCA_H +# include +#endif + +#if defined (ELM_WIN32) || defined (ELM_WINCE) +# include +# ifndef alloca +# define alloca _alloca +# endif +#endif + + +/* EFL headers */ +#include +#include +#include +#include +#include +#include +#include +#include + +#ifdef ELM_EDBUS +# include +#endif + +#ifdef ELM_EFREET +# include +# include +# include +#endif + +#ifdef ELM_ETHUMB +# include +#endif + +#ifdef EAPI +# undef EAPI +#endif + +#ifdef _WIN32 +# ifdef ELEMENTARY_BUILD +# ifdef DLL_EXPORT +# define EAPI __declspec(dllexport) +# else +# define EAPI +# endif /* ! DLL_EXPORT */ +# else +# define EAPI __declspec(dllimport) +# endif /* ! EFL_EVAS_BUILD */ +#else +# ifdef __GNUC__ +# if __GNUC__ >= 4 +# define EAPI __attribute__ ((visibility("default"))) +# else +# define EAPI +# endif +# else +# define EAPI +# endif +#endif /* ! _WIN32 */ + + +/* allow usage from c++ */ +#ifdef __cplusplus +extern "C" { +#endif + +#define ELM_VERSION_MAJOR @VMAJ@ +#define ELM_VERSION_MINOR @VMIN@ + + typedef struct _Elm_Version + { + int major; + int minor; + int micro; + int revision; + } Elm_Version; + + EAPI extern Elm_Version *elm_version; + +/* handy macros */ +#define ELM_RECTS_INTERSECT(x, y, w, h, xx, yy, ww, hh) (((x) < ((xx) + (ww))) && ((y) < ((yy) + (hh))) && (((x) + (w)) > (xx)) && (((y) + (h)) > (yy))) +#define ELM_PI 3.14159265358979323846 + + /** + * Defines couple of standard Evas_Object layers to be used + * with evas_object_layer_set(). + * + * @note whenever extending with new values, try to keep some padding + * to siblings so there is room for further extensions. + */ + typedef enum _Elm_Object_Layer + { + ELM_OBJECT_LAYER_BACKGROUND = EVAS_LAYER_MIN + 64, /**< where to place backgrounds */ + ELM_OBJECT_LAYER_DEFAULT = 0, /**< Evas_Object default layer (and thus for Elementary) */ + ELM_OBJECT_LAYER_FOCUS = EVAS_LAYER_MAX - 128, /**< where focus object visualization is */ + ELM_OBJECT_LAYER_TOOLTIP = EVAS_LAYER_MAX - 64, /**< where to show tooltips */ + ELM_OBJECT_LAYER_CURSOR = EVAS_LAYER_MAX - 32, /**< where to show cursors */ + ELM_OBJECT_LAYER_LAST /**< last layer known by Elementary */ + } Elm_Object_Layer; + +/**************************************************************************/ + EAPI extern int ELM_ECORE_EVENT_ETHUMB_CONNECT; + + /* Objects */ + /** + * Emitted when policy value changed. + */ + EAPI extern int ELM_EVENT_POLICY_CHANGED; + typedef struct _Elm_Event_Policy_Changed + { + unsigned int policy; + int new_value; + int old_value; + } Elm_Event_Policy_Changed; + + /** + * Policy identifiers. + * + * @see elm_policy_set() + */ + typedef enum _Elm_Policy + { + ELM_POLICY_QUIT, /**< when should quit application automatically. + * @see Elm_Policy_Quit. + */ + ELM_POLICY_LAST + } Elm_Policy; + + typedef enum _Elm_Policy_Quit + { + ELM_POLICY_QUIT_NONE = 0, /**< never quit application automatically */ + ELM_POLICY_QUIT_LAST_WINDOW_CLOSED /**< quit when last window is closed */ + } Elm_Policy_Quit; + + typedef enum _Elm_Focus_Direction + { + ELM_FOCUS_PREVIOUS, + ELM_FOCUS_NEXT + } Elm_Focus_Direction; + + typedef enum _Elm_Text_Format + { + ELM_TEXT_FORMAT_PLAIN_UTF8, + ELM_TEXT_FORMAT_MARKUP_UTF8 + } Elm_Text_Format; + + /** + * Called back when a widget's tooltip is activated and needs content. + * @param data user-data given to elm_object_tooltip_content_cb_set() + * @param obj owner widget. + */ + typedef Evas_Object *(*Elm_Tooltip_Content_Cb) (void *data, Evas_Object *obj); + + /** + * Called back when a widget's item tooltip is activated and needs content. + * @param data user-data given to elm_object_tooltip_content_cb_set() + * @param obj owner widget. + * @param item context dependent item. As an example, if tooltip was + * set on Elm_List_Item, then it is of this type. + */ + typedef Evas_Object *(*Elm_Tooltip_Item_Content_Cb) (void *data, Evas_Object *obj, void *item); + + typedef Eina_Bool (*Elm_Event_Cb) (void *data, Evas_Object *obj, Evas_Object *src, Evas_Callback_Type type, void *event_info); + +#ifndef ELM_LIB_QUICKLAUNCH +#define ELM_MAIN() int main(int argc, char **argv) {elm_init(argc, argv); return elm_main(argc, argv);} +#else +#define ELM_MAIN() int main(int argc, char **argv) {return elm_quicklaunch_fallback(argc, argv);} +#endif + +/**************************************************************************/ + /* General calls */ + EAPI int elm_init(int argc, char **argv); + EAPI int elm_shutdown(void); + EAPI void elm_run(void); + EAPI void elm_exit(void); + + EAPI void elm_quicklaunch_mode_set(Eina_Bool ql_on); + EAPI Eina_Bool elm_quicklaunch_mode_get(void); + EAPI int elm_quicklaunch_init(int argc, char **argv); + EAPI int elm_quicklaunch_sub_init(int argc, char **argv); + EAPI int elm_quicklaunch_sub_shutdown(void); + EAPI int elm_quicklaunch_shutdown(void); + EAPI void elm_quicklaunch_seed(void); + EAPI Eina_Bool elm_quicklaunch_prepare(int argc, char **argv); + EAPI Eina_Bool elm_quicklaunch_fork(int argc, char **argv, char *cwd, void (postfork_func) (void *data), void *postfork_data); + EAPI void elm_quicklaunch_cleanup(void); + EAPI int elm_quicklaunch_fallback(int argc, char **argv); + EAPI char *elm_quicklaunch_exe_path_get(const char *exe); + + EAPI Eina_Bool elm_need_efreet(void); + EAPI Eina_Bool elm_need_e_dbus(void); + EAPI Eina_Bool elm_need_ethumb(void); + + EAPI Eina_Bool elm_policy_set(unsigned int policy, int value); + EAPI int elm_policy_get(unsigned int policy); + + EAPI void elm_all_flush(void); + EAPI int elm_cache_flush_interval_get(void); + EAPI void elm_cache_flush_interval_set(int size); + EAPI void elm_cache_flush_interval_all_set(int size); + EAPI Eina_Bool elm_cache_flush_enmabled_get(void); + EAPI void elm_cache_flush_enabled_set(Eina_Bool enabled); + EAPI void elm_cache_flush_enabled_all_set(Eina_Bool enabled); + EAPI int elm_font_cache_get(void); + EAPI void elm_font_cache_set(int size); + EAPI void elm_font_cache_all_set(int size); + EAPI int elm_image_cache_get(void); + EAPI void elm_image_cache_set(int size); + EAPI void elm_image_cache_all_set(int size); + EAPI int elm_edje_file_cache_get(void); + EAPI void elm_edje_file_cache_set(int size); + EAPI void elm_edje_file_cache_all_set(int size); + EAPI int elm_edje_collection_cache_get(void); + EAPI void elm_edje_collection_cache_set(int size); + EAPI void elm_edje_collection_cache_all_set(int size); + + EAPI void elm_object_scale_set(Evas_Object *obj, double scale) EINA_ARG_NONNULL(1); + EAPI double elm_object_scale_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_style_set(Evas_Object *obj, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_object_style_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_disabled_set(Evas_Object *obj, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_object_disabled_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI Eina_Bool elm_object_widget_check(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_object_parent_widget_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_object_top_widget_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const char *elm_object_widget_type_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI double elm_scale_get(void); + EAPI void elm_scale_set(double scale); + EAPI void elm_scale_all_set(double scale); + + EAPI Eina_Bool elm_config_save(void); + EAPI void elm_config_reload(void); + + EAPI const char *elm_profile_current_get(void); + EAPI const char *elm_profile_dir_get(const char *profile, Eina_Bool is_user); + EAPI void elm_profile_dir_free(const char *p_dir); + EAPI Eina_List *elm_profile_list_get(void); + EAPI void elm_profile_list_free(Eina_List *l); + EAPI void elm_profile_set(const char *profile); + EAPI void elm_profile_all_set(const char *profile); + + EAPI const char *elm_engine_current_get(void); + EAPI void elm_engine_set(const char *engine); + + typedef struct _Elm_Text_Class + { + const char *name; + const char *desc; + } Elm_Text_Class; + + typedef struct _Elm_Font_Overlay + { + const char *text_class; + const char *font; + Evas_Font_Size size; + } Elm_Font_Overlay; + + typedef struct _Elm_Font_Properties + { + const char *name; + Eina_List *styles; + } Elm_Font_Properties; + + EAPI const Eina_List *elm_text_classes_list_get(void); + EAPI void elm_text_classes_list_free(const Eina_List *list); + + EAPI const Eina_List *elm_font_overlay_list_get(void); + EAPI void elm_font_overlay_set(const char *text_class, const char *font, Evas_Font_Size size); + EAPI void elm_font_overlay_unset(const char *text_class); + EAPI void elm_font_overlay_apply(void); + EAPI void elm_font_overlay_all_apply(void); + + EAPI Elm_Font_Properties *elm_font_properties_get(const char *font) EINA_ARG_NONNULL(1); + EAPI void elm_font_properties_free(Elm_Font_Properties *efp) EINA_ARG_NONNULL(1); + EAPI const char *elm_font_fontconfig_name_get(const char *name, const char *style) EINA_ARG_NONNULL(1); + EAPI void elm_font_fontconfig_name_free(const char *name) EINA_ARG_NONNULL(1); + EAPI Eina_Hash *elm_font_available_hash_add(Eina_List *list); + EAPI void elm_font_available_hash_del(Eina_Hash *hash); + + EAPI Evas_Coord elm_finger_size_get(void); + EAPI void elm_finger_size_set(Evas_Coord size); + EAPI void elm_finger_size_all_set(Evas_Coord size); + + EAPI Eina_Bool elm_focus_highlight_enabled_get(void); + EAPI void elm_focus_highlight_enabled_set(Eina_Bool enable); + EAPI Eina_Bool elm_focus_highlight_animate_get(void); + EAPI void elm_focus_highlight_animate_set(Eina_Bool animate); + + EAPI Eina_Bool elm_object_focus_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_focus(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_unfocus(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_focus_allow_set(Evas_Object *obj, Eina_Bool enable) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_object_focus_allow_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI void elm_object_focus_custom_chain_set(Evas_Object *obj, Eina_List *objs) EINA_ARG_NONNULL(1); + EAPI void elm_object_focus_custom_chain_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_object_focus_custom_chain_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_focus_custom_chain_append(Evas_Object *obj, Evas_Object *child, Evas_Object *relative_child) EINA_ARG_NONNULL(1, 2); + EAPI void elm_object_focus_custom_chain_prepend(Evas_Object *obj, Evas_Object *child, Evas_Object *relative_child) EINA_ARG_NONNULL(1, 2); + EAPI void elm_object_focus_cycle(Evas_Object *obj, Elm_Focus_Direction dir) EINA_ARG_NONNULL(1); + EAPI void elm_object_focus_direction_go(Evas_Object *obj, int x, int y) EINA_ARG_NONNULL(1); + + EAPI Eina_Bool elm_scroll_bounce_enabled_get(void); + EAPI void elm_scroll_bounce_enabled_set(Eina_Bool enabled); + EAPI void elm_scroll_bounce_enabled_all_set(Eina_Bool enabled); + EAPI double elm_scroll_bounce_friction_get(void); + EAPI void elm_scroll_bounce_friction_set(double friction); + EAPI void elm_scroll_bounce_friction_all_set(double friction); + EAPI double elm_scroll_page_scroll_friction_get(void); + EAPI void elm_scroll_page_scroll_friction_set(double friction); + EAPI void elm_scroll_page_scroll_friction_all_set(double friction); + EAPI double elm_scroll_bring_in_scroll_friction_get(void); + EAPI void elm_scroll_bring_in_scroll_friction_set(double friction); + EAPI void elm_scroll_bring_in_scroll_friction_all_set(double friction); + EAPI double elm_scroll_zoom_friction_get(void); + EAPI void elm_scroll_zoom_friction_set(double friction); + EAPI void elm_scroll_zoom_friction_all_set(double friction); + EAPI Eina_Bool elm_scroll_thumbscroll_enabled_get(void); + EAPI void elm_scroll_thumbscroll_enabled_set(Eina_Bool enabled); + EAPI void elm_scroll_thumbscroll_enabled_all_set(Eina_Bool enabled); + EAPI unsigned int elm_scroll_thumbscroll_threshold_get(void); + EAPI void elm_scroll_thumbscroll_threshold_set(unsigned int threshold); + EAPI void elm_scroll_thumbscroll_threshold_all_set(unsigned int threshold); + EAPI double elm_scroll_thumbscroll_momentum_threshold_get(void); + EAPI void elm_scroll_thumbscroll_momentum_threshold_set(double threshold); + EAPI void elm_scroll_thumbscroll_momentum_threshold_all_set(double threshold); + EAPI double elm_scroll_thumbscroll_friction_get(void); + EAPI void elm_scroll_thumbscroll_friction_set(double friction); + EAPI void elm_scroll_thumbscroll_friction_all_set(double friction); + EAPI double elm_scroll_thumbscroll_border_friction_get(void); + EAPI void elm_scroll_thumbscroll_border_friction_set(double friction); + EAPI void elm_scroll_thumbscroll_border_friction_all_set(double friction); + + EAPI void elm_object_scroll_hold_push(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_scroll_hold_pop(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_scroll_freeze_push(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_scroll_freeze_pop(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_scroll_lock_x_set(Evas_Object *obj, Eina_Bool lock) EINA_ARG_NONNULL(1); + EAPI void elm_object_scroll_lock_y_set(Evas_Object *obj, Eina_Bool lock) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_object_scroll_lock_x_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_object_scroll_lock_y_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI void elm_object_signal_emit(Evas_Object *obj, const char *emission, const char *source) EINA_ARG_NONNULL(1); + EAPI void elm_object_signal_callback_add(Evas_Object *obj, const char *emission, const char *source, void (*func) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) EINA_ARG_NONNULL(1, 4); + EAPI void *elm_object_signal_callback_del(Evas_Object *obj, const char *emission, const char *source, void (*func) (void *data, Evas_Object *o, const char *emission, const char *source)) EINA_ARG_NONNULL(1, 4); + + EAPI void elm_object_event_callback_add(Evas_Object *obj, Elm_Event_Cb func, const void *data) EINA_ARG_NONNULL(1, 2); + EAPI void *elm_object_event_callback_del(Evas_Object *obj, Elm_Event_Cb func, const void *data) EINA_ARG_NONNULL(1, 2); + + EAPI void elm_coords_finger_size_adjust(int times_w, Evas_Coord *w, int times_h, Evas_Coord *h); + + EAPI double elm_longpress_timeout_get(void); + EAPI void elm_longpress_timeout_set(double longpress_timeout); + + /* debug + * don't use it unless you are sure + */ + EAPI void elm_object_tree_dump(const Evas_Object *top); + EAPI void elm_object_tree_dot_dump(const Evas_Object *top, const char *file); + + + /* theme */ + typedef struct _Elm_Theme Elm_Theme; + + EAPI Elm_Theme *elm_theme_new(void); + EAPI void elm_theme_free(Elm_Theme *th); + EAPI void elm_theme_copy(Elm_Theme *th, Elm_Theme *thdst); + EAPI void elm_theme_ref_set(Elm_Theme *th, Elm_Theme *thref); + EAPI Elm_Theme *elm_theme_ref_get(Elm_Theme *th); + EAPI Elm_Theme *elm_theme_default_get(void); + EAPI void elm_theme_overlay_add(Elm_Theme *th, const char *item); + EAPI void elm_theme_overlay_del(Elm_Theme *th, const char *item); + EAPI void elm_theme_extension_add(Elm_Theme *th, const char *item); + EAPI void elm_theme_extension_del(Elm_Theme *th, const char *item); + EAPI void elm_theme_set(Elm_Theme *th, const char *theme); + EAPI const char *elm_theme_get(Elm_Theme *th); + EAPI const Eina_List *elm_theme_list_get(const Elm_Theme *th); + EAPI char *elm_theme_list_item_path_get(const char *f, Eina_Bool *in_search_path); + EAPI void elm_theme_flush(Elm_Theme *th); + EAPI void elm_theme_full_flush(void); + + EAPI void elm_theme_all_set(const char *theme); + + EAPI Eina_List *elm_theme_name_available_list_new(void); + EAPI void elm_theme_name_available_list_free(Eina_List *list); + + EAPI void elm_object_theme_set(Evas_Object *obj, Elm_Theme *th) EINA_ARG_NONNULL(1); + EAPI Elm_Theme *elm_object_theme_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* win */ + typedef enum _Elm_Win_Type + { + ELM_WIN_BASIC, + ELM_WIN_DIALOG_BASIC, + ELM_WIN_DESKTOP, + ELM_WIN_DOCK, + ELM_WIN_TOOLBAR, + ELM_WIN_MENU, + ELM_WIN_UTILITY, + ELM_WIN_SPLASH + } Elm_Win_Type; + + typedef enum _Elm_Win_Keyboard_Mode + { + ELM_WIN_KEYBOARD_UNKNOWN, + ELM_WIN_KEYBOARD_OFF, + ELM_WIN_KEYBOARD_ON, + ELM_WIN_KEYBOARD_ALPHA, + ELM_WIN_KEYBOARD_NUMERIC, + ELM_WIN_KEYBOARD_PIN, + ELM_WIN_KEYBOARD_PHONE_NUMBER, + ELM_WIN_KEYBOARD_HEX, + ELM_WIN_KEYBOARD_TERMINAL, + ELM_WIN_KEYBOARD_PASSWORD, + ELM_WIN_KEYBOARD_IP, + ELM_WIN_KEYBOARD_HOST, + ELM_WIN_KEYBOARD_FILE, + ELM_WIN_KEYBOARD_URL, + ELM_WIN_KEYBOARD_KEYPAD, + ELM_WIN_KEYBOARD_J2ME + } Elm_Win_Keyboard_Mode; + + EAPI Evas_Object *elm_win_add(Evas_Object *parent, const char *name, Elm_Win_Type type); + EAPI void elm_win_resize_object_add(Evas_Object *obj, Evas_Object *subobj) EINA_ARG_NONNULL(1); + EAPI void elm_win_resize_object_del(Evas_Object *obj, Evas_Object *subobj) EINA_ARG_NONNULL(1); + EAPI void elm_win_title_set(Evas_Object *obj, const char *title) EINA_ARG_NONNULL(1); + EAPI const char *elm_win_title_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_autodel_set(Evas_Object *obj, Eina_Bool autodel) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_autodel_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_activate(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_lower(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_raise(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_borderless_set(Evas_Object *obj, Eina_Bool borderless) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_borderless_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_shaped_set(Evas_Object *obj, Eina_Bool shaped) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_shaped_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_alpha_set(Evas_Object *obj, Eina_Bool alpha) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_transparent_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_transparent_set(Evas_Object *obj, Eina_Bool transparent) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_alpha_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_override_set(Evas_Object *obj, Eina_Bool override) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_override_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_fullscreen_set(Evas_Object *obj, Eina_Bool fullscreen) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_fullscreen_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_maximized_set(Evas_Object *obj, Eina_Bool maximized) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_maximized_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_iconified_set(Evas_Object *obj, Eina_Bool iconified) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_iconified_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_layer_set(Evas_Object *obj, int layer) EINA_ARG_NONNULL(1); + EAPI int elm_win_layer_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_rotation_set(Evas_Object *obj, int rotation) EINA_ARG_NONNULL(1); + EAPI void elm_win_rotation_with_resize_set(Evas_Object *obj, int rotation) EINA_ARG_NONNULL(1); + EAPI int elm_win_rotation_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_sticky_set(Evas_Object *obj, Eina_Bool sticky) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_sticky_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_conformant_set(Evas_Object *obj, Eina_Bool conformant) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_conformant_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_quickpanel_set(Evas_Object *obj, Eina_Bool quickpanel) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_quickpanel_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_quickpanel_priority_major_set(Evas_Object *obj, int priority) EINA_ARG_NONNULL(1); + EAPI int elm_win_quickpanel_priority_major_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_quickpanel_priority_minor_set(Evas_Object *obj, int priority) EINA_ARG_NONNULL(1); + EAPI int elm_win_quickpanel_priority_minor_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_quickpanel_zone_set(Evas_Object *obj, int zone) EINA_ARG_NONNULL(1); + EAPI int elm_win_quickpanel_zone_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_focus_highlight_enabled_set(Evas_Object *obj, Eina_Bool enabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_focus_highlight_enabled_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_focus_highlight_style_set(Evas_Object *obj, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_win_focus_highlight_style_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /*... + * ecore_x_icccm_hints_set -> accepts_focus (add to ecore_evas) + * ecore_x_icccm_hints_set -> window_group (add to ecore_evas) + * ecore_x_icccm_size_pos_hints_set -> request_pos (add to ecore_evas) + * ecore_x_icccm_client_leader_set -> l (add to ecore_evas) + * ecore_x_icccm_window_role_set -> role (add to ecore_evas) + * ecore_x_icccm_transient_for_set -> forwin (add to ecore_evas) + * ecore_x_netwm_window_type_set -> type (add to ecore_evas) + * + * (add to ecore_x) set netwm argb icon! (add to ecore_evas) + * (blank mouse, private mouse obj, defaultmouse) + * + */ + EAPI void elm_win_keyboard_mode_set(Evas_Object *obj, Elm_Win_Keyboard_Mode mode) EINA_ARG_NONNULL(1); + EAPI Elm_Win_Keyboard_Mode elm_win_keyboard_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_keyboard_win_set(Evas_Object *obj, Eina_Bool is_keyboard) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_win_keyboard_win_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI void elm_win_screen_position_get(const Evas_Object *obj, int *x, int *y) EINA_ARG_NONNULL(1); + + EAPI Evas_Object *elm_win_inwin_add(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_inwin_activate(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_win_inwin_content_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_win_inwin_content_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_win_inwin_content_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + /* available styles: + * default + * minimal + * minimal_vertical + */ + /* X specific calls - won't work on non-x engines (return 0) */ + EAPI Ecore_X_Window elm_win_xwindow_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "delete,request" - the user requested to delete the window + * "focus,in" - window got focus + * "focus,out" - window lost focus + * "moved" - window that holds the canvas was moved + */ + + /* bg */ + typedef enum _Elm_Bg_Option + { + ELM_BG_OPTION_CENTER, /**< center the background */ + ELM_BG_OPTION_SCALE, /**< scale the background retaining aspect ratio */ + ELM_BG_OPTION_STRETCH, /**< stretch the background to fill */ + ELM_BG_OPTION_TILE /**< tile background at its original size */ + } Elm_Bg_Option; + + EAPI Evas_Object *elm_bg_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_bg_file_set(Evas_Object *obj, const char *file, const char *group) EINA_ARG_NONNULL(1); + EAPI void elm_bg_file_get(const Evas_Object *obj, const char **file, const char **group) EINA_ARG_NONNULL(1); + EAPI void elm_bg_option_set(Evas_Object *obj, Elm_Bg_Option option) EINA_ARG_NONNULL(1); + EAPI Elm_Bg_Option elm_bg_option_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_bg_color_set(Evas_Object *obj, int r, int g, int b) EINA_ARG_NONNULL(1); + EAPI void elm_bg_color_get(const Evas_Object *obj, int *r, int *g, int *b) EINA_ARG_NONNULL(1); + EAPI void elm_bg_overlay_set(Evas_Object *obj, Evas_Object *overlay) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_bg_overlay_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_bg_overlay_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + */ + + /* icon */ + typedef enum _Elm_Icon_Lookup_Order + { + ELM_ICON_LOOKUP_FDO_THEME, /**< icon look up order: freedesktop, theme */ + ELM_ICON_LOOKUP_THEME_FDO, /**< icon look up order: theme, freedesktop */ + ELM_ICON_LOOKUP_FDO, /**< icon look up order: freedesktop */ + ELM_ICON_LOOKUP_THEME /**< icon look up order: theme */ + } Elm_Icon_Lookup_Order; + + EAPI Evas_Object *elm_icon_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_icon_file_set(Evas_Object *obj, const char *file, const char *group) EINA_ARG_NONNULL(1, 2); + EAPI void elm_icon_file_get(const Evas_Object *obj, const char **file, const char **group) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_icon_standard_set(Evas_Object *obj, const char *name) EINA_ARG_NONNULL(1); + EAPI const char *elm_icon_standard_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_icon_smooth_set(Evas_Object *obj, Eina_Bool smooth) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_icon_smooth_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_icon_no_scale_set(Evas_Object *obj, Eina_Bool no_scale) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_icon_no_scale_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_icon_scale_set(Evas_Object *obj, Eina_Bool scale_up, Eina_Bool scale_down) EINA_ARG_NONNULL(1); + EAPI void elm_icon_scale_get(const Evas_Object *obj, Eina_Bool *scale_up, Eina_Bool *scale_down) EINA_ARG_NONNULL(1); + EAPI void elm_icon_fill_outside_set(Evas_Object *obj, Eina_Bool fill_outside) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_icon_fill_outside_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_icon_prescale_set(Evas_Object *obj, int size) EINA_ARG_NONNULL(1); + EAPI int elm_icon_prescale_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_icon_order_lookup_set(Evas_Object *obj, Elm_Icon_Lookup_Order order) EINA_ARG_NONNULL(1); + EAPI Elm_Icon_Lookup_Order elm_icon_order_lookup_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "clicked" - the user clicked the icon + */ + + /* image */ + typedef enum _Elm_Image_Orient + { + ELM_IMAGE_ORIENT_NONE, + ELM_IMAGE_ROTATE_90_CW, + ELM_IMAGE_ROTATE_180_CW, + ELM_IMAGE_ROTATE_90_CCW, + ELM_IMAGE_FLIP_HORIZONTAL, + ELM_IMAGE_FLIP_VERTICAL, + ELM_IMAGE_FLIP_TRANSPOSE, + ELM_IMAGE_FLIP_TRANSVERSE + } Elm_Image_Orient; + EAPI Evas_Object *elm_image_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_image_file_set(Evas_Object *obj, const char *file, const char *group) EINA_ARG_NONNULL(1, 2); + EAPI void elm_image_file_get(const Evas_Object *obj, const char **file, const char **group) EINA_ARG_NONNULL(1); + EAPI void elm_image_smooth_set(Evas_Object *obj, Eina_Bool smooth) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_image_smooth_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_image_object_size_get(const Evas_Object *obj, int *w, int *h) EINA_ARG_NONNULL(1); + EAPI void elm_image_no_scale_set(Evas_Object *obj, Eina_Bool no_scale) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_image_no_scale_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_image_scale_set(Evas_Object *obj, Eina_Bool scale_up, Eina_Bool scale_down) EINA_ARG_NONNULL(1); + EAPI void elm_image_scale_get(const Evas_Object *obj, Eina_Bool *scale_up, Eina_Bool *scale_down) EINA_ARG_NONNULL(1); + EAPI void elm_image_fill_outside_set(Evas_Object *obj, Eina_Bool fill_outside) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_image_fill_outside_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_image_prescale_set(Evas_Object *obj, int size) EINA_ARG_NONNULL(1); + EAPI int elm_image_prescale_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_image_orient_set(Evas_Object *obj, Elm_Image_Orient orient) EINA_ARG_NONNULL(1); + EAPI Elm_Image_Orient elm_image_orient_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_image_editable_set(Evas_Object *obj, Eina_Bool set) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_image_editable_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "clicked" - the user clicked the image + */ + + /* box */ + typedef struct _Elm_Box_Transition Elm_Box_Transition; + + EAPI Evas_Object *elm_box_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_box_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_box_horizontal_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_box_homogenous_set(Evas_Object *obj, Eina_Bool homogenous) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_box_homogenous_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_box_pack_start(Evas_Object *obj, Evas_Object *subobj) EINA_ARG_NONNULL(1); + EAPI void elm_box_pack_end(Evas_Object *obj, Evas_Object *subobj) EINA_ARG_NONNULL(1); + EAPI void elm_box_pack_before(Evas_Object *obj, Evas_Object *subobj, Evas_Object *before) EINA_ARG_NONNULL(1); + EAPI void elm_box_pack_after(Evas_Object *obj, Evas_Object *subobj, Evas_Object *after) EINA_ARG_NONNULL(1); + EAPI void elm_box_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_box_unpack(Evas_Object *obj, Evas_Object *subobj) EINA_ARG_NONNULL(1); + EAPI void elm_box_unpack_all(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_box_children_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_box_padding_set(Evas_Object *obj, Evas_Coord horizontal, Evas_Coord vertical) EINA_ARG_NONNULL(1); + EAPI void elm_box_padding_get(const Evas_Object *obj, Evas_Coord *horizontal, Evas_Coord *vertical) EINA_ARG_NONNULL(1); + EAPI void elm_box_align_set(Evas_Object *obj, double horizontal, double vertical) EINA_ARG_NONNULL(1); + EAPI void elm_box_align_get(const Evas_Object *obj, double *horizontal, double *vertical) EINA_ARG_NONNULL(1); + + EAPI void elm_box_layout_set(Evas_Object *obj, Evas_Object_Box_Layout cb, const void *data, void (*free_data)(void *data)) EINA_ARG_NONNULL(1); + EAPI void elm_box_layout_transition(Evas_Object *obj, Evas_Object_Box_Data *priv, void *data); + EAPI Elm_Box_Transition *elm_box_transition_new(const double duration, Evas_Object_Box_Layout start_layout, void *start_layout_data, void(*start_layout_free_data)(void *data), Evas_Object_Box_Layout end_layout, void *end_layout_data, void(*end_layout_free_data)(void *data), void(*transition_end_cb)(void *data), void *transition_end_data) EINA_ARG_NONNULL(2, 5); + EAPI void elm_box_transition_free(void *data); + /* smart callbacks called: + */ + + /* button */ + EAPI Evas_Object *elm_button_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_button_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_button_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_button_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_button_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_button_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_button_autorepeat_set(Evas_Object *obj, Eina_Bool on) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_button_autorepeat_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_button_autorepeat_initial_timeout_set(Evas_Object *obj, double t) EINA_ARG_NONNULL(1); + EAPI double elm_button_autorepeat_initial_timeout_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_button_autorepeat_gap_timeout_set(Evas_Object *obj, double t) EINA_ARG_NONNULL(1); + EAPI double elm_button_autorepeat_gap_timeout_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* available styles: + * default + * anchor + * hoversel_vertical + * hoversel_vertical_entry + */ + /* smart callbacks called: + * "clicked" - the user clicked the button + * "repeated" - the user pressed the button without releasing it + * "unpressed" - when the button is unpressed (released) + */ + + /* fileselector */ + EAPI Evas_Object *elm_fileselector_button_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_fileselector_button_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_fileselector_button_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_fileselector_button_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_window_title_set(Evas_Object *obj, const char *title) EINA_ARG_NONNULL(1); + EAPI const char *elm_fileselector_button_window_title_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_window_size_set(Evas_Object *obj, Evas_Coord width, Evas_Coord height) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_window_size_get(const Evas_Object *obj, Evas_Coord *width, Evas_Coord *height) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_path_set(Evas_Object *obj, const char *path) EINA_ARG_NONNULL(1); + EAPI const char *elm_fileselector_button_path_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_expandable_set(Evas_Object *obj, Eina_Bool value) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_button_expandable_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_folder_only_set(Evas_Object *obj, Eina_Bool value) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_button_folder_only_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_is_save_set(Evas_Object *obj, Eina_Bool value) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_button_is_save_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_button_inwin_mode_set(Evas_Object *obj, Eina_Bool value) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_button_inwin_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* available styles: + * default + * anchor + * hoversel_vertical + * hoversel_vertical_entry + */ + /* smart callbacks called: + * "file,chosen" - the user has selected a path, whose string pointer comes + as event info + */ + + EAPI Evas_Object *elm_fileselector_entry_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_button_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_fileselector_entry_button_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_button_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_fileselector_entry_button_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_fileselector_entry_button_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_window_title_set(Evas_Object *obj, const char *title) EINA_ARG_NONNULL(1); + EAPI const char *elm_fileselector_entry_window_title_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_window_size_set(Evas_Object *obj, Evas_Coord width, Evas_Coord height) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_window_size_get(const Evas_Object *obj, Evas_Coord *width, Evas_Coord *height) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_path_set(Evas_Object *obj, const char *path) EINA_ARG_NONNULL(1); + EAPI const char *elm_fileselector_entry_path_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_expandable_set(Evas_Object *obj, Eina_Bool value) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_entry_expandable_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_folder_only_set(Evas_Object *obj, Eina_Bool value) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_entry_folder_only_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_is_save_set(Evas_Object *obj, Eina_Bool value) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_entry_is_save_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_inwin_mode_set(Evas_Object *obj, Eina_Bool value) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_entry_inwin_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_entry_selected_set(Evas_Object *obj, const char *path) EINA_ARG_NONNULL(1); + EAPI const char *elm_fileselector_entry_selected_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* scroller policy */ + typedef enum _Elm_Scroller_Policy + { + ELM_SCROLLER_POLICY_AUTO = 0, + ELM_SCROLLER_POLICY_ON, + ELM_SCROLLER_POLICY_OFF, + ELM_SCROLLER_POLICY_LAST + } Elm_Scroller_Policy; + + EAPI Evas_Object *elm_scroller_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_content_set(Evas_Object *obj, Evas_Object *child) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_scroller_content_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_scroller_content_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_custom_widget_base_theme_set(Evas_Object *obj, const char *widget, const char *base) EINA_ARG_NONNULL(1, 2, 3); + EAPI void elm_scroller_content_min_limit(Evas_Object *obj, Eina_Bool w, Eina_Bool h) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_region_show(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_policy_set(Evas_Object *obj, Elm_Scroller_Policy policy_h, Elm_Scroller_Policy policy_v) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_policy_get(const Evas_Object *obj, Elm_Scroller_Policy *policy_h, Elm_Scroller_Policy *policy_v) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_region_get(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_child_size_get(const Evas_Object *obj, Evas_Coord *w, Evas_Coord *h) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_page_relative_set(Evas_Object *obj, double h_pagerel, double v_pagerel) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_page_size_set(Evas_Object *obj, Evas_Coord h_pagesize, Evas_Coord v_pagesize) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_region_bring_in(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h) EINA_ARG_NONNULL(1); + EAPI void elm_scroller_propagate_events_set(Evas_Object *obj, Eina_Bool propagation); + EAPI Eina_Bool elm_scroller_propagate_events_get(const Evas_Object *obj); + + /* smart callbacks called: + * "edge,left" + * "edge,right" + * "edge,top" + * "edge,bottom" + * "scroll" + * "scroll,anim,start" + * "scroll,anim,stop" + * "scroll,drag,start" + * "scroll,drag,stop" + */ + + /* label */ + EAPI Evas_Object *elm_label_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_label_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_label_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_label_line_wrap_set(Evas_Object *obj, Eina_Bool wrap) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_label_line_wrap_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_label_wrap_width_set(Evas_Object *obj, Evas_Coord w) EINA_ARG_NONNULL(1); + EAPI Evas_Coord elm_label_wrap_width_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_label_wrap_height_set(Evas_Object *obj, Evas_Coord h) EINA_ARG_NONNULL(1); + EAPI Evas_Coord elm_label_wrap_height_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_label_fontsize_set(Evas_Object *obj, int fontsize) EINA_ARG_NONNULL(1); + EAPI void elm_label_text_color_set(Evas_Object *obj, unsigned int r, unsigned int g, unsigned int b, unsigned int a) EINA_ARG_NONNULL(1); + EAPI void elm_label_text_align_set(Evas_Object *obj, const char *alignmode) EINA_ARG_NONNULL(1); + EAPI void elm_label_background_color_set(Evas_Object *obj, unsigned int r, unsigned int g, unsigned int b, unsigned int a) EINA_ARG_NONNULL(1); + EAPI void elm_label_ellipsis_set(Evas_Object *obj, Eina_Bool ellipsis) EINA_ARG_NONNULL(1); + EAPI void elm_label_slide_set(Evas_Object *obj, Eina_Bool slide) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_label_slide_get(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_label_slide_duration_set(Evas_Object *obj, double duration) EINA_ARG_NONNULL(1); + EAPI double elm_label_slide_duration_get(Evas_Object *obj) EINA_ARG_NONNULL(1); + /* available styles: + * default + * marker + */ + /* smart callbacks called: + */ + + /* toggle */ + EAPI Evas_Object *elm_toggle_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_toggle_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_toggle_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toggle_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_toggle_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_toggle_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toggle_states_labels_set(Evas_Object *obj, const char *onlabel, const char *offlabel) EINA_ARG_NONNULL(1); + EAPI void elm_toggle_states_labels_get(const Evas_Object *obj, const char **onlabel, const char **offlabel) EINA_ARG_NONNULL(1); + EAPI void elm_toggle_state_set(Evas_Object *obj, Eina_Bool state) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_toggle_state_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toggle_state_pointer_set(Evas_Object *obj, Eina_Bool *statep) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "changed" - the user toggled the state + */ + + /* frame */ + EAPI Evas_Object *elm_frame_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_frame_label_set(Evas_Object *obj, const char *label); EINA_ARG_NONNULL(1) + EAPI const char *elm_frame_label_get(const Evas_Object *obj); EINA_ARG_NONNULL(1) + EAPI void elm_frame_content_set(Evas_Object *obj, Evas_Object *content); EINA_ARG_NONNULL(1) + EAPI Evas_Object *elm_frame_content_get(const Evas_Object *obj); EINA_ARG_NONNULL(1) + EAPI Evas_Object *elm_frame_content_unset(Evas_Object *obj); EINA_ARG_NONNULL(1) + /* available styles: + * default + * pad_small + * pad_medium + * pad_large + * pad_huge + * outdent_top + * outdent_bottom + */ + /* smart callbacks called: + */ + + /* table */ + EAPI Evas_Object *elm_table_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_table_homogenous_set(Evas_Object *obj, Eina_Bool homogenous) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_table_homogeneous_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_table_padding_set(Evas_Object *obj, Evas_Coord horizontal, Evas_Coord vertical) EINA_ARG_NONNULL(1); + EAPI void elm_table_padding_get(const Evas_Object *obj, Evas_Coord *horizontal, Evas_Coord *vertical) EINA_ARG_NONNULL(1); + EAPI void elm_table_pack(Evas_Object *obj, Evas_Object *subobj, int x, int y, int w, int h) EINA_ARG_NONNULL(1); + EAPI void elm_table_unpack(Evas_Object *obj, Evas_Object *subobj) EINA_ARG_NONNULL(1); + EAPI void elm_table_clear(Evas_Object *obj, Eina_Bool clear) EINA_ARG_NONNULL(1); + + /* gengrid */ + typedef struct _Elm_Gengrid_Item_Class Elm_Gengrid_Item_Class; + typedef struct _Elm_Gengrid_Item_Class_Func Elm_Gengrid_Item_Class_Func; + typedef struct _Elm_Gengrid_Item Elm_Gengrid_Item; /**< Item of Elm_Gengrid. Sub-type of Elm_Widget_Item */ + typedef char *(*GridItemLabelGetFunc) (void *data, Evas_Object *obj, const char *part); + typedef Evas_Object *(*GridItemIconGetFunc) (void *data, Evas_Object *obj, const char *part); + typedef Eina_Bool (*GridItemStateGetFunc) (void *data, Evas_Object *obj, const char *part); + typedef void (*GridItemDelFunc) (void *data, Evas_Object *obj); + + struct _Elm_Gengrid_Item_Class + { + const char *item_style; + struct _Elm_Gengrid_Item_Class_Func { + GridItemLabelGetFunc label_get; + GridItemIconGetFunc icon_get; + GridItemStateGetFunc state_get; + GridItemDelFunc del; + } func; + }; + + EAPI Evas_Object *elm_gengrid_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_size_set(Evas_Object *obj, Evas_Coord w, Evas_Coord h) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_size_get(const Evas_Object *obj, Evas_Coord *w, Evas_Coord *h) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_align_set(Evas_Object *obj, double align_x, double align_y) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_align_get(const Evas_Object *obj, double *align_x, double *align_y) EINA_ARG_NONNULL(1); + + EAPI void elm_gengrid_always_select_mode_set(Evas_Object *obj, Eina_Bool always_select) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_gengrid_always_select_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_no_select_mode_set(Evas_Object *obj, Eina_Bool no_select) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_gengrid_no_select_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_multi_select_set(Evas_Object *obj, Eina_Bool multi) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_gengrid_multi_select_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_page_relative_set(Evas_Object *obj, double h_pagerel, double v_pagerel) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_page_size_set(Evas_Object *obj, Evas_Coord h_pagesize, Evas_Coord v_pagesize) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_horizontal_set(Evas_Object *obj, Eina_Bool setting) EINA_ARG_NONNULL(1); + + EAPI Elm_Gengrid_Item *elm_gengrid_first_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Gengrid_Item *elm_gengrid_last_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI Elm_Gengrid_Item *elm_gengrid_item_next_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Gengrid_Item *elm_gengrid_item_prev_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_gengrid_item_gengrid_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_del(Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_update(Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void *elm_gengrid_item_data_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_data_set(Elm_Gengrid_Item *item, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_pos_get(const Elm_Gengrid_Item *item, unsigned int *x, unsigned int *y) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_selected_set(Elm_Gengrid_Item *item, Eina_Bool selected) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_gengrid_item_selected_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI const Evas_Object *elm_gengrid_item_object_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_show(Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_bring_in(Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_disabled_set(Elm_Gengrid_Item *item, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_gengrid_item_disabled_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + + EAPI void elm_gengrid_item_tooltip_text_set(Elm_Gengrid_Item *item, const char *text) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_tooltip_content_cb_set(Elm_Gengrid_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_tooltip_unset(Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_tooltip_style_set(Elm_Gengrid_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_gengrid_item_tooltip_style_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_cursor_set(Elm_Gengrid_Item *item, const char *cursor) EINA_ARG_NONNULL(1); + EAPI const char *elm_gengrid_item_cursor_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_cursor_unset(Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_cursor_style_set(Elm_Gengrid_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_gengrid_item_cursor_style_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_gengrid_item_cursor_engine_only_set(Elm_Gengrid_Item *item, Eina_Bool engine_only) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_gengrid_item_cursor_engine_only_get(const Elm_Gengrid_Item *item) EINA_ARG_NONNULL(1); + + EAPI void elm_gengrid_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Gengrid_Item *elm_gengrid_selected_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_gengrid_selected_items_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI Elm_Gengrid_Item *elm_gengrid_item_append(Evas_Object *obj, const Elm_Gengrid_Item_Class *gic, const void *data, Evas_Smart_Cb func, const void *func_data) EINA_ARG_NONNULL(1); + EAPI Elm_Gengrid_Item *elm_gengrid_item_prepend(Evas_Object *obj, const Elm_Gengrid_Item_Class *gic, const void *data, Evas_Smart_Cb func, const void *func_data) EINA_ARG_NONNULL(1); + EAPI Elm_Gengrid_Item *elm_gengrid_item_insert_before(Evas_Object *obj, const Elm_Gengrid_Item_Class *gic, const void *data, Elm_Gengrid_Item *relative, Evas_Smart_Cb func, const void *func_data) EINA_ARG_NONNULL(1); + EAPI Elm_Gengrid_Item *elm_gengrid_item_insert_after(Evas_Object *obj, const Elm_Gengrid_Item_Class *gic, const void *data, Elm_Gengrid_Item *relative, Evas_Smart_Cb func, const void *func_data) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * + * selected - User has selected a item. + * unselected - User has unselected a item. + * clicked - User has double-clicked a item. + * realized - An evas object for a item was built. + * unrealized - An evas object for a item was deleted. + * changed - An item has been added, removed, resized or moved, + * or gengrid has been resized or horizontal property has been changed. + * scroll - the content has been scrolled (moved). + * "scroll,drag,start" - dragging the contents around has started. + * "scroll,drat,stop" - dragging the contents around has stopped. + * drag - Gengrid is being dragged. + * "drag,start,up" - Gengrid has been dragged (not scrolled) up. + * "drag,start,down" - Gengrid has been dragged (not scrolled) down. + * "drag,start,left" - Gengrid has been dragged (not scrolled) left. + * "drag,start,rigth" - Gengrid has been dragged (nto scrolled) right. + * "drag,stop" - Gengrid is not being dragged. + */ + + /* clock */ + typedef enum _Elm_Clock_Digedit + { + ELM_CLOCK_NONE = 0, + ELM_CLOCK_HOUR_DECIMAL = 1 << 0, + ELM_CLOCK_HOUR_UNIT = 1 << 1, + ELM_CLOCK_MIN_DECIMAL = 1 << 2, + ELM_CLOCK_MIN_UNIT = 1 << 3, + ELM_CLOCK_SEC_DECIMAL = 1 << 4, + ELM_CLOCK_SEC_UNIT = 1 << 5, + ELM_CLOCK_ALL = (1 << 6) - 1 + } Elm_Clock_Digedit; + + EAPI Evas_Object *elm_clock_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_clock_time_set(Evas_Object *obj, int hrs, int min, int sec) EINA_ARG_NONNULL(1); + EAPI void elm_clock_time_get(const Evas_Object *obj, int *hrs, int *min, int *sec) EINA_ARG_NONNULL(1); + EAPI void elm_clock_edit_set(Evas_Object *obj, Eina_Bool edit) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_clock_edit_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_clock_digit_edit_set(Evas_Object *obj, Elm_Clock_Digedit digedit) EINA_ARG_NONNULL(1); + EAPI Elm_Clock_Digedit elm_clock_digit_edit_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_clock_show_am_pm_set(Evas_Object *obj, Eina_Bool am_pm) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_clock_show_am_pm_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_clock_show_seconds_set(Evas_Object *obj, Eina_Bool seconds) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_clock_show_seconds_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_clock_interval_set(Evas_Object *obj, double interval) EINA_ARG_NONNULL(1); + EAPI double elm_clock_interval_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "changed" - the user changed the time + */ + + /* layout */ + EAPI Evas_Object *elm_layout_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_layout_file_set(Evas_Object *obj, const char *file, const char *group) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_layout_theme_set(Evas_Object *obj, const char *clas, const char *group, const char *style) EINA_ARG_NONNULL(1); + EAPI void elm_layout_content_set(Evas_Object *obj, const char *swallow, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI const Evas_Object *elm_layout_content_get(const Evas_Object *obj, const char *swallow) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_layout_content_unset(Evas_Object *obj, const char *swallow) EINA_ARG_NONNULL(1); + EAPI void elm_layout_text_set(Evas_Object *obj, const char *part, const char *text) EINA_ARG_NONNULL(1); + EAPI const char *elm_layout_text_get(const Evas_Object *obj, const char *part) EINA_ARG_NONNULL(1); + EAPI void elm_layout_box_append(Evas_Object *obj, const char *part, Evas_Object *child) EINA_ARG_NONNULL(1); + EAPI void elm_layout_box_prepend(Evas_Object *obj, const char *part, Evas_Object *child) EINA_ARG_NONNULL(1); + EAPI void elm_layout_box_insert_before(Evas_Object *obj, const char *part, Evas_Object *child, const Evas_Object *reference) EINA_ARG_NONNULL(1); + EAPI void elm_layout_box_insert_at(Evas_Object *obj, const char *part, Evas_Object *child, unsigned int pos) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_layout_box_remove(Evas_Object *obj, const char *part, Evas_Object *child) EINA_ARG_NONNULL(1, 2, 3); + EAPI void elm_layout_box_remove_all(Evas_Object *obj, const char *part, Eina_Bool clear) EINA_ARG_NONNULL(1, 2); + EAPI void elm_layout_table_pack(Evas_Object *obj, const char *part, Evas_Object *child_obj, unsigned short col, unsigned short row, unsigned short colspan, unsigned short rowspan) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_layout_table_unpack(Evas_Object *obj, const char *part, Evas_Object *child_obj) EINA_ARG_NONNULL(1, 2, 3); + EAPI void elm_layout_table_clear(Evas_Object *obj, const char *part, Eina_Bool clear) EINA_ARG_NONNULL(1, 2); + EAPI Evas_Object *elm_layout_edje_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const char *elm_layout_data_get(const Evas_Object *obj, const char *key) EINA_ARG_NONNULL(1, 2); + EAPI void elm_layout_sizing_eval(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_layout_part_cursor_set(Evas_Object *obj, const char *part_name, const char *cursor) EINA_ARG_NONNULL(1, 2); + EAPI const char *elm_layout_part_cursor_get(const Evas_Object *obj, const char *part_name) EINA_ARG_NONNULL(1, 2); + EAPI void elm_layout_part_cursor_unset(Evas_Object *obj, const char *part_name) EINA_ARG_NONNULL(1, 2); + EAPI Eina_Bool elm_layout_part_cursor_style_set(Evas_Object *obj, const char *part_name, const char *style) EINA_ARG_NONNULL(1, 2); + EAPI const char *elm_layout_part_cursor_style_get(const Evas_Object *obj, const char *part_name) EINA_ARG_NONNULL(1, 2); + EAPI Eina_Bool elm_layout_part_cursor_engine_only_set(Evas_Object *obj, const char *part_name, Eina_Bool engine_only) EINA_ARG_NONNULL(1, 2); + EAPI Eina_Bool elm_layout_part_cursor_engine_only_get(const Evas_Object *obj, const char *part_name) EINA_ARG_NONNULL(1, 2); +/** + * @def elm_layout_icon_set + * Convienience macro to set the icon object in a layout that follows the + * Elementary naming convention for its parts. + * + * @ingroup Layout + */ +#define elm_layout_icon_set(_ly, _obj) \ + do { \ + const char *sig; \ + elm_layout_content_set((_ly), "elm.swallow.icon", (_obj)); \ + if ((_obj)) sig = "elm,state,icon,visible"; \ + else sig = "elm,state,icon,hidden"; \ + elm_object_signal_emit((_ly), sig, "elm"); \ + } while (0) + +/** + * @def elm_layout_icon_get + * Convienience macro to get the icon object from a layout that follows the + * Elementary naming convention for its parts. + * + * @ingroup Layout + */ +#define elm_layout_icon_get(_ly) \ + elm_layout_content_get((_ly), "elm.swallow.icon") + +/** + * @def elm_layout_end_set + * Convienience macro to set the end object in a layout that follows the + * Elementary naming convention for its parts. + * + * @ingroup Layout + */ +#define elm_layout_end_set(_ly, _obj) \ + do { \ + const char *sig; \ + elm_layout_content_set((_ly), "elm.swallow.end", (_obj)); \ + if ((_obj)) sig = "elm,state,end,visible"; \ + else sig = "elm,state,end,hidden"; \ + elm_object_signal_emit((_ly), sig, "elm"); \ + } while (0) + +/** + * @def elm_layout_end_get + * Convienience macro to get the end object in a layout that follows the + * Elementary naming convention for its parts. + * + * @ingroup Layout + */ +#define elm_layout_end_get(_ly) \ + elm_layout_content_get((_ly), "elm.swallow.end") + +/** + * @def elm_layout_label_set + * Convienience macro to set the label in a layout that follows the + * Elementary naming convention for its parts. + * + * @ingroup Layout + */ +#define elm_layout_label_set(_ly, _txt) \ + elm_layout_text_set((_ly), "elm.text", (_txt)) + +/** + * @def elm_layout_label_get + * Convienience macro to get the label in a layout that follows the + * Elementary naming convention for its parts. + * + * @ingroup Layout + */ +#define elm_layout_label_get(_ly) \ + elm_layout_text_get((_ly), "elm.text") + + /* smart callbacks called: + */ + + /* notify */ + typedef enum _Elm_Notify_Orient + { + ELM_NOTIFY_ORIENT_TOP, + ELM_NOTIFY_ORIENT_CENTER, + ELM_NOTIFY_ORIENT_BOTTOM, + ELM_NOTIFY_ORIENT_LEFT, + ELM_NOTIFY_ORIENT_RIGHT, + ELM_NOTIFY_ORIENT_TOP_LEFT, + ELM_NOTIFY_ORIENT_TOP_RIGHT, + ELM_NOTIFY_ORIENT_BOTTOM_LEFT, + ELM_NOTIFY_ORIENT_BOTTOM_RIGHT, + ELM_NOTIFY_ORIENT_LAST + } Elm_Notify_Orient; + EAPI Evas_Object *elm_notify_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_notify_content_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_notify_content_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_notify_content_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_notify_parent_set(Evas_Object *obj, Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_notify_parent_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_notify_orient_set(Evas_Object *obj, Elm_Notify_Orient orient) EINA_ARG_NONNULL(1); + EAPI Elm_Notify_Orient elm_notify_orient_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_notify_timeout_set(Evas_Object *obj, double timeout) EINA_ARG_NONNULL(1); + EAPI double elm_notify_timeout_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_notify_repeat_events_set(Evas_Object *obj, Eina_Bool repeat) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_notify_repeat_events_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "timeout" - when timeout happens on notify and it's hidden + * "block,clicked" - when it's hidden by a click outside of the notify's view + */ + + /* hover */ + typedef enum _Elm_Hover_Axis + { + ELM_HOVER_AXIS_NONE, + ELM_HOVER_AXIS_HORIZONTAL, + ELM_HOVER_AXIS_VERTICAL, + ELM_HOVER_AXIS_BOTH + } Elm_Hover_Axis; + EAPI Evas_Object *elm_hover_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_hover_target_set(Evas_Object *obj, Evas_Object *target) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_hover_target_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_hover_parent_set(Evas_Object *obj, Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_hover_parent_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_hover_content_set(Evas_Object *obj, const char *swallow, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_hover_content_get(const Evas_Object *obj, const char *swallow) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_hover_content_unset(Evas_Object *obj, const char *swallow) EINA_ARG_NONNULL(1); + EAPI const char *elm_hover_best_content_location_get(const Evas_Object *obj, Elm_Hover_Axis pref_axis) EINA_ARG_NONNULL(1); + /* available styles: + * default + * popout + * menu + * hoversel_vertical + */ + /* smart callbacks called: + * "clicked" - the user clicked the empty space in the hover to dismiss + * "smart,changed" - a content object placed under the "smart" + * policy was replaced to a new slot direction. + */ + + /* entry */ + typedef struct _Elm_Entry_Anchor_Info Elm_Entry_Anchor_Info; + struct _Elm_Entry_Anchor_Info + { + const char *name; + int button; + Evas_Coord x, y, w, h; + }; + typedef enum _Elm_Icon_Type + { + ELM_ICON_NONE, + ELM_ICON_FILE, + ELM_ICON_STANDARD + } Elm_Icon_Type; + typedef struct _Elm_Hoversel_Item Elm_Hoversel_Item; /**< Item of Elm_Hoversel. Sub-type of Elm_Widget_Item */ + + EAPI Evas_Object *elm_entry_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_entry_single_line_set(Evas_Object *obj, Eina_Bool single_line) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_single_line_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_password_set(Evas_Object *obj, Eina_Bool password) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_password_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_entry_set(Evas_Object *obj, const char *entry) EINA_ARG_NONNULL(1); + EAPI const char *elm_entry_entry_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_is_empty(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const char *elm_entry_selection_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_entry_insert(Evas_Object *obj, const char *entry) EINA_ARG_NONNULL(1); + EAPI void elm_entry_line_wrap_set(Evas_Object *obj, Eina_Bool wrap) EINA_ARG_NONNULL(1); + EAPI void elm_entry_line_char_wrap_set(Evas_Object *obj, Eina_Bool wrap) EINA_ARG_NONNULL(1); + EAPI void elm_entry_editable_set(Evas_Object *obj, Eina_Bool editable) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_editable_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_select_none(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_select_all(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_cursor_next(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_cursor_prev(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_cursor_up(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_cursor_down(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_cursor_begin_set(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_cursor_end_set(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_cursor_line_begin_set(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_cursor_line_end_set(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_cursor_selection_begin(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_cursor_selection_end(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_cursor_is_format_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_cursor_is_visible_format_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const char *elm_entry_cursor_content_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_cursor_geometry_get(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h) EINA_ARG_NONNULL(1); + EAPI void elm_entry_selection_cut(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_selection_copy(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_selection_paste(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_context_menu_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_context_menu_item_add(Evas_Object *obj, const char *label, const char *icon_file, Elm_Icon_Type icon_type, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_entry_context_menu_disabled_set(Evas_Object *obj, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_context_menu_disabled_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_item_provider_append(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_entry_item_provider_prepend(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_entry_item_provider_remove(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_entry_text_filter_append(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_entry_text_filter_prepend(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_entry_text_filter_remove(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) EINA_ARG_NONNULL(1, 2); + EAPI char *elm_entry_markup_to_utf8(const char *s); + EAPI char *elm_entry_utf8_to_markup(const char *s); + EAPI void elm_entry_file_set(Evas_Object *obj, const char *file, Elm_Text_Format format) EINA_ARG_NONNULL(1); + EAPI void elm_entry_file_get(const Evas_Object *obj, const char **file, Elm_Text_Format *format) EINA_ARG_NONNULL(1); + EAPI void elm_entry_file_save(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_autosave_set(Evas_Object *obj, Eina_Bool autosave) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_autosave_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_entry_cnp_textonly_set(Evas_Object *obj, Eina_Bool textonly) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_entry_cnp_textonly_get(Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* pre-made filters for entries */ + typedef struct _Elm_Entry_Filter_Limit_Size Elm_Entry_Filter_Limit_Size; + struct _Elm_Entry_Filter_Limit_Size + { + int max_char_count; + int max_byte_count; + }; + EAPI void elm_entry_filter_limit_size(void *data, Evas_Object *entry, char **text) EINA_ARG_NONNULL(1, 2, 3); + typedef struct _Elm_Entry_Filter_Accept_Set Elm_Entry_Filter_Accept_Set; + struct _Elm_Entry_Filter_Accept_Set + { + const char *accepted; + const char *rejected; + }; + EAPI void elm_entry_filter_accept_set(void *data, Evas_Object *entry, char **text) EINA_ARG_NONNULL(1, 3); + /* smart callbacks called: + * "changed" - the text content changed + * "selection,start" - the user started selecting text + * "selection,changed" - the user modified the selection size/location + * "selection,cleared" - the user cleared the selection + * "selection,paste" - the user requested a paste of text + * "selection,copy" - the user copied the text + * "selection,cut" - the user cut the text + * "cursor,changed" - the cursor changed position + * "anchor,clicked" - achor called was clicked | event_info = Elm_Entry_Anchor_Info + * "activated" - when the enter key is pressed (useful for single line) + * "press" - when finger/mouse is pressed down + * "clicked" - when finger/mouse is pressed and released (without a drag etc.) + * "clicked,double" - when finger/mouse is double-pressed + * "longpressed" - the entry has been longpressed + * "focused" - the entry has received keyboard focus + * "unfocused" - keyboard focus is gone + */ + + /* composite widgets - these basically put together basic widgets above + * in convenient packages that do more than basic stuff */ + + /* anchorview */ + typedef struct _Elm_Entry_Anchorview_Info Elm_Entry_Anchorview_Info; + struct _Elm_Entry_Anchorview_Info + { + const char *name; + int button; + Evas_Object *hover; + struct { + Evas_Coord x, y, w, h; + } anchor, hover_parent; + Eina_Bool hover_left : 1; + Eina_Bool hover_right : 1; + Eina_Bool hover_top : 1; + Eina_Bool hover_bottom : 1; + }; + EAPI Evas_Object *elm_anchorview_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_anchorview_text_set(Evas_Object *obj, const char *text) EINA_ARG_NONNULL(1); + EAPI const char *elm_anchorview_text_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI void elm_anchorview_hover_parent_set(Evas_Object *obj, Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_anchorview_hover_parent_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_anchorview_hover_style_set(Evas_Object *obj, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_anchorview_hover_style_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_anchorview_hover_end(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_anchorview_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_anchorview_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_anchorview_item_provider_append(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorview, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_anchorview_item_provider_prepend(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorview, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_anchorview_item_provider_remove(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorview, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + /* smart callbacks called: + * "anchor,clicked" - achor called was clicked | event_info = Elm_Entry_Anchorview_Info + */ + + /* anchorblock */ + typedef struct _Elm_Entry_Anchorblock_Info Elm_Entry_Anchorblock_Info; + struct _Elm_Entry_Anchorblock_Info + { + const char *name; + int button; + Evas_Object *hover; + struct { + Evas_Coord x, y, w, h; + } anchor, hover_parent; + Eina_Bool hover_left : 1; + Eina_Bool hover_right : 1; + Eina_Bool hover_top : 1; + Eina_Bool hover_bottom : 1; + }; + EAPI Evas_Object *elm_anchorblock_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_anchorblock_text_set(Evas_Object *obj, const char *text) EINA_ARG_NONNULL(1); + EAPI const char *elm_anchorblock_text_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_anchorblock_hover_parent_set(Evas_Object *obj, Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_anchorblock_hover_parent_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_anchorblock_hover_style_set(Evas_Object *obj, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_anchorblock_hover_style_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_anchorblock_hover_end(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_anchorblock_item_provider_append(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorblock, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_anchorblock_item_provider_prepend(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorblock, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_anchorblock_item_provider_remove(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorblock, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + /* smart callbacks called: + * "anchor,clicked" - achor called was clicked | event_info = Elm_Entry_Anchorblock_Info + */ + + /* bubble */ + EAPI Evas_Object *elm_bubble_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_bubble_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_bubble_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_bubble_info_set(Evas_Object *obj, const char *info) EINA_ARG_NONNULL(1); + EAPI const char *elm_bubble_info_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI void elm_bubble_content_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_bubble_content_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_bubble_content_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_bubble_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_bubble_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_bubble_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_bubble_corner_set(Evas_Object *obj, const char *corner) EINA_ARG_NONNULL(1, 2); + EAPI const char *elm_bubble_corner_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "clicked" - the user clicked the bubble + */ + + /* photo */ + EAPI Evas_Object *elm_photo_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_photo_file_set(Evas_Object *obj, const char *file) EINA_ARG_NONNULL(1); + EAPI void elm_photo_size_set(Evas_Object *obj, int size) EINA_ARG_NONNULL(1); + EAPI void elm_photo_fill_inside_set(Evas_Object *obj, Eina_Bool fill) EINA_ARG_NONNULL(1); + EAPI void elm_photo_editable_set(Evas_Object *obj, Eina_Bool set) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "clicked" - the user clicked the icon + */ + + /* thumb */ + typedef enum _Elm_Thumb_Animation_Setting + { + ELM_THUMB_ANIMATION_START = 0, /* Play animation once */ + ELM_THUMB_ANIMATION_LOOP, /* Keep playing animation until stop is requested */ + ELM_THUMB_ANIMATION_STOP, + ELM_THUMB_ANIMATION_LAST + } Elm_Thumb_Animation_Setting; + + EAPI Evas_Object *elm_thumb_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_thumb_reload(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_thumb_file_set(Evas_Object *obj, const char *file, const char *key) EINA_ARG_NONNULL(1); + EAPI void elm_thumb_file_get(const Evas_Object *obj, const char **file, const char **key) EINA_ARG_NONNULL(1); + EAPI void elm_thumb_path_get(const Evas_Object *obj, const char **file, const char **key) EINA_ARG_NONNULL(1); + EAPI void elm_thumb_animate_set(Evas_Object *obj, Elm_Thumb_Animation_Setting s) EINA_ARG_NONNULL(1); + EAPI Elm_Thumb_Animation_Setting elm_thumb_animate_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void *elm_thumb_ethumb_client_get(void); + EAPI Eina_Bool elm_thumb_ethumb_client_connected(void); + EAPI Eina_Bool elm_thumb_editable_set(Evas_Object *obj, Eina_Bool edit) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_thumb_editable_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* available styles: + * default + * noframe + * + * smart callbacks called: + * "clicked" - the user clicked the thumb + * "clicked,double" - the user double clicked the thumb + * "press" - the user pressed the thumb + * "generate,start" - the thumbnail generation started + * "generate,stop" - the thumbnail generation stopped + * "generate,error" - the thumbnail generation failed + * "load,error" - the thumbnail image loading failed + */ + + /* hoversel */ + EAPI Evas_Object *elm_hoversel_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_hoversel_horizontal_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_hover_parent_set(Evas_Object *obj, Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_hoversel_hover_parent_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_hoversel_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_hoversel_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_hoversel_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_hover_begin(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_hover_end(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_hoversel_expanded_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_hoversel_items_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Hoversel_Item *elm_hoversel_item_add(Evas_Object *obj, const char *label, const char *icon_file, Elm_Icon_Type icon_type, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_item_del(Elm_Hoversel_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_item_del_cb_set(Elm_Hoversel_Item *it, Evas_Smart_Cb func) EINA_ARG_NONNULL(1); + EAPI void *elm_hoversel_item_data_get(const Elm_Hoversel_Item *it) EINA_ARG_NONNULL(1); + EAPI const char *elm_hoversel_item_label_get(const Elm_Hoversel_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_item_icon_set(Elm_Hoversel_Item *it, const char *icon_file, const char *icon_group, Elm_Icon_Type icon_type) EINA_ARG_NONNULL(1); + EAPI void elm_hoversel_item_icon_get(const Elm_Hoversel_Item *it, const char **icon_file, const char **icon_group, Elm_Icon_Type *icon_type) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "clicked" - the user clicked the hoversel button and popped up the sel + * "selected" - an item in the hoversel list is selected + * "dismissed" - the hover is dismissed + */ + + /* toolbar */ + typedef enum _Elm_Toolbar_Shrink_Mode + { + ELM_TOOLBAR_SHRINK_NONE, /**< set toolbar minimun size to fit all the items */ + ELM_TOOLBAR_SHRINK_HIDE, /**< hide excess items */ + ELM_TOOLBAR_SHRINK_SCROLL, /**< allow accessing excess items through a scroller */ + ELM_TOOLBAR_SHRINK_MENU /**< inserts a button to pop up a menu with excess items */ + } Elm_Toolbar_Shrink_Mode; + + typedef struct _Elm_Toolbar_Item Elm_Toolbar_Item; /**< Item of Elm_Toolbar. Sub-type of Elm_Widget_Item */ + typedef struct _Elm_Toolbar_Item_State Elm_Toolbar_Item_State; /** State of a Elm_Toolbar_Item */ + + EAPI Evas_Object *elm_toolbar_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_icon_size_set(Evas_Object *obj, int icon_size) EINA_ARG_NONNULL(1); + EAPI int elm_toolbar_icon_size_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_icon_order_lookup_set(Evas_Object *obj, Elm_Icon_Lookup_Order order) EINA_ARG_NONNULL(1); + EAPI Elm_Icon_Lookup_Order elm_toolbar_icon_order_lookup_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_no_select_mode_set(Evas_Object *obj, Eina_Bool no_select) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_toolbar_no_select_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_item_append(Evas_Object *obj, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_item_prepend(Evas_Object *obj, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_item_insert_before(Evas_Object *obj, Elm_Toolbar_Item *before, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_item_insert_after(Evas_Object *obj, Elm_Toolbar_Item *after, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_first_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_last_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_item_next_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_item_prev_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_toolbar_item_toolbar_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_priority_set(Elm_Toolbar_Item *item, int priority) EINA_ARG_NONNULL(1); + EAPI int elm_toolbar_item_priority_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI const char *elm_toolbar_item_icon_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI const char *elm_toolbar_item_label_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_label_set(Elm_Toolbar_Item *item, const char *label) EINA_ARG_NONNULL(1); + EAPI void *elm_toolbar_item_data_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_data_set(Elm_Toolbar_Item *item, const void *data) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_item_find_by_label(const Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_toolbar_item_selected_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_selected_set(Elm_Toolbar_Item *item, Eina_Bool selected) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item *elm_toolbar_selected_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_icon_set(Elm_Toolbar_Item *item, const char *icon) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_del(Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_del_cb_set(Elm_Toolbar_Item *item, Evas_Smart_Cb func) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_toolbar_item_disabled_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_disabled_set(Elm_Toolbar_Item *item, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_separator_set(Elm_Toolbar_Item *item, Eina_Bool separator) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_toolbar_item_separator_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_mode_shrink_set(Evas_Object *obj, Elm_Toolbar_Shrink_Mode shrink_mode) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Shrink_Mode elm_toolbar_mode_shrink_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_homogenous_set(Evas_Object *obj, Eina_Bool homogenous) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_toolbar_homogenous_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_menu_parent_set(Evas_Object *obj, Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_toolbar_menu_parent_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_align_set(Evas_Object *obj, double align) EINA_ARG_NONNULL(1); + EAPI double elm_toolbar_align_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_menu_set(Elm_Toolbar_Item *item, Eina_Bool menu) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_toolbar_item_menu_get(Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item_State *elm_toolbar_item_state_add(Elm_Toolbar_Item *item, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_toolbar_item_state_del(Elm_Toolbar_Item *item, Elm_Toolbar_Item_State *state) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_toolbar_item_state_set(Elm_Toolbar_Item *it, Elm_Toolbar_Item_State *state) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_state_unset(Elm_Toolbar_Item *it) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item_State *elm_toolbar_item_state_get(const Elm_Toolbar_Item *it) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item_State *elm_toolbar_item_state_next(Elm_Toolbar_Item *it) EINA_ARG_NONNULL(1); + EAPI Elm_Toolbar_Item_State *elm_toolbar_item_state_prev(Elm_Toolbar_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_tooltip_text_set(Elm_Toolbar_Item *item, const char *text) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_tooltip_content_cb_set(Elm_Toolbar_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_tooltip_unset(Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_tooltip_style_set(Elm_Toolbar_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_toolbar_item_tooltip_style_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_cursor_set(Elm_Toolbar_Item *item, const char *cursor) EINA_ARG_NONNULL(1); + EAPI const char *elm_toolbar_item_cursor_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_cursor_unset(Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_cursor_style_set(Elm_Toolbar_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_toolbar_item_cursor_style_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_toolbar_item_cursor_engine_only_set(Elm_Toolbar_Item *item, Eina_Bool engine_only) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_toolbar_item_cursor_engine_only_get(const Elm_Toolbar_Item *item) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "clicked" - when the user clicks on a toolbar item and becomes selected + */ + /* available styles: + * default + * transparent (no background or shadow, just show the provided content) + */ + + /* tooltip */ + EAPI double elm_tooltip_delay_get(void); + EAPI Eina_Bool elm_tooltip_delay_set(double delay); + EAPI void elm_object_tooltip_show(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_tooltip_hide(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_tooltip_text_set(Evas_Object *obj, const char *text) EINA_ARG_NONNULL(1, 2); + EAPI void elm_object_tooltip_content_cb_set(Evas_Object *obj, Elm_Tooltip_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) EINA_ARG_NONNULL(1); + EAPI void elm_object_tooltip_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_tooltip_style_set(Evas_Object *obj, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_object_tooltip_style_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_cursor_set(Evas_Object *obj, const char *cursor) EINA_ARG_NONNULL(1); + EAPI const char *elm_object_cursor_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_cursor_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_cursor_style_set(Evas_Object *obj, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_object_cursor_style_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_object_cursor_engine_only_set(Evas_Object *obj, Eina_Bool engine_only) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_object_cursor_engine_only_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* cursors */ + EAPI int elm_cursor_engine_only_get(void); + EAPI Eina_Bool elm_cursor_engine_only_set(int engine_only); + + /* menu */ + typedef struct _Elm_Menu_Item Elm_Menu_Item; /**< Item of Elm_Menu. Sub-type of Elm_Widget_Item */ + EAPI Evas_Object *elm_menu_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_menu_parent_set(Evas_Object *obj, Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_menu_parent_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_menu_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_menu_object_get(const Elm_Menu_Item *it) EINA_ARG_NONNULL(1); + EAPI Elm_Menu_Item *elm_menu_item_add(Evas_Object *obj, Elm_Menu_Item *parent, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_menu_item_label_set(Elm_Menu_Item *item, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_menu_item_label_get(const Elm_Menu_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_menu_item_icon_set(Elm_Menu_Item *item, const char *icon) EINA_ARG_NONNULL(1, 2); + EAPI const char *elm_menu_item_icon_get(const Elm_Menu_Item *item) EINA_ARG_NONNULL(1); + EAPI const Evas_Object *elm_menu_item_object_icon_get(const Elm_Menu_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_menu_item_disabled_set(Elm_Menu_Item *item, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_menu_item_disabled_get(const Elm_Menu_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Menu_Item *elm_menu_item_separator_add(Evas_Object *obj, Elm_Menu_Item *parent) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_menu_item_is_separator(Elm_Menu_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_menu_item_del(Elm_Menu_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_menu_item_del_cb_set(Elm_Menu_Item *it, Evas_Smart_Cb func) EINA_ARG_NONNULL(1); + EAPI void *elm_menu_item_data_get(const Elm_Menu_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_menu_item_data_set(Elm_Menu_Item *item, const void *data) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_menu_item_subitems_get(const Elm_Menu_Item *item) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "clicked" - the user clicked the empty space in the menu to dismiss. event_info is NULL. + */ + + /* list */ + typedef enum _Elm_List_Mode + { + ELM_LIST_COMPRESS = 0, + ELM_LIST_SCROLL, + ELM_LIST_LIMIT, + ELM_LIST_EXPAND, + ELM_LIST_LAST + } Elm_List_Mode; + typedef struct _Elm_List_Item Elm_List_Item; /**< Item of Elm_List. Sub-type of Elm_Widget_Item */ + EAPI Evas_Object *elm_list_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Elm_List_Item *elm_list_item_append(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI Elm_List_Item *elm_list_item_prepend(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI Elm_List_Item *elm_list_item_insert_before(Evas_Object *obj, Elm_List_Item *before, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1, 2); + EAPI Elm_List_Item *elm_list_item_insert_after(Evas_Object *obj, Elm_List_Item *after, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1, 2); + EAPI Elm_List_Item *elm_list_item_sorted_insert(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data, Eina_Compare_Cb cmp_func) EINA_ARG_NONNULL(1); + EAPI void elm_list_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_list_go(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_list_multi_select_set(Evas_Object *obj, Eina_Bool multi) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_list_multi_select_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_list_mode_set(Evas_Object *obj, Elm_List_Mode mode) EINA_ARG_NONNULL(1); + EAPI Elm_List_Mode elm_list_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_list_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_list_horizontal_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_list_always_select_mode_set(Evas_Object *obj, Eina_Bool always_select) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_list_always_select_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_list_items_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_List_Item *elm_list_selected_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_list_selected_items_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_separator_set(Elm_List_Item *it, Eina_Bool setting) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_list_item_separator_get(const Elm_List_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_selected_set(Elm_List_Item *item, Eina_Bool selected) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_list_item_selected_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_show(Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_bring_in(Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_del(Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_del_cb_set(Elm_List_Item *item, Evas_Smart_Cb func) EINA_ARG_NONNULL(1); + EAPI void *elm_list_item_data_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_list_item_icon_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_icon_set(Elm_List_Item *item, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_list_item_end_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_end_set(Elm_List_Item *item, Evas_Object *end) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_list_item_base_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI const char *elm_list_item_label_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_label_set(Elm_List_Item *item, const char *text) EINA_ARG_NONNULL(1); + EAPI Elm_List_Item *elm_list_item_prev(const Elm_List_Item *it) EINA_ARG_NONNULL(1); + EAPI Elm_List_Item *elm_list_item_next(const Elm_List_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_tooltip_text_set(Elm_List_Item *item, const char *text) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_tooltip_content_cb_set(Elm_List_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_tooltip_unset(Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_tooltip_style_set(Elm_List_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_list_item_tooltip_style_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_cursor_set(Elm_List_Item *item, const char *cursor) EINA_ARG_NONNULL(1); + EAPI const char *elm_list_item_cursor_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_cursor_unset(Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_cursor_style_set(Elm_List_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_list_item_cursor_style_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_cursor_engine_only_set(Elm_List_Item *item, Eina_Bool engine_only) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_list_item_cursor_engine_only_get(const Elm_List_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_list_item_disabled_set(Elm_List_Item *it, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_list_item_disabled_get(const Elm_List_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_list_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_list_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_list_scroller_policy_set(Evas_Object *obj, Elm_Scroller_Policy policy_h, Elm_Scroller_Policy policy_v) EINA_ARG_NONNULL(1); + EAPI void elm_list_scroller_policy_get(const Evas_Object *obj, Elm_Scroller_Policy *policy_h, Elm_Scroller_Policy *policy_v) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "clicked" - when the user double-clicked an item + * "selected" - when the user selected an item + * "unselected" - when the user selected an item + * "longpressed" - an item in the hoversel list is long-pressed + * "scroll,edge,top" - the list is scrolled until the top edge + * "scroll,edge,bottom" - the list is scrolled until the bottom edge + * "scroll,edge,left" - the list is scrolled until the left edge + * "scroll,edge,right" - the list is scrolled until the right edge + */ + + /* slider */ + EAPI Evas_Object *elm_slider_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_slider_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_slider_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slider_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_slider_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_slider_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slider_end_set(Evas_Object *obj, Evas_Object *end) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_slider_end_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_slider_end_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slider_span_size_set(Evas_Object *obj, Evas_Coord size) EINA_ARG_NONNULL(1); + EAPI Evas_Coord elm_slider_span_size_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slider_unit_format_set(Evas_Object *obj, const char *format) EINA_ARG_NONNULL(1); + EAPI const char *elm_slider_unit_format_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slider_indicator_format_set(Evas_Object *obj, const char *indicator) EINA_ARG_NONNULL(1); + EAPI const char *elm_slider_indicator_format_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slider_indicator_format_function_set(Evas_Object *obj, const char *(*func)(double val)) EINA_ARG_NONNULL(1); + EAPI void elm_slider_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_slider_horizontal_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slider_min_max_set(Evas_Object *obj, double min, double max) EINA_ARG_NONNULL(1); + EAPI void elm_slider_min_max_get(const Evas_Object *obj, double *min, double *max) EINA_ARG_NONNULL(1); + EAPI void elm_slider_value_set(Evas_Object *obj, double val) EINA_ARG_NONNULL(1); + EAPI double elm_slider_value_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slider_inverted_set(Evas_Object *obj, Eina_Bool inverted) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_slider_inverted_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slider_indicator_show_set(Evas_Object *obj, Eina_Bool show) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_slider_indicator_show_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* actionslider */ + typedef enum _Elm_Actionslider_Pos + { + ELM_ACTIONSLIDER_NONE = 0, + ELM_ACTIONSLIDER_LEFT = 1 << 0, + ELM_ACTIONSLIDER_CENTER = 1 << 1, + ELM_ACTIONSLIDER_RIGHT = 1 << 2, + ELM_ACTIONSLIDER_ALL = (1 << 3) -1 + } Elm_Actionslider_Pos; + + EAPI Evas_Object *elm_actionslider_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_actionslider_labels_set(Evas_Object *obj, const char *left_label, const char *center_label, const char *right_label) EINA_ARG_NONNULL(1); + EAPI void elm_actionslider_labels_get(const Evas_Object *obj, const char **left_label, const char **center_label, const char **right_label) EINA_ARG_NONNULL(1); + EAPI const char *elm_actionslider_selected_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_actionslider_indicator_pos_set(Evas_Object *obj, Elm_Actionslider_Pos pos) EINA_ARG_NONNULL(1); + EAPI Elm_Actionslider_Pos elm_actionslider_indicator_pos_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_actionslider_magnet_pos_set(Evas_Object *obj, Elm_Actionslider_Pos pos) EINA_ARG_NONNULL(1); + EAPI Elm_Actionslider_Pos elm_actionslider_magnet_pos_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_actionslider_enabled_pos_set(Evas_Object *obj, Elm_Actionslider_Pos pos) EINA_ARG_NONNULL(1); + EAPI Elm_Actionslider_Pos elm_actionslider_enabled_pos_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_actionslider_indicator_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_actionslider_indicator_label_get(Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "selected" - when user selects a position (the label is passed as + * event info)". + * "pos_changed" - when a button reaches to the special position like + * "left", "right" and "center". + */ + + /* genlist */ + typedef enum _Elm_Genlist_Item_Flags + { + ELM_GENLIST_ITEM_NONE = 0, + ELM_GENLIST_ITEM_SUBITEMS = (1 << 0), + ELM_GENLIST_ITEM_GROUP = (1 << 1) + } Elm_Genlist_Item_Flags; + typedef struct _Elm_Genlist_Item_Class Elm_Genlist_Item_Class; + typedef struct _Elm_Genlist_Item Elm_Genlist_Item; /**< Item of Elm_Genlist. Sub-type of Elm_Widget_Item */ + typedef struct _Elm_Genlist_Item_Class_Func Elm_Genlist_Item_Class_Func; + typedef char *(*GenlistItemLabelGetFunc) (void *data, Evas_Object *obj, const char *part); + typedef Evas_Object *(*GenlistItemIconGetFunc) (void *data, Evas_Object *obj, const char *part); + typedef Eina_Bool (*GenlistItemStateGetFunc) (void *data, Evas_Object *obj, const char *part); + typedef void (*GenlistItemDelFunc) (void *data, Evas_Object *obj); + + struct _Elm_Genlist_Item_Class + { + const char *item_style; + struct { + GenlistItemLabelGetFunc label_get; + GenlistItemIconGetFunc icon_get; + GenlistItemStateGetFunc state_get; + GenlistItemDelFunc del; + } func; + }; + + EAPI Evas_Object *elm_genlist_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_multi_select_set(Evas_Object *obj, Eina_Bool multi) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_multi_select_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_horizontal_mode_set(Evas_Object *obj, Elm_List_Mode mode) EINA_ARG_NONNULL(1); + EAPI Elm_List_Mode elm_genlist_horizontal_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_always_select_mode_set(Evas_Object *obj, Eina_Bool always_select) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_always_select_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_no_select_mode_set(Evas_Object *obj, Eina_Bool no_select) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_no_select_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_compress_mode_set(Evas_Object *obj, Eina_Bool compress) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_compress_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_height_for_width_mode_set(Evas_Object *obj, Eina_Bool height_for_width) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_height_for_width_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_homogeneous_set(Evas_Object *obj, Eina_Bool homogeneous) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_homogeneous_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_block_count_set(Evas_Object *obj, int n) EINA_ARG_NONNULL(1); + EAPI int elm_genlist_block_count_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_longpress_timeout_set(Evas_Object *obj, double timeout) EINA_ARG_NONNULL(1); + EAPI double elm_genlist_longpress_timeout_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* operations to add items */ + EAPI Elm_Genlist_Item *elm_genlist_item_append(Evas_Object *obj, const Elm_Genlist_Item_Class *itc, const void *data, Elm_Genlist_Item *parent, Elm_Genlist_Item_Flags flags, Evas_Smart_Cb func, const void *func_data) EINA_ARG_NONNULL(1); + EAPI Elm_Genlist_Item *elm_genlist_item_prepend(Evas_Object *obj, const Elm_Genlist_Item_Class *itc, const void *data, Elm_Genlist_Item *parent, Elm_Genlist_Item_Flags flags, Evas_Smart_Cb func, const void *func_data) EINA_ARG_NONNULL(1); + EAPI Elm_Genlist_Item *elm_genlist_item_insert_before(Evas_Object *obj, const Elm_Genlist_Item_Class *itc, const void *data, Elm_Genlist_Item *parent, Elm_Genlist_Item *before, Elm_Genlist_Item_Flags flags, Evas_Smart_Cb func, const void *func_data) EINA_ARG_NONNULL(1, 5); + EAPI Elm_Genlist_Item *elm_genlist_item_insert_after(Evas_Object *obj, const Elm_Genlist_Item_Class *itc, const void *data, Elm_Genlist_Item *parent, Elm_Genlist_Item *after, Elm_Genlist_Item_Flags flags, Evas_Smart_Cb func, const void *func_data) EINA_ARG_NONNULL(1, 5); + /* operations to retrieve existing items */ + EAPI Elm_Genlist_Item *elm_genlist_selected_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_genlist_selected_items_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_List *elm_genlist_realized_items_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Genlist_Item *elm_genlist_at_xy_item_get(const Evas_Object *obj, Evas_Coord x, Evas_Coord y, int *posret) EINA_ARG_NONNULL(1); + EAPI Elm_Genlist_Item *elm_genlist_first_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Genlist_Item *elm_genlist_last_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_scroller_policy_set(Evas_Object *obj, Elm_Scroller_Policy policy_h, Elm_Scroller_Policy policy_v) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_scroller_policy_get(const Evas_Object *obj, Elm_Scroller_Policy *policy_h, Elm_Scroller_Policy *policy_v) EINA_ARG_NONNULL(1); + /* available item styles: + * default + * default_style - The text part is a textblock + * double_label + * icon_top_text_bottom + */ + /* Genlist Item operation */ + EAPI Elm_Genlist_Item *elm_genlist_item_next_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Genlist_Item *elm_genlist_item_prev_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_genlist_item_genlist_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Genlist_Item *elm_genlist_item_parent_get(const Elm_Genlist_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_subitems_clear(Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_selected_set(Elm_Genlist_Item *item, Eina_Bool selected) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_item_selected_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_expanded_set(Elm_Genlist_Item *item, Eina_Bool expanded) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_item_expanded_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI int elm_genlist_item_expanded_depth_get(const Elm_Genlist_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_disabled_set(Elm_Genlist_Item *item, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_item_disabled_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_display_only_set(Elm_Genlist_Item *it, Eina_Bool display_only) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_item_display_only_get(const Elm_Genlist_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_show(Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_bring_in(Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_top_show(Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_top_bring_in(Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_middle_show(Elm_Genlist_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_middle_bring_in(Elm_Genlist_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_del(Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void *elm_genlist_item_data_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_data_set(Elm_Genlist_Item *it, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_icons_orphan(Elm_Genlist_Item *it) EINA_ARG_NONNULL(1); + EAPI const Evas_Object *elm_genlist_item_object_get(const Elm_Genlist_Item *it) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_update(Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_item_class_update(Elm_Genlist_Item *it, const Elm_Genlist_Item_Class *itc) EINA_ARG_NONNULL(1, 2); + EAPI void elm_genlist_item_tooltip_text_set(Elm_Genlist_Item *item, const char *text) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_tooltip_content_cb_set(Elm_Genlist_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_tooltip_unset(Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_tooltip_style_set(Elm_Genlist_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_genlist_item_tooltip_style_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_cursor_set(Elm_Genlist_Item *item, const char *cursor) EINA_ARG_NONNULL(1); + EAPI const char *elm_genlist_item_cursor_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_cursor_unset(Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_cursor_style_set(Elm_Genlist_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_genlist_item_cursor_style_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_genlist_item_cursor_engine_only_set(Elm_Genlist_Item *item, Eina_Bool engine_only) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_genlist_item_cursor_engine_only_get(const Elm_Genlist_Item *item) EINA_ARG_NONNULL(1); + + /* check */ + EAPI Evas_Object *elm_check_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_check_label_set(Evas_Object *obj, const char *label); EINA_ARG_NONNULL(1) + EAPI const char *elm_check_label_get(const Evas_Object *obj); EINA_ARG_NONNULL(1) + EAPI void elm_check_icon_set(Evas_Object *obj, Evas_Object *icon); EINA_ARG_NONNULL(1) + EAPI Evas_Object *elm_check_icon_get(const Evas_Object *obj); EINA_ARG_NONNULL(1) + EAPI Evas_Object *elm_check_icon_unset(Evas_Object *obj); EINA_ARG_NONNULL(1) + EAPI void elm_check_state_set(Evas_Object *obj, Eina_Bool state); EINA_ARG_NONNULL(1) + EAPI Eina_Bool elm_check_state_get(const Evas_Object *obj); EINA_ARG_NONNULL(1) + EAPI void elm_check_state_pointer_set(Evas_Object *obj, Eina_Bool *statep); EINA_ARG_NONNULL(1) + + /* radio */ + EAPI Evas_Object *elm_radio_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_radio_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_radio_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_radio_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_radio_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_radio_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_radio_group_add(Evas_Object *obj, Evas_Object *group) EINA_ARG_NONNULL(1); + EAPI void elm_radio_state_value_set(Evas_Object *obj, int value) EINA_ARG_NONNULL(1); + EAPI int elm_radio_state_value_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_radio_value_set(Evas_Object *obj, int value) EINA_ARG_NONNULL(1); + EAPI int elm_radio_value_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_radio_value_pointer_set(Evas_Object *obj, int *valuep) EINA_ARG_NONNULL(1); + + /* pager */ + EAPI Evas_Object *elm_pager_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_pager_content_push(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI void elm_pager_content_pop(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_pager_content_promote(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_pager_content_bottom_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_pager_content_top_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* available item styles: + * default + * fade + * fade_translucide + * fade_invisible + */ + + typedef struct _Elm_Slideshow_Item_Class Elm_Slideshow_Item_Class; + typedef struct _Elm_Slideshow_Item_Class_Func Elm_Slideshow_Item_Class_Func; + typedef struct _Elm_Slideshow_Item Elm_Slideshow_Item; /**< Item of Elm_Slideshow. Sub-type of Elm_Widget_Item */ + typedef Evas_Object *(*SlideshowItemGetFunc) (void *data, Evas_Object *obj); + typedef void (*SlideshowItemDelFunc) (void *data, Evas_Object *obj); + + struct _Elm_Slideshow_Item_Class + { + struct _Elm_Slideshow_Item_Class_Func { + SlideshowItemGetFunc get; + SlideshowItemDelFunc del; + } func; + }; + + EAPI Evas_Object *elm_slideshow_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Elm_Slideshow_Item *elm_slideshow_item_add(Evas_Object *obj, const Elm_Slideshow_Item_Class *itc, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_slideshow_show(Elm_Slideshow_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_slideshow_next(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slideshow_previous(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_slideshow_transitions_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slideshow_transition_set(Evas_Object *obj, const char *transition) EINA_ARG_NONNULL(1); + EAPI const char *elm_slideshow_transition_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slideshow_timeout_set(Evas_Object *obj, double timeout) EINA_ARG_NONNULL(1); + EAPI double elm_slideshow_timeout_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slideshow_loop_set(Evas_Object *obj, Eina_Bool loop) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_slideshow_loop_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slideshow_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_slideshow_items_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slideshow_item_del(Elm_Slideshow_Item *item) EINA_ARG_NONNULL(1); + EAPI void *elm_slideshow_item_data_get(const Elm_Slideshow_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Slideshow_Item *elm_slideshow_item_current_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object* elm_slideshow_item_object_get(const Elm_Slideshow_Item* item) EINA_ARG_NONNULL(1); + EAPI const char *elm_slideshow_layout_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_slideshow_layout_set(Evas_Object *obj, const char *layout) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_slideshow_layouts_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "changed" - when the slideshow switch to another item + */ + + /* file selector */ + typedef enum _Elm_Fileselector_Mode + { + ELM_FILESELECTOR_LIST = 0, + ELM_FILESELECTOR_GRID, + ELM_FILESELECTOR_LAST + } Elm_Fileselector_Mode; + + EAPI Evas_Object *elm_fileselector_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_is_save_set(Evas_Object *obj, Eina_Bool is_save) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_is_save_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_folder_only_set(Evas_Object *obj, Eina_Bool only) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_folder_only_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_buttons_ok_cancel_set(Evas_Object *obj, Eina_Bool buttons) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_buttons_ok_cancel_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_expandable_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_expandable_set(Evas_Object *obj, Eina_Bool expand) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_path_set(Evas_Object *obj, const char *path) EINA_ARG_NONNULL(1); + EAPI const char *elm_fileselector_path_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const char *elm_fileselector_selected_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_fileselector_selected_set(Evas_Object *obj, const char *path) EINA_ARG_NONNULL(1); + EAPI void elm_fileselector_mode_set(Evas_Object *obj, Elm_Fileselector_Mode mode) EINA_ARG_NONNULL(1); + EAPI Elm_Fileselector_Mode elm_fileselector_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "selected" - the user click on a file + * "directory,open" - the list is populate with a new content. event_info is a directory. + * "done" - the user click on the ok or cancel buttons + */ + + /* progressbar */ + EAPI Evas_Object *elm_progressbar_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_progressbar_pulse_set(Evas_Object *obj, Eina_Bool pulse) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_progressbar_pulse_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_progressbar_pulse(Evas_Object *obj, Eina_Bool state) EINA_ARG_NONNULL(1); + EAPI void elm_progressbar_value_set(Evas_Object *obj, double val) EINA_ARG_NONNULL(1); + EAPI double elm_progressbar_value_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_progressbar_label_set(Evas_Object *obj, const char *label) EINA_ARG_NONNULL(1); + EAPI const char *elm_progressbar_label_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_progressbar_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_progressbar_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_progressbar_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_progressbar_span_size_set(Evas_Object *obj, Evas_Coord size) EINA_ARG_NONNULL(1); + EAPI Evas_Coord elm_progressbar_span_size_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_progressbar_unit_format_set(Evas_Object *obj, const char *format) EINA_ARG_NONNULL(1); + EAPI const char *elm_progressbar_unit_format_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_progressbar_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_progressbar_horizontal_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_progressbar_inverted_set(Evas_Object *obj, Eina_Bool inverted) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_progressbar_inverted_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + */ + /* available item styles: + * default + * wheel (simple style, no text, no progression, only pulse is available) + */ + + /* separator */ + EAPI Evas_Object *elm_separator_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_separator_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_separator_horizontal_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + */ + + /* spinner */ + EAPI Evas_Object *elm_spinner_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_spinner_label_format_set(Evas_Object *obj, const char *fmt) EINA_ARG_NONNULL(1); + EAPI const char *elm_spinner_label_format_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_spinner_min_max_set(Evas_Object *obj, double min, double max) EINA_ARG_NONNULL(1); + EAPI void elm_spinner_min_max_get(const Evas_Object *obj, double *min, double *max) EINA_ARG_NONNULL(1); + EAPI void elm_spinner_step_set(Evas_Object *obj, double step) EINA_ARG_NONNULL(1); + EAPI double elm_spinner_step_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_spinner_value_set(Evas_Object *obj, double val) EINA_ARG_NONNULL(1); + EAPI double elm_spinner_value_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_spinner_wrap_set(Evas_Object *obj, Eina_Bool wrap) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_spinner_wrap_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_spinner_editable_set(Evas_Object *obj, Eina_Bool editable) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_spinner_editable_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_spinner_special_value_add(Evas_Object *obj, double value, const char *label) EINA_ARG_NONNULL(1); + EAPI void elm_spinner_interval_set(Evas_Object *obj, double interval) EINA_ARG_NONNULL(1); + EAPI double elm_spinner_interval_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "changed" - when the spinner value changes + * "delay,changed" - when the spinner value changed, but a small time after a change (use this if you only want to respond to a change once the spinner is held still for a short while). + */ + /* available item styles: + * default + * vertical (two up/down buttons at the right side and text left aligned) + */ + + /* index */ + typedef struct _Elm_Index_Item Elm_Index_Item; /**< Item of Elm_Index. Sub-type of Elm_Widget_Item */ + + EAPI Evas_Object *elm_index_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_index_active_set(Evas_Object *obj, Eina_Bool active) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_level_set(Evas_Object *obj, int level) EINA_ARG_NONNULL(1); + EAPI int elm_index_item_level_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void *elm_index_item_selected_get(const Evas_Object *obj, int level) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_append(Evas_Object *obj, const char *letter, const void *item) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_prepend(Evas_Object *obj, const char *letter, const void *item) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_append_relative(Evas_Object *obj, const char *letter, const void *item, const void *relative) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_prepend_relative(Evas_Object *obj, const char *letter, const void *item, const void *relative) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_sorted_insert(Evas_Object *obj, const char *letter, const void *item, Eina_Compare_Cb cmp_func, Eina_Compare_Cb cmp_data_func) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_del(Evas_Object *obj, const void *item) EINA_ARG_NONNULL(1); + EAPI Elm_Index_Item *elm_index_item_find(Evas_Object *obj, const void *item) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_go(Evas_Object *obj, int level) EINA_ARG_NONNULL(1); + EAPI void *elm_index_item_data_get(const Elm_Index_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_data_set(Elm_Index_Item *it, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_index_item_del_cb_set(Elm_Index_Item *it, Evas_Smart_Cb func) EINA_ARG_NONNULL(1); + EAPI const char *elm_index_item_letter_get(const Elm_Index_Item *item) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "changed" - when the selected index item changes + * "delay,changed" - when the selected index item changes, but after some small idle period + * "selected" - when the user releases a finger and selects an item + * "level,up" - when the user moves a finger from the first level to the second level + * "level,down" - when the user moves a finger from the second level to the first level + */ + + /* photocam */ + typedef enum _Elm_Photocam_Zoom_Mode + { + ELM_PHOTOCAM_ZOOM_MODE_MANUAL = 0, + ELM_PHOTOCAM_ZOOM_MODE_AUTO_FIT, + ELM_PHOTOCAM_ZOOM_MODE_AUTO_FILL, + ELM_PHOTOCAM_ZOOM_MODE_LAST + } Elm_Photocam_Zoom_Mode; + + EAPI Evas_Object *elm_photocam_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Evas_Load_Error elm_photocam_file_set(Evas_Object *obj, const char *file) EINA_ARG_NONNULL(1); + EAPI const char *elm_photocam_file_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_photocam_zoom_set(Evas_Object *obj, double zoom) EINA_ARG_NONNULL(1); + EAPI double elm_photocam_zoom_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_photocam_zoom_mode_set(Evas_Object *obj, Elm_Photocam_Zoom_Mode mode) EINA_ARG_NONNULL(1); + EAPI Elm_Photocam_Zoom_Mode elm_photocam_zoom_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_photocam_image_size_get(const Evas_Object *obj, int *w, int *h) EINA_ARG_NONNULL(1); + EAPI void elm_photocam_region_get(const Evas_Object *obj, int *x, int *y, int *w, int *h) EINA_ARG_NONNULL(1); + EAPI void elm_photocam_image_region_show(Evas_Object *obj, int x, int y, int w, int h) EINA_ARG_NONNULL(1); + EAPI void elm_photocam_image_region_bring_in(Evas_Object *obj, int x, int y, int w, int h) EINA_ARG_NONNULL(1); + EAPI void elm_photocam_paused_set(Evas_Object *obj, Eina_Bool paused) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_photocam_paused_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_photocam_internal_image_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_photocam_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_photocam_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "clicked" - when image clicked + * "press" - when mouse/finger held down initially on image + * "longpressed" - when mouse/finger held for long time on image + * "clicked,double" - when mouse/finger double-clicked + * "load" - when photo load begins + * "loaded" - when photo load done + * "load,details" - when detailed image load begins + * "loaded,details" - when detailed image load done + * "zoom,start" - when zooming started + * "zoom,stop" - when zooming stopped + * "zoom,change" - when auto zoom mode changed zoom level + * "scroll - the content has been scrolled (moved) + * "scroll,anim,start" - scrolling animation has started + * "scroll,anim,stop" - scrolling animation has stopped + * "scroll,drag,start" - dragging the contents around has started + * "scroll,drag,stop" - dragging the contents around has stopped + */ + + /* map */ + typedef enum _Elm_Map_Zoom_Mode + { + ELM_MAP_ZOOM_MODE_MANUAL, + ELM_MAP_ZOOM_MODE_AUTO_FIT, + ELM_MAP_ZOOM_MODE_AUTO_FILL, + ELM_MAP_ZOOM_MODE_LAST + } Elm_Map_Zoom_Mode; + + typedef enum _Elm_Map_Sources + { + ELM_MAP_SOURCE_MAPNIK, + ELM_MAP_SOURCE_OSMARENDER, + ELM_MAP_SOURCE_CYCLEMAP, + ELM_MAP_SOURCE_MAPLINT, + ELM_MAP_SOURCE_CUSTOM_1, + ELM_MAP_SOURCE_CUSTOM_2, + ELM_MAP_SOURCE_CUSTOM_3, + ELM_MAP_SOURCE_CUSTOM_4, + ELM_MAP_SOURCE_CUSTOM_5, + ELM_MAP_SOURCE_CUSTOM_6, + ELM_MAP_SOURCE_MODULE, + ELM_MAP_SOURCE_LAST + } Elm_Map_Sources; + + typedef struct _Elm_Map_Marker Elm_Map_Marker; + typedef struct _Elm_Map_Marker_Class Elm_Map_Marker_Class; + typedef struct _Elm_Map_Group_Class Elm_Map_Group_Class; + typedef Evas_Object *(*ElmMapMarkerGetFunc) (Evas_Object *obj, Elm_Map_Marker *marker, void *data); + typedef void (*ElmMapMarkerDelFunc) (Evas_Object *obj, Elm_Map_Marker *marker, void *data, Evas_Object *o); + typedef Evas_Object *(*ElmMapMarkerIconGetFunc) (Evas_Object *obj, Elm_Map_Marker *marker, void *data); + typedef Evas_Object *(*ElmMapGroupIconGetFunc) (Evas_Object *obj, void *data); + typedef char *(*ElmMapSourceURLFunc) (Evas_Object *obj, int x, int y, int zoom); + + EAPI Evas_Object *elm_map_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_map_zoom_set(Evas_Object *obj, int zoom) EINA_ARG_NONNULL(1); + EAPI double elm_map_zoom_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_map_zoom_mode_set(Evas_Object *obj, Elm_Map_Zoom_Mode mode) EINA_ARG_NONNULL(1); + EAPI Elm_Map_Zoom_Mode elm_map_zoom_mode_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_map_geo_region_get(const Evas_Object *obj, double *lon, double *lat) EINA_ARG_NONNULL(1); + EAPI void elm_map_geo_region_bring_in(Evas_Object *obj, double lon, double lat) EINA_ARG_NONNULL(1); + EAPI void elm_map_geo_region_show(Evas_Object *obj, double lon, double lat) EINA_ARG_NONNULL(1); + EAPI void elm_map_paused_set(Evas_Object *obj, Eina_Bool paused) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_map_paused_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_map_paused_markers_set(Evas_Object *obj, Eina_Bool paused) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_map_paused_markers_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_map_utils_downloading_status_get(const Evas_Object *obj, int *try_num, int *finish_num) EINA_ARG_NONNULL(1, 2, 3); + EAPI void elm_map_utils_convert_coord_into_geo(const Evas_Object *obj, int x, int y, int size, double *lon, double *lat); + EAPI void elm_map_utils_convert_geo_into_coord(const Evas_Object *obj, double lon, double lat, int size, int *x, int *y); + EAPI Elm_Map_Marker *elm_map_marker_add(Evas_Object *obj, double lon, double lat, Elm_Map_Marker_Class *clas, Elm_Map_Group_Class *clas_group, void *data) EINA_ARG_NONNULL(1, 4, 5); + EAPI void elm_map_max_marker_per_group_set(Evas_Object *obj, int max) EINA_ARG_NONNULL(1); + EAPI void elm_map_marker_remove(Elm_Map_Marker *marker) EINA_ARG_NONNULL(1); + EAPI void elm_map_marker_bring_in(Elm_Map_Marker *marker) EINA_ARG_NONNULL(1); + EAPI void elm_map_marker_show(Elm_Map_Marker *marker) EINA_ARG_NONNULL(1); + EAPI void elm_map_markers_list_show(Eina_List *markers) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_map_marker_object_get(const Elm_Map_Marker *marker) EINA_ARG_NONNULL(1); + EAPI void elm_map_marker_update(Elm_Map_Marker *marker) EINA_ARG_NONNULL(1); + EAPI void elm_map_bubbles_close(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Map_Group_Class *elm_map_group_class_new(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_map_group_class_style_set(Elm_Map_Group_Class *clas, const char *style) EINA_ARG_NONNULL(1); + EAPI void elm_map_group_class_icon_cb_set(Elm_Map_Group_Class *clas, ElmMapGroupIconGetFunc icon_get) EINA_ARG_NONNULL(1); + EAPI void elm_map_group_class_data_set(Elm_Map_Group_Class *clas, void *data) EINA_ARG_NONNULL(1); + EAPI void elm_map_group_class_zoom_displayed_set(Elm_Map_Group_Class *clas, int zoom) EINA_ARG_NONNULL(1); + EAPI void elm_map_group_class_zoom_grouped_set(Elm_Map_Group_Class *clas, int zoom) EINA_ARG_NONNULL(1); + EAPI void elm_map_group_class_hide_set(Evas_Object *obj, Elm_Map_Group_Class *clas, Eina_Bool hide) EINA_ARG_NONNULL(1, 2); + EAPI Elm_Map_Marker_Class *elm_map_marker_class_new(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_map_marker_class_style_set(Elm_Map_Marker_Class *clas, const char *style) EINA_ARG_NONNULL(1); + EAPI void elm_map_marker_class_icon_cb_set(Elm_Map_Marker_Class *clas, ElmMapMarkerIconGetFunc icon_get) EINA_ARG_NONNULL(1); + EAPI void elm_map_marker_class_get_cb_set(Elm_Map_Marker_Class *clas, ElmMapMarkerGetFunc get) EINA_ARG_NONNULL(1); + EAPI void elm_map_marker_class_del_cb_set(Elm_Map_Marker_Class *clas, ElmMapMarkerDelFunc del) EINA_ARG_NONNULL(1); + EAPI void elm_map_source_set(Evas_Object *obj, Elm_Map_Sources source) EINA_ARG_NONNULL(1); + EAPI Elm_Map_Sources elm_map_source_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_map_source_custom_api_set(Elm_Map_Sources source, const char *label, int zoom_min, int zoom_max, ElmMapSourceURLFunc url_cb) EINA_ARG_NONNULL(2, 5); + EAPI int elm_map_source_zoom_min_get(Elm_Map_Sources source); + EAPI int elm_map_source_zoom_max_get(Elm_Map_Sources source); + EAPI const char *elm_map_source_name_get(Elm_Map_Sources source); + /* smart callbacks called: + * "clicked" - when image clicked + * "press" - when mouse/finger held down initially on image + * "longpressed" - when mouse/finger held for long time on image + * "clicked,double" - when mouse/finger double-clicked + * "load,details" - when detailed image load begins + * "loaded,details" - when detailed image load done + * "zoom,start" - when zooming started + * "zoom,stop" - when zooming stopped + * "zoom,change" - when auto zoom mode changed zoom level + * "scroll - the content has been scrolled (moved) + * "scroll,anim,start" - scrolling animation has started + * "scroll,anim,stop" - scrolling animation has stopped + * "scroll,drag,start" - dragging the contents around has started + * "scroll,drag,stop" - dragging the contents around has stopped + */ + + /* panel */ + typedef enum _Elm_Panel_Orient + { + ELM_PANEL_ORIENT_TOP, + ELM_PANEL_ORIENT_BOTTOM, + ELM_PANEL_ORIENT_LEFT, + ELM_PANEL_ORIENT_RIGHT, + } Elm_Panel_Orient; + + EAPI Evas_Object *elm_panel_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_panel_orient_set(Evas_Object *obj, Elm_Panel_Orient orient) EINA_ARG_NONNULL(1); + EAPI Elm_Panel_Orient elm_panel_orient_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_panel_content_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_panel_content_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_panel_content_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_panel_hidden_set(Evas_Object *obj, Eina_Bool hidden) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_panel_hidden_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_panel_toggle(Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* panes */ + /** + * TODO + * + * Update the minimun height of the bar in the theme. No minimun should be set in the vertical theme + * Add events (move, start ...) + */ + EAPI Evas_Object *elm_panes_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_panes_content_left_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI void elm_panes_content_right_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_panes_content_left_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_panes_content_right_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_panes_content_left_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_panes_content_right_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI double elm_panes_content_left_size_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_panes_content_left_size_set(Evas_Object *obj, double size) EINA_ARG_NONNULL(1); + EAPI void elm_panes_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_panes_horizontal_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* flip */ + typedef enum _Elm_Flip_Mode + { + ELM_FLIP_ROTATE_Y_CENTER_AXIS, + ELM_FLIP_ROTATE_X_CENTER_AXIS, + ELM_FLIP_ROTATE_XZ_CENTER_AXIS, + ELM_FLIP_ROTATE_YZ_CENTER_AXIS, + ELM_FLIP_CUBE_LEFT, + ELM_FLIP_CUBE_RIGHT, + ELM_FLIP_CUBE_UP, + ELM_FLIP_CUBE_DOWN + } Elm_Flip_Mode; + + EAPI Evas_Object *elm_flip_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_flip_content_front_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI void elm_flip_content_back_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_flip_content_front_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_flip_content_back_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_flip_content_front_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_flip_content_back_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_flip_front_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_flip_perspective_set(Evas_Object *obj, Evas_Coord foc, Evas_Coord x, Evas_Coord y) EINA_ARG_NONNULL(1); + EAPI void elm_flip_go(Evas_Object *obj, Elm_Flip_Mode mode) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "animate,done" - when a flip animation is finished + */ + + /* scrolledentry */ + EAPI Evas_Object *elm_scrolled_entry_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_single_line_set(Evas_Object *obj, Eina_Bool single_line) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_single_line_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_password_set(Evas_Object *obj, Eina_Bool password) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_password_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_entry_set(Evas_Object *obj, const char *entry) EINA_ARG_NONNULL(1); + EAPI const char *elm_scrolled_entry_entry_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_is_empty(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const char *elm_scrolled_entry_selection_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_entry_insert(Evas_Object *obj, const char *entry) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_line_wrap_set(Evas_Object *obj, Eina_Bool wrap) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_line_char_wrap_set(Evas_Object *obj, Eina_Bool wrap) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_editable_set(Evas_Object *obj, Eina_Bool editable) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_editable_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_select_none(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_select_all(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_cursor_next(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_cursor_prev(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_cursor_up(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_cursor_down(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_cursor_begin_set(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_cursor_end_set(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_cursor_line_begin_set(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_cursor_line_end_set(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_cursor_selection_begin(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_cursor_selection_end(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_cursor_is_format_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_cursor_is_visible_format_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const char *elm_scrolled_entry_cursor_content_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_selection_cut(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_selection_copy(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_selection_paste(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_context_menu_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_context_menu_item_add(Evas_Object *obj, const char *label, const char *icon_file, Elm_Icon_Type icon_type, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_context_menu_disabled_set(Evas_Object *obj, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_context_menu_disabled_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_scrollbar_policy_set(Evas_Object *obj, Elm_Scroller_Policy h, Elm_Scroller_Policy v) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_icon_set(Evas_Object *obj, Evas_Object *icon) EINA_ARG_NONNULL(1, 2); + EAPI Evas_Object *elm_scrolled_entry_icon_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_scrolled_entry_icon_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_icon_visible_set(Evas_Object *obj, Eina_Bool setting) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_end_set(Evas_Object *obj, Evas_Object *end) EINA_ARG_NONNULL(1, 2); + EAPI Evas_Object *elm_scrolled_entry_end_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_scrolled_entry_end_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_end_visible_set(Evas_Object *obj, Eina_Bool setting) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_item_provider_append(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_scrolled_entry_item_provider_prepend(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_scrolled_entry_item_provider_remove(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_scrolled_entry_text_filter_append(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_scrolled_entry_text_filter_prepend(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_scrolled_entry_text_filter_remove(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_scrolled_entry_file_set(Evas_Object *obj, const char *file, Elm_Text_Format format) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_file_get(const Evas_Object *obj, const char **file, Elm_Text_Format *format) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_file_save(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_scrolled_entry_autosave_set(Evas_Object *obj, Eina_Bool autosave) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_scrolled_entry_autosave_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* conformant */ + EAPI Evas_Object *elm_conformant_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_conformant_content_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_conformant_content_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_conformant_content_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* mapbuf */ + EAPI Evas_Object *elm_mapbuf_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_mapbuf_content_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_mapbuf_content_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_mapbuf_content_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_mapbuf_enabled_set(Evas_Object *obj, Eina_Bool enabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_mapbuf_enabled_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_mapbuf_smooth_set(Evas_Object *obj, Eina_Bool smooth) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_mapbuf_smooth_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_mapbuf_alpha_set(Evas_Object *obj, Eina_Bool alpha) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_mapbuf_alpha_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + + /* flipselector */ + typedef struct _Elm_Flipselector_Item Elm_Flipselector_Item; + + EAPI Evas_Object *elm_flipselector_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_flipselector_flip_next(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_flipselector_flip_prev(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Flipselector_Item *elm_flipselector_item_append(Evas_Object *obj, const char *label, void (*func)(void *data, Evas_Object *obj, void *event_info), void *data) EINA_ARG_NONNULL(1); + EAPI Elm_Flipselector_Item *elm_flipselector_item_prepend(Evas_Object *obj, const char *label, void (*func)(void *data, Evas_Object *obj, void *event_info), void *data) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_flipselector_items_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Flipselector_Item *elm_flipselector_first_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Flipselector_Item *elm_flipselector_last_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Flipselector_Item *elm_flipselector_selected_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_flipselector_item_selected_set(Elm_Flipselector_Item *item, Eina_Bool selected) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_flipselector_item_selected_get(const Elm_Flipselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_flipselector_item_del(Elm_Flipselector_Item *item) EINA_ARG_NONNULL(1); + EAPI const char *elm_flipselector_item_label_get(const Elm_Flipselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_flipselector_item_label_set(Elm_Flipselector_Item *item, const char *label) EINA_ARG_NONNULL(1); + EAPI Elm_Flipselector_Item *elm_flipselector_item_prev_get(Elm_Flipselector_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Flipselector_Item *elm_flipselector_item_next_get(Elm_Flipselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_flipselector_interval_set(Evas_Object *obj, double interval) EINA_ARG_NONNULL(1); + EAPI double elm_flipselector_interval_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "selected" - when flipselector selected item is changed + * "overflowed" - when flipselector item is changed to first item + * from last item + * "underflowed" - when flipselector item is changed to last item + * from first item. + */ + /* available styles: + * default + */ + + /* animator */ + typedef enum + { + ELM_ANIMATOR_CURVE_LINEAR, + ELM_ANIMATOR_CURVE_IN_OUT, + ELM_ANIMATOR_CURVE_IN, + ELM_ANIMATOR_CURVE_OUT + } Elm_Animator_Curve_Style; + typedef struct _Elm_Animator Elm_Animator; + /** + * Called back per loop of an elementary animators cycle + * @param data user-data given to elm_animator_operation_callback_set() + * @param animator the animator being run + * @param double the position in the animation + */ + typedef void (*Elm_Animator_Operation_Cb) (void *data, Elm_Animator *animator, double frame); + /** + * Called back when an elementary animator finishes + * @param data user-data given to elm_animator_completion_callback_set() + */ + typedef void (*Elm_Animator_Completion_Cb) (void *data); + + EAPI Elm_Animator* elm_animator_add(Evas_Object *parent); + EAPI void elm_animator_del(Elm_Animator *animator) EINA_ARG_NONNULL(1); + EAPI void elm_animator_duration_set(Elm_Animator *animator, double duration) EINA_ARG_NONNULL(1); + EAPI void elm_animator_operation_callback_set(Elm_Animator *animator, Elm_Animator_Operation_Cb func, void *data) EINA_ARG_NONNULL(1); + EAPI void elm_animator_completion_callback_set(Elm_Animator *animator, Elm_Animator_Completion_Cb func, void *data) EINA_ARG_NONNULL(1); + EAPI void elm_animator_stop(Elm_Animator *animator) EINA_ARG_NONNULL(1); + EAPI void elm_animator_repeat_set(Elm_Animator *animator, unsigned int repeat_cnt) EINA_ARG_NONNULL(1); + EAPI void elm_animator_animate(Elm_Animator *animator) EINA_ARG_NONNULL(1); + EAPI void elm_animator_curve_style_set(Elm_Animator *animator, Elm_Animator_Curve_Style cs) EINA_ARG_NONNULL(1); + EAPI Elm_Animator_Curve_Style elm_animator_curve_style_get(const Elm_Animator *animator); EINA_ARG_NONNULL(1); + EAPI void elm_animator_auto_reverse_set(Elm_Animator *animator, Eina_Bool reverse) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_animator_auto_reverse_get(const Elm_Animator *animator) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_animator_operating_get(const Elm_Animator *animator) EINA_ARG_NONNULL(1); + EAPI unsigned int elm_animator_repeat_get(const Elm_Animator *animator) EINA_ARG_NONNULL(1); + EAPI void elm_animator_pause(Elm_Animator *animator) EINA_ARG_NONNULL(1); + EAPI void elm_animator_resume(Elm_Animator *animator) EINA_ARG_NONNULL(1); + + /* calendar */ + typedef enum + { + ELM_CALENDAR_UNIQUE, + ELM_CALENDAR_DAILY, + ELM_CALENDAR_WEEKLY, + ELM_CALENDAR_MONTHLY, + ELM_CALENDAR_ANNUALLY + } Elm_Calendar_Mark_Repeat; + typedef struct _Elm_Calendar_Mark Elm_Calendar_Mark; + + EAPI Evas_Object *elm_calendar_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI const char **elm_calendar_weekdays_names_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_calendar_weekdays_names_set(Evas_Object *obj, const char *weekdays[]) EINA_ARG_NONNULL(1, 2); + EAPI double elm_calendar_interval_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_calendar_interval_set(Evas_Object *obj, double interval) EINA_ARG_NONNULL(1); + EAPI void elm_calendar_min_max_year_get(const Evas_Object *obj, int *min, int *max) EINA_ARG_NONNULL(1); + EAPI void elm_calendar_min_max_year_set(Evas_Object *obj, int min, int max) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_calendar_day_selection_enabled_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_calendar_day_selection_enabled_set(Evas_Object *obj, Eina_Bool enabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_calendar_selected_time_get(const Evas_Object *obj, struct tm *selected_time) EINA_ARG_NONNULL(1, 2); + EAPI void elm_calendar_selected_time_set(Evas_Object *obj, struct tm *selected_time) EINA_ARG_NONNULL(1); + EAPI void elm_calendar_format_function_set(Evas_Object *obj, char * (*format_function) (struct tm *stime)) EINA_ARG_NONNULL(1); + EAPI Elm_Calendar_Mark *elm_calendar_mark_add(Evas_Object *obj, const char *mark_type, struct tm *mark_time, Elm_Calendar_Mark_Repeat repeat) EINA_ARG_NONNULL(1); + EAPI void elm_calendar_mark_del(Elm_Calendar_Mark *mark) EINA_ARG_NONNULL(1); + EAPI void elm_calendar_marks_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_calendar_marks_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_calendar_marks_draw(Evas_Object *obj) EINA_ARG_NONNULL(1); + EINA_DEPRECATED EAPI void elm_calendar_text_saturday_color_set(Evas_Object *obj, int pos) EINA_ARG_NONNULL(1); + EINA_DEPRECATED EAPI void elm_calendar_text_sunday_color_set(Evas_Object *obj, int pos) EINA_ARG_NONNULL(1); + EINA_DEPRECATED EAPI void elm_calendar_text_weekday_color_set(Evas_Object *obj, int pos) EINA_ARG_NONNULL(1); + + /* smart callbacks called: + * changed - emitted when the user select a day or change the displayed + * month. + */ + + /* diskselector */ + typedef struct _Elm_Diskselector_Item Elm_Diskselector_Item; + + EAPI Evas_Object *elm_diskselector_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_diskselector_round_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_round_set(Evas_Object *obj, Eina_Bool round) EINA_ARG_NONNULL(1); + EAPI int elm_diskselector_side_label_lenght_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_side_label_lenght_set(Evas_Object *obj, int len) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_scroller_policy_get(const Evas_Object *obj, Elm_Scroller_Policy *policy_h, Elm_Scroller_Policy *policy_v) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_scroller_policy_set(Evas_Object *obj, Elm_Scroller_Policy policy_h, Elm_Scroller_Policy policy_v) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI const Eina_List *elm_diskselector_items_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Diskselector_Item *elm_diskselector_item_append(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_del(Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_del_cb_set(Elm_Diskselector_Item *item, Evas_Smart_Cb func) EINA_ARG_NONNULL(1); + EAPI void *elm_diskselector_item_data_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_diskselector_item_icon_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_icon_set(Elm_Diskselector_Item *item, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI const char *elm_diskselector_item_label_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_label_set(Elm_Diskselector_Item *item, const char *label) EINA_ARG_NONNULL(1); + EAPI Elm_Diskselector_Item *elm_diskselector_selected_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_selected_set(Elm_Diskselector_Item *item, Eina_Bool selected) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_diskselector_item_selected_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Diskselector_Item *elm_diskselector_first_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Diskselector_Item *elm_diskselector_last_item_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI Elm_Diskselector_Item *elm_diskselector_item_prev_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI Elm_Diskselector_Item *elm_diskselector_item_next_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_tooltip_text_set(Elm_Diskselector_Item *item, const char *text) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_tooltip_content_cb_set(Elm_Diskselector_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_tooltip_unset(Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_tooltip_style_set(Elm_Diskselector_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_diskselector_item_tooltip_style_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_cursor_set(Elm_Diskselector_Item *item, const char *cursor) EINA_ARG_NONNULL(1); + EAPI const char *elm_diskselector_item_cursor_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_cursor_unset(Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_cursor_style_set(Elm_Diskselector_Item *item, const char *style) EINA_ARG_NONNULL(1); + EAPI const char *elm_diskselector_item_cursor_style_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_diskselector_item_cursor_engine_only_set(Elm_Diskselector_Item *item, Eina_Bool engine_only) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_diskselector_item_cursor_engine_only_get(const Elm_Diskselector_Item *item) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "selected" - when item is selected (scroller stops) + */ + + /* colorselector */ + EAPI Evas_Object *elm_colorselector_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI void elm_colorselector_color_set(Evas_Object *obj, int r, int g , int b, int a) EINA_ARG_NONNULL(1); + EAPI void elm_colorselector_color_get(const Evas_Object *obj, int *r, int *g , int *b, int *a) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "changed" - when the color value changes + */ + + /* Contextual Popup */ + typedef struct _Elm_Ctxpopup_Item Elm_Ctxpopup_Item; + + typedef enum _Elm_Ctxpopup_Direction + { + ELM_CTXPOPUP_DIRECTION_DOWN, + ELM_CTXPOPUP_DIRECTION_RIGHT, + ELM_CTXPOPUP_DIRECTION_LEFT, + ELM_CTXPOPUP_DIRECTION_UP, + } Elm_Ctxpopup_Direction; + + EAPI Evas_Object *elm_ctxpopup_add(Evas_Object *parent) EINA_ARG_NONNULL(1); + EAPI Evas_Object *elm_ctxpopup_item_icon_get(const Elm_Ctxpopup_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_item_icon_set(Elm_Ctxpopup_Item *item, Evas_Object *icon) EINA_ARG_NONNULL(1); + EAPI const char *elm_ctxpopup_item_label_get(const Elm_Ctxpopup_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_item_label_set(Elm_Ctxpopup_Item *item, const char *label) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_hover_parent_set(Evas_Object *obj, Evas_Object *parent) EINA_ARG_NONNULL(1, 2); + EAPI Evas_Object *elm_ctxpopup_hover_parent_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_clear(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_ctxpopup_horizontal_get(const Evas_Object *obj) EINA_ARG_NONNULL(1); + Elm_Ctxpopup_Item *elm_ctxpopup_item_append(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Smart_Cb func, const void *data) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_item_del(Elm_Ctxpopup_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_item_disabled_set(Elm_Ctxpopup_Item *item, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_ctxpopup_item_disabled_get(const Elm_Ctxpopup_Item *item) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_content_set(Evas_Object *obj, Evas_Object *content) EINA_ARG_NONNULL(1, 2); + EAPI Evas_Object *elm_ctxpopup_content_unset(Evas_Object *obj) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_direction_priority_set(Evas_Object *obj, Elm_Ctxpopup_Direction first, Elm_Ctxpopup_Direction second, Elm_Ctxpopup_Direction third, Elm_Ctxpopup_Direction fourth) EINA_ARG_NONNULL(1); + EAPI void elm_ctxpopup_direction_priority_get(Evas_Object *obj, Elm_Ctxpopup_Direction *first, Elm_Ctxpopup_Direction *second, Elm_Ctxpopup_Direction *third, Elm_Ctxpopup_Direction *fourth) EINA_ARG_NONNULL(1); + /* smart callbacks called: + * "dismissed" - the ctxpopup was dismissed + */ + + /* transit */ + typedef enum + { + ELM_TRANSIT_TWEEN_MODE_LINEAR, + ELM_TRANSIT_TWEEN_MODE_SINUSOIDAL, + ELM_TRANSIT_TWEEN_MODE_DECELERATE, + ELM_TRANSIT_TWEEN_MODE_ACCELERATE + } Elm_Transit_Tween_Mode; + typedef enum + { + ELM_TRANSIT_EFFECT_FLIP_AXIS_X, + ELM_TRANSIT_EFFECT_FLIP_AXIS_Y + } Elm_Transit_Effect_Flip_Axis; + typedef enum + { + ELM_TRANSIT_EFFECT_WIPE_DIR_LEFT, + ELM_TRANSIT_EFFECT_WIPE_DIR_RIGHT, + ELM_TRANSIT_EFFECT_WIPE_DIR_UP, + ELM_TRANSIT_EFFECT_WIPE_DIR_DOWN + } Elm_Transit_Effect_Wipe_Dir; + typedef enum + { + ELM_TRANSIT_EFFECT_WIPE_TYPE_HIDE, + ELM_TRANSIT_EFFECT_WIPE_TYPE_SHOW + } Elm_Transit_Effect_Wipe_Type; + + typedef struct _Elm_Transit Elm_Transit; + + EAPI Elm_Transit *elm_transit_add(void); + EAPI void elm_transit_del(Elm_Transit *transit) EINA_ARG_NONNULL(1); + EAPI void elm_transit_effect_add(Elm_Transit *transit, void (*cb)(void *data, Elm_Transit *transit, double progress), void *data, void (*data_free_cb)(void *data, Elm_Transit *transit)) EINA_ARG_NONNULL(1, 2); + EAPI void elm_transit_effect_del(Elm_Transit *transit, void (*cb)(void *data, Elm_Transit *transit, double progress), void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_transit_object_add(Elm_Transit *transit, Evas_Object *obj) EINA_ARG_NONNULL(1, 2); + EAPI void elm_transit_object_remove(Elm_Transit *transit, Evas_Object *obj) EINA_ARG_NONNULL(1, 2); + EAPI const Eina_List *elm_transit_objects_get(const Elm_Transit *transit) EINA_ARG_NONNULL(1); + EINA_DEPRECATED EAPI void elm_transit_event_block_set(Elm_Transit *transit, Eina_Bool disabled) EINA_ARG_NONNULL(1); + EINA_DEPRECATED EAPI Eina_Bool elm_transit_event_block_get(const Elm_Transit *transit) EINA_ARG_NONNULL(1); + EAPI void elm_transit_event_enabled_set(Elm_Transit *transit, Eina_Bool enabled) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_transit_event_enabled_get(const Elm_Transit *transit) EINA_ARG_NONNULL(1); + EAPI void elm_transit_del_cb_set(Elm_Transit *transit, void (*cb)(void *data, Elm_Transit* transit), void *data) EINA_ARG_NONNULL(1); + EAPI void elm_transit_auto_reverse_set(Elm_Transit *transit, Eina_Bool reverse) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_transit_auto_reverse_get(Elm_Transit *transit) EINA_ARG_NONNULL(1) EINA_ARG_NONNULL(1); + EAPI void elm_transit_repeat_times_set(Elm_Transit *transit, int repeat) EINA_ARG_NONNULL(1); + EAPI int elm_transit_repeat_times_get(Elm_Transit *transit) EINA_ARG_NONNULL(1); + EAPI void elm_transit_tween_mode_set(Elm_Transit *transit, Elm_Transit_Tween_Mode tween_mode) EINA_ARG_NONNULL(1); + EAPI Elm_Transit_Tween_Mode elm_transit_tween_mode_get(const Elm_Transit *transit) EINA_ARG_NONNULL(1) EINA_ARG_NONNULL(1); + EAPI void elm_transit_duration_set(Elm_Transit *transit, double duration) EINA_ARG_NONNULL(1); + EAPI double elm_transit_duration_get(const Elm_Transit *transit) EINA_ARG_NONNULL(1); + EAPI void elm_transit_go(Elm_Transit *transit) EINA_ARG_NONNULL(1); + EAPI void elm_transit_paused_set(Elm_Transit *transit, Eina_Bool paused) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_transit_paused_get(const Elm_Transit *transit) EINA_ARG_NONNULL(1); + EAPI double elm_transit_progress_value_get(const Elm_Transit *transit) EINA_ARG_NONNULL(1); + + EAPI void *elm_transit_effect_resizing_add(Elm_Transit* transit, Evas_Coord from_w, Evas_Coord from_h, Evas_Coord to_w, Evas_Coord to_h); + EAPI void *elm_transit_effect_translation_add(Elm_Transit* transit, Evas_Coord from_dx, Evas_Coord dy, Evas_Coord to_dx, Evas_Coord to_dy); + EAPI void *elm_transit_effect_zoom_add(Elm_Transit *transit, float from_rate, float to_rate); + EAPI void *elm_transit_effect_flip_add(Elm_Transit *transit, Elm_Transit_Effect_Flip_Axis axis, Eina_Bool cw); + EAPI void *elm_transit_effect_resizable_flip_add(Elm_Transit *transit, Elm_Transit_Effect_Flip_Axis axis, Eina_Bool cw); + EAPI void *elm_transit_effect_wipe_add(Elm_Transit *transit, Elm_Transit_Effect_Wipe_Type type, Elm_Transit_Effect_Wipe_Dir dir); + EAPI void *elm_transit_effect_color_add(Elm_Transit *transit, unsigned int from_r, unsigned int from_g, unsigned int from_b, unsigned int from_a, unsigned int to_r, unsigned int to_g, unsigned int to_b, unsigned int to_a); + EAPI void *elm_transit_effect_fade_add(Elm_Transit *transit); + EAPI void *elm_transit_effect_blend_add(Elm_Transit *transit); + EAPI void *elm_transit_effect_rotation_add(Elm_Transit *transit, float from_degree, float to_degree); + EAPI void *elm_transit_effect_image_animation_add(Elm_Transit *transit, Eina_List *images); + + typedef struct _Elm_Store Elm_Store; + typedef struct _Elm_Store_Filesystem Elm_Store_Filesystem; + typedef struct _Elm_Store_Item Elm_Store_Item; + typedef struct _Elm_Store_Item_Filesystem Elm_Store_Item_Filesystem; + typedef struct _Elm_Store_Item_Info Elm_Store_Item_Info; + typedef struct _Elm_Store_Item_Info_Filesystem Elm_Store_Item_Info_Filesystem; + typedef struct _Elm_Store_Item_Mapping Elm_Store_Item_Mapping; + typedef struct _Elm_Store_Item_Mapping_Empty Elm_Store_Item_Mapping_Empty; + typedef struct _Elm_Store_Item_Mapping_Icon Elm_Store_Item_Mapping_Icon; + typedef struct _Elm_Store_Item_Mapping_Photo Elm_Store_Item_Mapping_Photo; + typedef struct _Elm_Store_Item_Mapping_Custom Elm_Store_Item_Mapping_Custom; + + typedef Eina_Bool (*Elm_Store_Item_List_Cb) (void *data, Elm_Store_Item_Info *info); + typedef void (*Elm_Store_Item_Fetch_Cb) (void *data, Elm_Store_Item *sti); + typedef void (*Elm_Store_Item_Unfetch_Cb) (void *data, Elm_Store_Item *sti); + typedef void *(*Elm_Store_Item_Mapping_Cb) (void *data, Elm_Store_Item *sti, const char *part); + + typedef enum + { + ELM_STORE_ITEM_MAPPING_NONE = 0, + ELM_STORE_ITEM_MAPPING_LABEL, // const char * -> label + ELM_STORE_ITEM_MAPPING_STATE, // Eina_Bool -> state + ELM_STORE_ITEM_MAPPING_ICON, // char * -> icon path + ELM_STORE_ITEM_MAPPING_PHOTO, // char * -> photo path + ELM_STORE_ITEM_MAPPING_CUSTOM, // item->custom(it->data, it, part) -> void * (-> any) + // can add more here as needed by common apps + ELM_STORE_ITEM_MAPPING_LAST + } Elm_Store_Item_Mapping_Type; + + struct _Elm_Store_Item_Mapping_Icon + { + // FIXME: allow edje file icons + int w, h; + Elm_Icon_Lookup_Order lookup_order; + Eina_Bool standard_name : 1; + Eina_Bool no_scale : 1; + Eina_Bool smooth : 1; + Eina_Bool scale_up : 1; + Eina_Bool scale_down : 1; + }; + + struct _Elm_Store_Item_Mapping_Empty + { + Eina_Bool dummy; + }; + + struct _Elm_Store_Item_Mapping_Photo + { + int size; + }; + + struct _Elm_Store_Item_Mapping_Custom + { + Elm_Store_Item_Mapping_Cb func; + }; + + struct _Elm_Store_Item_Mapping + { + Elm_Store_Item_Mapping_Type type; + const char *part; + int offset; + union { + Elm_Store_Item_Mapping_Empty empty; + Elm_Store_Item_Mapping_Icon icon; + Elm_Store_Item_Mapping_Photo photo; + Elm_Store_Item_Mapping_Custom custom; + // add more types here + } details; + }; + + struct _Elm_Store_Item_Info + { + Elm_Genlist_Item_Class *item_class; + const Elm_Store_Item_Mapping *mapping; + void *data; + char *sort_id; + }; + + struct _Elm_Store_Item_Info_Filesystem + { + Elm_Store_Item_Info base; + char *path; + }; + +#define ELM_STORE_ITEM_MAPPING_END { ELM_STORE_ITEM_MAPPING_NONE, NULL, 0, { .empty = { EINA_TRUE } } } +#define ELM_STORE_ITEM_MAPPING_OFFSET(st, it) offsetof(st, it) + + EAPI void elm_store_free(Elm_Store *st); + + EAPI Elm_Store *elm_store_filesystem_new(void); + EAPI void elm_store_filesystem_directory_set(Elm_Store *st, const char *dir) EINA_ARG_NONNULL(1); + EAPI const char *elm_store_filesystem_directory_get(const Elm_Store *st) EINA_ARG_NONNULL(1); + EAPI const char *elm_store_item_filesystem_path_get(const Elm_Store_Item *sti) EINA_ARG_NONNULL(1); + + EAPI void elm_store_target_genlist_set(Elm_Store *st, Evas_Object *obj) EINA_ARG_NONNULL(1); + + EAPI void elm_store_cache_set(Elm_Store *st, int max) EINA_ARG_NONNULL(1); + EAPI int elm_store_cache_get(const Elm_Store *st) EINA_ARG_NONNULL(1); + EAPI void elm_store_list_func_set(Elm_Store *st, Elm_Store_Item_List_Cb func, const void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_store_fetch_func_set(Elm_Store *st, Elm_Store_Item_Fetch_Cb func, const void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_store_fetch_thread_set(Elm_Store *st, Eina_Bool use_thread) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_store_fetch_thread_get(const Elm_Store *st) EINA_ARG_NONNULL(1); + + EAPI void elm_store_unfetch_func_set(Elm_Store *st, Elm_Store_Item_Unfetch_Cb func, const void *data) EINA_ARG_NONNULL(1, 2); + EAPI void elm_store_sorted_set(Elm_Store *st, Eina_Bool sorted) EINA_ARG_NONNULL(1); + EAPI Eina_Bool elm_store_sorted_get(const Elm_Store *st) EINA_ARG_NONNULL(1); + EAPI void elm_store_item_data_set(Elm_Store_Item *sti, void *data) EINA_ARG_NONNULL(1); + EAPI void *elm_store_item_data_get(Elm_Store_Item *sti) EINA_ARG_NONNULL(1); + EAPI const Elm_Store *elm_store_item_store_get(const Elm_Store_Item *sti) EINA_ARG_NONNULL(1); + EAPI const Elm_Genlist_Item *elm_store_item_genlist_item_get(const Elm_Store_Item *sti) EINA_ARG_NONNULL(1); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/src/lib/Elementary_Cursor.h b/src/lib/Elementary_Cursor.h new file mode 100644 index 0000000..78a7c40 --- /dev/null +++ b/src/lib/Elementary_Cursor.h @@ -0,0 +1,88 @@ +#ifndef _ELM_CURSOR_H +#define _ELM_CURSOR_H + +/** + * @file + * @brief Defines the various cursor types for the X Windows system. + */ + +#define ELM_CURSOR_X "x" +#define ELM_CURSOR_ARROW "arrow" +#define ELM_CURSOR_BASED_ARROW_DOWN "based_arrow_down" +#define ELM_CURSOR_BASED_ARROW_UP "based_arrow_up" +#define ELM_CURSOR_BOAT "boat" +#define ELM_CURSOR_BOGOSITY "bogosity" +#define ELM_CURSOR_BOTTOM_LEFT_CORNER "bottom_left_corner" +#define ELM_CURSOR_BOTTOM_RIGHT_CORNER "bottom_right_corner" +#define ELM_CURSOR_BOTTOM_SIDE "bottom_side" +#define ELM_CURSOR_BOTTOM_TEE "bottom_tee" +#define ELM_CURSOR_BOX_SPIRAL "box_spiral" +#define ELM_CURSOR_CENTER_PTR "center_ptr" +#define ELM_CURSOR_CIRCLE "circle" +#define ELM_CURSOR_CLOCK "clock" +#define ELM_CURSOR_COFFEE_MUG "coffee_mug" +#define ELM_CURSOR_CROSS "cross" +#define ELM_CURSOR_CROSS_REVERSE "cross_reverse" +#define ELM_CURSOR_CROSSHAIR "crosshair" +#define ELM_CURSOR_DIAMOND_CROSS "diamond_cross" +#define ELM_CURSOR_DOT "dot" +#define ELM_CURSOR_DOT_BOX_MASK "dot_box_mask" +#define ELM_CURSOR_DOUBLE_ARROW "double_arrow" +#define ELM_CURSOR_DRAFT_LARGE "draft_large" +#define ELM_CURSOR_DRAFT_SMALL "draft_small" +#define ELM_CURSOR_DRAPED_BOX "draped_box" +#define ELM_CURSOR_EXCHANGE "exchange" +#define ELM_CURSOR_FLEUR "fleur" +#define ELM_CURSOR_GOBBLER "gobbler" +#define ELM_CURSOR_GUMBY "gumby" +#define ELM_CURSOR_HAND1 "hand1" +#define ELM_CURSOR_HAND2 "hand2" +#define ELM_CURSOR_HEART "heart" +#define ELM_CURSOR_ICON "icon" +#define ELM_CURSOR_IRON_CROSS "iron_cross" +#define ELM_CURSOR_LEFT_PTR "left_ptr" +#define ELM_CURSOR_LEFT_SIDE "left_side" +#define ELM_CURSOR_LEFT_TEE "left_tee" +#define ELM_CURSOR_LEFTBUTTON "leftbutton" +#define ELM_CURSOR_LL_ANGLE "ll_angle" +#define ELM_CURSOR_LR_ANGLE "lr_angle" +#define ELM_CURSOR_MAN "man" +#define ELM_CURSOR_MIDDLEBUTTON "middlebutton" +#define ELM_CURSOR_MOUSE "mouse" +#define ELM_CURSOR_PENCIL "pencil" +#define ELM_CURSOR_PIRATE "pirate" +#define ELM_CURSOR_PLUS "plus" +#define ELM_CURSOR_QUESTION_ARROW "question_arrow" +#define ELM_CURSOR_RIGHT_PTR "right_ptr" +#define ELM_CURSOR_RIGHT_SIDE "right_side" +#define ELM_CURSOR_RIGHT_TEE "right_tee" +#define ELM_CURSOR_RIGHTBUTTON "rightbutton" +#define ELM_CURSOR_RTL_LOGO "rtl_logo" +#define ELM_CURSOR_SAILBOAT "sailboat" +#define ELM_CURSOR_SB_DOWN_ARROW "sb_down_arrow" +#define ELM_CURSOR_SB_H_DOUBLE_ARROW "sb_h_double_arrow" +#define ELM_CURSOR_SB_LEFT_ARROW "sb_left_arrow" +#define ELM_CURSOR_SB_RIGHT_ARROW "sb_right_arrow" +#define ELM_CURSOR_SB_UP_ARROW "sb_up_arrow" +#define ELM_CURSOR_SB_V_DOUBLE_ARROW "sb_v_double_arrow" +#define ELM_CURSOR_SHUTTLE "shuttle" +#define ELM_CURSOR_SIZING "sizing" +#define ELM_CURSOR_SPIDER "spider" +#define ELM_CURSOR_SPRAYCAN "spraycan" +#define ELM_CURSOR_STAR "star" +#define ELM_CURSOR_TARGET "target" +#define ELM_CURSOR_TCROSS "tcross" +#define ELM_CURSOR_TOP_LEFT_ARROW "top_left_arrow" +#define ELM_CURSOR_TOP_LEFT_CORNER "top_left_corner" +#define ELM_CURSOR_TOP_RIGHT_CORNER "top_right_corner" +#define ELM_CURSOR_TOP_SIDE "top_side" +#define ELM_CURSOR_TOP_TEE "top_tee" +#define ELM_CURSOR_TREK "trek" +#define ELM_CURSOR_UL_ANGLE "ul_angle" +#define ELM_CURSOR_UMBRELLA "umbrella" +#define ELM_CURSOR_UR_ANGLE "ur_angle" +#define ELM_CURSOR_WATCH "watch" +#define ELM_CURSOR_XTERM "xterm" + +#endif // ifndef _ELM_CURSOR_H + diff --git a/src/lib/Makefile.am b/src/lib/Makefile.am new file mode 100644 index 0000000..ab9e24a --- /dev/null +++ b/src/lib/Makefile.am @@ -0,0 +1,137 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +AM_CPPFLAGS = \ +-DELM_INTERAL_API_MDFGELQ=1 \ +-I. \ +-I$(top_builddir) \ +-I$(top_srcdir) \ +-I$(top_srcdir)/src/lib \ +-I$(top_builddir)/src/lib \ +-DPACKAGE_DATA_DIR=\"$(datadir)/$(PACKAGE)\" \ +-DPACKAGE_LIB_DIR=\"$(libdir)\" \ +@ELEMENTARY_CFLAGS@ \ +@ELEMENTARY_X_CFLAGS@ \ +@ELEMENTARY_FB_CFLAGS@ \ +@ELEMENTARY_SDL_CFLAGS@ \ +@ELEMENTARY_WIN32_CFLAGS@ \ +@ELEMENTARY_WINCE_CFLAGS@ \ +@ELEMENTARY_EDBUS_CFLAGS@ \ +@ELEMENTARY_EFREET_CFLAGS@ \ +@ELEMENTARY_ETHUMB_CFLAGS@ \ +@EVIL_CFLAGS@ \ +@EFL_PTHREAD_CFLAGS@ + +if ELEMENTARY_WINDOWS_BUILD +AM_CPPFLAGS += -DELEMENTARY_BUILD +endif + +lib_LTLIBRARIES = libelementary.la + +includes_HEADERS = \ +Elementary.h \ +Elementary_Cursor.h \ +elm_widget.h +includesdir = $(includedir)/elementary-@VMAJ@ + +libelementary_la_SOURCES = \ +elm_priv.h \ +\ +elm_main.c \ +elm_util.c \ +elm_theme.c \ +elm_module.c \ +elm_store.c \ +\ +elm_win.c \ +elm_widget.c \ +elm_bg.c \ +elm_icon.c \ +elm_image.c \ +elm_box.c \ +elm_button.c \ +elm_scroller.c \ +elm_label.c \ +elm_toggle.c \ +elm_frame.c \ +elm_table.c \ +elm_gengrid.c \ +elm_clock.c \ +elm_layout.c \ +elm_hover.c \ +elm_entry.c \ +elm_bubble.c \ +elm_photo.c \ +elm_toolbar.c \ +elm_list.c \ +elm_slider.c \ +elm_actionslider.c \ +elm_genlist.c \ +elm_check.c \ +elm_radio.c \ +elm_pager.c \ +elm_progressbar.c \ +elm_separator.c \ +elm_spinner.c \ +elm_index.c \ +elm_photocam.c \ +elm_notify.c \ +elm_slideshow.c \ +elm_menu.c \ +elm_panel.c \ +elm_panes.c \ +elm_map.c \ +elm_flip.c \ +elm_conform.c \ +elm_mapbuf.c \ +elm_thumb.c \ +elm_config.c \ +elm_font.c \ +elm_animator.c \ +elm_transit.c \ +elm_calendar.c \ +elm_flipselector.c \ +elm_diskselector.c \ +elm_colorselector.c \ +\ +elc_anchorblock.c \ +elc_anchorview.c \ +elc_ctxpopup.c \ +elc_fileselector.c \ +elc_fileselector_button.c \ +elc_fileselector_entry.c \ +elc_hoversel.c \ +elc_scrolled_entry.c \ +\ +els_tooltip.c \ +els_cursor.c \ +els_pan.c \ +els_pan.h \ +els_scroller.c \ +els_scroller.h \ +els_box.c \ +els_box.h \ +els_icon.c \ +els_icon.h \ +\ +elm_cnp_helper.c + + +libelementary_la_CFLAGS = +libelementary_la_LIBADD = \ +@my_libs@ \ +@dlopen_libs@ \ +@ELEMENTARY_LIBS@ \ +@ELEMENTARY_X_LIBS@ \ +@ELEMENTARY_FB_LIBS@ \ +@ELEMENTARY_SDL_LIBS@ \ +@ELEMENTARY_WIN32_LIBS@ \ +@ELEMENTARY_WINCE_LIBS@ \ +@ELEMENTARY_EDBUS_LIBS@ \ +@ELEMENTARY_EFREET_LIBS@ \ +@ELEMENTARY_ETHUMB_LIBS@ \ +@EVIL_LIBS@ \ +@EFL_PTHREAD_LIBS@ +libelementary_la_LDFLAGS = \ +-no-undefined @lt_enable_auto_import@ \ +-version-info @version_info@ @release_info@ diff --git a/src/lib/elc_anchorblock.c b/src/lib/elc_anchorblock.c new file mode 100644 index 0000000..7c75062 --- /dev/null +++ b/src/lib/elc_anchorblock.c @@ -0,0 +1,461 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Anchorblock Anchorblock + * + * Anchorblock is for displaying tet that contains markup with anchors like: + * \something\ in it. These will be drawn differently and will + * be able to be clicked on by the user to display a popup. This popup then + * is intended to contain extra options such as "call", "add to contacts", + * "open web page" etc. + * + * Signals that you can add callbacks for are: + * + * anchor,clicked - anchor called was clicked. event_info is anchor info - + * Elm_Entry_Anchorview_Info + */ +typedef struct _Widget_Data Widget_Data; +typedef struct _Elm_Anchorblock_Item_Provider Elm_Anchorblock_Item_Provider; + +struct _Widget_Data +{ + Evas_Object *entry; + Evas_Object *hover_parent; + Evas_Object *pop, *hover; + Eina_List *item_providers; + const char *hover_style; +}; + +struct _Elm_Anchorblock_Item_Provider +{ + Evas_Object *(*func) (void *data, Evas_Object *anchorblock, const char *item); + void *data; +}; + +static const char *widtype = NULL; + +static const char SIG_ANCHOR_CLICKED[] = "anchor,clicked"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_ANCHOR_CLICKED, ""}, /* TODO: declare the type properly, as data is + * being passed + */ + {NULL, NULL} +}; + +static void _del_pre_hook(Evas_Object *obj); +static void _del_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _parent_del(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_event_callback_del_full(wd->entry, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + elm_anchorblock_hover_end(obj); + elm_anchorblock_hover_parent_set(obj, NULL); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Anchorblock_Item_Provider *ip; + if (!wd) return; + if (wd->hover_style) eina_stringshare_del(wd->hover_style); + EINA_LIST_FREE(wd->item_providers, ip) + { + free(ip); + } + free(wd); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + evas_object_size_hint_min_get(wd->entry, &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_hover_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_anchorblock_hover_end(data); +} + +static void +_anchor_clicked(void *data, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Elm_Entry_Anchor_Info *info = event_info; + Evas_Object *hover_parent; + Elm_Entry_Anchorblock_Info ei; + Evas_Coord x, w, y, h, px, py; + if (!wd) return; + wd->pop = elm_icon_add(obj); + evas_object_move(wd->pop, info->x, info->y); + evas_object_resize(wd->pop, info->w, info->h); + wd->hover = elm_hover_add(obj); + if (wd->hover_style) + elm_object_style_set(wd->hover, wd->hover_style); + hover_parent = wd->hover_parent; + if (!hover_parent) hover_parent = obj; + elm_hover_parent_set(wd->hover, hover_parent); + elm_hover_target_set(wd->hover, wd->pop); + ei.name = info->name; + ei.button = info->button; + ei.hover = wd->hover; + ei.anchor.x = info->x; + ei.anchor.y = info->y; + ei.anchor.w = info->w; + ei.anchor.h = info->h; + evas_object_geometry_get(hover_parent, &x, &y, &w, &h); + ei.hover_parent.x = x; + ei.hover_parent.y = y; + ei.hover_parent.w = w; + ei.hover_parent.h = h; + px = info->x + (info->w / 2); + py = info->y + (info->h / 2); + ei.hover_left = 1; + if (px < (x + (w / 3))) ei.hover_left = 0; + ei.hover_right = 1; + if (px > (x + ((w * 2) / 3))) ei.hover_right = 0; + ei.hover_top = 1; + if (py < (y + (h / 3))) ei.hover_top = 0; + ei.hover_bottom = 1; + if (py > (y + ((h * 2) / 3))) ei.hover_bottom = 0; + evas_object_smart_callback_call(data, SIG_ANCHOR_CLICKED, &ei); + evas_object_smart_callback_add(wd->hover, "clicked", _hover_clicked, data); + evas_object_show(wd->hover); +} + +static void +_parent_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->hover_parent = NULL; +} + +static Evas_Object * +_item_provider(void *data, Evas_Object *entry __UNUSED__, const char *item) +{ + Widget_Data *wd = elm_widget_data_get(data); + Eina_List *l; + Elm_Anchorblock_Item_Provider *ip; + + EINA_LIST_FOREACH(wd->item_providers, l, ip) + { + Evas_Object *o; + + o = ip->func(ip->data, data, item); + if (o) return o; + } + return NULL; +} + +/** + * Add a new Anchorblock object + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Anchorblock + */ +EAPI Evas_Object * +elm_anchorblock_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "anchorblock"); + elm_widget_type_set(obj, "anchorblock"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + + wd->entry = elm_entry_add(parent); + elm_entry_item_provider_prepend(wd->entry, _item_provider, obj); + elm_widget_resize_object_set(obj, wd->entry); + elm_entry_editable_set(wd->entry, 0); + evas_object_size_hint_weight_set(wd->entry, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(wd->entry, EVAS_HINT_FILL, EVAS_HINT_FILL); + + evas_object_event_callback_add(wd->entry, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + + elm_entry_entry_set(wd->entry, ""); + + evas_object_smart_callback_add(wd->entry, "anchor,clicked", + _anchor_clicked, obj); + + _sizing_eval(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the text markup of the anchorblock + * + * This sets the text of the anchorblock to be the text given as @p text. This + * text is in markup format with \ beginning an achor with the + * string link of 'XXX', and \ or \ ending the link. Other markup can + * be used dependign on the style support. + * + * @param obj The anchorblock object + * @param text The text to set, or NULL to clear + * + * @ingroup Anchorblock + */ +EAPI void +elm_anchorblock_text_set(Evas_Object *obj, const char *text) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_entry_set(wd->entry, text); + if (wd->hover) evas_object_del(wd->hover); + if (wd->pop) evas_object_del(wd->pop); + wd->hover = NULL; + wd->pop = NULL; + _sizing_eval(obj); +} + +/** + * Get the markup text set for the anchorblock + * + * This retrieves back the string set by @c elm_anchorblock_text_set(). + * + * @param obj The anchorblock object + * @return text The markup text set or @c NULL, either if it was not set + * or an error occurred + * + * @ingroup Anchorblock + */ +EAPI const char* +elm_anchorblock_text_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_entry_entry_get(wd->entry); +} + +/** + * Set the parent of the hover popup + * + * This sets the parent of the hover that anchorblock will create. See hover + * objects for more information on this. + * + * @param obj The anchorblock object + * @param parent The parent the hover should use + * + * @ingroup Anchorblock + */ +EAPI void +elm_anchorblock_hover_parent_set(Evas_Object *obj, Evas_Object *parent) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->hover_parent) + evas_object_event_callback_del_full(wd->hover_parent, EVAS_CALLBACK_DEL, _parent_del, obj); + wd->hover_parent = parent; + if (wd->hover_parent) + evas_object_event_callback_add(wd->hover_parent, EVAS_CALLBACK_DEL, _parent_del, obj); +} + +/** + * Get the parent of the hover popup + * + * This sgets the parent of the hover that anchorblock will create. See hover + * objects for more information on this. + * + * @param obj The anchorblock object + * @return The parent used by the hover + * + * @ingroup Anchorblock + */ +EAPI Evas_Object * +elm_anchorblock_hover_parent_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->hover_parent; +} + +/** + * Set the style that the hover should use + * + * This sets the style for the hover that anchorblock will create. See hover + * objects for more information + * + * @param obj The anchorblock object + * @param style The style to use + * + * @ingroup Anchorblock + */ +EAPI void +elm_anchorblock_hover_style_set(Evas_Object *obj, const char *style) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->hover_style, style); +} + +/** + * Get the style that the hover should use + * + * This gets the style for the hover that anchorblock will create. See hover + * objects for more information + * + * @param obj The anchorblock object + * @return The style defined + * + * @ingroup Anchorblock + */ +EAPI const char * +elm_anchorblock_hover_style_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->hover_style; +} + +/** + * Stop the hover popup in the anchorblock + * + * This will stop the hover popup in the anchorblock if it is currently active. + * + * @param obj The anchorblock object + * + * @ingroup Anchorblock + */ +EAPI void +elm_anchorblock_hover_end(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->hover) evas_object_del(wd->hover); + if (wd->pop) evas_object_del(wd->pop); + wd->hover = NULL; + wd->pop = NULL; +} + +/** + * This appends a custom item provider to the list for that anchorblock + * + * This appends the given callback. The list is walked from beginning to end + * with each function called given the item href string in the text. If the + * function returns an object handle other than NULL (it should create an + * and object to do this), then this object is used to replace that item. If + * not the next provider is called until one provides an item object, or the + * default provider in anchorblock does. + * + * @param obj The anchorblock object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Anchorblock + */ +EAPI void +elm_anchorblock_item_provider_append(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorblock, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + Elm_Anchorblock_Item_Provider *ip = calloc(1, sizeof(Elm_Anchorblock_Item_Provider)); + if (!ip) return; + ip->func = func; + ip->data = data; + wd->item_providers = eina_list_append(wd->item_providers, ip); +} + +/** + * This prepends a custom item provider to the list for that anchorblock + * + * This prepends the given callback. See elm_anchorblock_item_provider_append() for + * more information + * + * @param obj The anchorblock object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Anchorblock + */ +EAPI void +elm_anchorblock_item_provider_prepend(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorblock, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + Elm_Anchorblock_Item_Provider *ip = calloc(1, sizeof(Elm_Anchorblock_Item_Provider)); + if (!ip) return; + ip->func = func; + ip->data = data; + wd->item_providers = eina_list_prepend(wd->item_providers, ip); +} + +/** + * This removes a custom item provider to the list for that anchorblock + * + * This removes the given callback. See elm_anchorblock_item_provider_append() for + * more information + * + * @param obj The anchorblock object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Anchorblock + */ +EAPI void +elm_anchorblock_item_provider_remove(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorblock, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Elm_Anchorblock_Item_Provider *ip; + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + EINA_LIST_FOREACH(wd->item_providers, l, ip) + { + if ((ip->func == func) && (ip->data == data)) + { + wd->item_providers = eina_list_remove_list(wd->item_providers, l); + free(ip); + return; + } + } +} diff --git a/src/lib/elc_anchorview.c b/src/lib/elc_anchorview.c new file mode 100644 index 0000000..df61e53 --- /dev/null +++ b/src/lib/elc_anchorview.c @@ -0,0 +1,494 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Anchorview Anchorview + * + * This is just like the Anchorblock object, but provides a scroller to hold + * the text automatically. + * + * Signals that you can add callbacks for are: + * + * anchor,clicked - achor called was clicked. event_info is anchor info - + * Elm_Entry_Anchorview_Info + */ +typedef struct _Widget_Data Widget_Data; +typedef struct _Elm_Anchorview_Item_Provider Elm_Anchorview_Item_Provider; + +struct _Widget_Data +{ + Evas_Object *scroller, *entry; + Evas_Object *hover_parent; + Evas_Object *pop, *hover; + Eina_List *item_providers; + const char *hover_style; +}; + +struct _Elm_Anchorview_Item_Provider +{ + Evas_Object *(*func) (void *data, Evas_Object *anchorview, const char *item); + void *data; +}; + +static const char *widtype = NULL; + +static const char SIG_ANCHOR_CLICKED[] = "anchor,clicked"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_ANCHOR_CLICKED, ""}, /* TODO: declare the type properly, as data is + * being passed + */ + {NULL, NULL} +}; + +static void _del_pre_hook(Evas_Object *obj); +static void _del_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _parent_del(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static void +_del_pre_hook(Evas_Object *obj) +{ + elm_anchorview_hover_end(obj); + elm_anchorview_hover_parent_set(obj, NULL); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Anchorview_Item_Provider *ip; + if (!wd) return; + if (wd->hover_style) eina_stringshare_del(wd->hover_style); + EINA_LIST_FREE(wd->item_providers, ip) + { + free(ip); + } + free(wd); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_hover_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_anchorview_hover_end(data); +} + +static void +_anchor_clicked(void *data, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Elm_Entry_Anchor_Info *info = event_info; + Evas_Object *hover_parent; + Elm_Entry_Anchorview_Info ei; + Evas_Coord x, w, y, h, px, py; + if (!wd) return; + wd->pop = elm_icon_add(obj); + evas_object_move(wd->pop, info->x, info->y); + evas_object_resize(wd->pop, info->w, info->h); + wd->hover = elm_hover_add(obj); + if (wd->hover_style) elm_object_style_set(wd->hover, wd->hover_style); + hover_parent = wd->hover_parent; + if (!hover_parent) hover_parent = obj; + elm_hover_parent_set(wd->hover, hover_parent); + elm_hover_target_set(wd->hover, wd->pop); + ei.name = info->name; + ei.button = info->button; + ei.hover = wd->hover; + ei.anchor.x = info->x; + ei.anchor.y = info->y; + ei.anchor.w = info->w; + ei.anchor.h = info->h; + evas_object_geometry_get(hover_parent, &x, &y, &w, &h); + ei.hover_parent.x = x; + ei.hover_parent.y = y; + ei.hover_parent.w = w; + ei.hover_parent.h = h; + px = info->x + (info->w / 2); + py = info->y + (info->h / 2); + ei.hover_left = 1; + if (px < (x + (w / 3))) ei.hover_left = 0; + ei.hover_right = 1; + if (px > (x + ((w * 2) / 3))) ei.hover_right = 0; + ei.hover_top = 1; + if (py < (y + (h / 3))) ei.hover_top = 0; + ei.hover_bottom = 1; + if (py > (y + ((h * 2) / 3))) ei.hover_bottom = 0; + evas_object_smart_callback_call(data, SIG_ANCHOR_CLICKED, &ei); + evas_object_smart_callback_add(wd->hover, "clicked", _hover_clicked, data); + evas_object_show(wd->hover); +} + +static void +_parent_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->hover_parent = NULL; +} + +static Evas_Object * +_item_provider(void *data, Evas_Object *entry __UNUSED__, const char *item) +{ + Widget_Data *wd = elm_widget_data_get(data); + Eina_List *l; + Elm_Anchorview_Item_Provider *ip; + + EINA_LIST_FOREACH(wd->item_providers, l, ip) + { + Evas_Object *o; + + o = ip->func(ip->data, data, item); + if (o) return o; + } + return NULL; +} + +/** + * Add a new Anchorview object + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Anchorview + */ +EAPI Evas_Object * +elm_anchorview_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "anchorview"); + elm_widget_type_set(obj, "anchorview"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + + wd->scroller = elm_scroller_add(parent); + elm_widget_resize_object_set(obj, wd->scroller); + wd->entry = elm_entry_add(parent); + elm_entry_item_provider_prepend(wd->entry, _item_provider, obj); + elm_entry_editable_set(wd->entry, 0); + evas_object_size_hint_weight_set(wd->entry, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(wd->entry, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_scroller_content_set(wd->scroller, wd->entry); + evas_object_show(wd->entry); + + evas_object_event_callback_add(wd->entry, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + + elm_entry_entry_set(wd->entry, ""); + + evas_object_smart_callback_add(wd->entry, "anchor,clicked", + _anchor_clicked, obj); + + _sizing_eval(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the text markup of the anchorview + * + * This sets the text of the anchorview to be the text given as @p text. This + * text is in markup format with \ beginning an achor with the + * string link of 'XXX', and \ or \ ending the link. Other markup can + * be used dependign on the style support. + * + * @param obj The anchorview object + * @param text The text to set, or NULL to clear + * + * @ingroup Anchorview + */ +EAPI void +elm_anchorview_text_set(Evas_Object *obj, const char *text) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_entry_set(wd->entry, text); + if (wd->hover) evas_object_del(wd->hover); + if (wd->pop) evas_object_del(wd->pop); + wd->hover = NULL; + wd->pop = NULL; + _sizing_eval(obj); +} + +/** + * Get the markup text set for the anchorview + * + * This retrieves back the string set by @c elm_anchorview_text_set(). + * + * @param obj The anchorview object + * @return text The markup text set or @c NULL, either if it was not set + * or an error occurred + * + * @ingroup Anchorview + */ +EAPI const char* +elm_anchorview_text_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_entry_entry_get(wd->entry); +} + +/** + * Set the parent of the hover popup + * + * This sets the parent of the hover that anchorview will create. See hover + * objects for more information on this. + * + * @param obj The anchorview object + * @param parent The parent the hover should use + * + * @ingroup Anchorview + */ +EAPI void +elm_anchorview_hover_parent_set(Evas_Object *obj, Evas_Object *parent) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->hover_parent) + evas_object_event_callback_del_full(wd->hover_parent, EVAS_CALLBACK_DEL, _parent_del, obj); + wd->hover_parent = parent; + if (wd->hover_parent) + evas_object_event_callback_add(wd->hover_parent, EVAS_CALLBACK_DEL, _parent_del, obj); +} + +/** + * Get the parent of the hover popup + * + * This gets the parent of the hover that anchorview will created. See hover + * objects for more information on this. + * + * @param obj The anchorview object + * @return The parent used by hover + * + * @ingroup Anchorview + */ +EAPI Evas_Object * +elm_anchorview_hover_parent_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->hover_parent; +} + +/** + * Set the style that the hover should use + * + * This sets the style for the hover that anchorview will create. See hover + * objects for more information + * + * @param obj The anchorview object + * @param style The style to use + * + * @ingroup Anchorview + */ +EAPI void +elm_anchorview_hover_style_set(Evas_Object *obj, const char *style) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->hover_style, style); +} + +/** + * Get the style that the hover should use + * + * This gets the style for the hover that anchorview will create. See hover + * objects for more information + * + * @param obj The anchorview object + * @return The style defined + * + * @ingroup Anchorview + */ +EAPI const char * +elm_anchorview_hover_style_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->hover_style; +} + +/** + * Stop the hover popup in the anchorview + * + * This will stop the hover popup in the anchorview if it is currently active. + * + * @param obj The anchorview object + * + * @ingroup Anchorview + */ +EAPI void +elm_anchorview_hover_end(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->hover) evas_object_del(wd->hover); + if (wd->pop) evas_object_del(wd->pop); + wd->hover = NULL; + wd->pop = NULL; +} + +/** + * Set bounce mode + * + * This will enable or disable the scroller bounce mode for the anchorview. See + * elm_scroller_bounce_set() for details + * + * @param obj The anchorview anchorview + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Anchorview + */ +EAPI void +elm_anchorview_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_scroller_bounce_set(wd->scroller, h_bounce, v_bounce); +} + +/** + * Get the bounce mode + * + * @param obj The Anchorview object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Anchorview + */ +EAPI void +elm_anchorview_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_scroller_bounce_get(wd->scroller, h_bounce, v_bounce); +} + +/** + * This appends a custom item provider to the list for that anchorview + * + * This appends the given callback. The list is walked from beginning to end + * with each function called given the item href string in the text. If the + * function returns an object handle other than NULL (it should create an + * and object to do this), then this object is used to replace that item. If + * not the next provider is called until one provides an item object, or the + * default provider in anchorview does. + * + * @param obj The anchorview object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Anchorview + */ +EAPI void +elm_anchorview_item_provider_append(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorview, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + Elm_Anchorview_Item_Provider *ip = calloc(1, sizeof(Elm_Anchorview_Item_Provider)); + if (!ip) return; + ip->func = func; + ip->data = data; + wd->item_providers = eina_list_append(wd->item_providers, ip); +} + +/** + * This prepends a custom item provider to the list for that anchorview + * + * This prepends the given callback. See elm_anchorview_item_provider_append() for + * more information + * + * @param obj The anchorview object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Anchorview + */ +EAPI void +elm_anchorview_item_provider_prepend(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorview, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + Elm_Anchorview_Item_Provider *ip = calloc(1, sizeof(Elm_Anchorview_Item_Provider)); + if (!ip) return; + ip->func = func; + ip->data = data; + wd->item_providers = eina_list_prepend(wd->item_providers, ip); +} + +/** + * This removes a custom item provider to the list for that anchorview + * + * This removes the given callback. See elm_anchorview_item_provider_append() for + * more information + * + * @param obj The anchorview object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Anchorview + */ +EAPI void +elm_anchorview_item_provider_remove(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *anchorview, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Elm_Anchorview_Item_Provider *ip; + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + EINA_LIST_FOREACH(wd->item_providers, l, ip) + { + if ((ip->func == func) && (ip->data == data)) + { + wd->item_providers = eina_list_remove_list(wd->item_providers, l); + free(ip); + return; + } + } +} diff --git a/src/lib/elc_ctxpopup.c b/src/lib/elc_ctxpopup.c new file mode 100644 index 0000000..6454967 --- /dev/null +++ b/src/lib/elc_ctxpopup.c @@ -0,0 +1,1563 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Ctxpopup + * + * A ctxpopup is a widget that, when shown, pops up a list of items. + * It automatically chooses an area inside its parent object's view + * (set via elm_ctxpopup_add() and elm_ctxpopup_hover_parent_set()) to + * optimally fit into it. In the default theme, it will also point an + * arrow to the cursor position at the time one shows it. Ctxpopup + * items have a label and/or an icon. It is intended for a small + * number of items (hence the use of list, not genlist). + * + * Signals that you can add callbacks for are: + * + * dismissed - the ctxpopup was dismissed + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Elm_Ctxpopup_Item +{ + Elm_Widget_Item base; + const char *label; + Evas_Object *icon; + Evas_Smart_Cb func; + Eina_Bool disabled:1; +}; + +struct _Widget_Data +{ + Evas_Object *parent; + Evas_Object *base; + Evas_Object *content; + Evas_Object *box; + Evas_Object *arrow; + Evas_Object *scr; + Evas_Object *bg; + Evas_Object *hover_parent; + Eina_List *items; + Elm_Ctxpopup_Direction dir; + Elm_Ctxpopup_Direction dir_priority[4]; + Evas_Coord max_sc_w, max_sc_h; + Eina_Bool horizontal:1; + Eina_Bool visible:1; + Eina_Bool finished:1; +}; + +static const char *widtype = NULL; + +static void _del_hook(Evas_Object *obj); +static void _del_pre_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _hover_parent_resize(void *data, Evas *e __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__); +static void _hover_parent_move(void *data, Evas *e __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__); +static void _hover_parent_del(void *data, Evas *e __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__); +static void _hover_parent_callbacks_del(Evas_Object *obj); +static void _bg_clicked_cb(void *data, Evas_Object *obj __UNUSED__, + const char *emission __UNUSED__, + const char *source __UNUSED__); +static void _parent_resize(void *data, Evas *e, Evas_Object *obj, + void *event_info __UNUSED__); +static void _ctxpopup_show(void *data __UNUSED__, Evas *e __UNUSED__, + Evas_Object *obj, void *event_info __UNUSED__); +static void _ctxpopup_hide(void *data __UNUSED__, Evas *e __UNUSED__, + Evas_Object *obj, void *event_info __UNUSED__); +static void _ctxpopup_move(void *data __UNUSED__, Evas *e __UNUSED__, + Evas_Object *obj, void *event_info __UNUSED__); +static void _scroller_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__); +static void _ctxpopup_changed_size_hints(void *data __UNUSED__, + Evas *e __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__); +static void _item_new(Elm_Ctxpopup_Item *item, char *group_name); +static void _list_new(Evas_Object *obj); +static void _item_sizing_eval(Elm_Ctxpopup_Item *item); +static void _item_select_cb(void *data, Evas_Object *obj __UNUSED__, + const char *emission __UNUSED__, + const char *source __UNUSED__); +static Elm_Ctxpopup_Direction _calc_base_geometry(Evas_Object *obj, + Evas_Coord_Rectangle *rect); +static void _update_arrow(Evas_Object *obj, Elm_Ctxpopup_Direction dir); +static void _shift_base_by_arrow(Evas_Object *arrow, + Elm_Ctxpopup_Direction dir, + Evas_Coord_Rectangle *rect); +static void _adjust_pos_x(Evas_Coord_Point *pos, Evas_Coord_Point *base_size, + Evas_Coord_Rectangle *hover_area); +static void _adjust_pos_y(Evas_Coord_Point *pos, Evas_Coord_Point *base_size, + Evas_Coord_Rectangle *hover_area); +static void _scroller_size_reset(Widget_Data *wd); +static void _hide(Evas_Object *obj); +static void _content_del(void *data, Evas *e, Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__); +static void _freeze_on(void *data __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__); +static void _freeze_off(void *data __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__); +static void _hold_on(void *data __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__); +static void _hold_off(void *data __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__); +static void _item_icon_set(Elm_Ctxpopup_Item *item, Evas_Object *icon); +static void _item_label_set(Elm_Ctxpopup_Item *item, const char *label); +static void _remove_items(Widget_Data * wd); + +static const char SIG_DISMISSED[] = "dismissed"; + +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_DISMISSED, ""}, + {NULL, NULL} +}; + +#define ELM_CTXPOPUP_ITEM_CHECK_RETURN(it, ...) \ + ELM_WIDGET_ITEM_CHECK_OR_RETURN((Elm_Widget_Item *)it, __VA_ARGS__); \ + ELM_CHECK_WIDTYPE(item->base.widget, widtype) __VA_ARGS__; + +static void +_freeze_on(void *data __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return; + elm_object_scroll_freeze_push(wd->scr); +} + +static void +_freeze_off(void *data __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return; + elm_object_scroll_freeze_pop(wd->scr); +} + +static void +_hold_on(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return; + elm_object_scroll_hold_push(wd->scr); +} + +static void +_hold_off(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return; + elm_object_scroll_hold_pop(wd->scr); +} + +static void +_scroller_size_reset(Widget_Data *wd) +{ + wd->finished = EINA_FALSE; + wd->max_sc_h = -1; + wd->max_sc_w = -1; +} + +static void +_hover_parent_callbacks_del(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if ((!wd) || (!wd->hover_parent)) + return; + + evas_object_event_callback_del_full(wd->hover_parent, EVAS_CALLBACK_DEL, + _hover_parent_del, obj); + evas_object_event_callback_del_full(wd->hover_parent, EVAS_CALLBACK_MOVE, + _hover_parent_move, obj); + evas_object_event_callback_del_full(wd->hover_parent, EVAS_CALLBACK_RESIZE, + _hover_parent_resize, obj); +} + +static void +_hover_parent_resize(void *data, Evas *e __UNUSED__, + Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + + if (!wd) + return; + + if (wd->visible) + { + _scroller_size_reset(wd); + _sizing_eval(data); + } +} + +static void +_hover_parent_move(void *data, Evas *e __UNUSED__, + Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + + if (!wd) + return; + + if (wd->visible) + { + _scroller_size_reset(wd); + _sizing_eval(obj); + } +} + +static void +_hover_parent_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + + if (!wd) + return; + + wd->hover_parent = NULL; +} + +static void +_item_sizing_eval(Elm_Ctxpopup_Item *item) +{ + Evas_Coord min_w = -1, min_h = -1, max_w = -1, max_h = -1; + + Evas_Coord x, y, w, h; + + if (!item) + return; + + evas_object_geometry_get(item->base.view, &x, &y, &w, &h); + edje_object_size_min_restricted_calc(item->base.view, &min_w, &min_h, min_w, + min_h); + evas_object_size_hint_min_set(item->base.view, min_w, min_h); + evas_object_size_hint_max_set(item->base.view, max_w, max_h); +} + +static void +_adjust_pos_x(Evas_Coord_Point *pos, Evas_Coord_Point *base_size, + Evas_Coord_Rectangle *hover_area) +{ + pos->x -= (base_size->x / 2); + + if (pos->x < hover_area->x) + pos->x = hover_area->x; + else if ((pos->x + base_size->x) > (hover_area->x + hover_area->w)) + pos->x = (hover_area->x + hover_area->w) - base_size->x; + + if (base_size->x > hover_area->w) + base_size->x -= (base_size->x - hover_area->w); + + if (pos->x < hover_area->x) + pos->x = hover_area->x; +} + +static void +_adjust_pos_y(Evas_Coord_Point *pos, Evas_Coord_Point *base_size, + Evas_Coord_Rectangle *hover_area) +{ + pos->y -= (base_size->y / 2); + + if (pos->y < hover_area->y) + pos->y = hover_area->y; + else if ((pos->y + base_size->y) > (hover_area->y + hover_area->h)) + pos->y = hover_area->y + hover_area->h - base_size->y; + + if (base_size->y > hover_area->h) + base_size->y -= (base_size->y - hover_area->h); + + if (pos->y < hover_area->y) + pos->y = hover_area->y; +} + +static void +_ctxpopup_changed_size_hints(void *data __UNUSED__, Evas *e __UNUSED__, + Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (wd->visible) + _sizing_eval(obj); +} + +static Elm_Ctxpopup_Direction +_calc_base_geometry(Evas_Object *obj, Evas_Coord_Rectangle *rect) +{ + Widget_Data *wd; + Evas_Coord_Point pos = {0, 0}; + Evas_Coord_Point base_size; + Evas_Coord_Point max_size; + Evas_Coord_Point min_size; + Evas_Coord_Rectangle hover_area; + Evas_Coord_Rectangle parent_size; + Evas_Coord_Point arrow_size; + Elm_Ctxpopup_Direction arrow = ELM_CTXPOPUP_DIRECTION_DOWN; + Evas_Coord finger_size; + Evas_Coord_Point temp; + int idx; + + wd = elm_widget_data_get(obj); + + if ((!wd) || (!rect)) + return ELM_CTXPOPUP_DIRECTION_DOWN; + + finger_size = elm_finger_size_get(); + + edje_object_part_geometry_get(wd->arrow, "ctxpopup_arrow", NULL, NULL, + &arrow_size.x, &arrow_size.y); + evas_object_resize(wd->arrow, arrow_size.x, arrow_size.y); + + //Initialize Area Rectangle. + if (wd->hover_parent) + evas_object_geometry_get(wd->hover_parent, &hover_area.x, &hover_area.y, + &hover_area.w, &hover_area.h); + else + { + evas_object_geometry_get(wd->parent, &parent_size.x, &parent_size.y, + &parent_size.w, &parent_size.h); + hover_area.x = parent_size.x; + hover_area.y = parent_size.y; + hover_area.w = parent_size.w; + hover_area.h = parent_size.h; + } + + evas_object_geometry_get(obj, &pos.x, &pos.y, NULL, NULL); + + //recalc the edje + edje_object_size_min_calc(wd->base, &base_size.x, &base_size.y); + evas_object_smart_calculate(wd->base); + + //Limit to Max Size + evas_object_size_hint_max_get(obj, &max_size.x, &max_size.y); + + if ((max_size.y > 0) && (base_size.y > max_size.y)) + base_size.y = max_size.y; + + if ((max_size.x > 0) && (base_size.x > max_size.x)) + base_size.x = max_size.x; + + //Limit to Min Size + evas_object_size_hint_min_get(obj, &min_size.x, &min_size.y); + + if ((min_size.y > 0) && (base_size.y < min_size.y)) + base_size.y = min_size.y; + + if ((min_size.x > 0) && (base_size.x < min_size.x)) + base_size.x = min_size.x; + + //Check the Which direction is available. + //If find a avaialble direction, it adjusts position and size. + for (idx = 0; idx < 4; idx++) + { + switch (wd->dir_priority[idx]) + { + case ELM_CTXPOPUP_DIRECTION_UP: + temp.y = pos.y - base_size.y; + if ((temp.y - arrow_size.y - finger_size) < hover_area.y) + continue; + _adjust_pos_x(&pos, &base_size, &hover_area); + pos.y -= (base_size.y + finger_size); + arrow = ELM_CTXPOPUP_DIRECTION_DOWN; + break; + case ELM_CTXPOPUP_DIRECTION_LEFT: + temp.x = (pos.x - base_size.x); + if ((temp.x - arrow_size.x - finger_size) < hover_area.x) + continue; + _adjust_pos_y(&pos, &base_size, &hover_area); + pos.x -= (base_size.x + finger_size); + arrow = ELM_CTXPOPUP_DIRECTION_RIGHT; + break; + case ELM_CTXPOPUP_DIRECTION_RIGHT: + temp.x = (pos.x + base_size.x); + if ((temp.x + arrow_size.x + finger_size) > + (hover_area.x + hover_area.w)) + continue; + _adjust_pos_y(&pos, &base_size, &hover_area); + pos.x += finger_size; + arrow = ELM_CTXPOPUP_DIRECTION_LEFT; + break; + case ELM_CTXPOPUP_DIRECTION_DOWN: + temp.y = (pos.y + base_size.y); + if ((temp.y + arrow_size.y + finger_size) > + (hover_area.y + hover_area.h)) + continue; + _adjust_pos_x(&pos, &base_size, &hover_area); + pos.y += finger_size; + arrow = ELM_CTXPOPUP_DIRECTION_UP; + break; + default: + break; + } + break; + } + + //In this case, all directions are invalid because of lack of space. + if (idx == 4) + { + //TODO 1: Find the largest space direction. + Evas_Coord length[2]; + + length[0] = pos.y - hover_area.y; + length[1] = (hover_area.y + hover_area.h) - pos.y; + + if (length[0] > length[1]) + idx = ELM_CTXPOPUP_DIRECTION_DOWN; + else + idx = ELM_CTXPOPUP_DIRECTION_UP; + + //TODO 2: determine x , y + switch (idx) + { + case ELM_CTXPOPUP_DIRECTION_UP: + _adjust_pos_x(&pos, &base_size, &hover_area); + pos.y -= (base_size.y + finger_size); + arrow = ELM_CTXPOPUP_DIRECTION_DOWN; + if (pos.y < hover_area.y + arrow_size.y) + { + base_size.y -= ((hover_area.y + arrow_size.y) - pos.y); + pos.y = hover_area.y + arrow_size.y; + } + break; + case ELM_CTXPOPUP_DIRECTION_LEFT: + _adjust_pos_y(&pos, &base_size, &hover_area); + pos.x -= (base_size.x + finger_size); + arrow = ELM_CTXPOPUP_DIRECTION_RIGHT; + if (pos.x < hover_area.x + arrow_size.x) + { + base_size.x -= ((hover_area.x + arrow_size.x) - pos.x); + pos.x = hover_area.x + arrow_size.x; + } + break; + case ELM_CTXPOPUP_DIRECTION_RIGHT: + _adjust_pos_y(&pos, &base_size, &hover_area); + pos.x += finger_size; + arrow = ELM_CTXPOPUP_DIRECTION_LEFT; + if (pos.x + arrow_size.x + base_size.x > + hover_area.x + hover_area.w) + base_size.x -= + ((pos.x + arrow_size.x + base_size.x) - + (hover_area.x + hover_area.w)); + break; + case ELM_CTXPOPUP_DIRECTION_DOWN: + _adjust_pos_x(&pos, &base_size, &hover_area); + pos.y += finger_size; + arrow = ELM_CTXPOPUP_DIRECTION_UP; + if (pos.y + arrow_size.y + base_size.y > + hover_area.y + hover_area.h) + base_size.y -= + ((pos.y + arrow_size.y + base_size.y) - + (hover_area.y + hover_area.h)); + break; + default: + break; + } + } + + //Final position and size. + rect->x = pos.x; + rect->y = pos.y; + rect->w = base_size.x; + rect->h = base_size.y; + + return arrow; +} + +static void +_update_arrow(Evas_Object *obj, Elm_Ctxpopup_Direction dir) +{ + Evas_Coord x, y; + Evas_Coord_Rectangle arrow_size; + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + evas_object_geometry_get(obj, &x, &y, NULL, NULL); + evas_object_geometry_get(wd->arrow, NULL, NULL, &arrow_size.w, + &arrow_size.h); + + switch (dir) + { + case ELM_CTXPOPUP_DIRECTION_LEFT: + edje_object_signal_emit(wd->arrow, "elm,state,left", "elm"); + arrow_size.y = (y - (arrow_size.h * 0.5)); + arrow_size.x = (x + elm_finger_size_get()); + break; + case ELM_CTXPOPUP_DIRECTION_RIGHT: + edje_object_signal_emit(wd->arrow, "elm,state,right", "elm"); + arrow_size.y = (y - (arrow_size.h * 0.5)); + arrow_size.x = (x - elm_finger_size_get() - arrow_size.w); + break; + case ELM_CTXPOPUP_DIRECTION_UP: + edje_object_signal_emit(wd->arrow, "elm,state,top", "elm"); + arrow_size.x = (x - (arrow_size.w * 0.5)); + arrow_size.y = (y + elm_finger_size_get()); + break; + case ELM_CTXPOPUP_DIRECTION_DOWN: + edje_object_signal_emit(wd->arrow, "elm,state,bottom", "elm"); + arrow_size.x = (x - (arrow_size.w * 0.5)); + arrow_size.y = (y - elm_finger_size_get() - arrow_size.h); + break; + default: + break; + } + + evas_object_move(wd->arrow, arrow_size.x, arrow_size.y); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd; + Eina_List *elist; + Elm_Ctxpopup_Item *item; + Evas_Coord_Rectangle rect = { 0, 0, 1, 1 }; + Evas_Coord_Point box_size = { 0, 0 }; + Evas_Coord_Point _box_size = { 0, 0 }; + + wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->parent)) + return; + + //Box, Scroller + EINA_LIST_FOREACH(wd->items, elist, item) + { + _item_sizing_eval(item); + evas_object_size_hint_min_get(item->base.view, &_box_size.x, &_box_size.y); + if (!wd->horizontal) + { + if (_box_size.x > box_size.x) + box_size.x = _box_size.x; + if (_box_size.y != -1) + box_size.y += _box_size.y; + } + else + { + if (_box_size.x != -1) + box_size.x += _box_size.x; + if (_box_size.y > box_size.y) + box_size.y = _box_size.y; + } + } + + if (!wd->content) + { + evas_object_size_hint_min_set(wd->box, box_size.x, box_size.y); + evas_object_size_hint_min_set(wd->scr, box_size.x, box_size.y); + } + + //Base + wd->dir = _calc_base_geometry(obj, &rect); + _update_arrow(obj, wd->dir); + _shift_base_by_arrow(wd->arrow, wd->dir, &rect); + + //resize scroller according to final size. + if (!wd->content) + evas_object_smart_calculate(wd->scr); + + evas_object_move(wd->base, rect.x, rect.y); + evas_object_resize(wd->base, rect.w, rect.h); +} + +static void +_shift_base_by_arrow(Evas_Object *arrow, Elm_Ctxpopup_Direction dir, + Evas_Coord_Rectangle *rect) +{ + Evas_Coord arrow_w, arrow_h; + + evas_object_geometry_get(arrow, NULL, NULL, &arrow_w, &arrow_h); + + switch (dir) + { + case ELM_CTXPOPUP_DIRECTION_LEFT: + rect->x += arrow_w; + break; + case ELM_CTXPOPUP_DIRECTION_RIGHT: + rect->x -= arrow_w; + break; + case ELM_CTXPOPUP_DIRECTION_UP: + rect->y += arrow_h; + break; + case ELM_CTXPOPUP_DIRECTION_DOWN: + rect->y -= arrow_h; + break; + default: + break; + } +} + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_RESIZE, + _parent_resize, obj); + + _hover_parent_callbacks_del(obj); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + elm_ctxpopup_clear(obj); + evas_object_del(wd->arrow); + evas_object_del(wd->base); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd; + Eina_List *elist; + Elm_Ctxpopup_Item *item; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + //Items + EINA_LIST_FOREACH(wd->items, elist, item) + { + if (item->label && item->icon) + _elm_theme_object_set(obj, item->base.view, "ctxpopup", + "icon_text_style_item", + elm_widget_style_get(obj)); + else if (item->label) + _elm_theme_object_set(obj, item->base.view, "ctxpopup", "text_style_item", + elm_widget_style_get(obj)); + else if (item->icon) + _elm_theme_object_set(obj, item->base.view, "ctxpopup", "icon_style_item", + elm_widget_style_get(obj)); + if (item->label) + edje_object_part_text_set(item->base.view, "elm.text", item->label); + + if (item->disabled) + edje_object_signal_emit(item->base.view, "elm,state,disabled", "elm"); + + edje_object_message_signal_process(item->base.view); + } + + _elm_theme_object_set(obj, wd->bg, "ctxpopup", "bg", + elm_widget_style_get(obj)); + _elm_theme_object_set(obj, wd->base, "ctxpopup", "base", + elm_widget_style_get(obj)); + _elm_theme_object_set(obj, wd->arrow, "ctxpopup", "arrow", + elm_widget_style_get(obj)); + + if (!strncmp(elm_object_style_get(obj), "default", + strlen("default"))) + elm_object_style_set(wd->scr, "ctxpopup"); + else + elm_object_style_set(wd->scr, elm_object_style_get(obj)); + + if (wd->visible) + { + _scroller_size_reset(wd); + _sizing_eval(obj); + } +} + +static void +_bg_clicked_cb(void *data, Evas_Object *obj __UNUSED__, + const char *emission __UNUSED__, const char *source __UNUSED__) +{ + evas_object_hide(data); +} + +static void +_parent_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__) +{ + Evas_Coord w, h; + Widget_Data *wd; + + wd = elm_widget_data_get(data); + if (!wd) + return; + + evas_object_geometry_get(obj, NULL, NULL, &w, &h); + evas_object_resize(wd->bg, w, h); + + if (!wd->visible) + return; + + _hide(data); +} + +static void +_ctxpopup_show(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + if ((!wd->items) && (!wd->content)) + return; + + wd->visible = EINA_TRUE; + + evas_object_show(wd->bg); + evas_object_show(wd->base); + evas_object_show(wd->arrow); + + edje_object_signal_emit(wd->bg, "elm,state,show", "elm"); + + _sizing_eval(obj); +} + +static void +_hide(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return; + + evas_object_hide(wd->bg); + evas_object_hide(wd->arrow); + evas_object_hide(wd->base); + + _scroller_size_reset(wd); + + evas_object_smart_callback_call(obj, SIG_DISMISSED, NULL); + wd->visible = EINA_FALSE; +} + +static void +_ctxpopup_hide(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (!wd->visible) + return; + + _hide(obj); +} + +static void +_scroller_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd; + Evas_Coord w, h; + + wd = elm_widget_data_get(data); + if (!wd) + return; + + if (!wd->visible) + return; + if (wd->finished) + return; + + evas_object_geometry_get(obj, 0, 0, &w, &h); + + if (w != 0 && h != 0) + { + if ((w <= wd->max_sc_w) && (h <= wd->max_sc_h)) + { + _sizing_eval(data); + wd->finished = EINA_TRUE; + return; + } + } + + if (wd->max_sc_w < w) + wd->max_sc_w = w; + if (wd->max_sc_h < h) + wd->max_sc_h = h; + + _sizing_eval(data); +} + +static void +_ctxpopup_move(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + + if (!wd) + return; + + if (wd->visible) + evas_object_show(wd->arrow); + + _scroller_size_reset(wd); + _sizing_eval(obj); +} + +static void +_item_select_cb(void *data, Evas_Object *obj __UNUSED__, + const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Elm_Ctxpopup_Item *item = data; + + if (!item) + return; + if (item->disabled) + return; + + if (item->func) + item->func((void*) item->base.data, item->base.widget, data); +} + +static void +_item_icon_set(Elm_Ctxpopup_Item *item, Evas_Object *icon) +{ + if (item->icon) + { + elm_widget_sub_object_del(item->base.view, item->icon); + evas_object_del(item->icon); + } + + item->icon = icon; + edje_object_part_swallow(item->base.view, "elm.swallow.icon", item->icon); + edje_object_message_signal_process(item->base.view); +} + +static void +_item_label_set(Elm_Ctxpopup_Item *item, const char *label) +{ + if (!eina_stringshare_replace(&item->label, label)) + return; + + edje_object_part_text_set(item->base.view, "elm.text", label); + edje_object_message_signal_process(item->base.view); +} + +static void +_item_new(Elm_Ctxpopup_Item *item, char *group_name) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(item->base.widget); + if (!wd) + return; + + item->base.view = edje_object_add(evas_object_evas_get(wd->base)); + _elm_theme_object_set(item->base.widget, item->base.view, "ctxpopup", group_name, + elm_widget_style_get(item->base.widget)); + edje_object_signal_callback_add(item->base.view, "elm,action,click", "", + _item_select_cb, item); + evas_object_size_hint_align_set(item->base.view, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(item->base.view); +} + +static void +_content_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + elm_ctxpopup_content_unset(data); +} + +static void +_list_del(Widget_Data *wd) +{ + if (!wd->scr) + return; + + edje_object_part_unswallow(wd->base, wd->scr); + evas_object_del(wd->scr); + wd->scr = NULL; + wd->box = NULL; +} + +static void +_list_new(Evas_Object *obj) +{ + Widget_Data *wd; + wd = elm_widget_data_get(obj); + if (!wd) + return; + + //scroller + wd->scr = elm_scroller_add(obj); + elm_object_style_set(wd->scr, "ctxpopup"); + evas_object_size_hint_align_set(wd->scr, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_event_callback_add(wd->scr, EVAS_CALLBACK_RESIZE, + _scroller_resize, obj); + edje_object_part_swallow(wd->base, "elm.swallow.content", wd->scr); + + //box + wd->box = elm_box_add(obj); + evas_object_size_hint_weight_set(wd->box, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + + elm_scroller_content_set(wd->scr, wd->box); + elm_ctxpopup_horizontal_set(obj, wd->horizontal); +} + +/** + * Add a new Ctxpopup object to the parent. + * + * @param parent Parent object + * @return New object or @c NULL, if it cannot be created + * + * @ingroup Ctxpopup + */ +EAPI Evas_Object * +elm_ctxpopup_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + Evas_Coord x, y, w, h; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) + return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "ctxpopup"); + elm_widget_type_set(obj, "ctxpopup"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + + wd->parent = parent; + + //Background + wd->bg = edje_object_add(e); + elm_widget_sub_object_add(obj, wd->bg); + _elm_theme_object_set(obj, wd->bg, "ctxpopup", "bg", "default"); + evas_object_geometry_get(parent, &x, &y, &w, &h); + evas_object_move(wd->bg, x, y); + evas_object_resize(wd->bg, w, h); + edje_object_signal_callback_add(wd->bg, "elm,action,click", "", + _bg_clicked_cb, obj); + + //Base + wd->base = edje_object_add(e); + elm_widget_sub_object_add(obj, wd->base); + _elm_theme_object_set(obj, wd->base, "ctxpopup", "base", "default"); + + //Arrow + wd->arrow = edje_object_add(e); + elm_widget_sub_object_add(obj, wd->arrow); + _elm_theme_object_set(obj, wd->arrow, "ctxpopup", "arrow", "default"); + + wd->dir_priority[0] = ELM_CTXPOPUP_DIRECTION_UP; + wd->dir_priority[1] = ELM_CTXPOPUP_DIRECTION_LEFT; + wd->dir_priority[2] = ELM_CTXPOPUP_DIRECTION_RIGHT; + wd->dir_priority[3] = ELM_CTXPOPUP_DIRECTION_DOWN; + + evas_object_event_callback_add(parent, EVAS_CALLBACK_RESIZE, _parent_resize, + obj); + evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, _ctxpopup_show, + NULL); + evas_object_event_callback_add(obj, EVAS_CALLBACK_HIDE, _ctxpopup_hide, + NULL); + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOVE, _ctxpopup_move, + NULL); + evas_object_event_callback_add(obj, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _ctxpopup_changed_size_hints, NULL); + evas_object_smart_callback_add(obj, "scroll-freeze-on", _freeze_on, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-off", _freeze_off, obj); + evas_object_smart_callback_add(obj, "scroll-hold-on", _hold_on, obj); + evas_object_smart_callback_add(obj, "scroll-hold-off", _hold_off, obj); + + evas_object_smart_callbacks_descriptions_set(obj, _signals); + + return obj; +} + +/** + * Get the icon object for the given ctxpopup item. + * + * @param item Ctxpopup item + * @return icon object or @c NULL, if the item does not have icon or an error occurred + * + * @ingroup Ctxpopup + */ +EAPI Evas_Object * +elm_ctxpopup_item_icon_get(const Elm_Ctxpopup_Item *item) +{ + ELM_CTXPOPUP_ITEM_CHECK_RETURN(item, NULL); + return item->icon; +} + +/** + * Sets the side icon associated with the ctxpopup item + * + * Once the icon object is set, a previously set one will be deleted. + * You probably don't want, then, to have the same icon object + * set for more than one item of the list (when replacing one of its + * instances). + * + * @param item Ctxpopup item + * @param icon Icon object to be set + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_item_icon_set(Elm_Ctxpopup_Item *item, Evas_Object *icon) +{ + ELM_CTXPOPUP_ITEM_CHECK_RETURN(item); + + Widget_Data *wd; + + wd = elm_widget_data_get(item->base.widget); + if (!wd) + return; + + _item_icon_set(item, icon); + + if (wd->visible) + { + _scroller_size_reset(wd); + _sizing_eval(item->base.widget); + } +} + +/** + * Get the label object for the given ctxpopup item. + * + * @param item Ctxpopup item + * @return label object or @c NULL, if the item does not have label or an error occured + * + * @ingroup Ctxpopup + * + */ +EAPI const char * +elm_ctxpopup_item_label_get(const Elm_Ctxpopup_Item *item) +{ + ELM_CTXPOPUP_ITEM_CHECK_RETURN(item, NULL); + return item->label; +} + +/** + * (Re)set the label on the given ctxpopup item. + * + * @param item Ctxpopup item + * @param label String to set as label + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_item_label_set(Elm_Ctxpopup_Item *item, const char *label) +{ + ELM_CTXPOPUP_ITEM_CHECK_RETURN(item); + + Widget_Data *wd; + + wd = elm_widget_data_get(item->base.widget); + if (!wd) + return; + + _item_label_set(item, label); + + if (wd->visible) + { + _scroller_size_reset(wd); + _sizing_eval(item->base.widget); + } +} + +/** + * Set the Ctxpopup's parent + * Set the parent object (it would much probably be the + * window that the ctxpopup is in). + * + * @param obj The ctxpopup object + * @param area The parent to use + * + * @note elm_ctxpopup_add() will automatically call this function + * with its @c parent argument. + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_hover_parent_set(Evas_Object *obj, Evas_Object *hover_parent) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + _hover_parent_callbacks_del(obj); + + if (hover_parent) + { + evas_object_event_callback_add(hover_parent, EVAS_CALLBACK_DEL, + _hover_parent_del, obj); + evas_object_event_callback_add(hover_parent, EVAS_CALLBACK_MOVE, + _hover_parent_move, obj); + evas_object_event_callback_add(hover_parent, EVAS_CALLBACK_RESIZE, + _hover_parent_resize, obj); + } + + wd->hover_parent = hover_parent; +} + +/** + * Get the Ctxpopup's parent + * + * @param obj The ctxpopup object + * + * @see elm_ctxpopup_hover_parent_set() for more information + * + * @ingroup Ctxpopup + */ +EAPI Evas_Object * +elm_ctxpopup_hover_parent_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return NULL; + + return wd->hover_parent; +} + +static void +_remove_items(Widget_Data *wd) +{ + Eina_List *elist; + Elm_Ctxpopup_Item *item; + + if (!wd->items) + return; + + EINA_LIST_FOREACH(wd->items, elist, item) + { + if (item->label) + eina_stringshare_del(item->label); + if (item->icon) + evas_object_del(item->icon); + wd->items = eina_list_remove(wd->items, item); + free(item); + } + + wd->items = NULL; +} + +/** + * Clear all items in the given ctxpopup object. + * + * @param obj Ctxpopup object + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_clear(Evas_Object * obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return; + + _remove_items(wd); + _list_del(wd); +} + +/** + * Change the ctxpopup's orientation to horizontal or vertical. + * + * @param obj Ctxpopup object + * @param horizontal @c EINA_TRUE for horizontal mode, @c EINA_FALSE for vertical + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + wd->horizontal = !!horizontal; + + if ((!wd->scr) && (!wd->box)) + return; + + if (!horizontal) + { + elm_box_horizontal_set(wd->box, EINA_FALSE); + elm_scroller_bounce_set(wd->scr, EINA_FALSE, EINA_TRUE); + } + else + { + elm_box_horizontal_set(wd->box, EINA_TRUE); + elm_scroller_bounce_set(wd->scr, EINA_TRUE, EINA_FALSE); + } + + if (wd->visible) + _sizing_eval(obj); +} + +/** + * Get the value of current ctxpopup object's orientation. + * + * @param obj Ctxpopup object + * @return @c EINA_TRUE for horizontal mode, @c EINA_FALSE for vertical mode (or errors) + * + * @ingroup Ctxpopup + */ +EAPI Eina_Bool +elm_ctxpopup_horizontal_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return EINA_FALSE; + + return wd->horizontal; +} + +/** + * Add a new item to a ctxpopup object. + * + * Both a item list and a content could not be set at the same time! + * once you set add a item, the previous content will be removed. + * + * @param obj Ctxpopup object + * @param icon Icon to be set on new item + * @param label The Label of the new item + * @param func Convenience function called when item selected + * @param data Data passed to @p func above + * @return A handle to the item added or @c NULL, on errors + * + * @ingroup Ctxpopup + */ +EAPI Elm_Ctxpopup_Item * +elm_ctxpopup_item_append(Evas_Object *obj, const char *label, + Evas_Object *icon, Evas_Smart_Cb func, + const void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Widget_Data *wd; + Elm_Ctxpopup_Item *item; + + wd = elm_widget_data_get(obj); + if (!wd) + return NULL; + + item = elm_widget_item_new(obj, Elm_Ctxpopup_Item); + if (!item) + return NULL; + + //The first item is appended. + if (wd->content) + evas_object_del(elm_ctxpopup_content_unset(obj)); + + if (!wd->items) + _list_new(obj); + + item->func = func; + item->base.data = data; + + if (icon && label) + _item_new(item, "icon_text_style_item"); + else if (label) + _item_new(item, "text_style_item"); + else + _item_new(item, "icon_style_item"); + + _item_icon_set(item, icon); + _item_label_set(item, label); + elm_box_pack_end(wd->box, item->base.view); + wd->items = eina_list_append(wd->items, item); + + if (wd->visible) + { + _scroller_size_reset(wd); + _sizing_eval(obj); + } + + return item; +} + +/** + * Delete the given item in a ctxpopup object. + * + * @param item Ctxpopup item to be deleted + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_item_del(Elm_Ctxpopup_Item *item) +{ + ELM_CTXPOPUP_ITEM_CHECK_RETURN(item); + + Widget_Data *wd; + + wd = elm_widget_data_get(item->base.widget); + if (!wd) + return; + + if (item->icon) + evas_object_del(item->icon); + if (item->base.view) + evas_object_del(item->base.view); + + eina_stringshare_del(item->label); + + wd->items = eina_list_remove(wd->items, item); + + if (eina_list_count(wd->items) < 1) + wd->items = NULL; + + if (wd->visible) + _sizing_eval(item->base.widget); + + free(item); +} + +/** + * Set the ctxpopup item's state as disabled or enabled. + * + * @param item Ctxpopup item to be enabled/disabled + * @param disabled @c EINA_TRUE to disable it, @c EINA_FALSE to enable it + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_item_disabled_set(Elm_Ctxpopup_Item *item, Eina_Bool disabled) +{ + ELM_CTXPOPUP_ITEM_CHECK_RETURN(item); + + Widget_Data *wd; + + wd = elm_widget_data_get(item->base.widget); + if (!wd) + return; + + if (disabled == item->disabled) + return; + + if (disabled) + edje_object_signal_emit(item->base.view, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(item->base.view, "elm,state,enabled", "elm"); + + item->disabled = !!disabled; +} + +/** + * Get the ctxpopup item's disabled/enabled state. + * + * @param item Ctxpopup item to be enabled/disabled + * @return disabled @c EINA_TRUE, if disabled, @c EINA_FALSE otherwise + * + * @ingroup Ctxpopup + */ +EAPI Eina_Bool +elm_ctxpopup_item_disabled_get(const Elm_Ctxpopup_Item *item) +{ + ELM_CTXPOPUP_ITEM_CHECK_RETURN(item, EINA_FALSE); + + return item->disabled; +} + +/** + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_ctxpopup_content_unset() function + * + * Both a item list and a content could not be set at the same time! + * once you set a content, the previous list items will be removed. + * + * @param obj Ctxpopup object + * @param content Content to be swallowed + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_content_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if ((!wd) || (!content)) + return; + + if (wd->items) + elm_ctxpopup_clear(obj); + + if (wd->content) + evas_object_del(wd->content); + + evas_object_event_callback_add(content, EVAS_CALLBACK_DEL, _content_del, + obj); + + elm_widget_sub_object_add(obj, content); + edje_object_part_swallow(wd->base, "elm.swallow.content", content); + edje_object_message_signal_process(wd->base); + + wd->content = content; + + if (wd->visible) + _sizing_eval(obj); +} + +/** + * Unset the ctxpopup content + * + * Unparent and return the content object which was set for this widget + * + * @param obj Ctxpopup object + * @return The content that was being used + * + * @ingroup Ctxpopup + */ +EAPI Evas_Object * +elm_ctxpopup_content_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Widget_Data *wd; + Evas_Object *content; + + wd = elm_widget_data_get(obj); + if (!wd) + return NULL; + + content = wd->content; + if (!content) + return NULL; + + edje_object_part_unswallow(wd->base, content); + elm_widget_sub_object_del(obj, content); + evas_object_event_callback_del(content, EVAS_CALLBACK_DEL, _content_del); + edje_object_signal_emit(wd->base, "elm,state,content,disable", "elm"); + + wd->content = NULL; + + return content; +} + +/** + * Set the direction priority of a ctxpopup. + * This functions gives a chance to user to set the priority of ctxpopup showing direction. + * + * @param obj Ctxpopup object + * @param first 1st priority of direction + * @param second 2nd priority of direction + * @param third 3th priority of direction + * @param fourth 4th priority of direction + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_direction_priority_set(Evas_Object *obj, + Elm_Ctxpopup_Direction first, + Elm_Ctxpopup_Direction second, + Elm_Ctxpopup_Direction third, + Elm_Ctxpopup_Direction fourth) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + wd->dir_priority[0] = first; + wd->dir_priority[1] = second; + wd->dir_priority[2] = third; + wd->dir_priority[3] = fourth; + + if (wd->visible) + _sizing_eval(obj); +} + +/** + * Get the direction priority of a ctxpopup. + * + * @param obj Ctxpopup object + * @param first 1st priority of direction to be returned + * @param second 2nd priority of direction to be returned + * @param third 3th priority of direction to be returned + * @param fourth 4th priority of direction to be returned + * + * @see elm_ctxpopup_direction_priority_set for more information. + * + * @ingroup Ctxpopup + */ +EAPI void +elm_ctxpopup_direction_priority_get(Evas_Object *obj, + Elm_Ctxpopup_Direction *first, + Elm_Ctxpopup_Direction *second, + Elm_Ctxpopup_Direction *third, + Elm_Ctxpopup_Direction *fourth) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (first) + *first = wd->dir_priority[0]; + if (second) + *second = wd->dir_priority[1]; + if (third) + *third = wd->dir_priority[2]; + if (fourth) + *fourth = wd->dir_priority[3]; +} diff --git a/src/lib/elc_fileselector.c b/src/lib/elc_fileselector.c new file mode 100644 index 0000000..2cf3010 --- /dev/null +++ b/src/lib/elc_fileselector.c @@ -0,0 +1,1052 @@ +/** + * @defgroup Fileselector Fileselector + * + * A fileselector is a widget that allows a user to navigate through a + * tree of files. It contains buttons for Home(~) and Up(..) as well + * as cancel/ok buttons to confirm/cancel a selection. This widget is + * currently very much in progress. + * + * TODO + * child elements focusing support + * userdefined icon/label cb + * show/hide/add buttons ??? + * show/Hide hidden files + * double click to choose a file + * multiselection + * make variable/function names that are sensible + * Filter support + * + * Signals that you can add callbacks for are: + * + * "selected" - the user clicks on a file + * "directory,open" - the list is populated with new content. + * event_info is a directory. + * "done" - the user clicks on the ok or cancel button + */ + +#include +#include "elm_priv.h" + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *edje; + Evas_Object *filename_entry; + Evas_Object *path_entry; + Evas_Object *files_list; + Evas_Object *files_grid; + Evas_Object *up_button; + Evas_Object *home_button; + + Evas_Object *ok_button; + Evas_Object *cancel_button; + + const char *path; + const char *selection; + Ecore_Idler *sel_idler; + + const char *path_separator; + + Elm_Fileselector_Mode mode; + + Eina_Bool only_folder : 1; + Eina_Bool expand : 1; +}; + +struct sel_data +{ + Evas_Object *fs; + const char *path; +}; + +Elm_Genlist_Item_Class list_itc; +Elm_Gengrid_Item_Class grid_itc; + +static const char *widtype = NULL; + +static const char SIG_DIRECTORY_OPEN[] = "directory,open"; +static const char SIG_DONE[] = "done"; +static const char SIG_SELECTED[] = "selected"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_DIRECTORY_OPEN, "s"}, + {SIG_DONE, "s"}, + {SIG_SELECTED, "s"}, + {NULL, NULL} +}; + +static void _populate(Evas_Object *obj, + const char *path, + Elm_Genlist_Item *parent); +static void _do_anchors(Evas_Object *obj, + const char *path); + +/*** ELEMENTARY WIDGET ***/ +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd; + void *sd; + + wd = elm_widget_data_get(obj); + if (!wd) return; + + if (wd->path) eina_stringshare_del(wd->path); + if (wd->selection) eina_stringshare_del(wd->selection); + if (wd->sel_idler) + { + sd = ecore_idler_del(wd->sel_idler); + free(sd); + } + free(wd); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->edje, &minw, &minh, minw, minh); + evas_object_size_hint_min_set(obj, minw, minh); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const char *style = elm_widget_style_get(obj); + const char *data; + char buf[1024]; + + if (!wd) return; + _elm_theme_object_set(obj, wd->edje, "fileselector", "base", style); + + if (elm_object_disabled_get(obj)) + edje_object_signal_emit(wd->edje, "elm,state,disabled", "elm"); + + data = edje_object_data_get(wd->edje, "path_separator"); + if (data) + wd->path_separator = data; + else + wd->path_separator = "/"; + + if (!style) style = "default"; + snprintf(buf, sizeof(buf), "fileselector/%s", style); + +#define SWALLOW(part_name, object_ptn) \ + if (object_ptn) \ + { \ + elm_widget_style_set(object_ptn, buf); \ + if (edje_object_part_swallow(wd->edje, part_name, object_ptn)) \ + evas_object_show(object_ptn); \ + else \ + evas_object_hide(object_ptn); \ + } + SWALLOW("elm.swallow.up", wd->up_button); + SWALLOW("elm.swallow.home", wd->home_button); + + if (wd->mode == ELM_FILESELECTOR_LIST) + { + if (edje_object_part_swallow(wd->edje, "elm.swallow.files", + wd->files_list)) + { + evas_object_show(wd->files_list); + evas_object_hide(wd->files_grid); + } + else + evas_object_hide(wd->files_list); + } + else + { + if (edje_object_part_swallow(wd->edje, "elm.swallow.files", + wd->files_grid)) + { + evas_object_show(wd->files_grid); + evas_object_hide(wd->files_list); + } + else + evas_object_hide(wd->files_grid); + } + + SWALLOW("elm.swallow.filename", wd->filename_entry); + SWALLOW("elm.swallow.path", wd->path_entry); + + snprintf(buf, sizeof(buf), "fileselector/actions/%s", style); + SWALLOW("elm.swallow.cancel", wd->cancel_button); + SWALLOW("elm.swallow.ok", wd->ok_button); +#undef SWALLOW + + edje_object_message_signal_process(wd->edje); + edje_object_scale_set + (wd->edje, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +/*** GENLIST "MODEL" ***/ +static char * +_itc_label_get(void *data, + Evas_Object *obj __UNUSED__, + const char *source __UNUSED__) +{ + return strdup(ecore_file_file_get(data)); /* NOTE this will be + * free() by the + * caller */ +} + +static Evas_Object * +_itc_icon_get(void *data, + Evas_Object *obj, + const char *source) +{ + Evas_Object *ic; + + if (!strcmp(source, "elm.swallow.icon")) + { + ic = elm_icon_add(obj); + if (ecore_file_is_dir((char *)data)) + elm_icon_standard_set(ic, "folder"); + else + elm_icon_standard_set(ic, "file"); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, + 1, 1); + evas_object_show(ic); + return ic; + } + return NULL; +} + +static Eina_Bool +_itc_state_get(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + const char *source __UNUSED__) +{ + return EINA_FALSE; +} + +static void +_itc_del(void *data, + Evas_Object *obj __UNUSED__) +{ + eina_stringshare_del(data); +} + +static void +_expand_done(void *data, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = event_info; + const char *path = elm_genlist_item_data_get(it); + _populate(data, path, it); +} + +static void +_contract_done(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_subitems_clear(it); +} + +static void +_expand_req(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, 1); +} + +static void +_contract_req(void *data __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = event_info; + elm_genlist_item_expanded_set(it, 0); +} + +/*** PRIVATES ***/ +static Eina_Bool +_sel_do(void *data) +{ + struct sel_data *sd; + const char *path; + Widget_Data *wd; + const char *p; + + sd = data; + wd = elm_widget_data_get(sd->fs); + path = sd->path; + + if ((!wd->only_folder) && ecore_file_is_dir(path)) + { + if (wd->expand && wd->mode == ELM_FILESELECTOR_LIST) + { + _do_anchors(sd->fs, path); + elm_scrolled_entry_entry_set(wd->filename_entry, ""); + } + else + { + /* keep a ref to path 'couse it will be destroyed by _populate */ + p = eina_stringshare_add(path); + _populate(sd->fs, p, NULL); + eina_stringshare_del(p); + } + goto end; + } + else /* navigating through folders only or file is not a dir. */ + { + if (wd->expand && wd->mode == ELM_FILESELECTOR_LIST) + _do_anchors(sd->fs, path); + else if (wd->only_folder) + { + /* keep a ref to path 'couse it will be destroyed by _populate */ + p = eina_stringshare_add(path); + _populate(sd->fs, p, NULL); + eina_stringshare_del(p); + } + elm_scrolled_entry_entry_set(wd->filename_entry, + ecore_file_file_get(path)); + } + + evas_object_smart_callback_call(sd->fs, SIG_SELECTED, (void *)path); + +end: + wd->sel_idler = NULL; + free(sd); + return ECORE_CALLBACK_CANCEL; +} + +static void +_sel(void *data, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + struct sel_data *sd; + Widget_Data *wd; + void *old_sd; + char *dir; + + wd = elm_widget_data_get(data); + if (!wd) return; + + sd = malloc(sizeof(*sd)); + sd->fs = data; + sd->path = wd->mode == ELM_FILESELECTOR_LIST ? + elm_genlist_item_data_get(event_info) : + elm_gengrid_item_data_get(event_info); + + if (!sd->path) + { + eina_stringshare_replace(&wd->path, ""); + goto end; + } + + dir = wd->only_folder ? strdup(sd->path) : ecore_file_dir_get(sd->path); + if (dir) + { + eina_stringshare_replace(&wd->path, dir); + free(dir); + } + else + { + eina_stringshare_replace(&wd->path, ""); + } + +end: + if (wd->sel_idler) + { + old_sd = ecore_idler_del(wd->sel_idler); + free(old_sd); + } + wd->sel_idler = ecore_idler_add(_sel_do, sd); +} + +static void +_up(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + char *parent; + + Widget_Data *wd = elm_widget_data_get(fs); + if (!wd) return; + parent = ecore_file_dir_get(wd->path); + _populate(fs, parent, NULL); + free(parent); +} + +static void +_home(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + _populate(fs, getenv("HOME"), NULL); +} + +static void +_ok(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + evas_object_smart_callback_call(fs, SIG_DONE, + (void *)elm_fileselector_selected_get(fs)); +} + +static void +_canc(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *fs = data; + evas_object_smart_callback_call(fs, SIG_DONE, NULL); +} + +static void +_anchor_clicked(void *data, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Evas_Object *fs = data; + Widget_Data *wd = elm_widget_data_get(fs); + Elm_Entry_Anchor_Info *info = event_info; + const char *p; + if (!wd) return; + // keep a ref to path 'couse it will be destroyed by _populate + p = eina_stringshare_add(info->name); + _populate(fs, p, NULL); + evas_object_smart_callback_call(data, SIG_SELECTED, (void *)p); + eina_stringshare_del(p); +} + +static void +_do_anchors(Evas_Object *obj, + const char *path) +{ + Widget_Data *wd = elm_widget_data_get(obj); + char **tok, buf[PATH_MAX * 3]; + int i, j; + if (!wd) return; + buf[0] = '\0'; + tok = eina_str_split(path, "/", 0); + eina_strlcat(buf, "root", sizeof(buf)); + for (i = 0; tok[i]; i++) + { + if ((!tok[i]) || (!tok[i][0])) continue; + eina_strlcat(buf, wd->path_separator, sizeof(buf)); + eina_strlcat(buf, "", sizeof(buf)); + eina_strlcat(buf, tok[i], sizeof(buf)); + eina_strlcat(buf, "", sizeof(buf)); + } + free(tok[0]); + free(tok); + + elm_scrolled_entry_entry_set(wd->path_entry, buf); +} + +static void +_populate(Evas_Object *obj, + const char *path, + Elm_Genlist_Item *parent) +{ + Widget_Data *wd = elm_widget_data_get(obj); + DIR *dir; + struct dirent *dp; + char buf[PATH_MAX]; + char *real; + Eina_List *files = NULL, *dirs = NULL, *l; + + if ((!wd) || (!ecore_file_is_dir(path))) return; + dir = opendir(path); + if (!dir) return; + evas_object_smart_callback_call(obj, SIG_DIRECTORY_OPEN, (void *)path); + if (!parent) + { + elm_genlist_clear(wd->files_list); + elm_gengrid_clear(wd->files_grid); + eina_stringshare_replace(&wd->path, path); + _do_anchors(obj, path); + } + + if (wd->filename_entry) elm_scrolled_entry_entry_set(wd->filename_entry, ""); + while ((dp = readdir(dir))) + { + if (dp->d_name[0] == '.') continue; // TODO make this configurable + + snprintf(buf, sizeof(buf), "%s/%s", path, dp->d_name); + real = ecore_file_realpath(buf); /* TODO: this will resolv + * symlinks...I dont like + * it*/ + if (ecore_file_is_dir(real)) + dirs = eina_list_append(dirs, real); + else if (!wd->only_folder) + files = eina_list_append(files, real); + } + closedir(dir); + + files = eina_list_sort(files, eina_list_count(files), + EINA_COMPARE_CB(strcoll)); + dirs = eina_list_sort(dirs, eina_list_count(dirs), EINA_COMPARE_CB(strcoll)); + EINA_LIST_FOREACH(dirs, l, real) + { + if (wd->mode == ELM_FILESELECTOR_LIST) + elm_genlist_item_append(wd->files_list, &list_itc, + eina_stringshare_add(real), /* item data */ + parent, + wd->expand ? ELM_GENLIST_ITEM_SUBITEMS : + ELM_GENLIST_ITEM_NONE, + NULL, NULL); + else if (wd->mode == ELM_FILESELECTOR_GRID) + elm_gengrid_item_append(wd->files_grid, &grid_itc, + eina_stringshare_add(real), /* item data */ + NULL, NULL); + + free(real); + } + eina_list_free(dirs); + + EINA_LIST_FOREACH(files, l, real) + { + if (wd->mode == ELM_FILESELECTOR_LIST) + elm_genlist_item_append(wd->files_list, &list_itc, + eina_stringshare_add(real), /* item data */ + parent, ELM_GENLIST_ITEM_NONE, + NULL, NULL); + else if (wd->mode == ELM_FILESELECTOR_GRID) + elm_gengrid_item_append(wd->files_grid, &grid_itc, + eina_stringshare_add(real), /* item data */ + NULL, NULL); + free(real); + } + eina_list_free(files); +} + +/*** API ***/ + +/** + * Add a new Fileselector object + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Fileselector + */ +EAPI Evas_Object * +elm_fileselector_add(Evas_Object *parent) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + Evas *e = evas_object_evas_get(parent); + if (!e) return NULL; + Evas_Object *obj, *ic, *bt, *li, *en, *grid; + Widget_Data *wd; + int s; + + // Elementary Widget + wd = ELM_NEW(Widget_Data); + wd->expand = !!_elm_config->fileselector_expand_enable; + obj = elm_widget_add(evas_object_evas_get(parent)); + ELM_SET_WIDTYPE(widtype, "fileselector"); + elm_widget_type_set(obj, "fileselector"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->edje = edje_object_add(e); + _elm_theme_object_set(obj, wd->edje, "fileselector", "base", "default"); + elm_widget_resize_object_set(obj, wd->edje); + + // up btn + ic = elm_icon_add(parent); + elm_icon_standard_set(ic, "arrow_up"); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + bt = elm_button_add(parent); + elm_button_icon_set(bt, ic); + elm_button_label_set(bt, "Up"); + evas_object_size_hint_align_set(bt, 0.0, 0.0); + + evas_object_smart_callback_add(bt, "clicked", _up, obj); + + elm_widget_sub_object_add(obj, bt); + wd->up_button = bt; + + // home btn + ic = elm_icon_add(parent); + elm_icon_standard_set(ic, "home"); + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + bt = elm_button_add(parent); + elm_button_icon_set(bt, ic); + elm_button_label_set(bt, "Home"); + evas_object_size_hint_align_set(bt, 0.0, 0.0); + + evas_object_smart_callback_add(bt, "clicked", _home, obj); + + elm_widget_sub_object_add(obj, bt); + wd->home_button = bt; + + list_itc.item_style = grid_itc.item_style = "default"; + list_itc.func.label_get = grid_itc.func.label_get = _itc_label_get; + list_itc.func.icon_get = grid_itc.func.icon_get = _itc_icon_get; + list_itc.func.state_get = grid_itc.func.state_get = _itc_state_get; + list_itc.func.del = grid_itc.func.del = _itc_del; + + li = elm_genlist_add(parent); + evas_object_size_hint_align_set(li, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(li, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_min_set(li, 100, 100); + + grid = elm_gengrid_add(parent); + evas_object_size_hint_align_set(grid, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(grid, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + s = elm_finger_size_get() * 2; + elm_gengrid_item_size_set(grid, s, s); + elm_gengrid_align_set(grid, 0.0, 0.0); + + evas_object_smart_callback_add(li, "selected", _sel, obj); + evas_object_smart_callback_add(li, "expand,request", _expand_req, obj); + evas_object_smart_callback_add(li, "contract,request", _contract_req, obj); + evas_object_smart_callback_add(li, "expanded", _expand_done, obj); + evas_object_smart_callback_add(li, "contracted", _contract_done, obj); + + evas_object_smart_callback_add(grid, "selected", _sel, obj); + + elm_widget_sub_object_add(obj, li); + elm_widget_sub_object_add(obj, grid); + wd->files_list = li; + wd->files_grid = grid; + + // path entry + en = elm_scrolled_entry_add(parent); + elm_scrolled_entry_editable_set(en, EINA_FALSE); + elm_scrolled_entry_single_line_set(en, EINA_TRUE); + elm_scrolled_entry_line_char_wrap_set(en, EINA_TRUE); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + + evas_object_smart_callback_add(en, "anchor,clicked", _anchor_clicked, obj); + + elm_widget_sub_object_add(obj, en); + wd->path_entry = en; + + // filename entry + en = elm_scrolled_entry_add(parent); + elm_scrolled_entry_editable_set(en, EINA_TRUE); + elm_scrolled_entry_single_line_set(en, EINA_TRUE); + elm_scrolled_entry_line_char_wrap_set(en, EINA_TRUE); + evas_object_size_hint_weight_set(en, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(en, EVAS_HINT_FILL, EVAS_HINT_FILL); + + elm_widget_sub_object_add(obj, en); + wd->filename_entry = en; + + elm_fileselector_buttons_ok_cancel_set(obj, EINA_TRUE); + elm_fileselector_is_save_set(obj, EINA_FALSE); + + _theme_hook(obj); + + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * This enables/disables the file name entry box where the user can + * type in a name for the file to be saved as. + * + * @param obj The fileselector object + * @param is_save If true, the fileselector is a save dialog + * + * @ingroup Fileselector + */ +EAPI void +elm_fileselector_is_save_set(Evas_Object *obj, + Eina_Bool is_save) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + elm_object_disabled_set(wd->filename_entry, is_save); + + if (is_save) + edje_object_signal_emit(wd->edje, "elm,state,save,on", "elm"); + else + edje_object_signal_emit(wd->edje, "elm,state,save,off", "elm"); +} + +/** + * This returns whether the fileselector is a "save" type fileselector + * + * @param obj The fileselector object + * @return If true, the fileselector is a save type. + * + * @ingroup Fileselector + */ +EAPI Eina_Bool +elm_fileselector_is_save_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_object_disabled_get(wd->filename_entry); +} + +/** + * This enables/disables folder-only view in the fileselector. + * + * @param obj The fileselector object + * @param only If true, the fileselector will only display directories. + * If false, files are displayed also. + * + * @ingroup Fileselector + */ +EAPI void +elm_fileselector_folder_only_set(Evas_Object *obj, + Eina_Bool only) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->only_folder == only) return; + wd->only_folder = !!only; + if (wd->path) _populate(obj, wd->path, NULL); +} + +/** + * This gets the state of file display in the fileselector. + * + * @param obj The fileselector object + * @return If true, files are not being shown in the fileselector. + * If false, files are being shown. + * + * @ingroup Fileselector + */ +EAPI Eina_Bool +elm_fileselector_folder_only_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->only_folder; +} + +/** + * This enables/disables the ok,cancel buttons. + * + * @param obj The fileselector object + * @param only If true, a box containing ok and cancel buttons is created. + * If false, the box and the buttons are destroyed. + * + * @ingroup Fileselector + */ +EAPI void +elm_fileselector_buttons_ok_cancel_set(Evas_Object *obj, + Eina_Bool visible) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *bt; + if (!wd) return; + + if (visible) + { + // cancel btn + bt = elm_button_add(obj); + elm_button_label_set(bt, "Cancel"); + + evas_object_smart_callback_add(bt, "clicked", _canc, obj); + + elm_widget_sub_object_add(obj, bt); + wd->cancel_button = bt; + + // ok btn + bt = elm_button_add(obj); + elm_button_label_set(bt, "OK"); + + evas_object_smart_callback_add(bt, "clicked", _ok, obj); + + elm_widget_sub_object_add(obj, bt); + wd->ok_button = bt; + + _theme_hook(obj); + } + else + { + evas_object_del(wd->cancel_button); + wd->cancel_button = NULL; + evas_object_del(wd->ok_button); + wd->ok_button = NULL; + } +} + +/** + * This gets the state of the box containing ok and cancel buttons. + * + * @param obj The fileselector object + * @return If true, the box exists. + * If false, the box does not exist. + * + * @ingroup Fileselector + */ +EAPI Eina_Bool +elm_fileselector_buttons_ok_cancel_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->ok_button ? EINA_TRUE : EINA_FALSE; +} + +/** + * This enables a tree view in the fileselector, if in @c + * ELM_FILESELECTOR_LIST mode. If it's in other mode, the changes + * made by this function will only be visible when one switches back + * to list mode. + * + * @param obj The fileselector object + * @param expand If true, tree view is enabled. + * If false, tree view is disabled. + * + * In a tree view, arrows are created on the sides of directories, + * allowing them to expand in place. + * + * @ingroup Fileselector + */ +EAPI void +elm_fileselector_expandable_set(Evas_Object *obj, + Eina_Bool expand) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) return; + + wd->expand = !!expand; + + if (wd->path) _populate(obj, wd->path, NULL); +} + +/** + * This gets the state of tree view in the fileselector. + * + * @param obj The fileselector object + * @return If true, tree view is enabled and folders will be expandable. + * If false, tree view is disabled. + * + * @ingroup Fileselector + */ +EAPI Eina_Bool +elm_fileselector_expandable_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->expand; +} + +/** + * This sets the path that the fileselector will display. + * + * @param obj The fileselector object + * @param path The path of the fileselector + * + * @ingroup Fileselector + */ +EAPI void +elm_fileselector_path_set(Evas_Object *obj, + const char *path) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + _populate(obj, path, NULL); +} + +/** + * This gets the path that the fileselector displays. + * + * @param obj The fileselector object + * @return The path that the fileselector is displaying + * + * @ingroup Fileselector + */ +EAPI const char * +elm_fileselector_path_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->path; +} + +/** + * This sets the mode in which the fileselector will display files. + * + * @param obj The fileselector object + + * @param mode The mode of the fileselector, being it one of @c + * ELM_FILESELECTOR_LIST (default) or @c ELM_FILESELECTOR_GRID. The + * first one, naturally, will display the files in a list. By using + * elm_fileselector_expandable_set(), the user will trigger a tree + * view for that list. The latter will make the widget to display its + * entries in a grid form. + * + * @see elm_fileselector_expandable_set(). + * + * @ingroup Fileselector + */ +EAPI void +elm_fileselector_mode_set(Evas_Object *obj, + Elm_Fileselector_Mode mode) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (mode == wd->mode) return; + + if (mode == ELM_FILESELECTOR_LIST) + { + if (edje_object_part_swallow(wd->edje, "elm.swallow.files", + wd->files_list)) + { + evas_object_show(wd->files_list); + evas_object_hide(wd->files_grid); + } + else + evas_object_hide(wd->files_list); + } + else + { + if (edje_object_part_swallow(wd->edje, "elm.swallow.files", + wd->files_grid)) + { + evas_object_show(wd->files_grid); + evas_object_hide(wd->files_list); + } + else + evas_object_hide(wd->files_grid); + } + + wd->mode = mode; + + _populate(obj, wd->path, NULL); +} + +/** + * This gets the mode in which the fileselector is displaying files. + * + * @param obj The fileselector object + * @return The mode in which the fileselector is at + * + * @ingroup Fileselector + */ +EAPI Elm_Fileselector_Mode +elm_fileselector_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_FILESELECTOR_LAST; + + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_FILESELECTOR_LAST; + + return wd->mode; +} + +/** + * This gets the currently selected path in the file selector. + * + * @param obj The file selector object + * @return The absolute path of the selected object in the fileselector + * + * @ingroup Fileselector + */ +EAPI const char * +elm_fileselector_selected_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + if (wd->filename_entry) + { + const char *name; + char buf[PATH_MAX]; + + name = elm_scrolled_entry_entry_get(wd->filename_entry); + snprintf(buf, sizeof(buf), "%s/%s", + wd->only_folder ? ecore_file_dir_get(wd->path) : wd->path, + name); + eina_stringshare_replace(&wd->selection, buf); + return wd->selection; + } + + if (wd->mode == ELM_FILESELECTOR_LIST) + { + Elm_Genlist_Item *it; + it = elm_genlist_selected_item_get(wd->files_list); + if (it) return elm_genlist_item_data_get(it); + } + else + { + Elm_Gengrid_Item *it; + it = elm_gengrid_selected_item_get(wd->files_grid); + if (it) return elm_gengrid_item_data_get(it); + } + + return wd->path; +} + +/** + * This sets the currently selected path in the file selector. + * + * @param obj The file selector object + * @param path The path to a file or directory + * @return @c EINA_TRUE on success, @c EINA_FALSE on failure. The + * latter case occurs if the directory or file pointed to do not + * exist. + * + * @ingroup Fileselector + */ +EAPI Eina_Bool +elm_fileselector_selected_set(Evas_Object *obj, + const char *path) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + + if (ecore_file_is_dir(path)) + _populate(obj, path, NULL); + else + { + if (!ecore_file_exists(path)) + return EINA_FALSE; + + _populate(obj, ecore_file_dir_get(path), NULL); + if (wd->filename_entry) + { + elm_scrolled_entry_entry_set(wd->filename_entry, + ecore_file_file_get(path)); + eina_stringshare_replace(&wd->selection, path); + } + } + + return EINA_TRUE; +} + diff --git a/src/lib/elc_fileselector_button.c b/src/lib/elc_fileselector_button.c new file mode 100644 index 0000000..dbdeeb2 --- /dev/null +++ b/src/lib/elc_fileselector_button.c @@ -0,0 +1,683 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup File_Selector_Button File Selector Button + * + * A button that, when clicked, creates an Elementary window (or inner + * window) with an Elementary File Selector within. When a file is + * chosen, the (inner) window is closed and the selected file is + * exposed as an evas_object_smart_callback_call() of the button. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *self, *btn, *fs, *fsw; + const char *window_title; + Evas_Coord w, h; + struct + { + const char *path; + Eina_Bool expandable : 1; + Eina_Bool folder_only : 1; + Eina_Bool is_save : 1; + } fsd; + Eina_Bool inwin_mode : 1; +}; + +#define DEFAULT_WINDOW_TITLE "Select a file" + +static const char *widtype = NULL; + +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, + Evas *e, + Evas_Object *obj, + void *event_info); +static void _on_focus_hook(void *data, + Evas_Object *obj); +static void _selection_done(void *data, + Evas_Object *obj, + void *event_info); +static void _activate(Widget_Data *wd); + +static const char SIG_FILE_CHOSEN[] = "file,chosen"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_FILE_CHOSEN, "s"}, + {NULL, NULL} +}; + +static void +_del_hook(Evas_Object *obj) +{ + Evas_Object *win; + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) return; + + if (wd->window_title) eina_stringshare_del(wd->window_title); + if (wd->fsd.path) eina_stringshare_del(wd->fsd.path); + if (wd->fs) + { + win = evas_object_data_del(obj, "win"); + evas_object_del(win); + } + free(wd); +} + +static void +_on_focus_hook(void *data __UNUSED__, + Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + elm_widget_focus_steal(wd->btn); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + char buf[4096]; + if (!wd) return; + snprintf(buf, sizeof(buf), "fileselector_button/%s", + elm_widget_style_get(obj)); + elm_object_style_set(wd->btn, buf); + _sizing_eval(obj); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_widget_disabled_set(wd->btn, elm_widget_disabled_get(obj)); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + evas_object_size_hint_min_get(wd->btn, &minw, &minh); + evas_object_size_hint_max_get(wd->btn, &maxw, &maxh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_changed_size_hints(void *data, + Evas *e __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + _sizing_eval(data); +} + +static void +_activate_hook(Evas_Object *obj) +{ + Widget_Data *wd; + wd = elm_widget_data_get(obj); + if (!wd) return; + _activate(wd); +} + +static void +_button_clicked(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + _activate(data); +} + +static Evas_Object * +_parent_win_get(Evas_Object *obj) +{ + while ((obj) && (strcmp(elm_widget_type_get(obj), "win"))) + obj = elm_object_parent_widget_get(obj); + + return obj; +} + +static Evas_Object * +_new_window_add(Widget_Data *wd) +{ + Evas_Object *win, *bg; + + win = elm_win_add(NULL, "fileselector_button", ELM_WIN_DIALOG_BASIC); + elm_win_title_set(win, wd->window_title); + elm_win_autodel_set(win, EINA_TRUE); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + evas_object_resize(win, wd->w, wd->h); + return win; +} + +static void +_activate(Widget_Data *wd) +{ + Eina_Bool is_inwin = EINA_FALSE; + + if (wd->fs) return; + + if (wd->inwin_mode) + { + wd->fsw = _parent_win_get(wd->self); + + if (!wd->fsw) + wd->fsw = _new_window_add(wd); + else + { + wd->fsw = elm_win_inwin_add(wd->fsw); + is_inwin = EINA_TRUE; + } + } + else + wd->fsw = _new_window_add(wd); + + wd->fs = elm_fileselector_add(wd->fsw); + elm_fileselector_expandable_set(wd->fs, wd->fsd.expandable); + elm_fileselector_folder_only_set(wd->fs, wd->fsd.folder_only); + elm_fileselector_is_save_set(wd->fs, wd->fsd.is_save); + elm_fileselector_selected_set(wd->fs, wd->fsd.path); + evas_object_size_hint_weight_set(wd->fs, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(wd->fs, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_smart_callback_add(wd->fs, "done", _selection_done, wd); + evas_object_show(wd->fs); + + if (is_inwin) + { + elm_win_inwin_content_set(wd->fsw, wd->fs); + elm_win_inwin_activate(wd->fsw); + } + else + { + elm_win_resize_object_add(wd->fsw, wd->fs); + evas_object_show(wd->fsw); + } +} + +static void +_selection_done(void *data, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + const char *file = event_info; + Widget_Data *wd = data; + Evas_Object *del; + if (!wd) return; + + if (file) eina_stringshare_replace(&wd->fsd.path, file); + + del = wd->fsw; + wd->fs = NULL; + wd->fsw = NULL; + evas_object_del(del); + + evas_object_smart_callback_call(wd->self, SIG_FILE_CHOSEN, + (void *)wd->fsd.path); +} + +/** + * Add a new file selector button into the parent object. + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup File_Selector_Button + */ +EAPI Evas_Object * +elm_fileselector_button_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + wd->window_title = eina_stringshare_add(DEFAULT_WINDOW_TITLE); + wd->fsd.path = eina_stringshare_add(getenv("HOME")); + wd->fsd.expandable = _elm_config->fileselector_expand_enable; + wd->inwin_mode = _elm_config->inwin_dialogs_enable; + wd->w = 400; + wd->h = 400; + + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "fileselector_button"); + elm_widget_type_set(obj, "fileselector_button"); + elm_widget_sub_object_add(parent, obj); + wd->self = obj; + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_activate_hook_set(obj, _activate_hook); + + wd->btn = elm_button_add(parent); + elm_widget_resize_object_set(obj, wd->btn); + evas_object_event_callback_add(wd->btn, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + evas_object_smart_callback_add(wd->btn, "clicked", _button_clicked, wd); + elm_widget_sub_object_add(obj, wd->btn); + + _theme_hook(obj); + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the label used in the file selector button. + * + * @param obj The button object + * @param label The text label text to be displayed on the button + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_label_set(Evas_Object *obj, + const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_button_label_set(wd->btn, label); +} + +/** + * Get the label used in the file selector button. + * + * @param obj The button object + * @return The button label + * + * @ingroup File_Selector_Button + */ +EAPI const char * +elm_fileselector_button_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_button_label_get(wd->btn); +} + +/** + * Set the title of the file selector button's window. + * + * @param obj The button object + * @param title The title string + * + * Note that it will only take any effect if the fileselector button + * not at "inwin mode". + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_window_title_set(Evas_Object *obj, + const char *title) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + eina_stringshare_replace(&wd->window_title, title); + + if (wd->fsw) + elm_win_title_set(wd->fsw, wd->window_title); +} + +/** + * Get the title of the file selector button's window. + * + * @param obj The button object + * @return Title of the file selector button's window + * + * @ingroup File_Selector_Button + */ +EAPI const char * +elm_fileselector_button_window_title_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return NULL; + return wd->window_title; +} + +/** + * Set the size of the file selector button's window. + * + * @param obj The button object + * @param width The width + * @param height The height + * + * Note that it will only take any effect if the fileselector button not at + * "inwin mode". Default size for the window (when applicable) is 400x400. + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_window_size_set(Evas_Object *obj, + Evas_Coord width, + Evas_Coord height) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->w = width; + wd->h = height; + + if (wd->fsw) + evas_object_resize(wd->fsw, wd->w, wd->h); +} + +/** + * Get the size of the file selector button's window. + * + * @param obj The button object + * @param width Pointer into which to store the width value + * @param height Pointer into which to store the height value + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_window_size_get(const Evas_Object *obj, + Evas_Coord *width, + Evas_Coord *height) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + if (width) *width = wd->w; + if (height) *height = wd->h; +} + +/** + * Set the starting path of the file selector button's window. + * + * @param obj The button object + * @param path The path string + * + * It must be a directory path. + * Default path is "HOME" environment variable's value. + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_path_set(Evas_Object *obj, + const char *path) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + eina_stringshare_replace(&wd->fsd.path, path); + + if (wd->fs) + elm_fileselector_selected_set(wd->fs, wd->fsd.path); +} + +/** + * Get the last path of the file selector button's window. + * + * @param obj The button object + * + * @ingroup File_Selector_Button + */ +EAPI const char * +elm_fileselector_button_path_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->fsd.path; +} + +/** + * Set whether the button's file selector is to present itself as an + * Elementary Generic List (which will expand its entries for nested + * directories) or as canonical list, which will be rendered again + * with the contents of each selected directory. + * + * @param obj The button object + * @param value The expandable flag + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_expandable_set(Evas_Object *obj, + Eina_Bool value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->fsd.expandable = value; + + if (wd->fs) + elm_fileselector_expandable_set(wd->fs, wd->fsd.expandable); +} + +/** + * Get the button's file selector expandable flag. + * + * @param obj The button object + * @return value The expandable flag + * + * @ingroup File_Selector_Button + */ +EAPI Eina_Bool +elm_fileselector_button_expandable_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->fsd.expandable; +} + +/** + * Set whether the button's file selector list is to display folders + * only or the directory contents, as well. + * + * @param obj The button object + * @param value The "folder only" flag + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_folder_only_set(Evas_Object *obj, + Eina_Bool value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->fsd.folder_only = value; + + if (wd->fs) + elm_fileselector_folder_only_set(wd->fs, wd->fsd.folder_only); +} + +/** + * Get the button's file selector "folder only" flag. + * + * @param obj The button object + * @return value The "folder only" flag + * + * @ingroup File_Selector_Button + */ +EAPI Eina_Bool +elm_fileselector_button_folder_only_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->fsd.folder_only; +} + +/** + * Set whether the button's file selector has an editable text entry + * which will hold its current selection. + * + * @param obj The button object + * @param value The "is save" flag + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_is_save_set(Evas_Object *obj, + Eina_Bool value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->fsd.is_save = value; + + if (wd->fs) + elm_fileselector_is_save_set(wd->fs, wd->fsd.is_save); +} + +/** + * Get the button's file selector "is save" flag. + * + * @param obj The button object + * @return value The "is save" flag + * + * @ingroup File_Selector_Button + */ +EAPI Eina_Bool +elm_fileselector_button_is_save_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->fsd.is_save; +} + +/** + * Set whether the button's file selector will raise an Elementary + * Inner Window, instead of a dedicated Elementary Window. By default, + * it won't. + * + * @param obj The button object + * @param value The "inwin mode" flag + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_inwin_mode_set(Evas_Object *obj, + Eina_Bool value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->inwin_mode = value; +} + +/** + * Get the button's file selector "inwin mode" flag. + * + * @param obj The button object + * @return value The "inwin mode" flag + * + * @ingroup File_Selector_Button + */ +EAPI Eina_Bool +elm_fileselector_button_inwin_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->inwin_mode; +} + +/** + * Set the icon used for the button + * + * Once the icon object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_fileselector_button_icon_unset() function. + * + * @param obj The button object + * @param icon The icon object for the button + * + * @ingroup File_Selector_Button + */ +EAPI void +elm_fileselector_button_icon_set(Evas_Object *obj, + Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + { + evas_object_del(icon); + return; + } + elm_button_icon_set(wd->btn, icon); +} + +/** + * Get the icon used for the button + * + * @param obj The button object + * @return The icon object that is being used + * + * @ingroup File_Selector_Button + */ +EAPI Evas_Object * +elm_fileselector_button_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_button_icon_get(wd->btn); +} + +/** + * Unset the icon used for the button + * + * Unparent and return the icon object which was set for this widget. + * + * @param obj The button object + * @return The icon object that was being used + * + * @ingroup File_Selector_Button + */ +EAPI Evas_Object * +elm_fileselector_button_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_button_icon_unset(wd->btn); +} + diff --git a/src/lib/elc_fileselector_entry.c b/src/lib/elc_fileselector_entry.c new file mode 100644 index 0000000..7b0ad6d --- /dev/null +++ b/src/lib/elc_fileselector_entry.c @@ -0,0 +1,655 @@ +#include +#include "elm_priv.h" + + /** + * @defgroup File_Selector_Entry File Selector Entry + * + * An entry that shows to enter/display path and have an associated + * button to allow selecting the file from a dialog. + * + * The button, when clicked, creates an Elementary window (or inner + * window) with an Elementary File Selector within. When a file is + * chosen, the (inner) window is closed and the selected file is + * exposed as an evas_object_smart_callback_call() of the button. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *edje; + Evas_Object *button; + Evas_Object *entry; +}; + +static const char *widtype = NULL; + +static const char SIG_CHANGED[] = "changed"; +static const char SIG_ACTIVATED[] = "activated"; +static const char SIG_PRESS[] = "press"; +static const char SIG_LONGPRESSED[] = "longpressed"; +static const char SIG_CLICKED[] = "clicked"; +static const char SIG_CLICKED_DOUBLE[] = "clicked,double"; +static const char SIG_FOCUSED[] = "focused"; +static const char SIG_UNFOCUSED[] = "unfocused"; +static const char SIG_SELECTION_PASTE[] = "selection,paste"; +static const char SIG_SELECTION_COPY[] = "selection,copy"; +static const char SIG_SELECTION_CUT[] = "selection,cut"; +static const char SIG_UNPRESSED[] = "unpressed"; +static const char SIG_FILE_CHOSEN[] = "file,chosen"; +static const Evas_Smart_Cb_Description _signals[] = +{ + {SIG_CHANGED, ""}, + {SIG_ACTIVATED, ""}, + {SIG_PRESS, ""}, + {SIG_LONGPRESSED, ""}, + {SIG_CLICKED, ""}, + {SIG_CLICKED_DOUBLE, ""}, + {SIG_FOCUSED, ""}, + {SIG_UNFOCUSED, ""}, + {SIG_SELECTION_PASTE, ""}, + {SIG_SELECTION_COPY, ""}, + {SIG_SELECTION_CUT, ""}, + {SIG_UNPRESSED, ""}, + {SIG_FILE_CHOSEN, "s"}, + {NULL, NULL} +}; + +#define SIG_FWD(name) \ +static void \ +_##name##_fwd(void *data, Evas_Object *obj __UNUSED__, void *event_info) \ +{ \ + evas_object_smart_callback_call(data, SIG_##name, event_info); \ +} +SIG_FWD(CHANGED) +SIG_FWD(PRESS) +SIG_FWD(LONGPRESSED) +SIG_FWD(CLICKED) +SIG_FWD(CLICKED_DOUBLE) +SIG_FWD(FOCUSED) +SIG_FWD(UNFOCUSED) +SIG_FWD(SELECTION_PASTE) +SIG_FWD(SELECTION_COPY) +SIG_FWD(SELECTION_CUT) +SIG_FWD(UNPRESSED) +#undef SIG_FWD + +static void +_FILE_CHOSEN_fwd(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + const char *file = event_info; + elm_scrolled_entry_entry_set(wd->entry, file); + evas_object_smart_callback_call(data, SIG_FILE_CHOSEN, event_info); +} + +static void +_ACTIVATED_fwd(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + const char *file = elm_scrolled_entry_entry_get(wd->entry); + elm_fileselector_button_path_set(wd->button, file); + evas_object_smart_callback_call(data, SIG_ACTIVATED, event_info); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + free(wd); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + if (!wd) return; + edje_object_size_min_calc(wd->edje, &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static Eina_Bool +_elm_fileselector_entry_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return EINA_FALSE; + + Evas_Object *chain[2]; + + /* Direction */ + if (dir == ELM_FOCUS_PREVIOUS) + { + chain[0] = wd->button; + chain[1] = wd->entry; + } + else if (dir == ELM_FOCUS_NEXT) + { + chain[0] = wd->entry; + chain[1] = wd->button; + } + else + return EINA_FALSE; + + unsigned char i = elm_widget_focus_get(chain[1]); + + if (elm_widget_focus_next_get(chain[i], dir, next)) + return EINA_TRUE; + + i = !i; + + Evas_Object *to_focus; + if (elm_widget_focus_next_get(chain[i], dir, &to_focus)) + { + *next = to_focus; + return !!i; + } + + return EINA_FALSE; +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const char *style = elm_widget_style_get(obj); + char buf[1024]; + + if (!wd) return; + _elm_theme_object_set(obj, wd->edje, "fileselector_entry", "base", style); + if (elm_object_disabled_get(obj)) + edje_object_signal_emit(wd->edje, "elm,state,disabled", "elm"); + + if (!style) style = "default"; + snprintf(buf, sizeof(buf), "fileselector_entry/%s", style); + elm_widget_style_set(wd->button, buf); + elm_widget_style_set(wd->entry, buf); + + edje_object_part_swallow(obj, "elm.swallow.button", wd->button); + edje_object_part_swallow(obj, "elm.swallow.entry", wd->entry); + + edje_object_message_signal_process(wd->edje); + edje_object_scale_set + (wd->edje, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Eina_Bool val = elm_widget_disabled_get(obj); + if (!wd) return; + if (val) + edje_object_signal_emit(wd->edje, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(wd->edje, "elm,state,enabled", "elm"); + + elm_widget_disabled_set(wd->button, val); + elm_widget_disabled_set(wd->entry, val); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +/** + * Add a new file selector entry into the parent object. + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup File_Selector_Entry + */ +EAPI Evas_Object * +elm_fileselector_entry_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e = evas_object_evas_get(parent); + if (!e) return NULL; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "fileselector_entry"); + elm_widget_type_set(obj, "fileselector_entry"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_focus_next_hook_set(obj, _elm_fileselector_entry_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + elm_widget_theme_hook_set(obj, _theme_hook); + + wd->edje = edje_object_add(e); + _elm_theme_object_set(obj, wd->edje, "fileselector_entry", "base", "default"); + elm_widget_resize_object_set(obj, wd->edje); + + wd->button = elm_fileselector_button_add(obj); + elm_widget_style_set(wd->button, "fileselector_entry/default"); + edje_object_part_swallow(wd->edje, "elm.swallow.button", wd->button); + elm_widget_sub_object_add(obj, wd->button); + evas_object_event_callback_add + (wd->button, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + elm_fileselector_button_expandable_set(wd->button, + _elm_config->fileselector_expand_enable); + +#define SIG_FWD(name) \ + evas_object_smart_callback_add(wd->button, SIG_##name, _##name##_fwd, obj) + SIG_FWD(CLICKED); + SIG_FWD(UNPRESSED); + SIG_FWD(FILE_CHOSEN); +#undef SIG_FWD + + wd->entry = elm_scrolled_entry_add(obj); + elm_widget_style_set(wd->entry, "fileselector_entry/default"); + elm_scrolled_entry_single_line_set(wd->entry, EINA_TRUE); + elm_scrolled_entry_editable_set(wd->entry, EINA_TRUE); + edje_object_part_swallow(wd->edje, "elm.swallow.entry", wd->entry); + elm_widget_sub_object_add(obj, wd->entry); + evas_object_event_callback_add + (wd->entry, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + +#define SIG_FWD(name) \ + evas_object_smart_callback_add(wd->entry, SIG_##name, _##name##_fwd, obj) + SIG_FWD(CHANGED); + SIG_FWD(ACTIVATED); + SIG_FWD(PRESS); + SIG_FWD(LONGPRESSED); + SIG_FWD(CLICKED); + SIG_FWD(CLICKED_DOUBLE); + SIG_FWD(FOCUSED); + SIG_FWD(UNFOCUSED); + SIG_FWD(SELECTION_PASTE); + SIG_FWD(SELECTION_COPY); + SIG_FWD(SELECTION_CUT); +#undef SIG_FWD + + _sizing_eval(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the label used in the file selector entry. + * + * @param obj The entry object + * @param label The text label text to be displayed on the entry + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_button_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_label_set(wd->button, label); +} + +EAPI const char * +elm_fileselector_entry_button_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_fileselector_button_label_get(wd->button); +} + +/** + * Set the path to start the entry's file selector with, when clicked. + * + * @param obj The entry object + * @param path Path to a file/directory + * + * Default path is "HOME" environment variable's value. + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_selected_set(Evas_Object *obj, const char *path) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_path_set(wd->button, path); +} + +/** + * Get the last path which the entry's file selector was set to. + * + * @param obj The entry object + * @param path Path to a file/directory + * + * Default path is "HOME" environment variable's value. + * + * @ingroup File_Selector_Entry + */ +EAPI const char * +elm_fileselector_entry_selected_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_fileselector_button_path_get(wd->button); +} + +/** + * Set the title of the file selector entry's window. + * + * @param obj The entry object + * @param title The title string + * + * Note that it will only take any effect if the fileselector entry + * not at "inwin mode". + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_window_title_set(Evas_Object *obj, const char *title) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_window_title_set(wd->button, title); +} + +/** + * Get the title of the file selector entry's window. + * + * @param obj The entry object + * + * @ingroup File_Selector_Entry + */ +EAPI const char * +elm_fileselector_entry_window_title_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_fileselector_button_window_title_get(wd->button); +} + +/** + * Set the size of the file selector entry's window. + * + * @param obj The entry object + * @param width The width + * @param height The height + * + * Note that it will only take any effect if the fileselector entry not at + * "inwin mode". Default size for the window (when applicable) is 400x400. + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_window_size_set(Evas_Object *obj, Evas_Coord width, Evas_Coord height) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_window_size_set(wd->button, width, height); +} + +/** + * Get the size of the file selector entry's window. + * + * @param obj The entry object + * @param width Pointer into which to store the width value + * @param height Pointer into which to store the height value + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_window_size_get(const Evas_Object *obj, Evas_Coord *width, Evas_Coord *height) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_window_size_get(wd->button, width, height); +} + +/** + * Set the starting path of the file selector entry's window. + * + * @param obj The entry object + * @param path The path string + * + * It must be a directory path. + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_path_set(Evas_Object *obj, const char *path) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_path_set(wd->button, path); + elm_scrolled_entry_entry_set(wd->entry, path); +} + +/** + * Get the last path of the file selector entry's window. + * + * @param obj The entry object + * + * @ingroup File_Selector_Entry + */ +EAPI const char * +elm_fileselector_entry_path_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_scrolled_entry_entry_get(wd->entry); +} + +/** + * Set whether the entry's file selector is to present itself as an + * Elementary Generic List (which will expand its entries for nested + * directories) or as canonical list, which will be rendered again + * with the contents of each selected directory. + * + * @param obj The entry object + * @param value The expandable flag + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_expandable_set(Evas_Object *obj, Eina_Bool value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_expandable_set(wd->button, value); +} + +/** + * Get the entry's file selector expandable flag. + * + * @param obj The entry object + * @return value The expandable flag + * + * @ingroup File_Selector_Entry + */ +EAPI Eina_Bool +elm_fileselector_entry_expandable_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_fileselector_button_expandable_get(wd->button); +} + +/** + * Set whether the entry's file selector list is to display folders + * only or the directory contents, as well. + * + * @param obj The entry object + * @param value The "folder only" flag + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_folder_only_set(Evas_Object *obj, Eina_Bool value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_folder_only_set(wd->button, value); +} + +/** + * Get the entry's file selector "folder only" flag. + * + * @param obj The entry object + * @return value The "folder only" flag + * + * @ingroup File_Selector_Entry + */ +EAPI Eina_Bool +elm_fileselector_entry_folder_only_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_fileselector_button_folder_only_get(wd->button); +} + +/** + * Set whether the entry's file selector has an editable text entry + * which will hold its current selection. + * + * @param obj The entry object + * @param value The "is save" flag + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_is_save_set(Evas_Object *obj, Eina_Bool value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_is_save_set(wd->button, value); +} + +/** + * Get the entry's file selector "is save" flag. + * + * @param obj The entry object + * @return value The "is save" flag + * + * @ingroup File_Selector_Entry + */ +EAPI Eina_Bool +elm_fileselector_entry_is_save_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_fileselector_button_is_save_get(wd->button); +} + +/** + * Set whether the entry's file selector will raise an Elementary + * Inner Window, instead of a dedicated Elementary Window. By default, + * it won't. + * + * @param obj The entry object + * @param value The "inwin mode" flag + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_inwin_mode_set(Evas_Object *obj, Eina_Bool value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_inwin_mode_set(wd->button, value); +} + +/** + * Get the entry's file selector "inwin mode" flag. + * + * @param obj The entry object + * @return value The "inwin mode" flag + * + * @ingroup File_Selector_Entry + */ +EAPI Eina_Bool +elm_fileselector_entry_inwin_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_fileselector_button_inwin_mode_get(wd->button); +} + +/** + * Set the icon used for the entry button + * + * Once the icon object is set, a previously set one will be deleted. + * + * @param obj The entry object + * @param icon The image for the entry + * + * @ingroup File_Selector_Entry + */ +EAPI void +elm_fileselector_entry_button_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_fileselector_button_icon_set(wd->button, icon); +} + +/** + * Get the icon used for the entry button + * + * @param obj The entry object + * @return The image for the entry + * + * @ingroup File_Selector_Entry + */ +EAPI Evas_Object * +elm_fileselector_entry_button_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_fileselector_button_icon_get(wd->button); +} + +/** + * Unset the icon used for the entry button + * + * Unparent and return the icon object which was set for this widget. + * + * @param obj The entry object + * @return The icon object that was being used + * + * @ingroup File_Selector_Entry + */ +EAPI Evas_Object * +elm_fileselector_entry_button_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_fileselector_button_icon_unset(wd->button); +} diff --git a/src/lib/elc_hoversel.c b/src/lib/elc_hoversel.c new file mode 100644 index 0000000..0ee816e --- /dev/null +++ b/src/lib/elc_hoversel.c @@ -0,0 +1,721 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Hoversel + * + * A hoversel is a button that pops up a list of items (automatically + * choosing the direction to display) that have a lable and/or an icon to + * select from. It is a convenience widget to avoid the need to do all the + * piecing together yourself. It is intended for a small number of items in + * the hoversel menu (no more than 8), though is capable of many more. + * + * Signals that you can add callbacks for are: + * + * clicked - the user clicked the hoversel button and popped up the sel + * + * selected - an item in the hoversel list is selected. event_info is the item + * selected - Elm_Hoversel_Item + * + * dismissed - the hover is dismissed + */ +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *btn, *hover; + Evas_Object *hover_parent; + Eina_List *items; + Eina_Bool horizontal : 1; + Eina_Bool expanded : 1; +}; + +struct _Elm_Hoversel_Item +{ + Elm_Widget_Item base; + const char *label; + const char *icon_file; + const char *icon_group; + Elm_Icon_Type icon_type; + Evas_Smart_Cb func; +}; + +static const char *widtype = NULL; +static void _del_pre_hook(Evas_Object *obj); +static void _del_hook(Evas_Object *obj); +static void _activate(Evas_Object *obj); +static void _activate_hook(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _parent_del(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static void +_del_pre_hook(Evas_Object *obj) +{ + Elm_Hoversel_Item *item; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_hoversel_hover_end(obj); + elm_hoversel_hover_parent_set(obj, NULL); + EINA_LIST_FREE(wd->items, item) + { + elm_widget_item_pre_notify_del(item); + eina_stringshare_del(item->label); + eina_stringshare_del(item->icon_file); + eina_stringshare_del(item->icon_group); + elm_widget_item_del(item); + } +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + char buf[4096]; + if (!wd) return; + elm_hoversel_hover_end(obj); + if (wd->horizontal) + snprintf(buf, sizeof(buf), "hoversel_horizontal/%s", elm_widget_style_get(obj)); + else + snprintf(buf, sizeof(buf), "hoversel_vertical/%s", elm_widget_style_get(obj)); + elm_object_style_set(wd->btn, buf); + elm_object_disabled_set(wd->btn, elm_widget_disabled_get(obj)); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_object_disabled_set(wd->btn, elm_widget_disabled_get(obj)); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + evas_object_size_hint_min_get(wd->btn, &minw, &minh); + evas_object_size_hint_max_get(wd->btn, &maxw, &maxh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + elm_widget_focus_steal(wd->btn); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_hover_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + elm_hoversel_hover_end(data); +} + +static void +_item_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Hoversel_Item *item = data; + Evas_Object *obj2 = item->base.widget; + + elm_hoversel_hover_end(obj2); + if (item->func) item->func((void *)item->base.data, obj2, item); + evas_object_smart_callback_call(obj2, "selected", item); +} + +static void +_activate(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *bt, *bx, *ic; + const Eina_List *l; + const Elm_Hoversel_Item *item; + char buf[4096]; + + if (!wd) return; + if (wd->expanded) + { + elm_hoversel_hover_end(obj); + return; + } + wd->expanded = EINA_TRUE; + + if (elm_widget_disabled_get(obj)) return; + wd->hover = elm_hover_add(obj); + if (wd->horizontal) + snprintf(buf, sizeof(buf), "hoversel_horizontal/%s", elm_widget_style_get(obj)); + else + snprintf(buf, sizeof(buf), "hoversel_vertical/%s", elm_widget_style_get(obj)); + elm_object_style_set(wd->hover, buf); + evas_object_smart_callback_add(wd->hover, "clicked", _hover_clicked, obj); + elm_hover_parent_set(wd->hover, wd->hover_parent); + elm_hover_target_set(wd->hover, wd->btn); + + bx = elm_box_add(wd->hover); + elm_box_homogenous_set(bx, 1); + + elm_box_horizontal_set(bx, wd->horizontal); + + if (wd->horizontal) + snprintf(buf, sizeof(buf), "hoversel_horizontal_entry/%s", + elm_widget_style_get(obj)); + else + snprintf(buf, sizeof(buf), "hoversel_vertical_entry/%s", + elm_widget_style_get(obj)); + EINA_LIST_FOREACH(wd->items, l, item) + { + bt = elm_button_add(wd->hover); + elm_object_style_set(bt, buf); + elm_button_label_set(bt, item->label); + if (item->icon_file) + { + ic = elm_icon_add(obj); + elm_icon_scale_set(ic, 0, 1); + if (item->icon_type == ELM_ICON_FILE) + elm_icon_file_set(ic, item->icon_file, item->icon_group); + else if (item->icon_type == ELM_ICON_STANDARD) + elm_icon_standard_set(ic, item->icon_file); + elm_button_icon_set(bt, ic); + evas_object_show(ic); + } + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_box_pack_end(bx, bt); + evas_object_smart_callback_add(bt, "clicked", _item_clicked, item); + evas_object_show(bt); + } + + if (wd->horizontal) + elm_hover_content_set(wd->hover, + elm_hover_best_content_location_get(wd->hover, + ELM_HOVER_AXIS_HORIZONTAL), + bx); + else + elm_hover_content_set(wd->hover, + elm_hover_best_content_location_get(wd->hover, + ELM_HOVER_AXIS_VERTICAL), + bx); + evas_object_show(bx); + + evas_object_show(wd->hover); + evas_object_smart_callback_call(obj, "clicked", NULL); + +// if (wd->horizontal) evas_object_hide(wd->btn); +} + +static void +_activate_hook(Evas_Object *obj) +{ + _activate(obj); +} + +static void +_button_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _activate(data); +} + +static void +_parent_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->hover_parent = NULL; +} + +/** + * Add a new Hoversel object + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Hoversel + */ +EAPI Evas_Object * +elm_hoversel_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "hoversel"); + elm_widget_type_set(obj, "hoversel"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_activate_hook_set(obj, _activate_hook); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_can_focus_set(obj, EINA_TRUE); + + wd->btn = elm_button_add(parent); + wd->expanded = EINA_FALSE; + elm_widget_resize_object_set(obj, wd->btn); + evas_object_event_callback_add(wd->btn, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + evas_object_smart_callback_add(wd->btn, "clicked", _button_clicked, obj); + elm_widget_sub_object_add(obj, wd->btn); + + elm_hoversel_hover_parent_set(obj, parent); + _theme_hook(obj); + return obj; +} + +/** + * Set the Hover parent + * + * Sets the hover parent object. Should probably be the window that the hoversel + * is in. See Hover objects for more information. + * + * @param obj The hoversel object + * @param parent The parent to use + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_hover_parent_set(Evas_Object *obj, Evas_Object *parent) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->hover_parent) + evas_object_event_callback_del_full(wd->hover_parent, EVAS_CALLBACK_DEL, + _parent_del, obj); + wd->hover_parent = parent; + if (wd->hover_parent) + evas_object_event_callback_add(wd->hover_parent, EVAS_CALLBACK_DEL, + _parent_del, obj); +} + +/** + * Get the Hover parent + * + * Gets the hover parent object. Should probably be the window that the hoversel + * is in. See Hover objects for more information. + * + * @param obj The hoversel object + * @return The used parent + * + * @ingroup Hoversel + */ +EAPI Evas_Object * +elm_hoversel_hover_parent_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->hover_parent; +} + +/** + * Set the hoversel button label + * + * This sets the label of the button that is always visible (before it is + * clicked and expanded). Also see elm_button_label_set(). + * + * @param obj The hoversel object + * @param label The label text. + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_button_label_set(wd->btn, label); +} + +/** + * Get the hoversel button label + * + * @param obj The hoversel object + * @return The label text. + * + * @ingroup Hoversel + */ +EAPI const char * +elm_hoversel_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->btn)) return NULL; + return elm_button_label_get(wd->btn); +} + +/** + * This sets the hoversel to expand horizontally. The initial button + * will display horizontally regardless of this setting. + * + * @param obj The hoversel object + * @param horizontal If true, the hover will expand horizontally to the right. + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->horizontal = !!horizontal; +} + + +/** + * This returns whether the hoversel is set to expand horizontally. + * + * @param obj The hoversel object + * @return If true, the hover will expand horizontally to the right. + * + * @ingroup Hoversel + */ +EAPI Eina_Bool +elm_hoversel_horizontal_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->horizontal; +} + +/** + * Set the icon of the hoversel button + * + * Sets the icon of the button that is always visible (before it is clicked + * and expanded). Also see elm_button_icon_set(). + * Once the icon object is set, a previously set one will be deleted + * If you want to keep that old content object, use the + * elm_hoversel_icon_unset() function. + * + * @param obj The hoversel object + * @param icon The icon object + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_button_icon_set(wd->btn, icon); +} + +/** + * Get the icon of the hoversel button + * + * Get the icon of the button that is always visible (before it is clicked + * and expanded). Also see elm_button_icon_get(). + * + * @param obj The hoversel object + * @return The icon object + * + * @ingroup Hoversel + */ +EAPI Evas_Object * +elm_hoversel_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->btn)) return NULL; + return elm_button_icon_get(wd->btn); +} + +/** + * Get the icon of the hoversel button + * + * Unparent and return the icon of the button that is always visible + * (before it is clicked and expanded). Also see elm_button_icon_unset(). + * + * @param obj The hoversel object + * @return The icon object that was being used + * + * @ingroup Hoversel + */ +EAPI Evas_Object * +elm_hoversel_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->btn)) return NULL; + return elm_button_icon_unset(wd->btn); +} + +/** + * This triggers the hoversel popup from code, the same as though the + * user clicked the button. + * + * @param obj The hoversel object + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_hover_begin(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->hover) return; + _activate(obj); +} + +/** + * This ends the hoversel popup as though the user clicked outside the hover. + * + * @param obj The hoversel object + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_hover_end(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (!wd->hover) return; + wd->expanded = EINA_FALSE; + evas_object_del(wd->hover); + wd->hover = NULL; + evas_object_smart_callback_call(obj, "dismissed", NULL); +} + +/** + * Returns whether the hoversel is expanded. + * + * @param obj The hoversel object + * @return This will return EINA_TRUE if the hoversel + * is expanded or EINA_FALSE if it is not expanded. + * + * @ingroup Hoversel + */ +EAPI Eina_Bool +elm_hoversel_expanded_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return (wd->hover) ? EINA_TRUE : EINA_FALSE; +} + +/** + * This will remove all the children items from the hoversel. (should not be + * called while the hoversel is active; use elm_hoversel_expanded_get() + * to check first). + * + * @param obj The hoversel object + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_clear(Evas_Object *obj) +{ + Elm_Hoversel_Item *item; + Eina_List *l, *ll; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_LIST_FOREACH_SAFE(wd->items, l, ll, item) elm_hoversel_item_del(item); +} + +/** + * Get the list of items within the given hoversel. + * + * @param obj The hoversel object + * @return Returns a list of Elm_Hoversel_Item* + * + * @ingroup Hoversel + */ +EAPI const Eina_List * +elm_hoversel_items_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->items; +} + +/** + * Add an item to the hoversel button + * + * This adds an item to the hoversel to show when it is clicked. Note: if you + * need to use an icon from an edje file then use elm_hoversel_item_icon_set() + * right after the this function, and set icon_file to NULL here. + * + * @param obj The hoversel object + * @param label The text label to use for the item (NULL if not desired) + * @param icon_file An image file path on disk to use for the icon or standard + * icon name (NULL if not desired) + * @param icon_type The icon type if relevant + * @param func Convenience function to call when this item is selected + * @param data Data to pass to item-related functions + * @return A handle to the item added. + * + * @ingroup Hoversel + */ +EAPI Elm_Hoversel_Item * +elm_hoversel_item_add(Evas_Object *obj, const char *label, const char *icon_file, Elm_Icon_Type icon_type, Evas_Smart_Cb func, const void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + Elm_Hoversel_Item *item = elm_widget_item_new(obj, Elm_Hoversel_Item); + if (!item) return NULL; + wd->items = eina_list_append(wd->items, item); + item->label = eina_stringshare_add(label); + item->icon_file = eina_stringshare_add(icon_file); + item->icon_type = icon_type; + item->func = func; + item->base.data = data; + return item; +} + +/** + * Delete an item from the hoversel + * + * This deletes the item from the hoversel (should not be called while the + * hoversel is active; use elm_hoversel_expanded_get() + * to check first). + * + * @param item The item to delete + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_item_del(Elm_Hoversel_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + Widget_Data *wd = elm_widget_data_get(item->base.widget); + if (!wd) return; + elm_hoversel_hover_end(item->base.widget); + wd->items = eina_list_remove(wd->items, item); + elm_widget_item_pre_notify_del(item); + eina_stringshare_del(item->label); + eina_stringshare_del(item->icon_file); + eina_stringshare_del(item->icon_group); + elm_widget_item_del(item); +} + +/** + * Set the function called when an item within the hoversel + * is freed. That function will receive these parameters: + * + * void *item_data + * Evas_Object *the_item_object + * Elm_Hoversel_Item *the_object_struct + * + * @param item The item to set the callback on + * @param func The function called + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_item_del_cb_set(Elm_Hoversel_Item *item, Evas_Smart_Cb func) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_del_cb_set(item, func); +} + +/** + * This returns the data pointer supplied with elm_hoversel_item_add() that + * will be passed to associated function callbacks. + * + * @param item The item to get the data from + * @return The data pointer set with elm_hoversel_item_add() + * + * @ingroup Hoversel + */ +EAPI void * +elm_hoversel_item_data_get(const Elm_Hoversel_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_data_get(item); +} + +/** + * This returns the label text of the given hoversel item. + * + * @param item The item to get the label + * @return The label text of the hoversel item + * + * @ingroup Hoversel + */ +EAPI const char * +elm_hoversel_item_label_get(const Elm_Hoversel_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->label; +} + +/** + * This sets the icon for the given hoversel item. The icon can be loaded from + * the standard set, from an image file, or from an edje file. + * + * @param item The item to set the icon + * @param icon_file An image file path on disk to use for the icon or standard + * icon name + * @param icon_group The edje group to use if @p icon_file is an edje file. Set this + * to NULL if the icon is not an edje file + * @param icon_type The icon type + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_item_icon_set(Elm_Hoversel_Item *item, const char *icon_file, const char *icon_group, Elm_Icon_Type icon_type) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + eina_stringshare_replace(&item->icon_file, icon_file); + eina_stringshare_replace(&item->icon_group, icon_group); + item->icon_type = icon_type; +} + +/** + * Get the icon object of the hoversel item + * + * @param item The item to get the icon from + * @param icon_file The image file path on disk used for the icon or standard + * icon name + * @param icon_group The edje group used if @p icon_file is an edje file. NULL + * if the icon is not an edje file + * @param icon_type The icon type + * + * @ingroup Hoversel + */ +EAPI void +elm_hoversel_item_icon_get(const Elm_Hoversel_Item *item, const char **icon_file, const char **icon_group, Elm_Icon_Type *icon_type) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (icon_file) *icon_file = item->icon_file; + if (icon_group) *icon_group = item->icon_group; + if (icon_type) *icon_type = item->icon_type; +} + diff --git a/src/lib/elc_scrolled_entry.c b/src/lib/elc_scrolled_entry.c new file mode 100644 index 0000000..f7d4433 --- /dev/null +++ b/src/lib/elc_scrolled_entry.c @@ -0,0 +1,1611 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Scrolled_Entry Scrolled_Entry + * + * A scrolled entry is a convenience widget which shows + * a box that the user can enter text into. Unlike an + * @ref Entry widget, scrolled entries scroll with user + * input so that the window will not expand if the length + * of text inside the entry exceeds the initial size of the + * widget. + * + * Signals that you can add callbacks for are: + * - "changed" - The text within the entry was changed + * - "activated" - The entry has received focus and the cursor + * - "press" - The entry has been clicked + * - "longpressed" - The entry has been clicked for a couple seconds + * - "clicked" - The entry has been clicked + * - "clicked,double" - The entry has been double clicked + * - "focused" - The entry has received focus + * - "unfocused" - The entry has lost focus + * - "selection,paste" - A paste action has occurred + * - "selection,copy" - A copy action has occurred + * - "selection,cut" - A cut action has occurred + * - "selection,start" - A selection has begun + * - "selection,changed" - The selection has changed + * - "selection,cleared" - The selection has been cleared + * - "cursor,changed" - The cursor has changed + * - "anchor,clicked" - The anchor has been clicked + */ + +typedef struct _Widget_Data Widget_Data; +typedef struct _Elm_Entry_Context_Menu_Item Elm_Entry_Context_Menu_Item; +typedef struct _Elm_Entry_Item_Provider Elm_Entry_Item_Provider; +typedef struct _Elm_Entry_Text_Filter Elm_Entry_Text_Filter; + +struct _Widget_Data +{ + Evas_Object *scroller; + Evas_Object *entry; + Evas_Object *icon; + Evas_Object *end; + Elm_Scroller_Policy policy_h, policy_v; + Eina_List *items; + Eina_List *item_providers; + Eina_List *text_filters; + Eina_Bool single_line : 1; +}; + +struct _Elm_Entry_Context_Menu_Item +{ + Evas_Object *obj; + Evas_Smart_Cb func; + void *data; +}; + +struct _Elm_Entry_Item_Provider +{ + Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item); + void *data; +}; + +struct _Elm_Entry_Text_Filter +{ + void (*func) (void *data, Evas_Object *entry, char **text); + void *data; +}; + +static const char *widtype = NULL; + +static const char SIG_CHANGED[] = "changed"; +static const char SIG_ACTIVATED[] = "activated"; +static const char SIG_PRESS[] = "press"; +static const char SIG_LONGPRESSED[] = "longpressed"; +static const char SIG_CLICKED[] = "clicked"; +static const char SIG_CLICKED_DOUBLE[] = "clicked,double"; +static const char SIG_FOCUSED[] = "focused"; +static const char SIG_UNFOCUSED[] = "unfocused"; +static const char SIG_SELECTION_PASTE[] = "selection,paste"; +static const char SIG_SELECTION_COPY[] = "selection,copy"; +static const char SIG_SELECTION_CUT[] = "selection,cut"; +static const char SIG_SELECTION_START[] = "selection,start"; +static const char SIG_SELECTION_CHANGED[] = "selection,changed"; +static const char SIG_SELECTION_CLEARED[] = "selection,cleared"; +static const char SIG_CURSOR_CHANGED[] = "cursor,changed"; +static const char SIG_ANCHOR_CLICKED[] = "anchor,clicked"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_CHANGED, ""}, + {SIG_ACTIVATED, ""}, + {SIG_PRESS, ""}, + {SIG_LONGPRESSED, ""}, + {SIG_CLICKED, ""}, + {SIG_CLICKED_DOUBLE, ""}, + {SIG_FOCUSED, ""}, + {SIG_UNFOCUSED, ""}, + {SIG_SELECTION_PASTE, ""}, + {SIG_SELECTION_COPY, ""}, + {SIG_SELECTION_CUT, ""}, + {SIG_SELECTION_START, ""}, + {SIG_SELECTION_CHANGED, ""}, + {SIG_SELECTION_CLEARED, ""}, + {SIG_CURSOR_CHANGED, ""}, + {SIG_ANCHOR_CLICKED, ""}, + {NULL, NULL} +}; + +static void +_del_hook(Evas_Object *obj) +{ + Elm_Entry_Context_Menu_Item *ci; + Elm_Entry_Item_Provider *ip; + Elm_Entry_Text_Filter *tf; + + Widget_Data *wd = elm_widget_data_get(obj); + + EINA_LIST_FREE(wd->items, ci) + free(ci); + EINA_LIST_FREE(wd->item_providers, ip) + free(ip); + EINA_LIST_FREE(wd->text_filters, tf) + free(tf); + + if (!wd) return; + free(wd); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd; + Evas_Coord minw, minh, minw_scr, minh_scr; + wd = elm_widget_data_get(obj); + if (!wd) return; + + evas_object_size_hint_min_get(obj, &minw, &minh); + evas_object_size_hint_min_get(wd->scroller, &minw_scr, &minh_scr); + if (minw < minw_scr) minw = minw_scr; + if (minh < minh_scr) minh = minh_scr; + + evas_object_size_hint_min_set(obj, minw, minh); + if (wd->single_line) + evas_object_size_hint_max_set(obj, -1, minh); + else + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_object_style_set(wd->entry, elm_widget_style_get(obj)); + elm_object_style_set(wd->scroller, elm_widget_style_get(obj)); + elm_object_disabled_set(wd->entry, elm_widget_disabled_get(obj)); + elm_object_disabled_set(wd->scroller, elm_widget_disabled_get(obj)); + _sizing_eval(obj); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + elm_widget_focus_steal(wd->entry); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_object_disabled_set(wd->entry, elm_widget_disabled_get(obj)); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_object_signal_emit(wd->entry, emission, source); + elm_object_signal_emit(wd->scroller, emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_object_signal_callback_add(wd->entry, emission, source, func_cb, data); + elm_object_signal_callback_add(wd->scroller, emission, source, func_cb, + data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + elm_object_signal_callback_del(wd->entry, emission, source, func_cb); + elm_object_signal_callback_del(wd->scroller, emission, source, func_cb); +} + +static void +_on_focus_region_hook(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h) +{ + Widget_Data *wd = elm_widget_data_get(obj); + elm_widget_focus_region_get(wd->entry, x, y, w, h); +} + +static void +_changed_size_hints(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + _sizing_eval(obj); +} + +static void +_entry_changed(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + _sizing_eval(data); + evas_object_smart_callback_call(data, SIG_CHANGED, event_info); +} + +static void +_entry_activated(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_ACTIVATED, event_info); +} + +static void +_entry_press(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_PRESS, event_info); +} + +static void +_entry_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_CLICKED, event_info); +} + +static void +_entry_clicked_double(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_CLICKED_DOUBLE, event_info); +} + +static void +_entry_cursor_changed(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_CURSOR_CHANGED, event_info); +} + +static void +_entry_anchor_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_ANCHOR_CLICKED, event_info); +} + +static void +_entry_selection_start(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_SELECTION_START, event_info); +} + +static void +_entry_selection_changed(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_SELECTION_CHANGED, event_info); +} + +static void +_entry_selection_cleared(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_SELECTION_CLEARED, event_info); +} + +static void +_entry_selection_paste(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_SELECTION_PASTE, event_info); +} + +static void +_entry_selection_copy(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_SELECTION_COPY, event_info); +} + +static void +_entry_selection_cut(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_SELECTION_CUT, event_info); +} + +static void +_entry_longpressed(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_LONGPRESSED, event_info); +} + +static void +_entry_focused(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_FOCUSED, event_info); +} + +static void +_entry_unfocused(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + evas_object_smart_callback_call(data, SIG_UNFOCUSED, event_info); +} + +static void +_context_item_wrap_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Entry_Context_Menu_Item *ci = data; + ci->func(ci->data, ci->obj, event_info); +} + +static Evas_Object * +_item_provider_wrap_cb(void *data, Evas_Object *obj __UNUSED__, const char *item) +{ + Widget_Data *wd = elm_widget_data_get(data); + Eina_List *l; + Elm_Entry_Item_Provider *ip; + + EINA_LIST_FOREACH(wd->item_providers, l, ip) + { + Evas_Object *o; + o = ip->func(ip->data, data, item); + if (o) return o; + } + return NULL; +} + +static void +_text_filter_wrap_cb(void *data, Evas_Object *obj __UNUSED__, char **text) +{ + Widget_Data *wd = elm_widget_data_get(data); + Eina_List *l; + Elm_Entry_Text_Filter *tf; + + EINA_LIST_FOREACH(wd->text_filters, l, tf) + { + tf->func(tf->data, data, text); + if (!*text) break; + } +} + +/** + * This adds a scrolled entry to @p parent object. + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Scrolled_Entry + */ +EAPI Evas_Object * +elm_scrolled_entry_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "scrolled_entry"); + elm_widget_type_set(obj, "scrolled_entry"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_on_focus_region_hook_set(obj, _on_focus_region_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + + wd->scroller = elm_scroller_add(obj); + elm_scroller_custom_widget_base_theme_set(wd->scroller, "scroller", "entry"); + elm_widget_resize_object_set(obj, wd->scroller); + evas_object_size_hint_weight_set(wd->scroller, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(wd->scroller, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_scroller_bounce_set(wd->scroller, EINA_FALSE, EINA_FALSE); + elm_scroller_propagate_events_set(wd->scroller, EINA_TRUE); + evas_object_show(wd->scroller); + + wd->entry = elm_entry_add(obj); + evas_object_size_hint_weight_set(wd->entry, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(wd->entry, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_scroller_content_set(wd->scroller, wd->entry); + evas_object_show(wd->entry); + + elm_entry_text_filter_prepend(wd->entry, _text_filter_wrap_cb, obj); + elm_entry_item_provider_prepend(wd->entry, _item_provider_wrap_cb, obj); + + evas_object_smart_callback_add(wd->entry, "changed", _entry_changed, obj); + evas_object_smart_callback_add(wd->entry, "activated", _entry_activated, obj); + evas_object_smart_callback_add(wd->entry, "press", _entry_press, obj); + evas_object_smart_callback_add(wd->entry, "clicked", _entry_clicked, obj); + evas_object_smart_callback_add(wd->entry, "clicked,double", _entry_clicked_double, obj); + evas_object_smart_callback_add(wd->entry, "cursor,changed", _entry_cursor_changed, obj); + evas_object_smart_callback_add(wd->entry, "anchor,clicked", _entry_anchor_clicked, obj); + evas_object_smart_callback_add(wd->entry, "selection,start", _entry_selection_start, obj); + evas_object_smart_callback_add(wd->entry, "selection,changed", _entry_selection_changed, obj); + evas_object_smart_callback_add(wd->entry, "selection,cleared", _entry_selection_cleared, obj); + evas_object_smart_callback_add(wd->entry, "selection,paste", _entry_selection_paste, obj); + evas_object_smart_callback_add(wd->entry, "selection,copy", _entry_selection_copy, obj); + evas_object_smart_callback_add(wd->entry, "selection,cut", _entry_selection_cut, obj); + evas_object_smart_callback_add(wd->entry, "longpressed", _entry_longpressed, obj); + evas_object_smart_callback_add(wd->entry, "focused", _entry_focused, obj); + evas_object_smart_callback_add(wd->entry, "unfocused", _entry_unfocused, obj); + + evas_object_event_callback_add(obj, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, NULL); + + _sizing_eval(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * This sets a widget to be displayed to the left of a scrolled entry. + * + * @param obj The scrolled entry object + * @param icon The widget to display on the left side of the scrolled + * entry. + * + * @note A previously set widget will be destroyed. + * @note If the object being set does not have minimum size hints set, + * it won't get properly displayed. + * + * @ingroup Scrolled_Entry + * @see elm_scrolled_entry_end_set + */ +EAPI void +elm_scrolled_entry_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *edje; + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(icon); + if (wd->icon == icon) return; + if (wd->icon) evas_object_del(wd->icon); + wd->icon = icon; + edje = _elm_scroller_edje_object_get(wd->scroller); + if (!edje) return; + edje_object_part_swallow(edje, "elm.swallow.icon", wd->icon); + edje_object_signal_emit(edje, "elm,action,show,icon", "elm"); + _sizing_eval(obj); +} + +/** + * Gets the leftmost widget of the scrolled entry. This object is + * owned by the scrolled entry and should not be modified. + * + * @param obj The scrolled entry object + * @return the left widget inside the scroller + * + * @ingroup Scrolled_Entry + */ +EAPI Evas_Object * +elm_scrolled_entry_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->icon; +} + +/** + * Unset the leftmost widget of the scrolled entry, unparenting and + * returning it. + * + * @param obj The scrolled entry object + * @return the previously set icon sub-object of this entry, on + * success. + * + * @see elm_scrolled_entry_icon_set() + * + * @ingroup Scrolled_Entry + */ +EAPI Evas_Object * +elm_scrolled_entry_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *ret = NULL; + if (!wd) return NULL; + if (wd->icon) + { + Evas_Object *edje = _elm_scroller_edje_object_get(wd->scroller); + if (!edje) return NULL; + ret = wd->icon; + edje_object_part_unswallow(edje, wd->icon); + edje_object_signal_emit(edje, "elm,action,hide,icon", "elm"); + wd->icon = NULL; + _sizing_eval(obj); + } + return ret; +} + +/** + * Sets the visibility of the left-side widget of the scrolled entry, + * set by @elm_scrolled_entry_icon_set(). + * + * @param obj The scrolled entry object + * @param setting EINA_TRUE if the object should be displayed, + * EINA_FALSE if not. + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_icon_visible_set(Evas_Object *obj, Eina_Bool setting) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->icon)) return; + if (setting) + evas_object_hide(wd->icon); + else + evas_object_show(wd->icon); + _sizing_eval(obj); +} + +/** + * This sets a widget to be displayed to the end of a scrolled entry. + * + * @param obj The scrolled entry object + * @param end The widget to display on the right side of the scrolled + * entry. + * + * @note A previously set widget will be destroyed. + * @note If the object being set does not have minimum size hints set, + * it won't get properly displayed. + * + * @ingroup Scrolled_Entry + * @see elm_scrolled_entry_icon_set + */ +EAPI void +elm_scrolled_entry_end_set(Evas_Object *obj, Evas_Object *end) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *edje; + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(end); + if (wd->end == end) return; + if (wd->end) evas_object_del(wd->end); + wd->end = end; + edje = _elm_scroller_edje_object_get(wd->scroller); + if (!edje) return; + edje_object_part_swallow(edje, "elm.swallow.end", wd->end); + edje_object_signal_emit(edje, "elm,action,show,end", "elm"); + _sizing_eval(obj); +} + +/** + * Gets the endmost widget of the scrolled entry. This object is owned + * by the scrolled entry and should not be modified. + * + * @param obj The scrolled entry object + * @return the right widget inside the scroller + * + * @ingroup Scrolled_Entry + */ +EAPI Evas_Object * +elm_scrolled_entry_end_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->end; +} + +/** + * Unset the endmost widget of the scrolled entry, unparenting and + * returning it. + * + * @param obj The scrolled entry object + * @return the previously set icon sub-object of this entry, on + * success. + * + * @see elm_scrolled_entry_icon_set() + * + * @ingroup Scrolled_Entry + */ +EAPI Evas_Object * +elm_scrolled_entry_end_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *ret = NULL; + if (!wd) return NULL; + if (wd->end) + { + Evas_Object *edje = _elm_scroller_edje_object_get(wd->scroller); + if (!edje) return NULL; + ret = wd->end; + edje_object_part_unswallow(edje, wd->end); + edje_object_signal_emit(edje, "elm,action,hide,end", "elm"); + wd->end = NULL; + _sizing_eval(obj); + } + return ret; +} + +/** + * Sets the visibility of the end widget of the scrolled entry, set by + * @elm_scrolled_entry_end_set(). + * + * @param obj The scrolled entry object + * @param setting EINA_TRUE if the object should be displayed, + * EINA_FALSE if not. + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_end_visible_set(Evas_Object *obj, Eina_Bool setting) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->end)) return; + if (setting) + evas_object_hide(wd->end); + else + evas_object_show(wd->end); + _sizing_eval(obj); +} + +/** + * This sets the scrolled entry object not to line wrap. All input will + * be on a single line, and the entry box will scroll with user input. + * + * @param obj The scrolled entry object + * @param single_line If true, the text in the scrolled entry + * will be on a single line. + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_single_line_set(Evas_Object *obj, Eina_Bool single_line) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->single_line == single_line) return; + elm_entry_single_line_set(wd->entry, single_line); + wd->single_line = single_line; + if (single_line) + { + elm_scroller_policy_set(wd->scroller, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_OFF); + elm_scroller_content_min_limit(wd->scroller, 0, 1); + } + else + { + elm_scroller_policy_set(wd->scroller, wd->policy_h, wd->policy_v); + elm_scroller_content_min_limit(wd->scroller, 0, 0); + } + _sizing_eval(obj); +} + +/** + * This returns true if the scrolled entry has been set to single line mode. + * See also elm_scrolled_entry_single_line_set(). + * + * @param obj The scrolled entry object + * @return single_line If true, the text in the scrolled entry is set to display + * on a single line. + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_single_line_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_single_line_get(wd->entry); +} + + +/** + * This sets the scrolled entry object to password mode. All text entered + * and/or displayed within the widget will be replaced with asterisks (*). + * + * @param obj The scrolled entry object + * @param password If true, password mode is enabled. + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_password_set(Evas_Object *obj, Eina_Bool password) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_password_set(wd->entry, password); +} + +/** + * This returns whether password mode is enabled. + * See also elm_scrolled_entry_password_set(). + * + * @param obj The scrolled entry object + * @return If true, the scrolled entry is set to display all characters + * as asterisks (*). + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_password_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_password_get(wd->entry); +} + + +/** + * This sets the text displayed within the scrolled entry to @p entry. + * + * @param obj The scrolled entry object + * @param entry The text to be displayed + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_entry_set(Evas_Object *obj, const char *entry) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_entry_set(wd->entry, entry); +} + +/** + * This returns the text currently shown in object @p entry. + * See also elm_scrolled_entry_entry_set(). + * + * @param obj The scrolled entry object + * @return The currently displayed text or NULL on failure + * + * @ingroup Scrolled_Entry + */ +EAPI const char * +elm_scrolled_entry_entry_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_entry_entry_get(wd->entry); +} + +/** + * This returns EINA_TRUE if the entry is empty/there was an error + * and EINA_FALSE if it is not empty. + * + * @param obj The entry object + * @return If the entry is empty or not. + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_is_empty(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_TRUE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_TRUE; + return elm_entry_is_empty(wd->entry); +} + +/** + * This returns all selected text within the scrolled entry. + * + * @param obj The scrolled entry object + * @return The selected text within the scrolled entry or NULL on failure + * + * @ingroup Scrolled_Entry + */ +EAPI const char * +elm_scrolled_entry_selection_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_entry_selection_get(wd->entry); +} + +/** + * This inserts text in @p entry at the beginning of the scrolled entry + * object. + * + * @param obj The scrolled entry object + * @param entry The text to insert + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_entry_insert(Evas_Object *obj, const char *entry) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_entry_insert(wd->entry, entry); +} + +/** + * This enables word line wrapping in the scrolled entry object. It is the opposite + * of elm_scrolled_entry_single_line_set(). Additionally, setting this disables + * character line wrapping. + * See also elm_scrolled_entry_line_char_wrap_set(). + * + * @param obj The scrolled entry object + * @param wrap If true, the scrolled entry will be wrapped once it reaches the end + * of the object. Wrapping will occur at the end of the word before the end of the + * object. + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_line_wrap_set(Evas_Object *obj, Eina_Bool wrap) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_line_wrap_set(wd->entry, wrap); +} + +/** + * This enables character line wrapping in the scrolled entry object. It is the opposite + * of elm_scrolled_entry_single_line_set(). Additionally, setting this disables + * word line wrapping. + * See also elm_scrolled_entry_line_wrap_set(). + * + * @param obj The scrolled entry object + * @param wrap If true, the scrolled entry will be wrapped once it reaches the end + * of the object. Wrapping will occur immediately upon reaching the end of the object. + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_line_char_wrap_set(Evas_Object *obj, Eina_Bool wrap) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_line_char_wrap_set(wd->entry, wrap); +} + +/** + * This sets the editable attribute of the scrolled entry. + * + * @param obj The scrolled entry object + * @param editable If true, the scrolled entry will be editable by the user. + * If false, it will be set to the disabled state. + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_editable_set(Evas_Object *obj, Eina_Bool editable) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_editable_set(wd->entry, editable); +} + +/** + * This gets the editable attribute of the scrolled entry. + * See also elm_scrolled_entry_editable_set(). + * + * @param obj The scrolled entry object + * @return If true, the scrolled entry is editable by the user. + * If false, it is not editable by the user + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_editable_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_editable_get(wd->entry); +} + + +/** + * This drops any existing text selection within the scrolled entry. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_select_none(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_select_none(wd->entry); +} + +/** + * This selects all text within the scrolled entry. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_select_all(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_select_all(wd->entry); +} + +/** + * This moves the cursor one place to the right within the entry. + * + * @param obj The scrolled entry object + * @return EINA_TRUE upon success, EINA_FALSE upon failure + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_cursor_next(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_cursor_next(wd->entry); +} + +/** + * This moves the cursor one place to the left within the entry. + * + * @param obj The scrolled entry object + * @return EINA_TRUE upon success, EINA_FALSE upon failure + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_cursor_prev(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_cursor_prev(wd->entry); +} + +/** + * This moves the cursor one line up within the entry. + * + * @param obj The scrolled entry object + * @return EINA_TRUE upon success, EINA_FALSE upon failure + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_cursor_up(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_cursor_up(wd->entry); +} + +/** + * This moves the cursor one line down within the entry. + * + * @param obj The scrolled entry object + * @return EINA_TRUE upon success, EINA_FALSE upon failure + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_cursor_down(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_cursor_down(wd->entry); +} + +/** + * This moves the cursor to the beginning of the entry. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_cursor_begin_set(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_cursor_begin_set(wd->entry); +} + +/** + * This moves the cursor to the end of the entry. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_cursor_end_set(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + int x, y, w, h; + elm_entry_cursor_end_set(wd->entry); + elm_widget_show_region_get(wd->entry, &x, &y, &w, &h); + elm_scroller_region_show(wd->scroller, x, y, w, h); +} + +/** + * This moves the cursor to the beginning of the current line. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_cursor_line_begin_set(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_cursor_line_begin_set(wd->entry); +} + +/** + * This moves the cursor to the end of the current line. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_cursor_line_end_set(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_cursor_line_end_set(wd->entry); +} + +/** + * This begins a selection within the scrolled entry as though + * the user were holding down the mouse button to make a selection. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_cursor_selection_begin(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_cursor_selection_begin(wd->entry); +} + +/** + * This ends a selection within the scrolled entry as though + * the user had just released the mouse button while making a selection. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_cursor_selection_end(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_cursor_selection_end(wd->entry); +} + +/** + * TODO: fill this in + * + * @param obj The scrolled entry object + * @return TODO: fill this in + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_cursor_is_format_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_cursor_is_format_get(wd->entry); +} + +/** + * This returns whether the cursor is visible. + * + * @param obj The scrolled entry object + * @return If true, the cursor is visible. + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_cursor_is_visible_format_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_cursor_is_visible_format_get(wd->entry); +} + +/** + * TODO: fill this in + * + * @param obj The scrolled entry object + * @return TODO: fill this in + * + * @ingroup Scrolled_Entry + */ +EAPI const char * +elm_scrolled_entry_cursor_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_entry_cursor_content_get(wd->entry); +} + +/** + * This executes a "cut" action on the selected text in the scrolled entry. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_selection_cut(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_selection_cut(wd->entry); +} + +/** + * This executes a "copy" action on the selected text in the scrolled entry. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_selection_copy(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_selection_copy(wd->entry); +} + +/** + * This executes a "paste" action in the scrolled entry. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_selection_paste(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_selection_paste(wd->entry); +} + +/** + * This clears and frees the items in a scrolled entry's contextual (right click) menu. + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_context_menu_clear(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_context_menu_clear(wd->entry); +} + +/** + * This adds an item to the scrolled entry's contextual menu. + * + * @param obj The scrolled entry object + * @param label The item's text label + * @param icon_file The item's icon file + * @param icon_type The item's icon type + * @param func The callback to execute when the item is clicked + * @param data The data to associate with the item for related functions + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_context_menu_item_add(Evas_Object *obj, const char *label, const char *icon_file, Elm_Icon_Type icon_type, Evas_Smart_Cb func, const void *data) +{ + Elm_Entry_Context_Menu_Item *ci; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + ci = malloc(sizeof(Elm_Entry_Context_Menu_Item)); + if (!ci) return; + ci->func = func; + ci->data = (void *)data; + ci->obj = obj; + wd->items = eina_list_append(wd->items, ci); + elm_entry_context_menu_item_add(wd->entry, label, icon_file, icon_type, _context_item_wrap_cb, ci); +} + +/** + * This disables the scrolled entry's contextual (right click) menu. + * + * @param obj The scrolled entry object + * @param disabled If true, the menu is disabled + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_context_menu_disabled_set(Evas_Object *obj, Eina_Bool disabled) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_context_menu_disabled_set(wd->entry, disabled); +} + +/** + * This returns whether the scrolled entry's contextual (right click) menu is disabled. + * + * @param obj The scrolled entry object + * @return If true, the menu is disabled + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_context_menu_disabled_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_context_menu_disabled_get(wd->entry); +} + +/** + * This sets the scrolled entry's scrollbar policy (ie. enabling/disabling them). + * + * @param obj The scrolled entry object + * @param h The horizontal scrollbar policy to apply + * @param v The vertical scrollbar policy to apply + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_scrollbar_policy_set(Evas_Object *obj, Elm_Scroller_Policy h, Elm_Scroller_Policy v) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->policy_h = h; + wd->policy_v = v; + elm_scroller_policy_set(wd->scroller, h, v); +} + +/** + * This enables/disables bouncing within the entry. + * + * @param obj The scrolled entry object + * @param h The horizontal bounce state + * @param v The vertical bounce state + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_scroller_bounce_set(wd->scroller, h_bounce, v_bounce); +} + +/** + * Get the bounce mode + * + * @param obj The Scrolled_Entry object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_scroller_bounce_get(wd->scroller, h_bounce, v_bounce); +} + +/** + * This appends a custom item provider to the list for that entry + * + * This appends the given callback. The list is walked from beginning to end + * with each function called given the item href string in the text. If the + * function returns an object handle other than NULL (it should create an + * and object to do this), then this object is used to replace that item. If + * not the next provider is called until one provides an item object, or the + * default provider in entry does. + * + * @param obj The entry object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_item_provider_append(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + Elm_Entry_Item_Provider *ip = calloc(1, sizeof(Elm_Entry_Item_Provider)); + if (!ip) return; + ip->func = func; + ip->data = data; + wd->item_providers = eina_list_append(wd->item_providers, ip); +} + +/** + * This prepends a custom item provider to the list for that entry + * + * This prepends the given callback. See elm_scrolled_entry_item_provider_append() for + * more information + * + * @param obj The entry object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_item_provider_prepend(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + Elm_Entry_Item_Provider *ip = calloc(1, sizeof(Elm_Entry_Item_Provider)); + if (!ip) return; + ip->func = func; + ip->data = data; + wd->item_providers = eina_list_prepend(wd->item_providers, ip); +} + +/** + * This removes a custom item provider to the list for that entry + * + * This removes the given callback. See elm_scrolled_entry_item_provider_append() for + * more information + * + * @param obj The entry object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_item_provider_remove(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Elm_Entry_Item_Provider *ip; + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + EINA_LIST_FOREACH(wd->item_providers, l, ip) + { + if ((ip->func == func) && (ip->data == data)) + { + wd->item_providers = eina_list_remove_list(wd->item_providers, l); + free(ip); + return; + } + } +} + +/** + * Append a filter function for text inserted in the entry + * + * Append the given callback to the list. This functions will be called + * whenever any text is inserted into the entry, with the text to be inserted + * as a parameter. The callback function is free to alter the text in any way + * it wants, but it must remember to free the given pointer and update it. + * If the new text is to be discarded, the function can free it and set it text + * parameter to NULL. This will also prevent any following filters from being + * called. + * + * @param obj The entry object + * @param func The function to use as text filter + * @param data User data to pass to @p func + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_text_filter_append(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) +{ + Widget_Data *wd; + Elm_Entry_Text_Filter *tf; + ELM_CHECK_WIDTYPE(obj, widtype); + + wd = elm_widget_data_get(obj); + + EINA_SAFETY_ON_NULL_RETURN(func); + + tf = ELM_NEW(Elm_Entry_Text_Filter); + if (!tf) return; + tf->func = func; + tf->data = data; + wd->text_filters = eina_list_append(wd->text_filters, tf); +} + +/** + * Prepend a filter function for text insdrted in the entry + * + * Prepend the given callback to the list. See elm_scrolled_entry_text_filter_append() + * for more information + * + * @param obj The entry object + * @param func The function to use as text filter + * @param data User data to pass to @p func + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_text_filter_prepend(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) +{ + Widget_Data *wd; + Elm_Entry_Text_Filter *tf; + ELM_CHECK_WIDTYPE(obj, widtype); + + wd = elm_widget_data_get(obj); + + EINA_SAFETY_ON_NULL_RETURN(func); + + tf = ELM_NEW(Elm_Entry_Text_Filter); + if (!tf) return; + tf->func = func; + tf->data = data; + wd->text_filters = eina_list_prepend(wd->text_filters, tf); +} + +/** + * Remove a filter from the list + * + * Removes the given callback from the filter list. See elm_scrolled_entry_text_filter_append() + * for more information. + * + * @param obj The entry object + * @param func The filter function to remove + * @param data The user data passed when adding the function + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_text_filter_remove(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) +{ + Widget_Data *wd; + Eina_List *l; + Elm_Entry_Text_Filter *tf; + ELM_CHECK_WIDTYPE(obj, widtype); + + wd = elm_widget_data_get(obj); + + EINA_SAFETY_ON_NULL_RETURN(func); + + EINA_LIST_FOREACH(wd->text_filters, l, tf) + { + if ((tf->func == func) && (tf->data == data)) + { + wd->text_filters = eina_list_remove_list(wd->text_filters, l); + free(tf); + return; + } + } +} + +/** + * This sets the file (and implicitly loads it) for the text to display and + * then edit. All changes are written back to the file after a short delay if + * the entry object is set to autosave. + * + * @param obj The scrolled entry object + * @param file The path to the file to load and save + * @param format The file format + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_file_set(Evas_Object *obj, const char *file, Elm_Text_Format format) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_file_set(wd->entry, file, format); +} + +/** + * Gets the file to load and save and the file format + * + * @param obj The scrolled entry object + * @param file The path to the file to load and save + * @param format The file format + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_file_get(const Evas_Object *obj, const char **file, Elm_Text_Format *format) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_file_get(wd->entry, file, format); +} + +/** + * This function writes any changes made to the file set with + * elm_scrolled_entry_file_set() + * + * @param obj The scrolled entry object + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_file_save(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_file_save(wd->entry); +} + +/** + * This sets the entry object to 'autosave' the loaded text file or not. + * + * @param obj The scrolled entry object + * @param autosave Autosave the loaded file or not + * + * @ingroup Scrolled_Entry + */ +EAPI void +elm_scrolled_entry_autosave_set(Evas_Object *obj, Eina_Bool autosave) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_entry_autosave_set(wd->entry, autosave); +} + +/** + * This gets the entry object's 'autosave' status. + * + * @param obj The scrolled entry object + * @return Autosave the loaded file or not + * + * @ingroup Scrolled_Entry + */ +EAPI Eina_Bool +elm_scrolled_entry_autosave_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return elm_entry_autosave_get(wd->entry); +} diff --git a/src/lib/elm_actionslider.c b/src/lib/elm_actionslider.c new file mode 100644 index 0000000..2aafd7c --- /dev/null +++ b/src/lib/elm_actionslider.c @@ -0,0 +1,546 @@ +/** + * @addtogroup Actionslider Actionslider + * + * A magnet slider is a switcher for 3 labels with customizable + * magnet properties. When the position is set with magnet, the knob + * will be moved to it if it's nearest the magnetized position. + * + * Signals emmitted: + * "selected" - when user selects a position (the label is passed as + * event info)". + * "pos_changed" - when a button reaches to the special position like + * "left", "right" and "center". + */ + +#include +#include +#include "elm_priv.h" + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *as; // actionslider + Evas_Object *drag_button_base; + Elm_Actionslider_Pos magnet_position, enabled_position; + const char *text_left, *text_right, *text_center; + const char *indicator_label; + Ecore_Animator *button_animator; + double final_position; + Eina_Bool mouse_down : 1; +}; + +static const char *widtype = NULL; + +#define SIG_CHANGED "pos_changed" +#define SIG_SELECTED "selected" + +static const Evas_Smart_Cb_Description _signals[] = +{ + {SIG_CHANGED, ""}, + {SIG_SELECTED, ""}, + {NULL, NULL} +}; + + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->drag_button_base) + { + evas_object_del(wd->drag_button_base); + wd->drag_button_base = NULL; + } + if (wd->text_left) eina_stringshare_del(wd->text_left); + if (wd->text_right) eina_stringshare_del(wd->text_right); + if (wd->text_center) eina_stringshare_del(wd->text_center); + if (wd->indicator_label) eina_stringshare_del(wd->indicator_label); + free(wd); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(wd->drag_button_base, minw, minh); + evas_object_size_hint_max_set(wd->drag_button_base, -1, -1); + + minw = -1; + minh = -1; + elm_coords_finger_size_adjust(3, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->as, &minw, &minh, minw, minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (!edje_object_part_swallow_get(wd->as, "elm.drag_button_base")) + edje_object_part_unswallow(wd->as, wd->drag_button_base); + + _elm_theme_object_set(obj, wd->as, "actionslider", + "base", elm_widget_style_get(obj)); + _elm_theme_object_set(obj, wd->drag_button_base, "actionslider", + "drag_button", elm_widget_style_get(obj)); + edje_object_part_swallow(wd->as, "elm.drag_button_base", wd->drag_button_base); + edje_object_part_text_set(wd->as, "elm.text.left", wd->text_left); + edje_object_part_text_set(wd->as, "elm.text.right", wd->text_right); + edje_object_part_text_set(wd->as, "elm.text.center", wd->text_center); + edje_object_part_text_set(wd->as, "elm.text.indicator", wd->indicator_label); + edje_object_message_signal_process(wd->as); + _sizing_eval(obj); +} + +static void +_drag_button_down_cb(void *data, Evas_Object *o __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get((Evas_Object *) data); + if (!wd) return; + wd->mouse_down = EINA_TRUE; +} + +static void +_drag_button_move_cb(void *data, Evas_Object *o __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Evas_Object *as = (Evas_Object *) data; + Widget_Data *wd = elm_widget_data_get(as); + double pos = 0.0; + if (!wd) return; + + if (!wd->mouse_down) return; + edje_object_part_drag_value_get(wd->as, "elm.drag_button_base", &pos, NULL); + if (pos == 0.0) + evas_object_smart_callback_call(as, SIG_CHANGED, "left"); + else if (pos == 1.0) + evas_object_smart_callback_call(as, SIG_CHANGED, "right"); + else if (pos >= 0.45 && pos <= 0.55) + evas_object_smart_callback_call(as, SIG_CHANGED, "center"); +} + +static Eina_Bool +_button_animation(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + double cur_position = 0.0, new_position = 0.0; + double move_amount = 0.05; + Eina_Bool flag_finish_animation = EINA_FALSE; + if (!wd) return EINA_FALSE; + + edje_object_part_drag_value_get(wd->as, + "elm.drag_button_base", &cur_position, NULL); + if ((wd->final_position == 0.0) || + (wd->final_position == 0.5 && cur_position >= wd->final_position)) + { + new_position = cur_position - move_amount; + if (new_position <= wd->final_position) + { + new_position = wd->final_position; + flag_finish_animation = EINA_TRUE; + } + } + else if ((wd->final_position == 1.0) || + (wd->final_position == 0.5 && cur_position < wd->final_position)) + { + new_position = cur_position + move_amount; + if (new_position >= wd->final_position) + { + new_position = wd->final_position; + flag_finish_animation = EINA_TRUE; + } + } + edje_object_part_drag_value_set(wd->as, + "elm.drag_button_base", new_position, 0.5); + if (flag_finish_animation) + { + if ((!wd->final_position) && + (wd->enabled_position & ELM_ACTIONSLIDER_LEFT)) + evas_object_smart_callback_call(data, SIG_SELECTED, + (void *)wd->text_left); + else if ((wd->final_position == 0.5) && + (wd->enabled_position & ELM_ACTIONSLIDER_CENTER)) + evas_object_smart_callback_call(data, SIG_SELECTED, + (void *)wd->text_center); + else if ((wd->final_position == 1) && + (wd->enabled_position & ELM_ACTIONSLIDER_RIGHT)) + evas_object_smart_callback_call(data, SIG_SELECTED, + (void *)wd->text_right); + return EINA_FALSE; + } + return EINA_TRUE; +} + +static void +_drag_button_up_cb(void *data, Evas_Object *o __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + double position = 0.0; + if (!wd) return; + + wd->mouse_down = EINA_FALSE; + + edje_object_part_drag_value_get(wd->as, "elm.drag_button_base", + &position, NULL); + + if (position == 0.0 && (wd->enabled_position & ELM_ACTIONSLIDER_LEFT)) + { + wd->final_position = 0; + evas_object_smart_callback_call(data, SIG_SELECTED, + (void *)wd->text_left); + return; + } + if (position >= 0.45 && position <= 0.55 && + (wd->enabled_position & ELM_ACTIONSLIDER_CENTER)) + { + wd->final_position = 0.5; + evas_object_smart_callback_call(data, SIG_SELECTED, + (void *)wd->text_center); + return; + } + if (position == 1.0 && (wd->enabled_position & ELM_ACTIONSLIDER_RIGHT)) + { + wd->final_position = 1; + evas_object_smart_callback_call(data, SIG_SELECTED, + (void *)wd->text_right); + return; + } + + if (wd->magnet_position == ELM_ACTIONSLIDER_NONE) return; + + if (position < 0.3) + { + if (wd->magnet_position & ELM_ACTIONSLIDER_LEFT) + wd->final_position = 0; + else if (wd->magnet_position & ELM_ACTIONSLIDER_CENTER) + wd->final_position = 0.5; + else if (wd->magnet_position & ELM_ACTIONSLIDER_RIGHT) + wd->final_position = 1; + } + else if ((position >= 0.3) && (position <= 0.7)) + { + if (wd->magnet_position & ELM_ACTIONSLIDER_CENTER) + wd->final_position = 0.5; + else if (position < 0.5) + { + if (wd->magnet_position & ELM_ACTIONSLIDER_LEFT) + wd->final_position = 0; + else + wd->final_position = 1; + } + else + { + if (wd->magnet_position & ELM_ACTIONSLIDER_RIGHT) + wd->final_position = 1; + else + wd->final_position = 0; + } + } + else + { + if (wd->magnet_position & ELM_ACTIONSLIDER_RIGHT) + wd->final_position = 1; + else if (wd->magnet_position & ELM_ACTIONSLIDER_CENTER) + wd->final_position = 0.5; + else + wd->final_position = 0; + } + wd->button_animator = ecore_animator_add(_button_animation, data); +} + +/** + * Add a new actionslider to the parent. + * + * @param parent The parent object + * @return The new actionslider object or NULL if it cannot be created + * + * @ingroup Actionslider + */ +EAPI Evas_Object * +elm_actionslider_add(Evas_Object *parent) +{ + Evas_Object *obj; + Widget_Data *wd; + Evas *e; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "actionslider"); + elm_widget_type_set(obj, "actionslider"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + + wd->mouse_down = EINA_FALSE; + wd->enabled_position = ELM_ACTIONSLIDER_ALL; + + wd->as = edje_object_add(e); + _elm_theme_object_set(obj, wd->as, "actionslider", "base", "default"); + elm_widget_resize_object_set(obj, wd->as); + + wd->drag_button_base = evas_object_rectangle_add(e); + evas_object_color_set(wd->drag_button_base, 0, 0, 0, 0); + edje_object_part_swallow(wd->as, "elm.drag_button_base", wd->drag_button_base); + + edje_object_signal_callback_add(wd->as, + "elm.drag_button,mouse,up", "", + _drag_button_up_cb, obj); + edje_object_signal_callback_add(wd->as, + "elm.drag_button,mouse,down", "", + _drag_button_down_cb, obj); + edje_object_signal_callback_add(wd->as, + "elm.drag_button,mouse,move", "", + _drag_button_move_cb, obj); + + evas_object_smart_callbacks_descriptions_set(obj, _signals); + _sizing_eval(obj); + return obj; +} + +/** + * Set actionslider indicator position. + * + * @param obj The actionslider object. + * @param pos The position of the indicator. + * + * @ingroup Actionslider + */ +EAPI void +elm_actionslider_indicator_pos_set(Evas_Object *obj, Elm_Actionslider_Pos pos) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + double position = 0.0; + if (!wd) return; + if (pos == ELM_ACTIONSLIDER_CENTER) position = 0.5; + else if (pos == ELM_ACTIONSLIDER_RIGHT) position = 1.0; + edje_object_part_drag_value_set(wd->as, "elm.drag_button_base", position, 0.5); +} + +/** + * Get actionslider indicator position. + * + * @param obj The actionslider object. + * @return The position of the indicator. + * + * @ingroup Actionslider + */ +EAPI Elm_Actionslider_Pos +elm_actionslider_indicator_pos_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_ACTIONSLIDER_NONE; + Widget_Data *wd = elm_widget_data_get(obj); + double position; + if (!wd) return ELM_ACTIONSLIDER_NONE; + + edje_object_part_drag_value_get(wd->as, "elm.drag_button_base", &position, NULL); + if (position < 0.3) + return ELM_ACTIONSLIDER_LEFT; + else if (position < 0.7) + return ELM_ACTIONSLIDER_CENTER; + else + return ELM_ACTIONSLIDER_RIGHT; +} + +/** + * Set actionslider magnet position. + * + * @param obj The actionslider object. + * @param pos Bit mask indicating the magnet positions. + * Example: use (ELM_ACTIONSLIDER_LEFT | ELM_ACTIONSLIDER_RIGHT) + * to put magnet property on both positions + * + * @ingroup Actionslider + */ +EAPI void +elm_actionslider_magnet_pos_set(Evas_Object *obj, Elm_Actionslider_Pos pos) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->magnet_position = pos; +} + +/** + * Get actionslider magnet position. + * + * @param obj The actionslider object. + * @return The positions with magnet property. + * + * @ingroup Actionslider + */ +EAPI Elm_Actionslider_Pos +elm_actionslider_magnet_pos_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_ACTIONSLIDER_NONE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_ACTIONSLIDER_NONE; + return wd->magnet_position; +} + +/** + * Set actionslider enabled position. + * + * All the positions are enabled by default. + * + * @param obj The actionslider object. + * @param pos Bit mask indicating the enabled positions. + * Example: use (ELM_ACTIONSLIDER_LEFT | ELM_ACTIONSLIDER_RIGHT) + * to enable both positions, so the user can select it. + * + * @ingroup Actionslider + */ +EAPI void +elm_actionslider_enabled_pos_set(Evas_Object *obj, Elm_Actionslider_Pos pos) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->enabled_position = pos; +} + +/** + * Get actionslider enabled position. + * + * All the positions are enabled by default. + * + * @param obj The actionslider object. + * @return The enabled positions. + * + * @ingroup Actionslider + */ +EAPI Elm_Actionslider_Pos +elm_actionslider_enabled_pos_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_ACTIONSLIDER_NONE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_ACTIONSLIDER_NONE; + return wd->enabled_position; +} + +/** + * Set actionslider labels. + * + * @param obj The actionslider object + * @param left_label The label which is going to be set. + * @param center_label The label which is going to be set. + * @param right_label The label which is going to be set. + * + * @ingroup Actionslider + */ +EAPI void +elm_actionslider_labels_set(Evas_Object *obj, const char *left_label, const char *center_label, const char *right_label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + eina_stringshare_replace(&wd->text_left, left_label); + edje_object_part_text_set(wd->as, "elm.text.left", left_label); + eina_stringshare_replace(&wd->text_center, center_label); + edje_object_part_text_set(wd->as, "elm.text.center", center_label); + eina_stringshare_replace(&wd->text_right, right_label); + edje_object_part_text_set(wd->as, "elm.text.right", right_label); +} + +/** + * Get actionslider labels. + * + * @param obj The actionslider object + * @param left_label A char** to place the left_label of @p obj into + * @param center_label A char** to place the center_label of @p obj into + * @param right_label A char** to place the right_label of @p obj into + * + * @ingroup Actionslider + */ +EAPI void +elm_actionslider_labels_get(const Evas_Object *obj, const char **left_label, const char **center_label, const char **right_label) +{ + if (left_label) *left_label= NULL; + if (center_label) *center_label= NULL; + if (right_label) *right_label= NULL; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (left_label) *left_label = wd->text_left; + if (center_label) *center_label = wd->text_center; + if (right_label) *right_label = wd->text_right; +} + +/** + * Get actionslider selected label. + * + * @param obj The actionslider object + * @return The selected label + * + * @ingroup Actionslider + */ +EAPI const char * +elm_actionslider_selected_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + if ((wd->final_position == 0.0) && + (wd->enabled_position & ELM_ACTIONSLIDER_LEFT)) + return wd->text_left; + + if ((wd->final_position == 0.5) && + (wd->enabled_position & ELM_ACTIONSLIDER_CENTER)) + return wd->text_center; + + if ((wd->final_position == 1.0) && + (wd->enabled_position & ELM_ACTIONSLIDER_RIGHT)) + return wd->text_right; + + return NULL; +} + +/** + * Set the label used on the indicator object. + * + * @param obj The actionslider object + * @param label The label which is going to be set. + * + * @ingroup Actionslider + */ +EAPI void +elm_actionslider_indicator_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + eina_stringshare_replace(&wd->indicator_label, label); + edje_object_part_text_set(wd->as, "elm.text.indicator", wd->indicator_label); +} + +/** + * Get the label used on the indicator object. + * + * @param obj The actionslider object + * @return The indicator label + * + * @ingroup Actionslider + */ +EAPI const char * +elm_actionslider_indicator_label_get(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->indicator_label; +} diff --git a/src/lib/elm_animator.c b/src/lib/elm_animator.c new file mode 100644 index 0000000..1c642c8 --- /dev/null +++ b/src/lib/elm_animator.c @@ -0,0 +1,446 @@ +#include +#include "elm_priv.h" + +#define ELM_ANIMATOR_CHECK_OR_RETURN(animator, ...) \ + do { \ + if (!animator) { \ + CRITICAL("Elm_Animator " # animator " is NULL!"); \ + return __VA_ARGS__; \ + } \ + if (!EINA_MAGIC_CHECK(animator, ELM_ANIMATOR_MAGIC)) { \ + EINA_MAGIC_FAIL(animator, ELM_ANIMATOR_MAGIC); \ + return __VA_ARGS__; \ + } \ + } while (0) + + +/** + * @addtogroup Animator Animator + * @ingroup Elementary + * + * elm_animator is designed to provides animation frame. + * It is somewhat different with any others widgets however elm_animator + * might useful when your GUIs have animation. + * Basically, it computes normalized frame value for animation, + * provides additional functions to adjust this also. + * + */ + +struct _Elm_Animator +{ +#define ELM_ANIMATOR_MAGIC 0x40777770 + EINA_MAGIC; + + Evas_Object *parent; + Ecore_Animator *animator; + double begin_time; + double cur_time; + double duration; + unsigned int repeat_cnt; + unsigned int cur_repeat_cnt; + void (*animator_op) (void *data, Elm_Animator *animator, double frame); + void *animator_arg; + void (*completion_op) (void *data); + void *completion_arg; + Elm_Animator_Curve_Style curve_style; + Eina_Bool auto_reverse:1; + Eina_Bool on_animating:1; +}; + +static double _animator_curve_linear(double frame); +static double _animator_curve_in_out(double frame); +static double _animator_curve_in(double frame); +static double _animator_curve_out(double frame); +static unsigned int _animator_compute_reverse_repeat_count(unsigned int cnt); +static unsigned int _animator_compute_no_reverse_repeat_count(unsigned int cnt); +static Eina_Bool _animator_animate_cb(void *data); +static void _delete_animator(Elm_Animator *animator); +static void _animator_parent_del(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event __UNUSED__); + +static unsigned int +_animator_compute_reverse_repeat_count(unsigned int cnt) +{ + return ((cnt + 1) * 2) - 1; +} + +static unsigned int +_animator_compute_no_reverse_repeat_count(unsigned int cnt) +{ + return cnt / 2; +} + +static double +_animator_curve_linear(double frame) +{ + return frame; +} + +static double +_animator_curve_in_out(double frame) +{ + if (frame < 0.5) return _animator_curve_in(frame * 2) * 0.5; + else return (_animator_curve_out(frame * 2 - 1) * 0.5) + 0.5; +} + +static double +_animator_curve_in(double frame) +{ + return 1 - sqrt(1 - pow(frame, 2)); +} + +static double +_animator_curve_out(double frame) +{ + return sqrt(1 - pow(frame - 1, 2)); +} + +static void +_delete_animator(Elm_Animator *animator) +{ + if (!animator->animator) return; + ecore_animator_del(animator->animator); + animator->animator = NULL; +} + +static Eina_Bool +_animator_animate_cb(void *data) +{ + double elapsed_time, frame; + Elm_Animator *animator = (Elm_Animator *) data; + + animator->cur_time = ecore_loop_time_get(); + elapsed_time = animator->cur_time - animator->begin_time; + if (elapsed_time > animator->duration) elapsed_time = animator->duration; + + //Compute current frame + switch (animator->curve_style) + { + case ELM_ANIMATOR_CURVE_IN_OUT: + frame = _animator_curve_in_out(elapsed_time / animator->duration); + break; + case ELM_ANIMATOR_CURVE_IN: + frame = _animator_curve_in(elapsed_time / animator->duration); + break; + case ELM_ANIMATOR_CURVE_OUT: + frame = _animator_curve_out(elapsed_time / animator->duration); + break; + default: + frame = _animator_curve_linear(elapsed_time / animator->duration); + break; + } + + //Reverse? + if (animator->auto_reverse) + { + if (!(animator->cur_repeat_cnt % 2)) frame = 1 - frame; + } + + if (animator->duration > 0) + animator->animator_op(animator->animator_arg, animator, frame); + //Not end. Keep going. + if (elapsed_time < animator->duration) return ECORE_CALLBACK_RENEW; + + //Repeat and reverse and time done! + if (!animator->cur_repeat_cnt) + { + animator->on_animating = EINA_FALSE; + _delete_animator(animator); + if (animator->completion_op) + animator->completion_op(animator->completion_arg); + return ECORE_CALLBACK_CANCEL; + } + + //Repeat Case + animator->cur_repeat_cnt--; + animator->begin_time = ecore_loop_time_get(); + + return ECORE_CALLBACK_RENEW; +} + +static void +_animator_parent_del(void *data, Evas *evas __UNUSED__, + Evas_Object *obj __UNUSED__, void *event __UNUSED__) +{ + elm_animator_del(data); +} + +/** + * Get the value of reverse mode. + * + * @param[in] animator Animator object + * @return EINA_TRUE is reverse mode + * + * @ingroup Animator + */ +EAPI Eina_Bool +elm_animator_auto_reverse_get(const Elm_Animator *animator) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator, EINA_FALSE); + return animator->auto_reverse; +} + +/** + * Get the value of repeat count. + * + * @param[in] animator Animator object + * @return Repeat count + * + * @ingroup Animator + */ +EAPI unsigned int +elm_animator_repeat_get(const Elm_Animator *animator) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator, 0); + return animator->repeat_cnt; +} + +/** + * Set the animation acceleration style. + * + * @param[in] animator Animator object + * @param[in] cs Curve style. Default is ELM_ANIMATOR_CURVE_LINEAR + * + * @ingroup Animator + */ +EAPI Elm_Animator_Curve_Style +elm_animator_curve_style_get(const Elm_Animator *animator) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator, ELM_ANIMATOR_CURVE_LINEAR); + + return animator->curve_style; +} + +/** + * Set auto reverse function. + * + * @param[in] animator Animator object + * @param[in] reverse Reverse or not + * + * @ingroup Animator + */ +EAPI void +elm_animator_auto_reverse_set(Elm_Animator *animator, Eina_Bool reverse) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + if (animator->auto_reverse == reverse) return; + animator->auto_reverse = reverse; + if (reverse) + animator->repeat_cnt = + _animator_compute_reverse_repeat_count(animator->repeat_cnt); + else + animator->repeat_cnt = + _animator_compute_no_reverse_repeat_count(animator->repeat_cnt); +} + +/** + * Set the animation acceleration style. + * + * @param[in] animator Animator object + * @param[in] cs Curve style. Default is ELM_ANIMATOR_CURVE_LINEAR + * + * @ingroup Animator + */ +EAPI void +elm_animator_curve_style_set(Elm_Animator *animator, + Elm_Animator_Curve_Style cs) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + + animator->curve_style = cs; +} + +/** + * Set the operation duration. + * + * @param[in] animator Animator object + * @param[in] duration Duration in second + * + * @ingroup Animator + */ +EAPI void +elm_animator_duration_set(Elm_Animator *animator, double duration) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + if (animator->on_animating) return; + animator->duration = duration; +} + +/** + * Set the callback function for animator operation. + * The range of callback function frame data is to 0 ~ 1 + * User can refer this frame value for one's animation frame data. + * @param[in] animator Animator object + * @param[in] func Callback function pointer + * @param[in] data Callback function user argument + * + * @ingroup Animator + */ +EAPI void +elm_animator_operation_callback_set(Elm_Animator *animator, + Elm_Animator_Operation_Cb func, + void *data) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + if (animator->on_animating) return; + animator->animator_op = func; + animator->animator_arg = data; +} + +/** + * Add new animator. + * + * @param[in] parent Parent object + * @return animator object + * + * @ingroup Animator + */ +EAPI Elm_Animator * +elm_animator_add(Evas_Object *parent) +{ + Elm_Animator *animator = ELM_NEW(Elm_Animator); + if (!animator) return NULL; + EINA_MAGIC_SET(animator, ELM_ANIMATOR_MAGIC); + animator->parent = parent; + elm_animator_auto_reverse_set(animator, EINA_FALSE); + elm_animator_curve_style_set(animator, ELM_ANIMATOR_CURVE_LINEAR); + if (parent) + evas_object_event_callback_add(parent, EVAS_CALLBACK_DEL, + _animator_parent_del, animator); + return animator; +} + +/** + * Get the status for the animator operation. + * + * @param[in] animator Animator object + * @return EINA_TRUE is animator is operating. + * + * @ingroup Animator + */ +EAPI Eina_Bool +elm_animator_operating_get(const Elm_Animator *animator) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator, EINA_FALSE); + return animator->on_animating; +} + +/** + * Delete animator. + * + * @param[in] animator Animator object + * + * @ingroup Animator + */ +EAPI void +elm_animator_del(Elm_Animator *animator) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + _delete_animator(animator); + if (animator->parent) + evas_object_event_callback_del(animator->parent, EVAS_CALLBACK_DEL, + _animator_parent_del); + + EINA_MAGIC_SET(animator, EINA_MAGIC_NONE); + free(animator); +} + +/** + * Set the callback function for the animator end. + * + * @param[in] animator Animator object + * @param[in] func Callback function pointe + * @param[in] data Callback function user argument + * + * @ingroup Animator + */ +EAPI void +elm_animator_completion_callback_set(Elm_Animator *animator, + Elm_Animator_Completion_Cb func, + void *data) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + if (animator->on_animating) return; + animator->completion_op = func; + animator->completion_arg = data; +} + +/** + * Pause the animator. + * + * @param[in] animator Animator object + * + * @ingroup Animator + */ +EAPI void +elm_animator_pause(Elm_Animator *animator) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + if (!animator->on_animating) return; + ecore_animator_freeze(animator->animator); +} + +/** + * Resume the animator. + * + * @param[in] animator Animator object + * + * @ingroup Animator + */ +EAPI void +elm_animator_resume(Elm_Animator *animator) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + if (!animator->on_animating) return; + ecore_animator_thaw(animator->animator); +} + +/** + * Stop animator. + * + * @param[in] animator Animator object + * + * @ingroup Animator + */ +EAPI void +elm_animator_stop(Elm_Animator *animator) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + animator->on_animating = EINA_FALSE; + _delete_animator(animator); +} + +/** + * Set the animator repeat count. + * + * @param[in] animator Animator object + * @param[in] repeat_cnt Repeat count + * + * @ingroup Animator + */ +EAPI void +elm_animator_repeat_set(Elm_Animator *animator, unsigned int repeat_cnt) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + if (!animator->auto_reverse) animator->repeat_cnt = repeat_cnt; + else + animator->repeat_cnt = _animator_compute_reverse_repeat_count(repeat_cnt); +} + +/** + * Animate now. + * + * @param[in] animator Animator object + * + * @ingroup Animator + */ +EAPI void +elm_animator_animate(Elm_Animator *animator) +{ + ELM_ANIMATOR_CHECK_OR_RETURN(animator); + if (!animator->animator_op) return; + animator->begin_time = ecore_loop_time_get(); + animator->cur_repeat_cnt = animator->repeat_cnt; + if (!animator->animator) + animator->animator = ecore_animator_add(_animator_animate_cb, animator); + if (animator->animator) animator->on_animating = EINA_TRUE; +} diff --git a/src/lib/elm_bg.c b/src/lib/elm_bg.c new file mode 100644 index 0000000..50dd1e0 --- /dev/null +++ b/src/lib/elm_bg.c @@ -0,0 +1,398 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Bg Bg + * + * The bg object is used for setting a solid background to a window or packing + * into any container object. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *base, *rect, *img, *overlay; + const char *file, *group; + Elm_Bg_Option option; +}; + +static const char *widtype = NULL; + +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _custom_resize(void *data, Evas *a, Evas_Object *obj, void *event_info); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord w, h; + + _elm_theme_object_set(obj, wd->base, "bg", "base", + elm_widget_style_get(obj)); + + if (wd->rect) + edje_object_part_swallow(wd->base, "elm.swallow.rectangle", wd->rect); + if (wd->img) + edje_object_part_swallow(wd->base, "elm.swallow.background", wd->img); + if (wd->overlay) + edje_object_part_swallow(wd->base, "elm.swallow.content", wd->overlay); + +// FIXME: if i don't do this, bg doesnt calc correctly. why? + evas_object_geometry_get(wd->base, NULL, NULL, &w, &h); + evas_object_resize(wd->base, w, h); +} + +static void +_custom_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = data; + Evas_Coord bx = 0, by = 0, bw = 0, bh = 0; + Evas_Coord iw = 0, ih = 0, mw = -1, mh = -1; + Evas_Coord fx = 0, fy = 0, fw = 0, fh = 0; + Evas_Coord nx = 0, ny = 0, nw = 0, nh = 0; + const char *p; + + if ((!wd->img) || (!wd->file)) return; + if (((p = strrchr(wd->file, '.'))) && (!strcasecmp(p, ".edj"))) return; + + /* grab image size */ + evas_object_image_size_get(wd->img, &iw, &ih); + if ((iw < 1) || (ih < 1)) return; + + /* grab base object dimensions */ + evas_object_geometry_get(wd->base, &bx, &by, &bw, &bh); + + /* set some defaults */ + nx = bx; + ny = by; + nw = bw; + nh = bh; + + switch (wd->option) + { + case ELM_BG_OPTION_CENTER: + fw = nw = iw; + fh = nh = ih; + nx = ((bw - fw) / 2); + ny = ((bh - fh) / 2); + mw = iw; + mh = ih; + break; + case ELM_BG_OPTION_SCALE: + fw = bw; + fh = ((ih * fw) / iw); + if (fh < bh) + { + fh = bh; + fw = ((iw * fh) / ih); + } + fx = ((bw - fw) / 2); + fy = ((bh - fh) / 2); + break; + case ELM_BG_OPTION_TILE: + fw = iw; + fh = ih; + break; + case ELM_BG_OPTION_STRETCH: + default: + fw = bw; + fh = bh; + break; + } + + evas_object_move(wd->img, nx, ny); + evas_object_resize(wd->img, nw, nh); + evas_object_image_fill_set(wd->img, fx, fy, fw, fh); + + evas_object_size_hint_min_set(wd->img, mw, mh); + evas_object_size_hint_max_set(wd->img, mw, mh); +} + +/** + * Add a new background to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Bg + */ +EAPI Evas_Object * +elm_bg_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "bg"); + elm_widget_type_set(obj, "bg"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->base = edje_object_add(e); + _elm_theme_object_set(obj, wd->base, "bg", "base", "default"); + elm_widget_resize_object_set(obj, wd->base); + + evas_object_event_callback_add(wd->base, EVAS_CALLBACK_RESIZE, + _custom_resize, wd); + + wd->option = ELM_BG_OPTION_SCALE; + return obj; +} + +/** + * Set the file (image or edje) used for the background + * + * @param obj The bg object + * @param file The file path + * @param group Optional key (group in Edje) within the file + * + * This sets the image file used in the background object. The image (or edje) + * will be stretched (retaining aspect if its an image file) to completely fill + * the bg object. This may mean some parts are not visible. + * + * @note Once the image of @p obj is set, a previously set one will be deleted, + * even if @p file is NULL. + * + * @ingroup Bg + */ +EAPI void +elm_bg_file_set(Evas_Object *obj, const char *file, const char *group) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + const char *p; + + if (wd->img) + { + evas_object_del(wd->img); + wd->img = NULL; + } + if (!file) + { + eina_stringshare_del(wd->file); + wd->file = NULL; + eina_stringshare_del(wd->group); + wd->group = NULL; + return; + } + eina_stringshare_replace(&wd->file, file); + eina_stringshare_replace(&wd->group, group); + if (((p = strrchr(file, '.'))) && (!strcasecmp(p, ".edj"))) + { + wd->img = edje_object_add(evas_object_evas_get(wd->base)); + edje_object_file_set(wd->img, file, group); + } + else + { + wd->img = evas_object_image_add(evas_object_evas_get(wd->base)); + evas_object_image_file_set(wd->img, file, group); + } + evas_object_repeat_events_set(wd->img, EINA_TRUE); + edje_object_part_swallow(wd->base, "elm.swallow.background", wd->img); + elm_widget_sub_object_add(obj, wd->img); + _custom_resize(wd, NULL, NULL, NULL); +} + +/** + * Get the file (image or edje) used for the background + * + * @param obj The bg object + * @param file The file path + * @param group Optional key (group in Edje) within the file + * + * @ingroup Bg + */ +EAPI void +elm_bg_file_get(const Evas_Object *obj, const char **file, const char **group) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (file) *file = wd->file; + if (group) *group = wd->group; +} + +/** + * Set the option used for the background image + * + * @param obj The bg object + * @param option The desired background option (TILE, SCALE) + * + * This sets the option used for manipulating the display of the background + * image. The image can be tiled or scaled. + * + * @ingroup Bg + */ +EAPI void +elm_bg_option_set(Evas_Object *obj, Elm_Bg_Option option) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + wd->option = option; + _custom_resize(wd, NULL, NULL, NULL); +} + +/** + * Get the option used for the background image + * + * @param obj The bg object + * @return The desired background option (TILE, SCALE) + * + * @ingroup Bg + */ +EAPI Elm_Bg_Option +elm_bg_option_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + return wd->option; +} + +/** + * Set the option used for the background color + * + * @param obj The bg object + * @param r + * @param g + * @param b + * + * This sets the color used for the background rectangle. + * + * @ingroup Bg + */ +EAPI void +elm_bg_color_set(Evas_Object *obj, int r, int g, int b) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd->rect) + { + wd->rect = evas_object_rectangle_add(evas_object_evas_get(wd->base)); + edje_object_part_swallow(wd->base, "elm.swallow.rectangle", wd->rect); + elm_widget_sub_object_add(obj, wd->rect); + _custom_resize(wd, NULL, NULL, NULL); + } + evas_object_color_set(wd->rect, r, g, b, 255); +} + +/** + * Get the option used for the background color + * + * @param obj The bg object + * @param r + * @param g + * @param b + * + * @ingroup Bg + */ +EAPI void +elm_bg_color_get(const Evas_Object *obj, int *r, int *g, int *b) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + evas_object_color_get(wd->rect, r, g, b, NULL); +} + +/** + * Set the overlay object used for the background object. + * + * @param obj The bg object + * @param overlay The overlay object + * + * This provides a way for elm_bg to have an 'overlay' (such as animated fog) + * Once the over object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_bg_overlay_unset() function. + * + * @ingroup Bg + */ +EAPI void +elm_bg_overlay_set(Evas_Object *obj, Evas_Object *overlay) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->overlay) + { + evas_object_del(wd->overlay); + wd->overlay = NULL; + } + if (overlay) + { + wd->overlay = overlay; + edje_object_part_swallow(wd->base, "elm.swallow.content", wd->overlay); + elm_widget_sub_object_add(obj, wd->overlay); + } + + _custom_resize(wd, NULL, NULL, NULL); +} + +/** + * Set the overlay object used for the background object. + * + * @param obj The bg object + * @return The content that is being used + * + * Return the content object which is set for this widget + * + * @ingroup Bg + */ +EAPI Evas_Object * +elm_bg_overlay_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->overlay; +} + +/** + * Get the overlay object used for the background object. + * + * @param obj The bg object + * @return The content that was being used + * + * Unparent and return the overlay object which was set for this widget + * + * @ingroup Bg + */ +EAPI Evas_Object * +elm_bg_overlay_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *overlay; + if (!wd) return NULL; + if (!wd->overlay) return NULL; + overlay = wd->overlay; + elm_widget_sub_object_del(obj, wd->overlay); + edje_object_part_unswallow(wd->base, wd->overlay); + wd->overlay = NULL; + _custom_resize(wd, NULL, NULL, NULL); + return overlay; +} diff --git a/src/lib/elm_box.c b/src/lib/elm_box.c new file mode 100644 index 0000000..0d6449d --- /dev/null +++ b/src/lib/elm_box.c @@ -0,0 +1,894 @@ +#include +#include "elm_priv.h" + +#define SIG_CHILD_ADDED "child,added" +#define SIG_CHILD_REMOVED "child,removed" + +/** + * @defgroup Box Box + * + * A box object arranges objects in a single row within a box. Sub objects can + * be added at the start, end or before or after any existing object in the + * box already. It can have its orientation changed too. How a child object is + * sized and otherwise arranged within the box depends on evas hints. + * evas_object_size_hint_align_set() will set either the alignment within its + * region if the region allocated is bigger than the object size. If you want + * the sub object sized up to fill the allocated region, use -1.0 for the + * apporpriate horizontal or vertical axes. evas_object_size_hint_weight_set() + * will set the packing weight. The weights of all items being packed are added + * up and if items are to be sized up to fit, those with the higher weights get + * proportionally more space. + * + * NOTE: Objects should not be added to box objects using _add() calls. + */ +typedef struct _Widget_Data Widget_Data; +typedef struct _Transition_Animation_Data Transition_Animation_Data; + +struct _Widget_Data +{ + Evas_Object *box; + Eina_Bool horizontal:1; + Eina_Bool homogeneous:1; +}; + +struct _Elm_Box_Transition +{ + double initial_time; + double duration; + Eina_Bool animation_ended:1; + Eina_Bool recalculate:1; + Ecore_Animator *animator; + + struct + { + Evas_Object_Box_Layout layout; + void *data; + void(*free_data)(void *data); + } start, end; + + void(*transition_end_cb)(void *data); + void *transition_end_data; + void (*transition_end_free_data)(void *data); + Eina_List *objs; + Evas_Object *box; +}; + +struct _Transition_Animation_Data +{ + Evas_Object *obj; + struct + { + Evas_Coord x, y, w, h; + } start, end; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_event_callback_del_full + (wd->box, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + evas_object_box_remove_all(wd->box, 0); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void * +_elm_box_list_data_get(const Eina_List *list) +{ + Evas_Object_Box_Option *opt = eina_list_data_get(list); + return opt->obj; +} + +static Eina_Bool +_elm_box_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const Eina_List *items; + void *(*list_data_get) (const Eina_List *list); + + if ((!wd) || (!wd->box)) + return EINA_FALSE; + + /* Focus chain */ + /* TODO: Change this to use other chain */ + if ((items = elm_widget_focus_custom_chain_get(obj))) + list_data_get = eina_list_data_get; + else + { + Evas_Object_Box_Data *bd = evas_object_smart_data_get(wd->box); + items = bd->children; + list_data_get = _elm_box_list_data_get; + + if (!items) return EINA_FALSE; + } + + return elm_widget_focus_list_next_get(obj, items, list_data_get, dir, next); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + Evas_Coord w, h; + if (!wd) return; + evas_object_size_hint_min_get(wd->box, &minw, &minh); + evas_object_size_hint_max_get(wd->box, &maxw, &maxh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); + evas_object_geometry_get(obj, NULL, NULL, &w, &h); + if (w < minw) w = minw; + if (h < minh) h = minh; + if ((maxw >= 0) && (w > maxw)) w = maxw; + if ((maxh >= 0) && (h > maxh)) h = maxh; + evas_object_resize(obj, w, h); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + _sizing_eval(obj); +} + +static void +_layout(Evas_Object *o, Evas_Object_Box_Data *priv, void *data) +{ + Widget_Data *wd = data; + if (!wd) return; + _els_box_layout(o, priv, wd->horizontal, wd->homogeneous); +} + +static Eina_Bool +_transition_animation(void *data) +{ + evas_object_smart_changed(data); + return ECORE_CALLBACK_RENEW; +} + +static void +_transition_layout_child_added(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Transition_Animation_Data *tad; + Evas_Object_Box_Option *opt = event_info; + Elm_Box_Transition *layout_data = data; + + tad = calloc(1, sizeof(Transition_Animation_Data)); + if (!tad) return; + tad->obj = opt->obj; + layout_data->objs = eina_list_append(layout_data->objs, tad); + layout_data->recalculate = EINA_TRUE; +} + +static void +_transition_layout_child_removed(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Eina_List *l; + Transition_Animation_Data *tad; + Elm_Box_Transition *layout_data = data; + + EINA_LIST_FOREACH(layout_data->objs, l, tad) + { + if (tad->obj == event_info) + { + free(eina_list_data_get(l)); + layout_data->objs = eina_list_remove_list(layout_data->objs, l); + layout_data->recalculate = EINA_TRUE; + break; + } + } +} + +static void +_transition_layout_obj_resize_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Box_Transition *layout_data = data; + layout_data->recalculate = EINA_TRUE; +} + +static void +_transition_layout_calculate_coords(Evas_Object *obj, Evas_Object_Box_Data *priv, + Elm_Box_Transition *layout_data) +{ + Eina_List *l; + Transition_Animation_Data *tad; + Evas_Coord x, y, w, h; + const double curtime = ecore_loop_time_get(); + + layout_data->duration = + layout_data->duration - (curtime - layout_data->initial_time); + layout_data->initial_time = curtime; + + evas_object_geometry_get(obj, &x, &y, &w, &h); + EINA_LIST_FOREACH(layout_data->objs, l, tad) + { + evas_object_geometry_get(tad->obj, &tad->start.x, &tad->start.y, + &tad->start.w, &tad->start.h); + tad->start.x = tad->start.x - x; + tad->start.y = tad->start.y - y; + } + layout_data->end.layout(obj, priv, layout_data->end.data); + EINA_LIST_FOREACH(layout_data->objs, l, tad) + { + evas_object_geometry_get(tad->obj, &tad->end.x, &tad->end.y, + &tad->end.w, &tad->end.h); + tad->end.x = tad->end.x - x; + tad->end.y = tad->end.y - y; + } +} + +static Eina_Bool +_transition_layout_load_children_list(Evas_Object_Box_Data *priv, + Elm_Box_Transition *layout_data) +{ + Eina_List *l; + Evas_Object_Box_Option *opt; + Transition_Animation_Data *tad; + + EINA_LIST_FREE(layout_data->objs, tad) + free(tad); + + EINA_LIST_FOREACH(priv->children, l, opt) + { + tad = calloc(1, sizeof(Transition_Animation_Data)); + if (!tad) + { + EINA_LIST_FREE(layout_data->objs, tad) + free(tad); + layout_data->objs = NULL; + return EINA_FALSE; + } + tad->obj = opt->obj; + layout_data->objs = eina_list_append(layout_data->objs, tad); + } + return EINA_TRUE; +} + +static Eina_Bool +_transition_layout_animation_start(Evas_Object *obj, Evas_Object_Box_Data *priv, + Elm_Box_Transition *layout_data, Eina_Bool(*transition_animation_cb)(void *data)) +{ + layout_data->start.layout(obj, priv, layout_data->start.data); + layout_data->box = obj; + layout_data->initial_time = ecore_loop_time_get(); + + if (!_transition_layout_load_children_list(priv, layout_data)) + return EINA_FALSE; + _transition_layout_calculate_coords(obj, priv, layout_data); + + evas_object_event_callback_add(obj, EVAS_CALLBACK_RESIZE, + _transition_layout_obj_resize_cb, layout_data); + evas_object_smart_callback_add(obj, SIG_CHILD_ADDED, + _transition_layout_child_added, layout_data); + evas_object_smart_callback_add(obj, SIG_CHILD_REMOVED, + _transition_layout_child_removed, layout_data); + if (!layout_data->animator) + layout_data->animator = ecore_animator_add(transition_animation_cb, obj); + layout_data->animation_ended = EINA_FALSE; + return EINA_TRUE; +} + +static void +_transition_layout_animation_stop(Elm_Box_Transition *layout_data) +{ + layout_data->animation_ended = EINA_TRUE; + if (layout_data->animator) + { + ecore_animator_del(layout_data->animator); + layout_data->animator = NULL; + } + + if (layout_data->transition_end_cb) + layout_data->transition_end_cb(layout_data->transition_end_data); +} + +static void +_transition_layout_animation_exec(Evas_Object *obj, Evas_Object_Box_Data *priv __UNUSED__, + Elm_Box_Transition *layout_data, const double curtime) +{ + Eina_List *l; + Transition_Animation_Data *tad; + Evas_Coord x, y, w, h; + Evas_Coord cur_x, cur_y, cur_w, cur_h; + double progress = 0.0; + + progress = (curtime - layout_data->initial_time) / layout_data->duration; + evas_object_geometry_get(obj, &x, &y, &w, &h); + + EINA_LIST_FOREACH(layout_data->objs, l, tad) + { + cur_x = x + tad->start.x + ((tad->end.x - tad->start.x) * progress); + cur_y = y + tad->start.y + ((tad->end.y - tad->start.y) * progress); + cur_w = tad->start.w + ((tad->end.w - tad->start.w) * progress); + cur_h = tad->start.h + ((tad->end.h - tad->start.h) * progress); + evas_object_move(tad->obj, cur_x, cur_y); + evas_object_resize(tad->obj, cur_w, cur_h); + } +} + +/** + * Add a new box to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Box + */ +EAPI Evas_Object * +elm_box_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "box"); + elm_widget_type_set(obj, "box"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_focus_next_hook_set(obj, _elm_box_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + elm_widget_highlight_ignore_set(obj, EINA_TRUE); + + wd->box = evas_object_box_add(e); + /*evas_object_box_layout_set(wd->box, evas_object_box_layout_vertical, + NULL, NULL);*/ + evas_object_box_layout_set(wd->box, _layout, wd, NULL); + + evas_object_event_callback_add(wd->box, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + elm_widget_resize_object_set(obj, wd->box); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + return obj; +} + +/** + * Set the horizontal orientation + * + * By default box object arrange their contents vertically from top to bottom. + * By calling this and providing @p horizontal as true, the box will become + * horizontal arranging contents left to right. + * + * @param obj The box object + * @param horizontal The horizontal flag (1 = horizontal, 0 = vertical) + * + * @ingroup Box + */ +EAPI void +elm_box_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->horizontal = !!horizontal; + evas_object_smart_calculate(wd->box); + /*if (wd->horizontal) + { + if (wd->homogeneous) + evas_object_box_layout_set(wd->box, + evas_object_box_layout_homogeneous_horizontal, NULL, NULL); + else + evas_object_box_layout_set(wd->box, evas_object_box_layout_horizontal, + NULL, NULL); + } + else + { + if (wd->homogeneous) + evas_object_box_layout_set(wd->box, + evas_object_box_layout_homogeneous_vertical, NULL, NULL); + else + evas_object_box_layout_set(wd->box, evas_object_box_layout_horizontal, + NULL, NULL); + }*/ +} + +/** + * Get the horizontal orientation + * + * @param obj The box object + * @return If is horizontal + * + * @ingroup Box + */ +EAPI Eina_Bool +elm_box_horizontal_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->horizontal; +} + +/** + * Set homogenous layout + * + * If enabled, homogenous layout makes all items the same size. This size is + * of course governed by the size of the largest item in the box. + * + * @param obj The box object + * @param homogenous The homogenous flag (1 = on, 2 = off) + * + * @ingroup Box + */ +EAPI void +elm_box_homogenous_set(Evas_Object *obj, Eina_Bool homogenous) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->homogeneous = !!homogenous; + evas_object_smart_calculate(wd->box); + /*if (wd->horizontal) + { + if (wd->homogeneous) + evas_object_box_layout_set(wd->box, + evas_object_box_layout_homogeneous_horizontal, NULL, NULL); + else + evas_object_box_layout_set(wd->box, evas_object_box_layout_horizontal, + NULL, NULL); + } + else + { + if (wd->homogeneous) + evas_object_box_layout_set(wd->box, + evas_object_box_layout_homogeneous_vertical, NULL, NULL); + else + evas_object_box_layout_set(wd->box, evas_object_box_layout_horizontal, + NULL, NULL); + }*/ +} + +/** + * Get homogenous layout + * + * @param obj The box object + * @return If is homogenous + * + * @ingroup Box + */ +EAPI Eina_Bool +elm_box_homogenous_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->homogeneous; +} + +/** + * This adds a box at the start of the box (top or left based on orientation) + * + * This will add the @p subobj to the box object indicated at the beginning + * of the box (the left or top end). + * + * @param obj The box object + * @param subobj The object to add to the box + * + * @ingroup Box + */ +EAPI void +elm_box_pack_start(Evas_Object *obj, Evas_Object *subobj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_widget_sub_object_add(obj, subobj); + evas_object_box_prepend(wd->box, subobj); +} + +/** + * This adds a box at the end of the box (bottom or right based on orientation) + * + * This will add the @p subobj to the box object indicated at the end + * of the box (the right or bottom end). + * + * @param obj The box object + * @param subobj The object to add to the box + * + * @ingroup Box + */ +EAPI void +elm_box_pack_end(Evas_Object *obj, Evas_Object *subobj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_widget_sub_object_add(obj, subobj); + evas_object_box_append(wd->box, subobj); +} + +/** + * This adds adds an object to the box before the indicated object + * + * This will add the @p subobj to the box indicated before the object + * indicated with @p before. If @p before is not already in the box, results + * are undefined. Before means either to the left of the indicated object or + * above it depending on orientation. + * + * @param obj The box object + * @param subobj The object to add to the box + * @param before The object before which to add it + * + * @ingroup Box + */ +EAPI void +elm_box_pack_before(Evas_Object *obj, Evas_Object *subobj, Evas_Object *before) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_widget_sub_object_add(obj, subobj); + evas_object_box_insert_before(wd->box, subobj, before); +} + +/** + * This adds adds an object to the box after the indicated object + * + * This will add the @p subobj to the box indicated after the object + * indicated with @p after. If @p after is not already in the box, results + * are undefined. After means either to the right of the indicated object or + * below it depending on orientation. + * + * @param obj The box object + * @param subobj The object to add to the box + * @param after The object after which to add it + * + * @ingroup Box + */ +EAPI void +elm_box_pack_after(Evas_Object *obj, Evas_Object *subobj, Evas_Object *after) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_widget_sub_object_add(obj, subobj); + evas_object_box_insert_after(wd->box, subobj, after); +} + +/** + * This clears the box items + * + * This delete all members of the box object, but not the box itself. + * + * @param obj The box object + * + * @ingroup Box + */ +EAPI void +elm_box_clear(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_box_remove_all(wd->box, EINA_TRUE); +} + +/** + * This unpack a box item + * + * This unpack the selected member from the box object, but does not delete + * the box itself or the packed items. + * + * @param obj The box object + * + * @ingroup Box + */ +EAPI void +elm_box_unpack(Evas_Object *obj, Evas_Object *subobj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_box_remove(wd->box, subobj); +} + +/** + * This unpack the box items + * + * This unpack all members from the box object, but does not delete + * the box itself or the packed items. + * + * @param obj The box object + * + * @ingroup Box + */ +EAPI void +elm_box_unpack_all(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_box_remove_all(wd->box, EINA_FALSE); +} + +/** + * Set the callback layout function (@p cb) to the @p obj elm_box class. + * + * This function will use evas_object_box_layout_set() to set @p cb as the + * layout callback function for this box object. + * All layout funtions from evas_object_box can be used as @p cb. Some examples + * are evas_object_box_layout_horizontal, evas_object_box_layout_vertical and + * evas_object_box_layout_stack. elm_box_layout_transition can also be used. + * If @p cb is NULL, the default layout function from elm_box will be used. + * + * @note Changing the layout function will make horizontal/homogeneous fields + * from Widget_Data have NO further usage as they are controlled by default + * layout function. So calling elm_box_horizontal_set() or + * elm_box_homogenous_set() won't affect layout behavior. + * + * @param obj The box object + * @param cb The callback function used for layout + * @param data Data that will be passed to layout function + * @param free_data Function called to free @p data + * + * @ingroup Box + */ +EAPI void +elm_box_layout_set(Evas_Object *obj, Evas_Object_Box_Layout cb, const void *data, void (*free_data)(void *data)) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (cb) + evas_object_box_layout_set(wd->box, cb, data, free_data); + else + evas_object_box_layout_set(wd->box, _layout, wd, NULL); +} + +/** + * Layout function which display a transition animation from start layout to end layout. + * + * This function should no be called directly. It may be used by elm_box_layout_set() or + * evas_object_box_layout_set() as a layout function. + * The @p data passed to this function must be a Elm_Box_Transition*, that can be created + * using elm_box_transition_new() and freed with elm_box_transition_free(). + * + * Usage Example: + * @code + * Evas_Object *box = elm_box_add(parent); + * Elm_Box_Transition *t = elm_box_transition_new(...add params here...); + * elm_box_layout_set(box, elm_box_layout_transition, t, elm_box_transition_free); + * @endcode + * + * @see elm_box_transition_new + * @see elm_box_transition_free + * @see elm_box_layout_set + * + * @ingroup Box + * @warning Do not call this function directly because the @p obj is not the Widget Box + * from elm_box_add(), it is the internal Evas_Object of the Widget Box. + */ +EAPI void +elm_box_layout_transition(Evas_Object *obj, Evas_Object_Box_Data *priv, void *data) +{ + Elm_Box_Transition *box_data = data; + const double curtime = ecore_loop_time_get(); + + if (box_data->animation_ended) + { + box_data->end.layout(obj, priv, box_data->end.data); + return; + } + + if (!box_data->animator) + { + if (!_transition_layout_animation_start(obj, priv, box_data, + _transition_animation)) + return; + } + else + { + if (box_data->recalculate) + { + _transition_layout_calculate_coords(obj, priv, box_data); + box_data->recalculate = EINA_FALSE; + } + } + + if ((curtime >= box_data->duration + box_data->initial_time)) + _transition_layout_animation_stop(box_data); + else + _transition_layout_animation_exec(obj, priv, box_data, curtime); +} + +/** + * Create a new Elm_Box_Transition setted with informed parameters. + * + * The returned instance may be used as data parameter to elm_box_layout_transition() + * and should be freed with elm_box_transition_free(). + * + * @param start_layout The layout function that will be used to start the animation + * @param start_layout_data The data to be passed the @p start_layout function + * @param start_layout_free_data Function to free @p start_layout_data + * @param end_layout The layout function that will be used to end the animation + * @param end_layout_free_data The data to be passed the @p end_layout function + * @param end_layout_free_data Function to free @p end_layout_data + * @param transition_end_cb Callback function called when animation ends + * @param transition_end_data Data to be passed to @p transition_end_cb + * @return An instance of Elm_Box_Transition setted with informed parameters + * + * @see elm_box_transition_new + * @see elm_box_layout_transition + * + * @ingroup Box + */ +EAPI Elm_Box_Transition * +elm_box_transition_new(const double duration, + Evas_Object_Box_Layout start_layout, void *start_layout_data, + void(*start_layout_free_data)(void *data), + Evas_Object_Box_Layout end_layout, void *end_layout_data, + void(*end_layout_free_data)(void *data), + void(*transition_end_cb)(void *data), + void *transition_end_data) +{ + Elm_Box_Transition *box_data; + + EINA_SAFETY_ON_NULL_RETURN_VAL(start_layout, NULL); + EINA_SAFETY_ON_NULL_RETURN_VAL(end_layout, NULL); + + box_data = calloc(1, sizeof(Elm_Box_Transition)); + if (!box_data) + return NULL; + + box_data->start.layout = start_layout; + box_data->start.data = start_layout_data; + box_data->start.free_data = start_layout_free_data; + box_data->end.layout = end_layout; + box_data->end.data = end_layout_data; + box_data->end.free_data = end_layout_free_data; + box_data->duration = duration; + box_data->transition_end_cb = transition_end_cb; + box_data->transition_end_data = transition_end_data; + return box_data; +} + +/** + * Free a Elm_Box_Transition instance created with elm_box_transition_new(). + * + * @param data The Elm_Box_Transition instance to be freed. + * + * @see elm_box_transition_new + * @see elm_box_layout_transition + * + * @ingroup Box + */ +EAPI void +elm_box_transition_free(void *data) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + + Transition_Animation_Data *tad; + Elm_Box_Transition *box_data = data; + if ((box_data->start.free_data) && (box_data->start.data)) + box_data->start.free_data(box_data->start.data); + if ((box_data->end.free_data) && (box_data->end.data)) + box_data->end.free_data(box_data->end.data); + EINA_LIST_FREE(box_data->objs, tad) + free(tad); + evas_object_event_callback_del(box_data->box, EVAS_CALLBACK_RESIZE, _transition_layout_obj_resize_cb); + evas_object_smart_callback_del(box_data->box, SIG_CHILD_ADDED, _transition_layout_child_added); + evas_object_smart_callback_del(box_data->box, SIG_CHILD_REMOVED, _transition_layout_child_removed); + if (box_data->animator) + { + ecore_animator_del(box_data->animator); + box_data->animator = NULL; + } + free(data); +} + +/** + * Retrieve the list of children packed into an elm_box + * + * @param obj The Elm_Box + * + * @ingroup Box + */ +EAPI const Eina_List * +elm_box_children_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return evas_object_box_children_get(wd->box); +} + +/** + * Set the space (padding) between the box's elements. + * + * @param obj The Elm_Box + * @param horizontal The horizontal space between elements + * @param vertical The vertical space between elements + * + * @ingroup Box + */ +EAPI void +elm_box_padding_set(Evas_Object *obj, Evas_Coord horizontal, Evas_Coord vertical) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_box_padding_set(wd->box, horizontal, vertical); +} + +/** + * Get the space (padding) between the box's elements. + * + * @param obj The Elm_Box + * @param horizontal The horizontal space between elements + * @param vertical The vertical space between elements + * + * @ingroup Box + */ +EAPI void +elm_box_padding_get(const Evas_Object *obj, Evas_Coord *horizontal, Evas_Coord *vertical) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_box_padding_get(wd->box, horizontal, vertical); +} + +/** + * Set the alignment of the whole bouding box of contents. + * + * @param obj The Elm_Box + * @param horizontal The horizontal alignment of elements + * @param vertical The vertical alignment of elements + * + * @ingroup Box + */ +EAPI void +elm_box_align_set(Evas_Object *obj, double horizontal, double vertical) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_box_align_set(wd->box, horizontal, vertical); +} + +/** + * Get the alignment of the whole bouding box of contents. + * + * @param obj The Elm_Box + * @param horizontal The horizontal alignment of elements + * @param vertical The vertical alignment of elements + * + * @ingroup Box + */ +EAPI void +elm_box_align_get(const Evas_Object *obj, double *horizontal, double *vertical) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_box_align_get(wd->box, horizontal, vertical); +} diff --git a/src/lib/elm_bubble.c b/src/lib/elm_bubble.c new file mode 100644 index 0000000..2be1dcd --- /dev/null +++ b/src/lib/elm_bubble.c @@ -0,0 +1,476 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Bubble Bubble + * + * The Bubble is an widget used to show a text in a frame as speech is + * represented in comics. + * + * Signals that you can add callbacks for are: + * + * clicked - This is called when a user has clicked the bubble. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *bbl; + Evas_Object *content, *icon; + const char *label, *info, *corner; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); + +#define SIG_CLICKED "clicked" +static const Evas_Smart_Cb_Description _signals[] = +{ + {SIG_CLICKED, ""}, + {NULL, NULL} +}; + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->label) eina_stringshare_del(wd->label); + if (wd->info) eina_stringshare_del(wd->info); + if (wd->corner) eina_stringshare_del(wd->corner); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->bbl, "bubble", wd->corner, + elm_widget_style_get(obj)); + edje_object_part_text_set(wd->bbl, "elm.text", wd->label); + if (wd->label) edje_object_signal_emit(wd->bbl, "elm,state,text,visible", "elm"); + else edje_object_signal_emit(wd->bbl, "elm,state,text,hidden", "elm"); + edje_object_part_text_set(wd->bbl, "elm.info", wd->info); + if (wd->info) edje_object_signal_emit(wd->bbl, "elm,state,info,visible", "elm"); + else edje_object_signal_emit(wd->bbl, "elm,state,info,hidden", "elm"); + if (wd->content) + { + edje_object_part_swallow(wd->bbl, "elm.swallow.content", wd->content); + edje_object_message_signal_process(wd->bbl); + } + if (wd->icon) + edje_object_signal_emit(wd->bbl, "elm,state,icon,visible", "elm"); + else + edje_object_signal_emit(wd->bbl, "elm,state,icon,hidden", "elm"); + edje_object_scale_set(wd->bbl, + elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static Eina_Bool +_elm_bubble_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *cur; + + if ((!wd) || (!wd->content)) + return EINA_FALSE; + + cur = wd->content; + + /* Try Focus cycle in subitem */ + return elm_widget_focus_next_get(cur, dir, next); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->bbl, &minw, &minh, minw, minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + if (sub == wd->content) wd->content = NULL; + else if (sub == wd->icon) + { + edje_object_signal_emit(wd->bbl, "elm,state,icon,hidden", "elm"); + wd->icon = NULL; + edje_object_message_signal_process(wd->bbl); + } + _sizing_eval(obj); +} + +static void +_mouse_up(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Up *ev = event_info; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + return; + evas_object_smart_callback_call(data, SIG_CLICKED, NULL); +} + +/** + * Add a new bubble to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * This function adds a text bubble to the given parent evas object. + * + * @ingroup Bubble + */ +EAPI Evas_Object * +elm_bubble_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "bubble"); + elm_widget_type_set(obj, "bubble"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_focus_next_hook_set(obj, _elm_bubble_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->corner = eina_stringshare_add("base"); + + wd->bbl = edje_object_add(e); + _elm_theme_object_set(obj, wd->bbl, "bubble", "base", "default"); + elm_widget_resize_object_set(obj, wd->bbl); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + evas_object_event_callback_add(wd->bbl, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, obj); + + evas_object_smart_callbacks_descriptions_set(obj, _signals); + _sizing_eval(obj); + return obj; +} + +/** + * Set the label of the bubble + * + * @param obj The bubble object + * @param label The string to set in the label + * + * This function sets the title of the bubble that is shown on top of + * the bubble. + * + * @ingroup Bubble + */ +EAPI void +elm_bubble_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->label, label); + edje_object_part_text_set(wd->bbl, "elm.text", label); + if (label) edje_object_signal_emit(wd->bbl, "elm,state,text,visible", "elm"); + else edje_object_signal_emit(wd->bbl, "elm,state,text,hidden", "elm"); + _sizing_eval(obj); +} + +/** + * Get the label of the bubble + * + * @param obj The bubble object + * @return The string of set in the label + * + * This function gets the title of the bubble that is shown on top of + * the bubble. + * + * @ingroup Bubble + */ +EAPI const char* +elm_bubble_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the info of the bubble + * + * @param obj The bubble object + * @param info The given info about the bubble + * + * This function sets the text shown on the top right of bubble. + * In the Anchorblock example of the Elementary tests application it + * shows time. + * + * @ingroup Bubble + * + */ +EAPI void +elm_bubble_info_set(Evas_Object *obj, const char *info) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->info, info); + edje_object_part_text_set(wd->bbl, "elm.info", info); + if (info) edje_object_signal_emit(wd->bbl, "elm,state,info,visible", "elm"); + else edje_object_signal_emit(wd->bbl, "elm,state,info,hidden", "elm"); + _sizing_eval(obj); +} + +/** + * Get the info of the bubble + * + * @param obj The bubble object + * + * @return The "info" string of the bubble + * + * This function gets the text set to be displayed at the top right of + * the bubble. + * + * @ingroup Bubble + * + */ +EAPI const char * +elm_bubble_info_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->info; +} + +/** + * Set the content to be shown in the bubble + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep the old content object, use the + * elm_bubble_content_unset() function. + * + * @param obj The bubble object + * @param content The given content of the bubble + * + * This function sets the content shown on the middle of the bubble. + * In the Anchorblock example of the Elementary tests application it + * shows time. + * + * @ingroup Bubble + */ +EAPI void +elm_bubble_content_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->content == content) return; + if (wd->content) evas_object_del(wd->content); + wd->content = content; + if (content) + { + elm_widget_sub_object_add(obj, content); + evas_object_event_callback_add(content, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->bbl, "elm.swallow.content", content); + } + _sizing_eval(obj); +} + +/** + * Get the content shown in the bubble + * + * Return the content object which is set for this widget. + * + * @param obj The bubble object + * @return The content that is being used + * + * @ingroup Bubble + */ +EAPI Evas_Object * +elm_bubble_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->content; +} + +/** + * Unset the content shown in the bubble + * + * Unparent and return the content object which was set for this widget. + * + * @param obj The bubble object + * @return The content that was being used + * + * @ingroup Bubble + */ +EAPI Evas_Object * +elm_bubble_content_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *content; + if (!wd) return NULL; + if (!wd->content) return NULL; + content = wd->content; + elm_widget_sub_object_del(obj, content); + edje_object_part_unswallow(wd->bbl, content); + wd->content = NULL; + return content; +} + +/** + * Set the icon of the bubble + * + * Once the icon object is set, a previously set one will be deleted. + * If you want to keep the old content object, use the + * elm_icon_content_unset() function. + * + * @param obj The bubble object + * @param icon The given icon for the bubble + * + * @ingroup Bubble + */ +EAPI void +elm_bubble_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->icon == icon) return; + if (wd->icon) evas_object_del(wd->icon); + wd->icon = icon; + if (icon) + { + elm_widget_sub_object_add(obj, icon); + edje_object_part_swallow(wd->bbl, "elm.swallow.icon", icon); + evas_object_event_callback_add(icon, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_signal_emit(wd->bbl, "elm,state,icon,visible", "elm"); + edje_object_message_signal_process(wd->bbl); + } + _sizing_eval(obj); +} + +/** + * Get the icon of the bubble + * + * @param obj The bubble object + * @return The icon for the bubble + * + * This function gets the icon shown on the top left of bubble. + * + * @ingroup Bubble + */ +EAPI Evas_Object * +elm_bubble_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->icon; +} + +/** + * Unset the icon of the bubble + * + * Unparent and return the icon object which was set for this widget. + * + * @param obj The bubble object + * @return The icon that was being used + * + * @ingroup Bubble + */ +EAPI Evas_Object * +elm_bubble_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *icon; + if (!wd) return NULL; + if (!wd->icon) return NULL; + icon = wd->icon; + elm_widget_sub_object_del(obj, icon); + edje_object_part_unswallow(wd->bbl, icon); + wd->icon = NULL; + return icon; +} + +/** + * Set the corner of the bubble + * + * @param obj The bubble object. + * @param corner The given corner for the bubble. + * + * This function sets the corner of the bubble. + * The corner will be used to find the group in the theme + * For example, if you set the corner to "bottom_right", + * the following group will be searched: + * "elm/bubble/bottom_right/default", + * considering default style. + * + * @ingroup Bubble + */ +EAPI void +elm_bubble_corner_set(Evas_Object *obj, const char *corner) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(corner); + eina_stringshare_replace(&wd->corner, corner); + _theme_hook(obj); +} + +/** + * Get the corner of the bubble + * + * @param obj The bubble object. + * @return The given corner for the bubble. + * + * This function gets the corner of the bubble. + * + * @ingroup Bubble + */ +EAPI const char* +elm_bubble_corner_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->corner; +} diff --git a/src/lib/elm_button.c b/src/lib/elm_button.c new file mode 100644 index 0000000..6ebd759 --- /dev/null +++ b/src/lib/elm_button.c @@ -0,0 +1,564 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Button Button + * + * This is a push-button. Press it and run some function. It can contain + * a simple label and icon object. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *btn, *icon; + const char *label; + Eina_Bool autorepeat; + Eina_Bool repeating; + double ar_threshold; + double ar_interval; + Ecore_Timer *timer; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _signal_clicked(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_pressed(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_unpressed(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _on_focus_hook(void *data, Evas_Object *obj); +static void _activate(Evas_Object *obj); +static void _activate_hook(Evas_Object *obj); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); + +static const char SIG_CLICKED[] = "clicked"; +static const char SIG_REPEATED[] = "repeated"; +static const char SIG_UNPRESSED[] = "unpressed"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_CLICKED, ""}, + {SIG_REPEATED, ""}, + {SIG_UNPRESSED, ""}, + {NULL, NULL} +}; + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + if ((strcmp(ev->keyname, "Return")) && + (strcmp(ev->keyname, "KP_Enter")) && + (strcmp(ev->keyname, "space"))) + return EINA_FALSE; + _activate(obj); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + edje_object_signal_emit(wd->btn, "elm,anim,activate", "elm"); + return EINA_TRUE; +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->label) eina_stringshare_del(wd->label); + free(wd); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->btn, "elm,action,focus", "elm"); + evas_object_focus_set(wd->btn, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->btn, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->btn, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const char *str; + if (!wd) return; + _elm_theme_object_set(obj, wd->btn, "button", "base", elm_widget_style_get(obj)); + if (wd->icon) + edje_object_part_swallow(wd->btn, "elm.swallow.content", wd->icon); + if (wd->label) + edje_object_signal_emit(wd->btn, "elm,state,text,visible", "elm"); + else + edje_object_signal_emit(wd->btn, "elm,state,text,hidden", "elm"); + if (wd->icon) + edje_object_signal_emit(wd->btn, "elm,state,icon,visible", "elm"); + else + edje_object_signal_emit(wd->btn, "elm,state,icon,hidden", "elm"); + edje_object_part_text_set(wd->btn, "elm.text", wd->label); + if (elm_object_disabled_get(obj)) + edje_object_signal_emit(wd->btn, "elm,state,disabled", "elm"); + edje_object_message_signal_process(wd->btn); + edje_object_scale_set(wd->btn, elm_widget_scale_get(obj) * _elm_config->scale); + str = edje_object_data_get(wd->btn, "focus_highlight"); + if ((str) && (!strcmp(str, "on"))) + elm_widget_highlight_in_theme_set(obj, EINA_TRUE); + else + elm_widget_highlight_in_theme_set(obj, EINA_FALSE); + _sizing_eval(obj); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_disabled_get(obj)) + edje_object_signal_emit(wd->btn, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(wd->btn, "elm,state,enabled", "elm"); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_emit(wd->btn, emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_callback_add(wd->btn, emission, source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_del_full(wd->btn, emission, source, func_cb, + data); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->btn, &minw, &minh, minw, minh); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(obj, minw, minh); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (obj != wd->icon) return; + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->icon) + { + edje_object_signal_emit(wd->btn, "elm,state,icon,hidden", "elm"); + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->icon = NULL; + edje_object_message_signal_process(wd->btn); + _sizing_eval(obj); + } +} + +static void +_activate(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->timer) + { + ecore_timer_del(wd->timer); + wd->timer = NULL; + } + wd->repeating = EINA_FALSE; + evas_object_smart_callback_call(obj, SIG_CLICKED, NULL); +} + +static void +_activate_hook(Evas_Object *obj) +{ + _activate(obj); +} + +static void +_signal_clicked(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + _activate(data); +} + +static Eina_Bool +_autorepeat_send(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + + evas_object_smart_callback_call(data, SIG_REPEATED, NULL); + if (!wd->repeating) + { + wd->timer = NULL; + return ECORE_CALLBACK_CANCEL; + } + + return ECORE_CALLBACK_RENEW; +} + +static Eina_Bool +_autorepeat_initial_send(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + + if (wd->timer) ecore_timer_del(wd->timer); + wd->repeating = EINA_TRUE; + _autorepeat_send(data); + wd->timer = ecore_timer_add(wd->ar_interval, _autorepeat_send, data); + + return ECORE_CALLBACK_CANCEL; +} + +static void +_signal_pressed(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + + if ((wd->autorepeat) && (!wd->repeating)) + { + if (wd->ar_threshold <= 0.0) + _autorepeat_initial_send(data); /* call immediately */ + else + wd->timer = ecore_timer_add(wd->ar_threshold, _autorepeat_initial_send, data); + } +} + +static void +_signal_unpressed(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + + if (wd->timer) + { + ecore_timer_del(wd->timer); + wd->timer = NULL; + } + wd->repeating = EINA_FALSE; + evas_object_smart_callback_call(data, SIG_UNPRESSED, NULL); +} + +/** + * Add a new button to the parent + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Button + */ +EAPI Evas_Object * +elm_button_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "button"); + elm_widget_type_set(obj, "button"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set( obj, _on_focus_hook, NULL ); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_activate_hook_set(obj, _activate_hook); + elm_widget_event_hook_set(obj, _event_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + + wd->btn = edje_object_add(e); + _elm_theme_object_set(obj, wd->btn, "button", "base", "default"); + edje_object_signal_callback_add(wd->btn, "elm,action,click", "", + _signal_clicked, obj); + edje_object_signal_callback_add(wd->btn, "elm,action,press", "", + _signal_pressed, obj); + edje_object_signal_callback_add(wd->btn, "elm,action,unpress", "", + _signal_unpressed, obj); + elm_widget_resize_object_set(obj, wd->btn); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + _theme_hook(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the label used in the button + * + * @param obj The button object + * @param label The text will be written on the button + * + * @ingroup Button + */ +EAPI void +elm_button_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->label, label); + if (label) + edje_object_signal_emit(wd->btn, "elm,state,text,visible", "elm"); + else + edje_object_signal_emit(wd->btn, "elm,state,text,hidden", "elm"); + edje_object_message_signal_process(wd->btn); + edje_object_part_text_set(wd->btn, "elm.text", label); + _sizing_eval(obj); +} + +EAPI const char * +elm_button_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the icon used for the button + * + * Once the icon object is set, a previously set one will be deleted + * If you want to keep that old content object, use the + * elm_button_icon_unset() function. + * + * @param obj The button object + * @param icon The icon object for the button + * + * @ingroup Button + */ +EAPI void +elm_button_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->icon == icon) return; + if (wd->icon) evas_object_del(wd->icon); + wd->icon = icon; + if (icon) + { + elm_widget_sub_object_add(obj, icon); + evas_object_event_callback_add(icon, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->btn, "elm.swallow.content", icon); + edje_object_signal_emit(wd->btn, "elm,state,icon,visible", "elm"); + edje_object_message_signal_process(wd->btn); + } + _sizing_eval(obj); +} + +/** + * Get the icon used for the button + * + * Return the icon object which is set for this widget. + * + * @param obj The button object + * @return The icon object that is being used + * + * @ingroup Button + */ +EAPI Evas_Object * +elm_button_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->icon; +} + +/** + * Unset the icon used for the button + * + * Unparent and return the icon object which was set for this widget. + * + * @param obj The button object + * @return The icon object that was being used + * + * @ingroup Button + */ +EAPI Evas_Object * +elm_button_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->icon) return NULL; + Evas_Object *icon = wd->icon; + elm_widget_sub_object_del(obj, wd->icon); + edje_object_part_unswallow(wd->btn, wd->icon); + wd->icon = NULL; + return icon; +} + +/** + * Turn on/off the autorepeat event generated when the user keeps pressing on the button + * + * @param obj The button object + * @param on A bool to turn on/off the event + * + * @ingroup Button + */ +EAPI void +elm_button_autorepeat_set(Evas_Object *obj, Eina_Bool on) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->timer) + { + ecore_timer_del(wd->timer); + wd->timer = NULL; + } + wd->autorepeat = on; + wd->repeating = EINA_FALSE; +} + +/** + * Get if autorepeat event is on + * + * @param obj The button object + * @return If autorepeat is on + * + * @ingroup Button + */ +EAPI Eina_Bool +elm_button_autorepeat_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->autorepeat; +} + +/** + * Set the initial timeout before the autorepeat event is generated + * + * @param obj The button object + * @param t Timeout + * + * @ingroup Button + */ +EAPI void +elm_button_autorepeat_initial_timeout_set(Evas_Object *obj, double t) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->ar_threshold == t) return; + if (wd->timer) + { + ecore_timer_del(wd->timer); + wd->timer = NULL; + } + wd->ar_threshold = t; +} + +/** + * Get the initial timeout before the autorepeat event is generated + * + * @param obj The button object + * @return Timeout + * + * @ingroup Button + */ +EAPI double +elm_button_autorepeat_initial_timeout_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->ar_threshold; +} + +/** + * Set the interval between each generated autorepeat event + * + * @param obj The button object + * @param t Interval + * + * @ingroup Button + */ +EAPI void +elm_button_autorepeat_gap_timeout_set(Evas_Object *obj, double t) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->ar_interval == t) return; + + wd->ar_interval = t; + if ((wd->repeating) && (wd->timer)) ecore_timer_interval_set(wd->timer, t); +} + +/** + * Get the interval between each generated autorepeat event + * + * @param obj The button object + * @return Interval + * + * @ingroup Button + */ +EAPI double +elm_button_autorepeat_gap_timeout_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->ar_interval; +} diff --git a/src/lib/elm_calendar.c b/src/lib/elm_calendar.c new file mode 100644 index 0000000..3c2ff39 --- /dev/null +++ b/src/lib/elm_calendar.c @@ -0,0 +1,1280 @@ +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif + +#ifdef HAVE_EVIL +# include +#endif + +#include +#include "elm_priv.h" + +/** + * @defgroup Calendar + * + * A calendar is a widget that allows the user to select a date. It has + * support to adding check marks (holidays and checks by default). The calendar + * is displayed one month at a time. + * + * Weekday names and the function used to format month and year to + * be displayed can be set, giving more flexibility to this widget. + * + * Signals that you can add callbacks for are: + * + * changed - emitted when the user selects a day or changes the displayed + * month, what actually changes the selected day as well. + */ + +typedef enum _Day_Color // EINA_DEPRECATED +{ + DAY_WEEKDAY = 0, + DAY_SATURDAY = 1, + DAY_SUNDAY = 2 +} Day_Color; + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *calendar; + Eina_List *marks; + double interval, first_interval; + int year_min, year_max, spin_speed; + int today_it, selected_it, first_day_it; + Ecore_Timer *spin, *update_timer; + char * (*format_func) (struct tm *stime); + const char *weekdays[7]; + struct tm current_time, selected_time; + Day_Color day_color[42]; // EINA_DEPRECATED + Eina_Bool selection_enabled : 1; +}; + +struct _Elm_Calendar_Mark +{ + Evas_Object *obj; + Eina_List *node; + struct tm mark_time; + const char *mark_type; + Elm_Calendar_Mark_Repeat repeat; +}; + +static const char *widtype = NULL; +static void _on_focus_hook(void *data, Evas_Object *obj); + +static const char *_days_abbrev[] = +{ + "Sun", "Mon", "Tue", "Wed", + "Thu", "Fri", "Sat" +}; + +static int _days_in_month[2][12] = +{ + {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}, + {31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31} +}; + +static Elm_Calendar_Mark * +_mark_new(Evas_Object *obj, const char *mark_type, struct tm *mark_time, Elm_Calendar_Mark_Repeat repeat) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Calendar_Mark *mark; + + if (!wd) return NULL; + mark = calloc(1, sizeof(Elm_Calendar_Mark)); + if (!mark) return NULL; + mark->obj = obj; + mark->mark_type = eina_stringshare_add(mark_type); + mark->mark_time = *mark_time; + mark->repeat = repeat; + return mark; +} + +static inline void +_mark_free(Elm_Calendar_Mark *mark) +{ + eina_stringshare_del(mark->mark_type); + free(mark); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + if (!wd) return; + elm_coords_finger_size_adjust(8, &minw, 7, &minh); + edje_object_size_min_restricted_calc(wd->calendar, &minw, &minh, minw, minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static inline int +_maxdays_get(struct tm *time) +{ + int month, year; + + month = time->tm_mon; + year = time->tm_year + 1900; + + return _days_in_month[((!(year % 4)) && + ((!(year % 400)) || + (year % 100)))] + [month]; +} + +static inline void +_unselect(Widget_Data *wd, int selected) +{ + char emission[32]; + snprintf(emission, sizeof(emission), "cit_%i,unselected", selected); + edje_object_signal_emit(wd->calendar, emission, "elm"); +} + +static inline void +_select(Widget_Data *wd, int selected) +{ + char emission[32]; + snprintf(emission, sizeof(emission), "cit_%i,selected", selected); + edje_object_signal_emit(wd->calendar, emission, "elm"); +} + +static inline void +_not_today(Widget_Data *wd) +{ + char emission[32]; + snprintf(emission, sizeof(emission), "cit_%i,not_today", wd->today_it); + edje_object_signal_emit(wd->calendar, emission, "elm"); + wd->today_it = -1; +} + +static inline void +_today(Widget_Data *wd, int it) +{ + char emission[32]; + snprintf(emission, sizeof(emission), "cit_%i,today", it); + edje_object_signal_emit(wd->calendar, emission, "elm"); + wd->today_it = it; +} + +static char * +_format_month_year(struct tm *stime) +{ + char buf[32]; + if (!strftime(buf, sizeof(buf), "%B %Y", stime)) return NULL; + return strdup(buf); +} + +static inline void +_cit_mark(Evas_Object *cal, int cit, const char *mtype) +{ + char sign[64]; + snprintf(sign, sizeof(sign), "cit_%i,%s", cit, mtype); + edje_object_signal_emit(cal, sign, "elm"); +} + +static inline int +_weekday_get(int first_week_day, int day) +{ + return (day + first_week_day - 1) % 7; +} + +// EINA_DEPRECATED +static void +_text_day_color_update(Widget_Data *wd, int pos) +{ + char emission[32]; + + switch (wd->day_color[pos]) + { + case DAY_WEEKDAY: + snprintf(emission, sizeof(emission), "cit_%i,weekday", pos); + break; + case DAY_SATURDAY: + snprintf(emission, sizeof(emission), "cit_%i,saturday", pos); + break; + case DAY_SUNDAY: + snprintf(emission, sizeof(emission), "cit_%i,sunday", pos); + break; + default: + return; + } + + edje_object_signal_emit(wd->calendar, emission, "elm"); +} + +// EINA_DEPRECATED +static void +_text_day_color_set(Widget_Data *wd, Day_Color col, int pos) +{ + if ((pos < 0) || (pos >= 42)) return; + if (wd->day_color[pos] == col) return; + wd->day_color[pos] = col; + _text_day_color_update(wd, pos); +} + +static void +_populate(Evas_Object *obj) +{ + int maxdays, day, mon, year, i; + Elm_Calendar_Mark *mark; + char part[12], day_s[3]; + struct tm first_day; + Eina_List *l; + char *buf; + Eina_Bool last_row = EINA_TRUE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + + if (wd->today_it > 0) _not_today(wd); + + maxdays = _maxdays_get(&wd->selected_time); + mon = wd->selected_time.tm_mon; + year = wd->selected_time.tm_year; + + /* Set selected month */ + buf = wd->format_func(&wd->selected_time); + if (buf) + { + edje_object_part_text_set(wd->calendar, "month_text", buf); + free(buf); + } + else + edje_object_part_text_set(wd->calendar, "month_text", ""); + + /* Set days */ + day = 0; + first_day = wd->selected_time; + first_day.tm_mday = 1; + mktime(&first_day); + + // Layout of the calendar is changed for removing the unfilled last row. + wd->first_day_it = first_day.tm_wday; + + if ((35 - wd->first_day_it) > (maxdays - 1)) last_row = EINA_FALSE; + + if (!last_row) + { + char emission[32]; + + for (i = 0; i < 5; i++) + { + snprintf(emission, sizeof(emission), "cseph_%i,row_hide", i); + edje_object_signal_emit(wd->calendar, emission, "elm"); + } + snprintf(emission, sizeof(emission), "cseph_%i,row_invisible", 5); + edje_object_signal_emit(wd->calendar, emission, "elm"); + for (i = 0; i < 35; i++) + { + snprintf(emission, sizeof(emission), "cit_%i,cell_expanded", i); + edje_object_signal_emit(wd->calendar, emission, "elm"); + } + for (i = 35; i < 42; i++) + { + snprintf(emission, sizeof(emission), "cit_%i,cell_invisible", i); + edje_object_signal_emit(wd->calendar, emission, "elm"); + } + } + else + { + char emission[32]; + + for (i = 0; i < 6; i++) + { + snprintf(emission, sizeof(emission), "cseph_%i,row_show", i); + edje_object_signal_emit(wd->calendar, emission, "elm"); + } + for (i = 0; i < 42; i++) + { + snprintf(emission, sizeof(emission), "cit_%i,cell_default", i); + edje_object_signal_emit(wd->calendar, emission, "elm"); + } + } + + for (i = 0; i < 42; i++) + { + _text_day_color_update(wd, i); // EINA_DEPRECATED + if ((!day) && (i == first_day.tm_wday)) day = 1; + + if ((day == wd->current_time.tm_mday) + && (mon == wd->current_time.tm_mon) + && (year == wd->current_time.tm_year)) + _today(wd, i); + + if (day == wd->selected_time.tm_mday) + { + if ((wd->selected_it > -1) && (wd->selected_it != i)) + _unselect(wd, wd->selected_it); + + if (wd->selection_enabled) _select(wd, i); + + wd->selected_it = i; + } + + if ((day) && (day <= maxdays)) + snprintf(day_s, sizeof(day_s), "%i", day++); + else + day_s[0] = 0; + + snprintf(part, sizeof(part), "cit_%i.text", i); + edje_object_part_text_set(wd->calendar, part, day_s); + /* Clear previous marks */ + _cit_mark(wd->calendar, i, "clear"); + } + + /* Set marks */ + EINA_LIST_FOREACH(wd->marks, l, mark) + { + struct tm *mtime = &mark->mark_time; + int mon = wd->selected_time.tm_mon; + int year = wd->selected_time.tm_year; + int mday_it = mtime->tm_mday + wd->first_day_it - 1; + + switch (mark->repeat) + { + case ELM_CALENDAR_UNIQUE: + if ((mtime->tm_mon == mon) && (mtime->tm_year == year)) + _cit_mark(wd->calendar, mday_it, mark->mark_type); + break; + case ELM_CALENDAR_DAILY: + if (((mtime->tm_year == year) && (mtime->tm_mon < mon)) || + (mtime->tm_year < year)) + day = 1; + else if ((mtime->tm_year == year) && (mtime->tm_mon == mon)) + day = mtime->tm_mday; + else + break; + for (; day <= maxdays; day++) + _cit_mark(wd->calendar, day + wd->first_day_it - 1, + mark->mark_type); + break; + case ELM_CALENDAR_WEEKLY: + if (((mtime->tm_year == year) && (mtime->tm_mon < mon)) || + (mtime->tm_year < year)) + day = 1; + else if ((mtime->tm_year == year) && (mtime->tm_mon == mon)) + day = mtime->tm_mday; + else + break; + for (; day <= maxdays; day++) + if (mtime->tm_wday == _weekday_get(wd->first_day_it, day)) + _cit_mark(wd->calendar, day + wd->first_day_it - 1, + mark->mark_type); + break; + case ELM_CALENDAR_MONTHLY: + if (((mtime->tm_year < year) || + ((mtime->tm_year == year) && (mtime->tm_mon <= mon))) && + (mtime->tm_mday <= maxdays)) + _cit_mark(wd->calendar, mday_it, mark->mark_type); + break; + case ELM_CALENDAR_ANNUALLY: + if ((mtime->tm_year <= year) && (mtime->tm_mon == mon) && + (mtime->tm_mday <= maxdays)) + _cit_mark(wd->calendar, mday_it, mark->mark_type); + break; + } + } +} + +static void +_set_headers(Evas_Object *obj) +{ + static char part[] = "ch_0.text"; + int i; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + for (i = 0; i < 7; i++) + { + part[3] = i + '0'; + edje_object_part_text_set(wd->calendar, part, wd->weekdays[i]); + } +} + +static void +_del_hook(Evas_Object *obj) +{ + int i; + Elm_Calendar_Mark *mark; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + + if (wd->spin) ecore_timer_del(wd->spin); + if (wd->update_timer) ecore_timer_del(wd->update_timer); + + if (wd->marks) + { + EINA_LIST_FREE(wd->marks, mark) + { + _mark_free(mark); + } + } + + for (i = 0; i < 7; i++) + eina_stringshare_del(wd->weekdays[i]); + + free(wd); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->calendar, "elm,action,focus", "elm"); + evas_object_focus_set(wd->calendar, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->calendar, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->calendar, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->calendar, "calendar", "base", + elm_widget_style_get(obj)); + _set_headers(obj); + _populate(obj); + edje_object_message_signal_process(wd->calendar); + edje_object_scale_set(wd->calendar, + elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_emit(wd->calendar, emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_callback_add(wd->calendar, emission, + source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_callback_del_full(wd->calendar, emission, source, func_cb, + data); +} + +/* Set correct tm_wday and tm_yday after other fields changes*/ +static inline void +_fix_selected_time(Widget_Data *wd) +{ + mktime(&wd->selected_time); +} + +static Eina_Bool +_update_month(Evas_Object *obj, int delta) +{ + struct tm time_check; + int maxdays; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + + /* check if it's a valid time. for 32 bits, year greater than 2037 is not */ + time_check = wd->selected_time; + time_check.tm_mon += delta; + if (mktime(&time_check) == -1) + return EINA_FALSE; + + wd->selected_time.tm_mon += delta; + if (wd->selected_time.tm_mon < 0) + { + if (wd->selected_time.tm_year == wd->year_min) + { + wd->selected_time.tm_mon++; + return EINA_FALSE; + } + wd->selected_time.tm_mon = 11; + wd->selected_time.tm_year--; + } + else if (wd->selected_time.tm_mon > 11) + { + if (wd->selected_time.tm_year == wd->year_max) + { + wd->selected_time.tm_mon--; + return EINA_FALSE; + } + wd->selected_time.tm_mon = 0; + wd->selected_time.tm_year++; + } + + maxdays = _maxdays_get(&wd->selected_time); + if (wd->selected_time.tm_mday > maxdays) + wd->selected_time.tm_mday = maxdays; + + _fix_selected_time(wd); + evas_object_smart_callback_call(obj, "changed", NULL); + + return EINA_TRUE; +} + +static Eina_Bool +_spin_value(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + if (_update_month(data, wd->spin_speed)) _populate(data); + wd->interval = wd->interval / 1.05; + ecore_timer_interval_set(wd->spin, wd->interval); + return ECORE_CALLBACK_RENEW; +} + +static void +_button_inc_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->interval = wd->first_interval; + wd->spin_speed = 1; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = ecore_timer_add(wd->interval, _spin_value, data); + _spin_value(data); +} + +static void +_button_dec_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->interval = wd->first_interval; + wd->spin_speed = -1; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = ecore_timer_add(wd->interval, _spin_value, data); + _spin_value(data); +} + +static void +_button_stop(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->interval = wd->first_interval; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = NULL; +} + +static int +_get_item_day(Evas_Object *obj, int selected_it) +{ + int day; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + + day = selected_it - wd->first_day_it + 1; + if ((day < 0) || (day > _maxdays_get(&wd->selected_time))) + return 0; + + return day; +} + +static void +_update_sel_it(Evas_Object *obj, int sel_it) +{ + int day; + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->selection_enabled)) + return; + + day = _get_item_day(obj, sel_it); + if (!day) + return; + + _unselect(wd, wd->selected_it); + + wd->selected_it = sel_it; + wd->selected_time.tm_mday = day; + _select(wd, wd->selected_it); + _fix_selected_time(wd); + evas_object_smart_callback_call(obj, "changed", NULL); +} + +static void +_day_selected(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source) +{ + int sel_it; + Widget_Data *wd = elm_widget_data_get(data); + if ((!wd) || (!wd->selection_enabled)) + return; + sel_it = atoi(source); + + _update_sel_it(data, sel_it); +} + +static inline int +_time_to_next_day(struct tm *t) +{ + return ((((24 - t->tm_hour) * 60) - t->tm_min) * 60) - t->tm_sec; +} + +static Eina_Bool +_update_cur_date(void *data) +{ + time_t current_time; + int t, day; + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_RENEW; + + if (wd->today_it > 0) _not_today(wd); + + current_time = time(NULL); + localtime_r(¤t_time, &wd->current_time); + t = _time_to_next_day(&wd->current_time); + ecore_timer_interval_set(wd->update_timer, t); + + if ((wd->current_time.tm_mon != wd->selected_time.tm_mon) || + (wd->current_time.tm_year!= wd->selected_time.tm_year)) + return ECORE_CALLBACK_RENEW; + + day = wd->current_time.tm_mday + wd->first_day_it - 1; + _today(wd, day); + + return ECORE_CALLBACK_RENEW; +} + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + if (!wd->selection_enabled) return EINA_FALSE; + + if ((!strcmp(ev->keyname, "Left")) || + (!strcmp(ev->keyname, "KP_Left"))) + { + _update_sel_it(obj, wd->selected_it-1); + } + else if ((!strcmp(ev->keyname, "Right")) || + (!strcmp(ev->keyname, "KP_Right"))) + { + _update_sel_it(obj, wd->selected_it+1); + } + else if ((!strcmp(ev->keyname, "Up")) || + (!strcmp(ev->keyname, "KP_Up"))) + { + _update_sel_it(obj, wd->selected_it-7); + } + else if ((!strcmp(ev->keyname, "Down")) || + (!strcmp(ev->keyname, "KP_Down"))) + { + _update_sel_it(obj, wd->selected_it+7); + } + else if ((!strcmp(ev->keyname, "Prior")) || + (!strcmp(ev->keyname, "KP_Prior"))) + { + if (_update_month(obj, -1)) _populate(obj); + } + else if ((!strcmp(ev->keyname, "Next")) || + (!strcmp(ev->keyname, "KP_Next"))) + { + if (_update_month(obj, 1)) _populate(obj); + } + else return EINA_FALSE; + + return EINA_TRUE; +} + +/** + * Add a new calendar to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Calendar + */ +EAPI Evas_Object * +elm_calendar_add(Evas_Object *parent) +{ + time_t current_time; + Evas_Object *obj; + Widget_Data *wd; + int i, t; + Evas *e; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "calendar"); + elm_widget_type_set(obj, "calendar"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->first_interval = 0.85; + wd->year_min = 2; + wd->year_max = -1; + wd->today_it = -1; + wd->selected_it = -1; + wd->first_day_it = -1; + wd->selection_enabled = EINA_TRUE; + wd->format_func = _format_month_year; + wd->marks = NULL; + + wd->calendar = edje_object_add(e); + _elm_theme_object_set(obj, wd->calendar, "calendar", "base", "default"); + elm_widget_resize_object_set(obj, wd->calendar); + + edje_object_signal_callback_add(wd->calendar, "elm,action,increment,start", + "*", _button_inc_start, obj); + edje_object_signal_callback_add(wd->calendar, "elm,action,decrement,start", + "*", _button_dec_start, obj); + edje_object_signal_callback_add(wd->calendar, "elm,action,stop", + "*", _button_stop, obj); + edje_object_signal_callback_add(wd->calendar, "elm,action,selected", + "*", _day_selected, obj); + + for (i = 0; i < 7; i++) + wd->weekdays[i] = eina_stringshare_add(_days_abbrev[i]); + + current_time = time(NULL); + localtime_r(¤t_time, &wd->selected_time); + wd->current_time = wd->selected_time; + t = _time_to_next_day(&wd->current_time); + wd->update_timer = ecore_timer_add(t, _update_cur_date, obj); + + _set_headers(obj); + _populate(obj); + _sizing_eval(obj); + return obj; +} + +/** + * Set weekdays names to display in the calendar. + * + * By default, the following abbreviations are displayed: + * "Sun, Mon, Tue, Wed, Thu, Fri, Sat" + * The first string should be related to Sunday, the second to Monday... + * + * The usage should be like this: + * @code + * const char *weekdays[] = + * { + * "Sunday", "Monday", "Tuesday", "Wednesday", + * "Thursday", "Friday", "Saturday" + * }; + * elm_calendar_weekdays_names_set(calendar, weekdays); + * @endcode + * + * @param obj The calendar object + * @param weedays Array of seven strings to be used as weekday names. + * Warning: it must have 7 elements, or it will access invalid memory. + * The strings must be NULL terminated ('@\0'). + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_weekdays_names_set(Evas_Object *obj, const char *weekdays[]) +{ + int i; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + EINA_SAFETY_ON_NULL_RETURN(weekdays); + + for (i = 0; i < 7; i++) + { + eina_stringshare_replace(&wd->weekdays[i], weekdays[i]); + } + _set_headers(obj); +} + +/** + * Get weekdays names displayed in the calendar. + * + * By default, the following abbreviations are displayed: + * "Sun, Mon, Tue, Wed, Thu, Fri, Sat" + * The first string is related to Sunday, the second to Monday... + * + * @param obj The calendar object + * @return Array of seven strings to used as weekday names. + * + * @ingroup Calendar + */ +EAPI const char ** +elm_calendar_weekdays_names_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->weekdays; +} + +/** + * Set the interval for the calendar + * + * The interval value is decreased while the user increments or decrements + * the calendar value. The next interval value is the previous interval / 1.05, + * so it speed up a bit. Default value is 0.85 seconds. + * + * @param obj The calendar object + * @param interval The interval value in seconds + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_interval_set(Evas_Object *obj, double interval) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->first_interval = interval; +} + +/** + * Get the interval of the calendar + * + * The interval value is decreased while the user increments or decrements + * the calendar value. The next interval value is the previous interval / 1.05, + * so it speed up a bit. Default value is 0.85 seconds. + * + * @param obj The calendar object + * @return The value of the first interval in seconds + * + * @ingroup Calendar + */ +EAPI double +elm_calendar_interval_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->first_interval; +} + +/** + * Set the minimum and maximum values for the year + * + * Maximum must be greater than minimum, except if you don't wan't to set + * maximum year. + * Default values are 1902 and -1. + * + * If the maximum year is a negative value, it will be limited depending of the + * platform architecture (2037 for 32 bits); + * + * @param obj The calendar object + * @param min The minimum year, greater than 1901; + * @param max The maximum year; + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_min_max_year_set(Evas_Object *obj, int min, int max) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + min -= 1900; + max -= 1900; + if ((wd->year_min == min) && (wd->year_max == max)) return; + wd->year_min = min > 2 ? min : 2; + wd->year_max = max; + if (wd->selected_time.tm_year > wd->year_max) + wd->selected_time.tm_year = wd->year_max; + if (wd->selected_time.tm_year < wd->year_min) + wd->selected_time.tm_year = wd->year_min; + _fix_selected_time(wd); + _populate(obj); +} + +/** + * Get the minimum and maximum values for the year + * + * Default values are 1902 and -1. + * + * If the maximum year is a negative value, it will be limited depending of the + * platform architecture (2037 for 32 bits); + * + * @param obj The calendar object + * @param min The minimum year + * @param max The maximum year + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_min_max_year_get(const Evas_Object *obj, int *min, int *max) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (min) *min = wd->year_min + 1900; + if (max) *max = wd->year_max + 1900; +} + +/** + * Enable or disable day selection + * + * Enabled by default. If disabled, the user can select months, but not days. + * It should be used if you won't need such selection for the widget usage. + * + * @param obj The calendar object + * @param enabled Boolean to enable (true) or disable (false) day selection + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_day_selection_enabled_set(Evas_Object *obj, Eina_Bool enabled) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->selection_enabled = enabled; + if (enabled) + _select(wd, wd->selected_it); + else + _unselect(wd, wd->selected_it); +} + +/** + * Get day selection state + * + * Enabled by default. If disabled, the user can select months, but not days. + * It should be used if you won't need such selection for the widget usage. + * + * @param obj The calendar object + * @return True if day selection is enabled, or false otherwise. It will + * return false if it can't get widget data. + * + * @ingroup Calendar + */ +EAPI Eina_Bool +elm_calendar_day_selection_enabled_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->selection_enabled; +} + +/** + * Set selected time + * + * Set the time selected, changing the displayed month if needed. + * Selected time changes when the user changes the month or select a day. + * + * @param obj The calendar object + * @param selected_time A tm struct to represent the selected date + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_selected_time_set(Evas_Object *obj, struct tm *selected_time) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + EINA_SAFETY_ON_NULL_RETURN(selected_time); + wd->selected_time = *selected_time; + _populate(obj); + return; +} + +/** + * Get selected time + * + * Get the time selected by the user. + * Selected time changes when the user changes the month or select a day. + * + * @param obj The calendar object + * @param selected_time A tm struct to represent the selected date + * @return It will return false if it can't get widget data, or true otherwise + * + * @ingroup Calendar + */ +EAPI Eina_Bool +elm_calendar_selected_time_get(const Evas_Object *obj, struct tm *selected_time) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + EINA_SAFETY_ON_NULL_RETURN_VAL(selected_time, EINA_FALSE); + *selected_time = wd->selected_time; + return EINA_TRUE; +} + +/** + * Set a function to format the string that will be used to display + * month - year + * + * By default it uses strftime with "%B %Y" format string. + * It should allocate the memory that will be used by the string, + * that will be freed by the widget after usage. + * A pointer to the string and a pointer to the time struct will be provided. + * + * Example: + * @code + * static char * + * _format_month_year(struct tm *stime) + * { + * char buf[32]; + * if (!strftime(buf, sizeof(buf), "%B %Y", stime)) return NULL; + * return strdup(buf); + * } + * elm_calendar_format_function_set(calendar, _format_month_year); + * @endcode + * + * @param obj The calendar object + * @param format_function Function to set the month-year string given + * the selected date + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_format_function_set(Evas_Object *obj, char * (*format_function) (struct tm *stime)) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->format_func = format_function; +} + +/** + * Add a new mark to the calendar + * + * Add a mark that will be drawn in the calendar respecting the insertion time + * and periodicity. It will emit the type as signal to the widget theme. + * By default, it supports "holiday" and "checked", but it can be extended. + * + * It won't immediately update the calendar, drawing the marks. For this, call + * elm_calendar_marks_draw(). + * + * Example + * @code + * struct tm selected_time; + * time_t current_time; + * + * current_time = time(NULL) + 5 * 84600; + * localtime_r(¤t_time, &selected_time); + * elm_calendar_mark_add(cal, "holiday", selected_time, ELM_CALENDAR_ANNUALLY); + * + * current_time = time(NULL) + 1 * 84600; + * localtime_r(¤t_time, &selected_time); + * elm_calendar_mark_add(cal, "checked", selected_time, ELM_CALENDAR_UNIQUE); + * + * elm_calendar_marks_draw(cal); + * @endcode + * + * @param obj The calendar object + * @param mark_type A string used to define the type of mark. It will be + * emitted to the theme, that should display a related modification on these + * days representation. + * @param mark_time A time struct to represent the date of inclusion of the + * mark. For marks that repeats it will just be displayed after the inclusion + * date in the calendar. + * @param repeat Repeat the event following this periodicity. Can be a unique + * mark (that don't repeat), daily, weekly, monthly or annually. + * + * @return The created mark or NULL upon failure + * + * @ingroup Calendar + */ +EAPI Elm_Calendar_Mark * +elm_calendar_mark_add(Evas_Object *obj, const char *mark_type, struct tm *mark_time, Elm_Calendar_Mark_Repeat repeat) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Calendar_Mark *mark; + if (!wd) return NULL; + + mark = _mark_new(obj, mark_type, mark_time, repeat); + wd->marks = eina_list_append(wd->marks, mark); + mark->node = eina_list_last(wd->marks); + return mark; +} + +/** + * Delete mark from the calendar. + * + * @param mark The mark to delete + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_mark_del(Elm_Calendar_Mark *mark) +{ + Evas_Object *obj; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN(mark); + + obj = mark->obj; + wd = elm_widget_data_get(obj); + if (!wd) return; + + wd->marks = eina_list_remove_list(wd->marks, mark->node); + _mark_free(mark); +} + +/** + * Remove all the marks from the calendar + * + * @param obj The calendar object + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_marks_clear(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Calendar_Mark *mark; + + if (!wd) return; + EINA_LIST_FREE(wd->marks, mark) + _mark_free(mark); +} + +/** + * Returns a list of all the calendar marks. + * + * @param obj The calendar object + * @return An Eina_List* of the calendar marks, or NULL on failure + * + * @ingroup Calendar + */ +EAPI const Eina_List * +elm_calendar_marks_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->marks; +} + +/** + * Draw calendar marks. + * + * Should be used after adding, removing or clearing marks. + * It will go through the entire marks list updating the calendar + * (not a cheap function). So if lots of marks will be added, + * add all the marks and then call this function. + * + * When the month is changed marks will be drawed. + * + * @param obj The calendar object + * + * @ingroup Calendar + */ +EAPI void +elm_calendar_marks_draw(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _populate(obj); +} + +/** + * Set a text color to the saturday color. + * + * Deprecated. use elm_calendar_mark_add() instead like: + * + * @code + * struct tm t = { 0, 0, 12, 6, 0, 0, 5, 5, -1 }; + * elm_calendar_mark_add(obj, "sat", &t, ELM_CALENDAR_WEEKLY); + * @endcode + * + * @param obj The calendar object + * @param pos The text position + * + * @ingroup Calendar + */ +EINA_DEPRECATED EAPI void +elm_calendar_text_saturday_color_set(Evas_Object *obj, int pos) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _text_day_color_set(wd, DAY_SATURDAY, pos); +} + +/** + * Set a text color to the sunday color. + * + * Deprecated. use elm_calendar_mark_add() instead like: + * + * @code + * struct tm t = { 0, 0, 12, 7, 0, 0, 6, 6, -1 }; + * elm_calendar_mark_add(obj, "sun", &t, ELM_CALENDAR_WEEKLY); + * @endcode + * + * @param obj The calendar object + * @param pos The text position + * + * @ingroup Calendar + */ +EINA_DEPRECATED EAPI void +elm_calendar_text_sunday_color_set(Evas_Object *obj, int pos) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _text_day_color_set(wd, DAY_SUNDAY, pos); +} + +/** + * Set a text color to the weekday color. + * + * Deprecated. use elm_calendar_mark_add() instead like: + * + * @code + * struct tm t = { 0, 0, 12, 1, 0, 0, 0, 0, -1 }; + * + * elm_calendar_mark_add(obj, "week", &t, ELM_CALENDAR_WEEKLY); // monday + * t.tm_tm_mday++; t.tm_wday++; t.tm_yday++; + * elm_calendar_mark_add(obj, "week", &t, ELM_CALENDAR_WEEKLY); // tuesday + * t.tm_tm_mday++; t.tm_wday++; t.tm_yday++; + * elm_calendar_mark_add(obj, "week", &t, ELM_CALENDAR_WEEKLY); // wednesday + * t.tm_tm_mday++; t.tm_wday++; t.tm_yday++; + * elm_calendar_mark_add(obj, "week", &t, ELM_CALENDAR_WEEKLY); // thursday + * t.tm_tm_mday++; t.tm_wday++; t.tm_yday++; + * elm_calendar_mark_add(obj, "week", &t, ELM_CALENDAR_WEEKLY); // friday + * @endcode + * + * @param obj The calendar object + * @param pos The text position + * + * @ingroup Calendar + */ +EINA_DEPRECATED EAPI void +elm_calendar_text_weekday_color_set(Evas_Object *obj, int pos) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _text_day_color_set(wd, DAY_WEEKDAY, pos); +} diff --git a/src/lib/elm_check.c b/src/lib/elm_check.c new file mode 100644 index 0000000..00badfa --- /dev/null +++ b/src/lib/elm_check.c @@ -0,0 +1,471 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Check Check + * + * The check widget allows for toggling a value between true or false (1 or 0). + * + * Signals that you can add callbacks for are: + * + * changed - This is called whenever the user changes the state of one of the + * check object. + * + * Check objects are a lot like radio objects in layout and functionality + * except they do not work as a group, but independently and only toggle the + * value of a boolean from false to true (0 or 1). elm_check_state_set() sets + * the boolean state (1 for true, 0 for false), and elm_check_state_get() + * returns the current state. For convenience, like the radio objects, you + * can set a pointer to a boolean directly with elm_check_state_pointer_set() + * for it to modify. + */ +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *chk, *icon; + Eina_Bool state; + Eina_Bool *statep; + const char *label; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _signal_check_off(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_check_on(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_check_toggle(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _on_focus_hook(void *data, Evas_Object *obj); +static void _activate_hook(Evas_Object *obj); +static void _activate(Evas_Object *obj); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); + +static const char SIG_CHANGED[] = "changed"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_CHANGED, ""}, + {NULL, NULL} +}; + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + if ((strcmp(ev->keyname, "Return")) && + (strcmp(ev->keyname, "KP_Enter")) && + (strcmp(ev->keyname, "space"))) + return EINA_FALSE; + _activate(obj); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; +} + + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->label) eina_stringshare_del(wd->label); + free(wd); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->chk, "elm,action,focus", "elm"); + evas_object_focus_set(wd->chk, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->chk, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->chk, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->chk, "check", "base", elm_widget_style_get(obj)); + if (wd->icon) + edje_object_signal_emit(wd->chk, "elm,state,icon,visible", "elm"); + else + edje_object_signal_emit(wd->chk, "elm,state,icon,hidden", "elm"); + if (wd->state) + edje_object_signal_emit(wd->chk, "elm,state,check,on", "elm"); + else + edje_object_signal_emit(wd->chk, "elm,state,check,off", "elm"); + if (wd->label) + edje_object_signal_emit(wd->chk, "elm,state,text,visible", "elm"); + else + edje_object_signal_emit(wd->chk, "elm,state,text,hidden", "elm"); + edje_object_part_text_set(wd->chk, "elm.text", wd->label); + if (elm_widget_disabled_get(obj)) + edje_object_signal_emit(wd->chk, "elm,state,disabled", "elm"); + edje_object_message_signal_process(wd->chk); + edje_object_scale_set(wd->chk, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_disabled_get(obj)) + edje_object_signal_emit(wd->chk, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(wd->chk, "elm,state,enabled", "elm"); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->chk, &minw, &minh, minw, minh); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (obj != wd->icon) return; + Evas_Coord mw, mh; + evas_object_size_hint_min_get(obj, &mw, &mh); + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->icon) + { + edje_object_signal_emit(wd->chk, "elm,state,icon,hidden", "elm"); + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->icon = NULL; + _sizing_eval(obj); + edje_object_message_signal_process(wd->chk); + } +} + +static void +_signal_check_off(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->state = EINA_FALSE; + if (wd->statep) *wd->statep = wd->state; + edje_object_signal_emit(wd->chk, "elm,state,check,off", "elm"); + evas_object_smart_callback_call(data, SIG_CHANGED, NULL); +} + +static void +_signal_check_on(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->state = EINA_TRUE; + if (wd->statep) *wd->statep = wd->state; + edje_object_signal_emit(wd->chk, "elm,state,check,on", "elm"); + evas_object_smart_callback_call(data, SIG_CHANGED, NULL); +} + +static void +_signal_check_toggle(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + _activate(data); +} + +static void +_activate_hook(Evas_Object *obj) +{ + _activate(obj); +} + +static void +_activate(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->state = !wd->state; + if (wd->statep) *wd->statep = wd->state; + if (wd->state) + edje_object_signal_emit(wd->chk, "elm,state,check,on", "elm"); + else + edje_object_signal_emit(wd->chk, "elm,state,check,off", "elm"); + evas_object_smart_callback_call(obj, SIG_CHANGED, NULL); +} + +/** + * Add a new Check object + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Check + */ +EAPI Evas_Object * +elm_check_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "check"); + elm_widget_type_set(obj, "check"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_activate_hook_set(obj, _activate_hook); + elm_widget_event_hook_set(obj, _event_hook); + + wd->chk = edje_object_add(e); + _elm_theme_object_set(obj, wd->chk, "check", "base", "default"); + edje_object_signal_callback_add(wd->chk, "elm,action,check,on", "", + _signal_check_on, obj); + edje_object_signal_callback_add(wd->chk, "elm,action,check,off", "", + _signal_check_off, obj); + edje_object_signal_callback_add(wd->chk, "elm,action,check,toggle", "", + _signal_check_toggle, obj); + elm_widget_resize_object_set(obj, wd->chk); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + _sizing_eval(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the text label of the check object + * + * @param obj The check object + * @param label The text label string in UTF-8 + * + * @ingroup Check + */ +EAPI void +elm_check_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->label, label); + if (label) + edje_object_signal_emit(wd->chk, "elm,state,text,visible", "elm"); + else + edje_object_signal_emit(wd->chk, "elm,state,text,hidden", "elm"); + edje_object_message_signal_process(wd->chk); + edje_object_part_text_set(wd->chk, "elm.text", label); + _sizing_eval(obj); +} + +/** + * Get the text label of the check object + * + * @param obj The check object + * @return The text label string in UTF-8 + * + * @ingroup Check + */ +EAPI const char * +elm_check_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the icon object of the check object + * + * Once the icon object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_check_icon_unset() function. + * + * @param obj The check object + * @param icon The icon object + * + * @ingroup Check + */ +EAPI void +elm_check_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->icon == icon) return; + if (wd->icon) evas_object_del(wd->icon); + wd->icon = icon; + if (icon) + { + elm_widget_sub_object_add(obj, icon); + evas_object_event_callback_add(icon, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->chk, "elm.swallow.content", icon); + edje_object_signal_emit(wd->chk, "elm,state,icon,visible", "elm"); + edje_object_message_signal_process(wd->chk); + } + _sizing_eval(obj); +} + +/** + * Get the icon object of the check object + * + * @param obj The check object + * @return The icon object + * + * @ingroup Check + */ +EAPI Evas_Object * +elm_check_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->icon; +} + +/** + * Unset the icon used for the check object + * + * Unparent and return the icon object which was set for this widget. + * + * @param obj The check object + * @return The icon object that was being used + * + * @ingroup Check + */ +EAPI Evas_Object * +elm_check_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->icon) return NULL; + Evas_Object *icon = wd->icon; + elm_widget_sub_object_del(obj, wd->icon); + edje_object_part_unswallow(wd->chk, wd->icon); + wd->icon = NULL; + return icon; +} + +/** + * Set the on/off state of the check object + * + * This sets the state of the check and will also set the value if pointed to + * to the state supplied, but will not call any callbacks. + * + * @param obj The check object + * @param state The state to use (1 == on, 0 == off) + * + * @ingroup Check + */ +EAPI void +elm_check_state_set(Evas_Object *obj, Eina_Bool state) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (state != wd->state) + { + wd->state = state; + if (wd->statep) *wd->statep = wd->state; + if (wd->state) + edje_object_signal_emit(wd->chk, "elm,state,check,on", "elm"); + else + edje_object_signal_emit(wd->chk, "elm,state,check,off", "elm"); + } +} + +/** + * Get the state of the check object + * + * @param obj The check object + * @return The boolean state + * + * @ingroup Check + */ +EAPI Eina_Bool +elm_check_state_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->state; +} + +/** + * Set a convenience pointer to a boolean to change + * + * This sets a pointer to a boolean, that, in addition to the check objects + * state will also be modified directly. To stop setting the object pointed + * to simply use NULL as the statep parameter. If statep is not NULL, then + * when this is called, the check objects state will also be modified to + * reflect the value of the boolean statep points to, just like calling + * elm_check_state_set(). + * + * @param obj The check object + * @param statep Pointer to the boolean to modify + * + * @ingroup Check + */ +EAPI void +elm_check_state_pointer_set(Evas_Object *obj, Eina_Bool *statep) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (statep) + { + wd->statep = statep; + if (*wd->statep != wd->state) + { + wd->state = *wd->statep; + if (wd->state) + edje_object_signal_emit(wd->chk, "elm,state,check,on", "elm"); + else + edje_object_signal_emit(wd->chk, "elm,state,check,off", "elm"); + } + } + else + wd->statep = NULL; +} diff --git a/src/lib/elm_clock.c b/src/lib/elm_clock.c new file mode 100644 index 0000000..f00dfea --- /dev/null +++ b/src/lib/elm_clock.c @@ -0,0 +1,837 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Clock Clock + * + * It's a widget to show clock with animation. The update of time is + * shown in an animation like the flip of a sheet. + * + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *clk; + double interval, first_interval; + Eina_Bool seconds : 1; + Eina_Bool am_pm : 1; + Eina_Bool edit : 1; + Elm_Clock_Digedit digedit; + int hrs, min, sec, timediff; + Evas_Object *digit[6]; + Evas_Object *ampm; + Evas_Object *sel_obj; + Ecore_Timer *ticker, *spin; + struct + { + int hrs, min, sec; + char ampm; + Eina_Bool seconds : 1; + Eina_Bool am_pm : 1; + Eina_Bool edit : 1; + Elm_Clock_Digedit digedit; + } cur; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _on_focus_hook(void *data, Evas_Object *obj); +static Eina_Bool _ticker(void *data); +static Eina_Bool _signal_clock_val_up(void *data); +static Eina_Bool _signal_clock_val_down(void *data); +static void _time_update(Evas_Object *obj); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + int i; + for (i = 0; i < 6; i++) + { + if (wd->digit[i]) evas_object_del(wd->digit[i]); + } + if (wd->ampm) evas_object_del(wd->ampm); + if (wd->ticker) ecore_timer_del(wd->ticker); + if (wd->spin) ecore_timer_del(wd->spin); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + edje_object_signal_emit(wd->clk, "elm,action,focus", "elm"); + else + edje_object_signal_emit(wd->clk, "elm,action,unfocus", "elm"); + wd->cur.am_pm = !wd->cur.am_pm; /* hack - force update */ + _time_update(obj); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->clk, "elm,action,focus", "elm"); + evas_object_focus_set(wd->clk, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->clk, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->clk, EINA_FALSE); + } +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int i; + if (!wd) return; + edje_object_signal_emit(wd->clk, emission, source); + for (i = 0; i < 6; i++) + { + if (wd->digit[i]) + edje_object_signal_emit(wd->digit[i], emission, source); + } +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int i; + if (!wd) return; + edje_object_signal_callback_add(wd->clk, emission, source, func_cb, data); + for (i = 0; i < 6; i++) + { + if (wd->digit[i]) + edje_object_signal_callback_add(wd->digit[i], emission, source, + func_cb, data); + } +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int i; + for (i = 0; i < 6; i++) + { + edje_object_signal_callback_del_full(wd->digit[i], emission, source, + func_cb, data); + } + edje_object_signal_callback_del_full(wd->clk, emission, source, func_cb, + data); +} + +static void +_timediff_set(Widget_Data *wd) +{ + struct timeval timev; + struct tm *tm; + time_t tt; + gettimeofday(&timev, NULL); + tt = (time_t)(timev.tv_sec); + tzset(); + tm = localtime(&tt); + wd->timediff = (((wd->hrs - tm->tm_hour) * 60 + + wd->min - tm->tm_min) * 60) + wd->sec - tm->tm_sec; +} + +static Eina_Bool +_ticker(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + double t; + struct timeval timev; + struct tm *tm; + time_t tt; + if (!wd) return ECORE_CALLBACK_CANCEL; + gettimeofday(&timev, NULL); + t = ((double)(1000000 - timev.tv_usec)) / 1000000.0; + wd->ticker = ecore_timer_add(t, _ticker, data); + if (!wd->edit) + { + tt = (time_t)(timev.tv_sec) + wd->timediff; + tzset(); + tm = localtime(&tt); + if (tm) + { + wd->hrs = tm->tm_hour; + wd->min = tm->tm_min; + wd->sec = tm->tm_sec; + _time_update(data); + } + } + return ECORE_CALLBACK_CANCEL; +} + +static Eina_Bool +_signal_clock_val_up(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) goto clock_val_up_exit_on_error; + if (!wd->edit) goto clock_val_up_cancel; + if (!wd->sel_obj) goto clock_val_up_cancel; + if (wd->sel_obj == wd->digit[0]) + { + wd->hrs = wd->hrs + 10; + if (wd->hrs >= 24) wd->hrs -= 24; + } + if (wd->sel_obj == wd->digit[1]) + { + wd->hrs = wd->hrs + 1; + if (wd->hrs >= 24) wd->hrs -= 24; + } + if (wd->sel_obj == wd->digit[2]) + { + wd->min = wd->min + 10; + if (wd->min >= 60) wd->min -= 60; + } + if (wd->sel_obj == wd->digit[3]) + { + wd->min = wd->min + 1; + if (wd->min >= 60) wd->min -= 60; + } + if (wd->sel_obj == wd->digit[4]) + { + wd->sec = wd->sec + 10; + if (wd->sec >= 60) wd->sec -= 60; + } + if (wd->sel_obj == wd->digit[5]) + { + wd->sec = wd->sec + 1; + if (wd->sec >= 60) wd->sec -= 60; + } + if (wd->sel_obj == wd->ampm) + { + wd->hrs = wd->hrs + 12; + if (wd->hrs > 23) wd->hrs -= 24; + } + wd->interval = wd->interval / 1.05; + ecore_timer_interval_set(wd->spin, wd->interval); + _time_update(data); + evas_object_smart_callback_call(data, "changed", NULL); + return ECORE_CALLBACK_RENEW; +clock_val_up_cancel: + wd->spin = NULL; +clock_val_up_exit_on_error: + return ECORE_CALLBACK_CANCEL; +} + +static Eina_Bool +_signal_clock_val_down(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) goto clock_val_down_exit_on_error; + if (!wd->edit) goto clock_val_down_cancel; + if (!wd->sel_obj) goto clock_val_down_cancel; + if (wd->sel_obj == wd->digit[0]) + { + wd->hrs = wd->hrs - 10; + if (wd->hrs < 0) wd->hrs += 24; + } + if (wd->sel_obj == wd->digit[1]) + { + wd->hrs = wd->hrs - 1; + if (wd->hrs < 0) wd->hrs += 24; + } + if (wd->sel_obj == wd->digit[2]) + { + wd->min = wd->min - 10; + if (wd->min < 0) wd->min += 60; + } + if (wd->sel_obj == wd->digit[3]) + { + wd->min = wd->min - 1; + if (wd->min < 0) wd->min += 60; + } + if (wd->sel_obj == wd->digit[4]) + { + wd->sec = wd->sec - 10; + if (wd->sec < 0) wd->sec += 60; + } + if (wd->sel_obj == wd->digit[5]) + { + wd->sec = wd->sec - 1; + if (wd->sec < 0) wd->sec += 60; + } + if (wd->sel_obj == wd->ampm) + { + wd->hrs = wd->hrs - 12; + if (wd->hrs < 0) wd->hrs += 24; + } + wd->interval = wd->interval / 1.05; + ecore_timer_interval_set(wd->spin, wd->interval); + _time_update(data); + evas_object_smart_callback_call(data, "changed", NULL); + return ECORE_CALLBACK_RENEW; +clock_val_down_cancel: + wd->spin = NULL; +clock_val_down_exit_on_error: + return ECORE_CALLBACK_CANCEL; +} + +static void +_signal_clock_val_up_start(void *data, Evas_Object *obj, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->interval = wd->first_interval; + wd->sel_obj = obj; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = ecore_timer_add(wd->interval, _signal_clock_val_up, data); + _signal_clock_val_up(data); +} + +static void +_signal_clock_val_down_start(void *data, Evas_Object *obj, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->interval = wd->first_interval; + wd->sel_obj = obj; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = ecore_timer_add(wd->interval, _signal_clock_val_down, data); + _signal_clock_val_down(data); +} + +static void +_signal_clock_val_change_stop(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = NULL; + wd->sel_obj = NULL; +} + +static void +_time_update(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Edje_Message_Int msg; + int ampm = 0; + const char *style = elm_widget_style_get(obj); + if (!wd) return; + if ((wd->cur.seconds != wd->seconds) || (wd->cur.am_pm != wd->am_pm) || + (wd->cur.edit != wd->edit) || (wd->cur.digedit != wd->digedit)) + { + int i; + Evas_Coord mw, mh; + + for (i = 0; i < 6; i++) + { + if (wd->digit[i]) + { + evas_object_del(wd->digit[i]); + wd->digit[i] = NULL; + } + } + if (wd->ampm) + { + evas_object_del(wd->ampm); + wd->ampm = NULL; + } + + if ((wd->seconds) && (wd->am_pm)) + _elm_theme_object_set(obj, wd->clk, "clock", "base-all", style); + else if (wd->seconds) + _elm_theme_object_set(obj, wd->clk, "clock", "base-seconds", style); + else if (wd->am_pm) + _elm_theme_object_set(obj, wd->clk, "clock", "base-am_pm", style); + else + _elm_theme_object_set(obj, wd->clk, "clock", "base", style); + edje_object_scale_set(wd->clk, elm_widget_scale_get(obj) * + _elm_config->scale); + + for (i = 0; i < 6; i++) + { + char buf[16]; + + if ((!wd->seconds) && (i >= 4)) break; + wd->digit[i] = edje_object_add(evas_object_evas_get(wd->clk)); + _elm_theme_object_set(obj, wd->digit[i], "clock", "flipdigit", style); + edje_object_scale_set(wd->digit[i], elm_widget_scale_get(obj) * + _elm_config->scale); + if ((wd->edit) && (wd->digedit & (1 << i))) + edje_object_signal_emit(wd->digit[i], "elm,state,edit,on", "elm"); + edje_object_signal_callback_add(wd->digit[i], "elm,action,up,start", + "", _signal_clock_val_up_start, obj); + edje_object_signal_callback_add(wd->digit[i], "elm,action,up,stop", + "", _signal_clock_val_change_stop, obj); + edje_object_signal_callback_add(wd->digit[i], "elm,action,down,start", + "", _signal_clock_val_down_start, obj); + edje_object_signal_callback_add(wd->digit[i], "elm,action,down,stop", + "", _signal_clock_val_change_stop, obj); + mw = mh = -1; + elm_coords_finger_size_adjust(1, &mw, 2, &mh); + edje_object_size_min_restricted_calc(wd->digit[i], &mw, &mh, mw, mh); + elm_coords_finger_size_adjust(1, &mw, 2, &mh); + edje_extern_object_min_size_set(wd->digit[i], mw, mh); + snprintf(buf, sizeof(buf), "d%i", i); + edje_object_part_swallow(wd->clk , buf, wd->digit[i]); + evas_object_show(wd->digit[i]); + } + if (wd->am_pm) + { + wd->ampm = edje_object_add(evas_object_evas_get(wd->clk)); + _elm_theme_object_set(obj, wd->ampm, "clock", "flipampm", style); + edje_object_scale_set(wd->ampm, elm_widget_scale_get(obj) * + _elm_config->scale); + if (wd->edit) + edje_object_signal_emit(wd->ampm, "elm,state,edit,on", "elm"); + edje_object_signal_callback_add(wd->ampm, "elm,action,up,start", + "", _signal_clock_val_up_start, obj); + edje_object_signal_callback_add(wd->ampm, "elm,action,up,stop", + "", _signal_clock_val_change_stop, obj); + edje_object_signal_callback_add(wd->ampm, "elm,action,down,start", + "", _signal_clock_val_down_start, obj); + edje_object_signal_callback_add(wd->ampm, "elm,action,down,stop", + "", _signal_clock_val_change_stop, obj); + mw = mh = -1; + elm_coords_finger_size_adjust(1, &mw, 2, &mh); + edje_object_size_min_restricted_calc(wd->ampm, &mw, &mh, mw, mh); + elm_coords_finger_size_adjust(1, &mw, 2, &mh); + edje_extern_object_min_size_set(wd->ampm, mw, mh); + edje_object_part_swallow(wd->clk , "ampm", wd->ampm); + evas_object_show(wd->ampm); + } + + edje_object_size_min_calc(wd->clk, &mw, &mh); + evas_object_size_hint_min_set(obj, mw, mh); + + wd->cur.hrs = 0; + wd->cur.min = 0; + wd->cur.sec = 0; + wd->cur.ampm = -1; + wd->cur.seconds = wd->seconds; + wd->cur.am_pm = wd->am_pm; + wd->cur.edit = wd->edit; + wd->cur.digedit = wd->digedit; + } + if (wd->hrs != wd->cur.hrs) + { + int hrs; + int d1, d2, dc1, dc2; + + hrs = wd->hrs; + if (wd->am_pm) + { + if (hrs >= 12) + { + if (hrs > 12) hrs -= 12; + ampm = 1; + } + else if (!hrs) hrs = 12; + } + d1 = hrs / 10; + d2 = hrs % 10; + dc1 = wd->cur.hrs / 10; + dc2 = wd->cur.hrs % 10; + if (d1 != dc1) + { + msg.val = d1; + edje_object_message_send(wd->digit[0], EDJE_MESSAGE_INT, 1, &msg); + } + if (d2 != dc2) + { + msg.val = d2; + edje_object_message_send(wd->digit[1], EDJE_MESSAGE_INT, 1, &msg); + } + wd->cur.hrs = hrs; + } + if (wd->min != wd->cur.min) + { + int d1, d2, dc1, dc2; + + d1 = wd->min / 10; + d2 = wd->min % 10; + dc1 = wd->cur.min / 10; + dc2 = wd->cur.min % 10; + if (d1 != dc1) + { + msg.val = d1; + edje_object_message_send(wd->digit[2], EDJE_MESSAGE_INT, 1, &msg); + } + if (d2 != dc2) + { + msg.val = d2; + edje_object_message_send(wd->digit[3], EDJE_MESSAGE_INT, 1, &msg); + } + wd->cur.min = wd->min; + } + if (wd->seconds) + { + if (wd->sec != wd->cur.sec) + { + int d1, d2, dc1, dc2; + + d1 = wd->sec / 10; + d2 = wd->sec % 10; + dc1 = wd->cur.sec / 10; + dc2 = wd->cur.sec % 10; + if (d1 != dc1) + { + msg.val = d1; + edje_object_message_send(wd->digit[4], EDJE_MESSAGE_INT, 1, &msg); + } + if (d2 != dc2) + { + msg.val = d2; + edje_object_message_send(wd->digit[5], EDJE_MESSAGE_INT, 1, &msg); + } + wd->cur.sec = wd->sec; + } + } + else + wd->cur.sec = -1; + + if (wd->am_pm) + { + if (wd->hrs >= 12) ampm = 1; + if (ampm != wd->cur.ampm) + { + if (wd->cur.ampm != ampm) + { + msg.val = ampm; + edje_object_message_send(wd->ampm, EDJE_MESSAGE_INT, 1, &msg); + } + wd->cur.ampm = ampm; + } + } + else + wd->cur.ampm = -1; +} + +/** + * Add a new clock to the parent + * + * @param parent The parent object + * + * This function inserts a clock widget on a given canvas to show a + * animated clock. + * + * @ingroup Clock + */ +EAPI Evas_Object * +elm_clock_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "clock"); + elm_widget_type_set(obj, "clock"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + + wd->clk = edje_object_add(e); + elm_widget_resize_object_set(obj, wd->clk); + + wd->cur.ampm = -1; + wd->cur.seconds = EINA_TRUE; + wd->cur.am_pm = EINA_TRUE; + wd->cur.edit = EINA_TRUE; + wd->cur.digedit = ELM_CLOCK_NONE; + wd->first_interval = 0.85; + wd->timediff = 0; + + _time_update(obj); + _ticker(obj); + + return obj; +} + +/** + * Set the clock time + * + * @param obj The clock object + * @param hrs The hours to set + * @param min The minutes to set + * @param sec The secondes to set + * + * This function updates the time that is showed by the clock widget + * + * @ingroup Clock + */ +EAPI void +elm_clock_time_set(Evas_Object *obj, int hrs, int min, int sec) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->hrs = hrs; + wd->min = min; + wd->sec = sec; + _timediff_set(wd); + _time_update(obj); +} + +/** + * Get clock time + * + * @param obj The clock object + * @param hrs Pointer to the variable to get the hour of this clock + * object + * @param min Pointer to the variable to get the minute of this clock + * object + * @param sec Pointer to the variable to get the second of this clock + * object + * + * This function gets the time set of the clock widget and returns it + * on the variables passed as the arguments to function + * + * @ingroup Clock + */ +EAPI void +elm_clock_time_get(const Evas_Object *obj, int *hrs, int *min, int *sec) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (hrs) *hrs = wd->hrs; + if (min) *min = wd->min; + if (sec) *sec = wd->sec; +} + +/** + * Set if the clock settings can be edited + * + * @param obj The clock object + * @param edit Bool option for edited (1 = yes, 0 = no) + * + * This function sets if the clock settings can be edited or not. + * By default or if digit_edit option was previously set to ELM_CLOCK_NONE, + * all digits are editable. To choose what digits to make editable + * use elm_clock_digit_edit_set(). + * + * @ingroup Clock + */ +EAPI void +elm_clock_edit_set(Evas_Object *obj, Eina_Bool edit) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->edit = edit; + if (!edit) + _timediff_set(wd); + if ((edit) && (wd->digedit == ELM_CLOCK_NONE)) + elm_clock_digit_edit_set(obj, ELM_CLOCK_ALL); + else + _time_update(obj); +} + +/** + * Get if the clock settings can be edited + * + * @param obj The clock object + * @return Bool option for edited (1 = yes, 0 = no) + * + * This function gets if the clock settings can be edited or not. + * + * @ingroup Clock + */ +EAPI Eina_Bool +elm_clock_edit_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->edit; +} + +/** + * Set what digits of the clock are editable + * + * @param obj The clock object + * @param digedit Bit mask indicating the digits to edit + * + * If the digedit param is ELM_CLOCK_NONE, editing will be disabled. + * + * @ingroup Clock + */ +EAPI void +elm_clock_digit_edit_set(Evas_Object *obj, Elm_Clock_Digedit digedit) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->digedit = digedit; + if (digedit == ELM_CLOCK_NONE) + elm_clock_edit_set(obj, EINA_FALSE); + else + _time_update(obj); +} + +/** + * Get what digits of the clock are editable + * + * @param obj The clock object + * @return Bit mask indicating the digits. + * + * @ingroup Clock + */ +EAPI Elm_Clock_Digedit +elm_clock_digit_edit_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->digedit; +} + +/** + * Set if the clock shows hours in military or am/pm mode + * + * @param obj The clock object + * @param am_pm Bool option for the hours mode + * (1 = am/pm, 0 = military) + * + * This function sets the clock to show hours in military or am/pm + * mode. Some countries like Brazil the military mode (00-24h-format) + * is used in opposition to the USA where the am/pm mode is more + * common used. + * + * @ingroup Clock + */ +EAPI void +elm_clock_show_am_pm_set(Evas_Object *obj, Eina_Bool am_pm) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->am_pm = am_pm; + _time_update(obj); +} + +/** + * Get if the clock shows hours in military or am/pm mode + * + * @param obj The clock object + * @return Bool option for the hours mode + * (1 = am/pm, 0 = military) + * + * This function gets if the clock show hours in military or am/pm + * mode. Some countries like Brazil the military mode (00-24h-format) + * is used in opposition to the USA where the am/pm mode is more + * common used. + * + * @ingroup Clock + */ +EAPI Eina_Bool +elm_clock_show_am_pm_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->am_pm; +} + +/** + * Set if the clock shows hour with the seconds + * + * @param obj The clock object + * @param seconds Bool option for the show seconds + * (1 = show seconds, 0 = not show seconds) + * + * This function sets the clock to show or not to show the elapsed + * seconds. + * + * @ingroup Clock + */ +EAPI void +elm_clock_show_seconds_set(Evas_Object *obj, Eina_Bool seconds) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->seconds = seconds; + _time_update(obj); +} + +/** + * Get if the clock shows hour with the seconds + * + * @param obj The clock object + * @return Bool option for the show seconds + * (1 = show seconds, 0 = not show seconds) + * + * This function gets if the clock show or not show the elapsed + * seconds. + * + * @ingroup Clock + */ +EAPI Eina_Bool +elm_clock_show_seconds_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->seconds; +} + +/** + * Set the interval for the clock + * + * @param obj The clock object + * @param interval The interval value in seconds + * + * The interval value is decreased while the user increments or decrements + * the clock value. The next interval value is the previous interval / 1.05, + * so it speed up a bit. Default value is 0.85 seconds. + * + * @ingroup Clock + */ +EAPI void +elm_clock_interval_set(Evas_Object *obj, double interval) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->first_interval = interval; +} + +/** + * Get the interval of the clock + * + * @param obj The clock object + * @return The value of the first interval in seconds + * + * The interval value is decreased while the user increments or decrements + * the clock value. The next interval value is the previous interval / 1.05, + * so it speed up a bit. Default value is 0.85 seconds. + * + * @ingroup Clock + */ +EAPI double +elm_clock_interval_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->first_interval; +} diff --git a/src/lib/elm_cnp_helper.c b/src/lib/elm_cnp_helper.c new file mode 100644 index 0000000..9d8fb1c --- /dev/null +++ b/src/lib/elm_cnp_helper.c @@ -0,0 +1,1779 @@ +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#include +#include "elm_priv.h" + +#include + +#ifdef HAVE_ELEMENTARY_X + +#define ARRAYINIT(foo) [foo] = + +//#define DEBUGON 1 + + +#ifdef DEBUGON +# define cnp_debug(x...) fprintf(stderr, __FILE__": " x) +#else +# define cnp_debug(x...) +#endif + +#define PROVIDER_SET "__elm_cnp_provider_set" + +typedef struct _Paste_Image Paste_Image; +typedef struct _Cnp_Selection Cnp_Selection; +typedef struct _Escape Escape; +typedef struct _Tmp_Info Tmp_Info; +typedef struct _Cnp_Atom Cnp_Atom; +typedef struct _Saved_Type Saved_Type; +typedef struct _Dropable Dropable; + +typedef Eina_Bool (*Converter_Fn_Cb) (char *target, void *data, int size, void **data_ret, int *size_ret, Ecore_X_Atom *ttype, int *typesize); +typedef int (*Response_Handler_Cb) (Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *); +typedef int (*Notify_Handler_Cb) (Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *); + +enum +{ + CNP_ATOM_TARGETS = 0, + CNP_ATOM_text_uri, + CNP_ATOM_text_urilist, + CNP_ATOM_text_x_vcard, + CNP_ATOM_image_png, + CNP_ATOM_image_jpeg, + CNP_ATOM_image_bmp, + CNP_ATOM_image_gif, + CNP_ATOM_image_tiff, + CNP_ATOM_image_svg, + CNP_ATOM_image_xpm, + CNP_ATOM_image_tga, + CNP_ATOM_image_ppm, + CNP_ATOM_XELM, + CNP_ATOM_text_html_utf8, + CNP_ATOM_text_html, + CNP_ATOM_UTF8STRING, + CNP_ATOM_STRING, + CNP_ATOM_TEXT, + CNP_ATOM_text_plain_utf8, + CNP_ATOM_text_plain, + + CNP_N_ATOMS, +}; + +struct _Paste_Image +{ + Evas_Object *entry; + const char *tag; + const char *file; + Evas_Object *img; +}; + +struct _Cnp_Selection +{ + const char *debug; + Evas_Object *widget; + char *selbuf; + Evas_Object *requestwidget; + void *udata; + Elm_Sel_Format requestformat; + Elm_Drop_Cb datacb; + Eina_Bool (*set) (Ecore_X_Window, const void *data, int size); + Eina_Bool (*clear) (void); + void (*request) (Ecore_X_Window, const char *target); + + Elm_Sel_Format format; + Ecore_X_Selection ecore_sel; + + Eina_Bool active : 1; +}; + +struct _Escape +{ + const char *escape; + const char value; +}; + +struct _Tmp_Info +{ + char *filename; + void *map; + int fd; + int len; +}; + +struct _Cnp_Atom +{ + const char *name; + Elm_Sel_Format formats; + /* Called by ecore to do conversion */ + Converter_Fn_Cb converter; + Response_Handler_Cb response; + Notify_Handler_Cb notify; + /* Atom */ + Ecore_X_Atom atom; +}; + +struct _Saved_Type +{ + const char **types; + Paste_Image *pi; + int ntypes; + int x, y; + Eina_Bool textreq: 1; +}; + +struct _Dropable +{ + Evas_Object *obj; + /* FIXME: Cache window */ + Elm_Sel_Format types; + Elm_Drop_Cb dropcb; + void *cbdata; +}; + +static Tmp_Info *elm_cnp_tempfile_create(int size); +static int tmpinfo_free(Tmp_Info *tmp); + +static Eina_Bool _elm_cnp_init(void); +static Eina_Bool selection_clear(void *udata __UNUSED__, int type, void *event); +static Eina_Bool selection_notify(void *udata __UNUSED__, int type, void *event); +static char *remove_tags(const char *p, int *len); +static char *mark_up(const char *start, int inlen, int *lenp); + +static Evas_Object *image_provider(void *images, Evas_Object *entry, const char *item); +static void entry_deleted(void *images, Evas *e, Evas_Object *entry, void *unused); + + +static Eina_Bool targets_converter(char *target, void *data, int size, void **data_ret, int *size_ret, Ecore_X_Atom *ttype, int *typesize); +static Eina_Bool text_converter(char *target, void *data, int size, void **data_ret, int *size_ret, Ecore_X_Atom *ttype, int *typesize); +static Eina_Bool html_converter(char *target, void *data, int size, void **data_ret, int *size_ret, Ecore_X_Atom *ttype, int *typesize); +static Eina_Bool edje_converter(char *target, void *data, int size, void **data_ret, int *size_ret, Ecore_X_Atom *ttype, int *typesize); +static Eina_Bool uri_converter(char *target, void *data, int size, void **data_ret, int *size_ret, Ecore_X_Atom *ttype, int *typesize); +static Eina_Bool image_converter(char *target, void *data, int size, void **data_ret, int *size_ret, Ecore_X_Atom *ttype, int *typesize); +static Eina_Bool vcard_send(char *target, void *data, int size, void **data_ret, int *size_ret, Ecore_X_Atom *ttype, int *typesize); + +static int response_handler_targets(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *); + +static int notify_handler_targets(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify); +static int notify_handler_text(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify); +static int notify_handler_image(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify); +static int notify_handler_uri(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify); +static int notify_handler_html(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify); +static int vcard_receive(Cnp_Selection *sed, Ecore_X_Event_Selection_Notify *notify); + +static Paste_Image *pasteimage_alloc(const char *file, int pathlen); +static Eina_Bool pasteimage_append(Paste_Image *pi, Evas_Object *entry); +static void pasteimage_free(Paste_Image *pi); + +/* Optimisation: Turn this into a 256 byte table: + * then can lookup in one index, not N checks */ +static const Escape escapes[] = { + { "
    ", '\n' }, + { "<\t>", '\t' }, + { "gt;", '>' }, + { "lt;", '<' }, + { "amp;", '&' }, + { "quot;", '\'' }, + { "dquot;", '"' } +}; +#define N_ESCAPES ((int)(sizeof(escapes) / sizeof(escapes[0]))) + +static const char *image_extensions[] = +{ + ".png", + ".jpg", ".jpeg", ".jpe", ".jfif", ".jfi", + ".bmp", + ".xpm", + ".ppm", "pgm", ".pbm", ".pnm", + ".gif", + ".tif", ".tiff", + ".svg", ".svg.gz", + ".tga", ".targa", + + NULL +}; + +static Cnp_Atom atoms[CNP_N_ATOMS] = { + [CNP_ATOM_TARGETS] = { + "TARGETS", + (Elm_Sel_Format) -1, // everything + targets_converter, + response_handler_targets, + notify_handler_targets, + 0 + }, + [CNP_ATOM_XELM] = { + "application/x-elementary-markup", + ELM_SEL_FORMAT_MARKUP, + edje_converter, + NULL, + NULL, + 0 + }, + [CNP_ATOM_text_uri] = { + "text/uri", + ELM_SEL_FORMAT_MARKUP | ELM_SEL_FORMAT_IMAGE, /* Either images or entries */ + uri_converter, + NULL, + notify_handler_uri, + 0 + }, + [CNP_ATOM_text_urilist] = { + "text/uri-list", + ELM_SEL_FORMAT_IMAGE, + uri_converter, + NULL, + notify_handler_uri, + 0 + }, + [CNP_ATOM_text_x_vcard] = { + "text/x-vcard", + ELM_SEL_FORMAT_VCARD, + vcard_send, NULL, + vcard_receive, 0 + }, + [CNP_ATOM_image_png] = { + "image/png", + ELM_SEL_FORMAT_IMAGE, + image_converter, + NULL, + notify_handler_image, + 0 + }, + [CNP_ATOM_image_jpeg] = { + "image/jpeg", + ELM_SEL_FORMAT_IMAGE, + image_converter, + NULL, + notify_handler_image,/* Raw image data is the same */ + 0 + }, + [CNP_ATOM_image_bmp] = { + "image/x-ms-bmp", + ELM_SEL_FORMAT_IMAGE, + image_converter, + NULL, + notify_handler_image,/* Raw image data is the same */ + 0 + }, + [CNP_ATOM_image_gif] = { + "image/gif", + ELM_SEL_FORMAT_IMAGE, + image_converter, + NULL, + notify_handler_image,/* Raw image data is the same */ + 0 + }, + [CNP_ATOM_image_tiff] = { + "image/tiff", + ELM_SEL_FORMAT_IMAGE, + image_converter, + NULL, + notify_handler_image,/* Raw image data is the same */ + 0 + }, + [CNP_ATOM_image_svg] = { + "image/svg+xml", + ELM_SEL_FORMAT_IMAGE, + image_converter, + NULL, + notify_handler_image,/* Raw image data is the same */ + 0 + }, + [CNP_ATOM_image_xpm] = { + "image/x-xpixmap", + ELM_SEL_FORMAT_IMAGE, + image_converter, + NULL, + notify_handler_image,/* Raw image data is the same */ + 0 + }, + [CNP_ATOM_image_tga] = { + "image/x-tga", + ELM_SEL_FORMAT_IMAGE, + image_converter, + NULL, + notify_handler_image,/* Raw image data is the same */ + 0 + }, + [CNP_ATOM_image_ppm] = { + "image/x-portable-pixmap", + ELM_SEL_FORMAT_IMAGE, + image_converter, + NULL, + notify_handler_image,/* Raw image data is the same */ + 0 + }, + [CNP_ATOM_text_html_utf8] = { + "text/html;charset=utf-8", + ELM_SEL_FORMAT_HTML, + html_converter, + NULL, + notify_handler_html, + 0 + }, + [CNP_ATOM_text_html] = { + "text/html", + ELM_SEL_FORMAT_HTML, + html_converter, + NULL, + notify_handler_html, /* No encoding: Webkit only */ + 0 + }, + [CNP_ATOM_UTF8STRING] = { + "UTF8_STRING", + ELM_SEL_FORMAT_TEXT | ELM_SEL_FORMAT_MARKUP | ELM_SEL_FORMAT_HTML, + text_converter, + NULL, + notify_handler_text, + 0 + }, + [CNP_ATOM_STRING] = { + "STRING", + ELM_SEL_FORMAT_TEXT | ELM_SEL_FORMAT_MARKUP | ELM_SEL_FORMAT_HTML, + text_converter, + NULL, + notify_handler_text, + 0 + }, + [CNP_ATOM_TEXT] = { + "TEXT", + ELM_SEL_FORMAT_TEXT | ELM_SEL_FORMAT_MARKUP | ELM_SEL_FORMAT_HTML, + text_converter, + NULL, + NULL, + 0 + }, + [CNP_ATOM_text_plain_utf8] = { + "text/plain;charset=utf-8", + ELM_SEL_FORMAT_TEXT | ELM_SEL_FORMAT_MARKUP | ELM_SEL_FORMAT_HTML, + text_converter, + NULL, + NULL, + 0 + }, + [CNP_ATOM_text_plain] = { + "text/plain", + ELM_SEL_FORMAT_TEXT | ELM_SEL_FORMAT_MARKUP | ELM_SEL_FORMAT_HTML, + text_converter, + NULL, + NULL, + 0 + }, +}; + +static Cnp_Selection selections[ELM_SEL_MAX] = { + ARRAYINIT(ELM_SEL_PRIMARY) { + .debug = "Primary", + .ecore_sel = ECORE_X_SELECTION_PRIMARY, + .set = ecore_x_selection_primary_set, + .clear = ecore_x_selection_primary_clear, + .request = ecore_x_selection_primary_request, + }, + ARRAYINIT(ELM_SEL_SECONDARY) { + .debug = "Secondary", + .ecore_sel = ECORE_X_SELECTION_SECONDARY, + .set = ecore_x_selection_secondary_set, + .clear = ecore_x_selection_secondary_clear, + .request = ecore_x_selection_secondary_request, + }, + ARRAYINIT(ELM_SEL_CLIPBOARD) { + .debug = "Clipboard", + .ecore_sel = ECORE_X_SELECTION_CLIPBOARD, + .set = ecore_x_selection_clipboard_set, + .clear = ecore_x_selection_clipboard_clear, + .request = ecore_x_selection_clipboard_request, + }, + ARRAYINIT(ELM_SEL_XDND) { + .debug = "XDnD", + .ecore_sel = ECORE_X_SELECTION_XDND, + .request = ecore_x_selection_xdnd_request, + }, +}; + +/* Data for DND in progress */ +static Saved_Type savedtypes = { NULL, NULL, 0, 0, 0, EINA_FALSE }; + +static void (*dragdonecb) (void *data, Evas_Object *obj) = NULL; +static void *dragdonedata = NULL; + +static int _elm_cnp_init_count = 0; +/* FIXME: who left this out of XAtoms.h */ +static Ecore_X_Atom clipboard_atom; + +static Eina_List *pastedimages = NULL; + +/** + * Drag & Drop functions + */ + +/* FIXME: Way too many globals */ +static Eina_List *drops = NULL; +static Evas_Object *dragwin = NULL; +static int _dragx = 0, _dragy = 0; +static Ecore_Event_Handler *handler_pos = NULL; +static Ecore_Event_Handler *handler_drop = NULL; +static Ecore_Event_Handler *handler_enter = NULL; +static Ecore_Event_Handler *handler_status = NULL; + +#endif + +/* Stringshared, so I can just compare pointers later */ +static const char *text_uri; + +Eina_Bool +elm_selection_set(Elm_Sel_Type selection, Evas_Object *widget, Elm_Sel_Format format, const char *selbuf) +{ +#ifdef HAVE_ELEMENTARY_X + Cnp_Selection *sel; + + if ((unsigned int)selection >= (unsigned int)ELM_SEL_MAX) return EINA_FALSE; + if (!_elm_cnp_init_count) _elm_cnp_init(); + if ((!selbuf) && (format != ELM_SEL_FORMAT_IMAGE)) + return elm_selection_clear(selection, widget); + + sel = selections + selection; + + sel->active = 1; + sel->widget = widget; + + sel->set(elm_win_xwindow_get(widget),&selection,sizeof(Elm_Sel_Type)); + sel->format = format; + sel->selbuf = selbuf ? strdup(selbuf) : NULL; + + return EINA_TRUE; +#else + return EINA_FALSE; +#endif +} + +Eina_Bool +elm_selection_clear(Elm_Sel_Type selection, Evas_Object *widget) +{ +#ifdef HAVE_ELEMENTARY_X + Cnp_Selection *sel; + + if ((unsigned int)selection >= (unsigned int)ELM_SEL_MAX) return EINA_FALSE; + if (!_elm_cnp_init_count) _elm_cnp_init(); + + sel = selections + selection; + + /* No longer this selection: Consider it gone! */ + if ((!sel->active) || (sel->widget != widget)) return EINA_TRUE; + + sel->active = 0; + sel->widget = NULL; + sel->clear(); + + return EINA_TRUE; +#else + return EINA_FALSE; +#endif +} + +Eina_Bool +elm_selection_get(Elm_Sel_Type selection, Elm_Sel_Format format, + Evas_Object *widget, Elm_Drop_Cb datacb, void *udata) +{ +#ifdef HAVE_ELEMENTARY_X + Evas_Object *top; + Cnp_Selection *sel; + + if ((unsigned int)selection >= (unsigned int)ELM_SEL_MAX) return EINA_FALSE; + if (!_elm_cnp_init_count) _elm_cnp_init(); + + sel = selections + selection; + top = elm_widget_top_get(widget); + if (!top) return EINA_FALSE; + + sel->requestformat = format; + sel->requestwidget = widget; + sel->request(elm_win_xwindow_get(top), ECORE_X_SELECTION_TARGET_TARGETS); + sel->datacb = datacb; + sel->udata = udata; + + return EINA_TRUE; +#else + return EINA_FALSE; +#endif +} + +#ifdef HAVE_ELEMENTARY_X + +static Eina_Bool +_elm_cnp_init(void) +{ + int i; + + if (_elm_cnp_init_count++) return EINA_TRUE; + for (i = 0; i < CNP_N_ATOMS; i++) + { + atoms[i].atom = ecore_x_atom_get(atoms[i].name); + ecore_x_selection_converter_atom_add(atoms[i].atom, + atoms[i].converter); + } + clipboard_atom = ecore_x_atom_get("CLIPBOARD"); + + ecore_event_handler_add(ECORE_X_EVENT_SELECTION_CLEAR, selection_clear, NULL); + ecore_event_handler_add(ECORE_X_EVENT_SELECTION_NOTIFY, selection_notify, NULL); + + text_uri = eina_stringshare_add("text/uri-list"); + return EINA_TRUE; +} + +static Eina_Bool +selection_clear(void *udata __UNUSED__, int type __UNUSED__, void *event) +{ + Ecore_X_Event_Selection_Clear *ev = event; + Cnp_Selection *sel; + int i; + + for (i = 0; i < ELM_SEL_MAX; i++) + { + if (selections[i].ecore_sel == ev->selection) break; + } + cnp_debug("selection %d clear\n", i); + /* Not me... Don't care */ + if (i == ELM_SEL_MAX) return ECORE_CALLBACK_PASS_ON; + + sel = selections + i; + sel->active = 0; + sel->widget = NULL; + sel->selbuf = NULL; + + return ECORE_CALLBACK_PASS_ON; +} + + +/* + * Response to a selection notify: + * - So we have asked for the selection list. + * - If it's the targets list, parse it, and fire of what we want, + * else it's the data we want. + */ +static Eina_Bool +selection_notify(void *udata __UNUSED__, int type __UNUSED__, void *event) +{ + Ecore_X_Event_Selection_Notify *ev = event; + Cnp_Selection *sel; + int i; + + cnp_debug("selection notify callback: %d\n",ev->selection); + switch (ev->selection) + { + case ECORE_X_SELECTION_CLIPBOARD: + sel = selections + ELM_SEL_CLIPBOARD; + break; + case ECORE_X_SELECTION_PRIMARY: + sel = selections + ELM_SEL_PRIMARY; + break; + case ECORE_X_SELECTION_SECONDARY: + sel = selections + ELM_SEL_SECONDARY; + break; + case ECORE_X_SELECTION_XDND: + sel = selections + ELM_SEL_XDND; + break; + default: + return ECORE_CALLBACK_PASS_ON; + } + cnp_debug("Target is %s\n", ev->target); + + for (i = 0; i < CNP_N_ATOMS; i++) + { + if (!strcmp(ev->target, atoms[i].name)) + { + if (atoms[i].notify) + { + cnp_debug("Found something: %s\n", atoms[i].name); + atoms[i].notify(sel, ev); + } + else + { + cnp_debug("Ignored: No handler!\n"); + } + } + } + + return ECORE_CALLBACK_PASS_ON; +} + + + +static Eina_Bool +targets_converter(char *target __UNUSED__, void *data, int size __UNUSED__, void **data_ret, int *size_ret, Ecore_X_Atom *ttype, int *typesize) +{ + int i,count; + Ecore_X_Atom *aret; + Cnp_Selection *sel; + + if (!data_ret) return EINA_FALSE; + + sel = selections + *((int *)data); + + for (i = 0, count = 0; i < CNP_N_ATOMS ; i++) + { + if (sel->format & atoms[i].formats) count++; + } + + aret = malloc(sizeof(Ecore_X_Atom) * count); + for (i = 0, count = 0; i < CNP_N_ATOMS; i++) + { + if (sel->format & atoms[i].formats) aret[count ++] = atoms[i].atom; + } + + *data_ret = aret; + if (typesize) *typesize = 32 /* urk */; + if (ttype) *ttype = ECORE_X_ATOM_ATOM; + if (size_ret) *size_ret = count; + + return EINA_TRUE; +} + +static Eina_Bool +image_converter(char *target __UNUSED__, void *data __UNUSED__, int size __UNUSED__, void **data_ret __UNUSED__, int *size_ret __UNUSED__, Ecore_X_Atom *ttype __UNUSED__, int *typesize __UNUSED__) +{ + cnp_debug("Image converter called\n"); + return EINA_TRUE; +} + +static Eina_Bool +vcard_send(char *target __UNUSED__, void *data __UNUSED__, int size __UNUSED__, void **data_ret, int *size_ret, Ecore_X_Atom *ttype __UNUSED__, int *typesize __UNUSED__) +{ + Cnp_Selection *sel; + + cnp_debug("Vcard send called\n"); + + sel = selections + *((int *)data); + + if (data_ret) *data_ret = strdup(sel->selbuf); + if (size_ret) *size_ret = strlen(sel->selbuf); + + return EINA_TRUE; +} +/* + * Callback to handle a targets response on a selection request: + * So pick the format we'd like; and then request it. + */ +static int +notify_handler_targets(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify) +{ + Ecore_X_Selection_Data_Targets *targets; + Ecore_X_Atom *atomlist; + int i, j; + + targets = notify->data; + atomlist = (Ecore_X_Atom *)(targets->data.data); + + for (j = 1; j < CNP_N_ATOMS; j++) + { + cnp_debug("\t%s %d\n", atoms[j].name, atoms[j].atom); + if (!(atoms[j].formats & sel->requestformat)) continue; + for (i = 0; i < targets->data.length; i++) + { + if ((atoms[j].atom == atomlist[i]) && (atoms[j].notify)) + { + cnp_debug("Atom %s matches\n",atoms[j].name); + goto done; + } + } + } + + cnp_debug("Couldn't find anything that matches\n"); + return ECORE_CALLBACK_PASS_ON; + + done: + cnp_debug("Sending request for %s\n",atoms[j].name); + sel->request(elm_win_xwindow_get(sel->requestwidget), atoms[j].name); + + return ECORE_CALLBACK_PASS_ON; +} + +static int +response_handler_targets(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify) +{ + Ecore_X_Selection_Data_Targets *targets; + Ecore_X_Atom *atomlist; + Evas_Object *top; + int i,j; + + targets = notify->data; + atomlist = (Ecore_X_Atom *)(targets->data.data); + + /* Start from 1: Skip targets */ + for (j = 1 ; j < CNP_N_ATOMS ; j ++) + { + if (!(atoms[j].formats & sel->requestformat)) continue; + for (i = 0 ; i < targets->data.length ; i ++) + { + if ((atoms[j].atom == atomlist[i]) && (atoms[j].response)) + { + /* Found a match: Use it */ + goto found; + } + } + } +found: + if (j == CNP_N_ATOMS) + { + cnp_debug("No matching type found\n"); + return 0; + } + + top = elm_widget_top_get(sel->requestwidget); + if (!top) return 0; + + sel->request(elm_win_xwindow_get(top), atoms[j].name); + return 0; +} + + +static int +notify_handler_text(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify) +{ + Ecore_X_Selection_Data *data; + char *str; + + data = notify->data; + cnp_debug("Notify handler text %d %d %p\n", data->format,data->length, data->data); + str = mark_up((char *)data->data, data->length, NULL); + cnp_debug("String is %s (from %s)\n", str, data->data); + elm_entry_entry_insert(sel->requestwidget, str); + free(str); + return 0; +} + + +/** + * So someone is pasting an image into my entry or widget... + */ +static int +notify_handler_uri(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify) +{ + Ecore_X_Selection_Data *data; + Ecore_X_Selection_Data_Files *files; + Paste_Image *pi; + char *p, *pp, *ext; + + data = notify->data; + cnp_debug("data->format is %d %p %p\n", data->format, notify, data); + if (data->content == ECORE_X_SELECTION_CONTENT_FILES) + { + cnp_debug("got a files list\n"); + files = notify->data; + if (files->num_files > 1) + { + /* Don't handle many items */ + cnp_debug("more then one file: Bailing\n"); + return 0; + } + p = files->files[0]; + } + else p = (char *)data->data; + if (!p) + { + cnp_debug("Couldn't find a file\n"); + return 0; + } + cnp_debug("Got %s\n",p); + if (strncmp(p, "file://", 7)) + { + /* Try and continue if it looks sane */ + if (*p != '/') return 0; + } + else p += strlen("file://"); + + ext = p + strlen(p); + if (ext) + { + Eina_Bool extok = EINA_FALSE; + int i; + + for (i = 0; image_extensions[i]; i++) + { + pp = ext - strlen(image_extensions[i]); + if ((pp >= p) && (!strcasecmp(pp, image_extensions[i]))) + { + extok = EINA_TRUE; + break; + } + } + if (!extok) + { + cnp_debug("No known image format extension, ignoring\n"); + if (savedtypes.textreq) savedtypes.textreq = 0; + return 0; + } + } + + if (savedtypes.pi) pasteimage_free(savedtypes.pi); + pi = pasteimage_alloc(p, strlen(p)); + if (savedtypes.textreq) + { + savedtypes.textreq = 0; + savedtypes.pi = pi; + } + else + { + pasteimage_append(pi, sel->requestwidget); + savedtypes.pi = NULL; + } + return 0; +} + +/** + * Just receieved an vcard, either through cut and paste, or dnd. + */ +static int +vcard_receive(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify) +{ + Dropable *dropable; + Eina_List *l; + Ecore_X_Selection_Data *data; + + data = notify->data; + cnp_debug("vcard receive\n"); + + if (sel == (selections + ELM_SEL_XDND)) + { + Elm_Selection_Data ddata; + + cnp_debug("drag & drop\n"); + /* FIXME: this needs to be generic: Used for all receives */ + EINA_LIST_FOREACH(drops, l, dropable) + { + if (dropable->obj == sel->requestwidget) break; + } + if (!dropable) + { + cnp_debug("Unable to find drop object"); + ecore_x_dnd_send_finished(); + return 0; + } + dropable = eina_list_data_get(l); + ddata.x = savedtypes.x; + ddata.y = savedtypes.y; + ddata.format = ELM_SEL_FORMAT_VCARD; + ddata.data = data->data; + ddata.len = data->length; + dropable->dropcb(dropable->cbdata, dropable->obj, &ddata); + ecore_x_dnd_send_finished(); + } + else if (sel->datacb) + { + Elm_Selection_Data ddata; + ddata.x = ddata.y = 0; + ddata.format = ELM_SEL_FORMAT_IMAGE; + ddata.data = data->data; + ddata.len = data->length; + sel->datacb(sel->udata, sel->widget, &ddata); + } + else + { + cnp_debug("Paste request\n"); + } + + return 0; + +} + + +static int +notify_handler_image(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify) +{ + Ecore_X_Selection_Data *data; + Tmp_Info *tmp; + Paste_Image *pi; + + cnp_debug("got a png (or a jpeg)!\n"); + data = notify->data; + + cnp_debug("Size if %d\n", data->length); + + if (sel->datacb) + { + Elm_Selection_Data ddata; + + ddata.x = ddata.y = 0; + ddata.format = ELM_SEL_FORMAT_IMAGE; + ddata.data = data->data; + ddata.len = data->length; + sel->datacb(sel->udata, sel->widget, &ddata); + return 0; + } + + /* generate tmp name */ + tmp = elm_cnp_tempfile_create(data->length); + memcpy(tmp->map, data->data, data->length); + munmap(tmp->map,data->length); + + /* FIXME: Add to paste image data to clean up */ + pi = pasteimage_alloc(tmp->filename, strlen(tmp->filename)); + pasteimage_append(pi, sel->requestwidget); + + tmpinfo_free(tmp); + return 0; +} + + +/** + * Warning: Generic text/html can';t handle it sanely. + * Firefox sends ucs2 (i think). + * chrome sends utf8... blerg + */ +static int +notify_handler_html(Cnp_Selection *sel, Ecore_X_Event_Selection_Notify *notify) +{ + Ecore_X_Selection_Data *data; + + cnp_debug("Got some HTML: Checking encoding is useful\n"); + data = notify->data; + + if (sel->datacb) + { + Elm_Selection_Data ddata; + ddata.x = ddata.y = 0; + ddata.format = ELM_SEL_FORMAT_HTML; + ddata.data = data->data; + ddata.len = data->length; + sel->datacb(sel->udata, sel->widget, &ddata); + return 0; + } + + char *stripstr = NULL; + stripstr = malloc(sizeof(char) * (data->length + 1)); + strncpy(stripstr, (char *)data->data, data->length); + stripstr[data->length] = '\0'; + cnp_debug("String is %s (%d bytes)\n", stripstr, data->length); + elm_entry_entry_insert(sel->requestwidget, stripstr); + free(stripstr); + return 0; +} + + +static Eina_Bool +text_converter(char *target __UNUSED__, void *data, int size __UNUSED__, void **data_ret, int *size_ret, Ecore_X_Atom *ttype __UNUSED__, int *typesize __UNUSED__) +{ + Cnp_Selection *sel; + + cnp_debug("text converter\n"); + sel = selections + *((int *)data); + if (!sel->active) return EINA_TRUE; + + if ((sel->format & ELM_SEL_FORMAT_MARKUP) || + (sel->format & ELM_SEL_FORMAT_HTML)) + { + *data_ret = remove_tags(sel->selbuf, size_ret); + } + else if (sel->format & ELM_SEL_FORMAT_TEXT) + { + *data_ret = strdup(sel->selbuf); + *size_ret = strlen(sel->selbuf); + } + else if (sel->format & ELM_SEL_FORMAT_IMAGE) + { + cnp_debug("Image %s\n", evas_object_type_get(sel->widget)); + cnp_debug("Elm type: %s\n", elm_object_widget_type_get(sel->widget)); + evas_object_image_file_get(elm_photocam_internal_image_get(sel->widget), (const char **)data_ret, NULL); + if (!*data_ret) *data_ret = strdup("No file"); + else *data_ret = strdup(*data_ret); + *size_ret = strlen(*data_ret); + } + return EINA_TRUE; +} + +static Eina_Bool +edje_converter(char *target __UNUSED__, void *data, int size __UNUSED__, void **data_ret, int *size_ret, Ecore_X_Atom *ttype __UNUSED__, int *typesize __UNUSED__) +{ + Cnp_Selection *sel; + + sel = selections + *((int *)data); + if (data_ret) *data_ret = strdup(sel->selbuf); + if (size_ret) *size_ret = strlen(sel->selbuf); + + return EINA_TRUE; +} + + +static Eina_Bool +html_converter(char *target __UNUSED__, void *data, int size __UNUSED__, void **data_ret, int *size_ret, Ecore_X_Atom *ttype __UNUSED__, int *typesize __UNUSED__) +{ + Cnp_Selection *sel; + + sel = selections + *(int *)data; + if (data_ret) *data_ret = strdup(sel->selbuf); + if (size_ret) *size_ret = strlen(sel->selbuf); + + return EINA_TRUE; +} + +static Eina_Bool +uri_converter(char *target __UNUSED__, void *data, int size __UNUSED__, void **data_ret, int *size_ret, Ecore_X_Atom *ttype __UNUSED__, int *typesize __UNUSED__) +{ + Cnp_Selection *sel; + sel = selections + *((int *)data); + cnp_debug("Uri converter\n"); + if (data_ret) *data_ret = strdup(sel->selbuf); + if (size_ret) *size_ret = strlen(sel->selbuf); + return EINA_TRUE; +} + +/* + * Image paste provide + */ + +/* FIXME: Should add provider for each pasted item: Use data to store it + * much easier */ +static Evas_Object * +image_provider(void *images __UNUSED__, Evas_Object *entry, const char *item) +{ + Paste_Image *pi; + Eina_List *l; + + cnp_debug("image provider for %s called\n", item); + EINA_LIST_FOREACH(pastedimages, l, pi) + { + cnp_debug("is it %s?\n",pi->tag); + if (!strcmp(pi->tag, item)) + { + /* Found it */ + Evas_Object *o; + o = evas_object_image_filled_add(evas_object_evas_get(entry)); + /* FIXME: Handle eets */ + cnp_debug("file is %s (object is %p)\n", pi->file, o); + evas_object_image_file_set(o, pi->file, NULL); + evas_object_show(o); + return o; + } + } + return NULL; +} + + +static Paste_Image * +pasteimage_alloc(const char *file, int pathlen) +{ + Paste_Image *pi; + int len; + char *buf, *filebuf; + int prefixlen = strlen("file://"); + + pi = calloc(1, sizeof(Paste_Image)); + if (!pi) return NULL; + + len = snprintf(NULL, 0, "pasteimage-%p", pi); + len++; + buf = malloc(len); + if (!buf) + { + free(pi); + return NULL; + } + snprintf(buf, len, "pasteimage-%p", pi); + pi->tag = buf; + + if (file) + { + if (strstr(file,"file://")) file += prefixlen; + filebuf = alloca(pathlen + 1); + strncpy(filebuf, file, pathlen); + filebuf[pathlen] = 0; + pi->file = strdup(filebuf); + } + + return pi; +} + +static void +pasteimage_free(Paste_Image *pi) +{ + if (!pi) return; + if (pi->file) free((void*)pi->file); + if (pi->tag) free((void*)pi->tag); + free(pi); +} + +static Eina_Bool +pasteimage_provider_set(Evas_Object *entry) +{ + void *v; + const char *type; + + if (!entry) return EINA_FALSE; + type = elm_widget_type_get(entry); + cnp_debug("type is %s\n", type); + if ((!type) || (strcmp(type, "entry"))) return EINA_FALSE; + + v = evas_object_data_get(entry, PROVIDER_SET); + if (!v) + { + evas_object_data_set(entry, PROVIDER_SET, pasteimage_provider_set); + elm_entry_item_provider_append(entry, image_provider, NULL); + evas_object_event_callback_add(entry, EVAS_CALLBACK_FREE, + entry_deleted, NULL); + } + return EINA_TRUE; +} + + +static Eina_Bool +pasteimage_append(Paste_Image *pi, Evas_Object *entry) +{ + char *entrytag; + int len; + static const char *tagstring = ""; + + if (!pi) return EINA_FALSE; + if (!entry) return EINA_FALSE; + + pasteimage_provider_set(entry); + + len = strlen(tagstring)+strlen(pi->file); + + pastedimages = eina_list_append(pastedimages, pi); + entrytag = alloca(len + 1); + snprintf(entrytag, len + 1, tagstring, pi->file); + elm_entry_entry_insert(entry, entrytag); + + return EINA_TRUE; +} + +static void +entry_deleted(void *images __UNUSED__, Evas *e __UNUSED__, Evas_Object *entry, void *unused __UNUSED__) +{ + Paste_Image *pi; + Eina_List *l,*next; + + EINA_LIST_FOREACH_SAFE(pastedimages, l, next, pi) + { + if (pi->entry == entry) + pastedimages = eina_list_remove_list(pastedimages, l); + } +} + + +static char * +remove_tags(const char *p, int *len) +{ + char *q,*ret; + int i; + if (!p) return NULL; + + q = malloc(strlen(p) + 1); + if (!q) return NULL; + ret = q; + + while (*p) + { + if ((*p != '<') && (*p != '&')) *q++ = *p++; + else if (*p == '<') + { + if ((p[1] == 'b') && (p[2] == 'r') && + ((p[3] == ' ') || (p[3] == '/') || (p[3] == '>'))) + *q++ = '\n'; + while ((*p) && (*p != '>')) p++; + p++; + } + else if (*p == '&') + { + p++; + for (i = 0 ; i < N_ESCAPES ; i++) + { + if (!strncmp(p,escapes[i].escape, strlen(escapes[i].escape))) + { + p += strlen(escapes[i].escape); + *q = escapes[i].value; + q++; + break; + } + } + if (i == N_ESCAPES) *q ++= '&'; + } + } + *q = 0; + if (len) *len = q - ret; + return ret; +} + +/* Mark up */ +static char * +mark_up(const char *start, int inlen, int *lenp) +{ + int l, i; + const char *p; + char *q, *ret; + const char *endp = NULL; + + if (!start) return NULL; + if (inlen >= 0) endp = start + inlen; + /* First pass: Count characters */ + for (l = 0, p = start; ((!endp) || (p < endp)) && (*p); p++) + { + for (i = 0 ; i < N_ESCAPES ; i ++) + { + if (*p == escapes[i].value) + { + l += strlen(escapes[i].escape); + break; + } + } + if (i == N_ESCAPES) l++; + } + + q = ret = malloc(l + 1); + + /* Second pass: Change characters */ + for (p = start; *p; ) + { + for (i = 0; i < N_ESCAPES; i++) + { + if (*p == escapes[i].value) + { + strcpy(q, escapes[i].escape); + q += strlen(escapes[i].escape); + p ++; + break; + } + } + if (i == N_ESCAPES) *q++ = *p++; + } + *q = 0; + + if (lenp) *lenp = l; + return ret; +} + + +static Eina_Bool +_dnd_enter(void *data __UNUSED__, int etype __UNUSED__, void *ev) +{ + Ecore_X_Event_Xdnd_Enter *enter = ev; + int i; + + /* Skip it */ + if ((!enter) || (!enter->num_types) || (!enter->types)) return EINA_TRUE; + + cnp_debug("Types\n"); + savedtypes.ntypes = enter->num_types; + if (savedtypes.types) free(savedtypes.types); + savedtypes.types = malloc(sizeof(char *) * enter->num_types); + if (!savedtypes.types) return EINA_FALSE; + + for (i = 0; i < enter->num_types; i++) + { + savedtypes.types[i] = eina_stringshare_add(enter->types[i]); + cnp_debug("Type is %s %p %p\n", enter->types[i], + savedtypes.types[i],text_uri); + if (savedtypes.types[i] == text_uri) + { + /* Request it, so we know what it is */ + cnp_debug("Sending uri request\n"); + savedtypes.textreq = 1; + savedtypes.pi = NULL; /* FIXME: Free? */ + ecore_x_selection_xdnd_request(enter->win, text_uri); + } + } + + /* FIXME: Find an object and make it current */ + return EINA_TRUE; +} + +static Eina_Bool +_dnd_drop(void *data __UNUSED__, int etype __UNUSED__, void *ev) +{ + struct _Ecore_X_Event_Xdnd_Drop *drop; + Dropable *dropable; + Eina_List *l; + Ecore_Evas *ee; + Ecore_X_Window xwin; + Elm_Selection_Data ddata; + int x, y, w, h; + int i, j; + + drop = ev; + + // check we still have something to drop + if (!drops) return EINA_TRUE; + + /* Find any widget in our window; then work out geometry rel to our window */ + for (l = drops; l; l = l->next) + { + dropable = l->data; + xwin = (Ecore_X_Window)ecore_evas_window_get + (ecore_evas_ecore_evas_get(evas_object_evas_get + (dropable->obj))); + if (xwin == drop->win) break; + } + /* didn't find a window */ + if (!l) return EINA_TRUE; + + /* Calculate real (widget relative) position */ + // - window position + // - widget position + ee = ecore_evas_ecore_evas_get(evas_object_evas_get(dropable->obj)); + ecore_evas_geometry_get(ee, &x, &y, NULL, NULL); + savedtypes.x = drop->position.x - x; + savedtypes.y = drop->position.y - y; + + cnp_debug("Drop position is %d,%d\n", savedtypes.x, savedtypes.y); + + for (; l; l = l->next) + { + dropable = l->data; + evas_object_geometry_get(dropable->obj, &x, &y, &w, &h); + if ((savedtypes.x >= x) && (savedtypes.y >= y) && + (savedtypes.x < x + w) && (savedtypes.y < y + h)) + break; /* found! */ + } + + if (!l) return EINA_TRUE; /* didn't find one */ + + evas_object_geometry_get(dropable->obj, &x, &y, NULL, NULL); + savedtypes.x -= x; + savedtypes.y -= y; + + /* Find our type from the previous list */ + for (i = 0; i < CNP_N_ATOMS; i++) + { + for (j = 0; j < savedtypes.ntypes; j++) + { + if (!strcmp(savedtypes.types[j], atoms[i].name)) goto found; + } + } + + cnp_debug("Didn't find a target\n"); + return EINA_TRUE; + +found: + cnp_debug("Found a target we'd like: %s\n", atoms[i].name); + cnp_debug("0x%x\n",xwin); + + if (i == CNP_ATOM_text_urilist) + { + cnp_debug("We found a URI... (%scached) %s\n", + savedtypes.pi ? "" : "not ", + savedtypes.pi->file); + if (savedtypes.pi) + { + char *entrytag; + static const char *tagstring = ""; + ddata.x = savedtypes.x; + ddata.y = savedtypes.y; + + /* If it's markup that also supports images */ + if ((dropable->types & ELM_SEL_FORMAT_MARKUP) && + (dropable->types & ELM_SEL_FORMAT_IMAGE)) + { + int len; + ddata.format = ELM_SEL_FORMAT_MARKUP; + pasteimage_provider_set(dropable->obj); + + pastedimages = eina_list_append(pastedimages, savedtypes.pi); + len = strlen(tagstring) + strlen(savedtypes.pi->file); + entrytag = alloca(len + 1); + snprintf(entrytag, len + 1, tagstring, savedtypes.pi->file); + ddata.data = entrytag; + cnp_debug("Insert %s\n", (char *)ddata.data); + dropable->dropcb(dropable->cbdata, dropable->obj, &ddata); + ecore_x_dnd_send_finished(); + return EINA_TRUE; + } + else if (dropable->types & ELM_SEL_FORMAT_IMAGE) + { + cnp_debug("Doing image insert (%s)\n", savedtypes.pi->file); + ddata.format = ELM_SEL_FORMAT_IMAGE; + ddata.data = (char *)savedtypes.pi->file; + dropable->dropcb(dropable->cbdata, dropable->obj, &ddata); + ecore_x_dnd_send_finished(); + + pasteimage_free(savedtypes.pi); + savedtypes.pi = NULL; + + return EINA_TRUE; + } + else + { + cnp_debug("Item doesn't support images... passing\n"); + pasteimage_free(savedtypes.pi); + return EINA_TRUE; + } + } + else if (savedtypes.textreq) + { + /* Already asked: Pretend we asked now, and paste immediately when + * it comes in */ + savedtypes.textreq = 0; + ecore_x_dnd_send_finished(); + return EINA_TRUE; + } + } + + cnp_debug("doing a request then\n"); + selections[ELM_SEL_XDND].requestwidget = dropable->obj; + selections[ELM_SEL_XDND].requestformat = ELM_SEL_FORMAT_MARKUP; + selections[ELM_SEL_XDND].active = EINA_TRUE; + + ecore_x_selection_xdnd_request(xwin, atoms[i].name); + + return EINA_TRUE; +} +static Eina_Bool +_dnd_position(void *data __UNUSED__, int etype __UNUSED__, void *ev) +{ + struct _Ecore_X_Event_Xdnd_Position *pos; + Ecore_X_Rectangle rect; + + pos = ev; + + /* Need to send a status back */ + /* FIXME: Should check I can drop here */ + /* FIXME: Should highlight widget */ + rect.x = pos->position.x - 5; + rect.y = pos->position.y - 5; + rect.width = 10; + rect.height = 10; + ecore_x_dnd_send_status(EINA_TRUE, EINA_FALSE, rect, pos->action); + + return EINA_TRUE; +} + +/** + * When dragging this is callback response from the destination. + * The important thing we care about: Can we drop; thus update cursor + * appropriately. + */ +static Eina_Bool +_dnd_status(void *data __UNUSED__, int etype __UNUSED__, void *ev) +{ + struct _Ecore_X_Event_Xdnd_Status *status = ev; + + if (!status) return EINA_TRUE; + + /* Only thing we care about: will accept */ + if (status->will_accept) + { + cnp_debug("Will accept\n"); + } + else + { /* Won't accept */ + cnp_debug("Won't accept accept\n"); + } + return EINA_TRUE; +} + +/** + * Add a widget as drop target. + */ +Eina_Bool +elm_drop_target_add(Evas_Object *obj, Elm_Sel_Type format, Elm_Drop_Cb dropcb, void *cbdata) +{ + Dropable *drop; + Ecore_X_Window xwin; + Eina_List *item; + int first; + + if (!obj) return EINA_FALSE; + if (!_elm_cnp_init_count) _elm_cnp_init(); + + /* Is this the first? */ + first = (!drops) ? 1 : 0; + + EINA_LIST_FOREACH(drops, item, drop) + { + if (drop->obj == obj) + { + /* Update: Not a new one */ + drop->dropcb = dropcb; + drop->cbdata = cbdata; + drop->types = format; + return EINA_TRUE; + } + } + + /* Create new drop */ + drop = calloc(1, sizeof(Dropable)); + if (!drop) return EINA_FALSE; + /* FIXME: Check for eina's deranged error method */ + drops = eina_list_append(drops, drop); + + if (!drops/* || or other error */) + { + free(drop); + return EINA_FALSE; + } + drop->dropcb = dropcb; + drop->cbdata = cbdata; + drop->types = format; + drop->obj = obj; + + evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, + /* I love C and varargs */ + (Evas_Object_Event_Cb)elm_drop_target_del, + obj); + /* FIXME: Handle resizes */ + + /* If not the first: We're done */ + if (!first) return EINA_TRUE; + + xwin = (Ecore_X_Window)ecore_evas_window_get + (ecore_evas_ecore_evas_get(evas_object_evas_get(obj))); + + ecore_x_dnd_aware_set(xwin, EINA_TRUE); + + cnp_debug("Adding drop target calls\n"); + handler_enter = ecore_event_handler_add(ECORE_X_EVENT_XDND_ENTER, + _dnd_enter, NULL); + handler_pos = ecore_event_handler_add(ECORE_X_EVENT_XDND_POSITION, + _dnd_position, NULL); + handler_drop = ecore_event_handler_add(ECORE_X_EVENT_XDND_DROP, + _dnd_drop, NULL); + + return EINA_TRUE; +} + +Eina_Bool +elm_drop_target_del(Evas_Object *obj) +{ + Dropable *drop,*del; + Eina_List *item; + Ecore_X_Window xwin; + + del = NULL; + EINA_LIST_FOREACH(drops, item, drop) + { + if (drop->obj == obj) + { + drops = eina_list_remove_list(drops, item); + del = drop; + break; + } + } + if (!del) return EINA_FALSE; + + evas_object_event_callback_del(obj, EVAS_CALLBACK_FREE, + (Evas_Object_Event_Cb)elm_drop_target_del); + free(drop); + /* If still drops there: All fine.. continue */ + if (drops) return EINA_TRUE; + + cnp_debug("Disabling DND\n"); + xwin = (Ecore_X_Window)ecore_evas_window_get + (ecore_evas_ecore_evas_get(evas_object_evas_get(obj))); + ecore_x_dnd_aware_set(xwin, EINA_FALSE); + + ecore_event_handler_del(handler_pos); + ecore_event_handler_del(handler_drop); + ecore_event_handler_del(handler_enter); + + if (savedtypes.pi) + { + pasteimage_free(savedtypes.pi); + savedtypes.pi = NULL; + } + + return EINA_TRUE; +} + + +static void +_drag_mouse_up(void *un __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *data __UNUSED__) +{ + evas_object_event_callback_del(obj, EVAS_CALLBACK_MOUSE_UP, _drag_mouse_up); + ecore_x_dnd_drop(); + if (dragdonecb) + { + dragdonecb(dragdonecb,selections[ELM_SEL_XDND].widget); + dragdonecb = NULL; + } + if (dragwin) + { + evas_object_del(dragwin); + dragwin = NULL; + } +} + +static void +_drag_move(void *data __UNUSED__, Ecore_X_Xdnd_Position *pos) +{ + evas_object_move(dragwin, + pos->position.x - _dragx, + pos->position.y - _dragy); +} + + +Eina_Bool +elm_drag_start(Evas_Object *obj, Elm_Sel_Format format, const char *data, void (*dragdone) (void *data, Evas_Object *), void *donecbdata) +{ + Ecore_X_Window xwin; + Cnp_Selection *sel; + Elm_Sel_Type xdnd = ELM_SEL_XDND; + Ecore_Evas *ee; + int x, y, x2, y2, x3, y3; + Evas_Object *icon; + int w, h; + + if (!_elm_cnp_init_count) _elm_cnp_init(); + + xwin = elm_win_xwindow_get(obj); + + cnp_debug("starting drag...\n"); + + ecore_x_dnd_type_set(xwin, "text/uri-list", 1); + sel = selections + ELM_SEL_XDND; + sel->active = 1; + sel->widget = obj; + sel->format = format; + sel->selbuf = data ? strdup(data) : NULL; + dragdonecb = dragdone; + dragdonedata = donecbdata; + + ecore_x_dnd_callback_pos_update_set(_drag_move, NULL); + ecore_x_dnd_begin(xwin, (unsigned char *)&xdnd, sizeof(Elm_Sel_Type)); + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOUSE_UP, + _drag_mouse_up, NULL); + + handler_status = ecore_event_handler_add(ECORE_X_EVENT_XDND_STATUS, + _dnd_status, NULL); + + dragwin = elm_win_add(NULL, "Elm Drag Object", ELM_WIN_UTILITY); + elm_win_override_set(dragwin, 1); + + /* FIXME: Images only */ + icon = elm_icon_add(dragwin); + elm_icon_file_set(icon, data + 7, NULL); /* 7!? "file://" */ + elm_win_resize_object_add(dragwin,icon); + evas_object_size_hint_weight_set(icon, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(icon, EVAS_HINT_FILL, EVAS_HINT_FILL); + + /* Position subwindow appropriately */ + ee = ecore_evas_ecore_evas_get(evas_object_evas_get(obj)); + ecore_evas_geometry_get(ee, &x, &y, NULL, NULL); + evas_object_geometry_get(obj, &x2, &y2, &w, &h); + x += x2; + y += y2; + evas_object_move(dragwin, x, y); + evas_object_resize(icon, w, h); + evas_object_resize(dragwin, w, h); + + evas_object_show(icon); + evas_object_show(dragwin); + + evas_pointer_canvas_xy_get(evas_object_evas_get(obj), &x3, &y3); + _dragx = x3 - x2; + _dragy = y3 - y2; + + return EINA_TRUE; +} + +static Tmp_Info * +elm_cnp_tempfile_create(int size) +{ + Tmp_Info *info; + const char *tmppath; + int len; + + info = malloc(sizeof(Tmp_Info)); + if (!info) return NULL; + + tmppath = getenv("TMP"); + if (!tmppath) tmppath = P_tmpdir; + if (!tmppath) tmppath = "/tmp"; + len = snprintf(NULL, 0, "%s/%sXXXXXX", tmppath, "elmcnpitem-"); + if (len < 0) + { + free(info); + return NULL; + } + len++; + info->filename = malloc(len); + if (!info->filename) + { + free(info); + return NULL; + } + snprintf(info->filename,len,"%s/%sXXXXXX", tmppath, "elmcnpitem-"); + + info->fd = mkstemp(info->filename); + +# ifdef __linux__ + { + char *tmp; + /* And before someone says anything see POSIX 1003.1-2008 page 400 */ + long pid; + + pid = (long)getpid(); + /* Use pid instead of /proc/self: That way if can be passed around */ + len = snprintf(NULL,0,"/proc/%li/fd/%i", pid, info->fd); + len++; + tmp = malloc(len); + if (tmp) + { + snprintf(tmp,len, "/proc/%li/fd/%i", pid, info->fd); + unlink(info->filename); + free(info->filename); + info->filename = tmp; + } + } +# endif + + cnp_debug("filename is %s\n", info->filename); + if (size < 1) + { + /* Set map to NULL and return */ + info->map = NULL; + info->len = 0; + return info; + } + + /* Map it in */ + if (ftruncate(info->fd, size)) + { + perror("ftruncate"); + info->map = NULL; + info->len = 0; + return info; + } + + info->map = mmap(NULL, size, PROT_READ|PROT_WRITE, MAP_SHARED, info->fd, 0); + if (info->map == MAP_FAILED) + { + perror("mmap"); + info->map = NULL; + info->len = 0; + } + + return info; +} + + +static int +tmpinfo_free(Tmp_Info *info) +{ + if (!info) return 0; + free(info->filename); + free(info); + return 0; +} + +#else +/* Stubs for windows */ +Eina_Bool +elm_drag_start(Evas_Object *o, Elm_Sel_Format f, const char *d, void (*donecb)(void *, Evas_Object *),void *cbdata) +{ + return EINA_FALSE; +} + +Eina_Bool +elm_drop_target_add(Evas_Object *obj, Elm_Sel_Type format, Elm_Drop_Cb dropcb, void *cbdata) +{ + return EINA_FALSE; +} + +Eina_Bool +elm_drop_target_del(Evas_Object *o) +{ + return EINA_TRUE; +} +#endif + +/* vim:set ts=8 sw=3 sts=3 expandtab cino=>5n-2f0^-2{2(0W1st0 :*/ diff --git a/src/lib/elm_colorselector.c b/src/lib/elm_colorselector.c new file mode 100644 index 0000000..53d4846 --- /dev/null +++ b/src/lib/elm_colorselector.c @@ -0,0 +1,878 @@ +#include +#include "elm_priv.h" + +/** + * @addtogroup Colorselector Colorselector + * + * By using colorselector, you can select a color. + * Colorselector made a color using HSV/HSB mode. + */ + +#define BASE_STEP 360.0 +#define HUE_STEP 360.0 +#define SAT_STEP 128.0 +#define LIG_STEP 256.0 +#define ALP_STEP 256.0 + +typedef enum _Button_State +{ + BUTTON_RELEASED, + L_BUTTON_PRESSED, + R_BUTTON_PRESSED +} Button_State; + +typedef enum _Color_Type +{ + HUE, + SATURATION, + LIGHTNESS, + ALPHA +} Color_Type; + +typedef struct _Colorselector_Data Colorselector_Data; +struct _Colorselector_Data +{ + Evas_Object *parent; + Evas_Object *colorbar; + Evas_Object *bar; + Evas_Object *lbt; + Evas_Object *rbt; + Evas_Object *bg_rect; + Evas_Object *arrow; + Evas_Object *touch_area; + Color_Type color_type; + Button_State button_state; +}; + +typedef struct _Widget_Data Widget_Data; +struct _Widget_Data +{ + Evas_Object *base; + Colorselector_Data *cp[4]; + Evas_Coord _x, _y, _w, _h; + int r, g, b, a; + int er, eg, eb; + int sr, sg, sb; + int lr, lg, lb; + double h, s, l; + Ecore_Timer *lp_timer; + Ecore_Timer *mv_timer; +}; + +static const char *widtype = NULL; + +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _rgb_to_hsl(void *data); +static void _hsl_to_rgb(void *data); +static void _color_with_saturation(void *data); +static void _color_with_lightness(void *data); +static void _draw_rects(void *data, double x); +static void _arrow_cb(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _colorbar_cb(void *data, Evas *e, Evas_Object *obj, void *event_info); +static Eina_Bool _mv_timer(void *data); +static Eina_Bool _long_press_timer(void *data); +static void _left_button_down_cb(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _right_button_down_cb(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _left_button_up_cb(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _right_button_up_cb(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _add_colorbar(Evas_Object *obj); +static void _set_color(Evas_Object *obj, int r, int g, int b, int a); + +#define SIG_CHANGED "changed" + +static const Evas_Smart_Cb_Description _signals[] = +{ + {SIG_CHANGED, ""}, + {NULL, NULL} +}; + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int i = 0; + + if (!wd) return; + if (wd->lp_timer) ecore_timer_del(wd->lp_timer); + if (wd->mv_timer) ecore_timer_del(wd->mv_timer); + for (i = 0; i < 4; i++) free(wd->cp[i]); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int i; + + if ((!wd) || (!wd->base)) return; + + _elm_theme_object_set(obj, wd->base, "colorselector", "bg", + elm_widget_style_get(obj)); + + for (i = 0; i < 4; i++) + { + evas_object_del(wd->cp[i]->colorbar); + wd->cp[i]->colorbar = NULL; + evas_object_del(wd->cp[i]->bar); + wd->cp[i]->bar = NULL; + evas_object_del(wd->cp[i]->lbt); + wd->cp[i]->lbt = NULL; + evas_object_del(wd->cp[i]->rbt); + wd->cp[i]->rbt = NULL; + if (i != 0) + { + evas_object_del(wd->cp[i]->bg_rect); + wd->cp[i]->bg_rect = NULL; + } + evas_object_del(wd->cp[i]->arrow); + wd->cp[i]->arrow = NULL; + evas_object_del(wd->cp[i]->touch_area); + wd->cp[i]->touch_area = NULL; + } + + _add_colorbar(obj); + _sizing_eval(obj); +} + +static void +_colorselector_set_size_hints(Evas_Object *obj, int timesw, int timesh) +{ + Evas_Coord minw = -1, minh = -1; + + elm_coords_finger_size_adjust(timesw, &minw, timesh, &minh); + edje_object_size_min_restricted_calc(obj, &minw, &minh, + minw, minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + int i; + + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + for (i = 0; i < 4; i++) + { + if (wd->cp[i]->bg_rect) + _colorselector_set_size_hints(wd->cp[i]->bg_rect, 1, 1); + _colorselector_set_size_hints(wd->cp[i]->bar, 1, 1); + _colorselector_set_size_hints(wd->cp[i]->rbt, 1, 1); + _colorselector_set_size_hints(wd->cp[i]->lbt, 1, 1); + + _colorselector_set_size_hints(wd->cp[i]->colorbar, 4, 1); + + } + + elm_coords_finger_size_adjust(4, &minw, 4, &minh); + edje_object_size_min_restricted_calc(wd->base, &minw, &minh, minw, minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_rgb_to_hsl(void *data) +{ + Widget_Data *wd = data; + double r, g, b; + double v, m, vm; + double r2, g2, b2; + + r = wd->r; + g = wd->g; + b = wd->b; + + r /= 255.0; + g /= 255.0; + b /= 255.0; + + v = (r > g) ? r : g; + v = (v > b) ? v : b; + + m = (r < g) ? r : g; + m = (m < b) ? m : b; + + wd->h = 0.0; + wd->s = 0.0; + wd->l = 0.0; + + wd->l = (m + v) / 2.0; + + if (wd->l <= 0.0) return; + + vm = v - m; + wd->s = vm; + + if (wd->s > 0.0) wd->s /= (wd->l <= 0.5) ? (v + m) : (2.0 - v - m); + else return; + + r2 = (v - r) / vm; + g2 = (v - g) / vm; + b2 = (v - b) / vm; + + if (r == v) wd->h = (g == m ? 5.0 + b2 : 1.0 - g2); + else if (g == v) wd->h = (b == m ? 1.0 + r2 : 3.0 - b2); + else wd->h = (r == m ? 3.0 + g2 : 5.0 - r2); + + wd->h *= 60.0; +} + +static void +_hsl_to_rgb(void *data) +{ + Widget_Data *wd = data; + double r = 0, g = 0, b = 0; + double _h, _s, _l; + int i = 0; + double sv, vsf, f, p, q, t, v; + + _h = wd->h; + _s = wd->s; + _l = wd->l; + + if (_s == 0.0) r = g = b = _l; + else + { + if (_h == 360.0) _h = 0.0; + _h /= 60.0; + + v = (_l <= 0.5) ? (_l * (1.0 + _s)) : (_l + _s - (_l * _s)); + p = _l + _l - v; + + if (v) sv = (v - p) / v; + else sv = 0; + + i = (int)_h; + f = _h - i; + + vsf = v * sv * f; + + t = p + vsf; + q = v - vsf; + + switch (i) + { + case 0: + r = v; + g = t; + b = p; + break; + case 1: + r = q; + g = v; + b = p; + break; + case 2: + r = p; + g = v; + b = t; + break; + case 3: + r = p; + g = q; + b = v; + break; + case 4: + r = t; + g = p; + b = v; + break; + case 5: + r = v; + g = p; + b = q; + break; + } + } + i = (int)(r * 255.0); + f = (r * 255.0) - i; + wd->r = (f <= 0.5) ? i : (i + 1); + + i = (int)(g * 255.0); + f = (g * 255.0) - i; + wd->g = (f <= 0.5) ? i : (i + 1); + + i = (int)(b * 255.0); + f = (b * 255.0) - i; + wd->b = (f <= 0.5) ? i : (i + 1); +} + +static void +_color_with_saturation(void *data) +{ + Widget_Data *wd = data; + + if (wd->er > 127) wd->sr = 127 + (int)((double)(wd->er - 127) * wd->s); + else wd->sr = 127 - (int)((double)(127 - wd->er) * wd->s); + if (wd->eg > 127) wd->sg = 127 + (int)((double)(wd->eg - 127) * wd->s); + else wd->sg = 127 - (int)((double)(127 - wd->eg) * wd->s); + if (wd->eb > 127) wd->sb = 127 + (int)((double)(wd->eb - 127) * wd->s); + else wd->sb = 127 - (int)((double)(127 - wd->eb) * wd->s); +} + +static void +_color_with_lightness(void *data) +{ + Widget_Data *wd = data; + + if (wd->l > 0.5) + { + wd->lr = wd->er + (int)((double)(255 - wd->er) * (wd->l - 0.5) * 2.0); + wd->lg = wd->eg + (int)((double)(255 - wd->eg) * (wd->l - 0.5) * 2.0); + wd->lb = wd->eb + (int)((double)(255 - wd->eb) * (wd->l - 0.5) * 2.0); + } + else if (wd->l < 0.5) + { + wd->lr = (double)wd->er * wd->l * 2.0; + wd->lg = (double)wd->eg * wd->l * 2.0; + wd->lb = (double)wd->eb * wd->l * 2.0; + } + else + { + wd->lr = wd->er; + wd->lg = wd->eg; + wd->lb = wd->eb; + } +} + +static void +_draw_rects(void *data, double x) +{ + Colorselector_Data *cp = data; + Widget_Data *wd = elm_widget_data_get(cp->parent); + double one_six = 1.0 / 6.0; + + switch (cp->color_type) + { + case HUE: + wd->h = 360.0 * x; + + if (x < one_six) + { + wd->er = 255; + wd->eg = (255.0 * x * 6.0); + wd->eb = 0; + } + else if (x < 2 * one_six) + { + wd->er = 255 - (int)(255.0 * (x - one_six) * 6.0); + wd->eg = 255; + wd->eb = 0; + } + else if (x < 3 * one_six) + { + wd->er = 0; + wd->eg = 255; + wd->eb = (int)(255.0 * (x - (2.0 * one_six)) * 6.0); + } + else if (x < 4 * one_six) + { + wd->er = 0; + wd->eg = 255 - (int)(255.0 * (x - (3.0 * one_six)) * 6.0); + wd->eb = 255; + } + else if (x < 5 * one_six) + { + wd->er = 255.0 * (x - (4.0 * one_six)) * 6.0; + wd->eg = 0; + wd->eb = 255; + } + else + { + wd->er = 255; + wd->eg = 0; + wd->eb = 255 - (int)(255.0 * (x - (5.0 * one_six)) * 6.0); + } + + evas_object_color_set(wd->cp[0]->arrow, wd->er, wd->eg, wd->eb, 255); + evas_object_color_set(wd->cp[1]->bg_rect, wd->er, wd->eg, wd->eb, 255); + evas_object_color_set(wd->cp[2]->bg_rect, wd->er, wd->eg, wd->eb, 255); + evas_object_color_set(wd->cp[3]->bar, wd->er, wd->eg, wd->eb, 255); + + _color_with_saturation(wd); + evas_object_color_set(wd->cp[1]->arrow, wd->sr, wd->sg, wd->sb, 255); + + _color_with_lightness(wd); + evas_object_color_set(wd->cp[2]->arrow, wd->lr, wd->lg, wd->lb, 255); + + evas_object_color_set(wd->cp[3]->arrow, + (wd->er * wd->a) / 255, + (wd->eg * wd->a) / 255, + (wd->eb * wd->a) / 255, + wd->a); + break; + + case SATURATION: + wd->s = 1.0 - x; + _color_with_saturation(wd); + evas_object_color_set(wd->cp[1]->arrow, wd->sr, wd->sg, wd->sb, 255); + break; + + case LIGHTNESS: + wd->l = x; + _color_with_lightness(wd); + evas_object_color_set(wd->cp[2]->arrow, wd->lr, wd->lg, wd->lb, 255); + break; + + case ALPHA: + wd->a = 255.0 * x; + evas_object_color_set(wd->cp[3]->arrow, wd->er, wd->eg, wd->eb, wd->a); + break; + + default: + break; + } + _hsl_to_rgb(wd); +} + +static void +_arrow_cb(void *data, Evas_Object *obj, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Colorselector_Data *cp = data; + double x, y; + + edje_object_part_drag_value_get(obj, "elm.arrow", &x, &y); + _draw_rects(data, x); + evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); +} + +static void +_colorbar_cb(void *data, Evas *e, Evas_Object *obj __UNUSED__, void *event_info) +{ + Colorselector_Data *cp = data; + Evas_Event_Mouse_Down *ev = event_info; + Evas_Coord x, y, w, h; + double arrow_x = 0, arrow_y; + + evas_object_geometry_get(cp->bar, &x, &y, &w, &h); + edje_object_part_drag_value_get(cp->colorbar, "elm.arrow", + &arrow_x, &arrow_y); + if (w > 0) arrow_x = (double)(ev->output.x - x) / (double)w; + if (arrow_x > 1) arrow_x = 1; + if (arrow_x < 0) arrow_x = 0; + edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", arrow_x, arrow_y); + _draw_rects(data, arrow_x); + evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); + evas_event_feed_mouse_cancel(e, 0, NULL); + evas_event_feed_mouse_down(e, 1, EVAS_BUTTON_NONE, 0, NULL); +} + +static Eina_Bool +_mv_timer(void *data) +{ + Colorselector_Data *cp = data; + Widget_Data *wd = elm_widget_data_get(cp->parent); + double x, y; + + if (!wd) return EINA_FALSE; + + edje_object_part_drag_value_get(cp->colorbar, "elm.arrow", &x, &y); + if (cp->button_state == L_BUTTON_PRESSED) + { + x -= 1.0 / BASE_STEP; + if (x < 0.0) x = 0.0; + edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", x, y); + _draw_rects(data, x); + evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); + return EINA_TRUE; + } + else if (cp->button_state == R_BUTTON_PRESSED) + { + x += 1.0 / BASE_STEP; + if (x > 1.0) x = 1.0; + edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", x, y); + _draw_rects(data, x); + evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); + return EINA_TRUE; + } + wd->mv_timer = NULL; + return EINA_FALSE; +} + +static Eina_Bool +_long_press_timer(void *data) +{ + Colorselector_Data *cp = data; + Widget_Data *wd = elm_widget_data_get(cp->parent); + + if (wd->mv_timer) ecore_timer_del(wd->mv_timer); + wd->mv_timer = ecore_timer_add(0.01, _mv_timer, cp); + + wd->lp_timer = NULL; + return EINA_FALSE; +} + +static void +_left_button_down_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Colorselector_Data *cp = data; + Widget_Data *wd = elm_widget_data_get(cp->parent); + double x, y; + + edje_object_signal_emit(cp->lbt, "elm,state,left,button,down", + "left_button"); + edje_object_part_drag_value_get(cp->colorbar, "elm.arrow", &x, &y); + + switch(cp->color_type) + { + case HUE : + x -= 1.0 / HUE_STEP; + break; + case SATURATION : + x -= 1.0 / SAT_STEP; + break; + case LIGHTNESS : + x -= 1.0 / LIG_STEP; + break; + case ALPHA : + x -= 1.0 / ALP_STEP; + break; + default : + break; + } + + if (x < 0.0) x = 0.0; + + edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", x, y); + _draw_rects(data, x); + evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); + cp->button_state = L_BUTTON_PRESSED; + if (wd->lp_timer) ecore_timer_del(wd->lp_timer); + wd->lp_timer = ecore_timer_add(_elm_config->longpress_timeout, _long_press_timer, cp); +} + +static void +_right_button_down_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Colorselector_Data *cp = data; + Widget_Data *wd = elm_widget_data_get(cp->parent); + double x, y; + + edje_object_signal_emit(cp->rbt, "elm,state,right,button,down", + "right_button"); + edje_object_part_drag_value_get(cp->colorbar, "elm.arrow", &x, &y); + + switch(cp->color_type) + { + case HUE : + x += 1.0 / HUE_STEP; + break; + case SATURATION : + x += 1.0 / SAT_STEP; + break; + case LIGHTNESS : + x += 1.0 / LIG_STEP; + break; + case ALPHA : + x += 1.0 / ALP_STEP; + break; + default : + break; + } + + if (x > 1.0) x = 1.0; + + edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", x, y); + _draw_rects(data, x); + evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); + cp->button_state = R_BUTTON_PRESSED; + wd->lp_timer = ecore_timer_add(_elm_config->longpress_timeout, _long_press_timer, cp); +} + +static void +_left_button_up_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Colorselector_Data *cp = data; + Widget_Data *wd = elm_widget_data_get(cp->parent); + + if (wd->lp_timer) + { + ecore_timer_del(wd->lp_timer); + wd->lp_timer = NULL; + } + if (wd->mv_timer) + { + ecore_timer_del(wd->mv_timer); + wd->mv_timer = NULL; + } + + cp->button_state = BUTTON_RELEASED; + edje_object_signal_emit(cp->lbt, "elm,state,left,button,up", "left_button"); +} + +static void +_right_button_up_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Colorselector_Data *cp = data; + Widget_Data *wd = elm_widget_data_get(cp->parent); + + if (wd->lp_timer) + { + ecore_timer_del(wd->lp_timer); + wd->lp_timer = NULL; + } + if (wd->mv_timer) + { + ecore_timer_del(wd->mv_timer); + wd->mv_timer = NULL; + } + + cp->button_state = BUTTON_RELEASED; + edje_object_signal_emit(cp->rbt, "elm,state,right,button,up", + "right_button"); +} + +static void +_add_colorbar(Evas_Object *obj) +{ + char colorbar_name[128]; + char colorbar_s[128]; + Widget_Data *wd; + Evas *e; + int i = 0; + + wd = elm_widget_data_get(obj); + if (!wd) return; + + e = evas_object_evas_get(obj); + + for (i = 0; i < 4; i++) + { + wd->cp[i] = ELM_NEW(Colorselector_Data); + wd->cp[i]->parent = obj; + switch(i) + { + case 0 : + wd->cp[i]->color_type = HUE; + break; + case 1 : + wd->cp[i]->color_type = SATURATION; + break; + case 2 : + wd->cp[i]->color_type = LIGHTNESS; + break; + case 3 : + wd->cp[i]->color_type = ALPHA; + break; + default : + break; + } + /* load colorbar area */ + wd->cp[i]->colorbar = edje_object_add(e); + _elm_theme_object_set(obj, wd->cp[i]->colorbar, "colorselector", "base", + "default"); + snprintf(colorbar_name, sizeof(colorbar_name), "colorbar_%d", i); + snprintf(colorbar_s, sizeof(colorbar_s), "elm.colorbar_%d", i); + edje_object_signal_callback_add(wd->cp[i]->colorbar, "drag", "*", + _arrow_cb, wd->cp[i]); + edje_object_part_swallow(wd->base, colorbar_s, wd->cp[i]->colorbar); + elm_widget_sub_object_add(obj, wd->cp[i]->colorbar); + + /* load colorbar image */ + wd->cp[i]->bar = edje_object_add(e); + _elm_theme_object_set(obj, wd->cp[i]->bar, "colorselector", "image", + colorbar_name); + edje_object_part_swallow(wd->cp[i]->colorbar, "elm.bar", + wd->cp[i]->bar); + elm_widget_sub_object_add(obj, wd->cp[i]->bar); + + /* provide expanded touch area */ + wd->cp[i]->touch_area = evas_object_rectangle_add(e); + evas_object_color_set(wd->cp[i]->touch_area, 0, 0, 0, 0); + edje_object_part_swallow(wd->cp[i]->colorbar, "elm.arrow_bg", + wd->cp[i]->touch_area); + evas_object_event_callback_add(wd->cp[i]->touch_area, + EVAS_CALLBACK_MOUSE_DOWN, _colorbar_cb, + wd->cp[i]); + elm_widget_sub_object_add(obj, wd->cp[i]->touch_area); + + /* load background rectangle of the colorbar. used for + changing color of the opacity bar */ + if ((i == 1) || (i == 2)) + { + wd->cp[i]->bg_rect = evas_object_rectangle_add(e); + evas_object_color_set(wd->cp[i]->bg_rect, wd->er, wd->eg, wd->eb, + 255); + edje_object_part_swallow(wd->cp[i]->colorbar, "elm.bar_bg", + wd->cp[i]->bg_rect); + + elm_widget_sub_object_add(obj, wd->cp[i]->bg_rect); + } + if (i == 3) + { + wd->cp[i]->bg_rect = edje_object_add(e); + _elm_theme_object_set(obj, wd->cp[i]->bg_rect, "colorselector", + "bg_image", colorbar_name); + edje_object_part_swallow(wd->cp[i]->colorbar, "elm.bar_bg", + wd->cp[i]->bg_rect); + elm_widget_sub_object_add(obj, wd->cp[i]->bg_rect); + evas_object_color_set(wd->cp[i]->bar, wd->er, wd->eg, wd->eb, 255); + } + /* load arrow image, pointing the colorbar */ + wd->cp[i]->arrow = edje_object_add(e); + _elm_theme_object_set(obj, wd->cp[i]->arrow, "colorselector", "image", + "updown"); + edje_object_part_swallow(wd->cp[i]->colorbar, "elm.arrow_icon", + wd->cp[i]->arrow); + elm_widget_sub_object_add(obj, wd->cp[i]->arrow); + if (i == 2) + evas_object_color_set(wd->cp[i]->arrow, 0, 0, 0, 255); + else + evas_object_color_set(wd->cp[i]->arrow, wd->er, wd->eg, wd->eb, 255); + + /* load left button */ + wd->cp[i]->lbt = edje_object_add(e); + _elm_theme_object_set(obj, wd->cp[i]->lbt, "colorselector", "button", + "left"); + evas_object_event_callback_add(wd->cp[i]->lbt, EVAS_CALLBACK_MOUSE_DOWN, + _left_button_down_cb, wd->cp[i]); + evas_object_event_callback_add(wd->cp[i]->lbt, EVAS_CALLBACK_MOUSE_UP, + _left_button_up_cb, wd->cp[i]); + edje_object_part_swallow(wd->cp[i]->colorbar, "elm.l_button", + wd->cp[i]->lbt); + elm_widget_sub_object_add(obj, wd->cp[i]->lbt); + + /* load right button */ + wd->cp[i]->rbt = edje_object_add(e); + _elm_theme_object_set(obj, wd->cp[i]->rbt, "colorselector", "button", + "right"); + evas_object_event_callback_add(wd->cp[i]->rbt, EVAS_CALLBACK_MOUSE_DOWN, + _right_button_down_cb, wd->cp[i]); + evas_object_event_callback_add(wd->cp[i]->rbt, EVAS_CALLBACK_MOUSE_UP, + _right_button_up_cb, wd->cp[i]); + edje_object_part_swallow(wd->cp[i]->colorbar, "elm.r_button", + wd->cp[i]->rbt); + elm_widget_sub_object_add(obj, wd->cp[i]->rbt); + + } +} + +static void +_set_color(Evas_Object *obj, int r, int g, int b, int a) +{ + Widget_Data *wd = elm_widget_data_get(obj); + double x, y; + + wd->r = r; + wd->g = g; + wd->b = b; + wd->a = a; + + _rgb_to_hsl(wd); + + edje_object_part_drag_value_get(wd->cp[0]->colorbar, "elm.arrow", &x, &y); + x = wd->h / 360.0; + edje_object_part_drag_value_set(wd->cp[0]->colorbar, "elm.arrow", x, y); + _draw_rects(wd->cp[0], x); + + edje_object_part_drag_value_get(wd->cp[1]->colorbar, "elm.arrow", &x, &y); + x = 1.0 - wd->s; + edje_object_part_drag_value_set(wd->cp[1]->colorbar, "elm.arrow", x, y); + _draw_rects(wd->cp[1], x); + + edje_object_part_drag_value_get(wd->cp[2]->colorbar, "elm.arrow", &x, &y); + x = wd->l; + edje_object_part_drag_value_set(wd->cp[2]->colorbar, "elm.arrow", x, y); + _draw_rects(wd->cp[2], x); + + edje_object_part_drag_value_get(wd->cp[3]->colorbar, "elm.arrow", &x, &y); + x = wd->a / 255.0; + edje_object_part_drag_value_set(wd->cp[3]->colorbar, "elm.arrow", x, y); + _draw_rects(wd->cp[3], x); +} + +/** + * Add a new colorselector to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Colorselector + */ +EAPI Evas_Object * +elm_colorselector_add(Evas_Object *parent) +{ + Evas_Object *obj = NULL; + Widget_Data *wd = NULL; + Evas *e; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "colorselector"); + elm_widget_type_set(obj, "colorselector"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + + /* load background edj */ + wd->base = edje_object_add(e); + _elm_theme_object_set(obj, wd->base, "colorselector", "bg", "default"); + elm_widget_resize_object_set(obj, wd->base); + + wd->er = 255; + wd->eg = 0; + wd->eb = 0; + wd->h = 0.0; + wd->s = 1.0; + wd->l = 0.0; + wd->a = 255; + + _hsl_to_rgb(wd); + _add_colorbar(obj); + _sizing_eval(obj); + + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set a color for the colorselector + * + * @param obj Colorselector object + * @param r r-value of color + * @param g g-value of color + * @param b b-value of color + * @param a a-value of color + * + * @ingroup Colorselector + */ +EAPI void +elm_colorselector_color_set(Evas_Object *obj, int r, int g, int b, int a) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + _set_color(obj, r, g, b, a); +} + +/** + * Get a color from the colorselector + * + * @param obj Colorselector object + * @param r integer pointer for r-value of color + * @param g integer pointer for g-value of color + * @param b integer pointer for b-value of color + * @param a integer pointer for a-value of color + * + * @ingroup Colorselector + */ +EAPI void +elm_colorselector_color_get(const Evas_Object *obj, int *r, int *g, int *b, int*a) +{ + Widget_Data *wd = elm_widget_data_get(obj); + ELM_CHECK_WIDTYPE(obj, widtype); + + if (r) *r = wd->r; + if (g) *g = wd->g; + if (b) *b = wd->b; + if (a) *a = wd->a; +} diff --git a/src/lib/elm_config.c b/src/lib/elm_config.c new file mode 100644 index 0000000..f0b006e --- /dev/null +++ b/src/lib/elm_config.c @@ -0,0 +1,1740 @@ +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif + +#ifdef HAVE_EVIL +# include +#endif + +#include +#include "elm_priv.h" + +Elm_Config *_elm_config = NULL; +char *_elm_profile = NULL; +static Eet_Data_Descriptor *_config_edd = NULL; +static Eet_Data_Descriptor *_config_font_overlay_edd = NULL; + +static Ecore_Poller *_elm_cache_flush_poller = NULL; + +const char *_elm_engines[] = { + "software_x11", + "fb", + "directfb", + "software_16_x11", + "software_8_x11", + "xrender_x11", + "opengl_x11", + "software_gdi", + "software_16_wince_gdi", + "sdl", + "software_16_sdl", + "opengl_sdl", + NULL +}; + +/* whenever you want to add a new text class support into Elementary, + declare it both here and in the (default) theme */ +static const Elm_Text_Class _elm_text_classes[] = { + {"button", "Button Labels"}, + {"label", "Text Labels"}, + {"entry", "Text Entries"}, + {"title_bar", "Title Bar"}, + {"list_item", "List Items"}, + {"grid_item", "Grid Items"}, + {"toolbar_item", "Toolbar Items"}, + {"menu_item", "Menu Items"}, + {NULL, NULL} +}; + +static void _desc_init(void); +static void _desc_shutdown(void); +static void _profile_fetch_from_conf(void); +static void _config_free(void); +static void _config_apply(void); +static Elm_Config *_config_user_load(void); +static Elm_Config *_config_system_load(void); +static void _config_load(void); +static void _config_update(void); +static void _env_get(void); +static size_t _elm_data_dir_snprintf(char *dst, + size_t size, + const char *fmt, ...) + EINA_PRINTF(3, 4); +static size_t _elm_user_dir_snprintf(char *dst, + size_t size, + const char *fmt, ...) + EINA_PRINTF(3, 4); + +#define ELM_CONFIG_VAL(edd, type, member, dtype) \ + EET_DATA_DESCRIPTOR_ADD_BASIC(edd, type, #member, member, dtype) +#define ELM_CONFIG_LIST(edd, type, member, eddtype) \ + EET_DATA_DESCRIPTOR_ADD_LIST(edd, type, #member, member, eddtype) + +#ifdef HAVE_ELEMENTARY_X +static Ecore_Event_Handler *_prop_change_handler = NULL; +static Ecore_X_Window _root_1st = 0; +#define ATOM_COUNT 22 +static Ecore_X_Atom _atom[ATOM_COUNT]; +static Ecore_X_Atom _atom_config = 0; +static const char *_atom_names[ATOM_COUNT] = +{ + "ENLIGHTENMENT_SCALE", + "ENLIGHTENMENT_FINGER_SIZE", + "ENLIGHTENMENT_THEME", + "ENLIGHTENMENT_PROFILE", + "ENLIGHTENMENT_FONT_OVERLAY", + "ENLIGHTENMENT_CACHE_FLUSH_INTERVAL", + "ENLIGHTENMENT_CACHE_FLUSH_ENABLE", + "ENLIGHTENMENT_FONT_CACHE", + "ENLIGHTENMENT_IMAGE_CACHE", + "ENLIGHTENMENT_EDJE_FILE_CACHE", + "ENLIGHTENMENT_EDJE_COLLECTION_CACHE", + "ENLIGHTENMENT_THUMBSCROLL_BOUNCE_ENABLE", + "ENLIGHTENMENT_THUMBSCROLL_BOUNCE_FRICTION", + "ENLIGHTENMENT_THUMBSCROLL_ENABLE", + "ENLIGHTENMENT_THUMBSCROLL_THRESHOLD", + "ENLIGHTENMENT_THUMBSCROLL_MOMENTUM_THRESHOLD", + "ENLIGHTENMENT_THUMBSCROLL_FRICTION", + "ENLIGHTENMENT_THUMBSCROLL_BORDER_FRICTION", + "ENLIGHTENMENT_THUMBSCROLL_PAGE_SCROLL_FRICTION", + "ENLIGHTENMENT_THUMBSCROLL_BRING_IN_SCROLL_FRICTION", + "ENLIGHTENMENT_THUMBSCROLL_ZOOM_FRICTION", + "ENLIGHTENMENT_CONFIG" +}; +#define ATOM_E_SCALE 0 +#define ATOM_E_FINGER_SIZE 1 +#define ATOM_E_THEME 2 +#define ATOM_E_PROFILE 3 +#define ATOM_E_FONT_OVERLAY 4 +#define ATOM_E_CACHE_FLUSH_INTERVAL 5 +#define ATOM_E_CACHE_FLUSH_ENABLE 6 +#define ATOM_E_FONT_CACHE 7 +#define ATOM_E_IMAGE_CACHE 8 +#define ATOM_E_EDJE_FILE_CACHE 9 +#define ATOM_E_EDJE_COLLECTION_CACHE 10 +#define ATOM_E_THUMBSCROLL_BOUNCE_ENABLE 11 +#define ATOM_E_THUMBSCROLL_BOUNCE_FRICTION 12 +#define ATOM_E_THUMBSCROLL_ENABLE 13 +#define ATOM_E_THUMBSCROLL_THRESHOLD 14 +#define ATOM_E_THUMBSCROLL_MOMENTUM_THRESHOLD 15 +#define ATOM_E_THUMBSCROLL_FRICTION 16 +#define ATOM_E_THUMBSCROLL_BORDER_FRICTION 17 +#define ATOM_E_THUMBSCROLL_PAGE_SCROLL_FRICTION 18 +#define ATOM_E_THUMBSCROLL_BRING_IN_SCROLL_FRICTION 19 +#define ATOM_E_THUMBSCROLL_ZOOM_FRICTION 20 +#define ATOM_E_CONFIG 21 + +static Eina_Bool _prop_config_get(void); +static Eina_Bool _prop_change(void *data __UNUSED__, + int ev_type __UNUSED__, + void *ev); + +static Eina_Bool +_prop_config_get(void) +{ + int size = 0; + Ecore_X_Atom atom; + char buf[512]; + unsigned char *data = NULL; + Elm_Config *config_data; + + snprintf(buf, sizeof(buf), "ENLIGHTENMENT_CONFIG_%s", _elm_profile); + atom = ecore_x_atom_get(buf); + _atom_config = atom; + if (!ecore_x_window_prop_property_get(_root_1st, + atom, _atom[ATOM_E_CONFIG], + 8, &data, &size)) + { + if (!ecore_x_window_prop_property_get(_root_1st, + _atom[ATOM_E_CONFIG], + _atom[ATOM_E_CONFIG], + 8, &data, &size)) + return EINA_FALSE; + else + _atom_config = _atom[ATOM_E_CONFIG]; + } + else + _atom_config = atom; + if (size < 1) + { + free(data); + return EINA_FALSE; + } + config_data = eet_data_descriptor_decode(_config_edd, data, size); + free(data); + if (!config_data) return EINA_FALSE; + + /* What do we do on version mismatch when someone changes the + * config in the rootwindow? */ + /* Most obvious case, new version and we are still linked to + * whatever was there before, we just ignore until user restarts us */ + if (config_data->config_version > ELM_CONFIG_VERSION) + return EINA_TRUE; + /* What in the case the version is older? Do we even support those + * cases or we only check for equality above? */ + + _config_free(); + _elm_config = config_data; + _config_apply(); + _elm_config_font_overlay_apply(); + _elm_rescale(); + _elm_recache(); + return EINA_TRUE; +} + +static Eina_Bool +_prop_change(void *data __UNUSED__, + int ev_type __UNUSED__, + void *ev) +{ + Ecore_X_Event_Window_Property *event = ev; + + if (event->win == _root_1st) + { + if (event->atom == _atom[ATOM_E_SCALE]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + double pscale; + + pscale = _elm_config->scale; + if (val > 0) _elm_config->scale = (double)val / 1000.0; + if (pscale != _elm_config->scale) + { + _elm_rescale(); + _elm_recache(); + } + } + } + else if (event->atom == _atom[ATOM_E_FINGER_SIZE]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + int pfinger_size; + + pfinger_size = _elm_config->finger_size; + _elm_config->finger_size = val; + if (pfinger_size != _elm_config->finger_size) + { + _elm_rescale(); + _elm_recache(); + } + } + } + else if (event->atom == _atom[ATOM_E_THEME]) + { + char *val = NULL; + + val = ecore_x_window_prop_string_get(event->win, + event->atom); + eina_stringshare_replace(&_elm_config->theme, val); + if (val) + { + _elm_theme_parse(NULL, val); + free(val); + _elm_rescale(); + _elm_recache(); + } + } + else if (event->atom == _atom[ATOM_E_PROFILE]) + { + char *val = NULL; + + val = ecore_x_window_prop_string_get(event->win, + event->atom); + if (val) + { + int changed = 0; + + if (_elm_profile) + { + if (strcmp(_elm_profile, val)) changed = 1; + free(_elm_profile); + } + _elm_profile = val; + if (changed) + { + if (!_prop_config_get()) + { + _config_free(); + _config_load(); + _config_apply(); + _elm_config_font_overlay_apply(); + _elm_rescale(); + } + } + } + } + else if (event->atom == _atom[ATOM_E_FONT_OVERLAY]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + _config_free(); + _config_load(); + _config_apply(); + _elm_config_font_overlay_apply(); + _elm_rescale(); + } + } + else if (event->atom == _atom[ATOM_E_CACHE_FLUSH_INTERVAL]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + int cache_flush_interval; + + cache_flush_interval = _elm_config->cache_flush_poll_interval; + _elm_config->cache_flush_poll_interval = val; + if (cache_flush_interval != + _elm_config->cache_flush_poll_interval) + _elm_recache(); + } + } + else if (event->atom == _atom[ATOM_E_CACHE_FLUSH_ENABLE]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + _elm_config->cache_flush_enable = !!val; + _elm_recache(); + } + } + else if (event->atom == _atom[ATOM_E_FONT_CACHE]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + int font_cache; + + font_cache = _elm_config->font_cache; + _elm_config->font_cache = val; + if (font_cache != _elm_config->font_cache) + _elm_recache(); + } + } + else if (event->atom == _atom[ATOM_E_IMAGE_CACHE]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + int image_cache; + + image_cache = _elm_config->image_cache; + _elm_config->image_cache = val; + if (image_cache != _elm_config->image_cache) + _elm_recache(); + } + } + else if (event->atom == _atom[ATOM_E_EDJE_FILE_CACHE]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + int edje_file_cache; + + edje_file_cache = _elm_config->edje_cache; + _elm_config->edje_cache = val; + if (edje_file_cache != _elm_config->edje_cache) + _elm_recache(); + } + } + else if (event->atom == _atom[ATOM_E_EDJE_COLLECTION_CACHE]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + int edje_collection_cache; + + edje_collection_cache = _elm_config->edje_collection_cache; + _elm_config->edje_collection_cache = val; + if (edje_collection_cache != + _elm_config->edje_collection_cache) + _elm_recache(); + } + } + else if (event->atom == _atom[ATOM_E_THUMBSCROLL_BOUNCE_ENABLE]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + _elm_config->thumbscroll_bounce_enable = !!val; + } + } + else if (event->atom == _atom[ATOM_E_THUMBSCROLL_BOUNCE_FRICTION]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + if (val > 0) + _elm_config->thumbscroll_bounce_friction = + (double)val / 1000.0; + } + } + else if (event->atom == _atom[ATOM_E_THUMBSCROLL_ENABLE]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + _elm_config->thumbscroll_enable = !!val; + } + } + else if (event->atom == _atom[ATOM_E_THUMBSCROLL_THRESHOLD]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + if (val > 0) _elm_config->thumbscroll_threshold = val; + } + } + else if (event->atom == _atom[ATOM_E_THUMBSCROLL_MOMENTUM_THRESHOLD]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + if (val > 0) + _elm_config->thumbscroll_momentum_threshold = + (double)val / 1000.0; + } + } + else if (event->atom == _atom[ATOM_E_THUMBSCROLL_FRICTION]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + if (val > 0) + _elm_config->thumbscroll_friction = (double)val / 1000.0; + } + } + else if (event->atom == _atom[ATOM_E_THUMBSCROLL_BORDER_FRICTION]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + if (val > 0) + _elm_config->thumbscroll_border_friction = + (double)val / 1000.0; + } + } + else if (event->atom == _atom[ATOM_E_THUMBSCROLL_PAGE_SCROLL_FRICTION]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + if (val > 0) + _elm_config->page_scroll_friction = + (double)val / 1000.0; + } + } + else if (event->atom == + _atom[ATOM_E_THUMBSCROLL_BRING_IN_SCROLL_FRICTION]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + if (val > 0) + _elm_config->bring_in_scroll_friction = + (double)val / 1000.0; + } + } + else if (event->atom == + _atom[ATOM_E_THUMBSCROLL_ZOOM_FRICTION]) + { + unsigned int val = 1000; + + if (ecore_x_window_prop_card32_get(event->win, + event->atom, + &val, 1) > 0) + { + if (val > 0) + _elm_config->zoom_friction = (double)val / 1000.0; + } + } + else if (((_atom_config > 0) && (event->atom == _atom_config)) || + (event->atom == _atom[ATOM_E_CONFIG])) + { + _prop_config_get(); + } + } + return ECORE_CALLBACK_PASS_ON; +} + +#endif + +static void +_desc_init(void) +{ + Eet_Data_Descriptor_Class eddc; + + EET_EINA_FILE_DATA_DESCRIPTOR_CLASS_SET(&eddc, Elm_Config); + eddc.func.str_direct_alloc = NULL; + eddc.func.str_direct_free = NULL; + + _config_edd = eet_data_descriptor_file_new(&eddc); + if (!_config_edd) + { + printf("EEEK! eet_data_descriptor_file_new() failed\n"); + return; + } + + memset(&eddc, 0, sizeof(eddc)); /* just in case... */ + EET_EINA_STREAM_DATA_DESCRIPTOR_CLASS_SET(&eddc, Elm_Font_Overlay); + eddc.func.str_direct_alloc = NULL; + eddc.func.str_direct_free = NULL; + + _config_font_overlay_edd = eet_data_descriptor_stream_new(&eddc); + if (!_config_font_overlay_edd) + { + printf("EEEK! eet_data_descriptor_stream_new() failed\n"); + eet_data_descriptor_free(_config_edd); + return; + } +#define T_INT EET_T_INT +#define T_DOUBLE EET_T_DOUBLE +#define T_STRING EET_T_STRING +#define T_UCHAR EET_T_UCHAR + +#define T Elm_Font_Overlay +#define D _config_font_overlay_edd + ELM_CONFIG_VAL(D, T, text_class, EET_T_STRING); + ELM_CONFIG_VAL(D, T, font, EET_T_STRING); + ELM_CONFIG_VAL(D, T, size, EET_T_INT); +#undef T +#undef D + +#define T Elm_Config +#define D _config_edd + ELM_CONFIG_VAL(D, T, config_version, T_INT); + ELM_CONFIG_VAL(D, T, engine, T_STRING); + ELM_CONFIG_VAL(D, T, thumbscroll_enable, T_UCHAR); + ELM_CONFIG_VAL(D, T, thumbscroll_threshold, T_INT); + ELM_CONFIG_VAL(D, T, thumbscroll_momentum_threshold, T_DOUBLE); + ELM_CONFIG_VAL(D, T, thumbscroll_friction, T_DOUBLE); + ELM_CONFIG_VAL(D, T, thumbscroll_bounce_friction, T_DOUBLE); + ELM_CONFIG_VAL(D, T, thumbscroll_border_friction, T_DOUBLE); + ELM_CONFIG_VAL(D, T, page_scroll_friction, T_DOUBLE); + ELM_CONFIG_VAL(D, T, bring_in_scroll_friction, T_DOUBLE); + ELM_CONFIG_VAL(D, T, zoom_friction, T_DOUBLE); + ELM_CONFIG_VAL(D, T, thumbscroll_bounce_enable, T_UCHAR); + ELM_CONFIG_VAL(D, T, scale, T_DOUBLE); + ELM_CONFIG_VAL(D, T, bgpixmap, T_INT); + ELM_CONFIG_VAL(D, T, compositing, T_INT); + /* EET_DATA_DESCRIPTOR_ADD_LIST(D, T, "font_dirs", font_dirs, sub_edd); */ + ELM_CONFIG_LIST(D, T, font_overlays, _config_font_overlay_edd); + ELM_CONFIG_VAL(D, T, font_hinting, T_INT); + ELM_CONFIG_VAL(D, T, cache_flush_poll_interval, T_INT); + ELM_CONFIG_VAL(D, T, cache_flush_enable, T_UCHAR); + ELM_CONFIG_VAL(D, T, image_cache, T_INT); + ELM_CONFIG_VAL(D, T, font_cache, T_INT); + ELM_CONFIG_VAL(D, T, edje_cache, T_INT); + ELM_CONFIG_VAL(D, T, edje_collection_cache, T_INT); + ELM_CONFIG_VAL(D, T, finger_size, T_INT); + ELM_CONFIG_VAL(D, T, fps, T_DOUBLE); + ELM_CONFIG_VAL(D, T, theme, T_STRING); + ELM_CONFIG_VAL(D, T, modules, T_STRING); + ELM_CONFIG_VAL(D, T, tooltip_delay, T_DOUBLE); + ELM_CONFIG_VAL(D, T, cursor_engine_only, T_UCHAR); + ELM_CONFIG_VAL(D, T, focus_highlight_enable, T_UCHAR); + ELM_CONFIG_VAL(D, T, focus_highlight_animate, T_UCHAR); + ELM_CONFIG_VAL(D, T, toolbar_shrink_mode, T_INT); + ELM_CONFIG_VAL(D, T, fileselector_expand_enable, T_UCHAR); + ELM_CONFIG_VAL(D, T, inwin_dialogs_enable, T_UCHAR); + ELM_CONFIG_VAL(D, T, icon_size, T_INT); + ELM_CONFIG_VAL(D, T, longpress_timeout, T_DOUBLE); +#undef T +#undef D +#undef T_INT +#undef T_DOUBLE +#undef T_STRING +#undef T_UCHAR +} + +static void +_desc_shutdown(void) +{ + if (_config_edd) + { + eet_data_descriptor_free(_config_edd); + _config_edd = NULL; + } + + if (_config_font_overlay_edd) + { + eet_data_descriptor_free(_config_font_overlay_edd); + _config_font_overlay_edd = NULL; + } +} + +static int +_sort_files_cb(const void *f1, + const void *f2) +{ + return strcmp(f1, f2); +} + +const char * +_elm_config_current_profile_get(void) +{ + return _elm_profile; +} + +static size_t +_elm_data_dir_snprintf(char *dst, + size_t size, + const char *fmt, + ...) +{ + size_t data_dir_len, off; + va_list ap; + + data_dir_len = eina_strlcpy(dst, _elm_data_dir, size); + + off = data_dir_len + 1; + if (off >= size) + goto end; + + va_start(ap, fmt); + dst[data_dir_len] = '/'; + + off = off + vsnprintf(dst + off, size - off, fmt, ap); + va_end(ap); + +end: + return off; +} + +static size_t +_elm_user_dir_snprintf(char *dst, + size_t size, + const char *fmt, + ...) +{ + const char *home; + size_t user_dir_len, off; + va_list ap; + + home = getenv("HOME"); + if (!home) + home = "/"; + + user_dir_len = eina_str_join_len(dst, size, '/', home, strlen(home), + ".elementary", sizeof(".elementary") - 1); + + off = user_dir_len + 1; + if (off >= size) + goto end; + + va_start(ap, fmt); + dst[user_dir_len] = '/'; + + off = off + vsnprintf(dst + off, size - off, fmt, ap); + va_end(ap); + +end: + return off; +} + +const char * +_elm_config_profile_dir_get(const char *prof, + Eina_Bool is_user) +{ + char buf[PATH_MAX]; + + if (!is_user) + goto not_user; + + _elm_user_dir_snprintf(buf, sizeof(buf), "config/%s", prof); + + if (ecore_file_is_dir(buf)) + return strdup(buf); + + return NULL; + +not_user: + snprintf(buf, sizeof(buf), "%s/config/%s", _elm_data_dir, prof); + + if (ecore_file_is_dir(buf)) + return strdup(buf); + + return NULL; +} + +Eina_List * +_elm_config_font_overlays_list(void) +{ + return _elm_config->font_overlays; +} + +void +_elm_config_font_overlay_set(const char *text_class, + const char *font, + Evas_Font_Size size) +{ + Elm_Font_Overlay *efd; + Eina_List *l; + + EINA_LIST_FOREACH(_elm_config->font_overlays, l, efd) + { + if (strcmp(efd->text_class, text_class)) + continue; + + if (efd->font) eina_stringshare_del(efd->font); + efd->font = eina_stringshare_add(font); + efd->size = size; + _elm_config->font_overlays = + eina_list_promote_list(_elm_config->font_overlays, l); + return; + } + + /* the text class doesn't exist */ + efd = calloc(1, sizeof(Elm_Font_Overlay)); + efd->text_class = eina_stringshare_add(text_class); + efd->font = eina_stringshare_add(font); + efd->size = size; + + _elm_config->font_overlays = eina_list_prepend(_elm_config->font_overlays, + efd); +} + +void +_elm_config_font_overlay_remove(const char *text_class) +{ + Elm_Font_Overlay *efd; + Eina_List *l; + + EINA_LIST_FOREACH(_elm_config->font_overlays, l, efd) + { + if (strcmp(efd->text_class, text_class)) + continue; + + _elm_config->font_overlays = + eina_list_remove_list(_elm_config->font_overlays, l); + if (efd->text_class) eina_stringshare_del(efd->text_class); + if (efd->font) eina_stringshare_del(efd->font); + free(efd); + + return; + } +} + +void +_elm_config_font_overlay_apply(void) +{ + Elm_Font_Overlay *efd; + Eina_List *l; + int i; + + for (i = 0; _elm_text_classes[i].desc; i++) + edje_text_class_del(_elm_text_classes[i].name); + + EINA_LIST_FOREACH(_elm_config->font_overlays, l, efd) + edje_text_class_set(efd->text_class, efd->font, efd->size); +} + +Eina_List * +_elm_config_text_classes_get(void) +{ + Eina_List *ret = NULL; + int i; + + for (i = 0; _elm_text_classes[i].desc; i++) + { + Elm_Text_Class *tc; + tc = malloc(sizeof(*tc)); + + *tc = _elm_text_classes[i]; + + ret = eina_list_append(ret, tc); + } + + return ret; +} + +void +_elm_config_text_classes_free(Eina_List *l) +{ + Elm_Text_Class *tc; + + EINA_LIST_FREE(l, tc) + free(tc); +} + +Eina_List * +_elm_config_profiles_list(void) +{ + const Eina_File_Direct_Info *info; + Eina_List *flist = NULL; + Eina_Iterator *file_it; + char buf[PATH_MAX]; + const char *dir; + size_t len; + + len = _elm_user_dir_snprintf(buf, sizeof(buf), "config"); + + file_it = eina_file_direct_ls(buf); + if (!file_it) + goto sys; + + buf[len] = '/'; + len++; + + len = sizeof(buf) - len; + + EINA_ITERATOR_FOREACH(file_it, info) + { + if (info->name_length >= len) + continue; + + if (info->type == EINA_FILE_DIR) + { + flist = + eina_list_sorted_insert(flist, _sort_files_cb, + eina_stringshare_add(info->path + + info->name_start)); + } + } + + eina_iterator_free(file_it); + +sys: + len = eina_str_join_len(buf, sizeof(buf), '/', _elm_data_dir, + strlen(_elm_data_dir), "config", + sizeof("config") - 1); + + file_it = eina_file_direct_ls(buf); + if (!file_it) + goto list_free; + + buf[len] = '/'; + len++; + + len = sizeof(buf) - len; + EINA_ITERATOR_FOREACH(file_it, info) + { + if (info->name_length >= len) + continue; + + switch (info->type) + { + case EINA_FILE_DIR: + { + const Eina_List *l; + const char *tmp; + + EINA_LIST_FOREACH(flist, l, tmp) + if (!strcmp(info->path + info->name_start, tmp)) + break; + + if (!l) + flist = + eina_list_sorted_insert(flist, _sort_files_cb, + eina_stringshare_add(info->path + + info->name_start)); + } + break; + + default: + continue; + } + } + return flist; + + eina_iterator_free(file_it); + +list_free: + EINA_LIST_FREE(flist, dir) + eina_stringshare_del(dir); + + return NULL; +} + +static void +_profile_fetch_from_conf(void) +{ + char buf[PATH_MAX], *p, *s; + Eet_File *ef = NULL; + int len = 0; + + _elm_profile = strdup("default"); + + // if env var - use profile without question + s = getenv("ELM_PROFILE"); + if (s) + { + free(_elm_profile); + _elm_profile = strdup(s); + return; + } + + // user profile + _elm_user_dir_snprintf(buf, sizeof(buf), "config/profile.cfg"); + ef = eet_open(buf, EET_FILE_MODE_READ); + if (ef) + { + p = eet_read(ef, "config", &len); + if (p) + { + free(_elm_profile); + _elm_profile = malloc(len + 1); + memcpy(_elm_profile, p, len); + _elm_profile[len] = 0; + free(p); + } + eet_close(ef); + if (!p) ef = NULL; + } + if (ef) return; + + // system profile + _elm_data_dir_snprintf(buf, sizeof(buf), "config/profile.cfg"); + ef = eet_open(buf, EET_FILE_MODE_READ); + if (ef) + { + p = eet_read(ef, "config", &len); + if (p) + { + free(_elm_profile); + _elm_profile = malloc(len + 1); + memcpy(_elm_profile, p, len); + _elm_profile[len] = 0; + free(p); + } + eet_close(ef); + } +} + +static void +_config_free(void) +{ + Elm_Font_Overlay *fo; + const char *fontdir; + + if (!_elm_config) return; + EINA_LIST_FREE(_elm_config->font_dirs, fontdir) + { + eina_stringshare_del(fontdir); + } + if (_elm_config->engine) eina_stringshare_del(_elm_config->engine); + EINA_LIST_FREE(_elm_config->font_overlays, fo) + { + if (fo->text_class) eina_stringshare_del(fo->text_class); + if (fo->font) eina_stringshare_del(fo->font); + free(fo); + } + if (_elm_config->theme) eina_stringshare_del(_elm_config->theme); + if (_elm_config->modules) eina_stringshare_del(_elm_config->modules); + free(_elm_config); + _elm_config = NULL; +} + +static void +_config_apply(void) +{ + _elm_theme_parse(NULL, _elm_config->theme); + ecore_animator_frametime_set(1.0 / _elm_config->fps); +} + +static void +_config_sub_apply(void) +{ + edje_frametime_set(1.0 / _elm_config->fps); + edje_scale_set(_elm_config->scale); + if (_elm_config->modules) _elm_module_parse(_elm_config->modules); +} + +static Eina_Bool +_elm_cache_flush_cb(void *data __UNUSED__) +{ + elm_all_flush(); + return ECORE_CALLBACK_RENEW; +} + +/* kind of abusing this call right now -- shared between all of those + * properties -- but they are not meant to be called that periodically + * anyway */ +void +_elm_recache(void) +{ + Eina_List *l; + Evas_Object *win; + + elm_all_flush(); + + EINA_LIST_FOREACH(_elm_win_list, l, win) + { + Evas *e = evas_object_evas_get(win); + evas_image_cache_set(e, _elm_config->image_cache); + evas_font_cache_set(e, _elm_config->font_cache); + } + edje_file_cache_set(_elm_config->edje_cache); + edje_collection_cache_set(_elm_config->edje_collection_cache); + + if (_elm_cache_flush_poller) + { + ecore_poller_del(_elm_cache_flush_poller); + _elm_cache_flush_poller = NULL; + } + if (_elm_config->cache_flush_enable) + { + if (_elm_config->cache_flush_poll_interval > 0) + { + _elm_cache_flush_poller = + ecore_poller_add(ECORE_POLLER_CORE, + _elm_config->cache_flush_poll_interval, + _elm_cache_flush_cb, NULL); + } + } +} + +static Elm_Config * +_config_user_load(void) +{ + Elm_Config *cfg = NULL; + Eet_File *ef; + char buf[PATH_MAX]; + + _elm_user_dir_snprintf(buf, sizeof(buf), "config/%s/base.cfg", + _elm_profile); + + ef = eet_open(buf, EET_FILE_MODE_READ); + if (ef) + { + cfg = eet_data_read(ef, _config_edd, "config"); + eet_close(ef); + } + return cfg; +} + +static Elm_Config * +_config_system_load(void) +{ + Elm_Config *cfg = NULL; + Eet_File *ef; + char buf[PATH_MAX]; + + _elm_data_dir_snprintf(buf, sizeof(buf), "config/%s/base.cfg", + _elm_profile); + + ef = eet_open(buf, EET_FILE_MODE_READ); + if (ef) + { + cfg = eet_data_read(ef, _config_edd, "config"); + eet_close(ef); + } + return cfg; +} + +static void +_config_load(void) +{ + _elm_config = _config_user_load(); + if (_elm_config) + { + if (_elm_config->config_version < ELM_CONFIG_VERSION) + _config_update(); + return; + } + + /* no user config, fallback for system. No need to check version for + * this one, if it's not the right one, someone screwed up at the time + * of installing it */ + _elm_config = _config_system_load(); + if (_elm_config) return; + /* FIXME: config load could have failed because of a non-existent + * profile. Fallback to default before moving on */ + + // config load fail - defaults + /* XXX: do these make sense? Only if it's valid to install the lib + * without the config, but do we want that? */ + _elm_config = ELM_NEW(Elm_Config); + _elm_config->config_version = ELM_CONFIG_VERSION; + _elm_config->engine = eina_stringshare_add("software_x11"); + _elm_config->thumbscroll_enable = EINA_TRUE; + _elm_config->thumbscroll_threshold = 24; + _elm_config->thumbscroll_momentum_threshold = 100.0; + _elm_config->thumbscroll_friction = 1.0; + _elm_config->thumbscroll_bounce_friction = 0.5; + _elm_config->thumbscroll_bounce_enable = EINA_TRUE; + _elm_config->page_scroll_friction = 0.5; + _elm_config->bring_in_scroll_friction = 0.5; + _elm_config->zoom_friction = 0.5; + _elm_config->thumbscroll_border_friction = 0.5; + _elm_config->scale = 1.0; + _elm_config->bgpixmap = 0; + _elm_config->compositing = 1; + _elm_config->font_hinting = 2; + _elm_config->cache_flush_poll_interval = 512; + _elm_config->cache_flush_enable = EINA_TRUE; + _elm_config->font_dirs = NULL; + _elm_config->image_cache = 4096; + _elm_config->font_cache = 512; + _elm_config->edje_cache = 32; + _elm_config->edje_collection_cache = 64; + _elm_config->finger_size = 40; + _elm_config->fps = 60.0; + _elm_config->theme = eina_stringshare_add("default"); + _elm_config->modules = NULL; + _elm_config->tooltip_delay = 1.0; + _elm_config->cursor_engine_only = EINA_TRUE; + _elm_config->focus_highlight_enable = EINA_FALSE; + _elm_config->focus_highlight_animate = EINA_TRUE; + _elm_config->toolbar_shrink_mode = 2; + _elm_config->fileselector_expand_enable = EINA_FALSE; + _elm_config->inwin_dialogs_enable = EINA_FALSE; + _elm_config->icon_size = 32; + _elm_config->longpress_timeout = 1.0; +} + +static const char * +_elm_config_eet_close_error_get(Eet_File *ef, + char *file) +{ + Eet_Error err; + const char *erstr = NULL; + + err = eet_close(ef); + switch (err) + { + case EET_ERROR_WRITE_ERROR: + erstr = "An error occurred while saving Elementary's " + "settings to disk. The error could not be " + "deterimined. The file where the error occurred was: " + "%s. This file has been deleted to avoid corrupt data."; + break; + + case EET_ERROR_WRITE_ERROR_FILE_TOO_BIG: + erstr = "Elementary's settings files are too big " + "for the file system they are being saved to. " + "This error is very strange as the files should " + "be extremely small. Please check the settings " + "for your home directory. " + "The file where the error occurred was: %s ." + "This file has been deleted to avoid corrupt data."; + break; + + case EET_ERROR_WRITE_ERROR_IO_ERROR: + erstr = "An output error occurred when writing the settings " + "files for Elementary. Your disk is having troubles " + "and possibly needs replacement. " + "The file where the error occurred was: %s ." + "This file has been deleted to avoid corrupt data."; + break; + + case EET_ERROR_WRITE_ERROR_OUT_OF_SPACE: + erstr = "Elementary cannot write its settings file " + "because it ran out of space to write the file. " + "You have either run out of disk space or have " + "gone over your quota limit. " + "The file where the error occurred was: %s ." + "This file has been deleted to avoid corrupt data."; + break; + + case EET_ERROR_WRITE_ERROR_FILE_CLOSED: + erstr = "Elementary unexpectedly had the settings file " + "it was writing closed on it. This is very unusual. " + "The file where the error occurred was: %s " + "This file has been deleted to avoid corrupt data."; + break; + + default: + break; + } + if (erstr) + { + /* delete any partially-written file */ + ecore_file_unlink(file); + return strdup(erstr); + } + + return NULL; +} + +static Eina_Bool +_elm_config_profile_save(void) +{ + char buf[4096], buf2[4096]; + int ok = 0, ret; + const char *err; + Eet_File *ef; + size_t len; + + len = _elm_user_dir_snprintf(buf, sizeof(buf), "config/profile.cfg"); + if (len + 1 >= sizeof(buf)) + return EINA_FALSE; + + len = _elm_user_dir_snprintf(buf2, sizeof(buf2), "config/profile.cfg.tmp"); + if (len + 1 >= sizeof(buf2)) + return EINA_FALSE; + + ef = eet_open(buf2, EET_FILE_MODE_WRITE); + if (!ef) + return EINA_FALSE; + + ok = eet_write(ef, "config", _elm_profile, strlen(_elm_profile), 0); + if (!ok) + goto err; + + err = _elm_config_eet_close_error_get(ef, buf2); + if (err) + { + ERR("%s", err); + free((void *)err); + goto err; + } + + ret = ecore_file_mv(buf2, buf); + if (!ret) + { + ERR("Error saving Elementary's configuration file"); + goto err; + } + + ecore_file_unlink(buf2); + return EINA_TRUE; + +err: + ecore_file_unlink(buf2); + return EINA_FALSE; +} + +Eina_Bool +_elm_config_save(void) +{ + char buf[4096], buf2[4096]; + int ok = 0, ret; + const char *err; + Eet_File *ef; + size_t len; + + len = _elm_user_dir_snprintf(buf, sizeof(buf), "config/%s", _elm_profile); + if (len + 1 >= sizeof(buf)) + return EINA_FALSE; + + ok = ecore_file_mkpath(buf); + if (!ok) + { + ERR("Problem acessing Elementary's user configuration directory: %s", + buf); + return EINA_FALSE; + } + + if (!_elm_config_profile_save()) + return EINA_FALSE; + + buf[len] = '/'; + len++; + + if (len + sizeof("base.cfg") >= sizeof(buf) - len) + return EINA_FALSE; + + memcpy(buf + len, "base.cfg", sizeof("base.cfg")); + len += sizeof("base.cfg") - 1; + + if (len + sizeof(".tmp") >= sizeof(buf)) + return EINA_FALSE; + + memcpy(buf2, buf, len); + memcpy(buf2 + len, ".tmp", sizeof(".tmp")); + + ef = eet_open(buf2, EET_FILE_MODE_WRITE); + if (!ef) + return EINA_FALSE; + + ok = eet_data_write(ef, _config_edd, "config", _elm_config, 1); + if (!ok) + goto err; + + err = _elm_config_eet_close_error_get(ef, buf2); + if (err) + { + ERR("%s", err); + free((void *)err); + goto err; + } + + ret = ecore_file_mv(buf2, buf); + if (!ret) + { + ERR("Error saving Elementary's configuration file"); + goto err; + } + + ecore_file_unlink(buf2); + return EINA_TRUE; + +err: + ecore_file_unlink(buf2); + return EINA_FALSE; +} + +static void +_config_update(void) +{ + Elm_Config *tcfg; + + tcfg = _config_system_load(); + if (!tcfg) + { + /* weird profile or something? We should probably fill + * with hardcoded defaults, or get from default previx */ + return; + } +#define IFCFG(v) if ((_elm_config->config_version & 0xffff) < (v)) { +#define IFCFGELSE } else { +#define IFCFGEND } +#define COPYVAL(x) do {_elm_config->x = tcfg->x; } while(0) +#define COPYPTR(x) do {_elm_config->x = tcfg->x; tcfg->x = NULL; } while(0) +#define COPYSTR(x) COPYPTR(x) + + /* we also need to update for property changes in the root window + * if needed, but that will be dependent on new properties added + * with each version */ + + IFCFG(0x0003); + COPYVAL(longpress_timeout); + IFCFGEND; + +#undef COPYSTR +#undef COPYPTR +#undef COPYVAL +#undef IFCFGEND +#undef IFCFGELSE +#undef IFCFG + + /* after updating user config, we must save */ +} + +static void +_env_get(void) +{ + char *s; + double friction; + + s = getenv("ELM_ENGINE"); + if (s) + { + if ((!strcasecmp(s, "x11")) || + (!strcasecmp(s, "x")) || + (!strcasecmp(s, "software-x11")) || + (!strcasecmp(s, "software_x11"))) + eina_stringshare_replace(&_elm_config->engine, ELM_SOFTWARE_X11); + else if ((!strcasecmp(s, "opengl")) || + (!strcasecmp(s, "gl")) || + (!strcasecmp(s, "opengl-x11")) || + (!strcasecmp(s, "opengl_x11"))) + eina_stringshare_replace(&_elm_config->engine, ELM_OPENGL_X11); + else if ((!strcasecmp(s, "x11-8")) || + (!strcasecmp(s, "x18")) || + (!strcasecmp(s, "software-8-x11")) || + (!strcasecmp(s, "software_8_x11"))) + eina_stringshare_replace(&_elm_config->engine, ELM_SOFTWARE_8_X11); + else if ((!strcasecmp(s, "x11-16")) || + (!strcasecmp(s, "x16")) || + (!strcasecmp(s, "software-16-x11")) || + (!strcasecmp(s, "software_16_x11"))) + eina_stringshare_replace(&_elm_config->engine, ELM_SOFTWARE_16_X11); + else if ((!strcasecmp(s, "xrender")) || + (!strcasecmp(s, "xr")) || + (!strcasecmp(s, "xrender-x11")) || + (!strcasecmp(s, "xrender_x11"))) + eina_stringshare_replace(&_elm_config->engine, ELM_XRENDER_X11); + else if ((!strcasecmp(s, "fb")) || + (!strcasecmp(s, "software-fb")) || + (!strcasecmp(s, "software_fb"))) + eina_stringshare_replace(&_elm_config->engine, ELM_SOFTWARE_FB); + else if ((!strcasecmp(s, "directfb")) || + (!strcasecmp(s, "dfb"))) + eina_stringshare_replace(&_elm_config->engine, ELM_SOFTWARE_DIRECTFB); + else if ((!strcasecmp(s, "sdl")) || + (!strcasecmp(s, "software-sdl")) || + (!strcasecmp(s, "software_sdl"))) + eina_stringshare_replace(&_elm_config->engine, ELM_SOFTWARE_SDL); + else if ((!strcasecmp(s, "sdl-16")) || + (!strcasecmp(s, "software-16-sdl")) || + (!strcasecmp(s, "software_16_sdl"))) + eina_stringshare_replace(&_elm_config->engine, ELM_SOFTWARE_16_SDL); + else if ((!strcasecmp(s, "opengl-sdl")) || + (!strcasecmp(s, "opengl_sdl")) || + (!strcasecmp(s, "gl-sdl")) || + (!strcasecmp(s, "gl_sdl"))) + eina_stringshare_replace(&_elm_config->engine, ELM_OPENGL_SDL); + else if ((!strcasecmp(s, "gdi")) || + (!strcasecmp(s, "software-gdi")) || + (!strcasecmp(s, "software_gdi"))) + eina_stringshare_replace(&_elm_config->engine, ELM_SOFTWARE_WIN32); + else if ((!strcasecmp(s, "wince-gdi")) || + (!strcasecmp(s, "software-16-wince-gdi")) || + (!strcasecmp(s, "software_16_wince_gdi"))) + eina_stringshare_replace(&_elm_config->engine, ELM_SOFTWARE_16_WINCE); + } + + s = getenv("ELM_THUMBSCROLL_ENABLE"); + if (s) _elm_config->thumbscroll_enable = !!atoi(s); + s = getenv("ELM_THUMBSCROLL_THRESHOLD"); + if (s) _elm_config->thumbscroll_threshold = atoi(s); + // FIXME: floatformat locale issues here 1.0 vs 1,0 - should just be 1.0 + s = getenv("ELM_THUMBSCROLL_MOMENTUM_THRESHOLD"); + if (s) _elm_config->thumbscroll_momentum_threshold = atof(s); + s = getenv("ELM_THUMBSCROLL_FRICTION"); + if (s) _elm_config->thumbscroll_friction = atof(s); + s = getenv("ELM_THUMBSCROLL_BOUNCE_ENABLE"); + if (s) _elm_config->thumbscroll_bounce_enable = !!atoi(s); + s = getenv("ELM_THUMBSCROLL_BOUNCE_FRICTION"); + if (s) _elm_config->thumbscroll_bounce_friction = atof(s); + s = getenv("ELM_PAGE_SCROLL_FRICTION"); + if (s) _elm_config->page_scroll_friction = atof(s); + s = getenv("ELM_BRING_IN_SCROLL_FRICTION"); + if (s) _elm_config->bring_in_scroll_friction = atof(s); + s = getenv("ELM_ZOOM_FRICTION"); + if (s) _elm_config->zoom_friction = atof(s); + s = getenv("ELM_THUMBSCROLL_BORDER_FRICTION"); + if (s) + { + friction = atof(s); + if (friction < 0.0) + friction = 0.0; + + if (friction > 1.0) + friction = 1.0; + + _elm_config->thumbscroll_border_friction = friction; + } + s = getenv("ELM_THEME"); + if (s) eina_stringshare_replace(&_elm_config->theme, s); + + s = getenv("ELM_FONT_HINTING"); + if (s) + { + if (!strcasecmp(s, "none")) _elm_config->font_hinting = 0; + else if (!strcasecmp(s, "auto")) + _elm_config->font_hinting = 1; + else if (!strcasecmp(s, "bytecode")) + _elm_config->font_hinting = 2; + } + + s = getenv("ELM_FONT_PATH"); + if (s) + { + const char *p, *pp; + char *buf2; + + EINA_LIST_FREE(_elm_config->font_dirs, p) + { + eina_stringshare_del(p); + } + + buf2 = alloca(strlen(s) + 1); + p = s; + pp = p; + for (;; ) + { + if ((*p == ':') || (*p == 0)) + { + int len; + + len = p - pp; + strncpy(buf2, pp, len); + buf2[len] = 0; + _elm_config->font_dirs = + eina_list_append(_elm_config->font_dirs, + eina_stringshare_add(buf2)); + if (*p == 0) break; + p++; + pp = p; + } + else + { + if (*p == 0) break; + p++; + } + } + } + + s = getenv("ELM_IMAGE_CACHE"); + if (s) _elm_config->image_cache = atoi(s); + + s = getenv("ELM_FONT_CACHE"); + if (s) _elm_config->font_cache = atoi(s); + + s = getenv("ELM_SCALE"); + if (s) _elm_config->scale = atof(s); + + _elm_config->finger_size = + (double)_elm_config->finger_size * _elm_config->scale; + s = getenv("ELM_FINGER_SIZE"); + if (s) _elm_config->finger_size = atoi(s); + + s = getenv("ELM_FPS"); + if (s) _elm_config->fps = atof(s); + if (_elm_config->fps < 1.0) _elm_config->fps = 1.0; + + s = getenv("ELM_MODULES"); + if (s) eina_stringshare_replace(&_elm_config->modules, s); + + s = getenv("ELM_TOOLTIP_DELAY"); + if (s) + { + double delay = atof(s); + if (delay >= 0.0) + _elm_config->tooltip_delay = delay; + } + + s = getenv("ELM_CURSOR_ENGINE_ONLY"); + if (s) _elm_config->cursor_engine_only = !!atoi(s); + + s = getenv("ELM_FOCUS_HIGHLIGHT_ENABLE"); + if (s) _elm_config->focus_highlight_enable = !!atoi(s); + + s = getenv("ELM_FOCUS_HIGHLIGHT_ANIMATE"); + if (s) _elm_config->focus_highlight_animate = !!atoi(s); + + s = getenv("ELM_TOOLBAR_SHRINK_MODE"); + if (s) _elm_config->toolbar_shrink_mode = atoi(s); + + s = getenv("ELM_FILESELECTOR_EXPAND_ENABLE"); + if (s) _elm_config->fileselector_expand_enable = !!atoi(s); + + s = getenv("ELM_INWIN_DIALOGS_ENABLE"); + if (s) _elm_config->inwin_dialogs_enable = !!atoi(s); + + s = getenv("ELM_ICON_SIZE"); + if (s) _elm_config->icon_size = atoi(s); + + s = getenv("ELM_LONGPRESS_TIMEOUT"); + if (s) _elm_config->longpress_timeout = atof(s); + if (_elm_config->longpress_timeout < 0.0) + _elm_config->longpress_timeout = 0.0; +} + +void +_elm_config_init(void) +{ + _desc_init(); + _profile_fetch_from_conf(); + _config_load(); + _env_get(); + _config_apply(); + _elm_config_font_overlay_apply(); + _elm_recache(); +} + +void +_elm_config_sub_init(void) +{ +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_X11) || + ENGINE_COMPARE(ELM_SOFTWARE_16_X11) || + ENGINE_COMPARE(ELM_XRENDER_X11) || + ENGINE_COMPARE(ELM_OPENGL_X11)) +#undef ENGINE_COMPARE + { +#ifdef HAVE_ELEMENTARY_X + unsigned int val = 1000; + + if (!ecore_x_init(NULL)) + { + ERR("Cannot connect to X11 display. check $DISPLAY variable"); + exit(1); + } + _root_1st = ecore_x_window_root_first_get(); + + if (!ecore_x_screen_is_composited(0)) + _elm_config->compositing = 0; + + ecore_x_atoms_get(_atom_names, ATOM_COUNT, _atom); + ecore_x_event_mask_set(_root_1st, + ECORE_X_EVENT_MASK_WINDOW_PROPERTY); + _prop_change_handler = ecore_event_handler_add + (ECORE_X_EVENT_WINDOW_PROPERTY, _prop_change, NULL); + if (!getenv("ELM_SCALE")) + { + if (ecore_x_window_prop_card32_get(_root_1st, + _atom[ATOM_E_SCALE], + &val, 1) > 0) + { + if (val > 0) + { + _elm_config->scale = (double)val / 1000.0; + // FIXME: hack until e export finger size too + if (!getenv("ELM_FINGER_SIZE")) + { + _elm_config->finger_size = 40.0 * _elm_config->scale; + } + edje_scale_set(_elm_config->scale); + } + } + } + if (!getenv("ELM_FINGER_SIZE")) + { + if (ecore_x_window_prop_card32_get(_root_1st, + _atom[ATOM_E_FINGER_SIZE], + &val, 1) > 0) + { + if (val > 0) + { + _elm_config->finger_size = val; + } + } + } + if (!getenv("ELM_THEME")) + { + char *s; + + s = ecore_x_window_prop_string_get(_root_1st, + _atom[ATOM_E_THEME]); + if (s) + { + eina_stringshare_replace(&_elm_config->theme, s); + _elm_theme_parse(NULL, s); + free(s); + } + } + if (!getenv("ELM_PROFILE")) + { + char *s; + + s = ecore_x_window_prop_string_get(_root_1st, + _atom[ATOM_E_PROFILE]); + if (s) + { + int changed = 0; + + if (_elm_profile) + { + if (strcmp(_elm_profile, s)) changed = 1; + free(_elm_profile); + } + _elm_profile = s; + if (changed) _prop_config_get(); + } + } +#endif + } + _config_sub_apply(); +} + +void +_elm_config_reload(void) +{ + _config_free(); + _config_load(); + _config_apply(); + _elm_config_font_overlay_apply(); + _elm_rescale(); + _elm_recache(); +} + +void +_elm_config_engine_set(const char *engine) +{ + if (_elm_config->engine && strcmp(_elm_config->engine, engine)) + eina_stringshare_del(_elm_config->engine); + + _elm_config->engine = eina_stringshare_add(engine); +} + +void +_elm_config_profile_set(const char *profile) +{ + Eina_Bool changed = EINA_FALSE; + + if (_elm_profile) + { + if (strcmp(_elm_profile, profile)) + changed = 1; + free(_elm_profile); + } + + _elm_profile = strdup(profile); + + if (changed) + { + _config_free(); + _config_load(); + _config_apply(); + _elm_config_font_overlay_apply(); + _elm_rescale(); + _elm_recache(); + } +} + +void +_elm_config_shutdown(void) +{ +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_X11) || + ENGINE_COMPARE(ELM_SOFTWARE_16_X11) || + ENGINE_COMPARE(ELM_XRENDER_X11) || + ENGINE_COMPARE(ELM_OPENGL_X11)) +#undef ENGINE_COMPARE + { +#ifdef HAVE_ELEMENTARY_X + ecore_event_handler_del(_prop_change_handler); + _prop_change_handler = NULL; +#endif + } + _config_free(); + if (_elm_profile) + { + free(_elm_profile); + _elm_profile = NULL; + } + _desc_shutdown(); +} + diff --git a/src/lib/elm_conform.c b/src/lib/elm_conform.c new file mode 100644 index 0000000..34e2e39 --- /dev/null +++ b/src/lib/elm_conform.c @@ -0,0 +1,346 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Conformant Conformant + * + * The aim is to provide a widget that can be used in elementary apps to + * account for space taken up by the indicator & softkey windows when running + * the illume2 module of E17. + */ + +typedef struct _Widget_Data Widget_Data; +struct _Widget_Data +{ + Evas_Object *base; + Evas_Object *shelf, *panel; + Evas_Object *content; + Ecore_Event_Handler *prop_hdl; + struct { + Ecore_Animator *animator; // animaton timer + double start; // time started + Evas_Coord auto_x, auto_y; // desired delta + Evas_Coord x, y; // current delta + } delta; +}; + +/* local function prototypes */ +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static Eina_Bool _prop_change(void *data, int type, void *event); + +/* local functions */ +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->prop_hdl) ecore_event_handler_del(wd->prop_hdl); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->base, "conformant", "base", elm_widget_style_get(obj)); + if (wd->content) + edje_object_part_swallow(wd->base, "elm.swallow.content", wd->content); + edje_object_scale_set(wd->base, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord mw = -1, mh = -1; + if (!wd) return; + edje_object_size_min_calc(wd->base, &mw, &mh); + evas_object_size_hint_min_set(obj, mw, mh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->content) + { + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->content = NULL; + _sizing_eval(obj); + } +} + +/* unused now - but meant to be for making sure the focused widget is always + * visible when the vkbd comes and goes by moving the conformant obj (and thus + * its children) to show the focused widget (and if focus changes follow) + +static Evas_Object * +_focus_object_get(const Evas_Object *obj) +{ + Evas_Object *win, *foc; + + win = elm_widget_top_get(obj); + if (!win) return NULL; + foc = elm_widget_top_get(win); +} + +static void +_focus_object_region_get(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h) +{ + evas_object_geometry_get(obj, x, y, w, h); +} + +static void +_focus_change_del(void *data, Evas_Object *obj, void *event_info) +{ + // called from toplevel when the focused window shanges +} + +static void +_autoscroll_move(Evas_Object *obj) +{ + // move conformant edje by delta to show focused widget +} + +static void +_autoscroll_mode_enable(Evas_Object *obj) +{ + // called when autoscroll mode should be on - content area smaller than + // its min size + // 1. get focused object + // 2. if not in visible conformant area calculate delta needed to + // get it in + // 3. store delta and call _autoscroll_move() which either asanimates + // or jumps right there +} + +static void +_autoscroll_mode_disable(Evas_Object *obj) +{ + // called when autoscroll mode should be off - set delta to 0 and + // call _autoscroll_move() +} +*/ + +static Eina_Bool +_prop_change(void *data, int type __UNUSED__, void *event) +{ +#ifdef HAVE_ELEMENTARY_X + Ecore_X_Event_Window_Property *ev; + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_PASS_ON; + ev = event; + if (ev->atom == ECORE_X_ATOM_E_ILLUME_ZONE) + { + Ecore_X_Window zone; + int sh = -1; + + zone = ecore_x_e_illume_zone_get(ev->win); + ecore_x_e_illume_indicator_geometry_get(zone, NULL, NULL, NULL, &sh); + if (sh < 0) sh = 0; + evas_object_size_hint_min_set(wd->shelf, -1, sh); + evas_object_size_hint_max_set(wd->shelf, -1, sh); + sh = -1; + ecore_x_e_illume_softkey_geometry_get(zone, NULL, NULL, NULL, &sh); + if (sh < 0) sh = 0; + evas_object_size_hint_min_set(wd->panel, -1, sh); + evas_object_size_hint_max_set(wd->panel, -1, sh); + } + else if (ev->atom == ECORE_X_ATOM_E_ILLUME_INDICATOR_GEOMETRY) + { + Ecore_X_Window zone; + int sh = -1; + + zone = ecore_x_e_illume_zone_get(ev->win); + ecore_x_e_illume_indicator_geometry_get(zone, NULL, NULL, NULL, &sh); + if (sh < 0) sh = 0; + evas_object_size_hint_min_set(wd->shelf, -1, sh); + evas_object_size_hint_max_set(wd->shelf, -1, sh); + } + else if (ev->atom == ECORE_X_ATOM_E_ILLUME_SOFTKEY_GEOMETRY) + { + Ecore_X_Window zone; + int sh = -1; + + zone = ecore_x_e_illume_zone_get(ev->win); + ecore_x_e_illume_softkey_geometry_get(zone, NULL, NULL, NULL, &sh); + if (sh < 0) sh = 0; + evas_object_size_hint_min_set(wd->panel, -1, sh); + evas_object_size_hint_max_set(wd->panel, -1, sh); + } + else if (ev->atom == ECORE_X_ATOM_E_ILLUME_KEYBOARD_GEOMETRY) + { + Ecore_X_Window zone; + int ky = -1; + + printf("Keyboard Geometry Changed\n"); + zone = ecore_x_e_illume_zone_get(ev->win); + ecore_x_e_illume_keyboard_geometry_get(zone, NULL, &ky, NULL, NULL); + printf("\tGeom: %d\n", ky); + } +#endif + + return ECORE_CALLBACK_PASS_ON; +} + +/** + * Add a new Conformant object + * + * @param parent The parent object + * @return The new conformant object or NULL if it cannot be created + * + * @ingroup Conformant + */ +EAPI Evas_Object * +elm_conformant_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *evas; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + + evas = evas_object_evas_get(parent); + if (!evas) return NULL; + + obj = elm_widget_add(evas); + ELM_SET_WIDTYPE(widtype, "conformant"); + elm_widget_type_set(obj, "conformant"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->base = edje_object_add(evas); + _elm_theme_object_set(obj, wd->base, "conformant", "base", "default"); + elm_widget_resize_object_set(obj, wd->base); + +#ifdef HAVE_ELEMENTARY_X + Ecore_X_Window zone, xwin; + int sh = -1; + + xwin = elm_win_xwindow_get(parent); + zone = ecore_x_e_illume_zone_get(xwin); + + ecore_x_e_illume_indicator_geometry_get(zone, NULL, NULL, NULL, &sh); + if (sh < 0) sh = 0; + wd->shelf = evas_object_rectangle_add(evas); + evas_object_color_set(wd->shelf, 0, 0, 0, 0); + evas_object_size_hint_min_set(wd->shelf, -1, sh); + evas_object_size_hint_max_set(wd->shelf, -1, sh); + edje_object_part_swallow(wd->base, "elm.swallow.shelf", wd->shelf); + + sh = -1; + ecore_x_e_illume_softkey_geometry_get(zone, NULL, NULL, NULL, &sh); + if (sh < 0) sh = 0; + wd->panel = evas_object_rectangle_add(evas); + evas_object_color_set(wd->panel, 0, 0, 0, 0); + evas_object_size_hint_min_set(wd->panel, -1, sh); + evas_object_size_hint_max_set(wd->panel, -1, sh); + edje_object_part_swallow(wd->base, "elm.swallow.panel", wd->panel); + + wd->prop_hdl = ecore_event_handler_add(ECORE_X_EVENT_WINDOW_PROPERTY, + _prop_change, obj); + // FIXME: get kbd region prop +#endif + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + _sizing_eval(obj); + return obj; +} + +/** + * Set the content of the conformant widget + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_conformat_content_unset() function. + * + * @param obj The conformant object + * @return The content that was being used + * + * @ingroup Conformant + */ +EAPI void +elm_conformant_content_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->content == content) return; + if (wd->content) evas_object_del(wd->content); + wd->content = content; + if (content) + { + elm_widget_sub_object_add(obj, content); + evas_object_event_callback_add(content, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->base, "elm.swallow.content", content); + } + _sizing_eval(obj); +} + +/** + * Get the content of the conformant widget + * + * Return the content object which is set for this widget; + * + * @param obj The conformant object + * @return The content that is being used + * + * @ingroup Conformant + */ +EAPI Evas_Object * +elm_conformant_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->content; +} + +/** + * Unset the content of the conformant widget + * + * Unparent and return the content object which was set for this widget; + * + * @param obj The conformant object + * @return The content that was being used + * + * @ingroup Conformant + */ +EAPI Evas_Object * +elm_conformant_content_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *content; + if (!wd) return NULL; + if (!wd->content) return NULL; + content = wd->content; + elm_widget_sub_object_del(obj, wd->content); + edje_object_part_unswallow(wd->base, wd->content); + wd->content = NULL; + return content; +} diff --git a/src/lib/elm_diskselector.c b/src/lib/elm_diskselector.c new file mode 100644 index 0000000..fe34ef9 --- /dev/null +++ b/src/lib/elm_diskselector.c @@ -0,0 +1,1543 @@ +/** + * @defgroup Diskselector + * + * A diskselector is a kind of list widget. It scrolls horizontally, + * and can contain label and icon objects. Three items are displayed + * with the selected on the middle. + * + * It can act like a circular list with round mode and labels can be + * reduced for a defined lenght for side items. + * + * Signal emitted by this widget: + * "selected" - when item is selected (scroller stops) + */ + +#include +#include "elm_priv.h" + +#ifndef MAX +# define MAX(a, b) (((a) > (b)) ? (a) : (b)) +#endif + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *self; + Evas_Object *scroller; + Evas_Object *main_box; + Evas_Object *left_blank; + Evas_Object *right_blank; + Elm_Diskselector_Item *selected_item; + Elm_Diskselector_Item *first; + Elm_Diskselector_Item *second; + Elm_Diskselector_Item *s_last; + Elm_Diskselector_Item *last; + Eina_List *items; + Eina_List *r_items; + int item_count, len_threshold, len_side; + Ecore_Idler *idler; + Ecore_Idler *check_idler; + Eina_Bool init:1; + Eina_Bool round:1; +}; + +struct _Elm_Diskselector_Item +{ + Elm_Widget_Item base; + Eina_List *node; + Evas_Object *icon; + const char *label; + Evas_Smart_Cb func; +}; + +static const char *widtype = NULL; + +#define ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it, ...) \ + ELM_WIDGET_ITEM_CHECK_OR_RETURN((Elm_Widget_Item *)it, __VA_ARGS__); \ + ELM_CHECK_WIDTYPE(it->base.widget, widtype) __VA_ARGS__; + +static Eina_Bool _move_scroller(void *data); +static void _del_hook(Evas_Object * obj); +static void _del_pre_hook(Evas_Object * obj); +static void _sizing_eval(Evas_Object * obj); +static void _theme_hook(Evas_Object * obj); +static void _on_focus_hook(void *data, Evas_Object *obj); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, Evas_Callback_Type type, void *event_info); +static void _sub_del(void *data, Evas_Object * obj, void *event_info); +static void _round_items_del(Widget_Data *wd); +static void _scroller_move_cb(void *data, Evas_Object *obj, void *event_info); + +static const char SIG_SELECTED[] = "selected"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_SELECTED, ""}, + {NULL, NULL} +}; + +static void +_diskselector_object_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd; + Evas_Coord w, h, minw = -1, minh = -1; + + wd = elm_widget_data_get(data); + if (!wd) return; + + elm_coords_finger_size_adjust(6, &minw, 1, &minh); + edje_object_size_min_restricted_calc(elm_smart_scroller_edje_object_get( + wd->scroller), &minw, &minh, minw, minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); + + evas_object_geometry_get(wd->scroller, NULL, NULL, &w, &h); + if (wd->round) + evas_object_resize(wd->main_box, w / 3 * (wd->item_count + 4), h); + else + evas_object_resize(wd->main_box, w / 3 * (wd->item_count + 2), h); + + elm_smart_scroller_paging_set(wd->scroller, 0, 0, + (int)(w / 3), 0); + + if (!wd->idler) + wd->idler = ecore_idler_add(_move_scroller, data); +} + +static Elm_Diskselector_Item * +_item_new(Evas_Object *obj, Evas_Object *icon, const char *label, Evas_Smart_Cb func, const void *data) +{ + Elm_Diskselector_Item *it; + const char *style = elm_widget_style_get(obj); + + it = elm_widget_item_new(obj, Elm_Diskselector_Item); + if (!it) return NULL; + + it->label = eina_stringshare_add(label); + it->icon = icon; + it->func = func; + it->base.data = data; + it->base.view = edje_object_add(evas_object_evas_get(obj)); + _elm_theme_object_set(obj, it->base.view, "diskselector", "item", style); + evas_object_size_hint_weight_set(it->base.view, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(it->base.view, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_show(it->base.view); + + if (it->label) + edje_object_part_text_set(it->base.view, "elm.text", it->label); + if (it->icon) + { + evas_object_size_hint_min_set(it->icon, 24, 24); + evas_object_size_hint_max_set(it->icon, 40, 40); + edje_object_part_swallow(it->base.view, "elm.swallow.icon", it->icon); + evas_object_show(it->icon); + elm_widget_sub_object_add(obj, it->icon); + } + return it; +} + +static void +_item_del(Elm_Diskselector_Item *item) +{ + if (!item) return; + eina_stringshare_del(item->label); + if (item->icon) + evas_object_del(item->icon); + elm_widget_item_del(item); +} + +static void +_theme_data_get(Widget_Data *wd) +{ + const char* str; + str = edje_object_data_get(wd->right_blank, "len_threshold"); + if (str) wd->len_threshold = atoi(str); + else wd->len_threshold = 0; +} + +static void +_del_hook(Evas_Object * obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_del_pre_hook(Evas_Object * obj) +{ + Elm_Diskselector_Item *it; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (wd->left_blank) + evas_object_del(wd->left_blank); + if (wd->right_blank) + evas_object_del(wd->right_blank); + if (wd->last) + { + eina_stringshare_del(wd->last->label); + evas_object_del(wd->last->base.view); + free(wd->last); + } + if (wd->s_last) + { + eina_stringshare_del(wd->s_last->label); + evas_object_del(wd->s_last->base.view); + free(wd->s_last); + } + if (wd->second) + { + eina_stringshare_del(wd->second->label); + evas_object_del(wd->second->base.view); + free(wd->second); + } + if (wd->first) + { + eina_stringshare_del(wd->first->label); + evas_object_del(wd->first->base.view); + free(wd->first); + } + + EINA_LIST_FREE(wd->items, it) _item_del(it); + eina_list_free(wd->r_items); +} + +static void +_sizing_eval(Evas_Object * obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _diskselector_object_resize(obj, NULL, obj, NULL); +} + +static void +_theme_hook(Evas_Object * obj) +{ + Eina_List *l; + Elm_Diskselector_Item *it; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (wd->scroller) + elm_smart_scroller_object_theme_set(obj, wd->scroller, "diskselector", + "base", elm_widget_style_get(obj)); + if (wd->round) + { + EINA_LIST_FOREACH(wd->r_items, l, it) + { + _elm_theme_object_set(obj, it->base.view, "diskselector", "item", + elm_widget_style_get(obj)); + } + } + else + { + EINA_LIST_FOREACH(wd->items, l, it) + { + _elm_theme_object_set(obj, it->base.view, "diskselector", "item", + elm_widget_style_get(obj)); + } + } + _theme_data_get(wd); + _sizing_eval(obj); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object * obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + Elm_Diskselector_Item *it; + const Eina_List *l; + + if (!wd) return; + if (!sub) abort(); + if (sub == wd->scroller) + wd->scroller = NULL; + else + { + EINA_LIST_FOREACH(wd->items, l, it) + { + if (sub == it->icon) + { + it->icon = NULL; + _sizing_eval(obj); + break; + } + } + } +} + +static void +_select_item(Elm_Diskselector_Item *it) +{ + if (!it) return; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + wd->selected_item = it; + if (it->func) it->func((void *)it->base.data, it->base.widget, it); + evas_object_smart_callback_call(it->base.widget, SIG_SELECTED, it); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->self, "elm,action,focus", "elm"); + evas_object_focus_set(wd->self, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->self, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->self, EINA_FALSE); + } +} + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + + Elm_Diskselector_Item *it = NULL; + Eina_List *l; + + if (!wd->selected_item) { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + + if ((!strcmp(ev->keyname, "Left")) || (!strcmp(ev->keyname, "KP_Left")) || + (!strcmp(ev->keyname, "Up")) || (!strcmp(ev->keyname, "KP_Up"))) + { + l = wd->selected_item->node->prev; + if ((!l) && (wd->round)) + l = eina_list_last(wd->items); + } + else if ((!strcmp(ev->keyname, "Right")) || (!strcmp(ev->keyname, "KP_Right")) || + (!strcmp(ev->keyname, "Down")) || (!strcmp(ev->keyname, "KP_Down"))) + { + l = wd->selected_item->node->next; + if ((!l) && (wd->round)) + l = wd->items; + } + else if ((!strcmp(ev->keyname, "Home")) || (!strcmp(ev->keyname, "KP_Home"))) + l = wd->items; + else if ((!strcmp(ev->keyname, "End")) || (!strcmp(ev->keyname, "KP_End"))) + l = eina_list_last(wd->items); + else return EINA_FALSE; + + if (l) + it = eina_list_data_get(l); + + if (it) + { + wd->selected_item = it; + if (!wd->idler) + wd->idler = ecore_idler_add(_move_scroller, obj); + } + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; +} + +static int +_check_letter(const char *str, int length) +{ + int code = str[length]; + + if (code == '\0') + return length; // null string + else if (((code >= 65) && (code <= 90)) || ((code >= 97) && (code <= 122))) + return length; // alphabet + else if ((48 <= code) && (code < 58)) + return length; // number + else if (((33 <= code) && (code < 47)) || ((58 <= code) && (code < 64)) + || ((91 <= code) && (code < 96)) || ((123 <= code) && (code < 126))) + return length; // special letter + return length - 1; +} + +static Eina_Bool +_check_string(void *data) +{ + int mid, steps, length, diff; + Elm_Diskselector_Item *it; + Eina_List *list, *l; + Evas_Coord ox, ow; + char buf[1024]; + Widget_Data *wd = data; + + evas_object_geometry_get(wd->scroller, &ox, NULL, &ow, NULL); + if (ow <= 0) + return EINA_FALSE; + if (!wd->init) + return EINA_FALSE; + if (!wd->round) + list = wd->items; + else + list = wd->r_items; + + EINA_LIST_FOREACH(list, l, it) + { + Evas_Coord x, w; + int len; + evas_object_geometry_get(it->base.view, &x, NULL, &w, NULL); + /* item not visible */ + if ((x + w <= ox) || (x >= ox + ow)) + continue; + + len = eina_stringshare_strlen(it->label); + + if (x <= ox + 5) + edje_object_signal_emit(it->base.view, "elm,state,left_side", + "elm"); + else if (x + w >= ox + ow - 5) + edje_object_signal_emit(it->base.view, "elm,state,right_side", + "elm"); + else + { + if ((wd->len_threshold) && (len > wd->len_threshold)) + edje_object_signal_emit(it->base.view, "elm,state,center_small", + "elm"); + else + edje_object_signal_emit(it->base.view, "elm,state,center", + "elm"); + } + + if (len <= wd->len_side) + continue; + + steps = len - wd->len_side + 1; + mid = x + w / 2; + if (mid <= ox + ow / 2) + diff = (ox + ow / 2) - mid; + else + diff = mid - (ox + ow / 2); + + length = len - (int)(diff * steps / (ow / 3)); + length = MAX(length, wd->len_side); + length = _check_letter(it->label, length); + strncpy(buf, it->label, length); + buf[length] = '\0'; + edje_object_part_text_set(it->base.view, "elm.text", buf); + } + + if (wd->check_idler) + ecore_idler_del(wd->check_idler); + wd->check_idler = NULL; + return EINA_FALSE; +} + +static void +_scroller_move_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Coord x, y, w, h, bw; + Widget_Data *wd = data; + + _check_string(wd); + elm_smart_scroller_child_pos_get(obj, &x, &y); + elm_smart_scroller_child_viewport_size_get(obj, &w, &h); + if (wd->round) + { + evas_object_geometry_get(wd->main_box, NULL, NULL, &bw, NULL); + if (x > w / 3 * (wd->item_count + 1)) + elm_smart_scroller_child_region_show(wd->scroller, + x - w / 3 * wd->item_count, + y, w, h); + else if (x < 0) + elm_smart_scroller_child_region_show(wd->scroller, + x + w / 3 * wd->item_count, + y, w, h); + } +} + +static void +_scroller_stop_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Diskselector_Item *it; + Widget_Data *wd = data; + Evas_Coord x, w, ow; + Eina_List *l, *list; + + if (wd->idler) + return; + + if (!wd->round) + list = wd->items; + else + list = wd->r_items; + + evas_object_geometry_get(wd->scroller, NULL, NULL, &ow, NULL); + EINA_LIST_FOREACH(list, l, it) + { + evas_object_geometry_get(it->base.view, &x, NULL, &w, NULL); + if (abs((int)(ow / 2 - (int)(x + w / 2))) < 10) + break; + } + + if (!it) + return; + + _select_item(it); +} + +static Eina_Bool +_move_scroller(void *data) +{ + Evas_Object *obj = data; + Widget_Data *wd; + Eina_List *l; + Elm_Diskselector_Item *dit; + Evas_Coord y, w, h; + int i; + + wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + + if (wd->round) + i = 1; + else + i = 0; + + EINA_LIST_FOREACH(wd->items, l, dit) + { + if (wd->selected_item == dit) + break; + i++; + } + if (!dit) + { + wd->selected_item = + (Elm_Diskselector_Item *) eina_list_nth(wd->items, 0); + return EINA_FALSE; + } + + evas_object_geometry_get(wd->scroller, NULL, &y, &w, &h); + elm_smart_scroller_child_region_show(wd->scroller, w / 3 * i, y, w, h); + _select_item(dit); + if (wd->idler) + { + ecore_idler_del(wd->idler); + wd->idler = NULL; + } + wd->init = EINA_TRUE; + _check_string(wd); + + return EINA_TRUE; +} + +static void +_round_item_del(Widget_Data *wd, Elm_Diskselector_Item *it) +{ + if (!it) return; + elm_box_unpack(wd->main_box, it->base.view); + wd->r_items = eina_list_remove(wd->r_items, it); + eina_stringshare_del(it->label); + evas_object_del(it->base.view); + free(it); +} + +static void +_round_items_del(Widget_Data *wd) +{ + _round_item_del(wd, wd->last); + wd->last = NULL; + _round_item_del(wd, wd->s_last); + wd->s_last = NULL; + _round_item_del(wd, wd->second); + wd->second = NULL; + _round_item_del(wd, wd->first); + wd->first = NULL; +} + +static void +_round_items_add(Widget_Data *wd) +{ + Elm_Diskselector_Item *dit; + Elm_Diskselector_Item *it; + + dit = it = eina_list_nth(wd->items, 0); + if (!dit) return; + + if (!wd->first) + { + wd->first = _item_new(it->base.widget, it->icon, it->label, it->func, + it->base.data); + wd->first->node = it->node; + wd->r_items = eina_list_append(wd->r_items, wd->first); + } + + it = eina_list_nth(wd->items, 1); + if (!it) + it = dit; + if (!wd->second) + { + wd->second = _item_new(it->base.widget, it->icon, it->label, it->func, + it->base.data); + wd->second->node = it->node; + wd->r_items = eina_list_append(wd->r_items, wd->second); + } + + it = eina_list_nth(wd->items, wd->item_count - 1); + if (!it) + it = dit; + if (!wd->last) + { + wd->last = _item_new(it->base.widget, it->icon, it->label, it->func, + it->base.data); + wd->last->node = it->node; + wd->r_items = eina_list_prepend(wd->r_items, wd->last); + } + + it = eina_list_nth(wd->items, wd->item_count - 2); + if (!it) + it = dit; + if (!wd->s_last) + { + wd->s_last = _item_new(it->base.widget, it->icon, it->label, it->func, + it->base.data); + wd->s_last->node = it->node; + wd->r_items = eina_list_prepend(wd->r_items, wd->s_last); + } +} + +/** + * Add a new diskselector object + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Diskselector + */ +EAPI Evas_Object * +elm_diskselector_add(Evas_Object *parent) +{ + Evas_Object *obj; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + wd->self = obj = elm_widget_add(evas_object_evas_get(parent)); + ELM_SET_WIDTYPE(widtype, "diskselector"); + elm_widget_type_set(obj, "diskselector"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_event_hook_set(obj, _event_hook); + + wd->item_count = 0; + wd->round = EINA_FALSE; + wd->init = EINA_FALSE; + wd->len_side = 3; + + wd->scroller = elm_smart_scroller_add(evas_object_evas_get(parent)); + elm_smart_scroller_widget_set(wd->scroller, obj); + _theme_hook(obj); + elm_widget_resize_object_set(obj, wd->scroller); + elm_smart_scroller_policy_set(wd->scroller, ELM_SMART_SCROLLER_POLICY_OFF, + ELM_SMART_SCROLLER_POLICY_OFF); + elm_smart_scroller_bounce_allow_set(wd->scroller, EINA_TRUE, EINA_FALSE); + evas_object_smart_callback_add(wd->scroller, "scroll", _scroller_move_cb, + wd); + evas_object_smart_callback_add(wd->scroller, "animate,stop", + _scroller_stop_cb, wd); + _elm_theme_object_set(obj, wd->scroller, "diskselector", "base", + "default"); + evas_object_event_callback_add(wd->scroller, EVAS_CALLBACK_RESIZE, + _diskselector_object_resize, obj); + + wd->main_box = elm_box_add(parent); + elm_box_horizontal_set(wd->main_box, EINA_TRUE); + elm_box_homogenous_set(wd->main_box, EINA_TRUE); + evas_object_size_hint_weight_set(wd->main_box, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(wd->main_box, EVAS_HINT_FILL, + EVAS_HINT_FILL); + _elm_theme_object_set(obj, wd->main_box, "diskselector", "base", + "default"); + elm_widget_sub_object_add(obj, wd->main_box); + + elm_smart_scroller_child_set(wd->scroller, wd->main_box); + + wd->left_blank = edje_object_add(evas_object_evas_get(obj)); + _elm_theme_object_set(obj, wd->left_blank, "diskselector", "item", + "default"); + evas_object_size_hint_weight_set(wd->left_blank, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(wd->left_blank, EVAS_HINT_FILL, + EVAS_HINT_FILL); + elm_box_pack_end(wd->main_box, wd->left_blank); + evas_object_show(wd->left_blank); + + wd->right_blank = edje_object_add(evas_object_evas_get(obj)); + _elm_theme_object_set(obj, wd->right_blank, "diskselector", "item", + "default"); + evas_object_size_hint_weight_set(wd->right_blank, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(wd->right_blank, EVAS_HINT_FILL, + EVAS_HINT_FILL); + elm_box_pack_end(wd->main_box, wd->right_blank); + evas_object_show(wd->right_blank); + + _theme_data_get(wd); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + evas_object_smart_callbacks_descriptions_set(obj, _signals); + _sizing_eval(obj); + return obj; +} + +/** + * Get round mode + * + * If round mode is activated the items list will work like a circle list, + * so when the user reaches the last item, the first one will popup. + * + * @param obj The diskselector object + * @return if or not set round mode or false if not a valid diskselector + * + * @ingroup Diskselector + */ +EAPI Eina_Bool +elm_diskselector_round_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->round; +} + +/** + * Set round mode + * + * If round mode is activated the items list will work like a circle list, + * so when the user reaches the last item, the first one will popup. + * + * @param it The item of diskselector + * @param if or not set round mode + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_round_set(Evas_Object * obj, Eina_Bool round) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (wd->round == round) + return; + + wd->round = round; + if (round) + { + wd->r_items = eina_list_clone(wd->items); + elm_box_unpack(wd->main_box, wd->left_blank); + evas_object_hide(wd->left_blank); + elm_box_unpack(wd->main_box, wd->right_blank); + evas_object_hide(wd->right_blank); + if (!wd->items) + return; + + _round_items_add(wd); + + if (wd->last) + elm_box_pack_start(wd->main_box, wd->last->base.view); + if (wd->s_last) + elm_box_pack_start(wd->main_box, wd->s_last->base.view); + if (wd->first) + elm_box_pack_end(wd->main_box, wd->first->base.view); + if (wd->second) + elm_box_pack_end(wd->main_box, wd->second->base.view); + } + else + { + _round_items_del(wd); + elm_box_pack_start(wd->main_box, wd->left_blank); + elm_box_pack_end(wd->main_box, wd->right_blank); + eina_list_free(wd->r_items); + wd->r_items = NULL; + } + _sizing_eval(obj); +} + +/** + * Get the side labels max lenght + * + * @param obj The diskselector object + * @return The max lenght defined for side labels, or 0 if not a valid + * diskselector + * + * @ingroup Diskselector + */ +EAPI int +elm_diskselector_side_label_lenght_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->len_side; +} + +/** + * Set the side labels max lenght + * + * @param obj The diskselector object + * @param len The max lenght defined for side labels + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_side_label_lenght_set(Evas_Object *obj, int len) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->len_side = len; +} + +/** + * Set bounce mode + * + * This will enable or disable the scroller bounce mode for the diskselector. + * See elm_scroller_bounce_set() for details. Horizontal bounce is enabled by + * default. + * + * @param obj The diskselector object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->scroller) + elm_smart_scroller_bounce_allow_set(wd->scroller, h_bounce, v_bounce); +} + +/** + * Get the bounce mode + * + * @param obj The Diskselector object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_bounce_allow_get(wd->scroller, h_bounce, v_bounce); +} + +/** + * Get the scrollbar policy + * + * This sets the scrollbar visibility policy for the given scroller. + * ELM_SMART_SCROLLER_POLICY_AUTO means the scrollber is made visible if it + * is needed, and otherwise kept hidden. ELM_SMART_SCROLLER_POLICY_ON turns + * it on all the time, and ELM_SMART_SCROLLER_POLICY_OFF always keeps it off. + * This applies respectively for the horizontal and vertical scrollbars. + * The both are disabled by default. + * + * @param obj The diskselector object + * @param policy_h Horizontal scrollbar policy + * @param policy_v Vertical scrollbar policy + * + * @ingroup Diskselector + */ + +EAPI void +elm_diskselector_scroller_policy_get(const Evas_Object *obj, Elm_Scroller_Policy *policy_h, Elm_Scroller_Policy *policy_v) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Elm_Smart_Scroller_Policy s_policy_h, s_policy_v; + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->scroller)) return; + elm_smart_scroller_policy_get(wd->scroller, &s_policy_h, &s_policy_v); + *policy_h = (Elm_Scroller_Policy) s_policy_h; + *policy_v = (Elm_Scroller_Policy) s_policy_v; +} + + +/** + * Set the scrollbar policy + * + * This sets the scrollbar visibility policy for the given scroller. + * ELM_SMART_SCROLLER_POLICY_AUTO means the scrollber is made visible if it + * is needed, and otherwise kept hidden. ELM_SMART_SCROLLER_POLICY_ON turns + * it on all the time, and ELM_SMART_SCROLLER_POLICY_OFF always keeps it off. + * This applies respectively for the horizontal and vertical scrollbars. + * The both are disabled by default. + * + * @param obj The diskselector object + * @param policy_h Horizontal scrollbar policy + * @param policy_v Vertical scrollbar policy + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_scroller_policy_set(Evas_Object *obj, Elm_Scroller_Policy policy_h, Elm_Scroller_Policy policy_v) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if ((policy_h >= 3) || (policy_v >= 3)) return; + if (wd->scroller) + elm_smart_scroller_policy_set(wd->scroller, policy_h, policy_v); +} + +/** + * Clears a diskselector of all items. + * + * @param obj The diskselector object + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_clear(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Diskselector_Item *it; + + if (!wd) return; + if (!wd->items) return; + + wd->selected_item = NULL; + EINA_LIST_FREE(wd->items, it) _item_del(it); + _round_items_del(wd); + _sizing_eval(obj); +} + +/** + * Returns a list of all the diskselector items. + * + * @param obj The diskselector object + * @return An Eina_List* of the diskselector items, or NULL on failure + * + * @ingroup Diskselector + */ +EAPI const Eina_List * +elm_diskselector_items_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->items; +} + +/** + * Appends an item to the diskselector object. + * + * @param obj The diskselector object + * @param label The label of the diskselector item + * @param icon The icon object to use for the left side of the item + * @param func The function to call when the item is selected + * @param data The data to associate with the item for related callbacks + * + * @return The created item or NULL upon failure + * + * @ingroup Diskselector + */ +EAPI Elm_Diskselector_Item * +elm_diskselector_item_append(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Smart_Cb func, const void *data) +{ + Elm_Diskselector_Item *it; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + it = _item_new(obj, icon, label, func, data); + wd->items = eina_list_append(wd->items, it); + it->node = eina_list_last(wd->items); + wd->item_count++; + if (wd->round) + { + _round_items_del(wd); + wd->r_items = eina_list_append(wd->r_items, it); + _round_items_add(wd); + if (wd->last) + elm_box_pack_start(wd->main_box, wd->last->base.view); + if (wd->s_last) + elm_box_pack_start(wd->main_box, wd->s_last->base.view); + elm_box_pack_end(wd->main_box, it->base.view); + if (wd->first) + elm_box_pack_end(wd->main_box, wd->first->base.view); + if (wd->second) + elm_box_pack_end(wd->main_box, wd->second->base.view); + } + else + { + elm_box_unpack(wd->main_box, wd->right_blank); + elm_box_pack_end(wd->main_box, it->base.view); + elm_box_pack_end(wd->main_box, wd->right_blank); + } + if (!wd->selected_item) + wd->selected_item = it; + if (!wd->idler) + wd->idler = ecore_idler_add(_move_scroller, obj); + _sizing_eval(obj); + return it; +} + +/** + * Delete the item + * + * @param it The item of diskselector + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_del(Elm_Diskselector_Item * it) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it); + Elm_Diskselector_Item *dit; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + if (!wd) return; + + elm_box_unpack(wd->main_box, it->base.view); + + if (wd->round) + wd->r_items = eina_list_remove(wd->r_items, it); + + wd->items = eina_list_remove(wd->items, it); + + if (wd->selected_item == it) + { + dit = (Elm_Diskselector_Item *) eina_list_nth(wd->items, 0); + if (dit != it) + wd->selected_item = dit; + else + wd->selected_item = eina_list_nth(wd->items, 1); + } + + _item_del(it); + wd->item_count -= 1; + + if (wd->round) + { + if (!wd->item_count) + { + evas_object_hide(wd->first->base.view); + evas_object_hide(wd->second->base.view); + evas_object_hide(wd->last->base.view); + evas_object_hide(wd->s_last->base.view); + } + else + { + dit = eina_list_nth(wd->items, 0); + if (dit) + { + eina_stringshare_replace(&wd->first->label, dit->label); + edje_object_part_text_set(wd->first->base.view, "elm.text", + wd->first->label); + } + dit = eina_list_nth(wd->items, 1); + if (dit) + { + eina_stringshare_replace(&wd->second->label, dit->label); + edje_object_part_text_set(wd->second->base.view, "elm.text", + wd->second->label); + } + dit = eina_list_nth(wd->items, eina_list_count(wd->items) - 1); + if (dit) + { + eina_stringshare_replace(&wd->last->label, dit->label); + edje_object_part_text_set(wd->last->base.view, "elm.text", + wd->last->label); + } + dit = eina_list_nth(wd->items, eina_list_count(wd->items) - 2); + if (dit) + { + eina_stringshare_replace(&wd->s_last->label, dit->label); + edje_object_part_text_set(wd->s_last->base.view, "elm.text", + wd->s_last->label); + } + } + } + wd->check_idler = ecore_idler_add(_check_string, wd); + _sizing_eval(it->base.widget); +} + +/** + * Get the label of item + * + * @param it The item of diskselector + * @return The label of item + * + * @ingroup Diskselector + */ +EAPI const char * +elm_diskselector_item_label_get(const Elm_Diskselector_Item * it) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it, NULL); + return it->label; +} + +/** + * Set the label of item + * + * @param it The item of diskselector + * @param label The label of item + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_label_set(Elm_Diskselector_Item * it, const char *label) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it); + eina_stringshare_replace(&it->label, label); + edje_object_part_text_set(it->base.view, "elm.text", it->label); +} + +/** + * Get the selected item + * + * @param obj The diskselector object + * @return The selected diskselector item + * + * @ingroup Diskselector + */ +EAPI Elm_Diskselector_Item * +elm_diskselector_selected_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->selected_item; +} + +/** + * Set the selected state of an item + * + * This sets the selected state (EINA_TRUE selected, EINA_FALSE not selected) + * of the given item @p it. + * If a new item is selected the previosly selected will be unselected. + * If the item @p it is unselected, the first item will be selected. + * + * @param it The diskselector item + * @param selected The selected state + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_selected_set(Elm_Diskselector_Item *it, Eina_Bool selected) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it); + Widget_Data *wd; + wd = elm_widget_data_get(it->base.widget); + if (!wd) return; + + if ((wd->selected_item == it) && (selected)) + return; + + if ((wd->selected_item == it) && (!selected)) + wd->selected_item = eina_list_data_get(wd->items); + else + wd->selected_item = it; + + if (!wd->idler) + ecore_idler_add(_move_scroller, it->base.widget); +} + +/* + * Get the selected state of @p item. + * + * @param it The diskselector item + * @return If true, the item is selected + * + * @ingroup Diskselector + */ +EAPI Eina_Bool +elm_diskselector_item_selected_get(const Elm_Diskselector_Item *it) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it, EINA_FALSE); + Widget_Data *wd; + + wd = elm_widget_data_get(it->base.widget); + if (!wd) return EINA_FALSE; + return (wd->selected_item == it); +} + +/** + * Set the function called when a diskselector item is freed. + * + * @param it The item to set the callback on + * @param func The function called + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_del_cb_set(Elm_Diskselector_Item *it, Evas_Smart_Cb func) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it); + elm_widget_item_del_cb_set(it, func); +} + +/** + * Returns the data associated with the item. + * + * @param it The diskselector item + * @return The data associated with @p it + * + * @ingroup Diskselector + */ +EAPI void * +elm_diskselector_item_data_get(const Elm_Diskselector_Item *it) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it, NULL); + return elm_widget_item_data_get(it); +} + +/** + * Returns the icon associated with the item. + * + * @param it The diskselector item + * @return The icon associated with @p it + * + * @ingroup Diskselector + */ +EAPI Evas_Object * +elm_diskselector_item_icon_get(const Elm_Diskselector_Item *it) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it, NULL); + return it->icon; +} + +/** + * Sets the icon associated with the item. + * + * Once the icon object is set, a previously set one will be deleted. + * You probably don't want, then, to have the same icon object set + * for more than one item of the diskselector. + * + * @param it The diskselector item + * @param icon The icon object to associate with @p it + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_icon_set(Elm_Diskselector_Item *it, Evas_Object *icon) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it); + if (it->icon == icon) return; + if (it->icon) + evas_object_del(it->icon); + it->icon = icon; + if (it->base.view) + edje_object_part_swallow(it->base.view, "elm.swallow.icon", icon); +} + +/** + * Gets the item before @p it in the list. + * + * @param it The diskselector item + * @return The item before @p it, or NULL on failure + * + * @ingroup Diskselector + */ +EAPI Elm_Diskselector_Item * +elm_diskselector_item_prev_get(const Elm_Diskselector_Item *it) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it, NULL); + if (it->node->prev) return it->node->prev->data; + else return NULL; +} + +/** + * Gets the item after @p it in the list. + * + * @param it The diskselector item + * @return The item after @p it, or NULL on failure + * + * @ingroup Diskselector + */ +EAPI Elm_Diskselector_Item * +elm_diskselector_item_next_get(const Elm_Diskselector_Item *it) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(it, NULL); + if (it->node->next) return it->node->next->data; + else return NULL; +} + +/** + * Get the first item in the diskselector + * + * @param obj The diskselector object + * @return The first item, or NULL if none + * + * @ingroup Diskselector + */ +EAPI Elm_Diskselector_Item * +elm_diskselector_first_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd || !wd->items) + return NULL; + + return eina_list_data_get(wd->items); +} + +/** + * Get the last item in the diskselector + * + * @param obj The diskselector object + * @return The last item, or NULL if none + * + * @ingroup Diskselector + */ +EAPI Elm_Diskselector_Item * +elm_diskselector_last_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Widget_Data *wd; + wd = elm_widget_data_get(obj); + if (!wd || !wd->items) + return NULL; + + return eina_list_data_get(eina_list_last(wd->items)); +} + +/** + * Set the text to be shown in the diskselector item. + * + * @param item Target item + * @param text The text to set in the content + * + * Setup the text as tooltip to object. The item can have only one tooltip, + * so any previous tooltip data is removed. + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_tooltip_text_set(Elm_Diskselector_Item *item, const char *text) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item); + elm_widget_item_tooltip_text_set(item, text); +} + +/** + * Set the content to be shown in the tooltip item + * + * Setup the tooltip to item. The item can have only one tooltip, + * so any previous tooltip data is removed. @p func(with @p data) will + * be called every time that need show the tooltip and it should + * return a valid Evas_Object. This object is then managed fully by + * tooltip system and is deleted when the tooltip is gone. + * + * @param item the diskselector item being attached a tooltip. + * @param func the function used to create the tooltip contents. + * @param data what to provide to @a func as callback data/context. + * @param del_cb called when data is not needed anymore, either when + * another callback replaces @func, the tooltip is unset with + * elm_diskselector_item_tooltip_unset() or the owner @a item + * dies. This callback receives as the first parameter the + * given @a data, and @c event_info is the item. + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_tooltip_content_cb_set(Elm_Diskselector_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item); + elm_widget_item_tooltip_content_cb_set(item, func, data, del_cb); +} + +/** + * Unset tooltip from item + * + * @param item diskselector item to remove previously set tooltip. + * + * Remove tooltip from item. The callback provided as del_cb to + * elm_diskselector_item_tooltip_content_cb_set() will be called to notify + * it is not used anymore. + * + * @see elm_diskselector_item_tooltip_content_cb_set() + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_tooltip_unset(Elm_Diskselector_Item *item) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item); + elm_widget_item_tooltip_unset(item); +} + +/** + * Sets a different style for this item tooltip. + * + * @note before you set a style you should define a tooltip with + * elm_diskselector_item_tooltip_content_cb_set() or + * elm_diskselector_item_tooltip_text_set() + * + * @param item diskselector item with tooltip already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_tooltip_style_set(Elm_Diskselector_Item *item, const char *style) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item); + elm_widget_item_tooltip_style_set(item, style); +} + +/** + * Get the style for this item tooltip. + * + * @param item diskselector item with tooltip already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a tooltip set, then NULL is returned. + * + * @ingroup Diskselector + */ +EAPI const char * +elm_diskselector_item_tooltip_style_get(const Elm_Diskselector_Item *item) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_tooltip_style_get(item); +} + +/** + * Set the cursor to be shown when mouse is over the diskselector item + * + * @param item Target item + * @param cursor the cursor name to be used. + * + * @see elm_object_cursor_set() + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_cursor_set(Elm_Diskselector_Item *item, const char *cursor) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item); + elm_widget_item_cursor_set(item, cursor); +} + +/** + * Get the cursor to be shown when mouse is over the diskselector item + * + * @param item diskselector item with cursor already set. + * @return the cursor name. + * + * @ingroup Diskselector + */ +EAPI const char * +elm_diskselector_item_cursor_get(const Elm_Diskselector_Item *item) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_cursor_get(item); +} + +/** + * Unset the cursor to be shown when mouse is over the diskselector item + * + * @param item Target item + * + * @see elm_object_cursor_unset() + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_cursor_unset(Elm_Diskselector_Item *item) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item); + elm_widget_item_cursor_unset(item); +} + +/** + * Sets a different style for this item cursor. + * + * @note before you set a style you should define a cursor with + * elm_diskselector_item_cursor_set() + * + * @param item diskselector item with cursor already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_cursor_style_set(Elm_Diskselector_Item *item, const char *style) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item); + elm_widget_item_cursor_style_set(item, style); +} + +/** + * Get the style for this item cursor. + * + * @param item diskselector item with cursor already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a cursor set, then NULL is returned. + * + * @ingroup Diskselector + */ +EAPI const char * +elm_diskselector_item_cursor_style_get(const Elm_Diskselector_Item *item) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_cursor_style_get(item); +} + +/** + * Set if the cursor set should be searched on the theme or should use + * the provided by the engine, only. + * + * @note before you set if should look on theme you should define a cursor + * with elm_object_cursor_set(). By default it will only look for cursors + * provided by the engine. + * + * @param item widget item with cursor already set. + * @param engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. + * + * @ingroup Diskselector + */ +EAPI void +elm_diskselector_item_cursor_engine_only_set(Elm_Diskselector_Item *item, Eina_Bool engine_only) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item); + elm_widget_item_cursor_engine_only_set(item, engine_only); +} + +/** + * Get the cursor engine only usage for this item cursor. + * + * @param item widget item with cursor already set. + * @return engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. If + * the object does not have a cursor set, then EINA_FALSE is returned. + * + * @ingroup Diskselector + */ +EAPI Eina_Bool +elm_diskselector_item_cursor_engine_only_get(const Elm_Diskselector_Item *item) +{ + ELM_DISKSELECTOR_ITEM_CHECK_OR_RETURN(item, EINA_FALSE); + return elm_widget_item_cursor_engine_only_get(item); +} diff --git a/src/lib/elm_entry.c b/src/lib/elm_entry.c new file mode 100644 index 0000000..9f08458 --- /dev/null +++ b/src/lib/elm_entry.c @@ -0,0 +1,2791 @@ +#include +#include +#include "elm_priv.h" + +/** + * @defgroup Entry Entry + * + * An entry is a convenience widget which shows + * a box that the user can enter text into. Unlike a + * @ref Scrolled_Entry widget, entries DO NOT scroll with user + * input. Entry widgets are capable of expanding past the + * boundaries of the window, thus resizing the window to its + * own length. + * + * You can also insert "items" in the entry with: + * + * \\ + * + * for example. sizing can be set bu size=WxH, relsize=WxH or absize=WxH with + * vsize=ascent or vsize=full. the href=NAME sets the item name. Entry + * supports a list of emoticon names by default. These are: + * + * - emoticon/angry + * - emoticon/angry-shout + * - emoticon/crazy-laugh + * - emoticon/evil-laugh + * - emoticon/evil + * - emoticon/goggle-smile + * - emoticon/grumpy + * - emoticon/grumpy-smile + * - emoticon/guilty + * - emoticon/guilty-smile + * - emoticon/haha + * - emoticon/half-smile + * - emoticon/happy-panting + * - emoticon/happy + * - emoticon/indifferent + * - emoticon/kiss + * - emoticon/knowing-grin + * - emoticon/laugh + * - emoticon/little-bit-sorry + * - emoticon/love-lots + * - emoticon/love + * - emoticon/minimal-smile + * - emoticon/not-happy + * - emoticon/not-impressed + * - emoticon/omg + * - emoticon/opensmile + * - emoticon/smile + * - emoticon/sorry + * - emoticon/squint-laugh + * - emoticon/surprised + * - emoticon/suspicious + * - emoticon/tongue-dangling + * - emoticon/tongue-poke + * - emoticon/uh + * - emoticon/unhappy + * - emoticon/very-sorry + * - emoticon/what + * - emoticon/wink + * - emoticon/worried + * - emoticon/wtf + * + * These are built-in currently, but you can add your own item provieer that + * can create inlined objects in the text and fill the space allocated to the + * item with a custom object of your own. + * + * See the entry test for some more examples of use of this. + * + * Entries have functions to load a text file, display it, + * allowing editing of it and saving of changes back to the file loaded. + * Changes are written back to the original file after a short delay. + * The file to load and save to is specified by elm_entry_file_set(). + * + * Signals that you can add callbacks for are: + * - "changed" - The text within the entry was changed + * - "activated" - The entry has had editing finished and changes are to be committed (generally when enter key is pressed) + * - "press" - The entry has been clicked + * - "longpressed" - The entry has been clicked for a couple seconds + * - "clicked" - The entry has been clicked + * - "clicked,double" - The entry has been double clicked + * - "focused" - The entry has received focus + * - "unfocused" - The entry has lost focus + * - "selection,paste" - A paste action has occurred + * - "selection,copy" - A copy action has occurred + * - "selection,cut" - A cut action has occurred + * - "selection,start" - A selection has begun + * - "selection,changed" - The selection has changed + * - "selection,cleared" - The selection has been cleared + * - "cursor,changed" - The cursor has changed + * - "anchor,clicked" - The anchor has been clicked + */ + +typedef struct _Mod_Api Mod_Api; + +typedef struct _Widget_Data Widget_Data; +typedef struct _Elm_Entry_Context_Menu_Item Elm_Entry_Context_Menu_Item; +typedef struct _Elm_Entry_Item_Provider Elm_Entry_Item_Provider; +typedef struct _Elm_Entry_Text_Filter Elm_Entry_Text_Filter; + +struct _Widget_Data +{ + Evas_Object *ent; + Evas_Object *hoversel; + Ecore_Job *deferred_recalc_job; + Ecore_Event_Handler *sel_notify_handler; + Ecore_Event_Handler *sel_clear_handler; + Ecore_Timer *longpress_timer; + Ecore_Timer *delay_write; + /* Only for clipboard */ + const char *cut_sel; + const char *text; + const char *file; + Elm_Text_Format format; + Evas_Coord lastw; + Evas_Coord downx, downy; + Evas_Coord cx, cy, cw, ch; + Eina_List *items; + Eina_List *item_providers; + Eina_List *text_filters; + Ecore_Job *hovdeljob; + Mod_Api *api; // module api if supplied + Eina_Bool changed : 1; + Eina_Bool linewrap : 1; + Eina_Bool char_linewrap : 1; + Eina_Bool single_line : 1; + Eina_Bool password : 1; + Eina_Bool editable : 1; + Eina_Bool selection_asked : 1; + Eina_Bool have_selection : 1; + Eina_Bool selmode : 1; + Eina_Bool deferred_cur : 1; + Eina_Bool disabled : 1; + Eina_Bool context_menu : 1; + Eina_Bool drag_selection_asked : 1; + Eina_Bool can_write : 1; + Eina_Bool autosave : 1; + Eina_Bool textonly : 1; +}; + +struct _Elm_Entry_Context_Menu_Item +{ + Evas_Object *obj; + const char *label; + const char *icon_file; + const char *icon_group; + Elm_Icon_Type icon_type; + Evas_Smart_Cb func; + void *data; +}; + +struct _Elm_Entry_Item_Provider +{ + Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item); + void *data; +}; + +struct _Elm_Entry_Text_Filter +{ + void (*func) (void *data, Evas_Object *entry, char **text); + void *data; +}; + +static const char *widtype = NULL; + +static Eina_Bool _drag_drop_cb(void *data, Evas_Object *obj, Elm_Selection_Data *); +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _on_focus_hook(void *data, Evas_Object *obj); +static void _resize(void *data, Evas *e, Evas_Object *obj, void *event_info); +static const char *_getbase(Evas_Object *obj); +static void _signal_entry_changed(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_selection_start(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_selection_changed(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_selection_cleared(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_entry_paste_request(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_entry_copy_notify(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_entry_cut_notify(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_cursor_changed(void *data, Evas_Object *obj, const char *emission, const char *source); + +static const char SIG_CHANGED[] = "changed"; +static const char SIG_ACTIVATED[] = "activated"; +static const char SIG_PRESS[] = "press"; +static const char SIG_LONGPRESSED[] = "longpressed"; +static const char SIG_CLICKED[] = "clicked"; +static const char SIG_CLICKED_DOUBLE[] = "clicked,double"; +static const char SIG_FOCUSED[] = "focused"; +static const char SIG_UNFOCUSED[] = "unfocused"; +static const char SIG_SELECTION_PASTE[] = "selection,paste"; +static const char SIG_SELECTION_COPY[] = "selection,copy"; +static const char SIG_SELECTION_CUT[] = "selection,cut"; +static const char SIG_SELECTION_START[] = "selection,start"; +static const char SIG_SELECTION_CHANGED[] = "selection,changed"; +static const char SIG_SELECTION_CLEARED[] = "selection,cleared"; +static const char SIG_CURSOR_CHANGED[] = "cursor,changed"; +static const char SIG_ANCHOR_CLICKED[] = "anchor,clicked"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_CHANGED, ""}, + {SIG_ACTIVATED, ""}, + {SIG_PRESS, ""}, + {SIG_LONGPRESSED, ""}, + {SIG_CLICKED, ""}, + {SIG_CLICKED_DOUBLE, ""}, + {SIG_FOCUSED, ""}, + {SIG_UNFOCUSED, ""}, + {SIG_SELECTION_PASTE, ""}, + {SIG_SELECTION_COPY, ""}, + {SIG_SELECTION_CUT, ""}, + {SIG_SELECTION_START, ""}, + {SIG_SELECTION_CHANGED, ""}, + {SIG_SELECTION_CLEARED, ""}, + {SIG_CURSOR_CHANGED, ""}, + {SIG_ANCHOR_CLICKED, ""}, + {NULL, NULL} +}; + +static Eina_List *entries = NULL; + +struct _Mod_Api +{ + void (*obj_hook) (Evas_Object *obj); + void (*obj_unhook) (Evas_Object *obj); + void (*obj_longpress) (Evas_Object *obj); +}; + +static Mod_Api * +_module(Evas_Object *obj __UNUSED__) +{ + static Elm_Module *m = NULL; + if (m) goto ok; // already found - just use + if (!(m = _elm_module_find_as("entry/api"))) return NULL; + // get module api + m->api = malloc(sizeof(Mod_Api)); + if (!m->api) return NULL; + ((Mod_Api *)(m->api) )->obj_hook = // called on creation + _elm_module_symbol_get(m, "obj_hook"); + ((Mod_Api *)(m->api) )->obj_unhook = // called on deletion + _elm_module_symbol_get(m, "obj_unhook"); + ((Mod_Api *)(m->api) )->obj_longpress = // called on long press menu + _elm_module_symbol_get(m, "obj_longpress"); + ok: // ok - return api + return m->api; +} + +static char * +_buf_append(char *buf, const char *str, int *len, int *alloc) +{ + int len2 = strlen(str); + if ((*len + len2) >= *alloc) + { + char *buf2 = realloc(buf, *alloc + len2 + 512); + if (!buf2) return NULL; + buf = buf2; + *alloc += (512 + len2); + } + strcpy(buf + *len, str); + *len += len2; + return buf; +} + +static char * +_load_file(const char *file) +{ + FILE *f; + size_t size; + int alloc = 0, len = 0; + char *text = NULL, buf[16384 + 1]; + + f = fopen(file, "rb"); + if (!f) return NULL; + while ((size = fread(buf, 1, sizeof(buf) - 1, f))) + { + char *tmp_text; + buf[size] = 0; + tmp_text = _buf_append(text, buf, &len, &alloc); + if (!tmp_text) break; + text = tmp_text; + } + fclose(f); + return text; +} + +static char * +_load_plain(const char *file) +{ + char *text; + + text = _load_file(file); + if (text) + { + char *text2; + + text2 = elm_entry_utf8_to_markup(text); + free(text); + return text2; + } + return NULL; +} + +static void +_load(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + char *text; + if (!wd) return; + if (!wd->file) + { + elm_entry_entry_set(obj, ""); + return; + } + switch (wd->format) + { + case ELM_TEXT_FORMAT_PLAIN_UTF8: + text = _load_plain(wd->file); + break; + case ELM_TEXT_FORMAT_MARKUP_UTF8: + text = _load_file(wd->file); + break; + default: + text = NULL; + break; + } + if (text) + { + elm_entry_entry_set(obj, text); + free(text); + } + else + elm_entry_entry_set(obj, ""); +} + +static void +_save_markup_utf8(const char *file, const char *text) +{ + FILE *f; + + if ((!text) || (!text[0])) + { + ecore_file_unlink(file); + return; + } + f = fopen(file, "wb"); + if (!f) + { + // FIXME: report a write error + return; + } + fputs(text, f); // FIXME: catch error + fclose(f); +} + +static void +_save_plain_utf8(const char *file, const char *text) +{ + char *text2; + + text2 = elm_entry_markup_to_utf8(text); + if (!text2) + return; + _save_markup_utf8(file, text2); + free(text2); +} + +static void +_save(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (!wd->file) return; + switch (wd->format) + { + case ELM_TEXT_FORMAT_PLAIN_UTF8: + _save_plain_utf8(wd->file, elm_entry_entry_get(obj)); + break; + case ELM_TEXT_FORMAT_MARKUP_UTF8: + _save_markup_utf8(wd->file, elm_entry_entry_get(obj)); + break; + default: + break; + } +} + +static Eina_Bool +_delay_write(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + _save(data); + wd->delay_write = NULL; + return ECORE_CALLBACK_CANCEL; +} + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->delay_write) + { + ecore_timer_del(wd->delay_write); + wd->delay_write = NULL; + if (wd->autosave) _save(obj); + } +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Entry_Context_Menu_Item *it; + Elm_Entry_Item_Provider *ip; + Elm_Entry_Text_Filter *tf; + + if (wd->file) eina_stringshare_del(wd->file); + + if (wd->hovdeljob) ecore_job_del(wd->hovdeljob); + if ((wd->api) && (wd->api->obj_unhook)) wd->api->obj_unhook(obj); // module - unhook + + entries = eina_list_remove(entries, obj); +#ifdef HAVE_ELEMENTARY_X + ecore_event_handler_del(wd->sel_notify_handler); + ecore_event_handler_del(wd->sel_clear_handler); +#endif + if (wd->cut_sel) eina_stringshare_del(wd->cut_sel); + if (wd->text) eina_stringshare_del(wd->text); + if (wd->deferred_recalc_job) ecore_job_del(wd->deferred_recalc_job); + if (wd->longpress_timer) ecore_timer_del(wd->longpress_timer); + EINA_LIST_FREE(wd->items, it) + { + eina_stringshare_del(it->label); + eina_stringshare_del(it->icon_file); + eina_stringshare_del(it->icon_group); + free(it); + } + EINA_LIST_FREE(wd->item_providers, ip) + { + free(ip); + } + EINA_LIST_FREE(wd->text_filters, tf) + { + free(tf); + } + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const char *t; + + t = eina_stringshare_add(elm_entry_entry_get(obj)); + _elm_theme_object_set(obj, wd->ent, "entry", _getbase(obj), elm_widget_style_get(obj)); + elm_entry_entry_set(obj, t); + eina_stringshare_del(t); + if (elm_widget_disabled_get(obj)) + edje_object_signal_emit(wd->ent, "elm,state,disabled", "elm"); + edje_object_message_signal_process(wd->ent); + edje_object_scale_set(wd->ent, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (elm_widget_disabled_get(obj)) + { + edje_object_signal_emit(wd->ent, "elm,state,disabled", "elm"); + wd->disabled = EINA_TRUE; + } + else + { + edje_object_signal_emit(wd->ent, "elm,state,enabled", "elm"); + wd->disabled = EINA_FALSE; + } +} + +static void +_elm_win_recalc_job(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord minw = -1, minh = -1, maxh = -1; + Evas_Coord resw, resh, minminw; + if (!wd) return; + wd->deferred_recalc_job = NULL; + evas_object_geometry_get(wd->ent, NULL, NULL, &resw, &resh); + resh = 0; + edje_object_size_min_restricted_calc(wd->ent, &minw, &minh, 0, 0); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + minminw = minw; + edje_object_size_min_restricted_calc(wd->ent, &minw, &minh, resw, 0); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(data, minminw, minh); + if (wd->single_line) maxh = minh; + evas_object_size_hint_max_set(data, -1, maxh); + if (wd->deferred_cur) + elm_widget_show_region_set(data, wd->cx, wd->cy, wd->cw, wd->ch); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + Evas_Coord resw, resh; + if (!wd) return; + if ((wd->linewrap) || (wd->char_linewrap)) + { + evas_object_geometry_get(wd->ent, NULL, NULL, &resw, &resh); + if ((resw == wd->lastw) && (!wd->changed)) return; + wd->changed = EINA_FALSE; + wd->lastw = resw; + if (wd->deferred_recalc_job) ecore_job_del(wd->deferred_recalc_job); + wd->deferred_recalc_job = ecore_job_add(_elm_win_recalc_job, obj); + } + else + { + evas_object_geometry_get(wd->ent, NULL, NULL, &resw, &resh); + edje_object_size_min_calc(wd->ent, &minw, &minh); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + if (wd->single_line) maxh = minh; + evas_object_size_hint_max_set(obj, maxw, maxh); + } +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *top = elm_widget_top_get(obj); + if (!wd) return; + if (!wd->editable) return; + if (elm_widget_focus_get(obj)) + { + evas_object_focus_set(wd->ent, EINA_TRUE); + edje_object_signal_emit(wd->ent, "elm,action,focus", "elm"); + if (top) elm_win_keyboard_mode_set(top, ELM_WIN_KEYBOARD_ON); + evas_object_smart_callback_call(obj, SIG_FOCUSED, NULL); + } + else + { + edje_object_signal_emit(wd->ent, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->ent, EINA_FALSE); + if (top) elm_win_keyboard_mode_set(top, ELM_WIN_KEYBOARD_OFF); + evas_object_smart_callback_call(obj, SIG_UNFOCUSED, NULL); + } +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_emit(wd->ent, emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_callback_add(wd->ent, emission, source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_del_full(wd->ent, emission, source, func_cb, + data); +} + +static void +_on_focus_region_hook(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_part_text_cursor_geometry_get(wd->ent, "elm.text", x, y, w, h); +} + +static void +_hoversel_position(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord cx, cy, cw, ch, x, y, mw, mh; + if (!wd) return; + evas_object_geometry_get(wd->ent, &x, &y, NULL, NULL); + edje_object_part_text_cursor_geometry_get(wd->ent, "elm.text", + &cx, &cy, &cw, &ch); + evas_object_size_hint_min_get(wd->hoversel, &mw, &mh); + if (cw < mw) + { + cx += (cw - mw) / 2; + cw = mw; + } + if (ch < mh) + { + cy += (ch - mh) / 2; + ch = mh; + } + evas_object_move(wd->hoversel, x + cx, y + cy); + evas_object_resize(wd->hoversel, cw, ch); +} + +static void +_move(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + + if (wd->hoversel) _hoversel_position(data); +} + +static void +_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if ((wd->linewrap) || (wd->char_linewrap)) + { + _sizing_eval(data); + } + if (wd->hoversel) _hoversel_position(data); +// Evas_Coord ww, hh; +// evas_object_geometry_get(wd->ent, NULL, NULL, &ww, &hh); +} + +static void +_hover_del(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + + if (wd->hoversel) + { + evas_object_del(wd->hoversel); + wd->hoversel = NULL; + } + wd->hovdeljob = NULL; +} + +static void +_dismissed(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (wd->hoversel) evas_object_hide(wd->hoversel); + if (wd->selmode) + { + if (!wd->password) + edje_object_part_text_select_allow_set(wd->ent, "elm.text", EINA_TRUE); + } + elm_widget_scroll_freeze_pop(data); + if (wd->hovdeljob) ecore_job_del(wd->hovdeljob); + wd->hovdeljob = ecore_job_add(_hover_del, data); +} + +static void +_select(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->selmode = EINA_TRUE; + edje_object_part_text_select_none(wd->ent, "elm.text"); + if (!wd->password) + edje_object_part_text_select_allow_set(wd->ent, "elm.text", EINA_TRUE); + edje_object_signal_emit(wd->ent, "elm,state,select,on", "elm"); + elm_widget_scroll_hold_push(data); +} + +static void +_paste(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_smart_callback_call(data, SIG_SELECTION_PASTE, NULL); + if (wd->sel_notify_handler) + { +#ifdef HAVE_ELEMENTARY_X + Elm_Sel_Format formats; + wd->selection_asked = EINA_TRUE; + formats = ELM_SEL_FORMAT_MARKUP; + if (!wd->textonly) + formats |= ELM_SEL_FORMAT_IMAGE; + elm_selection_get(ELM_SEL_CLIPBOARD, formats, data, NULL, NULL); +#endif + } +} + +static void +_store_selection(Elm_Sel_Type seltype, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const char *sel; + + if (!wd) return; + sel = edje_object_part_text_selection_get(wd->ent, "elm.text"); + elm_selection_set(seltype, obj, ELM_SEL_FORMAT_MARKUP, sel); + if (seltype == ELM_SEL_CLIPBOARD) + eina_stringshare_replace(&wd->cut_sel, sel); +} + +static void +_cut(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + + /* Store it */ + wd->selmode = EINA_FALSE; + edje_object_part_text_select_allow_set(wd->ent, "elm.text", 0); + edje_object_signal_emit(wd->ent, "elm,state,select,off", "elm"); + elm_widget_scroll_hold_pop(data); + _store_selection(ELM_SEL_CLIPBOARD, data); + edje_object_part_text_insert(wd->ent, "elm.text", ""); + edje_object_part_text_select_none(wd->ent, "elm.text"); +} + +static void +_copy(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->selmode = EINA_FALSE; + edje_object_part_text_select_allow_set(wd->ent, "elm.text", 0); + edje_object_signal_emit(wd->ent, "elm,state,select,off", "elm"); + elm_widget_scroll_hold_pop(data); + _store_selection(ELM_SEL_CLIPBOARD, data); +// edje_object_part_text_select_none(wd->ent, "elm.text"); +} + +static void +_cancel(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->selmode = EINA_FALSE; + edje_object_part_text_select_allow_set(wd->ent, "elm.text", 0); + edje_object_signal_emit(wd->ent, "elm,state,select,off", "elm"); + elm_widget_scroll_hold_pop(data); + edje_object_part_text_select_none(wd->ent, "elm.text"); +} + +static void +_item_clicked(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Entry_Context_Menu_Item *it = data; + Evas_Object *obj2 = it->obj; + if (it->func) it->func(it->data, obj2, NULL); +} + +static Eina_Bool +_long_press(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Object *top; + const Eina_List *l; + const Elm_Entry_Context_Menu_Item *it; + if (!wd) return ECORE_CALLBACK_CANCEL; + if ((wd->api) && (wd->api->obj_longpress)) + { + wd->api->obj_longpress(data); + } + else if (wd->context_menu) + { + const char *context_menu_orientation; + + if (wd->hoversel) evas_object_del(wd->hoversel); + else elm_widget_scroll_freeze_push(data); + wd->hoversel = elm_hoversel_add(data); + context_menu_orientation = edje_object_data_get + (wd->ent, "context_menu_orientation"); + if ((context_menu_orientation) && + (!strcmp(context_menu_orientation, "horizontal"))) + elm_hoversel_horizontal_set(wd->hoversel, EINA_TRUE); + elm_object_style_set(wd->hoversel, "entry"); + elm_widget_sub_object_add(data, wd->hoversel); + elm_hoversel_label_set(wd->hoversel, "Text"); + top = elm_widget_top_get(data); + if (top) elm_hoversel_hover_parent_set(wd->hoversel, top); + evas_object_smart_callback_add(wd->hoversel, "dismissed", _dismissed, data); + if (!wd->selmode) + { + if (!wd->password) + elm_hoversel_item_add(wd->hoversel, "Select", NULL, ELM_ICON_NONE, + _select, data); + if (1) // need way to detect if someone has a selection + { + if (wd->editable) + elm_hoversel_item_add(wd->hoversel, "Paste", NULL, ELM_ICON_NONE, + _paste, data); + } + } + else + { + if (!wd->password) + { + if (wd->have_selection) + { + elm_hoversel_item_add(wd->hoversel, "Copy", NULL, ELM_ICON_NONE, + _copy, data); + if (wd->editable) + elm_hoversel_item_add(wd->hoversel, "Cut", NULL, ELM_ICON_NONE, + _cut, data); + } + elm_hoversel_item_add(wd->hoversel, "Cancel", NULL, ELM_ICON_NONE, + _cancel, data); + } + } + EINA_LIST_FOREACH(wd->items, l, it) + { + elm_hoversel_item_add(wd->hoversel, it->label, it->icon_file, + it->icon_type, _item_clicked, it); + } + if (wd->hoversel) + { + _hoversel_position(data); + evas_object_show(wd->hoversel); + elm_hoversel_hover_begin(wd->hoversel); + } + edje_object_part_text_select_allow_set(wd->ent, "elm.text", 0); + edje_object_part_text_select_abort(wd->ent, "elm.text"); + } + wd->longpress_timer = NULL; + evas_object_smart_callback_call(data, SIG_LONGPRESSED, NULL); + return ECORE_CALLBACK_CANCEL; +} + +static void +_mouse_down(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Down *ev = event_info; + if (!wd) return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return; + if (ev->button != 1) return; + // if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK) + if (wd->longpress_timer) ecore_timer_del(wd->longpress_timer); + wd->longpress_timer = ecore_timer_add(_elm_config->longpress_timeout, _long_press, data); + wd->downx = ev->canvas.x; + wd->downy = ev->canvas.y; +} + +static void +_mouse_up(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Up *ev = event_info; + if (!wd) return; + if (ev->button != 1) return; + if (wd->longpress_timer) + { + ecore_timer_del(wd->longpress_timer); + wd->longpress_timer = NULL; + } +} + +static void +_mouse_move(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Move *ev = event_info; + if (!wd) return; + if (!wd->selmode) + { + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + { + if (wd->longpress_timer) + { + ecore_timer_del(wd->longpress_timer); + wd->longpress_timer = NULL; + } + } + else if (wd->longpress_timer) + { + Evas_Coord dx, dy; + + dx = wd->downx - ev->cur.canvas.x; + dx *= dx; + dy = wd->downy - ev->cur.canvas.y; + dy *= dy; + if ((dx + dy) > + ((_elm_config->finger_size / 2) * + (_elm_config->finger_size / 2))) + { + ecore_timer_del(wd->longpress_timer); + wd->longpress_timer = NULL; + } + } + } + else if (wd->longpress_timer) + { + Evas_Coord dx, dy; + + dx = wd->downx - ev->cur.canvas.x; + dx *= dx; + dy = wd->downy - ev->cur.canvas.y; + dy *= dy; + if ((dx + dy) > + ((_elm_config->finger_size / 2) * + (_elm_config->finger_size / 2))) + { + ecore_timer_del(wd->longpress_timer); + wd->longpress_timer = NULL; + } + } +} + +static const char * +_getbase(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return "base"; + if (wd->editable) + { + if (wd->password) return "base-password"; + else + { + if (wd->single_line) return "base-single"; + else + { + if (wd->linewrap) return "base"; + else if (wd->char_linewrap) return "base-charwrap"; + else return "base-nowrap"; + } + } + } + else + { + if (wd->password) return "base-password"; + else + { + if (wd->single_line) return "base-single-noedit"; + else + { + if (wd->linewrap) return "base-noedit"; + else if (wd->char_linewrap) return "base-noedit-charwrap"; + else return "base-nowrap-noedit"; + } + } + } + return "base"; +} + +static void +_signal_entry_changed(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->changed = EINA_TRUE; + _sizing_eval(data); + if (wd->text) eina_stringshare_del(wd->text); + wd->text = NULL; + evas_object_smart_callback_call(data, SIG_CHANGED, NULL); + if (wd->delay_write) + { + ecore_timer_del(wd->delay_write); + wd->delay_write = NULL; + } + if ((!wd->autosave) || (!wd->file)) return; + wd->delay_write = ecore_timer_add(2.0, _delay_write, data); +} + +static void +_signal_selection_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + const Eina_List *l; + Evas_Object *entry; + if (!wd) return; + EINA_LIST_FOREACH(entries, l, entry) + { + if (entry != data) elm_entry_select_none(entry); + } + wd->have_selection = EINA_TRUE; + evas_object_smart_callback_call(data, SIG_SELECTION_START, NULL); +#ifdef HAVE_ELEMENTARY_X + if (wd->sel_notify_handler) + { + const char *txt = elm_entry_selection_get(data); + Evas_Object *top; + + top = elm_widget_top_get(data); + if ((top) && (elm_win_xwindow_get(top))) + elm_selection_set(ELM_SEL_PRIMARY, data, ELM_SEL_FORMAT_MARKUP, txt); + } +#endif +} + +static void +_signal_selection_changed(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->have_selection = EINA_TRUE; + evas_object_smart_callback_call(data, SIG_SELECTION_CHANGED, NULL); + elm_selection_set(ELM_SEL_PRIMARY, obj, ELM_SEL_FORMAT_MARKUP, + elm_entry_selection_get(data)); +} + +static void +_signal_selection_cleared(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (!wd->have_selection) return; + wd->have_selection = EINA_FALSE; + evas_object_smart_callback_call(data, SIG_SELECTION_CLEARED, NULL); + if (wd->sel_notify_handler) + { + if (wd->cut_sel) + { +#ifdef HAVE_ELEMENTARY_X + Evas_Object *top; + + top = elm_widget_top_get(data); + if ((top) && (elm_win_xwindow_get(top))) + elm_selection_set(ELM_SEL_PRIMARY, data, ELM_SEL_FORMAT_MARKUP, + wd->cut_sel); +#endif + eina_stringshare_del(wd->cut_sel); + wd->cut_sel = NULL; + } + else + { +#ifdef HAVE_ELEMENTARY_X + Evas_Object *top; + + top = elm_widget_top_get(data); + if ((top) && (elm_win_xwindow_get(top))) + elm_selection_clear(ELM_SEL_PRIMARY, data); +#endif + } + } +} + +static void +_signal_entry_paste_request(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_smart_callback_call(data, SIG_SELECTION_PASTE, NULL); + if (wd->sel_notify_handler) + { +#ifdef HAVE_ELEMENTARY_X + Evas_Object *top; + + top = elm_widget_top_get(data); + if ((top) && (elm_win_xwindow_get(top))) + { + wd->selection_asked = EINA_TRUE; + elm_selection_get(ELM_SEL_CLIPBOARD, ELM_SEL_FORMAT_MARKUP, data, + NULL, NULL); + } +#endif + } +} + +static void +_signal_entry_copy_notify(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_smart_callback_call(data, SIG_SELECTION_COPY, NULL); + elm_selection_set(ELM_SEL_CLIPBOARD, obj, ELM_SEL_FORMAT_MARKUP, + elm_entry_selection_get(data)); +} + +static void +_signal_entry_cut_notify(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_smart_callback_call(data, SIG_SELECTION_CUT, NULL); + elm_selection_set(ELM_SEL_CLIPBOARD, obj, ELM_SEL_FORMAT_MARKUP, + elm_entry_selection_get(data)); + edje_object_part_text_insert(wd->ent, "elm.text", ""); + wd->changed = EINA_TRUE; + _sizing_eval(data); +} + +static void +_signal_cursor_changed(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord cx, cy, cw, ch; + if (!wd) return; + evas_object_smart_callback_call(data, SIG_CURSOR_CHANGED, NULL); + edje_object_part_text_cursor_geometry_get(wd->ent, "elm.text", + &cx, &cy, &cw, &ch); + if (!wd->deferred_recalc_job) + elm_widget_show_region_set(data, cx, cy, cw, ch); + else + { + wd->deferred_cur = EINA_TRUE; + wd->cx = cx; + wd->cy = cy; + wd->cw = cw; + wd->ch = ch; + } +} + +static void +_signal_anchor_down(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; +} + +static void +_signal_anchor_up(void *data, Evas_Object *obj __UNUSED__, const char *emission, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + Elm_Entry_Anchor_Info ei; + char *buf2, *p, *p2, *n; + if (!wd) return; + p = strrchr(emission, ','); + if (p) + { + const Eina_List *geoms; + + n = p + 1; + p2 = p -1; + while (p2 >= emission) + { + if (*p2 == ',') break; + p2--; + } + p2++; + buf2 = alloca(5 + p - p2); + strncpy(buf2, p2, p - p2); + buf2[p - p2] = 0; + ei.name = n; + ei.button = atoi(buf2); + ei.x = ei.y = ei.w = ei.h = 0; + geoms = + edje_object_part_text_anchor_geometry_get(wd->ent, "elm.text", ei.name); + if (geoms) + { + Evas_Textblock_Rectangle *r; + const Eina_List *l; + Evas_Coord px, py, x, y; + + evas_object_geometry_get(wd->ent, &x, &y, NULL, NULL); + evas_pointer_output_xy_get(evas_object_evas_get(wd->ent), &px, &py); + EINA_LIST_FOREACH(geoms, l, r) + { + if (((r->x + x) <= px) && ((r->y + y) <= py) && + ((r->x + x + r->w) > px) && ((r->y + y + r->h) > py)) + { + ei.x = r->x + x; + ei.y = r->y + y; + ei.w = r->w; + ei.h = r->h; + break; + } + } + } + if (!wd->disabled) + evas_object_smart_callback_call(data, SIG_ANCHOR_CLICKED, &ei); + } +} + +static void +_signal_anchor_move(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; +} + +static void +_signal_anchor_in(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; +} + +static void +_signal_anchor_out(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; +} + +static void +_signal_key_enter(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_smart_callback_call(data, SIG_ACTIVATED, NULL); +} + +static void +_signal_mouse_down(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_smart_callback_call(data, SIG_PRESS, NULL); +} + +static void +_signal_mouse_clicked(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_smart_callback_call(data, SIG_CLICKED, NULL); +} + +static void +_signal_mouse_double(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_smart_callback_call(data, SIG_CLICKED_DOUBLE, NULL); +} + +#ifdef HAVE_ELEMENTARY_X +static Eina_Bool +_event_selection_notify(void *data, int type __UNUSED__, void *event) +{ + Widget_Data *wd = elm_widget_data_get(data); + Ecore_X_Event_Selection_Notify *ev = event; + if (!wd) return ECORE_CALLBACK_PASS_ON; + if ((!wd->selection_asked) && (!wd->drag_selection_asked)) + return ECORE_CALLBACK_PASS_ON; + + if ((ev->selection == ECORE_X_SELECTION_CLIPBOARD) || + (ev->selection == ECORE_X_SELECTION_PRIMARY)) + { + Ecore_X_Selection_Data_Text *text_data; + + text_data = ev->data; + if (text_data->data.content == ECORE_X_SELECTION_CONTENT_TEXT) + { + if (text_data->text) + { + char *txt = _elm_util_text_to_mkup(text_data->text); + + if (txt) + { + elm_entry_entry_insert(data, txt); + free(txt); + } + } + } + wd->selection_asked = EINA_FALSE; + } + else if (ev->selection == ECORE_X_SELECTION_XDND) + { + Ecore_X_Selection_Data_Text *text_data; + + text_data = ev->data; + if (text_data->data.content == ECORE_X_SELECTION_CONTENT_TEXT) + { + if (text_data->text) + { + char *txt = _elm_util_text_to_mkup(text_data->text); + + if (txt) + { + /* Massive FIXME: this should be at the drag point */ + elm_entry_entry_insert(data, txt); + free(txt); + } + } + } + wd->drag_selection_asked = EINA_FALSE; + + ecore_x_dnd_send_finished(); + + } + return ECORE_CALLBACK_PASS_ON; +} + +static Eina_Bool +_event_selection_clear(void *data __UNUSED__, int type __UNUSED__, void *event __UNUSED__) +{ +/* + Widget_Data *wd = elm_widget_data_get(data); + Ecore_X_Event_Selection_Clear *ev = event; + if (!wd) return ECORE_CALLBACK_PASS_ON; + if (!wd->have_selection) return ECORE_CALLBACK_PASS_ON; + if ((ev->selection == ECORE_X_SELECTION_CLIPBOARD) || + (ev->selection == ECORE_X_SELECTION_PRIMARY)) + { + elm_entry_select_none(data); + } + return 1;*/ + return ECORE_CALLBACK_PASS_ON; +} + + +static Eina_Bool +_drag_drop_cb(void *data __UNUSED__, Evas_Object *obj, Elm_Selection_Data *drop) +{ + Widget_Data *wd; + Eina_Bool rv; + + wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + printf("Inserting at (%d,%d) %s\n",drop->x,drop->y,(char*)drop->data); + + edje_object_part_text_cursor_copy(wd->ent, "elm.text", + EDJE_CURSOR_MAIN,/*->*/EDJE_CURSOR_USER); + rv = edje_object_part_text_cursor_coord_set(wd->ent,"elm.text", + EDJE_CURSOR_MAIN,drop->x,drop->y); + if (!rv) printf("Warning: Failed to position cursor: paste anyway\n"); + elm_entry_entry_insert(obj, drop->data); + edje_object_part_text_cursor_copy(wd->ent, "elm.text", + EDJE_CURSOR_USER,/*->*/EDJE_CURSOR_MAIN); + + return EINA_TRUE; +} +#endif + +static Evas_Object * +_get_item(void *data, Evas_Object *edje __UNUSED__, const char *part __UNUSED__, const char *item) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Object *o; + Eina_List *l; + Elm_Entry_Item_Provider *ip; + + EINA_LIST_FOREACH(wd->item_providers, l, ip) + { + o = ip->func(ip->data, data, item); + if (o) return o; + } + if (!strncmp(item, "file://", 7)) + { + const char *fname = item + 7; + + o = evas_object_image_filled_add(evas_object_evas_get(data)); + evas_object_image_file_set(o, fname, NULL); + if (evas_object_image_load_error_get(o) == EVAS_LOAD_ERROR_NONE) + { + evas_object_show(o); + } + else + { + evas_object_del(o); + o = edje_object_add(evas_object_evas_get(data)); + _elm_theme_object_set(data, o, "entry/emoticon", "wtf", elm_widget_style_get(data)); + } + return o; + } + o = edje_object_add(evas_object_evas_get(data)); + if (!_elm_theme_object_set(data, o, "entry", item, elm_widget_style_get(data))) + _elm_theme_object_set(data, o, "entry/emoticon", "wtf", elm_widget_style_get(data)); + return o; +} + +static void +_text_filter(void *data, Evas_Object *edje __UNUSED__, const char *part __UNUSED__, Edje_Text_Filter_Type type, char **text) +{ + Widget_Data *wd = elm_widget_data_get(data); + Eina_List *l; + Elm_Entry_Text_Filter *tf; + + if (type == EDJE_TEXT_FILTER_FORMAT) + return; + + EINA_LIST_FOREACH(wd->text_filters, l, tf) + { + tf->func(tf->data, data, text); + if (!*text) + break; + } +} + +/** + * This adds an entry to @p parent object. + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Entry + */ +EAPI Evas_Object * +elm_entry_add(Evas_Object *parent) +{ + Evas_Object *obj, *top; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "entry"); + elm_widget_type_set(obj, "entry"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_on_focus_region_hook_set(obj, _on_focus_region_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + elm_object_cursor_set(obj, ELM_CURSOR_XTERM); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_highlight_ignore_set(obj, EINA_TRUE); + + wd->linewrap = EINA_TRUE; + wd->char_linewrap= EINA_FALSE; + wd->editable = EINA_TRUE; + wd->disabled = EINA_FALSE; + wd->context_menu = EINA_TRUE; + wd->autosave = EINA_TRUE; + wd->textonly = EINA_FALSE; + + wd->ent = edje_object_add(e); + edje_object_item_provider_set(wd->ent, _get_item, obj); + edje_object_text_insert_filter_callback_add(wd->ent,"elm.text", _text_filter, obj); + evas_object_event_callback_add(wd->ent, EVAS_CALLBACK_MOVE, _move, obj); + evas_object_event_callback_add(wd->ent, EVAS_CALLBACK_RESIZE, _resize, obj); + evas_object_event_callback_add(wd->ent, EVAS_CALLBACK_MOUSE_DOWN, + _mouse_down, obj); + evas_object_event_callback_add(wd->ent, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, obj); + evas_object_event_callback_add(wd->ent, EVAS_CALLBACK_MOUSE_MOVE, + _mouse_move, obj); + + _elm_theme_object_set(obj, wd->ent, "entry", "base", "default"); + edje_object_signal_callback_add(wd->ent, "entry,changed", "elm.text", + _signal_entry_changed, obj); + edje_object_signal_callback_add(wd->ent, "selection,start", "elm.text", + _signal_selection_start, obj); + edje_object_signal_callback_add(wd->ent, "selection,changed", "elm.text", + _signal_selection_changed, obj); + edje_object_signal_callback_add(wd->ent, "selection,cleared", "elm.text", + _signal_selection_cleared, obj); + edje_object_signal_callback_add(wd->ent, "entry,paste,request", "elm.text", + _signal_entry_paste_request, obj); + edje_object_signal_callback_add(wd->ent, "entry,copy,notify", "elm.text", + _signal_entry_copy_notify, obj); + edje_object_signal_callback_add(wd->ent, "entry,cut,notify", "elm.text", + _signal_entry_cut_notify, obj); + edje_object_signal_callback_add(wd->ent, "cursor,changed", "elm.text", + _signal_cursor_changed, obj); + edje_object_signal_callback_add(wd->ent, "anchor,mouse,down,*", "elm.text", + _signal_anchor_down, obj); + edje_object_signal_callback_add(wd->ent, "anchor,mouse,up,*", "elm.text", + _signal_anchor_up, obj); + edje_object_signal_callback_add(wd->ent, "anchor,mouse,move,*", "elm.text", + _signal_anchor_move, obj); + edje_object_signal_callback_add(wd->ent, "anchor,mouse,in,*", "elm.text", + _signal_anchor_in, obj); + edje_object_signal_callback_add(wd->ent, "anchor,mouse,out,*", "elm.text", + _signal_anchor_out, obj); + edje_object_signal_callback_add(wd->ent, "entry,key,enter", "elm.text", + _signal_key_enter, obj); + edje_object_signal_callback_add(wd->ent, "mouse,down,1", "elm.text", + _signal_mouse_down, obj); + edje_object_signal_callback_add(wd->ent, "mouse,clicked,1", "elm.text", + _signal_mouse_clicked, obj); + edje_object_signal_callback_add(wd->ent, "mouse,down,1,double", "elm.text", + _signal_mouse_double, obj); + edje_object_part_text_set(wd->ent, "elm.text", ""); + elm_widget_resize_object_set(obj, wd->ent); + _sizing_eval(obj); + +#ifdef HAVE_ELEMENTARY_X + top = elm_widget_top_get(obj); + if ((top) && (elm_win_xwindow_get(top))) + { + wd->sel_notify_handler = + ecore_event_handler_add(ECORE_X_EVENT_SELECTION_NOTIFY, + _event_selection_notify, obj); + wd->sel_clear_handler = + ecore_event_handler_add(ECORE_X_EVENT_SELECTION_CLEAR, + _event_selection_clear, obj); + } + + elm_drop_target_add(obj, ELM_SEL_FORMAT_MARKUP | ELM_SEL_FORMAT_IMAGE, + _drag_drop_cb, NULL); +#endif + + entries = eina_list_prepend(entries, obj); + + // module - find module for entry + wd->api = _module(obj); + // if found - hook in + if ((wd->api) && (wd->api->obj_hook)) wd->api->obj_hook(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + + +/** + * This sets the entry object not to line wrap. All input will + * be on a single line, and the entry box will extend with user input. + * + * @param obj The entry object + * @param single_line If true, the text in the entry + * will be on a single line. + * + * @ingroup Entry + */ +EAPI void +elm_entry_single_line_set(Evas_Object *obj, Eina_Bool single_line) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + const char *t; + if (!wd) return; + if (wd->single_line == single_line) return; + wd->single_line = single_line; + wd->linewrap = EINA_FALSE; + wd->char_linewrap = EINA_FALSE; + elm_entry_cnp_textonly_set(obj, EINA_TRUE); + t = eina_stringshare_add(elm_entry_entry_get(obj)); + _elm_theme_object_set(obj, wd->ent, "entry", _getbase(obj), elm_widget_style_get(obj)); + elm_entry_entry_set(obj, t); + eina_stringshare_del(t); + _sizing_eval(obj); +} + +/** + * This returns true if the entry has been set to single line mode. + * See also elm_entry_single_line_set(). + * + * @param obj The entry object + * @return single_line If true, the text in the entry is set to display + * on a single line. + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_single_line_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->single_line; +} + +/** + * This sets the entry object to password mode. All text entered + * and/or displayed within the widget will be replaced with asterisks (*). + * + * @param obj The entry object + * @param password If true, password mode is enabled. + * + * @ingroup Entry + */ +EAPI void +elm_entry_password_set(Evas_Object *obj, Eina_Bool password) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + const char *t; + if (!wd) return; + if (wd->password == password) return; + wd->password = password; + wd->single_line = EINA_TRUE; + wd->linewrap = EINA_FALSE; + wd->char_linewrap = EINA_FALSE; + t = eina_stringshare_add(elm_entry_entry_get(obj)); + _elm_theme_object_set(obj, wd->ent, "entry", _getbase(obj), elm_widget_style_get(obj)); + elm_entry_entry_set(obj, t); + eina_stringshare_del(t); + _sizing_eval(obj); +} + + +/** + * This returns whether password mode is enabled. + * See also elm_entry_password_set(). + * + * @param obj The entry object + * @return If true, the entry is set to display all characters + * as asterisks (*). + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_password_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->password; +} + +/** + * This sets the text displayed within the entry to @p entry. + * + * @param obj The entry object + * @param entry The text to be displayed + * + * @ingroup Entry + */ +EAPI void +elm_entry_entry_set(Evas_Object *obj, const char *entry) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (!entry) entry = ""; + edje_object_part_text_set(wd->ent, "elm.text", entry); + if (wd->text) eina_stringshare_del(wd->text); + wd->text = NULL; + wd->changed = EINA_TRUE; + _sizing_eval(obj); +} + +/** + * This returns the text currently shown in object @p entry. + * See also elm_entry_entry_set(). + * + * @param obj The entry object + * @return The currently displayed text or NULL on failure + * + * @ingroup Entry + */ +EAPI const char * +elm_entry_entry_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + const char *text; + if (!wd) return NULL; + if (wd->text) return wd->text; + text = edje_object_part_text_get(wd->ent, "elm.text"); + if (!text) + { + ERR("text=NULL for edje %p, part 'elm.text'", wd->ent); + return NULL; + } + eina_stringshare_replace(&wd->text, text); + return wd->text; +} + + +/** + * This returns EINA_TRUE if the entry is empty/there was an error + * and EINA_FALSE if it is not empty. + * + * @param obj The entry object + * @return If the entry is empty or not. + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_is_empty(const Evas_Object *obj) +{ + /* FIXME: until there's support for that in textblock, we just check + * to see if the there is text or not. */ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_TRUE; + Widget_Data *wd = elm_widget_data_get(obj); + const Evas_Object *tb; + Evas_Textblock_Cursor *cur; + Eina_Bool ret; + if (!wd) return EINA_TRUE; + /* It's a hack until we get the support suggested above. + * We just create a cursor, point it to the begining, and then + * try to advance it, if it can advance, the tb is not empty, + * otherwise it is. */ + tb = edje_object_part_object_get(wd->ent, "elm.text"); + cur = evas_object_textblock_cursor_new((Evas_Object *) tb); /* This is + actually, ok for the time being, thsese hackish stuff will be removed + once evas 1.0 is out*/ + evas_textblock_cursor_pos_set(cur, 0); + ret = evas_textblock_cursor_char_next(cur); + evas_textblock_cursor_free(cur); + + return !ret; +} + +/** + * This returns all selected text within the entry. + * + * @param obj The entry object + * @return The selected text within the entry or NULL on failure + * + * @ingroup Entry + */ +EAPI const char * +elm_entry_selection_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return edje_object_part_text_selection_get(wd->ent, "elm.text"); +} + +/** + * This inserts text in @p entry where the current cursor position. + * + * This inserts text at the cursor position is as if it was typed + * by the user (note this also allows markup which a user + * can't just "type" as it would be converted to escaped text, so this + * call can be used to insert things like emoticon items or bold push/pop + * tags, other font and color change tags etc.) + * + * @param obj The entry object + * @param entry The text to insert + * + * @ingroup Entry + */ +EAPI void +elm_entry_entry_insert(Evas_Object *obj, const char *entry) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_part_text_insert(wd->ent, "elm.text", entry); + wd->changed = EINA_TRUE; + _sizing_eval(obj); +} + +/** + * This enables word line wrapping in the entry object. It is the opposite + * of elm_entry_single_line_set(). Additionally, setting this disables + * character line wrapping. + * See also elm_entry_line_char_wrap_set(). + * + * @param obj The entry object + * @param wrap If true, the entry will be wrapped once it reaches the end + * of the object. Wrapping will occur at the end of the word before the end of the + * object. + * + * @ingroup Entry + */ +EAPI void +elm_entry_line_wrap_set(Evas_Object *obj, Eina_Bool wrap) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + const char *t; + if (!wd) return; + if (wd->linewrap == wrap) return; + wd->linewrap = wrap; + if(wd->linewrap) + wd->char_linewrap = EINA_FALSE; + t = eina_stringshare_add(elm_entry_entry_get(obj)); + _elm_theme_object_set(obj, wd->ent, "entry", _getbase(obj), elm_widget_style_get(obj)); + elm_entry_entry_set(obj, t); + eina_stringshare_del(t); + _sizing_eval(obj); +} + +/** + * This enables character line wrapping in the entry object. It is the opposite + * of elm_entry_single_line_set(). Additionally, setting this disables + * word line wrapping. + * See also elm_entry_line_wrap_set(). + * + * @param obj The entry object + * @param wrap If true, the entry will be wrapped once it reaches the end + * of the object. Wrapping will occur immediately upon reaching the end of the object. + * + * @ingroup Entry + */ +EAPI void +elm_entry_line_char_wrap_set(Evas_Object *obj, Eina_Bool wrap) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + const char *t; + if (!wd) return; + if (wd->char_linewrap == wrap) return; + wd->char_linewrap = wrap; + if(wd->char_linewrap) + wd->linewrap = EINA_FALSE; + t = eina_stringshare_add(elm_entry_entry_get(obj)); + _elm_theme_object_set(obj, wd->ent, "entry", _getbase(obj), elm_widget_style_get(obj)); + elm_entry_entry_set(obj, t); + eina_stringshare_del(t); + _sizing_eval(obj); +} + +/** + * This sets the editable attribute of the entry. + * + * @param obj The entry object + * @param editable If true, the entry will be editable by the user. + * If false, it will be set to the disabled state. + * + * @ingroup Entry + */ +EAPI void +elm_entry_editable_set(Evas_Object *obj, Eina_Bool editable) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + const char *t; + if (!wd) return; + if (wd->editable == editable) return; + wd->editable = editable; + t = eina_stringshare_add(elm_entry_entry_get(obj)); + _elm_theme_object_set(obj, wd->ent, "entry", _getbase(obj), elm_widget_style_get(obj)); + elm_entry_entry_set(obj, t); + eina_stringshare_del(t); + _sizing_eval(obj); + +#ifdef HAVE_ELEMENTARY_X + if (editable) + elm_drop_target_add(obj, ELM_SEL_FORMAT_MARKUP, _drag_drop_cb, NULL); + else + elm_drop_target_del(obj); +#endif +} + +/** + * This gets the editable attribute of the entry. + * See also elm_entry_editable_set(). + * + * @param obj The entry object + * @return If true, the entry is editable by the user. + * If false, it is not editable by the user + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_editable_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->editable; +} + +/** + * This drops any existing text selection within the entry. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_select_none(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->selmode) + { + wd->selmode = EINA_FALSE; + edje_object_part_text_select_allow_set(wd->ent, "elm.text", 0); + edje_object_signal_emit(wd->ent, "elm,state,select,off", "elm"); + } + wd->have_selection = EINA_FALSE; + edje_object_part_text_select_none(wd->ent, "elm.text"); +} + +/** + * This selects all text within the entry. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_select_all(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->selmode) + { + wd->selmode = EINA_FALSE; + edje_object_part_text_select_allow_set(wd->ent, "elm.text", 0); + edje_object_signal_emit(wd->ent, "elm,state,select,off", "elm"); + } + wd->have_selection = EINA_TRUE; + edje_object_part_text_select_all(wd->ent, "elm.text"); +} + +/** + * This function returns the geometry of the cursor. + * + * It's useful if you want to draw something on the cursor (or where it is), + * or for example in the case of scrolled entry where you want to show the + * cursor. + * + * @param obj The entry object + * @param x returned geometry + * @param y returned geometry + * @param w returned geometry + * @param h returned geometry + * @return EINA_TRUE upon success, EINA_FALSE upon failure + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_cursor_geometry_get(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + edje_object_part_text_cursor_geometry_get(wd->ent, "elm.text", x, y, w, h); + return EINA_TRUE; +} + +/** + * This moves the cursor one place to the right within the entry. + * + * @param obj The entry object + * @return EINA_TRUE upon success, EINA_FALSE upon failure + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_cursor_next(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return edje_object_part_text_cursor_next(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This moves the cursor one place to the left within the entry. + * + * @param obj The entry object + * @return EINA_TRUE upon success, EINA_FALSE upon failure + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_cursor_prev(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return edje_object_part_text_cursor_prev(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This moves the cursor one line up within the entry. + * + * @param obj The entry object + * @return EINA_TRUE upon success, EINA_FALSE upon failure + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_cursor_up(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return edje_object_part_text_cursor_up(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This moves the cursor one line down within the entry. + * + * @param obj The entry object + * @return EINA_TRUE upon success, EINA_FALSE upon failure + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_cursor_down(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return edje_object_part_text_cursor_down(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This moves the cursor to the beginning of the entry. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_cursor_begin_set(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_part_text_cursor_begin_set(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This moves the cursor to the end of the entry. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_cursor_end_set(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_part_text_cursor_end_set(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This moves the cursor to the beginning of the current line. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_cursor_line_begin_set(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_part_text_cursor_line_begin_set(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This moves the cursor to the end of the current line. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_cursor_line_end_set(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_part_text_cursor_line_end_set(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This begins a selection within the entry as though + * the user were holding down the mouse button to make a selection. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_cursor_selection_begin(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_part_text_select_begin(wd->ent, "elm.text"); +} + +/** + * This ends a selection within the entry as though + * the user had just released the mouse button while making a selection. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_cursor_selection_end(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_part_text_select_extend(wd->ent, "elm.text"); +} + +/** + * TODO: fill this in + * + * @param obj The entry object + * @return TODO: fill this in + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_cursor_is_format_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return edje_object_part_text_cursor_is_format_get(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This returns whether the cursor is visible. + * + * @param obj The entry object + * @return If true, the cursor is visible. + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_cursor_is_visible_format_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return edje_object_part_text_cursor_is_visible_format_get(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * TODO: fill this in + * + * @param obj The entry object + * @return TODO: fill this in + * + * @ingroup Entry + */ +EAPI const char * +elm_entry_cursor_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return edje_object_part_text_cursor_content_get(wd->ent, "elm.text", EDJE_CURSOR_MAIN); +} + +/** + * This executes a "cut" action on the selected text in the entry. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_selection_cut(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _cut(obj, NULL, NULL); +} + +/** + * This executes a "copy" action on the selected text in the entry. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_selection_copy(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _copy(obj, NULL, NULL); +} + +/** + * This executes a "paste" action in the entry. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_selection_paste(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _paste(obj, NULL, NULL); +} + +/** + * This clears and frees the items in a entry's contextual (right click) menu. + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_context_menu_clear(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Entry_Context_Menu_Item *it; + if (!wd) return; + EINA_LIST_FREE(wd->items, it) + { + eina_stringshare_del(it->label); + eina_stringshare_del(it->icon_file); + eina_stringshare_del(it->icon_group); + free(it); + } +} + +/** + * This adds an item to the entry's contextual menu. + * + * @param obj The entry object + * @param label The item's text label + * @param icon_file The item's icon file + * @param icon_type The item's icon type + * @param func The callback to execute when the item is clicked + * @param data The data to associate with the item for related functions + * + * @ingroup Entry + */ +EAPI void +elm_entry_context_menu_item_add(Evas_Object *obj, const char *label, const char *icon_file, Elm_Icon_Type icon_type, Evas_Smart_Cb func, const void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Entry_Context_Menu_Item *it; + if (!wd) return; + it = calloc(1, sizeof(Elm_Entry_Context_Menu_Item)); + if (!it) return; + wd->items = eina_list_append(wd->items, it); + it->obj = obj; + it->label = eina_stringshare_add(label); + it->icon_file = eina_stringshare_add(icon_file); + it->icon_type = icon_type; + it->func = func; + it->data = (void *)data; +} + +/** + * This disables the entry's contextual (right click) menu. + * + * @param obj The entry object + * @param disabled If true, the menu is disabled + * + * @ingroup Entry + */ +EAPI void +elm_entry_context_menu_disabled_set(Evas_Object *obj, Eina_Bool disabled) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->context_menu == !disabled) return; + wd->context_menu = !disabled; +} + +/** + * This returns whether the entry's contextual (right click) menu is disabled. + * + * @param obj The entry object + * @return If true, the menu is disabled + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_context_menu_disabled_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return !wd->context_menu; +} + +/** + * This appends a custom item provider to the list for that entry + * + * This appends the given callback. The list is walked from beginning to end + * with each function called given the item href string in the text. If the + * function returns an object handle other than NULL (it should create an + * and object to do this), then this object is used to replace that item. If + * not the next provider is called until one provides an item object, or the + * default provider in entry does. + * + * @param obj The entry object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Entry + */ +EAPI void +elm_entry_item_provider_append(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + Elm_Entry_Item_Provider *ip = calloc(1, sizeof(Elm_Entry_Item_Provider)); + if (!ip) return; + ip->func = func; + ip->data = data; + wd->item_providers = eina_list_append(wd->item_providers, ip); +} + +/** + * This prepends a custom item provider to the list for that entry + * + * This prepends the given callback. See elm_entry_item_provider_append() for + * more information + * + * @param obj The entry object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Entry + */ +EAPI void +elm_entry_item_provider_prepend(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + Elm_Entry_Item_Provider *ip = calloc(1, sizeof(Elm_Entry_Item_Provider)); + if (!ip) return; + ip->func = func; + ip->data = data; + wd->item_providers = eina_list_prepend(wd->item_providers, ip); +} + +/** + * This removes a custom item provider to the list for that entry + * + * This removes the given callback. See elm_entry_item_provider_append() for + * more information + * + * @param obj The entry object + * @param func The function called to provide the item object + * @param data The data passed to @p func + * + * @ingroup Entry + */ +EAPI void +elm_entry_item_provider_remove(Evas_Object *obj, Evas_Object *(*func) (void *data, Evas_Object *entry, const char *item), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Elm_Entry_Item_Provider *ip; + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(func); + EINA_LIST_FOREACH(wd->item_providers, l, ip) + { + if ((ip->func == func) && (ip->data == data)) + { + wd->item_providers = eina_list_remove_list(wd->item_providers, l); + free(ip); + return; + } + } +} + +/** + * Append a filter function for text inserted in the entry + * + * Append the given callback to the list. This functions will be called + * whenever any text is inserted into the entry, with the text to be inserted + * as a parameter. The callback function is free to alter the text in any way + * it wants, but it must remember to free the given pointer and update it. + * If the new text is to be discarded, the function can free it and set it text + * parameter to NULL. This will also prevent any following filters from being + * called. + * + * @param obj The entry object + * @param func The function to use as text filter + * @param data User data to pass to @p func + * + * @ingroup Entry + */ +EAPI void +elm_entry_text_filter_append(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) +{ + Widget_Data *wd; + Elm_Entry_Text_Filter *tf; + ELM_CHECK_WIDTYPE(obj, widtype); + + wd = elm_widget_data_get(obj); + + EINA_SAFETY_ON_NULL_RETURN(func); + + tf = ELM_NEW(Elm_Entry_Text_Filter); + if (!tf) return; + tf->func = func; + tf->data = data; + wd->text_filters = eina_list_append(wd->text_filters, tf); +} + +/** + * Prepend a filter function for text insdrted in the entry + * + * Prepend the given callback to the list. See elm_entry_text_filter_append() + * for more information + * + * @param obj The entry object + * @param func The function to use as text filter + * @param data User data to pass to @p func + * + * @ingroup Entry + */ +EAPI void +elm_entry_text_filter_prepend(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) +{ + Widget_Data *wd; + Elm_Entry_Text_Filter *tf; + ELM_CHECK_WIDTYPE(obj, widtype); + + wd = elm_widget_data_get(obj); + + EINA_SAFETY_ON_NULL_RETURN(func); + + tf = ELM_NEW(Elm_Entry_Text_Filter); + if (!tf) return; + tf->func = func; + tf->data = data; + wd->text_filters = eina_list_prepend(wd->text_filters, tf); +} + +/** + * Remove a filter from the list + * + * Removes the given callback from the filter list. See elm_entry_text_filter_append() + * for more information. + * + * @param obj The entry object + * @param func The filter function to remove + * @param data The user data passed when adding the function + * + * @ingroup Entry + */ +EAPI void +elm_entry_text_filter_remove(Evas_Object *obj, void (*func) (void *data, Evas_Object *entry, char **text), void *data) +{ + Widget_Data *wd; + Eina_List *l; + Elm_Entry_Text_Filter *tf; + ELM_CHECK_WIDTYPE(obj, widtype); + + wd = elm_widget_data_get(obj); + + EINA_SAFETY_ON_NULL_RETURN(func); + + EINA_LIST_FOREACH(wd->text_filters, l, tf) + { + if ((tf->func == func) && (tf->data == data)) + { + wd->text_filters = eina_list_remove_list(wd->text_filters, l); + free(tf); + return; + } + } +} + +/** + * This converts a markup (HTML-like) string into UTF-8. + * + * @param s The string (in markup) to be converted + * @return The converted string (in UTF-8) + * + * @ingroup Entry + */ +EAPI char * +elm_entry_markup_to_utf8(const char *s) +{ + char *ss = _elm_util_mkup_to_text(s); + if (!ss) ss = strdup(""); + return ss; +} + +/** + * This converts a UTF-8 string into markup (HTML-like). + * + * @param s The string (in UTF-8) to be converted + * @return The converted string (in markup) + * + * @ingroup Entry + */ +EAPI char * +elm_entry_utf8_to_markup(const char *s) +{ + char *ss = _elm_util_text_to_mkup(s); + if (!ss) ss = strdup(""); + return ss; +} + +/** + * Filter inserted text based on user defined character and byte limits + * + * Add this filter to an entry to limit the characters that it will accept + * based the the contents of the provided Elm_Entry_Filter_Limit_Size. + * The funtion works on the UTF-8 representation of the string, converting + * it from the set markup, thus not accounting for any format in it. + * + * The user must create an Elm_Entry_Filter_Limit_Size structure and pass + * it as data when setting the filter. In it it's possible to set limits + * by character count or bytes (any of them is disabled if 0), and both can + * be set at the same time. In that case, it first checks for characters, + * then bytes. + * + * The function will cut the inserted text in order to allow only the first + * number of characters that are still allowed. The cut is made in + * characters, even when limiting by bytes, in order to always contain + * valid ones and avoid half unicode characters making it in. + * + * @ingroup Entry + */ +EAPI void +elm_entry_filter_limit_size(void *data, Evas_Object *entry, char **text) +{ + Elm_Entry_Filter_Limit_Size *lim = data; + char *current; + int len, newlen; + const char *(*text_get)(const Evas_Object *); + const char *widget_type; + + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(entry); + EINA_SAFETY_ON_NULL_RETURN(text); + + /* hack. I don't want to copy the entire function to work with + * scrolled_entry */ + widget_type = elm_widget_type_get(entry); + if (!strcmp(widget_type, "entry")) + text_get = elm_entry_entry_get; + else if (!strcmp(widget_type, "scrolled_entry")) + text_get = elm_scrolled_entry_entry_get; + else /* huh? */ + return; + + current = elm_entry_markup_to_utf8(text_get(entry)); + + if (lim->max_char_count > 0) + { + int cut; + len = evas_string_char_len_get(current); + if (len >= lim->max_char_count) + { + free(*text); + free(current); + *text = NULL; + return; + } + newlen = evas_string_char_len_get(*text); + cut = strlen(*text); + while ((len + newlen) > lim->max_char_count) + { + cut = evas_string_char_prev_get(*text, cut, NULL); + newlen--; + } + (*text)[cut] = 0; + } + + if (lim->max_byte_count > 0) + { + len = strlen(current); + if (len >= lim->max_byte_count) + { + free(*text); + free(current); + *text = NULL; + return; + } + newlen = strlen(*text); + while ((len + newlen) > lim->max_byte_count) + { + int p = evas_string_char_prev_get(*text, newlen, NULL); + newlen -= (newlen - p); + } + if (newlen) + (*text)[newlen] = 0; + else + { + free(*text); + *text = NULL; + } + } + free(current); +} + +/** + * Filter inserted text based on accepted or rejected sets of characters + * + * Add this filter to an entry to restrict the set of accepted characters + * based on the sets in the provided Elm_Entry_Filter_Accept_Set. + * This structure contains both accepted and rejected sets, but they are + * mutually exclusive. If accepted is set, it will be used, otherwise it + * goes on to the rejected set. + */ +EAPI void +elm_entry_filter_accept_set(void *data, Evas_Object *entry __UNUSED__, char **text) +{ + Elm_Entry_Filter_Accept_Set *as = data; + const char *set; + char *insert; + Eina_Bool goes_in; + int read_idx, last_read_idx = 0, read_char; + + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(text); + + if ((!as->accepted) && (!as->rejected)) + return; + + if (as->accepted) + { + set = as->accepted; + goes_in = EINA_TRUE; + } + else + { + set = as->rejected; + goes_in = EINA_FALSE; + } + + insert = *text; + read_idx = evas_string_char_next_get(*text, 0, &read_char); + while (read_char) + { + int cmp_idx, cmp_char; + Eina_Bool in_set = EINA_FALSE; + + cmp_idx = evas_string_char_next_get(set, 0, &cmp_char); + while (cmp_char) + { + if (read_char == cmp_char) + { + in_set = EINA_TRUE; + break; + } + cmp_idx = evas_string_char_next_get(set, cmp_idx, &cmp_char); + } + if (in_set == goes_in) + { + int size = read_idx - last_read_idx; + const char *src = (*text) + last_read_idx; + if (src != insert) + memcpy(insert, *text + last_read_idx, size); + insert += size; + } + last_read_idx = read_idx; + read_idx = evas_string_char_next_get(*text, read_idx, &read_char); + } + *insert = 0; +} + +/** + * This sets the file (and implicitly loads it) for the text to display and + * then edit. All changes are written back to the file after a short delay if + * the entry object is set to autosave. + * + * @param obj The entry object + * @param file The path to the file to load and save + * @param format The file format + * + * @ingroup Entry + */ +EAPI void +elm_entry_file_set(Evas_Object *obj, const char *file, Elm_Text_Format format) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->delay_write) + { + ecore_timer_del(wd->delay_write); + wd->delay_write = NULL; + } + if (wd->autosave) _save(obj); + eina_stringshare_replace(&wd->file, file); + wd->format = format; + _load(obj); +} + +/** + * Gets the file to load and save and the file format + * + * @param obj The entry object + * @param file The path to the file to load and save + * @param format The file format + * + * @ingroup Entry + */ +EAPI void +elm_entry_file_get(const Evas_Object *obj, const char **file, Elm_Text_Format *format) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (file) *file = wd->file; + if (format) *format = wd->format; +} + +/** + * This function writes any changes made to the file set with + * elm_entry_file_set() + * + * @param obj The entry object + * + * @ingroup Entry + */ +EAPI void +elm_entry_file_save(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->delay_write) + { + ecore_timer_del(wd->delay_write); + wd->delay_write = NULL; + } + _save(obj); + wd->delay_write = ecore_timer_add(2.0, _delay_write, obj); +} + +/** + * This sets the entry object to 'autosave' the loaded text file or not. + * + * @param obj The entry object + * @param autosave Autosave the loaded file or not + * + * @ingroup Entry + */ +EAPI void +elm_entry_autosave_set(Evas_Object *obj, Eina_Bool autosave) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->autosave = !!autosave; +} + +/** + * This gets the entry object's 'autosave' status. + * + * @param obj The entry object + * @return Autosave the loaded file or not + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_autosave_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->autosave; +} + + +/** + * Control pasting of text and images for the widget. + * + * Normally the entry allows both text and images to be pasted. By setting + * textonly to be true, this prevents images from being pasted. + * + * Note this only changes the behaviour of text. + * + * @param obj The entry object + * @param pmode paste mode - 0 is text only, 1 is text+image+other. + * + * @ingroup Entry + */ +EAPI void +elm_entry_cnp_textonly_set(Evas_Object *obj, Eina_Bool textonly) +{ + Elm_Sel_Format format = ELM_SEL_FORMAT_MARKUP; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + textonly = !!textonly; + if (wd->textonly == textonly) return; + wd->textonly = !!textonly; + if (!textonly) format |= ELM_SEL_FORMAT_IMAGE; + elm_drop_target_add(obj, format, _drag_drop_cb, NULL); +} + +/** + * Getting elm_entry text paste/drop mode. + * + * In textonly mode, only text may be pasted or dropped into the widget. + * + * @param obj The entry object + * @return If the widget only accepts text from pastes. + * + * @ingroup Entry + */ +EAPI Eina_Bool +elm_entry_cnp_textonly_get(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->textonly; +} + diff --git a/src/lib/elm_flip.c b/src/lib/elm_flip.c new file mode 100644 index 0000000..7375984 --- /dev/null +++ b/src/lib/elm_flip.c @@ -0,0 +1,700 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Flip Flip + * + * This holds 2 content objects: one on the front and one on the back. It + * allows you to flip from front to back and vice-versa using various effects. + * + * Supported flip types: + * ELM_FLIP_ROTATE_Y_CENTER_AXIS + * ELM_FLIP_ROTATE_X_CENTER_AXIS + * ELM_FLIP_ROTATE_XZ_CENTER_AXIS + * ELM_FLIP_ROTATE_YZ_CENTER_AXIS + * + * Signals that you can add callbacks for are: + * + * "animate,done" - when a flip animation is finished + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Ecore_Animator *animator; + double start, len; + Elm_Flip_Mode mode; + Evas_Object *clip; + struct { + Evas_Object *content, *clip; + } front, back; + Eina_Bool state : 1; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); + +static void _configure(Evas_Object *obj); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->animator) ecore_animator_del(wd->animator); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _sizing_eval(obj); +} + +static Eina_Bool +_elm_flip_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return EINA_FALSE; + + /* Try Focus cycle in subitem */ + if (wd->state) + return elm_widget_focus_next_get(wd->front.content, dir, next); + else + return elm_widget_focus_next_get(wd->back.content, dir, next); + +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, minw2 = -1, minh2 = -1; + Evas_Coord maxw = -1, maxh = -1, maxw2 = -1, maxh2 = -1; + if (!wd) return; + if (wd->front.content) + evas_object_size_hint_min_get(wd->front.content, &minw, &minh); + if (wd->back.content) + evas_object_size_hint_min_get(wd->back.content, &minw2, &minh2); + if (wd->front.content) + evas_object_size_hint_max_get(wd->front.content, &maxw, &maxh); + if (wd->back.content) + evas_object_size_hint_max_get(wd->back.content, &maxw2, &maxh2); + + if (minw2 > minw) minw = minw2; + if (minh2 > minh) minh = minh2; + if ((maxw2 >= 0) && (maxw2 < maxw)) maxw = maxw2; + if ((maxh2 >= 0) && (maxh2 < maxh)) maxh = maxh2; + + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->front.content) + { + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->front.content = NULL; + evas_object_hide(wd->front.clip); + _sizing_eval(obj); + } + else if (sub == wd->back.content) + { + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->back.content = NULL; + evas_object_hide(wd->back.clip); + _sizing_eval(obj); + } +} + +static void +flip_show_hide(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (elm_flip_front_get(obj)) + { + if (wd->front.content) + evas_object_show(wd->front.clip); + else + evas_object_hide(wd->front.clip); + if (wd->back.content) + evas_object_hide(wd->back.clip); + else + evas_object_hide(wd->back.clip); + } + else + { + if (wd->front.content) + evas_object_hide(wd->front.clip); + else + evas_object_hide(wd->front.clip); + if (wd->back.content) + evas_object_show(wd->back.clip); + else + evas_object_hide(wd->back.clip); + } +} + +static Eina_Bool +_flip(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + double t = ecore_loop_time_get() - wd->start; + Evas_Coord x, y, w, h; + double p, deg; + Evas_Map *mf, *mb; + Evas_Coord cx, cy, px, py, foc; + int lx, ly, lz, lr, lg, lb, lar, lag, lab; + if (!wd->animator) return ECORE_CALLBACK_CANCEL; + t = t / wd->len; + if (t > 1.0) t = 1.0; + + if (!wd) return ECORE_CALLBACK_CANCEL; + + mf = evas_map_new(4); + evas_map_smooth_set(mf, 0); + mb = evas_map_new(4); + evas_map_smooth_set(mb, 0); + + if (wd->front.content) + { + evas_object_geometry_get(wd->front.content, &x, &y, &w, &h); + evas_map_util_points_populate_from_geometry(mf, x, y, w, h, 0); + } + if (wd->back.content) + { + evas_object_geometry_get(wd->back.content, &x, &y, &w, &h); + evas_map_util_points_populate_from_geometry(mb, x, y, w, h, 0); + } + + evas_object_geometry_get(obj, &x, &y, &w, &h); + + cx = x + (w / 2); + cy = y + (h / 2); + + px = x + (w / 2); + py = y + (h / 2); + foc = 2048; + + lx = cx; + ly = cy; + lz = -10000; + lr = 255; + lg = 255; + lb = 255; + lar = 0; + lag = 0; + lab = 0; + + switch (wd->mode) + { + case ELM_FLIP_ROTATE_Y_CENTER_AXIS: + p = 1.0 - t; + p = 1.0 - (p * p); + if (wd->state) deg = 180.0 * p; + else deg = 180 + (180.0 * p); + evas_map_util_3d_rotate(mf, 0.0, deg, 0.0, cx, cy, 0); + evas_map_util_3d_rotate(mb, 0.0, deg + 180.0, 0.0, cx, cy, 0); + break; + case ELM_FLIP_ROTATE_X_CENTER_AXIS: + p = 1.0 - t; + p = 1.0 - (p * p); + if (wd->state) deg = 180.0 * p; + else deg = 180 + (180.0 * p); + evas_map_util_3d_rotate(mf, deg, 0.0, 0.0, cx, cy, 0); + evas_map_util_3d_rotate(mb, deg + 180.0, 0.0, 0.0, cx, cy, 0); + break; + case ELM_FLIP_ROTATE_XZ_CENTER_AXIS: + p = 1.0 - t; + p = 1.0 - (p * p); + if (wd->state) deg = 180.0 * p; + else deg = 180 + (180.0 * p); + evas_map_util_3d_rotate(mf, deg, 0.0, deg, cx, cy, 0); + evas_map_util_3d_rotate(mb, deg + 180.0, 0.0, deg + 180.0, cx, cy, 0); + break; + case ELM_FLIP_ROTATE_YZ_CENTER_AXIS: + p = 1.0 - t; + p = 1.0 - (p * p); + if (wd->state) deg = 180.0 * p; + else deg = 180 + (180.0 * p); + evas_map_util_3d_rotate(mf, 0.0, deg, deg, cx, cy, 0); + evas_map_util_3d_rotate(mb, 0.0, deg + 180.0, deg + 180.0, cx, cy, 0); + break; + case ELM_FLIP_CUBE_LEFT: + p = 1.0 - t; + p = 1.0 - (p * p); + deg = -90.0 * p; + if (wd->state) + { + evas_map_util_3d_rotate(mf, 0.0, deg, 0.0, cx, cy, w / 2); + evas_map_util_3d_rotate(mb, 0.0, deg + 90, 0.0, cx, cy, w / 2); + } + else + { + evas_map_util_3d_rotate(mf, 0.0, deg + 90, 0.0, cx, cy, w / 2); + evas_map_util_3d_rotate(mb, 0.0, deg, 0.0, cx, cy, w / 2); + } + break; + case ELM_FLIP_CUBE_RIGHT: + p = 1.0 - t; + p = 1.0 - (p * p); + deg = 90.0 * p; + if (wd->state) + { + evas_map_util_3d_rotate(mf, 0.0, deg, 0.0, cx, cy, w / 2); + evas_map_util_3d_rotate(mb, 0.0, deg - 90, 0.0, cx, cy, w / 2); + } + else + { + evas_map_util_3d_rotate(mf, 0.0, deg - 90, 0.0, cx, cy, w / 2); + evas_map_util_3d_rotate(mb, 0.0, deg, 0.0, cx, cy, w / 2); + } + break; + case ELM_FLIP_CUBE_UP: + p = 1.0 - t; + p = 1.0 - (p * p); + deg = -90.0 * p; + if (wd->state) + { + evas_map_util_3d_rotate(mf, deg, 0.0, 0.0, cx, cy, h / 2); + evas_map_util_3d_rotate(mb, deg + 90, 0.0, 0.0, cx, cy, h / 2); + } + else + { + evas_map_util_3d_rotate(mf, deg + 90, 0.0, 0.0, cx, cy, h / 2); + evas_map_util_3d_rotate(mb, deg, 0.0, 0.0, cx, cy, h / 2); + } + break; + case ELM_FLIP_CUBE_DOWN: + p = 1.0 - t; + p = 1.0 - (p * p); + deg = 90.0 * p; + if (wd->state) + { + evas_map_util_3d_rotate(mf, deg, 0.0, 0.0, cx, cy, h / 2); + evas_map_util_3d_rotate(mb, deg - 90, 0.0, 0.0, cx, cy, h / 2); + } + else + { + evas_map_util_3d_rotate(mf, deg - 90, 0.0, 0.0, cx, cy, h / 2); + evas_map_util_3d_rotate(mb, deg, 0.0, 0.0, cx, cy, h / 2); + } + break; + default: + break; + } + + + if (wd->front.content) + { + evas_map_util_3d_lighting(mf, lx, ly, lz, lr, lg, lb, lar, lag, lab); + evas_map_util_3d_perspective(mf, px, py, 0, foc); + evas_object_map_set(wd->front.content, mf); + evas_object_map_enable_set(wd->front.content, 1); + if (evas_map_util_clockwise_get(mf)) evas_object_show(wd->front.clip); + else evas_object_hide(wd->front.clip); + } + + if (wd->back.content) + { + evas_map_util_3d_lighting(mb, lx, ly, lz, lr, lg, lb, lar, lag, lab); + evas_map_util_3d_perspective(mb, px, py, 0, foc); + evas_object_map_set(wd->back.content, mb); + evas_object_map_enable_set(wd->back.content, 1); + if (evas_map_util_clockwise_get(mb)) evas_object_show(wd->back.clip); + else evas_object_hide(wd->back.clip); + } + + evas_map_free(mf); + evas_map_free(mb); + + if (t >= 1.0) + { + evas_object_map_enable_set(wd->front.content, 0); + evas_object_map_enable_set(wd->back.content, 0); + // FIXME: hack around evas rendering bug (only fix makes evas bitch-slow + evas_object_resize(wd->front.content, 0, 0); + evas_object_resize(wd->back.content, 0, 0); + evas_smart_objects_calculate(evas_object_evas_get(obj)); + // FIXME: end hack + wd->animator = NULL; + wd->state = !wd->state; + _configure(obj); + evas_object_smart_callback_call(obj, "animate,done", NULL); + return ECORE_CALLBACK_CANCEL; + } + return ECORE_CALLBACK_RENEW; +} + +static void +_configure(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord x, y, w, h; + if (!wd) return; + evas_object_geometry_get(obj, &x, &y, &w, &h); + if (wd->front.content) + { + if (!wd->animator) + evas_object_move(wd->front.content, x, y); + evas_object_resize(wd->front.content, w, h); + } + if (wd->back.content) + { + if (!wd->animator) + evas_object_move(wd->back.content, x, y); + evas_object_resize(wd->back.content, w, h); + } + _flip(obj); +} + +static void +_move(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + _configure(obj); +} + +static void +_resize(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + _configure(obj); +} + +static Eina_Bool +_animate(void *data) +{ + return _flip(data); +} + +/** + * Add a new flip to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Flip + */ +EAPI Evas_Object * +elm_flip_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "flip"); + elm_widget_type_set(obj, "flip"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_focus_next_hook_set(obj, _elm_flip_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->clip = evas_object_rectangle_add(e); + evas_object_static_clip_set(wd->clip, 1); + evas_object_color_set(wd->clip, 255, 255, 255, 255); + evas_object_move(wd->clip, -49999, -49999); + evas_object_resize(wd->clip, 99999, 99999); + elm_widget_sub_object_add(obj, wd->clip); + evas_object_clip_set(wd->clip, evas_object_clip_get(obj)); + evas_object_smart_member_add(wd->clip, obj); + + wd->front.clip = evas_object_rectangle_add(e); + evas_object_static_clip_set(wd->front.clip, 1); + evas_object_data_set(wd->front.clip, "_elm_leaveme", obj); + evas_object_color_set(wd->front.clip, 255, 255, 255, 255); + evas_object_move(wd->front.clip, -49999, -49999); + evas_object_resize(wd->front.clip, 99999, 99999); + elm_widget_sub_object_add(obj, wd->front.clip); + evas_object_smart_member_add(wd->front.clip, obj); + evas_object_clip_set(wd->front.clip, wd->clip); + + wd->back.clip = evas_object_rectangle_add(e); + evas_object_static_clip_set(wd->back.clip, 1); + evas_object_data_set(wd->back.clip, "_elm_leaveme", obj); + evas_object_color_set(wd->back.clip, 255, 255, 255, 255); + evas_object_move(wd->back.clip, -49999, -49999); + evas_object_resize(wd->back.clip, 99999, 99999); + elm_widget_sub_object_add(wd->back.clip, obj); + evas_object_smart_member_add(obj, wd->back.clip); + evas_object_clip_set(wd->back.clip, wd->clip); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOVE, _move, NULL); + evas_object_event_callback_add(obj, EVAS_CALLBACK_RESIZE, _resize, NULL); + + wd->state = 1; + + _sizing_eval(obj); + return obj; +} + +/** + * Set the front content of the flip widget. + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_flip_content_front_unset() function. + * + * @param obj The flip object + * @param content The new front content object + * + * @ingroup Flip + */ +EAPI void +elm_flip_content_front_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->front.content == content) return; + if (wd->front.content) evas_object_del(wd->back.content); + wd->front.content = content; + if (content) + { + elm_widget_sub_object_add(obj, content); + evas_object_smart_member_add(content, obj); + evas_object_clip_set(content, wd->front.clip); + evas_object_event_callback_add(content, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + _sizing_eval(obj); + } + // force calc to contents are the right size before transition + evas_smart_objects_calculate(evas_object_evas_get(obj)); + flip_show_hide(obj); + _configure(obj); +} + +/** + * Set the back content of the flip widget. + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_flip_content_back_unset() function. + * + * @param obj The flip object + * @param content The new back content object + * + * @ingroup Flip + */ +EAPI void +elm_flip_content_back_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->back.content == content) return; + if (wd->back.content) evas_object_del(wd->back.content); + wd->back.content = content; + if (content) + { + elm_widget_sub_object_add(obj, content); + evas_object_smart_member_add(content, obj); + evas_object_clip_set(content, wd->back.clip); + evas_object_event_callback_add(content, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + _sizing_eval(obj); + } + // force calc to contents are the right size before transition + evas_smart_objects_calculate(evas_object_evas_get(obj)); + flip_show_hide(obj); + _configure(obj); +} + +/** + * Get the front content used for the flip + * + * Return the front content object which is set for this widget. + * + * @param obj The flip object + * @return The front content object that is being used + * + * @ingroup Flip + */ +EAPI Evas_Object * +elm_flip_content_front_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + return wd->front.content; +} + + +/** + * Get the back content used for the flip + * + * Return the back content object which is set for this widget. + * + * @param obj The flip object + * @return The back content object that is being used + * + * @ingroup Flip + */ +EAPI Evas_Object * +elm_flip_content_back_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + return wd->back.content; +} + +/** + * Unset the front content used for the flip + * + * Unparent and return the front content object which was set for this widget. + * + * @param obj The flip object + * @return The front content object that was being used + * + * @ingroup Flip + */ +EAPI Evas_Object * +elm_flip_content_front_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->front.content) return NULL; + Evas_Object *content = wd->front.content; + evas_object_clip_unset(content); + elm_widget_sub_object_del(obj, content); + evas_object_smart_member_del(content); + wd->front.content = NULL; + return content; +} + +/** + * Unset the back content used for the flip + * + * Unparent and return the back content object which was set for this widget. + * + * @param obj The flip object + * @return The back content object that was being used + * + * @ingroup Flip + */ +EAPI Evas_Object * +elm_flip_content_back_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->back.content) return NULL; + Evas_Object *content = wd->back.content; + evas_object_clip_unset(content); + elm_widget_sub_object_del(obj, content); + evas_object_smart_member_del(content); + wd->back.content = NULL; + return content; +} + +/** + * Get flip front visibility state + * + * @param obj The flip object + * @return If front front is showing or not currently + * + * @ingroup Flip + */ +EAPI Eina_Bool +elm_flip_front_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->state; +} + +/** + * Set flip perspective + * + * @param obj The flip object + * @param foc The coordinate to set the focus on + * @param x The X coordinate + * @param y The Y coordinate + * + * NOTE: This function currently does nothing. + * + * @ingroup Flip + */ +EAPI void +elm_flip_perspective_set(Evas_Object *obj, Evas_Coord foc __UNUSED__, Evas_Coord x __UNUSED__, Evas_Coord y __UNUSED__) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; +} + +/** + * Runs the flip animation + * + * @param obj The flip object + * @param mode The mode type. Currently accepted modes are: + * + * ELM_FLIP_ROTATE_Y_CENTER_AXIS + * ELM_FLIP_ROTATE_X_CENTER_AXIS + * ELM_FLIP_ROTATE_XZ_CENTER_AXIS + * ELM_FLIP_ROTATE_YZ_CENTER_AXIS + * ELM_FLIP_CUBE_LEFT + * ELM_FLIP_CUBE_RIGHT + * + * FIXME: add - ELM_FLIP_CUBE_UP + * FIXMEL add - ELM_FLIP_CUBE_DOWN + * + * @ingroup Flip + */ +EAPI void +elm_flip_go(Evas_Object *obj, Elm_Flip_Mode mode) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (!wd->animator) wd->animator = ecore_animator_add(_animate, obj); + flip_show_hide(obj); + wd->mode = mode; + wd->start = ecore_loop_time_get(); + wd->len = 0.5; + // force calc to contents are the right size before transition + evas_smart_objects_calculate(evas_object_evas_get(obj)); + _flip(obj); + // FIXME: hack around evas rendering bug (only fix makes evas bitch-slow + evas_object_map_enable_set(wd->front.content, 0); + evas_object_map_enable_set(wd->back.content, 0); + evas_object_resize(wd->front.content, 0, 0); + evas_object_resize(wd->back.content, 0, 0); + evas_smart_objects_calculate(evas_object_evas_get(obj)); + _configure(obj); + // FIXME: end hack +} diff --git a/src/lib/elm_flipselector.c b/src/lib/elm_flipselector.c new file mode 100644 index 0000000..3b783e8 --- /dev/null +++ b/src/lib/elm_flipselector.c @@ -0,0 +1,1158 @@ +#include +#include "elm_priv.h" + +/** + * @addtogroup Flipselector Flipselector + * + * A flip selector is a widget to show a set of label items, one at a + * time, with an animation when one changes the current selection + * (like the flip of calendar sheets, in the default theme). + */ + +/* TODO: ideally, the default theme would use map{} blocks on the TEXT + parts to implement their fading in/out propertly (as in the clock + widget) */ +/* TODO: if one ever wants to extend it to receiving generic widgets + as items, be my guest. in this case, remember to implement the + items tooltip infra. */ +/* TODO: implement disabled mode -- disable_hook() and stuff. */ +/* TODO: fix default theme image borders for looong strings as item + labels. */ +/* TODO: set text elipsis on labels if one enforces mininum size on + * the overall widget less the required for displaying it. */ +/* TODO: find a way to, in the default theme, to detect we are + * bootstrapping (receiving the 1st message) and populate the downmost + * TEXT parts with the same text as the upmost, where appropriate. */ + +#define FLIP_FIRST_INTERVAL (0.85) +#define FLIP_MIN_INTERVAL (0.1) +#define MSG_FLIP_DOWN (1) +#define MSG_FLIP_UP (2) +#define MAX_LEN_DEFAULT (50) + +#define DATA_GET eina_list_data_get + +struct _Elm_Flipselector_Item { + Elm_Widget_Item base; + const char *label; + Evas_Smart_Cb func; + void *data; + int deleted : 1; +}; + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data { + Evas_Object *self; + Evas_Object *base; + Eina_List *items; + Eina_List *current; + Eina_List *sentinel; /* item containing the largest label string */ + int walking; + unsigned int max_len; + Ecore_Timer *spin; + double interval, first_interval; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _update_view(Evas_Object *obj); +static void _callbacks_set(Evas_Object *obj); +static void _flip_up(Widget_Data *wd); +static void _flip_down(Widget_Data *wd); + +static const char SIG_SELECTED[] = "selected"; +static const char SIG_UNDERFLOWED[] = "underflowed"; +static const char SIG_OVERFLOWED[] = "overflowed"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_SELECTED, ""}, + {SIG_UNDERFLOWED, ""}, + {SIG_OVERFLOWED, ""}, + {NULL, NULL} +}; + +#define ELM_FLIPSELECTOR_ITEM_CHECK_DELETED_RETURN(it, ...) \ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, __VA_ARGS__); \ + if (it->deleted) \ + { \ + ERR(""#it" has been DELETED.\n"); \ + return __VA_ARGS__; \ + } \ + +static Elm_Flipselector_Item * +_item_new(Evas_Object *obj, const char *label, Evas_Smart_Cb func, const void *data) +{ + unsigned int len; + Elm_Flipselector_Item *it; + Widget_Data *wd = elm_widget_data_get(obj); + + it = elm_widget_item_new(obj, Elm_Flipselector_Item); + if (!it) + return NULL; + + len = strlen(label); + if (len > wd->max_len) + len = wd->max_len; + + it->label = eina_stringshare_add_length(label, len); + it->func = func; + it->base.data = data; + + /* TODO: no view here, but if one desires general contents in the + * future... */ + return it; +} + +static inline void +_item_free(Elm_Flipselector_Item *it) +{ + eina_stringshare_del(it->label); + elm_widget_item_del(it); +} + +static void +_del_hook(Evas_Object *obj) +{ + Elm_Flipselector_Item *item; + + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (wd->walking) + ERR("flipselector deleted while walking.\n"); + + EINA_LIST_FREE(wd->items, item) + _item_free(item); + + if (wd->spin) ecore_timer_del(wd->spin); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd; + const char *max_len; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + _elm_theme_object_set(obj, wd->base, "flipselector", "base", + elm_widget_style_get(obj)); + edje_object_scale_set(wd->base, + elm_widget_scale_get(obj) * _elm_config->scale); + + max_len = edje_object_data_get(wd->base, "max_len"); + if (!max_len) + wd->max_len = MAX_LEN_DEFAULT; + else + { + wd->max_len = atoi(max_len); + if (!wd->max_len) + wd->max_len = MAX_LEN_DEFAULT; + } + + _update_view(obj); + _sizing_eval(obj); +} + +static void +_sentinel_eval(Widget_Data *wd) +{ + Elm_Flipselector_Item *it; + Eina_List *l; + + if (!wd->items) + { + wd->sentinel = NULL; + return; + } + + wd->sentinel = wd->items; + + EINA_LIST_FOREACH(wd->items, l, it) + { + if (strlen(elm_flipselector_item_label_get(it)) > + strlen(elm_flipselector_item_label_get(DATA_GET(wd->sentinel)))) + wd->sentinel = l; + } +} + +/* TODO: create a flag to avoid looping here all times */ +static void +_flipselector_process_deletions(Widget_Data *wd) +{ + Elm_Flipselector_Item *it; + Eina_List *l; + Eina_Bool skip = EINA_TRUE; + Eina_Bool sentinel_eval = EINA_FALSE; + + wd->walking++; /* avoid nested deletions */ + + EINA_LIST_FOREACH(wd->items, l, it) + { + if (!it->deleted) + continue; + + if (wd->current == l) + { + if (wd->current == wd->sentinel) + sentinel_eval = EINA_TRUE; + + wd->current = eina_list_prev(wd->current); + } + wd->items = eina_list_remove(wd->items, it); + + if (!wd->current) + wd->current = wd->items; + + _item_free(it); + skip = EINA_FALSE; + + if (eina_list_count(wd->items) <= 1) + edje_object_signal_emit(wd->base, "elm,state,button,hidden", "elm"); + else + edje_object_signal_emit(wd->base, "elm,state,button,visible", "elm"); + } + + if (!skip) + _update_view(wd->self); + + if (sentinel_eval) + _sentinel_eval(wd); + + wd->walking--; +} + +static inline void +_flipselector_walk(Widget_Data *wd) +{ + if (wd->walking < 0) + { + ERR("walking was negative. fixed!\n"); + wd->walking = 0; + } + wd->walking++; +} + +static inline void +_flipselector_unwalk(Widget_Data *wd) +{ + wd->walking--; + if (wd->walking < 0) + { + ERR("walking became negative. fixed!\n"); + wd->walking = 0; + } + + if (wd->walking) + return; + + _flipselector_process_deletions(wd); +} + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + Evas_Event_Key_Down *ev; + Widget_Data *wd; + Eina_Bool is_up = EINA_TRUE; + + if (type != EVAS_CALLBACK_KEY_DOWN) + return EINA_FALSE; + + wd = elm_widget_data_get(obj); + if (!wd) + return EINA_FALSE; + + ev = event_info; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + return EINA_FALSE; + + if (elm_widget_disabled_get(obj)) + return EINA_FALSE; + + if ((!strcmp(ev->keyname, "Down")) || (!strcmp(ev->keyname, "KP_Down"))) + is_up = EINA_FALSE; + else if ((strcmp(ev->keyname, "Up")) && (strcmp(ev->keyname, "KP_Up"))) + return EINA_FALSE; + + if (wd->spin) ecore_timer_del(wd->spin); + + /* TODO: if direction setting via API is not coming in, replace + these calls by flip_{next,prev} */ + _flipselector_walk(wd); + if (is_up) + _flip_up(wd); + else + _flip_down(wd); + _flipselector_unwalk(wd); + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return; + + /* FIXME: no treatment of this signal so far */ + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->base, "elm,action,focus", "elm"); + evas_object_focus_set(wd->base, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->base, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->base, EINA_FALSE); + } +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd; + const char *tmp = NULL; + Evas_Coord minw = -1, minh = -1, w, h; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + elm_coords_finger_size_adjust(1, &minw, 2, &minh); + + if (wd->sentinel) + { + const char *label = \ + elm_flipselector_item_label_get(DATA_GET(wd->sentinel)); + + tmp = edje_object_part_text_get(wd->base, "top"); + edje_object_part_text_set(wd->base, "top", label); + } + + edje_object_size_min_restricted_calc(wd->base, &minw, &minh, minw, minh); + elm_coords_finger_size_adjust(1, &minw, 2, &minh); + evas_object_size_hint_min_get(obj, &w, &h); + + if (wd->sentinel) + edje_object_part_text_set(wd->base, "top", tmp); + + if (w > minw) minw = w; + if (h > minh) minh = h; + + evas_object_size_hint_min_set(obj, minw, minh); +} + +static void +_update_view(Evas_Object *obj) +{ + Widget_Data *wd; + const char *label; + Elm_Flipselector_Item *item; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + label = NULL; + item = DATA_GET(wd->current); + if (item) + label = item->label; + + edje_object_part_text_set(wd->base, "top", label ? label : ""); + edje_object_part_text_set(wd->base, "bottom", label ? label : ""); + + edje_object_message_signal_process(wd->base); +} + +static void +_changed(Widget_Data *wd) +{ + Elm_Flipselector_Item *item; + + item = DATA_GET(wd->current); + if (!item) + return; + + if (item->func) + item->func((void *)item->base.data, item->base.widget, item); + if (!item->deleted) + evas_object_smart_callback_call(wd->self, SIG_SELECTED, item); +} + +static void +_send_msg(Widget_Data *wd, int flipside, char *label) +{ + Edje_Message_String msg; + + msg.str = label; + edje_object_message_send(wd->base, EDJE_MESSAGE_STRING, flipside, &msg); + edje_object_message_signal_process(wd->base); + + _changed(wd); +} + +static void +_flip_up(Widget_Data *wd) +{ + Elm_Flipselector_Item *item; + + if (!wd->current) + return; + + if (wd->current == wd->items) + { + wd->current = eina_list_last(wd->items); + evas_object_smart_callback_call(wd->self, SIG_UNDERFLOWED, NULL); + } + else + wd->current = eina_list_prev(wd->current); + + item = DATA_GET(wd->current); + if (!item) + return; + + _send_msg(wd, MSG_FLIP_UP, (char *)item->label); +} + +static Eina_Bool +_signal_val_up(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + + if (!wd) + goto val_up_exit_on_error; + + _flipselector_walk(wd); + + if (wd->interval > FLIP_MIN_INTERVAL) + wd->interval = wd->interval / 1.05; + + ecore_timer_interval_set(wd->spin, wd->interval); + + _flip_up(wd); + + _flipselector_unwalk(wd); + + return ECORE_CALLBACK_RENEW; + + val_up_exit_on_error: + return ECORE_CALLBACK_CANCEL; +} + +static void +_signal_val_up_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) + return; + + wd->interval = wd->first_interval; + + if (wd->spin) + ecore_timer_del(wd->spin); + wd->spin = ecore_timer_add(wd->interval, _signal_val_up, data); + + _signal_val_up(data); +} + +static void +_flip_down(Widget_Data *wd) +{ + Elm_Flipselector_Item *item; + + if (!wd->current) + return; + + wd->current = eina_list_next(wd->current); + if (!wd->current) + { + wd->current = wd->items; + evas_object_smart_callback_call(wd->self, SIG_OVERFLOWED, NULL); + } + + item = DATA_GET(wd->current); + if (!item) + return; + + _send_msg(wd, MSG_FLIP_DOWN, (char *)item->label); +} + +static Eina_Bool +_signal_val_down(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + + if (!wd) + goto val_down_exit_on_error; + + _flipselector_walk(wd); + + if (wd->interval > FLIP_MIN_INTERVAL) + wd->interval = wd->interval / 1.05; + ecore_timer_interval_set(wd->spin, wd->interval); + + _flip_down(wd); + + _flipselector_unwalk(wd); + + return ECORE_CALLBACK_RENEW; + + val_down_exit_on_error: + return ECORE_CALLBACK_CANCEL; +} + +static void +_signal_val_down_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) + return; + + wd->interval = wd->first_interval; + + if (wd->spin) + ecore_timer_del(wd->spin); + wd->spin = ecore_timer_add(wd->interval, _signal_val_down, data); + + _signal_val_down(data); +} + +static void +_signal_val_change_stop(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) + return; + + if (wd->spin) + ecore_timer_del(wd->spin); + wd->spin = NULL; +} + +static void +_callbacks_set(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + edje_object_signal_callback_add(wd->base, "elm,action,up,start", + "", _signal_val_up_start, obj); + edje_object_signal_callback_add(wd->base, "elm,action,up,stop", + "", _signal_val_change_stop, obj); + edje_object_signal_callback_add(wd->base, "elm,action,down,start", + "", _signal_val_down_start, obj); + edje_object_signal_callback_add(wd->base, "elm,action,down,stop", + "", _signal_val_change_stop, obj); +} + +/** + * Add a new flipselector to the parent. + * + * @param parent The parent object + * @return The new object or NULL, if it cannot be created + * + * @ingroup Flipselector + */ +EAPI Evas_Object * +elm_flipselector_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + wd->self = obj; + ELM_SET_WIDTYPE(widtype, "flipselector"); + elm_widget_type_set(obj, "flipselector"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + /* TODO: elm_widget_disable_hook_set(obj, _disable_hook); */ + + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_event_hook_set(obj, _event_hook); + + wd->base = edje_object_add(e); + elm_widget_resize_object_set(obj, wd->base); + + _callbacks_set(obj); + + wd->first_interval = FLIP_FIRST_INTERVAL; + + _theme_hook(obj); + + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Select next item of a flipselector. + * + * @param obj The flipselector object + * + * @ingroup Flipselector + */ +EAPI void +elm_flipselector_flip_next(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (wd->spin) ecore_timer_del(wd->spin); + + _flipselector_walk(wd); + _flip_down(wd); + _flipselector_unwalk(wd); +} + +/** + * Select previous item of a flipselector. + * + * @param obj The flipselector object + * + * @ingroup Flipselector + */ +EAPI void +elm_flipselector_flip_prev(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (wd->spin) ecore_timer_del(wd->spin); + + _flipselector_walk(wd); + _flip_up(wd); + _flipselector_unwalk(wd); +} + +/** + * Append item to a flipselector. + * + * @param obj The flipselector object + * @param label The label of new item + * @param func Convenience function called when item selected + * @param data Data passed to @p func above + * @return A handle to the item added or NULL, on errors + * + * @note The maximum length of the label is going to be determined by + * the widget's theme. Strings larger than that value are going to be + * truncated. + * + * @ingroup Flipselector + */ +EAPI Elm_Flipselector_Item * +elm_flipselector_item_append(Evas_Object *obj, const char *label, void (*func)(void *data, Evas_Object *obj, void *event_info), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Elm_Flipselector_Item *item; + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return NULL; + + item = _item_new(obj, label, func, data); + if (!item) + return NULL; + + wd->items = eina_list_append(wd->items, item); + if (!wd->current) { + wd->current = wd->items; + _update_view(obj); + } + + if (!wd->sentinel || + (strlen(elm_flipselector_item_label_get(item)) > + strlen(elm_flipselector_item_label_get(DATA_GET(wd->sentinel))))) + { + wd->sentinel = eina_list_last(wd->items); + _sizing_eval(obj); + } + + if (eina_list_count(wd->items) >= 2) + edje_object_signal_emit(wd->base, "elm,state,button,visible", "elm"); + + return item; +} + +/** + * Prepend item to a flipselector. + * + * @param obj The flipselector object + * @param label The label of new item + * @param func Convenience function called when item selected + * @param data Data passed to @p func above + * @return A handle to the item added or NULL, on errors + * + * @note The maximum length of the label is going to be determined by + * the widget's theme. Strings larger than that value are going to be + * truncated. + * + * @ingroup Flipselector + */ +EAPI Elm_Flipselector_Item * +elm_flipselector_item_prepend(Evas_Object *obj, const char *label, void (*func)(void *data, Evas_Object *obj, void *event_info), void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Elm_Flipselector_Item *item; + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return NULL; + + item = _item_new(obj, label, func, data); + if (!item) + return NULL; + + wd->items = eina_list_prepend(wd->items, item); + if (!wd->current) { + wd->current = wd->items; + _update_view(obj); + } + + if (!wd->sentinel || + (strlen(elm_flipselector_item_label_get(item)) > + strlen(elm_flipselector_item_label_get(DATA_GET(wd->sentinel))))) + { + wd->sentinel = wd->items; + _sizing_eval(obj); + } + + if (eina_list_count(wd->items) >= 2) + edje_object_signal_emit(wd->base, "elm,state,button,visible", "elm"); + + return item; +} + +/* TODO: account for deleted items? */ +/** + * Get a list of items in the flipselector. + * + * @param obj The flipselector object + * @return The list of items, or NULL on errors. + * + * @ingroup Flipselector + */ +EAPI const Eina_List * +elm_flipselector_items_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return NULL; + + return wd->items; +} + +/** + * Get the first item in the flipselector + * + * @param obj The flipselector object + * @return The first item, or NULL if none + * + * @ingroup Flipselector + */ +EAPI Elm_Flipselector_Item * +elm_flipselector_first_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Elm_Flipselector_Item *it; + Widget_Data *wd; + Eina_List *l; + + wd = elm_widget_data_get(obj); + if (!wd || !wd->items) + return NULL; + + EINA_LIST_FOREACH(wd->items, l, it) + { + if (it->deleted) + continue; + + return it; + } + + return NULL; +} + +/** + * Get the last item in the flipselector + * + * @param obj The flipselector object + * @return The last item, or NULL if none + * + * @ingroup Flipselector + */ +EAPI Elm_Flipselector_Item * +elm_flipselector_last_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Elm_Flipselector_Item *it; + Widget_Data *wd; + Eina_List *l; + + wd = elm_widget_data_get(obj); + if (!wd || !wd->items) + return NULL; + + EINA_LIST_REVERSE_FOREACH(wd->items, l, it) + { + if (it->deleted) + continue; + + return it; + } + + return NULL; +} + +/** + * Get the selected item in a flipselector. + * + * @param obj The flipselector object + * @return The selected item, or NULL if none + * + * @ingroup Flipselector + */ +EAPI Elm_Flipselector_Item * +elm_flipselector_selected_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd || !wd->current) + return NULL; + + return DATA_GET(wd->current); +} + +/** + * Set the selected state of an item + * + * This sets the selected state (EINA_TRUE selected, EINA_FALSE not selected) + * of the given item @p item. + * If a new item is selected the previosly selected will be unselected. + * If the item @p item is unselected, the first item will be selected. + * + * @param item The item + * @param selected The selected state + * + * @ingroup Flipselector + */ +EAPI void +elm_flipselector_item_selected_set(Elm_Flipselector_Item *item, Eina_Bool selected) +{ + ELM_FLIPSELECTOR_ITEM_CHECK_DELETED_RETURN(item); + + Elm_Flipselector_Item *_item, *cur; + int flipside = MSG_FLIP_UP; + Widget_Data *wd; + Eina_List *l; + + wd = elm_widget_data_get(item->base.widget); + if (!wd) + return; + + cur = DATA_GET(wd->current); + if ((selected) && (cur == item)) + return; + + _flipselector_walk(wd); + + if ((!selected) && (cur == item)) + { + EINA_LIST_FOREACH(wd->items, l, _item) + { + if (!_item->deleted) + { + wd->current = l; + _send_msg(wd, MSG_FLIP_UP, (char *)_item->label); + break; + } + } + _flipselector_unwalk(wd); + return; + } + + EINA_LIST_FOREACH(wd->items, l, _item) + { + if (_item == cur) + flipside = MSG_FLIP_DOWN; + + if (_item == item) + { + wd->current = l; + _send_msg(wd, flipside, (char *)item->label); + break; + } + } + + _flipselector_unwalk(wd); +} + +/* + * Get the selected state of @p item. + * + * @param item The flipselector item + * @return If true, the item is selected + * + * @ingroup Flipselector + */ +EAPI Eina_Bool +elm_flipselector_item_selected_get(const Elm_Flipselector_Item *item) +{ + ELM_FLIPSELECTOR_ITEM_CHECK_DELETED_RETURN(item, EINA_FALSE); + Widget_Data *wd; + + wd = elm_widget_data_get(item->base.widget); + if (!wd) return EINA_FALSE; + return (eina_list_data_get(wd->current) == item); +} + +/** + * Delete a given item from a flipselector. + * + * @param item The item + * + * @ingroup Flipselector + */ +EAPI void +elm_flipselector_item_del(Elm_Flipselector_Item *item) +{ + ELM_FLIPSELECTOR_ITEM_CHECK_DELETED_RETURN(item); + + Widget_Data *wd; + + wd = elm_widget_data_get(item->base.widget); + if (!wd) + return; + + if (wd->walking > 0) + { + item->deleted = EINA_TRUE; + return; + } + + _flipselector_walk(wd); + + wd->items = eina_list_remove(wd->items, item); + _item_free(item); + _sentinel_eval(wd); + + _flipselector_unwalk(wd); +} + +/** + * Get the label of a given flipselector item. + * + * @param item The item + * @return The label of a given item, or NULL if none + * + * @ingroup Flipselector + */ +EAPI const char * +elm_flipselector_item_label_get(const Elm_Flipselector_Item *item) +{ + ELM_FLIPSELECTOR_ITEM_CHECK_DELETED_RETURN(item, NULL); + + Elm_Flipselector_Item *_item; + Widget_Data *wd; + Eina_List *l; + + wd = elm_widget_data_get(item->base.widget); + if ((!wd) || (!wd->items)) + return NULL; + + EINA_LIST_FOREACH(wd->items, l, _item) + if (_item == item) + return item->label; + + return NULL; +} + +/** + * Set the label of a given flipselector item. + * + * @param item The item + * @param label The text label string in UTF-8 + * + * @ingroup Flipselector + */ +EAPI void +elm_flipselector_item_label_set(Elm_Flipselector_Item *item, const char *label) +{ + ELM_FLIPSELECTOR_ITEM_CHECK_DELETED_RETURN(item); + + Widget_Data *wd; + Eina_List *l; + + if ((!item) || (!label)) + return; + + wd = elm_widget_data_get(item->base.widget); + if ((!wd) || (!wd->items)) + return; + + l = eina_list_data_find_list(wd->items, item); + if (!l) + return; + + eina_stringshare_del(item->label); + item->label = eina_stringshare_add_length(label, wd->max_len); + + if (strlen(label) > + strlen(elm_flipselector_item_label_get(DATA_GET(wd->sentinel)))) + wd->sentinel = l; + + if (wd->current == l) + { + _update_view(item->base.widget); + _sizing_eval(wd->self); + } + + return; +} + +/** + * Gets the item before @p item in a flipselector. + * + * @param item The item + * @return The item before the item @p item + * + * @ingroup Flipselector + */ +EAPI Elm_Flipselector_Item * +elm_flipselector_item_prev_get(Elm_Flipselector_Item *item) +{ + ELM_FLIPSELECTOR_ITEM_CHECK_DELETED_RETURN(item, NULL); + + Elm_Flipselector_Item *_item; + Widget_Data *wd; + Eina_List *l; + + wd = elm_widget_data_get(item->base.widget); + if ((!wd) || (!wd->items)) + return NULL; + + EINA_LIST_FOREACH(wd->items, l, _item) + if (_item == item) + { + l = eina_list_prev(l); + if (!l) + return NULL; + return DATA_GET(l); + } + + return NULL; +} + +/** + * Gets the item after @p item in a flipselector. + * + * @param item The item + * @return The item after the item @p item + * + * @ingroup Flipselector + */ +EAPI Elm_Flipselector_Item * +elm_flipselector_item_next_get(Elm_Flipselector_Item *item) +{ + ELM_FLIPSELECTOR_ITEM_CHECK_DELETED_RETURN(item, NULL); + + Elm_Flipselector_Item *_item; + Widget_Data *wd; + Eina_List *l; + + wd = elm_widget_data_get(item->base.widget); + if ((!wd) || (!wd->items)) + return NULL; + + EINA_LIST_FOREACH(wd->items, l, _item) + if (_item == item) + { + l = eina_list_next(l); + if (!l) + return NULL; + return DATA_GET(l); + } + + return NULL; +} + +/** + * Set the flipping interval for the flipselector. + * + * @param obj The flipselector object + * @param interval The interval value in seconds + * + * The interval value is decreased while the user flips the widget up + * or down repeatedly. The next interval value is the previous + * interval / 1.05, so it speeds up a bit. Default value is 0.85 + * seconds. + * + * @ingroup Flipselector + */ +EAPI void +elm_flipselector_interval_set(Evas_Object *obj, double interval) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return; + + wd->first_interval = interval; +} + +/** + * Get the flipping interval of the flipselector. + * + * @param obj The flipselector object + * @return The value of the first interval in seconds + * + * The interval value is decreased while the user flips the widget up + * or down repeatedly. The next interval value is the previous + * interval / 1.05, so it speeds up a bit. Default value is 0.85 + * seconds. + * + * @ingroup Flipselector + */ +EAPI double +elm_flipselector_interval_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return 0.0; + return wd->first_interval; +} diff --git a/src/lib/elm_font.c b/src/lib/elm_font.c new file mode 100644 index 0000000..844fc7b --- /dev/null +++ b/src/lib/elm_font.c @@ -0,0 +1,128 @@ +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif + +#ifdef HAVE_EVIL +# include +#endif + +#include +#include "elm_priv.h" + +Elm_Font_Properties * +_elm_font_properties_get(Eina_Hash **font_hash, + const char *font) +{ + Elm_Font_Properties *efp = NULL; + char *s1; + + s1 = strchr(font, ':'); + if (s1) + { + char *s2, *name, *style; + int len; + + len = s1 - font; + name = calloc(sizeof(char), len + 1); + strncpy(name, font, len); + + /* get subname (should be english) */ + s2 = strchr(name, ','); + if (s2) + { + len = s2 - name; + name = realloc(name, sizeof(char) * len + 1); + memset(name, 0, sizeof(char) * len + 1); + strncpy(name, font, len); + } + + if (!strncmp(s1, ELM_FONT_TOKEN_STYLE, strlen(ELM_FONT_TOKEN_STYLE))) + { + style = s1 + strlen(ELM_FONT_TOKEN_STYLE); + + if (font_hash) efp = eina_hash_find(*font_hash, name); + if (!efp) + { + efp = calloc(1, sizeof(Elm_Font_Properties)); + efp->name = eina_stringshare_add(name); + if (font_hash) + { + if (!*font_hash) + *font_hash = eina_hash_string_superfast_new(NULL); + eina_hash_add(*font_hash, name, efp); + } + } + s2 = strchr(style, ','); + if (s2) + { + char *style_old; + + len = s2 - style; + style_old = style; + style = calloc(sizeof(char), len + 1); + strncpy(style, style_old, len); + efp->styles = eina_list_append(efp->styles, + eina_stringshare_add(style)); + free(style); + } + else + efp->styles = eina_list_append(efp->styles, + eina_stringshare_add(style)); + } + free(name); + } + else + { + if (font_hash) efp = eina_hash_find(*font_hash, font); + if (!efp) + { + efp = calloc(1, sizeof(Elm_Font_Properties)); + efp->name = eina_stringshare_add(font); + if (font_hash) + { + if (!*font_hash) + *font_hash = eina_hash_string_superfast_new(NULL); + eina_hash_add(*font_hash, font, efp); + } + } + } + return efp; +} + +/* FIXME: do we really need it? */ +Eina_Hash * +_elm_font_available_hash_add(Eina_Hash *font_hash, + const char *full_name) +{ + _elm_font_properties_get(&font_hash, full_name); + return font_hash; +} + +static void +_elm_font_properties_free(Elm_Font_Properties *efp) +{ + const char *str; + + EINA_LIST_FREE(efp->styles, str) + if (str) eina_stringshare_del(str); + + if (efp->name) eina_stringshare_del(efp->name); + free(efp); +} + +static Eina_Bool +_font_hash_free_cb(const Eina_Hash *hash __UNUSED__, const void *key __UNUSED__, void *data, void *fdata __UNUSED__) +{ + Elm_Font_Properties *efp; + + efp = data; + _elm_font_properties_free(efp); + return EINA_TRUE; +} + +void +_elm_font_available_hash_del(Eina_Hash *hash) +{ + eina_hash_foreach(hash, _font_hash_free_cb, NULL); + eina_hash_free(hash); +} diff --git a/src/lib/elm_frame.c b/src/lib/elm_frame.c new file mode 100644 index 0000000..0e00a12 --- /dev/null +++ b/src/lib/elm_frame.c @@ -0,0 +1,251 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Frame Frame + * + * This holds some content and has a title. Looks like a frame, but + * supports styles so multple frames are avaible + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *frm; + Evas_Object *content; + const char *label; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->label) eina_stringshare_del(wd->label); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->frm, "frame", "base", elm_widget_style_get(obj)); + edje_object_part_text_set(wd->frm, "elm.text", wd->label); + if (wd->content) + edje_object_part_swallow(wd->frm, "elm.swallow.content", wd->content); + edje_object_scale_set(wd->frm, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static Eina_Bool +_elm_frame_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *cur; + + if ((!wd) || (!wd->content)) + return EINA_FALSE; + + cur = wd->content; + + /* Try Focus cycle in subitem */ + return elm_widget_focus_next_get(cur, dir, next); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + if (!wd) return; + edje_object_size_min_calc(wd->frm, &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + // FIXME: why is this needed? how does edje get this unswallowed or + // lose its callbacks to edje + if (!wd) return; + edje_object_part_swallow(wd->frm, "elm.swallow.content", wd->content); + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->content) + { + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->content = NULL; + _sizing_eval(obj); + } +} + +/** + * Add a new frame to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Frame + */ +EAPI Evas_Object * +elm_frame_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "frame"); + elm_widget_type_set(obj, "frame"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_focus_next_hook_set(obj, _elm_frame_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->frm = edje_object_add(e); + _elm_theme_object_set(obj, wd->frm, "frame", "base", "default"); + elm_widget_resize_object_set(obj, wd->frm); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + _sizing_eval(obj); + return obj; +} + +/** + * Set the frame label + * + * @param obj The frame object + * @param label The label of this frame object + * + * @ingroup Frame + */ +EAPI void +elm_frame_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&(wd->label), label); + edje_object_part_text_set(wd->frm, "elm.text", wd->label); + _sizing_eval(obj); +} + +/** + * Get the frame label + * + * @param obj The frame object + * + * @return The label of this frame objet or NULL if unable to get frame + * + * @ingroup Frame + */ +EAPI const char * +elm_frame_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the content of the frame widget + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_frame_content_unset() function. + * + * @param obj The frame object + * @param content The content will be filled in this frame object + * + * @ingroup Frame + */ +EAPI void +elm_frame_content_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->content == content) return; + if (wd->content) evas_object_del(wd->content); + wd->content = content; + if (content) + { + elm_widget_sub_object_add(obj, content); + evas_object_event_callback_add(content, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->frm, "elm.swallow.content", content); + } + _sizing_eval(obj); +} + +/** + * Get the content of the frame widget + * + * Return the content object which is set for this widget + * + * @param obj The frame object + * @return The content that is being used + * + * @ingroup Frame + */ +EAPI Evas_Object * +elm_frame_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->content; +} + +/** + * Unset the content of the frame widget + * + * Unparent and return the content object which was set for this widget + * + * @param obj The frame object + * @return The content that was being used + * + * @ingroup Frame + */ +EAPI Evas_Object * +elm_frame_content_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *content; + if (!wd) return NULL; + if (!wd->content) return NULL; + content = wd->content; + elm_widget_sub_object_del(obj, wd->content); + edje_object_part_unswallow(wd->frm, wd->content); + wd->content = NULL; + return content; +} diff --git a/src/lib/elm_gengrid.c b/src/lib/elm_gengrid.c new file mode 100644 index 0000000..0060898 --- /dev/null +++ b/src/lib/elm_gengrid.c @@ -0,0 +1,2904 @@ +#include +#include +#include "elm_priv.h" + +/** + * @defgroup Gengrid Gengrid + * + * This widget aims to position objects in a grid layout while + * actually building only the visible ones, using the same idea as + * genlist: the user define a class for each item, specifying + * functions that will be called at object creation and deletion. + * + * Signals that you can add callbacks for are: + * + * clicked - The user has double-clicked a item. The event_info + * parameter is the Gengrid item that was double-clicked. + * + * selected - The user has made an item selected. The event_info + * parameter is the Gengrid item that was selected. + * + * unselected - The user has made an item unselected. The event_info + * parameter is the Gengrid item that was unselected. + * + * realized - This is called when the item in the Gengrid is created + * as a real evas object. event_info is the Gengrid item that was + * created. The object may be deleted at any time, so it is up to the + * caller to not use the object pointer from + * elm_gengrid_item_object_get() in a way where it may point to freed + * objects. + * + * unrealized - This is called when the real evas object for this item + * is deleted. event_info is the Gengrid item that was created. + * + * changed - Called when an item is added, removed, resized or moved + * and when gengrid is resized or horizontal property changes. + * + * drag,start,up - Called when the item in the Gengrid has been + * dragged (not scrolled) up. + * + * drag,start,down - Called when the item in the Gengrid has been + * dragged (not scrolled) down. + * + * drag,start,left - Called when the item in the Gengrid has been + * dragged (not scrolled) left. + * + * drag,start,right - Called when the item in the Gengrid has been + * dragged (not scrolled) right. + * + * drag,stop - Called when the item in the Gengrid has stopped being + * dragged. + * + * drag - Called when the item in the Gengrid is being dragged. + * + * scroll - called when the content has been scrolled (moved). + * + * scroll,drag,start - called when dragging the content has started. + * + * scroll,drag,stop - called when dragging the content has stopped. + * + * + * A item in the Gengrid can have 0 or more text labels (they can be + * regular text or textblock - that's up to the style to determine), 0 + * or more icons (which are simply objects swallowed into the Gengrid + * item) and 0 or more boolean states that can be used for check, + * radio or other indicators by the edje theme style. A item may be + * one of several styles (Elementary provides 1 by default - + * "default", but this can be extended by system or application custom + * themes/overlays/extensions). + * + * In order to implement the ability to add and delete items on the + * fly, Gengrid implements a class/callback system where the + * application provides a structure with information about that type + * of item (Gengrid may contain multiple different items with + * different classes, states and styles). Gengrid will call the + * functions in this struct (methods) when a item is "realized" (that + * is created dynamically while scrolling). All objects will simply be + * deleted when no longer needed with evas_object_del(). The + * Elm_GenGrid_Item_Class structure contains the following members: + * + * item_style - This is a constant string and simply defines the name + * of the item style. It must be specified and the default should be + * "default". + * + * func.label_get - This function is called when an actual item object + * is created. The data parameter is the one passed to + * elm_gengrid_item_append() and related item creation functions. The + * obj parameter is the Gengrid object and the part parameter is the + * string name of the text part in the edje design that is listed as + * one of the possible labels that can be set. This function must + * return a strdup'()ed string as the caller will free() it when done. + * + * func.icon_get - This function is called when an actual item object + * is created. The data parameter is the one passed to + * elm_gengrid_item_append() and related item creation functions. The + * obj parameter is the Gengrid object and the part parameter is the + * string name of the icon part in the edje design that is listed as + * one of the possible icons that can be set. This must return NULL + * for no object or a valid object. The object will be deleted by + * Gengrid on shutdown or when the item is unrealized. + * + * func.state_get - This function is called when an actual item object + * is created. The data parameter is the one passed to + * elm_gengrid_item_append() and related item creation functions. The + * obj parameter is the Gengrid object and the part parameter is the + * string name of th state part in the edje design that is listed as + * one of the possible states that can be set. Return 0 for false and + * 1 for true. Gengrid will emit a signal to the edje object with + * "elm,state,XXX,active" "elm" when true (the default is false), + * where XXX is the name of the part. + * + * func.del - This is called when elm_gengrid_item_del() is called on + * a item or elm_gengrid_clear() is called on the Gengrid. This is + * intended for use when actual Gengrid items are deleted, so any + * backing data attached to the item (e.g. its data parameter on + * creation) can be deleted. + * + * If the application wants multiple items to be able to be selected, + * elm_gengrid_multi_select_set() can enable this. If the Gengrid is + * single-selection only (the default), then + * elm_gengrid_select_item_get() will return the selected item, if + * any, or NULL if none is selected. If the Gengrid is multi-select + * then elm_gengrid_selected_items_get() will return a list (that is + * only valid as long as no items are modified (added, deleted, + * selected or unselected). + * + * If a item changes (state of boolean changes, label or icons + * change), then use elm_gengrid_item_update() to have Gengrid update + * the item with the new state. Gengrid will re-realize the item thus + * call the functions in the _Elm_Gengrid_Item_Class for that item. + * + * To programmatically (un)select a item use + * elm_gengrid_item_selected_set(). To get its selected state use + * elm_gengrid_item_selected_get(). To make a item disabled (unable to + * be selected and appear differently) use + * elm_gengrid_item_disabled_set() to set this and + * elm_gengrid_item_disabled_get() to get the disabled state. + * + * Cells will only call their selection func and callback when first + * becoming selected. Any further clicks will do nothing, unless you + * enable always select with + * elm_gengrid_always_select_mode_set(). This means event if selected, + * every click will make the selected callbacks be called. + * elm_gengrid_no_select_mode_set() will turn off the ability to + * select items entirely and they will neither appear selected nor + * call selected callback function. + * + * Remember that you can create new styles and add your own theme + * augmentation per application with elm_theme_extension_add(). If you + * absolutely must have a specific style that overrides any theme the + * user or system sets up you can use elm_theme_overlay_add() to add + * such a file. + * + * -- + * TODO: + * * Handle non-homogeneous objects too. + */ + +typedef struct _Widget_Data Widget_Data; +typedef struct _Pan Pan; + +#define PRELOAD 1 + +struct _Elm_Gengrid_Item +{ + Elm_Widget_Item base; + EINA_INLIST; + Evas_Object *spacer; + const Elm_Gengrid_Item_Class *gic; + Ecore_Timer *long_timer; + Widget_Data *wd; + Eina_List *labels, *icons, *states, *icon_objs; + struct + { + Evas_Smart_Cb func; + const void *data; + } func; + + Evas_Coord x, y, dx, dy; + int relcount; + int walking; + + struct + { + const void *data; + Elm_Tooltip_Item_Content_Cb content_cb; + Evas_Smart_Cb del_cb; + const char *style; + } tooltip; + + const char *mouse_cursor; + + Eina_Bool want_unrealize : 1; + Eina_Bool realized : 1; + Eina_Bool dragging : 1; + Eina_Bool down : 1; + Eina_Bool delete_me : 1; + Eina_Bool display_only : 1; + Eina_Bool disabled : 1; + Eina_Bool selected : 1; + Eina_Bool hilighted : 1; +}; + +struct _Widget_Data +{ + Evas_Object *self, *scr; + Evas_Object *pan_smart; + Pan *pan; + Eina_Inlist *items; + Ecore_Job *calc_job; + Eina_List *selected; + Elm_Gengrid_Item *last_selected_item; + double align_x, align_y; + + Evas_Coord pan_x, pan_y; + Evas_Coord item_width, item_height; /* Each item size */ + Evas_Coord minw, minh; /* Total obj size */ + unsigned int nmax; + long count; + int walking; + + Eina_Bool horizontal : 1; + Eina_Bool on_hold : 1; + Eina_Bool longpressed : 1; + Eina_Bool multi : 1; + Eina_Bool no_select : 1; + Eina_Bool wasselected : 1; + Eina_Bool always_select : 1; + Eina_Bool clear_me : 1; +}; + +#define ELM_GENGRID_ITEM_FROM_INLIST(item) \ + ((item) ? EINA_INLIST_CONTAINER_GET(item, Elm_Gengrid_Item) : NULL) + +struct _Pan +{ + Evas_Object_Smart_Clipped_Data __clipped_data; + Widget_Data *wd; +}; + +static const char *widtype = NULL; +static void _item_hilight(Elm_Gengrid_Item *item); +static void _item_unrealize(Elm_Gengrid_Item *item); +static void _item_select(Elm_Gengrid_Item *item); +static void _item_unselect(Elm_Gengrid_Item *item); +static void _calc_job(void *data); +static void _on_focus_hook(void *data, + Evas_Object *obj); +static Eina_Bool _item_multi_select_up(Widget_Data *wd); +static Eina_Bool _item_multi_select_down(Widget_Data *wd); +static Eina_Bool _item_multi_select_left(Widget_Data *wd); +static Eina_Bool _item_multi_select_right(Widget_Data *wd); +static Eina_Bool _item_single_select_up(Widget_Data *wd); +static Eina_Bool _item_single_select_down(Widget_Data *wd); +static Eina_Bool _item_single_select_left(Widget_Data *wd); +static Eina_Bool _item_single_select_right(Widget_Data *wd); +static Eina_Bool _event_hook(Evas_Object *obj, + Evas_Object *src, + Evas_Callback_Type type, + void *event_info); +static Eina_Bool _deselect_all_items(Widget_Data *wd); + +static Evas_Smart_Class _pan_sc = EVAS_SMART_CLASS_INIT_VERSION; + +static Eina_Bool +_event_hook(Evas_Object *obj, + Evas_Object *src __UNUSED__, + Evas_Callback_Type type, + void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (!wd->items) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + + Elm_Gengrid_Item *item = NULL; + Evas_Coord x = 0; + Evas_Coord y = 0; + Evas_Coord step_x = 0; + Evas_Coord step_y = 0; + Evas_Coord v_w = 0; + Evas_Coord v_h = 0; + Evas_Coord page_x = 0; + Evas_Coord page_y = 0; + + elm_smart_scroller_child_pos_get(wd->scr, &x, &y); + elm_smart_scroller_step_size_get(wd->scr, &step_x, &step_y); + elm_smart_scroller_page_size_get(wd->scr, &page_x, &page_y); + elm_smart_scroller_child_viewport_size_get(wd->scr, &v_w, &v_h); + + if ((!strcmp(ev->keyname, "Left")) || (!strcmp(ev->keyname, "KP_Left"))) + { + if ((wd->horizontal) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_up(wd))) + || (_item_single_select_up(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!wd->horizontal) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_left(wd))) + || (_item_single_select_left(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + x -= step_x; + } + else if ((!strcmp(ev->keyname, "Right")) || (!strcmp(ev->keyname, "KP_Right"))) + { + if ((wd->horizontal) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_down(wd))) + || (_item_single_select_down(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!wd->horizontal) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_right(wd))) + || (_item_single_select_right(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + x += step_x; + } + else if ((!strcmp(ev->keyname, "Up")) || (!strcmp(ev->keyname, "KP_Up"))) + { + if ((wd->horizontal) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_left(wd))) + || (_item_single_select_left(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!wd->horizontal) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_up(wd))) + || (_item_single_select_up(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + y -= step_y; + } + else if ((!strcmp(ev->keyname, "Down")) || (!strcmp(ev->keyname, "KP_Down"))) + { + if ((wd->horizontal) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_right(wd))) + || (_item_single_select_right(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!wd->horizontal) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_down(wd))) + || (_item_single_select_down(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + y += step_y; + } + else if ((!strcmp(ev->keyname, "Home")) || (!strcmp(ev->keyname, "KP_Home"))) + { + item = elm_gengrid_first_item_get(obj); + elm_gengrid_item_bring_in(item); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "End")) || (!strcmp(ev->keyname, "KP_End"))) + { + item = elm_gengrid_last_item_get(obj); + elm_gengrid_item_bring_in(item); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "Prior")) || + (!strcmp(ev->keyname, "KP_Prior"))) + { + if (wd->horizontal) + { + if (page_x < 0) + x -= -(page_x * v_w) / 100; + else + x -= page_x; + } + else + { + if (page_y < 0) + y -= -(page_y * v_h) / 100; + else + y -= page_y; + } + } + else if ((!strcmp(ev->keyname, "Next")) || (!strcmp(ev->keyname, "KP_Next"))) + { + if (wd->horizontal) + { + if (page_x < 0) + x += -(page_x * v_w) / 100; + else + x += page_x; + } + else + { + if (page_y < 0) + y += -(page_y * v_h) / 100; + else + y += page_y; + } + } + else if (!strcmp(ev->keyname, "Escape")) + { + if (!_deselect_all_items(wd)) return EINA_FALSE; + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else return EINA_FALSE; + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + elm_smart_scroller_child_pos_set(wd->scr, x, y); + return EINA_TRUE; +} + +static Eina_Bool +_deselect_all_items(Widget_Data *wd) +{ + if (!wd->selected) return EINA_FALSE; + while(wd->selected) + elm_gengrid_item_selected_set(wd->selected->data, EINA_FALSE); + + return EINA_TRUE; +} + +static Eina_Bool +_item_multi_select_left(Widget_Data *wd) +{ + if (!wd->selected) return EINA_FALSE; + + Elm_Gengrid_Item *prev = elm_gengrid_item_prev_get(wd->last_selected_item); + if (!prev) return EINA_TRUE; + if (elm_gengrid_item_selected_get(prev)) + { + elm_gengrid_item_selected_set(wd->last_selected_item, EINA_FALSE); + wd->last_selected_item = prev; + elm_gengrid_item_show(wd->last_selected_item); + } + else + { + elm_gengrid_item_selected_set(prev, EINA_TRUE); + elm_gengrid_item_show(prev); + } + + return EINA_TRUE; +} + +static Eina_Bool +_item_multi_select_right(Widget_Data *wd) +{ + if (!wd->selected) return EINA_FALSE; + + Elm_Gengrid_Item *next = elm_gengrid_item_next_get(wd->last_selected_item); + if (!next) return EINA_TRUE; + if (elm_gengrid_item_selected_get(next)) + { + elm_gengrid_item_selected_set(wd->last_selected_item, EINA_FALSE); + wd->last_selected_item = next; + elm_gengrid_item_show(wd->last_selected_item); + } + else + { + elm_gengrid_item_selected_set(next, EINA_TRUE); + elm_gengrid_item_show(next); + } + + return EINA_TRUE; +} + +static Eina_Bool +_item_multi_select_up(Widget_Data *wd) +{ + unsigned int i; + Eina_Bool r = EINA_TRUE; + + if (!wd->selected) return EINA_FALSE; + + for (i = 0; (r) && (i < wd->nmax); i++) + r &= _item_multi_select_left(wd); + + return r; +} + +static Eina_Bool +_item_multi_select_down(Widget_Data *wd) +{ + unsigned int i; + Eina_Bool r = EINA_TRUE; + + if (!wd->selected) return EINA_FALSE; + + for (i = 0; (r) && (i < wd->nmax); i++) + r &= _item_multi_select_right(wd); + + return r; +} + +static Eina_Bool +_item_single_select_up(Widget_Data *wd) +{ + unsigned int i; + + Elm_Gengrid_Item *prev; + + if (!wd->selected) + { + prev = ELM_GENGRID_ITEM_FROM_INLIST(wd->items->last); + while ((prev) && (prev->delete_me)) + prev = ELM_GENGRID_ITEM_FROM_INLIST(EINA_INLIST_GET(prev)->prev); + elm_gengrid_item_selected_set(prev, EINA_TRUE); + elm_gengrid_item_show(prev); + return EINA_TRUE; + } + else prev = elm_gengrid_item_prev_get(wd->last_selected_item); + + if (!prev) return EINA_FALSE; + + for (i = 1; i < wd->nmax; i++) + { + Elm_Gengrid_Item *tmp = elm_gengrid_item_prev_get(prev); + if (!tmp) return EINA_FALSE; + prev = tmp; + } + + _deselect_all_items(wd); + + elm_gengrid_item_selected_set(prev, EINA_TRUE); + elm_gengrid_item_show(prev); + return EINA_TRUE; +} + +static Eina_Bool +_item_single_select_down(Widget_Data *wd) +{ + unsigned int i; + + Elm_Gengrid_Item *next; + + if (!wd->selected) + { + next = ELM_GENGRID_ITEM_FROM_INLIST(wd->items); + while ((next) && (next->delete_me)) + next = ELM_GENGRID_ITEM_FROM_INLIST(EINA_INLIST_GET(next)->next); + elm_gengrid_item_selected_set(next, EINA_TRUE); + elm_gengrid_item_show(next); + return EINA_TRUE; + } + else next = elm_gengrid_item_next_get(wd->last_selected_item); + + if (!next) return EINA_FALSE; + + for (i = 1; i < wd->nmax; i++) + { + Elm_Gengrid_Item *tmp = elm_gengrid_item_next_get(next); + if (!tmp) return EINA_FALSE; + next = tmp; + } + + _deselect_all_items(wd); + + elm_gengrid_item_selected_set(next, EINA_TRUE); + elm_gengrid_item_show(next); + return EINA_TRUE; +} + +static Eina_Bool +_item_single_select_left(Widget_Data *wd) +{ + Elm_Gengrid_Item *prev; + if (!wd->selected) + { + prev = ELM_GENGRID_ITEM_FROM_INLIST(wd->items->last); + while ((prev) && (prev->delete_me)) + prev = ELM_GENGRID_ITEM_FROM_INLIST(EINA_INLIST_GET(prev)->prev); + } + else prev = elm_gengrid_item_prev_get(wd->last_selected_item); + + if (!prev) return EINA_FALSE; + + _deselect_all_items(wd); + + elm_gengrid_item_selected_set(prev, EINA_TRUE); + elm_gengrid_item_show(prev); + return EINA_TRUE; +} + +static Eina_Bool +_item_single_select_right(Widget_Data *wd) +{ + Elm_Gengrid_Item *next; + if (!wd->selected) + { + next = ELM_GENGRID_ITEM_FROM_INLIST(wd->items); + while ((next) && (next->delete_me)) + next = ELM_GENGRID_ITEM_FROM_INLIST(EINA_INLIST_GET(next)->next); + } + else next = elm_gengrid_item_next_get(wd->last_selected_item); + + if (!next) return EINA_FALSE; + + _deselect_all_items(wd); + + elm_gengrid_item_selected_set(next, EINA_TRUE); + elm_gengrid_item_show(next); + return EINA_TRUE; +} + +static void +_on_focus_hook(void *data __UNUSED__, + Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->self, "elm,action,focus", "elm"); + evas_object_focus_set(wd->self, EINA_TRUE); + if ((wd->selected) && (!wd->last_selected_item)) + wd->last_selected_item = eina_list_data_get(wd->selected); + } + else + { + edje_object_signal_emit(wd->self, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->self, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_object_theme_set(obj, wd->scr, "gengrid", "base", + elm_widget_style_get(obj)); +} + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_gengrid_clear(obj); + evas_object_del(wd->pan_smart); + wd->pan_smart = NULL; +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + free(wd); +} + +static void +_signal_emit_hook(Evas_Object *obj, + const char *emission, + const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + emission, source); +} + +static void +_mouse_move(void *data, + Evas *evas __UNUSED__, + Evas_Object *obj, + void *event_info) +{ + Elm_Gengrid_Item *item = data; + Evas_Event_Mouse_Move *ev = event_info; + Evas_Coord minw = 0, minh = 0, x, y, dx, dy, adx, ady; + + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + { + if (!item->wd->on_hold) + { + item->wd->on_hold = EINA_TRUE; + if (!item->wd->wasselected) + _item_unselect(item); + } + } + if ((item->dragging) && (item->down)) + { + if (item->long_timer) + { + ecore_timer_del(item->long_timer); + item->long_timer = NULL; + } + evas_object_smart_callback_call(item->wd->self, "drag", item); + return; + } + if ((!item->down) || (item->wd->longpressed)) + { + if (item->long_timer) + { + ecore_timer_del(item->long_timer); + item->long_timer = NULL; + } + return; + } + if (!item->display_only) + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_geometry_get(obj, &x, &y, NULL, NULL); + x = ev->cur.canvas.x - x; + y = ev->cur.canvas.y - y; + dx = x - item->dx; + adx = dx; + if (adx < 0) adx = -dx; + dy = y - item->dy; + ady = dy; + if (ady < 0) ady = -dy; + minw /= 2; + minh /= 2; + if ((adx > minw) || (ady > minh)) + { + item->dragging = 1; + if (item->long_timer) + { + ecore_timer_del(item->long_timer); + item->long_timer = NULL; + } + if (!item->wd->wasselected) + _item_unselect(item); + if (dy < 0) + { + if (ady > adx) + evas_object_smart_callback_call(item->wd->self, "drag,start,up", + item); + else + { + if (dx < 0) + evas_object_smart_callback_call(item->wd->self, + "drag,start,left", item); + } + } + else + { + if (ady > adx) + evas_object_smart_callback_call(item->wd->self, + "drag,start,down", item); + else + { + if (dx < 0) + evas_object_smart_callback_call(item->wd->self, + "drag,start,left", item); + else + evas_object_smart_callback_call(item->wd->self, + "drag,start,right", item); + } + } + } +} + +static Eina_Bool +_long_press(void *data) +{ + Elm_Gengrid_Item *item = data; + + item->long_timer = NULL; + if ((item->disabled) || (item->dragging)) return ECORE_CALLBACK_CANCEL; + item->wd->longpressed = EINA_TRUE; + evas_object_smart_callback_call(item->wd->self, "longpressed", item); + return ECORE_CALLBACK_CANCEL; +} + +static void +_mouse_down(void *data, + Evas *evas __UNUSED__, + Evas_Object *obj, + void *event_info) +{ + Elm_Gengrid_Item *item = data; + Evas_Event_Mouse_Down *ev = event_info; + Evas_Coord x, y; + + if (ev->button != 1) return; + item->down = 1; + item->dragging = 0; + evas_object_geometry_get(obj, &x, &y, NULL, NULL); + item->dx = ev->canvas.x - x; + item->dy = ev->canvas.y - y; + item->wd->longpressed = EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) item->wd->on_hold = EINA_TRUE; + else item->wd->on_hold = EINA_FALSE; + item->wd->wasselected = item->selected; + _item_hilight(item); + if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK) + evas_object_smart_callback_call(item->wd->self, "clicked", item); + if (item->long_timer) ecore_timer_del(item->long_timer); + if (item->realized) + item->long_timer = ecore_timer_add(_elm_config->longpress_timeout, + _long_press, item); + else + item->long_timer = NULL; +} + +static void +_mouse_up(void *data, + Evas *evas __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Gengrid_Item *item = data; + Evas_Event_Mouse_Up *ev = event_info; + Eina_Bool dragged = EINA_FALSE; + + if (ev->button != 1) return; + item->down = EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) item->wd->on_hold = EINA_TRUE; + else item->wd->on_hold = EINA_FALSE; + if (item->long_timer) + { + ecore_timer_del(item->long_timer); + item->long_timer = NULL; + } + if (item->dragging) + { + item->dragging = EINA_FALSE; + evas_object_smart_callback_call(item->wd->self, "drag,stop", item); + dragged = EINA_TRUE; + } + if (item->wd->on_hold) + { + item->wd->longpressed = EINA_FALSE; + item->wd->on_hold = EINA_FALSE; + return; + } + if (item->wd->longpressed) + { + item->wd->longpressed = EINA_FALSE; + if (!item->wd->wasselected) _item_unselect(item); + item->wd->wasselected = EINA_FALSE; + return; + } + if (dragged) + { + if (item->want_unrealize) _item_unrealize(item); + } + if ((item->disabled) || (dragged)) return; + if (item->wd->multi) + { + if (!item->selected) + { + _item_hilight(item); + _item_select(item); + } + else _item_unselect(item); + } + else + { + if (!item->selected) + { + while (item->wd->selected) + _item_unselect(item->wd->selected->data); + } + else + { + const Eina_List *l, *l_next; + Elm_Gengrid_Item *item2; + + EINA_LIST_FOREACH_SAFE(item->wd->selected, l, l_next, item2) + if (item2 != item) _item_unselect(item2); + } + _item_hilight(item); + _item_select(item); + } +} + +static void +_item_hilight(Elm_Gengrid_Item *item) +{ + if ((item->wd->no_select) || (item->delete_me) || (item->hilighted)) return; + edje_object_signal_emit(item->base.view, "elm,state,selected", "elm"); + item->hilighted = EINA_TRUE; +} + +static void +_item_realize(Elm_Gengrid_Item *item) +{ + char buf[1024]; + char style[1024]; + + if ((item->realized) || (item->delete_me)) return; + item->base.view = edje_object_add(evas_object_evas_get(item->wd->self)); + edje_object_scale_set(item->base.view, elm_widget_scale_get(item->wd->self) * + _elm_config->scale); + evas_object_smart_member_add(item->base.view, item->wd->pan_smart); + elm_widget_sub_object_add(item->wd->self, item->base.view); + snprintf(style, sizeof(style), "item/%s", + item->gic->item_style ? item->gic->item_style : "default"); + _elm_theme_object_set(item->wd->self, item->base.view, "gengrid", style, + elm_widget_style_get(item->wd->self)); + item->spacer = + evas_object_rectangle_add(evas_object_evas_get(item->wd->self)); + evas_object_color_set(item->spacer, 0, 0, 0, 0); + elm_widget_sub_object_add(item->wd->self, item->spacer); + evas_object_size_hint_min_set(item->spacer, 2 * _elm_config->scale, 1); + edje_object_part_swallow(item->base.view, "elm.swallow.pad", item->spacer); + + if (item->gic->func.label_get) + { + const Eina_List *l; + const char *key; + + item->labels = + elm_widget_stringlist_get(edje_object_data_get(item->base.view, + "labels")); + EINA_LIST_FOREACH(item->labels, l, key) + { + char *s = item->gic->func.label_get + ((void *)item->base.data, item->wd->self, l->data); + if (s) + { + edje_object_part_text_set(item->base.view, l->data, s); + free(s); + } + } + } + + if (item->gic->func.icon_get) + { + const Eina_List *l; + const char *key; + + item->icons = + elm_widget_stringlist_get(edje_object_data_get(item->base.view, + "icons")); + EINA_LIST_FOREACH(item->icons, l, key) + { + Evas_Object *ic = item->gic->func.icon_get + ((void *)item->base.data, item->wd->self, l->data); + if (ic) + { + item->icon_objs = eina_list_append(item->icon_objs, ic); + edje_object_part_swallow(item->base.view, key, ic); + evas_object_show(ic); + elm_widget_sub_object_add(item->wd->self, ic); + } + } + } + + if (item->gic->func.state_get) + { + const Eina_List *l; + const char *key; + + item->states = + elm_widget_stringlist_get(edje_object_data_get(item->base.view, + "states")); + EINA_LIST_FOREACH(item->states, l, key) + { + Eina_Bool on = item->gic->func.state_get + ((void *)item->base.data, item->wd->self, l->data); + if (on) + { + snprintf(buf, sizeof(buf), "elm,state,%s,active", key); + edje_object_signal_emit(item->base.view, buf, "elm"); + } + } + } + + if ((!item->wd->item_width) && (!item->wd->item_height)) + { + edje_object_size_min_restricted_calc(item->base.view, + &item->wd->item_width, + &item->wd->item_height, + item->wd->item_width, + item->wd->item_height); + elm_coords_finger_size_adjust(1, &item->wd->item_width, + 1, &item->wd->item_height); + } + + evas_object_event_callback_add(item->base.view, EVAS_CALLBACK_MOUSE_DOWN, + _mouse_down, item); + evas_object_event_callback_add(item->base.view, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, item); + evas_object_event_callback_add(item->base.view, EVAS_CALLBACK_MOUSE_MOVE, + _mouse_move, item); + + if (item->selected) + edje_object_signal_emit(item->base.view, "elm,state,selected", "elm"); + if (item->disabled) + edje_object_signal_emit(item->base.view, "elm,state,disabled", "elm"); + + evas_object_show(item->base.view); + + if (item->tooltip.content_cb) + { + elm_widget_item_tooltip_content_cb_set(item, + item->tooltip.content_cb, + item->tooltip.data, NULL); + elm_widget_item_tooltip_style_set(item, item->tooltip.style); + } + + if (item->mouse_cursor) + elm_widget_item_cursor_set(item, item->mouse_cursor); + + item->realized = EINA_TRUE; + item->want_unrealize = EINA_FALSE; +} + +static void +_item_unrealize(Elm_Gengrid_Item *item) +{ + Evas_Object *icon; + + if (!item->realized) return; + if (item->long_timer) + { + ecore_timer_del(item->long_timer); + item->long_timer = NULL; + } + evas_object_del(item->base.view); + item->base.view = NULL; + evas_object_del(item->spacer); + item->spacer = NULL; + elm_widget_stringlist_free(item->labels); + item->labels = NULL; + elm_widget_stringlist_free(item->icons); + item->icons = NULL; + elm_widget_stringlist_free(item->states); + item->states = NULL; + + EINA_LIST_FREE(item->icon_objs, icon) + evas_object_del(icon); + + item->realized = EINA_FALSE; + item->want_unrealize = EINA_FALSE; +} + +static void +_item_place(Elm_Gengrid_Item *item, + Evas_Coord cx, + Evas_Coord cy) +{ + Evas_Coord x, y, ox, oy, cvx, cvy, cvw, cvh; + Evas_Coord tch, tcw, alignw = 0, alignh = 0, vw, vh; + + item->x = cx; + item->y = cy; + evas_object_geometry_get(item->wd->pan_smart, &ox, &oy, &vw, &vh); + + /* Preload rows/columns at each side of the Gengrid */ + cvx = ox - PRELOAD * item->wd->item_width; + cvy = oy - PRELOAD * item->wd->item_height; + cvw = vw + 2 * PRELOAD * item->wd->item_width; + cvh = vh + 2 * PRELOAD * item->wd->item_height; + + alignh = 0; + alignw = 0; + + if (item->wd->horizontal) + { + int columns, items_visible = 0, items_row; + + if (item->wd->item_height > 0) + items_visible = vh / item->wd->item_height; + if (items_visible < 1) + items_visible = 1; + + columns = item->wd->count / items_visible; + if (item->wd->count % items_visible) + columns++; + + tcw = item->wd->item_width * columns; + alignw = (vw - tcw) * item->wd->align_x; + + items_row = items_visible; + if (items_row > item->wd->count) + items_row = item->wd->count; + tch = items_row * item->wd->item_height; + alignh = (vh - tch) * item->wd->align_y; + } + else + { + int rows, items_visible = 0, items_col; + + if (item->wd->item_width > 0) + items_visible = vw / item->wd->item_width; + if (items_visible < 1) + items_visible = 1; + + rows = item->wd->count / items_visible; + if (item->wd->count % items_visible) + rows++; + + tch = item->wd->item_height * rows; + alignh = (vh - tch) * item->wd->align_y; + + items_col = items_visible; + if (items_col > item->wd->count) + items_col = item->wd->count; + tcw = items_col * item->wd->item_width; + alignw = (vw - tcw) * item->wd->align_x; + } + + x = cx * item->wd->item_width - item->wd->pan_x + ox + alignw; + y = cy * item->wd->item_height - item->wd->pan_y + oy + alignh; + + Eina_Bool was_realized = item->realized; + if (ELM_RECTS_INTERSECT(x, y, item->wd->item_width, item->wd->item_height, + cvx, cvy, cvw, cvh)) + { + _item_realize(item); + if (!was_realized) + evas_object_smart_callback_call(item->wd->self, "realized", item); + evas_object_move(item->base.view, x, y); + evas_object_resize(item->base.view, item->wd->item_width, + item->wd->item_height); + } + else + { + _item_unrealize(item); + if (was_realized) + evas_object_smart_callback_call(item->wd->self, "unrealized", item); + } +} + +static Elm_Gengrid_Item * +_item_create(Widget_Data *wd, + const Elm_Gengrid_Item_Class *gic, + const void *data, + Evas_Smart_Cb func, + const void *func_data) +{ + Elm_Gengrid_Item *item; + + item = elm_widget_item_new(wd->self, Elm_Gengrid_Item); + if (!item) return NULL; + wd->count++; + item->wd = wd; + item->gic = gic; + item->base.data = data; + item->func.func = func; + item->func.data = func_data; + item->mouse_cursor = NULL; + return item; +} + +static void +_item_del(Elm_Gengrid_Item *item) +{ + elm_widget_item_pre_notify_del(item); + if (item->selected) + item->wd->selected = eina_list_remove(item->wd->selected, item); + if (item->realized) _item_unrealize(item); + if ((!item->delete_me) && (item->gic->func.del)) + item->gic->func.del((void *)item->base.data, item->wd->self); + item->delete_me = EINA_TRUE; + item->wd->items = eina_inlist_remove(item->wd->items, EINA_INLIST_GET(item)); + if (item->long_timer) ecore_timer_del(item->long_timer); + if (item->tooltip.del_cb) + item->tooltip.del_cb((void *)item->tooltip.data, item->base.widget, item); + item->wd->walking -= item->walking; + item->wd->count--; + if (item->wd->calc_job) ecore_job_del(item->wd->calc_job); + item->wd->calc_job = ecore_job_add(_calc_job, item->wd); + elm_widget_item_del(item); +} + +static void +_item_select(Elm_Gengrid_Item *item) +{ + if ((item->wd->no_select) || (item->delete_me)) return; + if (item->selected) + { + if (item->wd->always_select) goto call; + return; + } + item->selected = EINA_TRUE; + item->wd->selected = eina_list_append(item->wd->selected, item); +call: + item->walking++; + item->wd->walking++; + if (item->func.func) + item->func.func((void *)item->func.data, item->wd->self, item); + if (!item->delete_me) + evas_object_smart_callback_call(item->wd->self, "selected", item); + item->walking--; + item->wd->walking--; + if ((item->wd->clear_me) && (!item->wd->walking)) + elm_gengrid_clear(item->base.widget); + else + { + if ((!item->walking) && (item->delete_me)) + if (!item->relcount) _item_del(item); + } + item->wd->last_selected_item = item; +} + +static void +_item_unselect(Elm_Gengrid_Item *item) +{ + if ((item->delete_me) || (!item->hilighted)) return; + edje_object_signal_emit(item->base.view, "elm,state,unselected", "elm"); + item->hilighted = EINA_FALSE; + if (item->selected) + { + item->selected = EINA_FALSE; + item->wd->selected = eina_list_remove(item->wd->selected, item); + evas_object_smart_callback_call(item->wd->self, "unselected", item); + } +} + +static void +_calc_job(void *data) +{ + Widget_Data *wd = data; + Evas_Coord minw = 0, minh = 0, nmax = 0, cvw, cvh; + int count; + + evas_object_geometry_get(wd->pan_smart, NULL, NULL, &cvw, &cvh); + if ((wd->horizontal) && (wd->item_height > 0)) + nmax = cvh / wd->item_height; + else if (wd->item_width > 0) + nmax = cvw / wd->item_width; + + if (nmax < 1) + nmax = 1; + + count = wd->count; + if (wd->horizontal) + { + minw = ceil(count / (float)nmax) * wd->item_width; + minh = nmax * wd->item_height; + } + else + { + minw = nmax * wd->item_width; + minh = ceil(count / (float)nmax) * wd->item_height; + } + + if ((minw != wd->minw) || (minh != wd->minh)) + { + wd->minh = minh; + wd->minw = minw; + evas_object_smart_callback_call(wd->pan_smart, "changed", NULL); + } + + wd->nmax = nmax; + wd->calc_job = NULL; + evas_object_smart_changed(wd->pan_smart); +} + +static void +_pan_add(Evas_Object *obj) +{ + Pan *sd; + Evas_Object_Smart_Clipped_Data *cd; + + _pan_sc.add(obj); + cd = evas_object_smart_data_get(obj); + sd = ELM_NEW(Pan); + if (!sd) return; + sd->__clipped_data = *cd; + free(cd); + evas_object_smart_data_set(obj, sd); +} + +static void +_pan_del(Evas_Object *obj) +{ + Pan *sd = evas_object_smart_data_get(obj); + + if (!sd) return; + _pan_sc.del(obj); +} + +static void +_pan_set(Evas_Object *obj, + Evas_Coord x, + Evas_Coord y) +{ + Pan *sd = evas_object_smart_data_get(obj); + if ((x == sd->wd->pan_x) && (y == sd->wd->pan_y)) return; + sd->wd->pan_x = x; + sd->wd->pan_y = y; + evas_object_smart_changed(obj); +} + +static void +_pan_get(Evas_Object *obj, + Evas_Coord *x, + Evas_Coord *y) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (x) *x = sd->wd->pan_x; + if (y) *y = sd->wd->pan_y; +} + +static void +_pan_child_size_get(Evas_Object *obj, + Evas_Coord *w, + Evas_Coord *h) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (w) *w = sd->wd->minw; + if (h) *h = sd->wd->minh; +} + +static void +_pan_max_get(Evas_Object *obj, + Evas_Coord *x, + Evas_Coord *y) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ow, oh; + + if (!sd) return; + evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); + if (x) + *x = (ow < sd->wd->minw) ? sd->wd->minw - ow : 0; + if (y) + *y = (oh < sd->wd->minh) ? sd->wd->minh - oh : 0; +} + +static void +_pan_min_get(Evas_Object *obj, + Evas_Coord *x, + Evas_Coord *y) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord mx, my; + + if (!sd) return; + _pan_max_get(obj, &mx, &my); + if (x) + *x = -mx * sd->wd->align_x; + if (y) + *y = -my * sd->wd->align_y; +} + +static void +_pan_resize(Evas_Object *obj, + Evas_Coord w, + Evas_Coord h) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ow, oh; + + evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); + if ((ow == w) && (oh == h)) return; + if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job); + sd->wd->calc_job = ecore_job_add(_calc_job, sd->wd); +} + +static void +_pan_calculate(Evas_Object *obj) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord cx = 0, cy = 0; + Elm_Gengrid_Item *item; + + if (!sd) return; + if (!sd->wd->nmax) return; + + EINA_INLIST_FOREACH(sd->wd->items, item) + { + _item_place(item, cx, cy); + if (sd->wd->horizontal) + { + cy = (cy + 1) % sd->wd->nmax; + if (!cy) cx++; + } + else + { + cx = (cx + 1) % sd->wd->nmax; + if (!cx) cy++; + } + } + evas_object_smart_callback_call(sd->wd->self, "changed", NULL); +} + +static void +_pan_move(Evas_Object *obj, + Evas_Coord x __UNUSED__, + Evas_Coord y __UNUSED__) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job); + sd->wd->calc_job = ecore_job_add(_calc_job, sd->wd); +} + +static void +_hold_on(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_hold_set(wd->scr, 1); +} + +static void +_hold_off(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_hold_set(wd->scr, 0); +} + +static void +_freeze_on(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_freeze_set(wd->scr, 1); +} + +static void +_freeze_off(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_freeze_set(wd->scr, 0); +} + +static void +_scr_drag_start(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll,drag,start", NULL); +} + +static void +_scr_drag_stop(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll,drag,stop", NULL); +} + +static void +_scr_scroll(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll", NULL); +} + +/** + * Add a new Gengrid object. + * + * @param parent The parent object. + * @return The new object or NULL if it cannot be created. + * + * @see elm_gengrid_item_size_set() + * @see elm_gengrid_horizontal_set() + * @see elm_gengrid_item_append() + * @see elm_gengrid_item_del() + * @see elm_gengrid_clear() + * + * @ingroup Gengrid + */ +EAPI Evas_Object * +elm_gengrid_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + static Evas_Smart *smart = NULL; + Eina_Bool bounce = _elm_config->thumbscroll_bounce_enable; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "gengrid"); + elm_widget_type_set(obj, "gengrid"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->scr = elm_smart_scroller_add(e); + elm_smart_scroller_widget_set(wd->scr, obj); + elm_smart_scroller_object_theme_set(obj, wd->scr, "gengrid", "base", + "default"); + elm_widget_resize_object_set(obj, wd->scr); + + evas_object_smart_callback_add(wd->scr, "drag,start", _scr_drag_start, obj); + evas_object_smart_callback_add(wd->scr, "drag,stop", _scr_drag_stop, obj); + evas_object_smart_callback_add(wd->scr, "scroll", _scr_scroll, obj); + + elm_smart_scroller_bounce_allow_set(wd->scr, bounce, bounce); + + wd->self = obj; + wd->align_x = 0.5; + wd->align_y = 0.5; + wd->no_select = EINA_FALSE; + + evas_object_smart_callback_add(obj, "scroll-hold-on", _hold_on, obj); + evas_object_smart_callback_add(obj, "scroll-hold-off", _hold_off, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-on", _freeze_on, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-off", _freeze_off, obj); + + if (!smart) + { + static Evas_Smart_Class sc; + + evas_object_smart_clipped_smart_set(&_pan_sc); + sc = _pan_sc; + sc.name = "elm_gengrid_pan"; + sc.version = EVAS_SMART_CLASS_VERSION; + sc.add = _pan_add; + sc.del = _pan_del; + sc.resize = _pan_resize; + sc.move = _pan_move; + sc.calculate = _pan_calculate; + smart = evas_smart_class_new(&sc); + } + if (smart) + { + wd->pan_smart = evas_object_smart_add(e, smart); + wd->pan = evas_object_smart_data_get(wd->pan_smart); + wd->pan->wd = wd; + } + + elm_smart_scroller_extern_pan_set(wd->scr, wd->pan_smart, + _pan_set, _pan_get, _pan_max_get, + _pan_min_get, _pan_child_size_get); + + return obj; +} + +/** + * Set the size for the item of the Gengrid. + * + * @param obj The Gengrid object. + * @param w The item's width. + * @param h The item's height; + * + * @see elm_gengrid_item_size_get() + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_size_set(Evas_Object *obj, + Evas_Coord w, + Evas_Coord h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if ((wd->item_width == w) && (wd->item_height == h)) return; + wd->item_width = w; + wd->item_height = h; + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); +} + +/** + * Get the size of the item of the Gengrid. + * + * @param obj The Gengrid object. + * @param w Pointer to the item's width. + * @param h Pointer to the item's height. + * + * @see elm_gengrid_item_size_get() + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_size_get(const Evas_Object *obj, + Evas_Coord *w, + Evas_Coord *h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (w) *w = wd->item_width; + if (h) *h = wd->item_height; +} + +/** + * Set item's alignment within the scroller. + * + * @param obj The Gengrid object. + * @param align_x The x alignment (0 <= x <= 1). + * @param align_y The y alignment (0 <= y <= 1). + * + * @see elm_gengrid_align_get() + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_align_set(Evas_Object *obj, + double align_x, + double align_y) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (align_x > 1.0) + align_x = 1.0; + else if (align_x < 0.0) + align_x = 0.0; + wd->align_x = align_x; + + if (align_y > 1.0) + align_y = 1.0; + else if (align_y < 0.0) + align_y = 0.0; + wd->align_y = align_y; +} + +/** + * Get the alignenment set for the Gengrid object. + * + * @param obj The Gengrid object. + * @param align_x Pointer to x alignenment. + * @param align_y Pointer to y alignenment. + * + * @see elm_gengrid_align_set() + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_align_get(const Evas_Object *obj, + double *align_x, + double *align_y) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (align_x) *align_x = wd->align_x; + if (align_y) *align_y = wd->align_y; +} + +/** + * Add item to the end of the Gengrid. + * + * @param obj The Gengrid object. + * @param gic The item class for the item. + * @param data The item data. + * @param func Convenience function called when item is selected. + * @param func_data Data passed to @p func above. + * @return A handle to the item added or NULL if not possible. + * + * @see elm_gengrid_item_prepend() + * @see elm_gengrid_item_insert_before() + * @see elm_gengrid_item_insert_after() + * @see elm_gengrid_item_del() + * + * @ingroup Gengrid + */ +EAPI Elm_Gengrid_Item * +elm_gengrid_item_append(Evas_Object *obj, + const Elm_Gengrid_Item_Class *gic, + const void *data, + Evas_Smart_Cb func, + const void *func_data) +{ + Elm_Gengrid_Item *item; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + item = _item_create(wd, gic, data, func, func_data); + if (!item) return NULL; + wd->items = eina_inlist_append(wd->items, EINA_INLIST_GET(item)); + + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + + return item; +} + +/** + * Add item at start of the Gengrid. + * + * This adds an item to the beginning of the grid. + * + * @param obj The Gengrid object. + * @param gic The item class for the item. + * @param data The item data. + * @param func Convenience function called when item is selected. + * @param func_data Data passed to @p func above. + * @return A handle to the item added or NULL if not possible. + * + * @see elm_gengrid_item_append() + * @see elm_gengrid_item_insert_before() + * @see elm_gengrid_item_insert_after() + * @see elm_gengrid_item_del() + * + * @ingroup Gengrid + */ +EAPI Elm_Gengrid_Item * +elm_gengrid_item_prepend(Evas_Object *obj, + const Elm_Gengrid_Item_Class *gic, + const void *data, + Evas_Smart_Cb func, + const void *func_data) +{ + Elm_Gengrid_Item *item; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + item = _item_create(wd, gic, data, func, func_data); + if (!item) return NULL; + wd->items = eina_inlist_prepend(wd->items, EINA_INLIST_GET(item)); + + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + + return item; +} + +/** + * Insert and item before another in the Gengrid. + * + * This inserts an item before another in the grid. + * + * @param obj The Gengrid object. + * @param gic The item class for the item. + * @param data The item data. + * @param relative The item to which insert before. + * @param func Convenience function called when item is selected. + * @param func_data Data passed to @p func above. + * @return A handle to the item added or NULL if not possible. + * + * @see elm_gengrid_item_append() + * @see elm_gengrid_item_prepend() + * @see elm_gengrid_item_insert_after() + * @see elm_gengrid_item_del() + * + * @ingroup Gengrid + */ +EAPI Elm_Gengrid_Item * +elm_gengrid_item_insert_before(Evas_Object *obj, + const Elm_Gengrid_Item_Class *gic, + const void *data, + Elm_Gengrid_Item *relative, + Evas_Smart_Cb func, + const void *func_data) +{ + Elm_Gengrid_Item *item; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + EINA_SAFETY_ON_NULL_RETURN_VAL(relative, NULL); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + item = _item_create(wd, gic, data, func, func_data); + if (!item) return NULL; + wd->items = eina_inlist_prepend_relative + (wd->items, EINA_INLIST_GET(item), EINA_INLIST_GET(relative)); + + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + + return item; +} + +/** + * Insert and item after another in the Gengrid. + * + * This inserts an item after another in the grid. + * + * @param obj The Gengrid object. + * @param gic The item class for the item. + * @param data The item data. + * @param relative The item to which insert after. + * @param func Convenience function called when item is selected. + * @param func_data Data passed to @p func above. + * @return A handle to the item added or NULL if not possible. + * + * @see elm_gengrid_item_append() + * @see elm_gengrid_item_prepend() + * @see elm_gengrid_item_insert_before() + * @see elm_gengrid_item_del() + * + * @ingroup Gengrid + */ +EAPI Elm_Gengrid_Item * +elm_gengrid_item_insert_after(Evas_Object *obj, + const Elm_Gengrid_Item_Class *gic, + const void *data, + Elm_Gengrid_Item *relative, + Evas_Smart_Cb func, + const void *func_data) +{ + Elm_Gengrid_Item *item; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + EINA_SAFETY_ON_NULL_RETURN_VAL(relative, NULL); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + item = _item_create(wd, gic, data, func, func_data); + if (!item) return NULL; + wd->items = eina_inlist_append_relative + (wd->items, EINA_INLIST_GET(item), EINA_INLIST_GET(relative)); + + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + + return item; +} + +/** + * Remove a item from the Gengrid. + * + * @param item The item to be removed. + * @return @c EINA_TRUE on success or @c EINA_FALSE otherwise. + * + * @see elm_gengrid_clear() to remove all items of the Gengrid. + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_del(Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if ((item->relcount > 0) || (item->walking > 0)) + { + item->delete_me = EINA_TRUE; + elm_widget_item_pre_notify_del(item); + if (item->selected) + item->wd->selected = eina_list_remove(item->wd->selected, item); + if (item->gic->func.del) + item->gic->func.del((void *)item->base.data, item->wd->self); + return; + } + + _item_del(item); +} + +/** + * Set for what direction the Gengrid will expand. + * + * @param obj The Gengrid object. + * @param setting If @c EINA_TRUE the Gengrid will expand horizontally + * or vertically if @c EINA_FALSE. + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_horizontal_set(Evas_Object *obj, + Eina_Bool setting) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (setting == wd->horizontal) return; + wd->horizontal = setting; + + /* Update the items to conform to the new layout */ + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); +} + +/** + * Clear the Gengrid + * + * This clears all items in the Gengrid, leaving it empty. + * + * @param obj The Gengrid object. + * + * @see elm_gengrid_item_del() to remove just one item. + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_clear(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (wd->calc_job) + { + ecore_job_del(wd->calc_job); + wd->calc_job = NULL; + } + + if (wd->walking > 0) + { + Elm_Gengrid_Item *item; + wd->clear_me = 1; + EINA_INLIST_FOREACH(wd->items, item) + item->delete_me = 1; + return; + } + wd->clear_me = 0; + while (wd->items) + { + Elm_Gengrid_Item *item = ELM_GENGRID_ITEM_FROM_INLIST(wd->items); + + wd->items = eina_inlist_remove(wd->items, wd->items); + elm_widget_item_pre_notify_del(item); + if (item->realized) _item_unrealize(item); + if (item->gic->func.del) + item->gic->func.del((void *)item->base.data, wd->self); + if (item->long_timer) ecore_timer_del(item->long_timer); + elm_widget_item_del(item); + } + + if (wd->selected) + { + eina_list_free(wd->selected); + wd->selected = NULL; + } + + wd->pan_x = 0; + wd->pan_y = 0; + wd->minw = 0; + wd->minh = 0; + wd->count = 0; + evas_object_size_hint_min_set(wd->pan_smart, wd->minw, wd->minh); + evas_object_smart_callback_call(wd->pan_smart, "changed", NULL); +} + +/** + * Get the real evas object of the Gengrid item + * + * This returns the actual evas object used for the specified Gengrid + * item. This may be NULL as it may not be created, and may be + * deleted at any time by Gengrid. Do not modify this object (move, + * resize, show, hide etc.) as Gengrid is controlling it. This + * function is for querying, emitting custom signals or hooking lower + * level callbacks for events. Do not delete this object under any + * circumstances. + * + * @param item The Gengrid item. + * @return the evas object associated to this item. + * + * @see elm_gengrid_item_data_get() + * + * @ingroup Gengrid + */ +EAPI const Evas_Object * +elm_gengrid_item_object_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->base.view; +} + +/** + * Update the contents of an item + * + * This updates an item by calling all the item class functions again + * to get the icons, labels and states. Use this when the original + * item data has changed and the changes are desired to be reflected. + * + * @param item The item + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_update(Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (!item->realized) return; + if (item->want_unrealize) return; + _item_unrealize(item); + _item_realize(item); + _item_place(item, item->x, item->y); +} + +/** + * Returns the data associated to a item + * + * This returns the data value passed on the elm_gengrid_item_append() + * and related item addition calls. + * + * @param item The Gengrid item. + * @return the data associated to this item. + * + * @see elm_gengrid_item_append() + * @see elm_gengrid_item_object_get() + * + * @ingroup Gengrid + */ +EAPI void * +elm_gengrid_item_data_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_data_get(item); +} + +/** + * Set the data item from the gengrid item + * + * This set the data value passed on the elm_gengrid_item_append() and + * related item addition calls. This function will also call + * elm_gengrid_item_update() so the item will be updated to reflect + * the new data. + * + * @param item The item + * @param data The new data pointer to set + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_data_set(Elm_Gengrid_Item *item, + const void *data) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_data_set(item, data); + elm_gengrid_item_update(item); +} + +/** + * Get the item's coordinates. + * + * This returns the logical position of the item whithin the Gengrid. + * + * @param item The Gengrid item. + * @param x The x-axis coordinate pointer. + * @param y The y-axis coordinate pointer. + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_pos_get(const Elm_Gengrid_Item *item, + unsigned int *x, + unsigned int *y) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (x) *x = item->x; + if (y) *y = item->y; +} + +/** + * Enable or disable multi-select in the Gengrid. + * + * This enables (EINA_TRUE) or disables (EINA_FALSE) multi-select in + * the Gengrid. This allows more than 1 item to be selected. + * + * @param obj The Gengrid object. + * @param multi Multi-select enabled/disabled + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_multi_select_set(Evas_Object *obj, + Eina_Bool multi) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->multi = multi; +} + +/** + * Get if multi-select in Gengrid is enabled or disabled + * + * @param obj The Gengrid object + * @return Multi-select enable/disable + * (EINA_TRUE = enabled / EINA_FALSE = disabled) + * + * @ingroup Gengrid + */ +EAPI Eina_Bool +elm_gengrid_multi_select_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->multi; +} + +/** + * Get the selected item in the Gengrid + * + * This gets the selected item in the Gengrid (if multi-select is + * enabled only the first item in the list is selected - which is not + * very useful, so see elm_gengrid_selected_items_get() for when + * multi-select is used). + * + * If no item is selected, NULL is returned. + * + * @param obj The Gengrid object. + * @return The selected item, or NULL if none. + * + * @ingroup Gengrid + */ +EAPI Elm_Gengrid_Item * +elm_gengrid_selected_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (wd->selected) return wd->selected->data; + return NULL; +} + +/** + * Get a list of selected items in the Gengrid. + * + * This returns a list of the selected items. This list pointer is + * only valid so long as no items are selected or unselected (or + * unselected implictly by deletion). The list contains + * Elm_Gengrid_Item pointers. + * + * @param obj The Gengrid object. + * @return The list of selected items, or NULL if none are selected. + * + * @ingroup Gengrid + */ +EAPI const Eina_List * +elm_gengrid_selected_items_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->selected; +} + +/** + * Set the selected state of a item. + * + * This sets the selected state of a item. If multi-select is not + * enabled and selected is EINA_TRUE, previously selected items are + * unselected. + * + * @param item The item + * @param selected The selected state. + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_selected_set(Elm_Gengrid_Item *item, + Eina_Bool selected) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + Widget_Data *wd = item->wd; + if (!wd) return; + if ((!item) || (item->delete_me)) return; + selected = !!selected; + if (item->selected == selected) return; + + if (selected) + { + if (!wd->multi) + { + while (wd->selected) + _item_unselect(wd->selected->data); + } + _item_hilight(item); + _item_select(item); + } + else + _item_unselect(item); +} + +/** + * Get the selected state of a item. + * + * This gets the selected state of a item (1 selected, 0 not selected). + * + * @param item The item + * @return The selected state + * + * @ingroup Gengrid + */ +EAPI Eina_Bool +elm_gengrid_item_selected_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + return item->selected; +} + +/** + * Sets the disabled state of a item. + * + * A disabled item cannot be selected or unselected. It will also + * change appearance to disabled. This sets the disabled state (1 + * disabled, 0 not disabled). + * + * @param item The item + * @param disabled The disabled state + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_disabled_set(Elm_Gengrid_Item *item, + Eina_Bool disabled) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (item->disabled == disabled) return; + if (item->delete_me) return; + item->disabled = disabled; + if (item->realized) + { + if (item->disabled) + edje_object_signal_emit(item->base.view, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(item->base.view, "elm,state,enabled", "elm"); + } +} + +/** + * Get the disabled state of a item. + * + * This gets the disabled state of the given item. + * + * @param item The item + * @return The disabled state + * + * @ingroup Gengrid + */ +EAPI Eina_Bool +elm_gengrid_item_disabled_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + if (item->delete_me) return EINA_FALSE; + return item->disabled; +} + +static Evas_Object * +_elm_gengrid_item_label_create(void *data, + Evas_Object *obj, + void *item __UNUSED__) +{ + Evas_Object *label = elm_label_add(obj); + if (!label) + return NULL; + elm_object_style_set(label, "tooltip"); + elm_label_label_set(label, data); + return label; +} + +static void +_elm_gengrid_item_label_del_cb(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + eina_stringshare_del(data); +} + +/** + * Set the text to be shown in the gengrid item. + * + * @param item Target item + * @param text The text to set in the content + * + * Setup the text as tooltip to object. The item can have only one + * tooltip, so any previous tooltip data is removed. + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_tooltip_text_set(Elm_Gengrid_Item *item, + const char *text) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + text = eina_stringshare_add(text); + elm_gengrid_item_tooltip_content_cb_set(item, _elm_gengrid_item_label_create, + text, + _elm_gengrid_item_label_del_cb); +} + +/** + * Set the content to be shown in the tooltip item + * + * Setup the tooltip to item. The item can have only one tooltip, so + * any previous tooltip data is removed. @p func(with @p data) will be + * called every time that need show the tooltip and it should return a + * valid Evas_Object. This object is then managed fully by tooltip + * system and is deleted when the tooltip is gone. + * + * @param item the gengrid item being attached a tooltip. + * @param func the function used to create the tooltip contents. + * @param data what to provide to @a func as callback data/context. + * @param del_cb called when data is not needed anymore, either when + * another callback replaces @func, the tooltip is unset with + * elm_gengrid_item_tooltip_unset() or the owner @a item + * dies. This callback receives as the first parameter the + * given @a data, and @c event_info is the item. + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_tooltip_content_cb_set(Elm_Gengrid_Item *item, + Elm_Tooltip_Item_Content_Cb func, + const void *data, + Evas_Smart_Cb del_cb) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_GOTO(item, error); + + if ((item->tooltip.content_cb == func) && (item->tooltip.data == data)) + return; + + if (item->tooltip.del_cb) + item->tooltip.del_cb((void *)item->tooltip.data, + item->base.widget, item); + item->tooltip.content_cb = func; + item->tooltip.data = data; + item->tooltip.del_cb = del_cb; + if (item->base.view) + { + elm_widget_item_tooltip_content_cb_set(item, + item->tooltip.content_cb, + item->tooltip.data, NULL); + elm_widget_item_tooltip_style_set(item, item->tooltip.style); + } + + return; + +error: + if (del_cb) del_cb((void *)data, NULL, NULL); +} + +/** + * Unset tooltip from item + * + * @param item gengrid item to remove previously set tooltip. + * + * Remove tooltip from item. The callback provided as del_cb to + * elm_gengrid_item_tooltip_content_cb_set() will be called to notify + * it is not used anymore. + * + * @see elm_gengrid_item_tooltip_content_cb_set() + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_tooltip_unset(Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if ((item->base.view) && (item->tooltip.content_cb)) + elm_widget_item_tooltip_unset(item); + + if (item->tooltip.del_cb) + item->tooltip.del_cb((void *)item->tooltip.data, item->base.widget, item); + item->tooltip.del_cb = NULL; + item->tooltip.content_cb = NULL; + item->tooltip.data = NULL; + if (item->tooltip.style) + elm_gengrid_item_tooltip_style_set(item, NULL); +} + +/** + * Sets a different style for this item tooltip. + * + * @note before you set a style you should define a tooltip with + * elm_gengrid_item_tooltip_content_cb_set() or + * elm_gengrid_item_tooltip_text_set() + * + * @param item gengrid item with tooltip already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_tooltip_style_set(Elm_Gengrid_Item *item, + const char *style) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + eina_stringshare_replace(&item->tooltip.style, style); + if (item->base.view) elm_widget_item_tooltip_style_set(item, style); +} + +/** + * Get the style for this item tooltip. + * + * @param item gengrid item with tooltip already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a tooltip set, then NULL is returned. + * + * @ingroup Gengrid + */ +EAPI const char * +elm_gengrid_item_tooltip_style_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->tooltip.style; +} + +/** + * Set the cursor to be shown when mouse is over the gengrid item + * + * @param item Target item + * @param cursor the cursor name to be used. + * + * @see elm_object_cursor_set() + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_cursor_set(Elm_Gengrid_Item *item, + const char *cursor) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + eina_stringshare_replace(&item->mouse_cursor, cursor); + if (item->base.view) elm_widget_item_cursor_set(item, cursor); +} + +/** + * Get the cursor to be shown when mouse is over the gengrid item + * + * @param item gengrid item with cursor already set. + * @return the cursor name. + * + * @ingroup Gengrid + */ +EAPI const char * +elm_gengrid_item_cursor_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_cursor_get(item); +} + +/** + * Unset the cursor to be shown when mouse is over the gengrid item + * + * @param item Target item + * + * @see elm_object_cursor_unset() + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_cursor_unset(Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (!item->mouse_cursor) + return; + + if (item->base.view) + elm_widget_item_cursor_unset(item); + + eina_stringshare_del(item->mouse_cursor); + item->mouse_cursor = NULL; +} + +/** + * Sets a different style for this item cursor. + * + * @note before you set a style you should define a cursor with + * elm_gengrid_item_cursor_set() + * + * @param item gengrid item with cursor already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_cursor_style_set(Elm_Gengrid_Item *item, + const char *style) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_cursor_style_set(item, style); +} + +/** + * Get the style for this item cursor. + * + * @param item gengrid item with cursor already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a cursor set, then NULL is returned. + * + * @ingroup Gengrid + */ +EAPI const char * +elm_gengrid_item_cursor_style_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_cursor_style_get(item); +} + +/** + * Set if the cursor set should be searched on the theme or should use + * the provided by the engine, only. + * + * @note before you set if should look on theme you should define a + * cursor with elm_object_cursor_set(). By default it will only look + * for cursors provided by the engine. + * + * @param item widget item with cursor already set. + * @param engine_only boolean to define it cursors should be looked + * only between the provided by the engine or searched on widget's + * theme as well. + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_cursor_engine_only_set(Elm_Gengrid_Item *item, + Eina_Bool engine_only) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_cursor_engine_only_set(item, engine_only); +} + +/** + * Get the cursor engine only usage for this item cursor. + * + * @param item widget item with cursor already set. + * @return engine_only boolean to define it cursors should be looked + * only between the provided by the engine or searched on widget's + * theme as well. If the object does not have a cursor set, then + * EINA_FALSE is returned. + * + * @ingroup Gengrid + */ +EAPI Eina_Bool +elm_gengrid_item_cursor_engine_only_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + return elm_widget_item_cursor_engine_only_get(item); +} + +/** + * Set the always select mode. + * + * Cells will only call their selection func and callback when first + * becoming selected. Any further clicks will do nothing, unless you + * enable always select with + * elm_gengrid_always_select_mode_set(). This means even if selected, + * every click will make the selected callbacks be called. + * + * @param obj The Gengrid object + * @param always_select The always select mode (EINA_TRUE = on, + * EINA_FALSE = off) + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_always_select_mode_set(Evas_Object *obj, + Eina_Bool always_select) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->always_select = always_select; +} + +/** + * Get the always select mode. + * + * @param obj The Gengrid object. + * @return The always select mode (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Gengrid + */ +EAPI Eina_Bool +elm_gengrid_always_select_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->always_select; +} + +/** + * Set no select mode. + * + * This will turn off the ability to select items entirely and they + * will neither appear selected nor call selected callback functions. + * + * @param obj The Gengrid object + * @param no_select The no select mode (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_no_select_mode_set(Evas_Object *obj, + Eina_Bool no_select) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->no_select = no_select; +} + +/** + * Gets no select mode. + * + * @param obj The Gengrid object + * @return The no select mode (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Gengrid + */ +EAPI Eina_Bool +elm_gengrid_no_select_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->no_select; +} + +/** + * Set bounce mode. + * + * This will enable or disable the scroller bounce mode for the + * Gengrid. See elm_scroller_bounce_set() for details. + * + * @param obj The Gengrid object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_bounce_set(Evas_Object *obj, + Eina_Bool h_bounce, + Eina_Bool v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_bounce_allow_set(wd->scr, h_bounce, v_bounce); +} + +/** + * Get the bounce mode + * + * @param obj The Gengrid object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_bounce_get(const Evas_Object *obj, + Eina_Bool *h_bounce, + Eina_Bool *v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_bounce_allow_get(wd->scr, h_bounce, v_bounce); +} + +/** + * Get all items in the Gengrid. + * + * This returns a list of the Gengrid items. The list contains + * Elm_Gengrid_Item pointers. + * + * @param obj The Gengrid object. + * @return The list of items, or NULL if none. + * + * @ingroup Gengrid + */ + +/** + * Set gengrid scroll page size relative to viewport size. + * + * The gengrid scroller is capable of limiting scrolling by the user + * to "pages" That is to jump by and only show a "whole page" at a + * time as if the continuous area of the scroller content is split + * into page sized pieces. This sets the size of a page relative to + * the viewport of the scroller. 1.0 is "1 viewport" is size + * (horizontally or vertically). 0.0 turns it off in that axis. This + * is mutually exclusive with page size (see + * elm_gengrid_page_size_set() for more information). Likewise 0.5 is + * "half a viewport". Sane usable valus are normally between 0.0 and + * 1.0 including 1.0. If you only want 1 axis to be page "limited", + * use 0.0 for the other axis. + * + * @param obj The gengrid object + * @param h_pagerel The horizontal page relative size + * @param v_pagerel The vertical page relative size + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_page_relative_set(Evas_Object *obj, + double h_pagerel, + double v_pagerel) +{ + Evas_Coord pagesize_h; + Evas_Coord pagesize_v; + + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + elm_smart_scroller_paging_get(wd->scr, NULL, NULL, &pagesize_h, &pagesize_v); + elm_smart_scroller_paging_set(wd->scr, h_pagerel, v_pagerel, pagesize_h, + pagesize_v); +} + +/** + * Set gengrid scroll page size. + * + * See also elm_gengrid_page_relative_set(). This, instead of a page + * size being relative to the viewport, sets it to an absolute fixed + * value, with 0 turning it off for that axis. + * + * @param obj The gengrid object + * @param h_pagesize The horizontal page size + * @param v_pagesize The vertical page size + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_page_size_set(Evas_Object *obj, + Evas_Coord h_pagesize, + Evas_Coord v_pagesize) +{ + double pagerel_h; + double pagerel_v; + + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_paging_get(wd->scr, &pagerel_h, &pagerel_v, NULL, NULL); + elm_smart_scroller_paging_set(wd->scr, pagerel_h, pagerel_v, h_pagesize, + v_pagesize); +} + +/** + * Get the first item in the gengrid + * + * This returns the first item in the list. + * + * @param obj The gengrid object + * @return The first item, or NULL if none + * + * @ingroup Gengrid + */ +EAPI Elm_Gengrid_Item * +elm_gengrid_first_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->items) return NULL; + Elm_Gengrid_Item *item = ELM_GENGRID_ITEM_FROM_INLIST(wd->items); + while ((item) && (item->delete_me)) + item = ELM_GENGRID_ITEM_FROM_INLIST(EINA_INLIST_GET(item)->next); + return item; +} + +/** + * Get the last item in the gengrid + * + * This returns the last item in the list. + * + * @return The last item, or NULL if none + * + * @ingroup Gengrid + */ +EAPI Elm_Gengrid_Item * +elm_gengrid_last_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd->items) return NULL; + Elm_Gengrid_Item *item = ELM_GENGRID_ITEM_FROM_INLIST(wd->items->last); + if (!wd) return NULL; + while ((item) && (item->delete_me)) + item = ELM_GENGRID_ITEM_FROM_INLIST(EINA_INLIST_GET(item)->prev); + return item; +} + +/** + * Get the next item in the gengrid + * + * This returns the item after the item @p item. + * + * @param item The item + * @return The item after @p item, or NULL if none + * + * @ingroup Gengrid + */ +EAPI Elm_Gengrid_Item * +elm_gengrid_item_next_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + while (item) + { + item = ELM_GENGRID_ITEM_FROM_INLIST(EINA_INLIST_GET(item)->next); + if ((item) && (!item->delete_me)) break; + } + return (Elm_Gengrid_Item *)item; +} + +/** + * Get the previous item in the gengrid + * + * This returns the item before the item @p item. + * + * @param item The item + * @return The item before @p item, or NULL if none + * + * @ingroup Gengrid + */ +EAPI Elm_Gengrid_Item * +elm_gengrid_item_prev_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + while (item) + { + item = ELM_GENGRID_ITEM_FROM_INLIST(EINA_INLIST_GET(item)->prev); + if ((item) && (!item->delete_me)) break; + } + return (Elm_Gengrid_Item *)item; +} + +/** + * Get the gengrid object from an item + * + * This returns the gengrid object itself that an item belongs to. + * + * @param item The item + * @return The gengrid object + * + * @ingroup Gengrid + */ +EAPI Evas_Object * +elm_gengrid_item_gengrid_get(const Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->base.widget; +} + +/** + * Show the given item + * + * This causes gengrid to jump to the given item @p item and show it + * (by scrolling), if it is not fully visible. + * + * @param item The item + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_show(Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + Widget_Data *wd = elm_widget_data_get(item->wd->self); + Evas_Coord minx = 0, miny = 0; + + if (!wd) return; + if ((!item) || (item->delete_me)) return; + _pan_min_get(wd->pan_smart, &minx, &miny); + + elm_smart_scroller_child_region_show(item->wd->scr, + item->x * wd->item_width + minx, + item->y * wd->item_height + miny, + item->wd->item_width, + item->wd->item_height); +} + +/** + * Bring in the given item + * + * This causes gengrig to jump to the given item @p item and show it + * (by scrolling), if it is not fully visible. This may use animation + * to do so and take a period of time + * + * @param item The item + * + * @ingroup Gengrid + */ +EAPI void +elm_gengrid_item_bring_in(Elm_Gengrid_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (item->delete_me) return; + + Evas_Coord minx = 0, miny = 0; + Widget_Data *wd = elm_widget_data_get(item->wd->self); + if (!wd) return; + _pan_min_get(wd->pan_smart, &minx, &miny); + + elm_smart_scroller_region_bring_in(item->wd->scr, + item->x * wd->item_width + minx, + item->y * wd->item_height + miny, + item->wd->item_width, + item->wd->item_height); +} diff --git a/src/lib/elm_genlist.c b/src/lib/elm_genlist.c new file mode 100644 index 0000000..b162574 --- /dev/null +++ b/src/lib/elm_genlist.c @@ -0,0 +1,4873 @@ +#include +#include +#include "elm_priv.h" + +#define SWIPE_MOVES 12 +#define MAX_ITEMS_PER_BLOCK 32 +#define LONGPRESS_TIMEOUT 1.0 + +/** + * @defgroup Genlist Genlist + * + * The aim was to have more expansive list than the simple list in + * Elementary that could have more flexible items and allow many more entries + * while still being fast and low on memory usage. At the same time it was + * also made to be able to do tree structures. But the price to pay is more + * complex when it comes to usage. If all you want is a simple list with + * icons and a single label, use the normal List object. + * + * Signals that you can add callbacks for are: + * + * clicked - This is called when a user has double-clicked an item. The + * event_info parameter is the genlist item that was double-clicked. + * + * selected - This is called when a user has made an item selected. The + * event_info parameter is the genlist item that was selected. + * + * unselected - This is called when a user has made an item unselected. The + * event_info parameter is the genlist item that was unselected. + * + * expanded - This is called when elm_genlist_item_expanded_set() is called + * and the item is now meant to be expanded. The event_info parameter is the + * genlist item that was indicated to expand. It is the job of this callback + * to then fill in the child items. + * + * contracted - This is called when elm_genlist_item_expanded_set() is called + * and the item is now meant to be contracted. The event_info parameter is + * the genlist item that was indicated to contract. It is the job of this + * callback to then delete the child items. + * + * expand,request - This is called when a user has indicated they want to + * expand a tree branch item. The callback should decide if the item can + * expand (has any children) and then call elm_genlist_item_expanded_set() + * appropriately to set the state. The event_info parameter is the genlist + * item that was indicated to expand. + * + * contract,request - This is called when a user has indicated they want to + * contract a tree branch item. The callback should decide if the item can + * contract (has any children) and then call elm_genlist_item_expanded_set() + * appropriately to set the state. The event_info parameter is the genlist + * item that was indicated to contract. + * + * realized - This is called when the item in the list is created as a real + * evas object. event_info parameter is the genlist item that was created. + * The object may be deleted at any time, so it is up to the caller to + * not use the object pointer from elm_genlist_item_object_get() in a way + * where it may point to freed objects. + * + * unrealized - This is called just before an item is unrealized. After + * this call icon objects provided will be deleted and the item object + * itself delete or be put into a floating cache. + * + * drag,start,up - This is called when the item in the list has been dragged + * (not scrolled) up. + * + * drag,start,down - This is called when the item in the list has been dragged + * (not scrolled) down. + * + * drag,start,left - This is called when the item in the list has been dragged + * (not scrolled) left. + * + * drag,start,right - This is called when the item in the list has been dragged + * (not scrolled) right. + * + * drag,stop - This is called when the item in the list has stopped being + * dragged. + * + * drag - This is called when the item in the list is being dragged. + * + * longpressed - This is called when the item is pressed for a certain amount + * of time. By default it's 1 second. + * + * scroll,edge,top - This is called when the genlist is scrolled until the top + * edge. + * + * scroll,edge,bottom - This is called when the genlist is scrolled until the + * bottom edge. + * + * scroll,edge,left - This is called when the genlist is scrolled until the + * left edge. + * + * scroll,edge,right - This is called when the genlist is scrolled until the + * right edge. + * + * multi,swipe,left - This is called when the genlist is multi-touch swiped + * left. + * + * multi,swipe,right - This is called when the genlist is multi-touch swiped + * right. + * + * multi,swipe,up - This is called when the genlist is multi-touch swiped + * up. + * + * multi,swipe,down - This is called when the genlist is multi-touch swiped + * down. + * + * multi,pinch,out - This is called when the genlist is multi-touch pinched + * out. + * + * multi,pinch,in - This is called when the genlist is multi-touch pinched + * in. + * + * Genlist has a fairly large API, mostly because it's relatively complex, + * trying to be both expansive, powerful and efficient. First we will begin + * an overview on the theory behind genlist. + * + * Evas tracks every object you create. Every time it processes an event + * (mouse move, down, up etc.) it needs to walk through objects and find out + * what event that affects. Even worse every time it renders display updates, + * in order to just calculate what to re-draw, it needs to walk through many + * many many objects. Thus, the more objects you keep active, the more + * overhead Evas has in just doing its work. It is advisable to keep your + * active objects to the minimum working set you need. Also remember that + * object creation and deletion carries an overhead, so there is a + * middle-ground, which is not easily determined. But don't keep massive lists + * of objects you can't see or use. Genlist does this with list objects. It + * creates and destroys them dynamically as you scroll around. It groups them + * into blocks so it can determine the visibility etc. of a whole block at + * once as opposed to having to walk the whole list. This 2-level list allows + * for very large numbers of items to be in the list (tests have used up to + * 2,000,000 items). Also genlist employs a queue for adding items. As items + * may be different sizes, every item added needs to be calculated as to its + * size and thus this presents a lot of overhead on populating the list, this + * genlist employs a queue. Any item added is queued and spooled off over + * time, actually appearing some time later, so if your list has many members + * you may find it takes a while for them to all appear, with your process + * consuming a lot of CPU while it is busy spooling. + * + * Genlist also implements a tree structure, but it does so with callbacks to + * the application, with the application filling in tree structures when + * requested (allowing for efficient building of a very deep tree that could + * even be used for file-management). See the above smart signal callbacks for + * details. + * + * An item in the genlist world can have 0 or more text labels (they can be + * regular text or textblock – that's up to the style to determine), 0 or + * more icons (which are simply objects swallowed into the genlist item) and + * 0 or more boolean states that can be used for check, radio or other + * indicators by the edje theme style. An item may be one of several styles + * (Elementary provides 4 by default - “default”, “double_label”, "group_index" + * and "icon_top_text_bottom", but this can be extended by system or + * application custom themes/overlays/extensions). + * + * In order to implement the ability to add and delete items on the fly, + * Genlist implements a class/callback system where the application provides + * a structure with information about that type of item (genlist may contain + * multiple different items with different classes, states and styles). + * Genlist will call the functions in this struct (methods) when an item is + * “realized” (that is created dynamically while scrolling). All objects will + * simply be deleted when no longer needed with evas_object_del(). The + * Elm_Genlist_Item_Class structure contains the following members: + * + * item_style - This is a constant string and simply defines the name of the + * item style. It must be specified and the default should be “default”. + * + * func.label_get - This function is called when an actual item object is + * created. The data parameter is the data parameter passed to + * elm_genlist_item_append() and related item creation functions. The obj + * parameter is the genlist object and the part parameter is the string name + * of the text part in the edje design that is listed as one of the possible + * labels that can be set. This function must return a strudup()'ed string as + * the caller will free() it when done. + * + * func.icon_get - This function is called when an actual item object is + * created. The data parameter is the data parameter passed to + * elm_genlist_item_append() and related item creation functions. The obj + * parameter is the genlist object and the part parameter is the string name + * of the icon part in the edje design that is listed as one of the possible + * icons that can be set. This must return NULL for no object or a valid + * object. The object will be deleted by genlist on shutdown or when the item + * is unrealized. + * + * func.state_get - This function is called when an actual item object is + * created. The data parameter is the data parameter passed to + * elm_genlist_item_append() and related item creation functions. The obj + * parameter is the genlist object and the part parameter is the string name + * of the state part in the edje design that is listed as one of the possible + * states that can be set. Return 0 for false or 1 for true. Genlist will + * emit a signal to the edje object with “elm,state,XXX,active” “elm” when + * true (the default is false), where XXX is the name of the part. + * + * func.del - This is called when elm_genlist_item_del() is called on an + * item, elm_genlist_clear() is called on the genlist, or + * elm_genlist_item_subitems_clear() is called to clear sub-items. This is + * intended for use when actual genlist items are deleted, so any backing + * data attached to the item (e.g. its data parameter on creation) can be + * deleted. + * + * Items can be added by several calls. All of them return a Elm_Genlist_Item + * handle that is an internal member inside the genlist. They all take a data + * parameter that is meant to be used for a handle to the applications + * internal data (eg the struct with the original item data). The parent + * parameter is the parent genlist item this belongs to if it is a tree or + * an indexed group, and NULL if there is no parent. The flags can be a bitmask + * of ELM_GENLIST_ITEM_NONE, ELM_GENLIST_ITEM_SUBITEMS and + * ELM_GENLIST_ITEM_GROUP. If ELM_GENLIST_ITEM_SUBITEMS is set then this item + * is displayed as an item that is able to expand and have child items. + * If ELM_GENLIST_ITEM_GROUP is set then this item is group idex item that is + * displayed at the top until the next group comes. The func parameter is a + * convenience callback that is called when the item is selected and the data + * parameter will be the func_data parameter, obj be the genlist object and + * event_info will be the genlist item. + * + * elm_genlist_item_append() appends an item to the end of the list, or if + * there is a parent, to the end of all the child items of the parent. + * elm_genlist_item_prepend() is the same but prepends to the beginning of + * the list or children list. elm_genlist_item_insert_before() inserts at + * item before another item and elm_genlist_item_insert_after() inserts after + * the indicated item. + * + * The application can clear the list with elm_genlist_clear() which deletes + * all the items in the list and elm_genlist_item_del() will delete a specific + * item. elm_genlist_item_subitems_clear() will clear all items that are + * children of the indicated parent item. + * + * If the application wants multiple items to be able to be selected, + * elm_genlist_multi_select_set() can enable this. If the list is + * single-selection only (the default), then elm_genlist_selected_item_get() + * will return the selected item, if any, or NULL I none is selected. If the + * list is multi-select then elm_genlist_selected_items_get() will return a + * list (that is only valid as long as no items are modified (added, deleted, + * selected or unselected)). + * + * To help inspect list items you can jump to the item at the top of the list + * with elm_genlist_first_item_get() which will return the item pointer, and + * similarly elm_genlist_last_item_get() gets the item at the end of the list. + * elm_genlist_item_next_get() and elm_genlist_item_prev_get() get the next + * and previous items respectively relative to the indicated item. Using + * these calls you can walk the entire item list/tree. Note that as a tree + * the items are flattened in the list, so elm_genlist_item_parent_get() will + * let you know which item is the parent (and thus know how to skip them if + * wanted). + * + * There are also convenience functions. elm_genlist_item_genlist_get() will + * return the genlist object the item belongs to. elm_genlist_item_show() + * will make the scroller scroll to show that specific item so its visible. + * elm_genlist_item_data_get() returns the data pointer set by the item + * creation functions. + * + * If an item changes (state of boolean changes, label or icons change), + * then use elm_genlist_item_update() to have genlist update the item with + * the new state. Genlist will re-realize the item thus call the functions + * in the _Elm_Genlist_Item_Class for that item. + * + * To programmatically (un)select an item use elm_genlist_item_selected_set(). + * To get its selected state use elm_genlist_item_selected_get(). Similarly + * to expand/contract an item and get its expanded state, use + * elm_genlist_item_expanded_set() and elm_genlist_item_expanded_get(). And + * again to make an item disabled (unable to be selected and appear + * differently) use elm_genlist_item_disabled_set() to set this and + * elm_genlist_item_disabled_get() to get the disabled state. + * + * In general to indicate how the genlist should expand items horizontally to + * fill the list area, use elm_genlist_horizontal_mode_set(). Valid modes are + * ELM_LIST_LIMIT and ELM_LIST_SCROLL . The default is ELM_LIST_SCROLL. This + * mode means that if items are too wide to fit, the scroller will scroll + * horizontally. Otherwise items are expanded to fill the width of the + * viewport of the scroller. If it is ELM_LIST_LIMIT, items will be expanded + * to the viewport width and limited to that size. This can be combined with + * a different style that uses edjes' ellipsis feature (cutting text off like + * this: “tex...”). + * + * Items will only call their selection func and callback when first becoming + * selected. Any further clicks will do nothing, unless you enable always + * select with elm_genlist_always_select_mode_set(). This means even if + * selected, every click will make the selected callbacks be called. + * elm_genlist_no_select_mode_set() will turn off the ability to select + * items entirely and they will neither appear selected nor call selected + * callback functions. + * + * Remember that you can create new styles and add your own theme augmentation + * per application with elm_theme_extension_add(). If you absolutely must + * have a specific style that overrides any theme the user or system sets up + * you can use elm_theme_overlay_add() to add such a file. + */ + +typedef struct _Widget_Data Widget_Data; +typedef struct _Item_Block Item_Block; +typedef struct _Pan Pan; +typedef struct _Item_Cache Item_Cache; + +struct _Widget_Data +{ + Evas_Object *obj, *scr, *pan_smart; + Eina_Inlist *items, *blocks; + Eina_List *group_items; + Pan *pan; + Evas_Coord pan_x, pan_y, w, h, minw, minh, realminw, prev_viewport_w; + Ecore_Job *calc_job, *update_job; + Ecore_Idler *queue_idler; + Ecore_Idler *must_recalc_idler; + Eina_List *queue, *selected; + Elm_Genlist_Item *show_item; + Elm_Genlist_Item *last_selected_item; + Eina_Inlist *item_cache; + Elm_Genlist_Item *anchor_item; + Evas_Coord anchor_y; + Elm_List_Mode mode; + Ecore_Timer *multi_timer; + Evas_Coord prev_x, prev_y, prev_mx, prev_my; + Evas_Coord cur_x, cur_y, cur_mx, cur_my; + Eina_Bool mouse_down : 1; + Eina_Bool multi_down : 1; + Eina_Bool multi_timeout : 1; + Eina_Bool multitouched : 1; + Eina_Bool on_hold : 1; + Eina_Bool multi : 1; + Eina_Bool always_select : 1; + Eina_Bool longpressed : 1; + Eina_Bool wasselected : 1; + Eina_Bool no_select : 1; + Eina_Bool bring_in : 1; + Eina_Bool compress : 1; + Eina_Bool height_for_width : 1; + Eina_Bool homogeneous : 1; + Eina_Bool clear_me : 1; + Eina_Bool swipe : 1; + struct + { + Evas_Coord x, y; + } history[SWIPE_MOVES]; + int multi_device; + int item_cache_count; + int item_cache_max; + int movements; + int walking; + int item_width; + int item_height; + int max_items_per_block; + double longpress_timeout; +}; + +struct _Item_Block +{ + EINA_INLIST; + int count; + int num; + Widget_Data *wd; + Eina_List *items; + Evas_Coord x, y, w, h, minw, minh; + Eina_Bool want_unrealize : 1; + Eina_Bool realized : 1; + Eina_Bool changed : 1; + Eina_Bool updateme : 1; + Eina_Bool showme : 1; + Eina_Bool must_recalc : 1; +}; + +struct _Elm_Genlist_Item +{ + Elm_Widget_Item base; + EINA_INLIST; + Widget_Data *wd; + Item_Block *block; + Eina_List *items; + Evas_Coord x, y, w, h, minw, minh; + const Elm_Genlist_Item_Class *itc; + Elm_Genlist_Item *parent; + Elm_Genlist_Item *group_item; + Elm_Genlist_Item_Flags flags; + struct + { + Evas_Smart_Cb func; + const void *data; + } func; + + Evas_Object *spacer; + Eina_List *labels, *icons, *states, *icon_objs; + Ecore_Timer *long_timer; + Ecore_Timer *swipe_timer; + Evas_Coord dx, dy; + Evas_Coord scrl_x, scrl_y; + + Elm_Genlist_Item *rel; + + struct + { + const void *data; + Elm_Tooltip_Item_Content_Cb content_cb; + Evas_Smart_Cb del_cb; + const char *style; + } tooltip; + + const char *mouse_cursor; + + int relcount; + int walking; + int expanded_depth; + int order_num_in; + + Eina_Bool before : 1; + + Eina_Bool want_unrealize : 1; + Eina_Bool want_realize : 1; + Eina_Bool realized : 1; + Eina_Bool selected : 1; + Eina_Bool hilighted : 1; + Eina_Bool expanded : 1; + Eina_Bool disabled : 1; + Eina_Bool display_only : 1; + Eina_Bool mincalcd : 1; + Eina_Bool queued : 1; + Eina_Bool showme : 1; + Eina_Bool delete_me : 1; + Eina_Bool down : 1; + Eina_Bool dragging : 1; + Eina_Bool updateme : 1; +}; + +struct _Item_Cache +{ + EINA_INLIST; + + Evas_Object *base_view, *spacer; + + const char *item_style; // it->itc->item_style + Eina_Bool tree : 1; // it->flags & ELM_GENLIST_ITEM_SUBITEMS + Eina_Bool compress : 1; // it->wd->compress + Eina_Bool odd : 1; // in & 0x1 + + Eina_Bool selected : 1; // it->selected + Eina_Bool disabled : 1; // it->disabled + Eina_Bool expanded : 1; // it->expanded +}; + +#define ELM_GENLIST_ITEM_FROM_INLIST(item) \ + ((item) ? EINA_INLIST_CONTAINER_GET(item, Elm_Genlist_Item) : NULL) + +struct _Pan +{ + Evas_Object_Smart_Clipped_Data __clipped_data; + Widget_Data *wd; + Ecore_Job *resize_job; +}; + +static const char *widtype = NULL; +static void _item_cache_zero(Widget_Data *wd); +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +//static void _show_region_hook(void *data, Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _item_unrealize(Elm_Genlist_Item *it); +static void _item_block_unrealize(Item_Block *itb); +static void _calc_job(void *data); +static void _on_focus_hook(void *data, + Evas_Object *obj); +static Eina_Bool _item_multi_select_up(Widget_Data *wd); +static Eina_Bool _item_multi_select_down(Widget_Data *wd); +static Eina_Bool _item_single_select_up(Widget_Data *wd); +static Eina_Bool _item_single_select_down(Widget_Data *wd); +static Eina_Bool _event_hook(Evas_Object *obj, + Evas_Object *src, + Evas_Callback_Type type, + void *event_info); +static Eina_Bool _deselect_all_items(Widget_Data *wd); +static void _pan_calculate(Evas_Object *obj); + +static Evas_Smart_Class _pan_sc = EVAS_SMART_CLASS_INIT_VERSION; + +static Eina_Bool +_event_hook(Evas_Object *obj, + Evas_Object *src __UNUSED__, + Evas_Callback_Type type, + void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (!wd->items) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + + Elm_Genlist_Item *it = NULL; + Evas_Coord x = 0; + Evas_Coord y = 0; + Evas_Coord step_x = 0; + Evas_Coord step_y = 0; + Evas_Coord v_w = 0; + Evas_Coord v_h = 0; + Evas_Coord page_x = 0; + Evas_Coord page_y = 0; + + elm_smart_scroller_child_pos_get(wd->scr, &x, &y); + elm_smart_scroller_step_size_get(wd->scr, &step_x, &step_y); + elm_smart_scroller_page_size_get(wd->scr, &page_x, &page_y); + elm_smart_scroller_child_viewport_size_get(wd->scr, &v_w, &v_h); + + if ((!strcmp(ev->keyname, "Left")) || (!strcmp(ev->keyname, "KP_Left"))) + { + x -= step_x; + } + else if ((!strcmp(ev->keyname, "Right")) || + (!strcmp(ev->keyname, "KP_Right"))) + { + x += step_x; + } + else if ((!strcmp(ev->keyname, "Up")) || (!strcmp(ev->keyname, "KP_Up"))) + { + if (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_up(wd))) + || (_item_single_select_up(wd))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + y -= step_y; + } + else if ((!strcmp(ev->keyname, "Down")) || (!strcmp(ev->keyname, "KP_Down"))) + { + if (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_down(wd))) + || (_item_single_select_down(wd))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + y += step_y; + } + else if ((!strcmp(ev->keyname, "Home")) || + (!strcmp(ev->keyname, "KP_Home"))) + { + it = elm_genlist_first_item_get(obj); + elm_genlist_item_bring_in(it); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "End")) || + (!strcmp(ev->keyname, "KP_End"))) + { + it = elm_genlist_last_item_get(obj); + elm_genlist_item_bring_in(it); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "Prior")) || + (!strcmp(ev->keyname, "KP_Prior"))) + { + if (page_y < 0) + y -= -(page_y * v_h) / 100; + else + y -= page_y; + } + else if ((!strcmp(ev->keyname, "Next")) || + (!strcmp(ev->keyname, "KP_Next"))) + { + if (page_y < 0) + y += -(page_y * v_h) / 100; + else + y += page_y; + } + else if(((!strcmp(ev->keyname, "Return")) || + (!strcmp(ev->keyname, "KP_Enter")) || + (!strcmp(ev->keyname, "space"))) + && (!wd->multi) && (wd->selected)) + { + Elm_Genlist_Item *it = elm_genlist_selected_item_get(obj); + elm_genlist_item_expanded_set(it, + !elm_genlist_item_expanded_get(it)); + } + else if (!strcmp(ev->keyname, "Escape")) + { + if (!_deselect_all_items(wd)) return EINA_FALSE; + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else return EINA_FALSE; + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + elm_smart_scroller_child_pos_set(wd->scr, x, y); + return EINA_TRUE; +} + +static Eina_Bool +_deselect_all_items(Widget_Data *wd) +{ + if (!wd->selected) return EINA_FALSE; + while(wd->selected) + elm_genlist_item_selected_set(wd->selected->data, EINA_FALSE); + + return EINA_TRUE; +} + +static Eina_Bool +_item_multi_select_up(Widget_Data *wd) +{ + if (!wd->selected) return EINA_FALSE; + if (!wd->multi) return EINA_FALSE; + + Elm_Genlist_Item *prev = elm_genlist_item_prev_get(wd->last_selected_item); + if (!prev) return EINA_TRUE; + + if (elm_genlist_item_selected_get(prev)) + { + elm_genlist_item_selected_set(wd->last_selected_item, EINA_FALSE); + wd->last_selected_item = prev; + elm_genlist_item_show(wd->last_selected_item); + } + else + { + elm_genlist_item_selected_set(prev, EINA_TRUE); + elm_genlist_item_show(prev); + } + return EINA_TRUE; +} + +static Eina_Bool +_item_multi_select_down(Widget_Data *wd) +{ + if (!wd->selected) return EINA_FALSE; + if (!wd->multi) return EINA_FALSE; + + Elm_Genlist_Item *next = elm_genlist_item_next_get(wd->last_selected_item); + if (!next) return EINA_TRUE; + + if (elm_genlist_item_selected_get(next)) + { + elm_genlist_item_selected_set(wd->last_selected_item, EINA_FALSE); + wd->last_selected_item = next; + elm_genlist_item_show(wd->last_selected_item); + } + else + { + elm_genlist_item_selected_set(next, EINA_TRUE); + elm_genlist_item_show(next); + } + return EINA_TRUE; +} + +static Eina_Bool +_item_single_select_up(Widget_Data *wd) +{ + Elm_Genlist_Item *prev; + if (!wd->selected) + { + prev = ELM_GENLIST_ITEM_FROM_INLIST(wd->items->last); + while ((prev) && (prev->delete_me)) + prev = ELM_GENLIST_ITEM_FROM_INLIST(EINA_INLIST_GET(prev)->prev); + } + else prev = elm_genlist_item_prev_get(wd->last_selected_item); + + if (!prev) return EINA_FALSE; + + _deselect_all_items(wd); + + elm_genlist_item_selected_set(prev, EINA_TRUE); + elm_genlist_item_show(prev); + return EINA_TRUE; +} + +static Eina_Bool +_item_single_select_down(Widget_Data *wd) +{ + Elm_Genlist_Item *next; + if (!wd->selected) + { + next = ELM_GENLIST_ITEM_FROM_INLIST(wd->items); + while ((next) && (next->delete_me)) + next = ELM_GENLIST_ITEM_FROM_INLIST(EINA_INLIST_GET(next)->next); + } + else next = elm_genlist_item_next_get(wd->last_selected_item); + + if (!next) return EINA_FALSE; + + _deselect_all_items(wd); + + elm_genlist_item_selected_set(next, EINA_TRUE); + elm_genlist_item_show(next); + return EINA_TRUE; +} + +static void +_on_focus_hook(void *data __UNUSED__, + Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->obj, "elm,action,focus", "elm"); + evas_object_focus_set(wd->obj, EINA_TRUE); + if ((wd->selected) && (!wd->last_selected_item)) + wd->last_selected_item = eina_list_data_get(wd->selected); + } + else + { + edje_object_signal_emit(wd->obj, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->obj, EINA_FALSE); + } +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _item_cache_zero(wd); + if (wd->calc_job) ecore_job_del(wd->calc_job); + if (wd->update_job) ecore_job_del(wd->update_job); + if (wd->must_recalc_idler) ecore_idler_del(wd->must_recalc_idler); + if (wd->multi_timer) ecore_timer_del(wd->multi_timer); + free(wd); +} + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_del(wd->pan_smart); + wd->pan_smart = NULL; + elm_genlist_clear(obj); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Item_Block *itb; + if (!wd) return; + _item_cache_zero(wd); + elm_smart_scroller_object_theme_set(obj, wd->scr, "genlist", "base", + elm_widget_style_get(obj)); +// edje_object_scale_set(wd->scr, elm_widget_scale_get(obj) * _elm_config->scale); + wd->item_width = wd->item_height = 0; + wd->minw = wd->minh = wd->realminw = 0; + EINA_INLIST_FOREACH(wd->blocks, itb) + { + Eina_List *l; + Elm_Genlist_Item *it; + + if (itb->realized) _item_block_unrealize(itb); + EINA_LIST_FOREACH(itb->items, l, it) + it->mincalcd = EINA_FALSE; + + itb->changed = EINA_TRUE; + } + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + _sizing_eval(obj); +} + +/* + static void + _show_region_hook(void *data, Evas_Object *obj) + { + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord x, y, w, h; + if (!wd) return; + elm_widget_show_region_get(obj, &x, &y, &w, &h); + elm_smart_scroller_child_region_show(wd->scr, x, y, w, h); + } + */ + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + evas_object_size_hint_min_get(wd->scr, &minw, &minh); + evas_object_size_hint_max_get(wd->scr, &maxw, &maxh); + minh = -1; + if (wd->height_for_width) + { + Evas_Coord vw, vh; + + elm_smart_scroller_child_viewport_size_get(wd->scr, &vw, &vh); + if ((vw != 0) && (vw != wd->prev_viewport_w)) + { + Item_Block *itb; + + wd->prev_viewport_w = vw; + EINA_INLIST_FOREACH(wd->blocks, itb) + { + itb->must_recalc = EINA_TRUE; + } + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + } + } + if (wd->mode == ELM_LIST_LIMIT) + { + Evas_Coord vmw, vmh, vw, vh; + + minw = wd->realminw; + maxw = -1; + elm_smart_scroller_child_viewport_size_get(wd->scr, &vw, &vh); + if ((minw > 0) && (vw < minw)) vw = minw; + else if ((maxw > 0) && (vw > maxw)) + vw = maxw; + edje_object_size_min_calc + (elm_smart_scroller_edje_object_get(wd->scr), &vmw, &vmh); + minw = vmw + minw; + } + else + { + Evas_Coord vmw, vmh; + + edje_object_size_min_calc + (elm_smart_scroller_edje_object_get(wd->scr), &vmw, &vmh); + minw = vmw; + minh = vmh; + } + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_item_hilight(Elm_Genlist_Item *it) +{ + const char *selectraise; + if ((it->wd->no_select) || (it->delete_me) || (it->hilighted)) return; + edje_object_signal_emit(it->base.view, "elm,state,selected", "elm"); + selectraise = edje_object_data_get(it->base.view, "selectraise"); + if ((selectraise) && (!strcmp(selectraise, "on"))) + { + evas_object_raise(it->base.view); + if ((it->group_item) && (it->group_item->realized)) + evas_object_raise(it->group_item->base.view); + } + it->hilighted = EINA_TRUE; +} + +static void +_item_block_del(Elm_Genlist_Item *it) +{ + Eina_Inlist *il; + Item_Block *itb = it->block; + + itb->items = eina_list_remove(itb->items, it); + itb->count--; + itb->changed = EINA_TRUE; + if (it->wd->calc_job) ecore_job_del(it->wd->calc_job); + it->wd->calc_job = ecore_job_add(_calc_job, it->wd); + if (itb->count < 1) + { + il = EINA_INLIST_GET(itb); + Item_Block *itbn = (Item_Block *)(il->next); + if (it->parent) + it->parent->items = eina_list_remove(it->parent->items, it); + else + it->wd->blocks = eina_inlist_remove(it->wd->blocks, il); + free(itb); + if (itbn) itbn->changed = EINA_TRUE; + } + else + { + if (itb->count < 16) + { + il = EINA_INLIST_GET(itb); + Item_Block *itbp = (Item_Block *)(il->prev); + Item_Block *itbn = (Item_Block *)(il->next); + if ((itbp) && ((itbp->count + itb->count) < 48)) + { + Elm_Genlist_Item *it2; + + EINA_LIST_FREE(itb->items, it2) + { + it2->block = itbp; + itbp->items = eina_list_append(itbp->items, it2); + itbp->count++; + itbp->changed = EINA_TRUE; + } + it->wd->blocks = eina_inlist_remove(it->wd->blocks, + EINA_INLIST_GET(itb)); + free(itb); + } + else if ((itbn) && ((itbn->count + itb->count) < 48)) + { + while (itb->items) + { + Eina_List *last = eina_list_last(itb->items); + Elm_Genlist_Item *it2 = last->data; + + it2->block = itbn; + itb->items = eina_list_remove_list(itb->items, last); + itbn->items = eina_list_prepend(itbn->items, it2); + itbn->count++; + itbn->changed = EINA_TRUE; + } + it->wd->blocks = + eina_inlist_remove(it->wd->blocks, EINA_INLIST_GET(itb)); + free(itb); + } + } + } +} + +static void +_item_del(Elm_Genlist_Item *it) +{ + elm_widget_item_pre_notify_del(it); + elm_genlist_item_subitems_clear(it); + it->wd->walking -= it->walking; + if (it->wd->show_item == it) it->wd->show_item = NULL; + if (it->selected) it->wd->selected = eina_list_remove(it->wd->selected, it); + if (it->realized) _item_unrealize(it); + if (it->block) _item_block_del(it); + if ((!it->delete_me) && (it->itc->func.del)) + it->itc->func.del((void *)it->base.data, it->base.widget); + it->delete_me = EINA_TRUE; + if (it->queued) + it->wd->queue = eina_list_remove(it->wd->queue, it); + if (it->wd->anchor_item == it) + { + it->wd->anchor_item = (Elm_Genlist_Item *)(EINA_INLIST_GET(it)->next); + if (!it->wd->anchor_item) + it->wd->anchor_item = (Elm_Genlist_Item *)(EINA_INLIST_GET(it)->prev); + } + it->wd->items = eina_inlist_remove(it->wd->items, EINA_INLIST_GET(it)); + if (it->parent) + it->parent->items = eina_list_remove(it->parent->items, it); + if (it->flags & ELM_GENLIST_ITEM_GROUP) + it->wd->group_items = eina_list_remove(it->wd->group_items, it); + if (it->long_timer) ecore_timer_del(it->long_timer); + if (it->swipe_timer) ecore_timer_del(it->swipe_timer); + + if (it->tooltip.del_cb) + it->tooltip.del_cb((void *)it->tooltip.data, it->base.widget, it); + + elm_widget_item_del(it); +} + +static void +_item_select(Elm_Genlist_Item *it) +{ + if ((it->wd->no_select) || (it->delete_me)) return; + if (it->selected) + { + if (it->wd->always_select) goto call; + return; + } + it->selected = EINA_TRUE; + it->wd->selected = eina_list_append(it->wd->selected, it); +call: + it->walking++; + it->wd->walking++; + if (it->func.func) it->func.func((void *)it->func.data, it->base.widget, it); + if (!it->delete_me) + evas_object_smart_callback_call(it->base.widget, "selected", it); + it->walking--; + it->wd->walking--; + if ((it->wd->clear_me) && (!it->wd->walking)) + elm_genlist_clear(it->base.widget); + else + { + if ((!it->walking) && (it->delete_me)) + { + if (!it->relcount) _item_del(it); + } + } + it->wd->last_selected_item = it; +} + +static void +_item_unselect(Elm_Genlist_Item *it) +{ + const char *stacking, *selectraise; + + if ((it->delete_me) || (!it->hilighted)) return; + edje_object_signal_emit(it->base.view, "elm,state,unselected", "elm"); + stacking = edje_object_data_get(it->base.view, "stacking"); + selectraise = edje_object_data_get(it->base.view, "selectraise"); + if ((selectraise) && (!strcmp(selectraise, "on"))) + { + if ((stacking) && (!strcmp(stacking, "below"))) + evas_object_lower(it->base.view); + } + it->hilighted = EINA_FALSE; + if (it->selected) + { + it->selected = EINA_FALSE; + it->wd->selected = eina_list_remove(it->wd->selected, it); + evas_object_smart_callback_call(it->base.widget, "unselected", it); + } +} + +static void +_mouse_move(void *data, + Evas *evas __UNUSED__, + Evas_Object *obj, + void *event_info) +{ + Elm_Genlist_Item *it = data; + Evas_Event_Mouse_Move *ev = event_info; + Evas_Coord minw = 0, minh = 0, x, y, dx, dy, adx, ady; + + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + { + if (!it->wd->on_hold) + { + it->wd->on_hold = EINA_TRUE; + if (!it->wd->wasselected) + _item_unselect(it); + } + } + if (it->wd->multitouched) + { + it->wd->cur_x = ev->cur.canvas.x; + it->wd->cur_y = ev->cur.canvas.y; + return; + } + if ((it->dragging) && (it->down)) + { + if (it->wd->movements == SWIPE_MOVES) it->wd->swipe = EINA_TRUE; + else + { + it->wd->history[it->wd->movements].x = ev->cur.canvas.x; + it->wd->history[it->wd->movements].y = ev->cur.canvas.y; + if (abs((it->wd->history[it->wd->movements].x - + it->wd->history[0].x)) > 40) + it->wd->swipe = EINA_TRUE; + else + it->wd->movements++; + } + if (it->long_timer) + { + ecore_timer_del(it->long_timer); + it->long_timer = NULL; + } + evas_object_smart_callback_call(it->base.widget, "drag", it); + return; + } + if ((!it->down) /* || (it->wd->on_hold)*/ || (it->wd->longpressed)) + { + if (it->long_timer) + { + ecore_timer_del(it->long_timer); + it->long_timer = NULL; + } + return; + } + if (!it->display_only) + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_geometry_get(obj, &x, &y, NULL, NULL); + x = ev->cur.canvas.x - x; + y = ev->cur.canvas.y - y; + dx = x - it->dx; + adx = dx; + if (adx < 0) adx = -dx; + dy = y - it->dy; + ady = dy; + if (ady < 0) ady = -dy; + minw /= 2; + minh /= 2; + if ((adx > minw) || (ady > minh)) + { + it->dragging = EINA_TRUE; + if (it->long_timer) + { + ecore_timer_del(it->long_timer); + it->long_timer = NULL; + } + if (!it->wd->wasselected) + _item_unselect(it); + if (dy < 0) + { + if (ady > adx) + evas_object_smart_callback_call(it->base.widget, + "drag,start,up", it); + else + { + if (dx < 0) + evas_object_smart_callback_call(it->base.widget, + "drag,start,left", it); + else + evas_object_smart_callback_call(it->base.widget, + "drag,start,right", it); + } + } + else + { + if (ady > adx) + evas_object_smart_callback_call(it->base.widget, + "drag,start,down", it); + else + { + if (dx < 0) + evas_object_smart_callback_call(it->base.widget, + "drag,start,left", it); + else + evas_object_smart_callback_call(it->base.widget, + "drag,start,right", it); + } + } + } +} + +static Eina_Bool +_long_press(void *data) +{ + Elm_Genlist_Item *it = data; + + it->long_timer = NULL; + if ((it->disabled) || (it->dragging) || (it->display_only)) + return ECORE_CALLBACK_CANCEL; + it->wd->longpressed = EINA_TRUE; + evas_object_smart_callback_call(it->base.widget, "longpressed", it); + return ECORE_CALLBACK_CANCEL; +} + +static void +_swipe(Elm_Genlist_Item *it) +{ + int i, sum = 0; + + if (!it) return; + it->wd->swipe = EINA_FALSE; + for (i = 0; i < it->wd->movements; i++) + { + sum += it->wd->history[i].x; + if (abs(it->wd->history[0].y - it->wd->history[i].y) > 10) return; + } + + sum /= it->wd->movements; + if (abs(sum - it->wd->history[0].x) <= 10) return; + evas_object_smart_callback_call(it->base.widget, "swipe", it); +} + +static Eina_Bool +_swipe_cancel(void *data) +{ + Elm_Genlist_Item *it = data; + + if (!it) return ECORE_CALLBACK_CANCEL; + it->wd->swipe = EINA_FALSE; + it->wd->movements = 0; + return ECORE_CALLBACK_RENEW; +} + +static Eina_Bool +_multi_cancel(void *data) +{ + Widget_Data *wd = data; + + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->multi_timeout = EINA_TRUE; + return ECORE_CALLBACK_RENEW; +} + +static void +_multi_touch_gesture_eval(void *data) +{ + Elm_Genlist_Item *it = data; + + it->wd->multitouched = EINA_FALSE; + if (it->wd->multi_timer) + { + ecore_timer_del(it->wd->multi_timer); + it->wd->multi_timer = NULL; + } + if (it->wd->multi_timeout) + { + it->wd->multi_timeout = EINA_FALSE; + return; + } + + Evas_Coord minw = 0, minh = 0; + Evas_Coord off_x, off_y, off_mx, off_my; + + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + off_x = abs(it->wd->cur_x - it->wd->prev_x); + off_y = abs(it->wd->cur_y - it->wd->prev_y); + off_mx = abs(it->wd->cur_mx - it->wd->prev_mx); + off_my = abs(it->wd->cur_my - it->wd->prev_my); + + if (((off_x > minw) || (off_y > minh)) && ((off_mx > minw) || (off_my > minh))) + { + if ((off_x + off_mx) > (off_y + off_my)) + { + if ((it->wd->cur_x > it->wd->prev_x) && (it->wd->cur_mx > it->wd->prev_mx)) + evas_object_smart_callback_call(it->base.widget, + "multi,swipe,right", it); + else if ((it->wd->cur_x < it->wd->prev_x) && (it->wd->cur_mx < it->wd->prev_mx)) + evas_object_smart_callback_call(it->base.widget, + "multi,swipe,left", it); + else if (abs(it->wd->cur_x - it->wd->cur_mx) > abs(it->wd->prev_x - it->wd->prev_mx)) + evas_object_smart_callback_call(it->base.widget, + "multi,pinch,out", it); + else + evas_object_smart_callback_call(it->base.widget, + "multi,pinch,in", it); + } + else + { + if ((it->wd->cur_y > it->wd->prev_y) && (it->wd->cur_my > it->wd->prev_my)) + evas_object_smart_callback_call(it->base.widget, + "multi,swipe,down", it); + else if ((it->wd->cur_y < it->wd->prev_y) && (it->wd->cur_my < it->wd->prev_my)) + evas_object_smart_callback_call(it->base.widget, + "multi,swipe,up", it); + else if (abs(it->wd->cur_y - it->wd->cur_my) > abs(it->wd->prev_y - it->wd->prev_my)) + evas_object_smart_callback_call(it->base.widget, + "multi,pinch,out", it); + else + evas_object_smart_callback_call(it->base.widget, + "multi,pinch,in", it); + } + } + it->wd->multi_timeout = EINA_FALSE; +} + +static void +_multi_down(void *data, + Evas *evas __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = data; + Evas_Event_Multi_Down *ev = event_info; + + if ((it->wd->multi_device != 0) || (it->wd->multitouched) || (it->wd->multi_timeout)) return; + it->wd->multi_device = ev->device; + it->wd->multi_down = EINA_TRUE; + it->wd->multitouched = EINA_TRUE; + it->wd->prev_mx = ev->canvas.x; + it->wd->prev_my = ev->canvas.y; + if (!it->wd->wasselected) _item_unselect(it); + it->wd->wasselected = EINA_FALSE; + it->wd->longpressed = EINA_FALSE; + if (it->long_timer) + { + ecore_timer_del(it->long_timer); + it->long_timer = NULL; + } + if (it->dragging) + { + it->dragging = EINA_FALSE; + evas_object_smart_callback_call(it->base.widget, "drag,stop", it); + } + if (it->swipe_timer) + { + ecore_timer_del(it->swipe_timer); + it->swipe_timer = NULL; + } + if (it->wd->on_hold) + { + it->wd->swipe = EINA_FALSE; + it->wd->movements = 0; + it->wd->on_hold = EINA_FALSE; + } +} + +static void +_multi_up(void *data, + Evas *evas __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = data; + Evas_Event_Multi_Up *ev = event_info; + + if (it->wd->multi_device != ev->device) return; + it->wd->multi_device = 0; + it->wd->multi_down = EINA_FALSE; + if (it->wd->mouse_down) return; + _multi_touch_gesture_eval(data); +} + +static void +_multi_move(void *data, + Evas *evas __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = data; + Evas_Event_Multi_Move *ev = event_info; + + if (it->wd->multi_device != ev->device) return; + it->wd->cur_mx = ev->cur.canvas.x; + it->wd->cur_my = ev->cur.canvas.y; +} + +static void +_mouse_down(void *data, + Evas *evas __UNUSED__, + Evas_Object *obj, + void *event_info) +{ + Elm_Genlist_Item *it = data; + Evas_Event_Mouse_Down *ev = event_info; + Evas_Coord x, y; + + if (ev->button != 1) return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + { + it->wd->on_hold = EINA_TRUE; + } + + it->down = EINA_TRUE; + it->dragging = EINA_FALSE; + evas_object_geometry_get(obj, &x, &y, NULL, NULL); + it->dx = ev->canvas.x - x; + it->dy = ev->canvas.y - y; + it->wd->mouse_down = EINA_TRUE; + if (!it->wd->multitouched) + { + it->wd->prev_x = ev->canvas.x; + it->wd->prev_y = ev->canvas.y; + it->wd->multi_timeout = EINA_FALSE; + if (it->wd->multi_timer) ecore_timer_del(it->wd->multi_timer); + it->wd->multi_timer = ecore_timer_add(1, _multi_cancel, it->wd); + } + it->wd->longpressed = EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) it->wd->on_hold = EINA_TRUE; + else it->wd->on_hold = EINA_FALSE; + if (it->wd->on_hold) return; + it->wd->wasselected = it->selected; + _item_hilight(it); + if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK) + evas_object_smart_callback_call(it->base.widget, "clicked", it); + if (it->long_timer) ecore_timer_del(it->long_timer); + if (it->swipe_timer) ecore_timer_del(it->swipe_timer); + it->swipe_timer = ecore_timer_add(0.4, _swipe_cancel, it); + if (it->realized) + it->long_timer = ecore_timer_add(it->wd->longpress_timeout, _long_press, + it); + else + it->long_timer = NULL; + it->wd->swipe = EINA_FALSE; + it->wd->movements = 0; +} + +static void +_mouse_up(void *data, + Evas *evas __UNUSED__, + Evas_Object *obj __UNUSED__, + void *event_info) +{ + Elm_Genlist_Item *it = data; + Evas_Event_Mouse_Up *ev = event_info; + Eina_Bool dragged = EINA_FALSE; + + if (ev->button != 1) return; + it->down = EINA_FALSE; + it->wd->mouse_down = EINA_FALSE; + if (it->wd->multitouched) + { + if (it->wd->multi_down) return; + _multi_touch_gesture_eval(data); + return; + } + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) it->wd->on_hold = EINA_TRUE; + else it->wd->on_hold = EINA_FALSE; + if (it->long_timer) + { + ecore_timer_del(it->long_timer); + it->long_timer = NULL; + } + if (it->dragging) + { + it->dragging = EINA_FALSE; + evas_object_smart_callback_call(it->base.widget, "drag,stop", it); + dragged = 1; + } + if (it->swipe_timer) + { + ecore_timer_del(it->swipe_timer); + it->swipe_timer = NULL; + } + if (it->wd->multi_timer) + { + ecore_timer_del(it->wd->multi_timer); + it->wd->multi_timer = NULL; + it->wd->multi_timeout = EINA_FALSE; + } + if (it->wd->on_hold) + { + if (it->wd->swipe) _swipe(data); + it->wd->longpressed = EINA_FALSE; + it->wd->on_hold = EINA_FALSE; + return; + } + if (it->wd->longpressed) + { + it->wd->longpressed = EINA_FALSE; + if (!it->wd->wasselected) + _item_unselect(it); + it->wd->wasselected = EINA_FALSE; + return; + } + if (dragged) + { + if (it->want_unrealize) + { + _item_unrealize(it); + if (it->block->want_unrealize) + _item_block_unrealize(it->block); + } + } + if ((it->disabled) || (dragged) || (it->display_only)) return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return; + if (it->wd->multi) + { + if (!it->selected) + { + _item_hilight(it); + _item_select(it); + } + else _item_unselect(it); + } + else + { + if (!it->selected) + { + Widget_Data *wd = it->wd; + if (wd) + { + while (wd->selected) _item_unselect(wd->selected->data); + } + } + else + { + const Eina_List *l, *l_next; + Elm_Genlist_Item *it2; + + EINA_LIST_FOREACH_SAFE(it->wd->selected, l, l_next, it2) + if (it2 != it) _item_unselect(it2); + //_item_hilight(it); + //_item_select(it); + } + _item_hilight(it); + _item_select(it); + } +} + +static void +_signal_expand_toggle(void *data, + Evas_Object *obj __UNUSED__, + const char *emission __UNUSED__, + const char *source __UNUSED__) +{ + Elm_Genlist_Item *it = data; + + if (it->expanded) + evas_object_smart_callback_call(it->base.widget, "contract,request", it); + else + evas_object_smart_callback_call(it->base.widget, "expand,request", it); +} + +static void +_signal_expand(void *data, + Evas_Object *obj __UNUSED__, + const char *emission __UNUSED__, + const char *source __UNUSED__) +{ + Elm_Genlist_Item *it = data; + + if (!it->expanded) + evas_object_smart_callback_call(it->base.widget, "expand,request", it); +} + +static void +_signal_contract(void *data, + Evas_Object *obj __UNUSED__, + const char *emission __UNUSED__, + const char *source __UNUSED__) +{ + Elm_Genlist_Item *it = data; + + if (it->expanded) + evas_object_smart_callback_call(it->base.widget, "contract,request", it); +} + +static void +_item_cache_clean(Widget_Data *wd) +{ + while ((wd->item_cache) && (wd->item_cache_count > wd->item_cache_max)) + { + Item_Cache *itc; + + itc = EINA_INLIST_CONTAINER_GET(wd->item_cache->last, Item_Cache); + wd->item_cache = eina_inlist_remove(wd->item_cache, + wd->item_cache->last); + wd->item_cache_count--; + if (itc->spacer) evas_object_del(itc->spacer); + if (itc->base_view) evas_object_del(itc->base_view); + if (itc->item_style) eina_stringshare_del(itc->item_style); + free(itc); + } +} + +static void +_item_cache_zero(Widget_Data *wd) +{ + int pmax = wd->item_cache_max; + wd->item_cache_max = 0; + _item_cache_clean(wd); + wd->item_cache_max = pmax; +} + +static void +_item_cache_add(Elm_Genlist_Item *it) +{ + Item_Cache *itc; + + if (it->wd->item_cache_max <= 0) + { + evas_object_del(it->base.view); + it->base.view = NULL; + evas_object_del(it->spacer); + it->spacer = NULL; + return; + } + + it->wd->item_cache_count++; + itc = calloc(1, sizeof(Item_Cache)); + it->wd->item_cache = eina_inlist_prepend(it->wd->item_cache, + EINA_INLIST_GET(itc)); + itc->spacer = it->spacer; + it->spacer = NULL; + itc->base_view = it->base.view; + it->base.view = NULL; + evas_object_hide(itc->base_view); + evas_object_move(itc->base_view, -9999, -9999); + itc->item_style = eina_stringshare_add(it->itc->item_style); + if (it->flags & ELM_GENLIST_ITEM_SUBITEMS) itc->tree = 1; + itc->compress = (it->wd->compress); + itc->odd = (it->order_num_in & 0x1); + itc->selected = it->selected; + itc->disabled = it->disabled; + itc->expanded = it->expanded; + if (it->long_timer) + { + ecore_timer_del(it->long_timer); + it->long_timer = NULL; + } + if (it->swipe_timer) + { + ecore_timer_del(it->swipe_timer); + it->swipe_timer = NULL; + } + // FIXME: other callbacks? + edje_object_signal_callback_del_full(itc->base_view, + "elm,action,expand,toggle", + "elm", _signal_expand_toggle, it); + edje_object_signal_callback_del_full(itc->base_view, "elm,action,expand", + "elm", + _signal_expand, it); + edje_object_signal_callback_del_full(itc->base_view, "elm,action,contract", + "elm", _signal_contract, it); + evas_object_event_callback_del_full(itc->base_view, EVAS_CALLBACK_MOUSE_DOWN, + _mouse_down, it); + evas_object_event_callback_del_full(itc->base_view, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, it); + evas_object_event_callback_del_full(itc->base_view, EVAS_CALLBACK_MOUSE_MOVE, + _mouse_move, it); + evas_object_event_callback_del_full(itc->base_view, EVAS_CALLBACK_MULTI_DOWN, + _multi_down, it); + evas_object_event_callback_del_full(itc->base_view, EVAS_CALLBACK_MULTI_UP, + _multi_up, it); + evas_object_event_callback_del_full(itc->base_view, EVAS_CALLBACK_MULTI_MOVE, + _multi_move, it); + _item_cache_clean(it->wd); +} + +static Item_Cache * +_item_cache_find(Elm_Genlist_Item *it) +{ + Item_Cache *itc; + Eina_Bool tree = 0, odd; + + if (it->flags & ELM_GENLIST_ITEM_SUBITEMS) tree = 1; + odd = (it->order_num_in & 0x1); + EINA_INLIST_FOREACH(it->wd->item_cache, itc) + { + if ((itc->selected) || (itc->disabled) || (itc->expanded)) + continue; + if ((itc->tree == tree) && + (itc->odd == odd) && + (itc->compress == it->wd->compress) && + (!strcmp(it->itc->item_style, itc->item_style))) + { + it->wd->item_cache = eina_inlist_remove(it->wd->item_cache, + EINA_INLIST_GET(itc)); + it->wd->item_cache_count--; + return itc; + } + } + return NULL; +} + +static void +_item_cache_free(Item_Cache *itc) +{ + if (itc->spacer) evas_object_del(itc->spacer); + if (itc->base_view) evas_object_del(itc->base_view); + if (itc->item_style) eina_stringshare_del(itc->item_style); + free(itc); +} + +static void +_item_realize(Elm_Genlist_Item *it, + int in, + int calc) +{ + Elm_Genlist_Item *it2; + const char *stacking; + const char *treesize; + char buf[1024]; + int depth, tsize = 20; + Item_Cache *itc; + + if ((it->realized) || (it->delete_me)) return; + it->order_num_in = in; + + itc = _item_cache_find(it); + if (itc) + { + it->base.view = itc->base_view; + itc->base_view = NULL; + it->spacer = itc->spacer; + itc->spacer = NULL; + } + else + { + it->base.view = edje_object_add(evas_object_evas_get(it->base.widget)); + edje_object_scale_set(it->base.view, + elm_widget_scale_get(it->base.widget) * + _elm_config->scale); + evas_object_smart_member_add(it->base.view, it->wd->pan_smart); + elm_widget_sub_object_add(it->base.widget, it->base.view); + + if (it->flags & ELM_GENLIST_ITEM_SUBITEMS) + strncpy(buf, "tree", sizeof(buf)); + else strncpy(buf, "item", sizeof(buf)); + if (it->wd->compress) + strncat(buf, "_compress", sizeof(buf) - strlen(buf)); + + if (in & 0x1) strncat(buf, "_odd", sizeof(buf) - strlen(buf)); + strncat(buf, "/", sizeof(buf) - strlen(buf)); + strncat(buf, it->itc->item_style, sizeof(buf) - strlen(buf)); + + _elm_theme_object_set(it->base.widget, it->base.view, "genlist", buf, + elm_widget_style_get(it->base.widget)); + it->spacer = + evas_object_rectangle_add(evas_object_evas_get(it->base.widget)); + evas_object_color_set(it->spacer, 0, 0, 0, 0); + elm_widget_sub_object_add(it->base.widget, it->spacer); + } + for (it2 = it, depth = 0; it2->parent; it2 = it2->parent) + { + if (it2->parent->flags != ELM_GENLIST_ITEM_GROUP) depth += 1; + } + it->expanded_depth = depth; + treesize = edje_object_data_get(it->base.view, "treesize"); + if (treesize) tsize = atoi(treesize); + evas_object_size_hint_min_set(it->spacer, + (depth * tsize) * _elm_config->scale, 1); + edje_object_part_swallow(it->base.view, "elm.swallow.pad", it->spacer); + if (!calc) + { + edje_object_signal_callback_add(it->base.view, + "elm,action,expand,toggle", + "elm", _signal_expand_toggle, it); + edje_object_signal_callback_add(it->base.view, "elm,action,expand", + "elm", _signal_expand, it); + edje_object_signal_callback_add(it->base.view, "elm,action,contract", + "elm", _signal_contract, it); + stacking = edje_object_data_get(it->base.view, "stacking"); + if (stacking) + { + if (!strcmp(stacking, "below")) evas_object_lower(it->base.view); + else if (!strcmp(stacking, "above")) + evas_object_raise(it->base.view); + } + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MOUSE_DOWN, + _mouse_down, it); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, it); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MOUSE_MOVE, + _mouse_move, it); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MULTI_DOWN, + _multi_down, it); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MULTI_UP, + _multi_up, it); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MULTI_MOVE, + _multi_move, it); + if (itc) + { + if (it->selected != itc->selected) + { + if (it->selected) + edje_object_signal_emit(it->base.view, + "elm,state,selected", "elm"); + } + if (it->disabled != itc->disabled) + { + if (it->disabled) + edje_object_signal_emit(it->base.view, + "elm,state,disabled", "elm"); + } + if (it->expanded != itc->expanded) + { + if (it->expanded) + edje_object_signal_emit(it->base.view, + "elm,state,expanded", "elm"); + } + } + else + { + if (it->selected) + edje_object_signal_emit(it->base.view, + "elm,state,selected", "elm"); + if (it->disabled) + edje_object_signal_emit(it->base.view, + "elm,state,disabled", "elm"); + if (it->expanded) + edje_object_signal_emit(it->base.view, + "elm,state,expanded", "elm"); + } + } + + if ((calc) && (it->wd->homogeneous) && (it->wd->item_width)) + { + /* homogenous genlist shortcut */ + if (!it->mincalcd) + { + it->w = it->minw = it->wd->item_width; + it->h = it->minh = it->wd->item_height; + it->mincalcd = EINA_TRUE; + } + } + else + { + if (it->itc->func.label_get) + { + const Eina_List *l; + const char *key; + + it->labels = + elm_widget_stringlist_get(edje_object_data_get(it->base.view, + "labels")); + EINA_LIST_FOREACH(it->labels, l, key) + { + char *s = it->itc->func.label_get + ((void *)it->base.data, it->base.widget, l->data); + + if (s) + { + edje_object_part_text_set(it->base.view, l->data, s); + free(s); + } + else if (itc) + edje_object_part_text_set(it->base.view, l->data, ""); + } + } + if (it->itc->func.icon_get) + { + const Eina_List *l; + const char *key; + + it->icons = + elm_widget_stringlist_get(edje_object_data_get(it->base.view, + "icons")); + EINA_LIST_FOREACH(it->icons, l, key) + { + Evas_Object *ic = it->itc->func.icon_get + ((void *)it->base.data, it->base.widget, l->data); + + if (ic) + { + it->icon_objs = eina_list_append(it->icon_objs, ic); + edje_object_part_swallow(it->base.view, key, ic); + evas_object_show(ic); + elm_widget_sub_object_add(it->base.widget, ic); + } + } + } + if (it->itc->func.state_get) + { + const Eina_List *l; + const char *key; + + it->states = + elm_widget_stringlist_get(edje_object_data_get(it->base.view, + "states")); + EINA_LIST_FOREACH(it->states, l, key) + { + Eina_Bool on = it->itc->func.state_get + ((void *)it->base.data, it->base.widget, l->data); + + if (on) + { + snprintf(buf, sizeof(buf), "elm,state,%s,active", key); + edje_object_signal_emit(it->base.view, buf, "elm"); + } + else if (itc) + { + snprintf(buf, sizeof(buf), "elm,state,%s,passive", key); + edje_object_signal_emit(it->base.view, buf, "elm"); + } + } + } + if (!it->mincalcd) + { + Evas_Coord mw = -1, mh = -1; + + if (it->wd->height_for_width) mw = it->wd->w; + + if (!it->display_only) + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + if (it->wd->height_for_width) mw = it->wd->prev_viewport_w; + edje_object_size_min_restricted_calc(it->base.view, &mw, &mh, mw, + mh); + if (!it->display_only) + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + it->w = it->minw = mw; + it->h = it->minh = mh; + it->mincalcd = EINA_TRUE; + + if ((!in) && (it->wd->homogeneous)) + { + it->wd->item_width = mw; + it->wd->item_height = mh; + } + } + if (!calc) evas_object_show(it->base.view); + } + + if (it->tooltip.content_cb) + { + elm_widget_item_tooltip_content_cb_set(it, + it->tooltip.content_cb, + it->tooltip.data, NULL); + elm_widget_item_tooltip_style_set(it, it->tooltip.style); + } + + if (it->mouse_cursor) + elm_widget_item_cursor_set(it, it->mouse_cursor); + + it->realized = EINA_TRUE; + it->want_unrealize = EINA_FALSE; + + if (itc) _item_cache_free(itc); + evas_object_smart_callback_call(it->base.widget, "realized", it); +} + +static void +_item_unrealize(Elm_Genlist_Item *it) +{ + Evas_Object *icon; + + if (!it->realized) return; + evas_object_smart_callback_call(it->base.widget, "unrealized", it); + if (it->long_timer) + { + ecore_timer_del(it->long_timer); + it->long_timer = NULL; + } + _item_cache_add(it); + elm_widget_stringlist_free(it->labels); + it->labels = NULL; + elm_widget_stringlist_free(it->icons); + it->icons = NULL; + elm_widget_stringlist_free(it->states); + + EINA_LIST_FREE(it->icon_objs, icon) + evas_object_del(icon); + + it->states = NULL; + it->realized = EINA_FALSE; + it->want_unrealize = EINA_FALSE; +} + +static Eina_Bool +_item_block_recalc(Item_Block *itb, + int in, + int qadd, + int norender) +{ + const Eina_List *l; + Elm_Genlist_Item *it; + Evas_Coord minw = 0, minh = 0; + Eina_Bool showme = EINA_FALSE, changed = EINA_FALSE; + Evas_Coord y = 0; + + itb->num = in; + EINA_LIST_FOREACH(itb->items, l, it) + { + if (it->delete_me) continue; + showme |= it->showme; + if (!itb->realized) + { + if (qadd) + { + if (!it->mincalcd) changed = EINA_TRUE; + if (changed) + { + _item_realize(it, in, 1); + _item_unrealize(it); + } + } + else + { + _item_realize(it, in, 1); + _item_unrealize(it); + } + } + else + _item_realize(it, in, 0); + minh += it->minh; + if (minw < it->minw) minw = it->minw; + in++; + it->x = 0; + it->y = y; + y += it->h; + } + itb->minw = minw; + itb->minh = minh; + itb->changed = EINA_FALSE; + /* force an evas norender to garbage collect deleted objects */ + if (norender) evas_norender(evas_object_evas_get(itb->wd->obj)); + return showme; +} + +static void +_item_block_realize(Item_Block *itb, + int in, + int full) +{ + const Eina_List *l; + Elm_Genlist_Item *it; + + if (itb->realized) return; + EINA_LIST_FOREACH(itb->items, l, it) + { + if (it->delete_me) continue; + if (full) _item_realize(it, in, 0); + in++; + } + itb->realized = EINA_TRUE; + itb->want_unrealize = EINA_FALSE; +} + +static void +_item_block_unrealize(Item_Block *itb) +{ + const Eina_List *l; + Elm_Genlist_Item *it; + Eina_Bool dragging = EINA_FALSE; + + if (!itb->realized) return; + EINA_LIST_FOREACH(itb->items, l, it) + { + if (it->flags != ELM_GENLIST_ITEM_GROUP) + { + if (it->dragging) + { + dragging = EINA_TRUE; + it->want_unrealize = EINA_TRUE; + } + else + _item_unrealize(it); + } + } + if (!dragging) + { + itb->realized = EINA_FALSE; + itb->want_unrealize = EINA_TRUE; + } + else + itb->want_unrealize = EINA_FALSE; +} + +static void +_item_block_position(Item_Block *itb, + int in) +{ + const Eina_List *l; + Elm_Genlist_Item *it; + Elm_Genlist_Item *git; + Evas_Coord y = 0, ox, oy, ow, oh, cvx, cvy, cvw, cvh; + int vis; + + evas_object_geometry_get(itb->wd->pan_smart, &ox, &oy, &ow, &oh); + evas_output_viewport_get(evas_object_evas_get(itb->wd->obj), &cvx, &cvy, + &cvw, &cvh); + EINA_LIST_FOREACH(itb->items, l, it) + { + if (it->delete_me) continue; + it->x = 0; + it->y = y; + it->w = itb->w; + it->scrl_x = itb->x + it->x - it->wd->pan_x + ox; + it->scrl_y = itb->y + it->y - it->wd->pan_y + oy; + + if (it->flags != ELM_GENLIST_ITEM_GROUP) + { + vis = (ELM_RECTS_INTERSECT(it->scrl_x, it->scrl_y, it->w, it->h, + cvx, cvy, cvw, cvh)); + if ((itb->realized) && (!it->realized)) + { + if (vis) _item_realize(it, in, 0); + } + if (it->realized) + { + if (vis) + { + git = it->group_item; + if (git) + { + if (git->scrl_y < oy) + git->scrl_y = oy; + if ((git->scrl_y + git->h) > (it->scrl_y + it->h)) + git->scrl_y = (it->scrl_y + it->h) - git->h; + git->want_realize = EINA_TRUE; + } + evas_object_resize(it->base.view, it->w, it->h); + evas_object_move(it->base.view, + it->scrl_x, it->scrl_y); + evas_object_show(it->base.view); + } + else + { + if (!it->dragging) _item_unrealize(it); + } + } + in++; + } + y += it->h; + } +} + +static void +_group_items_recalc(void *data) +{ + Widget_Data *wd = data; + Eina_List *l; + Elm_Genlist_Item *git; + + EINA_LIST_FOREACH(wd->group_items, l, git) + { + if (git->want_realize) + { + if (!git->realized) + _item_realize(git, 0, 0); + evas_object_resize(git->base.view, wd->minw, git->h); + evas_object_move(git->base.view, git->scrl_x, git->scrl_y); + evas_object_show(git->base.view); + evas_object_raise(git->base.view); + } + else if (!git->want_realize && git->realized) + { + if (!git->dragging) + _item_unrealize(git); + } + } +} + +static Eina_Bool +_must_recalc_idler(void *data) +{ + Widget_Data *wd = data; + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + wd->must_recalc_idler = NULL; + return ECORE_CALLBACK_CANCEL; +} + +static void +_calc_job(void *data) +{ + Widget_Data *wd = data; + Item_Block *itb; + Evas_Coord minw = -1, minh = 0, y = 0, ow; + Item_Block *chb = NULL; + int in = 0, minw_change = 0; + Eina_Bool changed = EINA_FALSE; + double t0, t; + Eina_Bool did_must_recalc = EINA_FALSE; + if (!wd) return; + + t0 = ecore_time_get(); + evas_object_geometry_get(wd->pan_smart, NULL, NULL, &ow, &wd->h); + if (wd->w != ow) + { + wd->w = ow; +// if (wd->height_for_width) changed = EINA_TRUE; + } + + EINA_INLIST_FOREACH(wd->blocks, itb) + { + Eina_Bool showme = EINA_FALSE; + + itb->num = in; + showme = itb->showme; + itb->showme = EINA_FALSE; + if (chb) + { + if (itb->realized) _item_block_unrealize(itb); + } + if ((itb->changed) || (changed) || + ((itb->must_recalc) && (!did_must_recalc))) + { + if ((changed) || (itb->must_recalc)) + { + Eina_List *l; + Elm_Genlist_Item *it; + EINA_LIST_FOREACH(itb->items, l, it) + if (it->mincalcd) it->mincalcd = EINA_FALSE; + itb->changed = EINA_TRUE; + if (itb->must_recalc) did_must_recalc = EINA_TRUE; + itb->must_recalc = EINA_FALSE; + } + if (itb->realized) _item_block_unrealize(itb); + showme = _item_block_recalc(itb, in, 0, 1); + chb = itb; + } + itb->y = y; + itb->x = 0; + minh += itb->minh; + if (minw == -1) minw = itb->minw; + else if ((!itb->must_recalc) && (minw < itb->minw)) + { + minw = itb->minw; + minw_change = 1; + } + itb->w = minw; + itb->h = itb->minh; + y += itb->h; + in += itb->count; + if ((showme) && (wd->show_item)) + { + wd->show_item->showme = EINA_FALSE; + if (wd->bring_in) + elm_smart_scroller_region_bring_in(wd->scr, + wd->show_item->x + + wd->show_item->block->x, + wd->show_item->y + + wd->show_item->block->y, + wd->show_item->block->w, + wd->show_item->h); + else + elm_smart_scroller_child_region_show(wd->scr, + wd->show_item->x + + wd->show_item->block->x, + wd->show_item->y + + wd->show_item->block->y, + wd->show_item->block->w, + wd->show_item->h); + wd->show_item = NULL; + } + } + if (minw_change) + { + EINA_INLIST_FOREACH(wd->blocks, itb) + { + itb->minw = minw; + itb->w = itb->minw; + } + } + if ((chb) && (EINA_INLIST_GET(chb)->next)) + { + EINA_INLIST_FOREACH(EINA_INLIST_GET(chb)->next, itb) + { + if (itb->realized) _item_block_unrealize(itb); + } + } + wd->realminw = minw; + if (minw < wd->w) minw = wd->w; + if ((minw != wd->minw) || (minh != wd->minh)) + { + wd->minw = minw; + wd->minh = minh; + evas_object_smart_callback_call(wd->pan_smart, "changed", NULL); + _sizing_eval(wd->obj); + if ((wd->anchor_item) && (wd->anchor_item->block)) + { + Elm_Genlist_Item *it; + Evas_Coord it_y; + + it = wd->anchor_item; + it_y = wd->anchor_y; + elm_smart_scroller_child_pos_set(wd->scr, wd->pan_x, + it->block->y + it->y + it_y); + wd->anchor_item = it; + wd->anchor_y = it_y; + } + } + t = ecore_time_get(); + if (did_must_recalc) + { + if (!wd->must_recalc_idler) + wd->must_recalc_idler = ecore_idler_add(_must_recalc_idler, wd); + } + wd->calc_job = NULL; + evas_object_smart_changed(wd->pan_smart); +} + +static void +_update_job(void *data) +{ + Widget_Data *wd = data; + Eina_List *l2; + Item_Block *itb; + int num, num0, position = 0, recalc = 0; + if (!wd) return; + wd->update_job = NULL; + num = 0; + EINA_INLIST_FOREACH(wd->blocks, itb) + { + Evas_Coord itminw, itminh; + Elm_Genlist_Item *it; + + if (!itb->updateme) + { + num += itb->count; + if (position) + _item_block_position(itb, num); + continue; + } + num0 = num; + recalc = 0; + EINA_LIST_FOREACH(itb->items, l2, it) + { + if (it->updateme) + { + itminw = it->w; + itminh = it->h; + + it->updateme = EINA_FALSE; + if (it->realized) + { + _item_unrealize(it); + _item_realize(it, num, 0); + position = 1; + } + else + { + _item_realize(it, num, 1); + _item_unrealize(it); + } + if ((it->minw != itminw) || (it->minh != itminh)) + recalc = 1; + } + num++; + } + itb->updateme = EINA_FALSE; + if (recalc) + { + position = 1; + itb->changed = EINA_TRUE; + _item_block_recalc(itb, num0, 0, 1); + _item_block_position(itb, num0); + } + } + if (position) + { + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + } +} + +static void +_pan_set(Evas_Object *obj, + Evas_Coord x, + Evas_Coord y) +{ + Pan *sd = evas_object_smart_data_get(obj); + Item_Block *itb; + +// Evas_Coord ow, oh; +// evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); +// ow = sd->wd->minw - ow; +// if (ow < 0) ow = 0; +// oh = sd->wd->minh - oh; +// if (oh < 0) oh = 0; +// if (x < 0) x = 0; +// if (y < 0) y = 0; +// if (x > ow) x = ow; +// if (y > oh) y = oh; + if ((x == sd->wd->pan_x) && (y == sd->wd->pan_y)) return; + sd->wd->pan_x = x; + sd->wd->pan_y = y; + + EINA_INLIST_FOREACH(sd->wd->blocks, itb) + { + if ((itb->y + itb->h) > y) + { + Elm_Genlist_Item *it; + Eina_List *l2; + + EINA_LIST_FOREACH(itb->items, l2, it) + { + if ((itb->y + it->y) >= y) + { + sd->wd->anchor_item = it; + sd->wd->anchor_y = -(itb->y + it->y - y); + goto done; + } + } + } + } +done: + evas_object_smart_changed(obj); +} + +static void +_pan_get(Evas_Object *obj, + Evas_Coord *x, + Evas_Coord *y) +{ + Pan *sd = evas_object_smart_data_get(obj); + + if (x) *x = sd->wd->pan_x; + if (y) *y = sd->wd->pan_y; +} + +static void +_pan_max_get(Evas_Object *obj, + Evas_Coord *x, + Evas_Coord *y) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ow, oh; + + evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); + ow = sd->wd->minw - ow; + if (ow < 0) ow = 0; + oh = sd->wd->minh - oh; + if (oh < 0) oh = 0; + if (x) *x = ow; + if (y) *y = oh; +} + +static void +_pan_min_get(Evas_Object *obj __UNUSED__, + Evas_Coord *x, + Evas_Coord *y) +{ + if (x) *x = 0; + if (y) *y = 0; +} + +static void +_pan_child_size_get(Evas_Object *obj, + Evas_Coord *w, + Evas_Coord *h) +{ + Pan *sd = evas_object_smart_data_get(obj); + + if (w) *w = sd->wd->minw; + if (h) *h = sd->wd->minh; +} + +static void +_pan_add(Evas_Object *obj) +{ + Pan *sd; + Evas_Object_Smart_Clipped_Data *cd; + + _pan_sc.add(obj); + cd = evas_object_smart_data_get(obj); + sd = ELM_NEW(Pan); + if (!sd) return; + sd->__clipped_data = *cd; + free(cd); + evas_object_smart_data_set(obj, sd); +} + +static void +_pan_del(Evas_Object *obj) +{ + Pan *sd = evas_object_smart_data_get(obj); + + if (!sd) return; + if (sd->resize_job) + { + ecore_job_del(sd->resize_job); + sd->resize_job = NULL; + } + _pan_sc.del(obj); +} + +static void +_pan_resize_job(void *data) +{ + Pan *sd = data; + _sizing_eval(sd->wd->obj); + sd->resize_job = NULL; +} + +static void +_pan_resize(Evas_Object *obj, + Evas_Coord w, + Evas_Coord h) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ow, oh; + + evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); + if ((ow == w) && (oh == h)) return; + if ((sd->wd->height_for_width) && (ow != w)) + { + if (sd->resize_job) ecore_job_del(sd->resize_job); + sd->resize_job = ecore_job_add(_pan_resize_job, sd); + } + if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job); + sd->wd->calc_job = ecore_job_add(_calc_job, sd->wd); +} + +static void +_pan_calculate(Evas_Object *obj) +{ + Pan *sd = evas_object_smart_data_get(obj); + Item_Block *itb; + Evas_Coord ox, oy, ow, oh, cvx, cvy, cvw, cvh; + int in = 0; + Elm_Genlist_Item *git; + Eina_List *l; + + evas_object_geometry_get(obj, &ox, &oy, &ow, &oh); + evas_output_viewport_get(evas_object_evas_get(obj), &cvx, &cvy, &cvw, &cvh); + EINA_LIST_FOREACH(sd->wd->group_items, l, git) + { + git->want_realize = EINA_FALSE; + } + EINA_INLIST_FOREACH(sd->wd->blocks, itb) + { + itb->w = sd->wd->minw; + if (ELM_RECTS_INTERSECT(itb->x - sd->wd->pan_x + ox, + itb->y - sd->wd->pan_y + oy, + itb->w, itb->h, + cvx, cvy, cvw, cvh)) + { + if ((!itb->realized) || (itb->changed)) + _item_block_realize(itb, in, 0); + _item_block_position(itb, in); + } + else + { + if (itb->realized) _item_block_unrealize(itb); + } + in += itb->count; + } + _group_items_recalc(sd->wd); +} + +static void +_pan_move(Evas_Object *obj, + Evas_Coord x __UNUSED__, + Evas_Coord y __UNUSED__) +{ + Pan *sd = evas_object_smart_data_get(obj); + + if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job); + sd->wd->calc_job = ecore_job_add(_calc_job, sd->wd); +} + +static void +_hold_on(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_hold_set(wd->scr, 1); +} + +static void +_hold_off(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_hold_set(wd->scr, 0); +} + +static void +_freeze_on(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_freeze_set(wd->scr, 1); +} + +static void +_freeze_off(void *data __UNUSED__, + Evas_Object *obj, + void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_freeze_set(wd->scr, 0); +} + +static void +_scroll_edge_left(void *data, + Evas_Object *scr __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *obj = data; + evas_object_smart_callback_call(obj, "scroll,edge,left", NULL); +} + +static void +_scroll_edge_right(void *data, + Evas_Object *scr __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *obj = data; + evas_object_smart_callback_call(obj, "scroll,edge,right", NULL); +} + +static void +_scroll_edge_top(void *data, + Evas_Object *scr __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *obj = data; + evas_object_smart_callback_call(obj, "scroll,edge,top", NULL); +} + +static void +_scroll_edge_bottom(void *data, + Evas_Object *scr __UNUSED__, + void *event_info __UNUSED__) +{ + Evas_Object *obj = data; + evas_object_smart_callback_call(obj, "scroll,edge,bottom", NULL); +} + +/** + * Add a new Genlist object + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Genlist + */ +EAPI Evas_Object * +elm_genlist_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + Evas_Coord minw, minh; + static Evas_Smart *smart = NULL; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + if (!smart) + { + static Evas_Smart_Class sc; + + evas_object_smart_clipped_smart_set(&_pan_sc); + sc = _pan_sc; + sc.name = "elm_genlist_pan"; + sc.version = EVAS_SMART_CLASS_VERSION; + sc.add = _pan_add; + sc.del = _pan_del; + sc.resize = _pan_resize; + sc.move = _pan_move; + sc.calculate = _pan_calculate; + if (!(smart = evas_smart_class_new(&sc))) return NULL; + } + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "genlist"); + elm_widget_type_set(obj, "genlist"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->scr = elm_smart_scroller_add(e); + elm_smart_scroller_widget_set(wd->scr, obj); + elm_smart_scroller_object_theme_set(obj, wd->scr, "genlist", "base", + elm_widget_style_get(obj)); + elm_smart_scroller_bounce_allow_set(wd->scr, EINA_FALSE, + _elm_config->thumbscroll_bounce_enable); + elm_widget_resize_object_set(obj, wd->scr); + + evas_object_smart_callback_add(wd->scr, "edge,left", _scroll_edge_left, obj); + evas_object_smart_callback_add(wd->scr, "edge,right", _scroll_edge_right, + obj); + evas_object_smart_callback_add(wd->scr, "edge,top", _scroll_edge_top, obj); + evas_object_smart_callback_add(wd->scr, "edge,bottom", _scroll_edge_bottom, + obj); + + wd->obj = obj; + wd->mode = ELM_LIST_SCROLL; + wd->max_items_per_block = MAX_ITEMS_PER_BLOCK; + wd->item_cache_max = wd->max_items_per_block * 2; + wd->longpress_timeout = _elm_config->longpress_timeout; + + evas_object_smart_callback_add(obj, "scroll-hold-on", _hold_on, obj); + evas_object_smart_callback_add(obj, "scroll-hold-off", _hold_off, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-on", _freeze_on, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-off", _freeze_off, obj); + + wd->pan_smart = evas_object_smart_add(e, smart); + wd->pan = evas_object_smart_data_get(wd->pan_smart); + wd->pan->wd = wd; + + elm_smart_scroller_extern_pan_set(wd->scr, wd->pan_smart, + _pan_set, _pan_get, _pan_max_get, + _pan_min_get, _pan_child_size_get); + + edje_object_size_min_calc(elm_smart_scroller_edje_object_get(wd->scr), + &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + + _sizing_eval(obj); + return obj; +} + +static Elm_Genlist_Item * +_item_new(Widget_Data *wd, + const Elm_Genlist_Item_Class *itc, + const void *data, + Elm_Genlist_Item *parent, + Elm_Genlist_Item_Flags flags, + Evas_Smart_Cb func, + const void *func_data) +{ + Elm_Genlist_Item *it; + + it = elm_widget_item_new(wd->obj, Elm_Genlist_Item); + if (!it) return NULL; + it->wd = wd; + it->itc = itc; + it->base.data = data; + it->parent = parent; + it->flags = flags; + it->func.func = func; + it->func.data = func_data; + it->mouse_cursor = NULL; + it->expanded_depth = 0; + return it; +} + +static void +_item_block_add(Widget_Data *wd, + Elm_Genlist_Item *it) +{ + Item_Block *itb = NULL; + + if (!it->rel) + { +newblock: + if (it->rel) + { + itb = calloc(1, sizeof(Item_Block)); + if (!itb) return; + itb->wd = wd; + if (!it->rel->block) + { + wd->blocks = + eina_inlist_append(wd->blocks, EINA_INLIST_GET(itb)); + itb->items = eina_list_append(itb->items, it); + } + else + { + if (it->before) + { + wd->blocks = eina_inlist_prepend_relative + (wd->blocks, EINA_INLIST_GET(itb), + EINA_INLIST_GET(it->rel->block)); + itb->items = + eina_list_prepend_relative(itb->items, it, it->rel); + } + else + { + wd->blocks = eina_inlist_append_relative + (wd->blocks, EINA_INLIST_GET(itb), + EINA_INLIST_GET(it->rel->block)); + itb->items = + eina_list_append_relative(itb->items, it, it->rel); + } + } + } + else + { + if (it->before) + { + if (wd->blocks) + { + itb = (Item_Block *)(wd->blocks); + if (itb->count >= wd->max_items_per_block) + { + itb = calloc(1, sizeof(Item_Block)); + if (!itb) return; + itb->wd = wd; + wd->blocks = + eina_inlist_prepend(wd->blocks, + EINA_INLIST_GET(itb)); + } + } + else + { + itb = calloc(1, sizeof(Item_Block)); + if (!itb) return; + itb->wd = wd; + wd->blocks = + eina_inlist_prepend(wd->blocks, EINA_INLIST_GET(itb)); + } + itb->items = eina_list_prepend(itb->items, it); + } + else + { + if (wd->blocks) + { + itb = (Item_Block *)(wd->blocks->last); + if (itb->count >= wd->max_items_per_block) + { + itb = calloc(1, sizeof(Item_Block)); + if (!itb) return; + itb->wd = wd; + wd->blocks = + eina_inlist_append(wd->blocks, + EINA_INLIST_GET(itb)); + } + } + else + { + itb = calloc(1, sizeof(Item_Block)); + if (!itb) return; + itb->wd = wd; + wd->blocks = + eina_inlist_append(wd->blocks, EINA_INLIST_GET(itb)); + } + itb->items = eina_list_append(itb->items, it); + } + } + } + else + { + itb = it->rel->block; + if (!itb) goto newblock; + if (it->before) + itb->items = eina_list_prepend_relative(itb->items, it, it->rel); + else + itb->items = eina_list_append_relative(itb->items, it, it->rel); + } + itb->count++; + itb->changed = EINA_TRUE; + it->block = itb; + if (itb->wd->calc_job) ecore_job_del(itb->wd->calc_job); + itb->wd->calc_job = ecore_job_add(_calc_job, itb->wd); + if (it->rel) + { + it->rel->relcount--; + if ((it->rel->delete_me) && (!it->rel->relcount)) + _item_del(it->rel); + it->rel = NULL; + } + if (itb->count > itb->wd->max_items_per_block) + { + int newc; + Item_Block *itb2; + Elm_Genlist_Item *it2; + + newc = itb->count / 2; + itb2 = calloc(1, sizeof(Item_Block)); + if (!itb2) return; + itb2->wd = wd; + wd->blocks = + eina_inlist_append_relative(wd->blocks, EINA_INLIST_GET(itb2), + EINA_INLIST_GET(itb)); + itb2->changed = EINA_TRUE; + while ((itb->count > newc) && (itb->items)) + { + Eina_List *l; + + l = eina_list_last(itb->items); + it2 = l->data; + itb->items = eina_list_remove_list(itb->items, l); + itb->count--; + + itb2->items = eina_list_prepend(itb2->items, it2); + it2->block = itb2; + itb2->count++; + } + } +} + +static int +_queue_proecess(Widget_Data *wd, + int norender) +{ + int n; + Eina_Bool showme = EINA_FALSE; + double t0, t; + + t0 = ecore_time_get(); + for (n = 0; (wd->queue) && (n < 128); n++) + { + Elm_Genlist_Item *it; + + it = wd->queue->data; + wd->queue = eina_list_remove_list(wd->queue, wd->queue); + it->queued = EINA_FALSE; + _item_block_add(wd, it); + t = ecore_time_get(); + if (it->block->changed) + { + showme = _item_block_recalc(it->block, it->block->num, 1, + norender); + it->block->changed = 0; + } + if (showme) it->block->showme = EINA_TRUE; + if (eina_inlist_count(wd->blocks) > 1) + { + if ((t - t0) > (ecore_animator_frametime_get())) break; + } + } + return n; +} + +static Eina_Bool +_item_idler(void *data) +{ + Widget_Data *wd = data; + + //xxx + //static double q_start = 0.0; + //if (q_start == 0.0) q_start = ecore_time_get(); + //xxx + + if (_queue_proecess(wd, 1) > 0) + { + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + } + if (!wd->queue) + { + //xxx + //printf("PROCESS TIME: %3.3f\n", ecore_time_get() - q_start); + //xxx + wd->queue_idler = NULL; + return ECORE_CALLBACK_CANCEL; + } + return ECORE_CALLBACK_RENEW; +} + +static void +_item_queue(Widget_Data *wd, + Elm_Genlist_Item *it) +{ + if (it->queued) return; + it->queued = EINA_TRUE; + wd->queue = eina_list_append(wd->queue, it); + while ((wd->queue) && ((!wd->blocks) || (!wd->blocks->next))) + { + if (wd->queue_idler) + { + ecore_idler_del(wd->queue_idler); + wd->queue_idler = NULL; + } + _queue_proecess(wd, 0); + } + if (!wd->queue_idler) wd->queue_idler = ecore_idler_add(_item_idler, wd); +} + +/** + * Append item to the end of the genlist + * + * This appends the given item to the end of the list or the end of + * the children if the parent is given. + * + * @param obj The genlist object + * @param itc The item class for the item + * @param data The item data + * @param parent The parent item, or NULL if none + * @param flags Item flags + * @param func Convenience function called when item selected + * @param func_data Data passed to @p func above. + * @return A handle to the item added or NULL if not possible + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_item_append(Evas_Object *obj, + const Elm_Genlist_Item_Class *itc, + const void *data, + Elm_Genlist_Item *parent, + Elm_Genlist_Item_Flags flags, + Evas_Smart_Cb func, + const void *func_data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Genlist_Item *it = _item_new(wd, itc, data, parent, flags, func, + func_data); + if (!wd) return NULL; + if (!it) return NULL; + if (!it->parent) + { + if (flags & ELM_GENLIST_ITEM_GROUP) + wd->group_items = eina_list_append(wd->group_items, it); + wd->items = eina_inlist_append(wd->items, EINA_INLIST_GET(it)); + it->rel = NULL; + } + else + { + Elm_Genlist_Item *it2 = NULL; + Eina_List *ll = eina_list_last(it->parent->items); + if (ll) it2 = ll->data; + it->parent->items = eina_list_append(it->parent->items, it); + if (!it2) it2 = it->parent; + wd->items = + eina_inlist_append_relative(wd->items, EINA_INLIST_GET(it), + EINA_INLIST_GET(it2)); + it->rel = it2; + it->rel->relcount++; + + if (it->parent->flags & ELM_GENLIST_ITEM_GROUP) + it->group_item = parent; + else if (it->parent->group_item) + it->group_item = it->parent->group_item; + } + it->before = EINA_FALSE; + _item_queue(wd, it); + return it; +} + +/** + * Prepend item at start of the genlist + * + * This adds an item to the beginning of the list or beginning of the + * children of the parent if given. + * + * @param obj The genlist object + * @param itc The item class for the item + * @param data The item data + * @param parent The parent item, or NULL if none + * @param flags Item flags + * @param func Convenience function called when item selected + * @param func_data Data passed to @p func above. + * @return A handle to the item added or NULL if not possible + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_item_prepend(Evas_Object *obj, + const Elm_Genlist_Item_Class *itc, + const void *data, + Elm_Genlist_Item *parent, + Elm_Genlist_Item_Flags flags, + Evas_Smart_Cb func, + const void *func_data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Genlist_Item *it = _item_new(wd, itc, data, parent, flags, func, + func_data); + if (!wd) return NULL; + if (!it) return NULL; + if (!it->parent) + { + if (flags & ELM_GENLIST_ITEM_GROUP) + wd->group_items = eina_list_prepend(wd->group_items, it); + wd->items = eina_inlist_prepend(wd->items, EINA_INLIST_GET(it)); + it->rel = NULL; + } + else + { + Elm_Genlist_Item *it2 = NULL; + Eina_List *ll = it->parent->items; + if (ll) it2 = ll->data; + it->parent->items = eina_list_prepend(it->parent->items, it); + if (!it2) it2 = it->parent; + wd->items = + eina_inlist_prepend_relative(wd->items, EINA_INLIST_GET(it), + EINA_INLIST_GET(it2)); + it->rel = it2; + it->rel->relcount++; + } + it->before = EINA_TRUE; + _item_queue(wd, it); + return it; +} + +/** + * Insert item before another in the genlist + * + * This inserts an item before another in the list. It will be in the + * same tree level or group as the item it is inseted before. + * + * @param obj The genlist object + * @param itc The item class for the item + * @param data The item data + * @param before The item to insert before + * @param flags Item flags + * @param func Convenience function called when item selected + * @param func_data Data passed to @p func above. + * @return A handle to the item added or NULL if not possible + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_item_insert_before(Evas_Object *obj, + const Elm_Genlist_Item_Class *itc, + const void *data, + Elm_Genlist_Item *parent, + Elm_Genlist_Item *before, + Elm_Genlist_Item_Flags flags, + Evas_Smart_Cb func, + const void *func_data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + EINA_SAFETY_ON_NULL_RETURN_VAL(before, NULL); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Genlist_Item *it = _item_new(wd, itc, data, parent, flags, func, + func_data); + if (!wd) return NULL; + if (!it) return NULL; + if (it->parent) + { + it->parent->items = eina_list_prepend_relative(it->parent->items, it, + before); + } + wd->items = eina_inlist_prepend_relative(wd->items, EINA_INLIST_GET(it), + EINA_INLIST_GET(before)); + it->rel = before; + it->rel->relcount++; + it->before = EINA_TRUE; + _item_queue(wd, it); + return it; +} + +/** + * Insert an item after another in the genlst + * + * This inserts an item after another in the list. It will be in the + * same tree level or group as the item it is inseted after. + * + * @param obj The genlist object + * @param itc The item class for the item + * @param data The item data + * @param after The item to insert after + * @param flags Item flags + * @param func Convenience function called when item selected + * @param func_data Data passed to @p func above. + * @return A handle to the item added or NULL if not possible + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_item_insert_after(Evas_Object *obj, + const Elm_Genlist_Item_Class *itc, + const void *data, + Elm_Genlist_Item *parent, + Elm_Genlist_Item *after, + Elm_Genlist_Item_Flags flags, + Evas_Smart_Cb func, + const void *func_data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + EINA_SAFETY_ON_NULL_RETURN_VAL(after, NULL); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Genlist_Item *it = _item_new(wd, itc, data, parent, flags, func, + func_data); + if (!wd) return NULL; + if (!it) return NULL; + wd->items = eina_inlist_append_relative(wd->items, EINA_INLIST_GET(it), + EINA_INLIST_GET(after)); + if (it->parent) + { + it->parent->items = eina_list_append_relative(it->parent->items, it, + after); + } + it->rel = after; + it->rel->relcount++; + it->before = EINA_FALSE; + _item_queue(wd, it); + return it; +} + +/** + * Clear the genlist + * + * This clears all items in the list, leaving it empty. + * + * @param obj The genlist object + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_clear(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->walking > 0) + { + Elm_Genlist_Item *it; + + wd->clear_me = EINA_TRUE; + EINA_INLIST_FOREACH(wd->items, it) + { + it->delete_me = EINA_TRUE; + } + return; + } + wd->clear_me = EINA_FALSE; + while (wd->items) + { + Elm_Genlist_Item *it = ELM_GENLIST_ITEM_FROM_INLIST(wd->items); + + if (wd->anchor_item == it) + { + wd->anchor_item = (Elm_Genlist_Item *)(EINA_INLIST_GET(it)->next); + if (!wd->anchor_item) + wd->anchor_item = + (Elm_Genlist_Item *)(EINA_INLIST_GET(it)->prev); + } + wd->items = eina_inlist_remove(wd->items, wd->items); + if (it->flags & ELM_GENLIST_ITEM_GROUP) + it->wd->group_items = eina_list_remove(it->wd->group_items, it); + elm_widget_item_pre_notify_del(it); + if (it->realized) _item_unrealize(it); + if (it->itc->func.del) + it->itc->func.del((void *)it->base.data, it->base.widget); + if (it->long_timer) ecore_timer_del(it->long_timer); + if (it->swipe_timer) ecore_timer_del(it->swipe_timer); + elm_widget_item_del(it); + } + wd->anchor_item = NULL; + while (wd->blocks) + { + Item_Block *itb = (Item_Block *)(wd->blocks); + + wd->blocks = eina_inlist_remove(wd->blocks, wd->blocks); + if (itb->items) eina_list_free(itb->items); + free(itb); + } + if (wd->calc_job) + { + ecore_job_del(wd->calc_job); + wd->calc_job = NULL; + } + if (wd->queue_idler) + { + ecore_idler_del(wd->queue_idler); + wd->queue_idler = NULL; + } + if (wd->must_recalc_idler) + { + ecore_idler_del(wd->must_recalc_idler); + wd->must_recalc_idler = NULL; + } + if (wd->queue) + { + eina_list_free(wd->queue); + wd->queue = NULL; + } + if (wd->selected) + { + eina_list_free(wd->selected); + wd->selected = NULL; + } + wd->show_item = NULL; + wd->pan_x = 0; + wd->pan_y = 0; + wd->minw = 0; + wd->minh = 0; + if (wd->pan_smart) + { + evas_object_size_hint_min_set(wd->pan_smart, wd->minw, wd->minh); + evas_object_smart_callback_call(wd->pan_smart, "changed", NULL); + } + _sizing_eval(obj); +} + +/** + * Enable or disable multi-select in the genlist + * + * This enables (EINA_TRUE) or disableds (EINA_FALSE) multi-select in + * the list. This allows more than 1 item to be selected. + * + * @param obj The genlist object + * @param multi Multi-select enable/disable + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_multi_select_set(Evas_Object *obj, + Eina_Bool multi) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->multi = multi; +} + +/** + * Gets if multi-select in genlist is enable or disable + * + * @param obj The genlist object + * @return Multi-select enable/disable + * (EINA_TRUE = enabled/EINA_FALSE = disabled) + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_multi_select_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->multi; +} + +/** + * Get the selectd item in the genlist + * + * This gets the selected item in the list (if multi-select is enabled + * only the first item in the list is selected - which is not very + * useful, so see elm_genlist_selected_items_get() for when + * multi-select is used). + * + * If no item is selected, NULL is returned. + * + * @param obj The genlist object + * @return The selected item, or NULL if none. + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_selected_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (wd->selected) return wd->selected->data; + return NULL; +} + +/** + * Get a list of selected items in the genlist + * + * This returns a list of the selected items. This list pointer is + * only valid so long as no items are selected or unselected (or + * unselected implicitly by deletion). The list contains + * Elm_Genlist_Item pointers. + * + * @param obj The genlist object + * @return The list of selected items, nor NULL if none are selected. + * + * @ingroup Genlist + */ +EAPI const Eina_List * +elm_genlist_selected_items_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->selected; +} + +/** + * Get a list of realized items in genlist + * + * This returns a list of the realized items in the genlist. The list + * contains Elm_Genlist_Item pointers. The list must be freed by the + * caller when done with eina_list_free(). The item pointers in the + * list are only valid so long as those items are not deleted or the + * genlist is not deleted. + * + * @param obj The genlist object + * @return The list of realized items, nor NULL if none are realized. + * + * @ingroup Genlist + */ +EAPI Eina_List * +elm_genlist_realized_items_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *list = NULL; + Item_Block *itb; + Eina_Bool done = EINA_FALSE; + if (!wd) return NULL; + EINA_INLIST_FOREACH(wd->blocks, itb) + { + if (itb->realized) + { + Eina_List *l; + Elm_Genlist_Item *it; + + done = 1; + EINA_LIST_FOREACH(itb->items, l, it) + { + if (it->realized) list = eina_list_append(list, it); + } + } + else + { + if (done) break; + } + } + return list; +} + +/** + * Get the item that is at the x, y canvas coords + * + * This returns the item at the given coordinates (which are canvas + * relative not object-relative). If an item is at that coordinate, + * that item handle is returned, and if @p posret is not NULL, the + * integer pointed to is set to a value of -1, 0 or 1, depending if + * the coordinate is on the upper portion of that item (-1), on the + * middle section (0) or on the lower part (1). If NULL is returned as + * an item (no item found there), then posret may indicate -1 or 1 + * based if the coordinate is above or below all items respectively in + * the genlist. + * + * @param it The item + * @param x The input x coordinate + * @param y The input y coordinate + * @param posret The position relative to the item returned here + * @return The item at the coordinates or NULL if none + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_at_xy_item_get(const Evas_Object *obj, + Evas_Coord x, + Evas_Coord y, + int *posret) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord ox, oy, ow, oh; + Item_Block *itb; + Evas_Coord lasty; + if (!wd) return NULL; + evas_object_geometry_get(wd->pan_smart, &ox, &oy, &ow, &oh); + lasty = oy; + EINA_INLIST_FOREACH(wd->blocks, itb) + { + Eina_List *l; + Elm_Genlist_Item *it; + + if (!ELM_RECTS_INTERSECT(ox + itb->x - itb->wd->pan_x, + oy + itb->y - itb->wd->pan_y, + itb->w, itb->h, x, y, 1, 1)) + continue; + EINA_LIST_FOREACH(itb->items, l, it) + { + Evas_Coord itx, ity; + + itx = ox + itb->x + it->x - itb->wd->pan_x; + ity = oy + itb->y + it->y - itb->wd->pan_y; + if (ELM_RECTS_INTERSECT(itx, ity, it->w, it->h, x, y, 1, 1)) + { + if (posret) + { + if (y <= (ity + (it->h / 4))) *posret = -1; + else if (y >= (ity + it->h - (it->h / 4))) + *posret = 1; + else *posret = 0; + } + return it; + } + lasty = ity + it->h; + } + } + if (posret) + { + if (y > lasty) *posret = 1; + else *posret = -1; + } + return NULL; +} + +/** + * Get the first item in the genlist + * + * This returns the first item in the list. + * + * @param obj The genlist object + * @return The first item, or NULL if none + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_first_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->items) return NULL; + Elm_Genlist_Item *it = ELM_GENLIST_ITEM_FROM_INLIST(wd->items); + while ((it) && (it->delete_me)) + it = ELM_GENLIST_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->next); + return it; +} + +/** + * Get the last item in the genlist + * + * This returns the last item in the list. + * + * @return The last item, or NULL if none + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_last_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd->items) return NULL; + Elm_Genlist_Item *it = ELM_GENLIST_ITEM_FROM_INLIST(wd->items->last); + if (!wd) return NULL; + while ((it) && (it->delete_me)) + it = ELM_GENLIST_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev); + return it; +} + +/** + * Get the next item in the genlist + * + * This returns the item after the item @p it. + * + * @param it The item + * @return The item after @p it, or NULL if none + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_item_next_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, NULL); + while (it) + { + it = ELM_GENLIST_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->next); + if ((it) && (!it->delete_me)) break; + } + return (Elm_Genlist_Item *)it; +} + +/** + * Get the previous item in the genlist + * + * This returns the item before the item @p it. + * + * @param it The item + * @return The item before @p it, or NULL if none + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_item_prev_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, NULL); + while (it) + { + it = ELM_GENLIST_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev); + if ((it) && (!it->delete_me)) break; + } + return (Elm_Genlist_Item *)it; +} + +/** + * Get the genlist object from an item + * + * This returns the genlist object itself that an item belongs to. + * + * @param it The item + * @return The genlist object + * + * @ingroup Genlist + */ +EAPI Evas_Object * +elm_genlist_item_genlist_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, NULL); + return it->base.widget; +} + +/** + * Get the parent item of the given item + * + * This returns the parent item of the item @p it given. + * + * @param it The item + * @return The parent of the item or NULL if none + * + * @ingroup Genlist + */ +EAPI Elm_Genlist_Item * +elm_genlist_item_parent_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, NULL); + return it->parent; +} + +/** + * Clear all sub-items (children) of the given item + * + * This clears all items that are children (or their descendants) of the + * given item @p it. + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_subitems_clear(Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + Eina_List *tl = NULL, *l; + Elm_Genlist_Item *it2; + + EINA_LIST_FOREACH(it->items, l, it2) + tl = eina_list_append(tl, it2); + EINA_LIST_FREE(tl, it2) + elm_genlist_item_del(it2); +} + +/** + * Set the selected state of an item + * + * This sets the selected state (1 selected, 0 not selected) of the given + * item @p it. + * + * @param it The item + * @param selected The selected state + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_selected_set(Elm_Genlist_Item *it, + Eina_Bool selected) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + Widget_Data *wd = elm_widget_data_get(it->base.widget); + if (!wd) return; + if (it->delete_me) return; + selected = !!selected; + if (it->selected == selected) return; + + if (selected) + { + if (!wd->multi) + { + while (wd->selected) + _item_unselect(wd->selected->data); + } + _item_hilight(it); + _item_select(it); + } + else + _item_unselect(it); +} + +/** + * Get the selected state of an item + * + * This gets the selected state of an item (1 selected, 0 not selected). + * + * @param it The item + * @return The selected state + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_item_selected_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, EINA_FALSE); + return it->selected; +} + +/** + * Sets the expanded state of an item (if it's a parent) + * + * This expands or contracts a parent item (thus showing or hiding the + * children). + * + * @param it The item + * @param expanded The expanded state (1 expanded, 0 not expanded). + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_expanded_set(Elm_Genlist_Item *it, + Eina_Bool expanded) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + if (it->expanded == expanded) return; + it->expanded = expanded; + if (it->expanded) + { + if (it->realized) + edje_object_signal_emit(it->base.view, "elm,state,expanded", "elm"); + evas_object_smart_callback_call(it->base.widget, "expanded", it); + } + else + { + if (it->realized) + edje_object_signal_emit(it->base.view, "elm,state,contracted", "elm"); + evas_object_smart_callback_call(it->base.widget, "contracted", it); + } +} + +/** + * Get the expanded state of an item + * + * This gets the expanded state of an item + * + * @param it The item + * @return Thre expanded state + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_item_expanded_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, EINA_FALSE); + return it->expanded; +} + +/** + * Get the depth of expanded item + * + * @param it The genlist item object + * @return The depth of expanded item + * + * @ingroup Genlist + */ +EAPI int +elm_genlist_item_expanded_depth_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, 0); + return it->expanded_depth; +} + +/** + * Sets the disabled state of an item. + * + * A disabled item cannot be selected or unselected. It will also + * change appearance to appear disabled. This sets the disabled state + * (1 disabled, 0 not disabled). + * + * @param it The item + * @param disabled The disabled state + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_disabled_set(Elm_Genlist_Item *it, + Eina_Bool disabled) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + if (it->disabled == disabled) return; + if (it->delete_me) return; + it->disabled = disabled; + if (it->realized) + { + if (it->disabled) + edje_object_signal_emit(it->base.view, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(it->base.view, "elm,state,enabled", "elm"); + } +} + +/** + * Get the disabled state of an item + * + * This gets the disabled state of the given item. + * + * @param it The item + * @return The disabled state + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_item_disabled_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, EINA_FALSE); + if (it->delete_me) return EINA_FALSE; + return it->disabled; +} + +/** + * Sets the display only state of an item. + * + * A display only item cannot be selected or unselected. It is for + * display only and not selecting or otherwise clicking, dragging + * etc. by the user, thus finger size rules will not be applied to + * this item. + * + * @param it The item + * @param display_only The display only state + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_display_only_set(Elm_Genlist_Item *it, + Eina_Bool display_only) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + if (!it->block) return; + if (it->display_only == display_only) return; + if (it->delete_me) return; + it->display_only = display_only; + it->mincalcd = EINA_FALSE; + it->updateme = EINA_TRUE; + it->block->updateme = EINA_TRUE; + if (it->wd->update_job) ecore_job_del(it->wd->update_job); + it->wd->update_job = ecore_job_add(_update_job, it->wd); +} + +/** + * Get the display only state of an item + * + * This gets the display only state of the given item. + * + * @param it The item + * @return The display only state + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_item_display_only_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, EINA_FALSE); + if (it->delete_me) return EINA_FALSE; + return it->display_only; +} + +/** + * Show the given item + * + * This causes genlist to jump to the given item @p it and show it (by + * scrolling), if it is not fully visible. + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_show(Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + Evas_Coord gith = 0; + if (it->delete_me) return; + if ((it->queued) || (!it->mincalcd)) + { + it->wd->show_item = it; + it->wd->bring_in = EINA_TRUE; + it->showme = EINA_TRUE; + return; + } + if (it->wd->show_item) + { + it->wd->show_item->showme = EINA_FALSE; + it->wd->show_item = NULL; + } + if ((it->group_item) && (it->wd->pan_y > (it->y + it->block->y))) + gith = it->group_item->h; + elm_smart_scroller_child_region_show(it->wd->scr, + it->x + it->block->x, + it->y + it->block->y - gith, + it->block->w, it->h); +} + +/** + * Bring in the given item + * + * This causes genlist to jump to the given item @p it and show it (by + * scrolling), if it is not fully visible. This may use animation to + * do so and take a period of time + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_bring_in(Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + Evas_Coord gith = 0; + if (it->delete_me) return; + if ((it->queued) || (!it->mincalcd)) + { + it->wd->show_item = it; + it->wd->bring_in = EINA_TRUE; + it->showme = EINA_TRUE; + return; + } + if (it->wd->show_item) + { + it->wd->show_item->showme = EINA_FALSE; + it->wd->show_item = NULL; + } + if ((it->group_item) && (it->wd->pan_y > (it->y + it->block->y))) + gith = it->group_item->h; + elm_smart_scroller_region_bring_in(it->wd->scr, + it->x + it->block->x, + it->y + it->block->y - gith, + it->block->w, it->h); +} + +/** + * Show the given item at the top + * + * This causes genlist to jump to the given item @p it and show it (by + * scrolling), if it is not fully visible. + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_top_show(Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + Evas_Coord ow, oh; + Evas_Coord gith = 0; + + if (it->delete_me) return; + if ((it->queued) || (!it->mincalcd)) + { + it->wd->show_item = it; + it->wd->bring_in = EINA_TRUE; + it->showme = EINA_TRUE; + return; + } + if (it->wd->show_item) + { + it->wd->show_item->showme = EINA_FALSE; + it->wd->show_item = NULL; + } + evas_object_geometry_get(it->wd->pan_smart, NULL, NULL, &ow, &oh); + if (it->group_item) gith = it->group_item->h; + elm_smart_scroller_child_region_show(it->wd->scr, + it->x + it->block->x, + it->y + it->block->y - gith, + it->block->w, oh); +} + +/** + * Bring in the given item at the top + * + * This causes genlist to jump to the given item @p it and show it (by + * scrolling), if it is not fully visible. This may use animation to + * do so and take a period of time + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_top_bring_in(Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + Evas_Coord ow, oh; + Evas_Coord gith = 0; + + if (it->delete_me) return; + if ((it->queued) || (!it->mincalcd)) + { + it->wd->show_item = it; + it->wd->bring_in = EINA_TRUE; + it->showme = EINA_TRUE; + return; + } + if (it->wd->show_item) + { + it->wd->show_item->showme = EINA_FALSE; + it->wd->show_item = NULL; + } + evas_object_geometry_get(it->wd->pan_smart, NULL, NULL, &ow, &oh); + if (it->group_item) gith = it->group_item->h; + elm_smart_scroller_region_bring_in(it->wd->scr, + it->x + it->block->x, + it->y + it->block->y - gith, + it->block->w, oh); +} + +/** + * Show the given item at the middle + * + * This causes genlist to jump to the given item @p it and show it (by + * scrolling), if it is not fully visible. + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_middle_show(Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + Evas_Coord ow, oh; + + if (it->delete_me) return; + if ((it->queued) || (!it->mincalcd)) + { + it->wd->show_item = it; + it->wd->bring_in = EINA_TRUE; + it->showme = EINA_TRUE; + return; + } + if (it->wd->show_item) + { + it->wd->show_item->showme = EINA_FALSE; + it->wd->show_item = NULL; + } + evas_object_geometry_get(it->wd->pan_smart, NULL, NULL, &ow, &oh); + elm_smart_scroller_child_region_show(it->wd->scr, + it->x + it->block->x, + it->y + it->block->y - oh / 2 + + it->h / 2, it->block->w, oh); +} + +/** + * Bring in the given item at the middle + * + * This causes genlist to jump to the given item @p it and show it (by + * scrolling), if it is not fully visible. This may use animation to + * do so and take a period of time + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_middle_bring_in(Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + Evas_Coord ow, oh; + + if (it->delete_me) return; + if ((it->queued) || (!it->mincalcd)) + { + it->wd->show_item = it; + it->wd->bring_in = EINA_TRUE; + it->showme = EINA_TRUE; + return; + } + if (it->wd->show_item) + { + it->wd->show_item->showme = EINA_FALSE; + it->wd->show_item = NULL; + } + evas_object_geometry_get(it->wd->pan_smart, NULL, NULL, &ow, &oh); + elm_smart_scroller_region_bring_in(it->wd->scr, + it->x + it->block->x, + it->y + it->block->y - oh / 2 + it->h / 2, + it->block->w, oh); +} + +/** + * Delete a given item + * + * This deletes the item from genlist and calls the genlist item del + * class callback defined in the item class, if it is set. This clears all + * subitems if it is a tree. + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_del(Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + if ((it->relcount > 0) || (it->walking > 0)) + { + elm_widget_item_pre_notify_del(it); + elm_genlist_item_subitems_clear(it); + it->delete_me = EINA_TRUE; + if (it->wd->show_item == it) it->wd->show_item = NULL; + if (it->selected) + it->wd->selected = eina_list_remove(it->wd->selected, + it); + if (it->block) + { + if (it->realized) _item_unrealize(it); + it->block->changed = EINA_TRUE; + if (it->wd->calc_job) ecore_job_del(it->wd->calc_job); + it->wd->calc_job = ecore_job_add(_calc_job, it->wd); + } + if (it->itc->func.del) + it->itc->func.del((void *)it->base.data, it->base.widget); + return; + } + _item_del(it); +} + +/** + * Set the data item from the genlist item + * + * This set the data value passed on the elm_genlist_item_append() and + * related item addition calls. This function will also call + * elm_genlist_item_update() so the item will be updated to reflect the + * new data. + * + * @param it The item + * @param data The new data pointer to set + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_data_set(Elm_Genlist_Item *it, + const void *data) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + elm_widget_item_data_set(it, data); + elm_genlist_item_update(it); +} + +/** + * Get the data item from the genlist item + * + * This returns the data value passed on the elm_genlist_item_append() + * and related item addition calls and elm_genlist_item_data_set(). + * + * @param it The item + * @return The data pointer provided when created + * + * @ingroup Genlist + */ +EAPI void * +elm_genlist_item_data_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, NULL); + return elm_widget_item_data_get(it); +} + +/** + * Tells genlist to "orphan" icons fetchs by the item class + * + * This instructs genlist to release references to icons in the item, + * meaning that they will no longer be managed by genlist and are + * floating "orphans" that can be re-used elsewhere if the user wants + * to. + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_icons_orphan(Elm_Genlist_Item *it) +{ + Evas_Object *icon; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + EINA_LIST_FREE(it->icon_objs, icon) + { + elm_widget_sub_object_del(it->base.widget, icon); + evas_object_smart_member_del(icon); + evas_object_hide(icon); + } +} + +/** + * Get the real evas object of the genlist item + * + * This returns the actual evas object used for the specified genlist + * item. This may be NULL as it may not be created, and may be deleted + * at any time by genlist. Do not modify this object (move, resize, + * show, hide etc.) as genlist is controlling it. This function is for + * querying, emitting custom signals or hooking lower level callbacks + * for events. Do not delete this object under any circumstances. + * + * @param it The item + * @return The object pointer + * + * @ingroup Genlist + */ +EAPI const Evas_Object * +elm_genlist_item_object_get(const Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, NULL); + return it->base.view; +} + +/** + * Update the contents of an item + * + * This updates an item by calling all the item class functions again + * to get the icons, labels and states. Use this when the original + * item data has changed and the changes are desired to be reflected. + * + * @param it The item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_update(Elm_Genlist_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + if (!it->block) return; + if (it->delete_me) return; + it->mincalcd = EINA_FALSE; + it->updateme = EINA_TRUE; + it->block->updateme = EINA_TRUE; + if (it->wd->update_job) ecore_job_del(it->wd->update_job); + it->wd->update_job = ecore_job_add(_update_job, it->wd); +} + +/** + * Update the item class of an item + * + * @param it The item + * @parem itc The item class for the item + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_item_class_update(Elm_Genlist_Item *it, + const Elm_Genlist_Item_Class *itc) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + if (!it->block) return; + EINA_SAFETY_ON_NULL_RETURN(itc); + if (it->delete_me) return; + it->itc = itc; + elm_genlist_item_update(it); +} + +static Evas_Object * +_elm_genlist_item_label_create(void *data, + Evas_Object *obj, + void *item __UNUSED__) +{ + Evas_Object *label = elm_label_add(obj); + if (!label) + return NULL; + elm_object_style_set(label, "tooltip"); + elm_label_label_set(label, data); + return label; +} + +static void +_elm_genlist_item_label_del_cb(void *data, + Evas_Object *obj __UNUSED__, + void *event_info __UNUSED__) +{ + eina_stringshare_del(data); +} + +/** + * Set the text to be shown in the genlist item. + * + * @param item Target item + * @param text The text to set in the content + * + * Setup the text as tooltip to object. The item can have only one + * tooltip, so any previous tooltip data is removed. + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_tooltip_text_set(Elm_Genlist_Item *item, + const char *text) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + text = eina_stringshare_add(text); + elm_genlist_item_tooltip_content_cb_set(item, _elm_genlist_item_label_create, + text, + _elm_genlist_item_label_del_cb); +} + +/** + * Set the content to be shown in the tooltip item + * + * Setup the tooltip to item. The item can have only one tooltip, so + * any previous tooltip data is removed. @p func(with @p data) will be + * called every time that need to show the tooltip and it should return a + * valid Evas_Object. This object is then managed fully by tooltip + * system and is deleted when the tooltip is gone. + * + * @param item the genlist item being attached by a tooltip. + * @param func the function used to create the tooltip contents. + * @param data what to provide to @a func as callback data/context. + * @param del_cb called when data is not needed anymore, either when + * another callback replaces @func, the tooltip is unset with + * elm_genlist_item_tooltip_unset() or the owner @a item + * dies. This callback receives as the first parameter the + * given @a data, and @c event_info is the item. + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_tooltip_content_cb_set(Elm_Genlist_Item *item, + Elm_Tooltip_Item_Content_Cb func, + const void *data, + Evas_Smart_Cb del_cb) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_GOTO(item, error); + + if ((item->tooltip.content_cb == func) && (item->tooltip.data == data)) + return; + + if (item->tooltip.del_cb) + item->tooltip.del_cb((void *)item->tooltip.data, + item->base.widget, item); + + item->tooltip.content_cb = func; + item->tooltip.data = data; + item->tooltip.del_cb = del_cb; + + if (item->base.view) + { + elm_widget_item_tooltip_content_cb_set(item, + item->tooltip.content_cb, + item->tooltip.data, NULL); + elm_widget_item_tooltip_style_set(item, item->tooltip.style); + } + + return; + +error: + if (del_cb) del_cb((void *)data, NULL, NULL); +} + +/** + * Unset tooltip from item + * + * @param item genlist item to remove previously set tooltip. + * + * Remove tooltip from item. The callback provided as del_cb to + * elm_genlist_item_tooltip_content_cb_set() will be called to notify + * it is not used anymore. + * + * @see elm_genlist_item_tooltip_content_cb_set() + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_tooltip_unset(Elm_Genlist_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if ((item->base.view) && (item->tooltip.content_cb)) + elm_widget_item_tooltip_unset(item); + + if (item->tooltip.del_cb) + item->tooltip.del_cb((void *)item->tooltip.data, item->base.widget, item); + item->tooltip.del_cb = NULL; + item->tooltip.content_cb = NULL; + item->tooltip.data = NULL; + if (item->tooltip.style) + elm_genlist_item_tooltip_style_set(item, NULL); +} + +/** + * Sets a different style for this item tooltip. + * + * @note before you set a style you should define a tooltip with + * elm_genlist_item_tooltip_content_cb_set() or + * elm_genlist_item_tooltip_text_set() + * + * @param item genlist item with tooltip already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_tooltip_style_set(Elm_Genlist_Item *item, + const char *style) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + eina_stringshare_replace(&item->tooltip.style, style); + if (item->base.view) elm_widget_item_tooltip_style_set(item, style); +} + +/** + * Get the style for this item tooltip. + * + * @param item genlist item with tooltip already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a tooltip set, then NULL is returned. + * + * @ingroup Genlist + */ +EAPI const char * +elm_genlist_item_tooltip_style_get(const Elm_Genlist_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->tooltip.style; +} + +/** + * Set the cursor to be shown when mouse is over the genlist item + * + * @param item Target item + * @param cursor the cursor name to be used. + * + * @see elm_object_cursor_set() + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_cursor_set(Elm_Genlist_Item *item, + const char *cursor) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + eina_stringshare_replace(&item->mouse_cursor, cursor); + if (item->base.view) elm_widget_item_cursor_set(item, cursor); +} + +/** + * Get the cursor to be shown when mouse is over the genlist item + * + * @param item genlist item with cursor already set. + * @return the cursor name. + * + * @ingroup Genlist + */ +EAPI const char * +elm_genlist_item_cursor_get(const Elm_Genlist_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_cursor_get(item); +} + +/** + * Unset the cursor to be shown when mouse is over the genlist item + * + * @param item Target item + * + * @see elm_object_cursor_unset() + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_cursor_unset(Elm_Genlist_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (!item->mouse_cursor) + return; + + if (item->base.view) + elm_widget_item_cursor_unset(item); + + eina_stringshare_del(item->mouse_cursor); + item->mouse_cursor = NULL; +} + +/** + * Sets a different style for this item cursor. + * + * @note before you set a style you should define a cursor with + * elm_genlist_item_cursor_set() + * + * @param item genlist item with cursor already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_cursor_style_set(Elm_Genlist_Item *item, + const char *style) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_cursor_style_set(item, style); +} + +/** + * Get the style for this item cursor. + * + * @param item genlist item with cursor already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a cursor set, then NULL is returned. + * + * @ingroup Genlist + */ +EAPI const char * +elm_genlist_item_cursor_style_get(const Elm_Genlist_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_cursor_style_get(item); +} + +/** + * Set if the cursor set should be searched on the theme or should use + * the provided by the engine, only. + * + * @note before you set if should look on theme you should define a + * cursor with elm_object_cursor_set(). By default it will only look + * for cursors provided by the engine. + * + * @param item widget item with cursor already set. + * @param engine_only boolean to define it cursors should be looked + * only between the provided by the engine or searched on widget's + * theme as well. + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_item_cursor_engine_only_set(Elm_Genlist_Item *item, + Eina_Bool engine_only) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_cursor_engine_only_set(item, engine_only); +} + +/** + * Get the cursor engine only usage for this item cursor. + * + * @param item widget item with cursor already set. + * @return engine_only boolean to define it cursors should be looked + * only between the provided by the engine or searched on widget's + * theme as well. If the object does not have a cursor set, then + * EINA_FALSE is returned. + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_item_cursor_engine_only_get(const Elm_Genlist_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + return elm_widget_item_cursor_engine_only_get(item); +} + +/** + * This sets the horizontal stretching mode + * + * This sets the mode used for sizing items horizontally. Valid modes + * are ELM_LIST_LIMIT and ELM_LIST_SCROLL. The default is + * ELM_LIST_SCROLL. This mode means that if items are too wide to fit, + * the scroller will scroll horizontally. Otherwise items are expanded + * to fill the width of the viewport of the scroller. If it is + * ELM_LIST_LIMIT, Items will be expanded to the viewport width and + * limited to that size. + * + * @param obj The genlist object + * @param mode The mode to use + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_horizontal_mode_set(Evas_Object *obj, + Elm_List_Mode mode) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->mode == mode) return; + wd->mode = mode; + _sizing_eval(obj); +} + +/** + * Gets the horizontal stretching mode + * + * @param obj The genlist object + * @return The mode to use + * (ELM_LIST_LIMIT, ELM_LIST_SCROLL) + * + * @ingroup Genlist + */ +EAPI Elm_List_Mode +elm_genlist_horizontal_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_LIST_LAST; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_LIST_LAST; + return wd->mode; +} + +/** + * Set the always select mode. + * + * Items will only call their selection func and callback when first + * becoming selected. Any further clicks will do nothing, unless you + * enable always select with elm_genlist_always_select_mode_set(). + * This means even if selected, every click will make the selected + * callbacks be called. + * + * @param obj The genlist object + * @param always_select The always select mode + * (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_always_select_mode_set(Evas_Object *obj, + Eina_Bool always_select) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->always_select = always_select; +} + +/** + * Get the always select mode. + * + * @param obj The genlist object + * @return The always select mode + * (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_always_select_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->always_select; +} + +/** + * Set no select mode + * + * This will turn off the ability to select items entirely and they + * will neither appear selected nor call selected callback functions. + * + * @param obj The genlist object + * @param no_select The no select mode + * (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_no_select_mode_set(Evas_Object *obj, + Eina_Bool no_select) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->no_select = no_select; +} + +/** + * Gets no select mode + * + * @param obj The genlist object + * @return The no select mode + * (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_no_select_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->no_select; +} + +/** + * Set compress mode + * + * This will enable the compress mode where items are "compressed" + * horizontally to fit the genlist scrollable viewport width. This is + * special for genlist. Do not rely on + * elm_genlist_horizontal_mode_set() being set to ELM_LIST_COMPRESS to + * work as genlist needs to handle it specially. + * + * @param obj The genlist object + * @param compress The compress mode + * (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_compress_mode_set(Evas_Object *obj, + Eina_Bool compress) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->compress = compress; +} + +/** + * Get the compress mode + * + * @param obj The genlist object + * @return The compress mode + * (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_compress_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->compress; +} + +/** + * Set height-for-width mode + * + * With height-for-width mode the item width will be fixed (restricted + * to a minimum of) to the list width when calculating its size in + * order to allow the height to be calculated based on it. This allows, + * for instance, text block to wrap lines if the Edje part is + * configured with "text.min: 0 1". + * + * @note This mode will make list resize slower as it will have to + * recalculate every item height again whenever the list width + * changes! + * + * @note When height-for-width mode is enabled, it also enables + * compress mode (see elm_genlist_compress_mode_set()) and + * disables homogeneous (see elm_genlist_homogeneous_set()). + * + * @param obj The genlist object + * @param setting The height-for-width mode (EINA_TRUE = on, + * EINA_FALSE = off) + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_height_for_width_mode_set(Evas_Object *obj, + Eina_Bool height_for_width) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->height_for_width = !!height_for_width; + if (wd->height_for_width) + { + elm_genlist_homogeneous_set(obj, EINA_FALSE); + elm_genlist_compress_mode_set(obj, EINA_TRUE); + } +} + +/** + * Get the height-for-width mode + * + * @param obj The genlist object + * @return The height-for-width mode (EINA_TRUE = on, EINA_FALSE = + * off) + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_height_for_width_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->height_for_width; +} + +/** + * Set bounce mode + * + * This will enable or disable the scroller bounce mode for the + * genlist. See elm_scroller_bounce_set() for details + * + * @param obj The genlist object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_bounce_set(Evas_Object *obj, + Eina_Bool h_bounce, + Eina_Bool v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_bounce_allow_set(wd->scr, h_bounce, v_bounce); +} + +/** + * Get the bounce mode + * + * @param obj The genlist object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_bounce_get(const Evas_Object *obj, + Eina_Bool *h_bounce, + Eina_Bool *v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_bounce_allow_get(obj, h_bounce, v_bounce); +} + +/** + * Set homogenous mode + * + * This will enable the homogeneous mode where items are of the same + * height and width so that genlist may do the lazy-loading at its + * maximum. This implies 'compressed' mode. + * + * @param obj The genlist object + * @param homogeneous Assume the items within the genlist are of the + * same height and width (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_homogeneous_set(Evas_Object *obj, + Eina_Bool homogeneous) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (homogeneous) elm_genlist_compress_mode_set(obj, EINA_TRUE); + wd->homogeneous = homogeneous; +} + +/** + * Get the homogenous mode + * + * @param obj The genlist object + * @return Assume the items within the genlist are of the same height + * and width (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Genlist + */ +EAPI Eina_Bool +elm_genlist_homogeneous_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->homogeneous; +} + +/** + * Set the maximum number of items within an item block + * + * This will configure the block count to tune to the target with + * particular performance matrix. + * + * @param obj The genlist object + * @param n Maximum number of items within an item block + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_block_count_set(Evas_Object *obj, + int n) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->max_items_per_block = n; + wd->item_cache_max = wd->max_items_per_block * 2; + _item_cache_clean(wd); +} + +/** + * Get the maximum number of items within an item block + * + * @param obj The genlist object + * @return Maximum number of items within an item block + * + * @ingroup Genlist + */ +EAPI int +elm_genlist_block_count_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->max_items_per_block; +} + +/** + * Set the timeout in seconds for the longpress event + * + * @param obj The genlist object + * @param timeout timeout in seconds + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_longpress_timeout_set(Evas_Object *obj, + double timeout) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->longpress_timeout = timeout; +} + +/** + * Get the timeout in seconds for the longpress event + * + * @param obj The genlist object + * @return timeout in seconds + * + * @ingroup Genlist + */ +EAPI double +elm_genlist_longpress_timeout_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->longpress_timeout; +} + +/** + * Set the scrollbar policy + * + * This sets the scrollbar visibility policy for the given genlist + * scroller. ELM_SMART_SCROLLER_POLICY_AUTO means the scrollbar is + * made visible if it is needed, and otherwise kept hidden. + * ELM_SMART_SCROLLER_POLICY_ON turns it on all the time, and + * ELM_SMART_SCROLLER_POLICY_OFF always keeps it off. This applies + * respectively for the horizontal and vertical scrollbars. + * + * @param obj The genlist object + * @param policy_h Horizontal scrollbar policy + * @param policy_v Vertical scrollbar policy + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_scroller_policy_set(Evas_Object *obj, + Elm_Scroller_Policy policy_h, + Elm_Scroller_Policy policy_v) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if ((policy_h >= ELM_SCROLLER_POLICY_LAST) || + (policy_v >= ELM_SCROLLER_POLICY_LAST)) + return; + if (wd->scr) + elm_smart_scroller_policy_set(wd->scr, policy_h, policy_v); +} + +/** + * Get the scrollbar policy + * + * @param obj The genlist object + * @param policy_h Horizontal scrollbar policy + * @param policy_v Vertical scrollbar policy + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_scroller_policy_get(const Evas_Object *obj, + Elm_Scroller_Policy *policy_h, + Elm_Scroller_Policy *policy_v) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Smart_Scroller_Policy s_policy_h, s_policy_v; + if ((!wd) || (!wd->scr)) return; + elm_smart_scroller_policy_get(wd->scr, &s_policy_h, &s_policy_v); + if (policy_h) *policy_h = (Elm_Scroller_Policy)s_policy_h; + if (policy_v) *policy_v = (Elm_Scroller_Policy)s_policy_v; +} diff --git a/src/lib/elm_hover.c b/src/lib/elm_hover.c new file mode 100644 index 0000000..45d5447 --- /dev/null +++ b/src/lib/elm_hover.c @@ -0,0 +1,957 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Hover Hover + * + * A Hover object will over its @p parent object at the @p target + * location. Anything in the background will be given a darker + * coloring to indicate that the hover object is on top (at the + * default theme). + * + * @note The hover object will take up the entire space of @p target + * object. + */ + +typedef struct _Widget_Data Widget_Data; +typedef struct _Content_Info Content_Info; + +#ifndef MAX +# define MAX(a, b) (((a) > (b)) ? (a) : (b)) +#endif + +#define ELM_HOVER_PARTS_FOREACH unsigned int i = 0; \ + for (i = 0; i < sizeof(wd->subs) / sizeof(wd->subs[0]); i++) + +static const char *_directions[] = { + "left", + "top-left", + "top", + "top-right", + "right", + "bottom-right", + "bottom", + "bottom-left", + "middle" +}; + +#define _HOV_LEFT (_directions[0]) +#define _HOV_TOP_LEFT (_directions[1]) +#define _HOV_TOP (_directions[2]) +#define _HOV_TOP_RIGHT (_directions[2]) +#define _HOV_RIGHT (_directions[4]) +#define _HOV_BOTTOM_RIGHT (_directions[5]) +#define _HOV_BOTTOM (_directions[6]) +#define _HOV_BOTTOM_LEFT (_directions[7]) +#define _HOV_MIDDLE (_directions[8]) + +struct _Content_Info +{ + const char *swallow; + Evas_Object *obj; +}; + +struct _Widget_Data +{ + Evas_Object *hov, *cov; + Evas_Object *offset, *size; + Evas_Object *parent, *target; + Evas_Object *smt_sub; + Content_Info subs[sizeof(_directions)/sizeof(_directions[0])]; +}; + +static const char *widtype = NULL; +static void _del_pre_hook(Evas_Object *obj); +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _reval_content(Evas_Object *obj); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _hov_show_do(Evas_Object *obj); +static void _hov_move(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _hov_resize(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _hov_show(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _hov_hide(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _on_focus_hook(void *data, Evas_Object *obj); +static void _elm_hover_sub_obj_placement_eval_cb(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _elm_hover_sub_obj_placement_eval(Evas_Object *obj); + +static const char SIG_CLICKED[] = "clicked"; +static const char SIG_SMART_LOCATION_CHANGED[] = "smart,changed"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_CLICKED, ""}, + {SIG_SMART_LOCATION_CHANGED, ""}, + {NULL, NULL} +}; + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (evas_object_visible_get(obj)) + evas_object_smart_callback_call(obj, SIG_CLICKED, NULL); + elm_hover_target_set(obj, NULL); + elm_hover_parent_set(obj, NULL); + evas_object_event_callback_del_full(wd->hov, EVAS_CALLBACK_MOVE, _hov_move, obj); + evas_object_event_callback_del_full(wd->hov, EVAS_CALLBACK_RESIZE, _hov_resize, obj); + evas_object_event_callback_del_full(wd->hov, EVAS_CALLBACK_SHOW, _hov_show, obj); + evas_object_event_callback_del_full(wd->hov, EVAS_CALLBACK_HIDE, _hov_hide, obj); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->cov, "elm,action,focus", "elm"); + evas_object_focus_set(wd->cov, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->cov, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->cov, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + // FIXME: hover contents doesn't seem to propagate resizes properly + _elm_theme_object_set(obj, wd->cov, "hover", "base", elm_widget_style_get(obj)); + edje_object_scale_set(wd->cov, elm_widget_scale_get(obj) * + _elm_config->scale); + + if (wd->smt_sub) + _elm_hover_sub_obj_placement_eval(obj); + else + _reval_content(obj); + _sizing_eval(obj); + if (evas_object_visible_get(wd->cov)) _hov_show_do(obj); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + edje_object_signal_emit(wd->cov, emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + edje_object_signal_callback_add(wd->hov, emission, source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + + edje_object_signal_callback_del_full(wd->hov, emission, source, func_cb, + data); +} + +static void +_elm_hover_left_space_calc(Widget_Data *wd, Evas_Coord *spc_l, Evas_Coord *spc_t, Evas_Coord *spc_r, Evas_Coord *spc_b) +{ + Evas_Coord x = 0, y = 0, w = 0, h = 0, x2 = 0, y2 = 0, w2 = 0, h2 = 0; + + if (wd->parent) + evas_object_geometry_get(wd->parent, &x, &y, &w, &h); + if (wd->target) + evas_object_geometry_get(wd->target, &x2, &y2, &w2, &h2); + + *spc_l = x2 - x; + *spc_r = (x + w) - (x2 + w2); + if (*spc_l < 0) + *spc_l = 0; + if (*spc_r < 0) + *spc_r = 0; + + *spc_t = y2 - y; + *spc_b = (y + h) - (y2 + h2); + if (*spc_t < 0) + *spc_t = 0; + if (*spc_b < 0) + *spc_b = 0; +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord x = 0, y = 0, w = 0, h = 0, x2 = 0, y2 = 0, w2 = 0, h2 = 0; + if (!wd) return; + if (wd->parent) evas_object_geometry_get(wd->parent, &x, &y, &w, &h); + if (wd->hov) evas_object_geometry_get(wd->hov, &x2, &y2, &w2, &h2); + evas_object_move(wd->cov, x, y); + evas_object_resize(wd->cov, w, h); + evas_object_size_hint_min_set(wd->offset, x2 - x, y2 - y); + evas_object_size_hint_min_set(wd->size, w2, h2); + edje_object_part_swallow(wd->cov, "elm.swallow.offset", wd->offset); + edje_object_part_swallow(wd->cov, "elm.swallow.size", wd->size); +} + +static void +_reval_content(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return; + + ELM_HOVER_PARTS_FOREACH + { + char buf[1024]; + snprintf(buf, sizeof(buf), "elm.swallow.slot.%s", wd->subs[i].swallow); + edje_object_part_swallow(wd->cov, buf, wd->subs[i].obj); + } +} + +static const char * +_elm_hover_smart_content_location_get(Widget_Data *wd, Evas_Coord spc_l, Evas_Coord spc_t, Evas_Coord spc_r, Evas_Coord spc_b) +{ + Evas_Coord c_w = 0, c_h = 0, mid_w, mid_h; + int max; + + evas_object_size_hint_min_get(wd->smt_sub, &c_w, &c_h); + mid_w = c_w / 2; + mid_h = c_h / 2; + + if (spc_l > spc_r) + goto left; + + max = MAX(spc_t, spc_r); + max = MAX(max, spc_b); + + if (max == spc_t) + { + if (mid_w > spc_l) + return _HOV_TOP_RIGHT; + + return _HOV_TOP; + } + + if (max == spc_r) + { + if (mid_h > spc_t) + return _HOV_BOTTOM_RIGHT; + else if (mid_h > spc_b) + return _HOV_TOP_RIGHT; + + return _HOV_RIGHT; + } + + if (mid_h > spc_l) + return _HOV_BOTTOM_RIGHT; + + return _HOV_BOTTOM; + +left: + max = MAX(spc_t, spc_l); + max = MAX(max, spc_b); + + if (max == spc_t) + { + if (mid_w > spc_r) + return _HOV_TOP_LEFT; + + return _HOV_TOP; + } + + if (max == spc_l) + { + if (mid_h > spc_t) + return _HOV_BOTTOM_LEFT; + else if (mid_h > spc_b) + return _HOV_TOP_LEFT; + + return _HOV_LEFT; + } + + if (mid_h > spc_r) + return _HOV_BOTTOM_LEFT; + + return _HOV_BOTTOM; +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd; + Evas_Object *sub; + + sub = event_info; + wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (wd->smt_sub) + { + if (wd->smt_sub == sub) + wd->smt_sub = NULL; + } + else + { + ELM_HOVER_PARTS_FOREACH + { + if (wd->subs[i].obj == sub) + { + wd->subs[i].obj = NULL; + break; + } + } + } +} + +static void +_hov_show_do(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (wd->cov) + { + evas_object_show(wd->cov); + edje_object_signal_emit(wd->cov, "elm,action,show", "elm"); + } + + ELM_HOVER_PARTS_FOREACH + { + char buf[1024]; + + if (wd->subs[i].obj) + { + snprintf(buf, sizeof(buf), "elm,action,slot,%s,show", + wd->subs[i].swallow); + edje_object_signal_emit(wd->cov, buf, "elm"); + } + } +} + +static void +_hov_move(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_hov_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_hov_show(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _hov_show_do(data); +} + +static void +_hov_hide(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (wd->cov) + { + edje_object_signal_emit(wd->cov, "elm,action,hide", "elm"); + evas_object_hide(wd->cov); + } + + ELM_HOVER_PARTS_FOREACH + { + char buf[1024]; + + if (wd->subs[i].obj) + { + snprintf(buf, sizeof(buf), "elm,action,slot,%s,hide", + wd->subs[i].swallow); + edje_object_signal_emit(wd->cov, buf, "elm"); + } + } +} + +static void +_target_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->target = NULL; +} + +static void +_target_move(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) + return; + + _sizing_eval(data); + _elm_hover_sub_obj_placement_eval(data); +} + +static void +_signal_dismiss(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_hide(data); + evas_object_smart_callback_call(data, SIG_CLICKED, NULL); +} + +static void +_parent_move(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_parent_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_parent_show(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ +} + +static void +_parent_hide(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_hide(wd->cov); +} + +static void +_parent_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + elm_hover_parent_set(data, NULL); + _sizing_eval(data); +} + +/** + * Adds a hover object to @p parent + * + * @param parent The parent object + * @return The hover object or NULL if one could not be created + * + * @ingroup Hover + */ +EAPI Evas_Object * +elm_hover_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + + ELM_HOVER_PARTS_FOREACH + wd->subs[i].swallow = _directions[i]; + + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "hover"); + elm_widget_type_set(obj, "hover"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + + wd->hov = evas_object_rectangle_add(e); + evas_object_pass_events_set(wd->hov, EINA_TRUE); + evas_object_color_set(wd->hov, 0, 0, 0, 0); + elm_widget_resize_object_set(obj, wd->hov); + evas_object_event_callback_add(wd->hov, EVAS_CALLBACK_MOVE, _hov_move, obj); + evas_object_event_callback_add(wd->hov, EVAS_CALLBACK_RESIZE, _hov_resize, obj); + evas_object_event_callback_add(wd->hov, EVAS_CALLBACK_SHOW, _hov_show, obj); + evas_object_event_callback_add(wd->hov, EVAS_CALLBACK_HIDE, _hov_hide, obj); + + wd->cov = edje_object_add(e); + _elm_theme_object_set(obj, wd->cov, "hover", "base", "default"); + elm_widget_sub_object_add(obj, wd->cov); + edje_object_signal_callback_add(wd->cov, "elm,action,dismiss", "", + _signal_dismiss, obj); + + wd->offset = evas_object_rectangle_add(e); + evas_object_pass_events_set(wd->offset, EINA_TRUE); + evas_object_color_set(wd->offset, 0, 0, 0, 0); + elm_widget_sub_object_add(obj, wd->offset); + + wd->size = evas_object_rectangle_add(e); + evas_object_pass_events_set(wd->size, EINA_TRUE); + evas_object_color_set(wd->size, 0, 0, 0, 0); + elm_widget_sub_object_add(obj, wd->size); + + edje_object_part_swallow(wd->cov, "elm.swallow.offset", wd->offset); + edje_object_part_swallow(wd->cov, "elm.swallow.size", wd->size); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + elm_hover_parent_set(obj, parent); + evas_object_smart_callbacks_descriptions_set(obj, _signals); + + _sizing_eval(obj); + return obj; +} + +/** + * Sets the target object for the hover. + * + * @param obj The hover object + * @param target The object to center the hover onto. The hover + * will take up the entire space that the target object fills. + * + * @ingroup Hover + */ +EAPI void +elm_hover_target_set(Evas_Object *obj, Evas_Object *target) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (wd->target) + { + evas_object_event_callback_del_full(wd->target, EVAS_CALLBACK_DEL, + _target_del, obj); + evas_object_event_callback_del_full(wd->target, EVAS_CALLBACK_MOVE, + _target_move, obj); + } + wd->target = target; + if (wd->target) + { + evas_object_event_callback_add(wd->target, EVAS_CALLBACK_DEL, + _target_del, obj); + evas_object_event_callback_add(wd->target, EVAS_CALLBACK_MOVE, + _target_move, obj); + elm_widget_hover_object_set(target, obj); + _sizing_eval(obj); + } +} + + +/** + * Sets the parent object for the hover. + * + * @param obj The hover object + * @param parent The object to locate the hover over. + * + * @ingroup Hover + */ +EAPI void +elm_hover_parent_set(Evas_Object *obj, Evas_Object *parent) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->parent) + { + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_MOVE, + _parent_move, obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_RESIZE, + _parent_resize, obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_SHOW, + _parent_show, obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_HIDE, + _parent_hide, obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_DEL, + _parent_del, obj); + } + wd->parent = parent; + if (wd->parent) + { + evas_object_event_callback_add(wd->parent, EVAS_CALLBACK_MOVE, + _parent_move, obj); + evas_object_event_callback_add(wd->parent, EVAS_CALLBACK_RESIZE, + _parent_resize, obj); + evas_object_event_callback_add(wd->parent, EVAS_CALLBACK_SHOW, + _parent_show, obj); + evas_object_event_callback_add(wd->parent, EVAS_CALLBACK_HIDE, + _parent_hide, obj); + evas_object_event_callback_add(wd->parent, EVAS_CALLBACK_DEL, + _parent_del, obj); +// elm_widget_sub_object_add(parent, obj); + } + _sizing_eval(obj); +} + +/** + * Gets the target object for the hover. + * + * @param obj The hover object + * @return The target object of the hover. + * + * @ingroup Hover + */ +EAPI Evas_Object * +elm_hover_target_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + return wd->target; +} + +/** + * Gets the parent object for the hover. + * + * @param obj The hover object + * @return The parent object to locate the hover over. + * + * @ingroup Hover + */ +EAPI Evas_Object * +elm_hover_parent_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + return wd->parent; +} + +static void +_elm_hover_subs_del(Widget_Data *wd) +{ + ELM_HOVER_PARTS_FOREACH + { + if (wd->subs[i].obj) + { + evas_object_del(wd->subs[i].obj); + wd->subs[i].obj = NULL; + } + } +} + +static void +_elm_hover_sub_obj_placement_eval(Evas_Object *obj) +{ + Evas_Coord spc_l, spc_r, spc_t, spc_b; + const char *smart_dir; + Widget_Data *wd; + char buf[1024]; + + wd = elm_widget_data_get(obj); + if (!wd->smt_sub) + return; + + _elm_hover_left_space_calc(wd, &spc_l, &spc_t, &spc_r, &spc_b); + + edje_object_part_unswallow(wd->cov, wd->smt_sub); + + smart_dir = _elm_hover_smart_content_location_get(wd, spc_l, spc_t, spc_r, + spc_b); + evas_object_smart_callback_call(obj, SIG_SMART_LOCATION_CHANGED, + (void *)smart_dir); + + snprintf(buf, sizeof(buf), "elm.swallow.slot.%s", smart_dir); + edje_object_part_swallow(wd->cov, buf, wd->smt_sub); +} + +static void +_elm_hover_sub_obj_placement_eval_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _elm_hover_sub_obj_placement_eval(data); +} + +/** + * Sets the content of the hover object and the direction in which + * it will pop out. + * + * Once the content object is set for a given direction, a previously + * set one (on the same direction) will be deleted. If you want to + * keep that old content object, use the elm_hover_content_unset() + * function. + * + * @param obj The hover object + * @param swallow The direction that the object will be displayed + * at. Accepted values are "left", "top-left", "top", "top-right", + * "right", "bottom-right", "bottom", "bottom-left", "middle" and + * "smart". + * @param content The content to place at @p swallow + * + * All directions may have contents at the same time, except for + * "smart". This is a special placement hint and its use case + * independs of the calculations coming from + * elm_hover_best_content_location_get(). Its use is for cases when + * one desires only one hover content, but with a dinamic special + * placement within the hover area. The content's geometry, whenever + * it changes, will be used to decide on a best location not + * extrapolating the hover's parent object view to show it in (still + * being the hover's target determinant of its medium part -- move and + * resize it to simulate finger sizes, for example). If one of the + * directions other than "smart" are used, a previously content set + * using it will be deleted, and vice-versa. + * + * @ingroup Hover + */ +EAPI void +elm_hover_content_set(Evas_Object *obj, const char *swallow, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (!strcmp(swallow, "smart")) + { + if (wd->smt_sub != content) + { + _elm_hover_subs_del(wd); + wd->smt_sub = content; + } + + if (content) + { + elm_widget_sub_object_add(obj, content); + evas_object_event_callback_add(wd->smt_sub, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _elm_hover_sub_obj_placement_eval_cb, + obj); + + _elm_hover_sub_obj_placement_eval(obj); + } + + goto end; + } + + if (wd->smt_sub) + { + evas_object_del(wd->smt_sub); + wd->smt_sub = NULL; + } + + ELM_HOVER_PARTS_FOREACH + { + if (!strcmp(swallow, wd->subs[i].swallow)) + { + if (content == wd->subs[i].obj) + return; + evas_object_del(wd->subs[i].obj); + wd->subs[i].obj = NULL; + + if (content) + { + char buf[1024]; + + snprintf(buf, sizeof(buf), "elm.swallow.slot.%s", swallow); + elm_widget_sub_object_add(obj, content); + edje_object_part_swallow(wd->cov, buf, content); + wd->subs[i].obj = content; + } + break; + } + } + + end: + _sizing_eval(obj); +} + +/** + * Get the content of the hover object, in a given direction. + * + * Return the content object which was set for this widget in the + * given direction. + * + * @param obj The hover object + * @param swallow The direction that the object was display at. + * @return The content that was being used + * + * @note See elm_hover_content_set() for more information. + * + * @ingroup Hover + */ +EAPI Evas_Object * +elm_hover_content_get(const Evas_Object *obj, const char *swallow) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return NULL; + + if (!strcmp(swallow, "smart")) + return wd->smt_sub; + + ELM_HOVER_PARTS_FOREACH + if (!strcmp(swallow, wd->subs[i].swallow)) + return wd->subs[i].obj; + + return NULL; +} + +static void +_elm_hover_sub_obj_unparent(Evas_Object *obj) +{ + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + + elm_widget_sub_object_del(obj, wd->smt_sub); + evas_object_event_callback_del_full(wd->smt_sub, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _elm_hover_sub_obj_placement_eval_cb, + obj); + edje_object_part_unswallow(wd->cov, wd->smt_sub); + wd->smt_sub = NULL; +} + +/** + * Unset the content of the hover object, in a given direction. + * + * Unparent and return the content object set at that direction. + * + * @param obj The hover object + * @param swallow The direction that the object was display at. + * @return The content that was being used. + * + * @note See elm_hover_content_set() for more information. + * + * @ingroup Hover + */ +EAPI Evas_Object * +elm_hover_content_unset(Evas_Object *obj, const char *swallow) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return NULL; + + if (!strcmp(swallow, "smart")) + { + Evas_Object *content; + + if (!wd->smt_sub) + return NULL; + + content = wd->smt_sub; + _elm_hover_sub_obj_unparent(obj); + return content; + } + + ELM_HOVER_PARTS_FOREACH + { + if (!strcmp(swallow, wd->subs[i].swallow)) + { + Evas_Object *content; + + if (!wd->subs[i].obj) + return NULL; + + content = wd->subs[i].obj; + elm_widget_sub_object_del(obj, wd->subs[i].obj); + edje_object_part_unswallow(wd->cov, wd->subs[i].obj); + wd->subs[i].obj = NULL; + + return content; + } + } + + return NULL; +} + +/** + * Returns the best swallow location for content in the hover. + * + * @param obj The hover object + * @param pref_axis The preferred orientation axis for the hover object to use + * @return The edje location to place content into the hover or @c + * NULL, on errors. + * + * @p pref_axis may be one of + *
      + * - @c ELM_HOVER_AXIS_NONE -- no prefered orientation + * - @c ELM_HOVER_AXIS_HORIZONTAL -- horizontal + * - @c ELM_HOVER_AXIS_VERTICAL -- vertical + * - @c ELM_HOVER_AXIS_BOTH -- both + *
    + * + * See also elm_hover_content_set(). + * + * @ingroup Hover + */ +EAPI const char * +elm_hover_best_content_location_get(const Evas_Object *obj, Elm_Hover_Axis pref_axis) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + Evas_Coord spc_l, spc_r, spc_t, spc_b; + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return NULL; + + _elm_hover_left_space_calc(wd, &spc_l, &spc_t, &spc_r, &spc_b); + + if (pref_axis == ELM_HOVER_AXIS_HORIZONTAL) + { + if (spc_l < spc_r) return _HOV_RIGHT; + else return _HOV_LEFT; + } + else if (pref_axis == ELM_HOVER_AXIS_VERTICAL) + { + if (spc_t < spc_b) return _HOV_BOTTOM; + else return _HOV_TOP; + } + + if (spc_l < spc_r) + { + if (spc_t > spc_r) return _HOV_TOP; + else if (spc_b > spc_r) return _HOV_BOTTOM; + return _HOV_RIGHT; + } + if (spc_t > spc_r) return _HOV_TOP; + else if (spc_b > spc_r) return _HOV_BOTTOM; + return _HOV_LEFT; +} diff --git a/src/lib/elm_icon.c b/src/lib/elm_icon.c new file mode 100644 index 0000000..c0fad61 --- /dev/null +++ b/src/lib/elm_icon.c @@ -0,0 +1,651 @@ +#include +#include "elm_priv.h" + +#ifdef ELM_EFREET +#define NON_EXISTING (void *)-1 +static const char *icon_theme = NULL; +#endif + +/** + * @defgroup Icon Icon + * + * A standard icon that may be provided by the theme (delete, edit, + * arrows etc.) or a custom file (PNG, JPG, EDJE etc.) used for an + * icon. The Icon may scale or not and of course... support alpha + * channels. + * + * Signals that you can add callbacks for are: + * + * clicked - This is called when a user has clicked the icon + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *img; + const char *stdicon; + Elm_Icon_Lookup_Order lookup_order; +#ifdef ELM_EFREET + struct { + int requested_size; + Eina_Bool use : 1; + } freedesktop; +#endif + Eina_Bool scale_up : 1; + Eina_Bool scale_down : 1; + Eina_Bool smooth : 1; + Eina_Bool fill_outside : 1; + Eina_Bool no_scale : 1; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _mouse_up(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static Eina_Bool _icon_standard_set(Widget_Data *wd, Evas_Object *obj, const char *name); +static Eina_Bool _icon_freedesktop_set(Widget_Data *wd, Evas_Object *obj, const char *name, int size); + +//FIXME: move this code to ecore +#ifdef _WIN32 +static Eina_Bool +_path_is_absolute(const char *path) +{ + //TODO: Check if this works with all absolute paths in windows + return ((isalpha (*path)) && (*(path + 1) == ':') && ((*(path + 2) == '\\') || (*(path + 2) == '/'))); +} +#else +static Eina_Bool +_path_is_absolute(const char *path) +{ + return (*path == '/'); +} +#endif + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + if (wd->stdicon) eina_stringshare_del(wd->stdicon); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->stdicon) + _elm_theme_object_icon_set(obj, wd->img, wd->stdicon, elm_widget_style_get(obj)); + _sizing_eval(obj); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + Evas_Object *icon_edje; + icon_edje = _els_smart_icon_edje_get(wd->img); + if (!icon_edje) return; + edje_object_signal_emit(icon_edje, emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + Evas_Object *icon_edje; + icon_edje = _els_smart_icon_edje_get(wd->img); + if (!icon_edje) return; + edje_object_signal_callback_add(icon_edje, emission, source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + Evas_Object *icon_edje; + icon_edje = _els_smart_icon_edje_get(wd->img); + if (!icon_edje) return; + edje_object_signal_callback_del_full(icon_edje, emission, source, func_cb, + data); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + int w, h; + + _els_smart_icon_size_get(wd->img, &w, &h); +#ifdef ELM_EFREET + if ((wd->freedesktop.use) && (!((w - wd->freedesktop.requested_size) % 16))) + { + /* This icon has been set to a freedesktop icon, and the requested + appears to have a different size than the requested size, so try to + request another, higher resolution, icon. + FIXME: Find a better heuristic to determine if there should be + an icon with a different resolution. */ + _icon_freedesktop_set(wd, obj, wd->stdicon, w); + } +#endif + _els_smart_icon_scale_up_set(wd->img, wd->scale_up); + _els_smart_icon_scale_down_set(wd->img, wd->scale_down); + _els_smart_icon_smooth_scale_set(wd->img, wd->smooth); + _els_smart_icon_fill_inside_set(wd->img, !(wd->fill_outside)); + if (wd->no_scale) _els_smart_icon_scale_set(wd->img, 1.0); + else + { + _els_smart_icon_scale_set(wd->img, elm_widget_scale_get(obj) * + _elm_config->scale); + _els_smart_icon_size_get(wd->img, &w, &h); + } + if (!wd->scale_down) + { + minw = w; + minh = h; + } + if (!wd->scale_up) + { + maxw = w; + maxh = h; + } + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_mouse_up(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Up *ev = event_info; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return; + evas_object_smart_callback_call(data, "clicked", event_info); +} + +/** + * Add a new icon to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Icon + */ +EAPI Evas_Object * +elm_icon_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "icon"); + elm_widget_type_set(obj, "icon"); + elm_widget_can_focus_set(obj, EINA_FALSE); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + + wd->lookup_order = ELM_ICON_LOOKUP_THEME_FDO; + wd->img = _els_smart_icon_add(e); + evas_object_event_callback_add(wd->img, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, obj); + evas_object_repeat_events_set(wd->img, EINA_TRUE); + elm_widget_resize_object_set(obj, wd->img); + + wd->smooth = EINA_TRUE; + wd->scale_up = EINA_TRUE; + wd->scale_down = EINA_TRUE; + + _sizing_eval(obj); + return obj; +} + +/** + * Set the file that will be used as icon + * + * @param obj The icon object + * @param file The path to file that will be used as icon + * @param group The group that the icon belongs in edje file + * + * @return (1 = success, 0 = error) + * + * @ingroup Icon + */ +EAPI Eina_Bool +elm_icon_file_set(Evas_Object *obj, const char *file, const char *group) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + Eina_Bool ret; + const char *p; + + if (!wd) return EINA_FALSE; + EINA_SAFETY_ON_NULL_RETURN_VAL(file, EINA_FALSE); + if (wd->stdicon) eina_stringshare_del(wd->stdicon); + wd->stdicon = NULL; + if (((p = strrchr(file, '.'))) && (!strcasecmp(p, ".edj"))) + ret = _els_smart_icon_file_edje_set(wd->img, file, group); + else + ret = _els_smart_icon_file_key_set(wd->img, file, group); + _sizing_eval(obj); + return ret; +} + +/** + * Get the file that will be used as icon + * + * @param obj The icon object + * @param file The path to file that will be used as icon + * @param group The group that the icon belongs in edje file + * + * @ingroup Icon + */ +EAPI void +elm_icon_file_get(const Evas_Object *obj, const char **file, const char **group) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _els_smart_icon_file_get(wd->img, file, group); +} + +static Eina_Bool +_icon_standard_set(Widget_Data *wd, Evas_Object *obj, const char *name) +{ + if (_elm_theme_object_icon_set(obj, wd->img, name, "default")) + { +#ifdef ELM_EFREET + /* TODO: elm_unneed_efreet() */ + wd->freedesktop.use = EINA_FALSE; +#endif + return EINA_TRUE; + } + return EINA_FALSE; +} + +static Eina_Bool +_icon_file_set(Widget_Data *wd, Evas_Object *obj, const char *path) +{ + if (elm_icon_file_set(obj, path, NULL)) + { +#ifdef ELM_EFREET + /* TODO: elm_unneed_efreet() */ + wd->freedesktop.use = EINA_FALSE; +#endif + return EINA_TRUE; + } + return EINA_FALSE; +} + +static Eina_Bool +_icon_freedesktop_set(Widget_Data *wd, Evas_Object *obj, const char *name, int size) +{ +#ifdef ELM_EFREET + const char *path; + + elm_need_efreet(); + if (icon_theme == NON_EXISTING) return EINA_FALSE; + if (!icon_theme) + { + Efreet_Icon_Theme *theme; + /* TODO: Listen for EFREET_EVENT_ICON_CACHE_UPDATE */ + theme = efreet_icon_theme_find(getenv("E_ICON_THEME")); + if (!theme) + { + const char **itr; + static const char *themes[] = { + "gnome", "Human", "oxygen", "hicolor", NULL + }; + for (itr = themes; *itr; itr++) + { + theme = efreet_icon_theme_find(*itr); + if (theme) break; + } + } + + if (!theme) + { + icon_theme = NON_EXISTING; + return EINA_FALSE; + } + else + icon_theme = eina_stringshare_add(theme->name.internal); + } + path = efreet_icon_path_find(icon_theme, name, size); + wd->freedesktop.use = !!path; + if (wd->freedesktop.use) + { + wd->freedesktop.requested_size = size; + elm_icon_file_set(obj, path, NULL); + return EINA_TRUE; + } +#endif + return EINA_FALSE; +} + +static inline int +_icon_size_min_get(Evas_Object *icon) +{ + int size; + _els_smart_icon_size_get(icon, &size, NULL); + return (size < 32) ? 32 : size; +} + +/** + * Set the theme, as standard, for a icon. + * If theme was not found and it is the absolute path of an image file, this + * image will be used. + * + * @param obj The icon object + * @param name The theme name + * + * @return (1 = success, 0 = error) + * + * @ingroup Icon + */ +EAPI Eina_Bool +elm_icon_standard_set(Evas_Object *obj, const char *name) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + char *tmp; + Eina_Bool ret; + + if ((!wd) || (!name)) return EINA_FALSE; + + /* try locating the icon using the specified lookup order */ + switch (wd->lookup_order) + { + case ELM_ICON_LOOKUP_FDO: + ret = _icon_freedesktop_set(wd, obj, name, _icon_size_min_get(wd->img)); + break; + case ELM_ICON_LOOKUP_THEME: + ret = _icon_standard_set(wd, obj, name); + break; + case ELM_ICON_LOOKUP_THEME_FDO: + ret = _icon_standard_set(wd, obj, name) || + _icon_freedesktop_set(wd, obj, name, _icon_size_min_get(wd->img)); + break; + case ELM_ICON_LOOKUP_FDO_THEME: + default: + ret = _icon_freedesktop_set(wd, obj, name, _icon_size_min_get(wd->img)) || + _icon_standard_set(wd, obj, name); + break; + } + + if (ret) + { + eina_stringshare_replace(&wd->stdicon, name); + _sizing_eval(obj); + return EINA_TRUE; + } + + if (_path_is_absolute(name)) + return _icon_file_set(wd, obj, name); + + /* if that fails, see if icon name is in the format size/name. if so, + try locating a fallback without the size specification */ + if (!(tmp = strchr(name, '/'))) return EINA_FALSE; + ++tmp; + if (*tmp) return elm_icon_standard_set(obj, tmp); + + /* give up */ + return EINA_FALSE; +} + +/** + * Get the theme, as standard, for a icon + * + * @param obj The icon object + * @return The theme name + * + * @ingroup Icon + */ +EAPI const char * +elm_icon_standard_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->stdicon; +} + +/** + * Sets icon lookup order, used by elm_icon_standard_set(). + * + * @param obj The icon object + * @param order The icon lookup order + * + * @ingroup Icon + */ +EAPI void +elm_icon_order_lookup_set(Evas_Object *obj, Elm_Icon_Lookup_Order order) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (wd) wd->lookup_order = order; +} + +/** + * Gets the icon lookup order. + * + * @param obj The icon object + * @return The icon lookup order + * + * @ingroup Icon + */ +EAPI Elm_Icon_Lookup_Order +elm_icon_order_lookup_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_ICON_LOOKUP_THEME_FDO; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_ICON_LOOKUP_THEME_FDO; + return wd->lookup_order; +} + +/** + * Set the smooth effect for a icon + * + * @param obj The icon object + * @param smooth A bool to set (or no) smooth effect + * (1 = smooth, 0 = not smooth) + * + * @ingroup Icon + */ +EAPI void +elm_icon_smooth_set(Evas_Object *obj, Eina_Bool smooth) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->smooth = smooth; + _sizing_eval(obj); +} + +/** + * Get the smooth effect for a icon + * + * @param obj The icon object + * @return If setted smooth effect + * + * @ingroup Icon + */ +EAPI Eina_Bool +elm_icon_smooth_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->smooth; +} + +/** + * Set if the object is scalable + * + * @param obj The icon object + * @param no_scale A bool to set scale (or no) + * (1 = no_scale, 0 = scale) + * + * @ingroup Icon + */ +EAPI void +elm_icon_no_scale_set(Evas_Object *obj, Eina_Bool no_scale) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->no_scale = no_scale; + _sizing_eval(obj); +} + +/** + * Get if the object isn't scalable + * + * @param obj The icon object + * @return If isn't scalable + * + * @ingroup Icon + */ +EAPI Eina_Bool +elm_icon_no_scale_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->no_scale; +} + +/** + * Set if the object is (up/down) scalable + * + * @param obj The icon object + * @param scale_up A bool to set if the object is scalable up + * @param scale_down A bool to set if the object is scalable down + * + * @ingroup Icon + */ +EAPI void +elm_icon_scale_set(Evas_Object *obj, Eina_Bool scale_up, Eina_Bool scale_down) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->scale_up = scale_up; + wd->scale_down = scale_down; + _sizing_eval(obj); +} + +/** + * Get if the object is (up/down) scalable + * + * @param obj The icon object + * @param scale_up A bool to set if the object is scalable up + * @param scale_down A bool to set if the object is scalable down + * + * @ingroup Icon + */ +EAPI void +elm_icon_scale_get(const Evas_Object *obj, Eina_Bool *scale_up, Eina_Bool *scale_down) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (scale_up) *scale_up = wd->scale_up; + if (scale_down) *scale_down = wd->scale_down; +} + +/** + * Set if the object is filled outside + * + * @param obj The icon object + * @param fill_outside A bool to set if the object is filled outside + * (1 = filled, 0 = no filled) + * + * @ingroup Icon + */ +EAPI void +elm_icon_fill_outside_set(Evas_Object *obj, Eina_Bool fill_outside) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->fill_outside = fill_outside; + _sizing_eval(obj); +} + +/** + * Get if the object is filled outside + * + * @param obj The icon object + * @return If the object is filled outside + * + * @ingroup Icon + */ +EAPI Eina_Bool +elm_icon_fill_outside_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->fill_outside; +} + +/** + * Set the prescale size for the icon + * + * @param obj The icon object + * @param size The prescale size + * + * @ingroup Icon + */ +EAPI void +elm_icon_prescale_set(Evas_Object *obj, int size) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + _els_smart_icon_scale_size_set(wd->img, size); +} + +/** + * Get the prescale size for the icon + * + * @param obj The icon object + * @return The prescale size + * + * @ingroup Icon + */ +EAPI int +elm_icon_prescale_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return 0; + return _els_smart_icon_scale_size_get(wd->img); +} diff --git a/src/lib/elm_image.c b/src/lib/elm_image.c new file mode 100644 index 0000000..a71fe11 --- /dev/null +++ b/src/lib/elm_image.c @@ -0,0 +1,487 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Image Image + * + * A standard image that may be provided by the theme (delete, edit, + * arrows etc.) or a custom file (PNG, JPG, EDJE etc.) used for an + * icon. The Icon may scale or not and of course... support alpha + * channels. + * + * Signals that you can add callbacks for are: + * + * - clicked: This is called when a user has clicked the image + * - drop: Something has been dropped on the image + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *img; + Eina_Bool scale_up : 1; + Eina_Bool scale_down : 1; + Eina_Bool smooth : 1; + Eina_Bool fill_outside : 1; + Eina_Bool no_scale : 1; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _mouse_up(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + free(wd); +} + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + evas_object_del(wd->img); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + int w, h; + + if (!wd) return; + _els_smart_icon_size_get(wd->img, &w, &h); + _els_smart_icon_scale_up_set(wd->img, wd->scale_up); + _els_smart_icon_scale_down_set(wd->img, wd->scale_down); + _els_smart_icon_smooth_scale_set(wd->img, wd->smooth); + _els_smart_icon_fill_inside_set(wd->img, !(wd->fill_outside)); + if (wd->no_scale) _els_smart_icon_scale_set(wd->img, 1.0); + else + { + _els_smart_icon_scale_set(wd->img, elm_widget_scale_get(obj) * _elm_config->scale); + _els_smart_icon_size_get(wd->img, &w, &h); + } + if (!wd->scale_down) + { + minw = w; + minh = h; + } + if (!wd->scale_up) + { + maxw = w; + maxh = h; + } + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_mouse_up(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "clicked", NULL); +} + +/** + * Add a new image to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Image + */ +EAPI Evas_Object * +elm_image_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "image"); + elm_widget_type_set(obj, "image"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->img = _els_smart_icon_add(e); + evas_object_event_callback_add(wd->img, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, obj); + evas_object_repeat_events_set(wd->img, EINA_TRUE); + elm_widget_resize_object_set(obj, wd->img); + + wd->smooth = EINA_TRUE; + wd->scale_up = EINA_TRUE; + wd->scale_down = EINA_TRUE; + + _els_smart_icon_scale_size_set(wd->img, 0); + + _sizing_eval(obj); + return obj; +} + +/** + * Set the file that will be used as image + * + * @param obj The image object + * @param file The path to file that will be used as image + * @param group The group that the image belongs in edje file + * + * @return (1 = success, 0 = error) + * + * @ingroup Image + */ +EAPI Eina_Bool +elm_image_file_set(Evas_Object *obj, const char *file, const char *group) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + Eina_Bool ret; + const char *p; + + if (!wd) return EINA_FALSE; + EINA_SAFETY_ON_NULL_RETURN_VAL(file, EINA_FALSE); + if (((p = strrchr(file, '.'))) && (!strcasecmp(p, ".edj"))) + ret = _els_smart_icon_file_edje_set(wd->img, file, group); + else + ret = _els_smart_icon_file_key_set(wd->img, file, group); + _sizing_eval(obj); + return ret; +} + +/** + * Get the file that will be used as image + * + * @param obj The image object + * @param file The path to file + * @param group The group that the image belongs in edje file + * + * @ingroup Image + */ +EAPI void +elm_image_file_get(const Evas_Object *obj, const char **file, const char **group) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _els_smart_icon_file_get(wd->img, file, group); +} + +/** + * Set the smooth effect for a image + * + * @param obj The image object + * @param smooth A bool to set (or no) smooth effect + * (1 = smooth, 0 = not smooth) + * + * @ingroup Image + */ +EAPI void +elm_image_smooth_set(Evas_Object *obj, Eina_Bool smooth) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->smooth = smooth; + _sizing_eval(obj); +} + +/** + * Get the smooth effect for a image + * + * @param obj The image object + * @return If setted smooth effect + * + * @ingroup Image + */ +EAPI Eina_Bool +elm_image_smooth_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->smooth; +} + +/** + * Gets the current size of the image. + * + * Either width or height (or both) may be NULL. + * + * On error, neither w or h will be written too. + * + * @param obj The image object. + * @param w Pointer to store width, or NULL. + * @param h Pointer to store height, or NULL. + */ +EAPI void +elm_image_object_size_get(const Evas_Object *obj, int *w, int *h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + _els_smart_icon_size_get(wd->img, w, h); +} + +/** + * Set if the object are scalable + * + * @param obj The image object. + * @param no_scale A bool to set scale (or no). + * (1 = no_scale, 0 = scale) + * + * @ingroup Image + */ +EAPI void +elm_image_no_scale_set(Evas_Object *obj, Eina_Bool no_scale) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->no_scale = no_scale; + _sizing_eval(obj); + +} + +/** + * Get if the object isn't scalable + * + * @param obj The image object + * @return If isn't scalable + * + * @ingroup Image + */ +EAPI Eina_Bool +elm_image_no_scale_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->no_scale; +} + +/** + * Set if the object is (up/down) scalable + * + * @param obj The image object + * @param scale_up A bool to set if the object is scalable up + * @param scale_down A bool to set if the object is scalable down + * + * @ingroup Image + */ +EAPI void +elm_image_scale_set(Evas_Object *obj, Eina_Bool scale_up, Eina_Bool scale_down) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->scale_up = scale_up; + wd->scale_down = scale_down; + _sizing_eval(obj); +} + +/** + * Get if the object is (up/down) scalable + * + * @param obj The image object + * @param scale_up A bool to set if the object is scalable up + * @param scale_down A bool to set if the object is scalable down + * + * @ingroup Image + */ +EAPI void +elm_image_scale_get(const Evas_Object *obj, Eina_Bool *scale_up, Eina_Bool *scale_down) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (scale_up) *scale_up = wd->scale_up; + if (scale_down) *scale_down = wd->scale_down; +} + +/** + * Set if the object is filled outside + * + * @param obj The image object + * @param fill_outside A bool to set if the object is filled outside + * (1 = filled, 0 = no filled) + * + * @ingroup Image + */ +EAPI void +elm_image_fill_outside_set(Evas_Object *obj, Eina_Bool fill_outside) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->fill_outside = fill_outside; + _sizing_eval(obj); +} + +/** + * Get if the object is filled outside + * + * @param obj The image object + * @return If the object is filled outside + * + * @ingroup Image + */ +EAPI Eina_Bool +elm_image_fill_outside_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->fill_outside; +} + +/** + * Set the prescale size for the image + * + * @param obj The image object + * @param size The prescale size + * + * @ingroup Image + */ +EAPI void +elm_image_prescale_set(Evas_Object *obj, int size) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + _els_smart_icon_scale_size_set(wd->img, size); +} + +/** + * Get the prescale size for the image + * + * @param obj The image object + * @return The prescale size + * + * @ingroup Image + */ +EAPI int +elm_image_prescale_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return 0; + return _els_smart_icon_scale_size_get(wd->img); +} + +/** + * Set the image orient + * + * @param obj The image object + * @param orient The image orient + * (ELM_IMAGE_ORIENT_NONE, ELM_IMAGE_ROTATE_90_CW, + * ELM_IMAGE_ROTATE_180_CW, ELM_IMAGE_ROTATE_90_CCW, + * ELM_IMAGE_FLIP_HORIZONTAL,ELM_IMAGE_FLIP_VERTICAL, + * ELM_IMAGE_FLIP_TRANSPOSE, ELM_IMAGE_FLIP_TRANSVERSE) + * + * @ingroup Image + */ +EAPI void +elm_image_orient_set(Evas_Object *obj, Elm_Image_Orient orient) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + _els_smart_icon_orient_set(wd->img, orient); +} + +/** + * Get the image orient + * + * @param obj The image object + * @return The image orient + * (ELM_IMAGE_ORIENT_NONE, ELM_IMAGE_ROTATE_90_CW, + * ELM_IMAGE_ROTATE_180_CW, ELM_IMAGE_ROTATE_90_CCW, + * ELM_IMAGE_FLIP_HORIZONTAL,ELM_IMAGE_FLIP_VERTICAL, + * ELM_IMAGE_FLIP_TRANSPOSE, ELM_IMAGE_FLIP_TRANSVERSE) + * + * @ingroup Image + */ +EAPI Elm_Image_Orient +elm_image_orient_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_IMAGE_ORIENT_NONE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_IMAGE_ORIENT_NONE; + return _els_smart_icon_orient_get(wd->img); +} + +/** + * Make the image 'editable'. + * + * This means the image is a valid drag target for drag and drop, and can be + * cut or pasted too. + * + * @param obj Image object. + * @param set Turn on or off editability. + */ +EAPI void +elm_image_editable_set(Evas_Object *obj, Eina_Bool set) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + _els_smart_icon_edit_set(wd->img, set, obj); +} + +/** + * Make the image 'editable'. + * + * This means the image is a valid drag target for drag and drop, and can be + * cut or pasted too. + * + * @param obj Image object. + * @return Editability. + */ +EAPI Eina_Bool +elm_image_editable_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return _els_smart_icon_edit_get(wd->img); +} + + +/* vim:set ts=8 sw=3 sts=3 expandtab cino=>5n-2f0^-2{2(0W1st0 :*/ diff --git a/src/lib/elm_index.c b/src/lib/elm_index.c new file mode 100644 index 0000000..c63a2a4 --- /dev/null +++ b/src/lib/elm_index.c @@ -0,0 +1,959 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Index Index + * + * An index object is a type of list that categorizes items in it + * by letter. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *base; + Evas_Object *event[2]; + Evas_Object *bx[2]; // 2 - for now all that's supported + Eina_List *items; // 1 list. yes N levels, but only 2 for now and # of items will be small + int level; + Evas_Coord dx, dy; + Ecore_Timer *delay; + Eina_Bool level_active[2]; + Eina_Bool horizontal : 1; + Eina_Bool active : 1; + Eina_Bool down : 1; +}; + +struct _Elm_Index_Item +{ + Elm_Widget_Item base; + const char *letter; + int level; + Eina_Bool selected : 1; +}; + +static const char *widtype = NULL; +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _index_box_auto_fill(Evas_Object *obj, Evas_Object *box, int level); +static void _index_box_clear(Evas_Object *obj, Evas_Object *box, int level); +static void _item_free(Elm_Index_Item *it); + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _index_box_clear(obj, wd->bx[wd->level], wd->level); + _index_box_clear(obj, wd->bx[0], 0); + while (wd->items) _item_free(wd->items->data); + if (wd->delay) ecore_timer_del(wd->delay); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + free(wd); +} + +static void +_layout(Evas_Object *o, Evas_Object_Box_Data *priv, void *data) +{ + Widget_Data *wd = data; + if (!wd) return; + _els_box_layout(o, priv, wd->horizontal, 1); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_emit(wd->base, emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_callback_add(wd->base, emission, source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_del_full(wd->base, emission, source, func_cb, + data); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Evas_Coord minw = 0, minh = 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _index_box_clear(obj, wd->bx[0], 0); + _index_box_clear(obj, wd->bx[1], 1); + if (wd->horizontal) + _elm_theme_object_set(obj, wd->base, "index", "base/horizontal", elm_widget_style_get(obj)); + else + _elm_theme_object_set(obj, wd->base, "index", "base/vertical", elm_widget_style_get(obj)); + edje_object_part_swallow(wd->base, "elm.swallow.event.0", wd->event[0]); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(wd->event[0], minw, minh); + edje_object_part_swallow(wd->base, "elm.swallow.index.0", wd->bx[0]); + if (edje_object_part_exists(wd->base, "elm.swallow.index.1")) + { + if (!wd->bx[1]) + { + wd->bx[1] = evas_object_box_add(evas_object_evas_get(wd->base)); + evas_object_box_layout_set(wd->bx[1], _layout, wd, NULL); + elm_widget_sub_object_add(obj, wd->bx[1]); + } + edje_object_part_swallow(wd->base, "elm.swallow.index.1", wd->bx[1]); + evas_object_show(wd->bx[1]); + } + else if (wd->bx[1]) + { + evas_object_del(wd->bx[1]); + wd->bx[1] = NULL; + } + if (edje_object_part_exists(wd->base, "elm.swallow.event.1")) + { + if (!wd->event[1]) + { + wd->event[1] = evas_object_rectangle_add(evas_object_evas_get(wd->base)); + evas_object_color_set(wd->event[1], 0, 0, 0, 0); + elm_widget_sub_object_add(obj, wd->event[1]); + } + edje_object_part_swallow(wd->base, "elm.swallow.event.1", wd->event[1]); + evas_object_size_hint_min_set(wd->event[1], minw, minh); + } + else if (wd->event[1]) + { + evas_object_del(wd->event[1]); + wd->event[1] = NULL; + } + edje_object_message_signal_process(wd->base); + edje_object_scale_set(wd->base, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); + _index_box_auto_fill(obj, wd->bx[0], 0); + if (wd->active) + if (wd->level == 1) + _index_box_auto_fill(obj, wd->bx[1], 1); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + edje_object_size_min_calc(wd->base, &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static Elm_Index_Item * +_item_new(Evas_Object *obj, const char *letter, const void *item) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Index_Item *it; + if (!wd) return NULL; + it = elm_widget_item_new(obj, Elm_Index_Item); + if (!it) return NULL; + it->letter = eina_stringshare_add(letter); + it->base.data = item; + it->level = wd->level; + return it; +} + +static Elm_Index_Item * +_item_find(Evas_Object *obj, const void *item) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Elm_Index_Item *it; + if (!wd) return NULL; + EINA_LIST_FOREACH(wd->items, l, it) + if (it->base.data == item) return it; + return NULL; +} + +static void +_item_free(Elm_Index_Item *it) +{ + Widget_Data *wd = elm_widget_data_get(it->base.widget); + if (!wd) return; + wd->items = eina_list_remove(wd->items, it); + elm_widget_item_pre_notify_del(it); + eina_stringshare_del(it->letter); + elm_widget_item_del(it); +} + +// FIXME: always have index filled +static void +_index_box_auto_fill(Evas_Object *obj, Evas_Object *box, int level) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Elm_Index_Item *it; + Evas_Coord mw, mh, w, h; + int i = 0; + if (!wd) return; + if (wd->level_active[level]) return; + evas_object_geometry_get(box, NULL, NULL, &w, &h); + EINA_LIST_FOREACH(wd->items, l, it) + { + Evas_Object *o; + const char *stacking; + + if (it->level != level) continue; + o = edje_object_add(evas_object_evas_get(obj)); + it->base.view = o; + if (i & 0x1) + _elm_theme_object_set(obj, o, "index", "item_odd/vertical", elm_widget_style_get(obj)); + else + _elm_theme_object_set(obj, o, "index", "item/vertical", elm_widget_style_get(obj)); + edje_object_part_text_set(o, "elm.text", it->letter); + edje_object_size_min_restricted_calc(o, &mw, &mh, 0, 0); + evas_object_size_hint_min_set(o, mw, mh); + evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(o, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_widget_sub_object_add(obj, o); + evas_object_box_append(box, o); + stacking = edje_object_data_get(o, "stacking"); + if (stacking) + { + if (!strcmp(stacking, "below")) evas_object_lower(o); + else if (!strcmp(stacking, "above")) evas_object_raise(o); + } + evas_object_show(o); + i++; + evas_object_smart_calculate(box); // force a calc so we know the size + evas_object_size_hint_min_get(box, &mw, &mh); + if (mh > h) + { + _index_box_clear(obj, box, level); + if (i > 0) + { + // FIXME: only i objects fit! try again. overflows right now + } + } + } + evas_object_smart_calculate(box); + wd->level_active[level] = 1; +} + +static void +_index_box_clear(Evas_Object *obj, Evas_Object *box __UNUSED__, int level) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Elm_Index_Item *it; + if (!wd) return; + if (!wd->level_active[level]) return; + EINA_LIST_FOREACH(wd->items, l, it) + { + if (!it->base.view) continue; + if (it->level != level) continue; + evas_object_del(it->base.view); + it->base.view = NULL; + } + wd->level_active[level] = 0; +} + +static Eina_Bool +_delay_change(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + void *d; + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->delay = NULL; + d = (void *)elm_index_item_selected_get(data, wd->level); + if (d) evas_object_smart_callback_call(data, "delay,changed", d); + return ECORE_CALLBACK_CANCEL; +} + +static void +_sel_eval(Evas_Object *obj, Evas_Coord evx, Evas_Coord evy) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Index_Item *it, *it_closest, *it_last; + Eina_List *l; + Evas_Coord x, y, w, h, bx, by, bw, bh, xx, yy; + double cdv = 0.5; + Evas_Coord dist; + char *label = NULL, *last = NULL; + int i; + if (!wd) return; + for (i = 0; i <= wd->level; i++) + { + it_last = NULL; + it_closest = NULL; + dist = 0x7fffffff; + evas_object_geometry_get(wd->bx[i], &bx, &by, &bw, &bh); + EINA_LIST_FOREACH(wd->items, l, it) + { + if (!((it->level == i) && (it->base.view))) continue; + if ((it->base.view) && (it->level != wd->level)) + { + if (it->selected) + { + it_closest = it; + break; + } + continue; + } + if (it->selected) + { + it_last = it; + it->selected = 0; + } + evas_object_geometry_get(it->base.view, &x, &y, &w, &h); + xx = x + (w / 2); + yy = y + (h / 2); + x = evx - xx; + y = evy - yy; + x = (x * x) + (y * y); + if ((x < dist) || (!it_closest)) + { + if (wd->horizontal) + cdv = (double)(xx - bx) / (double)bw; + else + cdv = (double)(yy - by) / (double)bh; + it_closest = it; + dist = x; + } + } + if ((!i) && (!wd->level)) + edje_object_part_drag_value_set(wd->base, "elm.dragable.index.1", + cdv, cdv); + if (it_closest) it_closest->selected = 1; + if (it_closest != it_last) + { + if (it_last) + { + const char *stacking, *selectraise; + + it = it_last; + edje_object_signal_emit(it->base.view, "elm,state,inactive", "elm"); + stacking = edje_object_data_get(it->base.view, "stacking"); + selectraise = edje_object_data_get(it->base.view, "selectraise"); + if ((selectraise) && (!strcmp(selectraise, "on"))) + { + if ((stacking) && (!strcmp(stacking, "below"))) + evas_object_lower(it->base.view); + } + } + if (it_closest) + { + const char *selectraise; + + it = it_closest; + edje_object_signal_emit(it->base.view, "elm,state,active", "elm"); + selectraise = edje_object_data_get(it->base.view, "selectraise"); + if ((selectraise) && (!strcmp(selectraise, "on"))) + evas_object_raise(it->base.view); + evas_object_smart_callback_call((void *)obj, "changed", (void *)it->base.data); + if (wd->delay) ecore_timer_del(wd->delay); + wd->delay = ecore_timer_add(0.2, _delay_change, obj); + } + } + if (it_closest) + { + it = it_closest; + if (!last) + last = strdup(it->letter); + else + { + if (!label) label = strdup(last); + else + { + /* FIXME: realloc return NULL if the request fails */ + label = realloc(label, strlen(label) + strlen(last) + 1); + strcat(label, last); + } + free(last); + last = strdup(it->letter); + } + } + } + if (!label) label = strdup(""); + if (!last) last = strdup(""); + edje_object_part_text_set(wd->base, "elm.text.body", label); + edje_object_part_text_set(wd->base, "elm.text", last); + free(label); + free(last); +} + +static void +_wheel(void *data, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); +// Evas_Event_Mouse_Wheel *ev = event_info; +// Evas_Object *obj = o; + if (!wd) return; +} + +static void +_mouse_down(void *data, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Down *ev = event_info; + Evas_Coord x, y; + if (!wd) return; + if (ev->button != 1) return; + wd->down = 1; + evas_object_geometry_get(wd->base, &x, &y, NULL, NULL); + wd->dx = ev->canvas.x - x; + wd->dy = ev->canvas.y - y; + elm_index_active_set(data, 1); + _sel_eval(data, ev->canvas.x, ev->canvas.y); + edje_object_part_drag_value_set(wd->base, "elm.dragable.pointer", + wd->dx, wd->dy); +} + +static void +_mouse_up(void *data, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Up *ev = event_info; + void *d; + if (!wd) return; + if (ev->button != 1) return; + wd->down = 0; + d = (void *)elm_index_item_selected_get(data, wd->level); + if (d) evas_object_smart_callback_call(data, "selected", d); + elm_index_active_set(data, 0); + edje_object_signal_emit(wd->base, "elm,state,level,0", "elm"); +} + +static void +_mouse_move(void *data, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Move *ev = event_info; + Evas_Coord minw = 0, minh = 0, x, y, dx, adx; + char buf[1024]; + if (!wd) return; + if (!wd->down) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_geometry_get(wd->base, &x, &y, NULL, NULL); + x = ev->cur.canvas.x - x; + y = ev->cur.canvas.y - y; + dx = x - wd->dx; + adx = dx; + if (adx < 0) adx = -dx; + edje_object_part_drag_value_set(wd->base, "elm.dragable.pointer", x, y); + if (!wd->horizontal) + { + if (adx > minw) + { + if (!wd->level) + { + wd->level = 1; + snprintf(buf, sizeof(buf), "elm,state,level,%i", wd->level); + edje_object_signal_emit(wd->base, buf, "elm"); + evas_object_smart_callback_call(data, "level,up", NULL); + } + } + else + { + if (wd->level == 1) + { + wd->level = 0; + snprintf(buf, sizeof(buf), "elm,state,level,%i", wd->level); + edje_object_signal_emit(wd->base, buf, "elm"); + evas_object_smart_callback_call(data, "level,down", NULL); + } + } + } + _sel_eval(data, ev->cur.canvas.x, ev->cur.canvas.y); +} + +/** + * Add a new index to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Index + */ +EAPI Evas_Object * +elm_index_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas_Object *o; + Evas *e; + Widget_Data *wd; + Evas_Coord minw, minh; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "index"); + elm_widget_type_set(obj, "index"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->horizontal = EINA_FALSE; + + wd->base = edje_object_add(e); + _elm_theme_object_set(obj, wd->base, "index", "base/vertical", "default"); + elm_widget_resize_object_set(obj, wd->base); + + o = evas_object_rectangle_add(e); + wd->event[0] = o; + evas_object_color_set(o, 0, 0, 0, 0); + minw = minh = 0; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(o, minw, minh); + edje_object_part_swallow(wd->base, "elm.swallow.event.0", o); + elm_widget_sub_object_add(obj, o); + evas_object_event_callback_add(o, EVAS_CALLBACK_MOUSE_WHEEL, _wheel, obj); + evas_object_event_callback_add(o, EVAS_CALLBACK_MOUSE_DOWN, _mouse_down, obj); + evas_object_event_callback_add(o, EVAS_CALLBACK_MOUSE_UP, _mouse_up, obj); + evas_object_event_callback_add(o, EVAS_CALLBACK_MOUSE_MOVE, _mouse_move, obj); + evas_object_show(o); + if (edje_object_part_exists(wd->base, "elm.swallow.event.1")) + { + o = evas_object_rectangle_add(e); + wd->event[1] = o; + evas_object_color_set(o, 0, 0, 0, 0); + evas_object_size_hint_min_set(o, minw, minh); + edje_object_part_swallow(wd->base, "elm.swallow.event.1", o); + elm_widget_sub_object_add(obj, o); + } + + wd->bx[0] = evas_object_box_add(e); + evas_object_box_layout_set(wd->bx[0], _layout, wd, NULL); + elm_widget_sub_object_add(obj, wd->bx[0]); + edje_object_part_swallow(wd->base, "elm.swallow.index.0", wd->bx[0]); + evas_object_show(wd->bx[0]); + + if (edje_object_part_exists(wd->base, "elm.swallow.index.1")) + { + wd->bx[1] = evas_object_box_add(e); + evas_object_box_layout_set(wd->bx[1], _layout, wd, NULL); + elm_widget_sub_object_add(obj, wd->bx[1]); + edje_object_part_swallow(wd->base, "elm.swallow.index.1", wd->bx[1]); + evas_object_show(wd->bx[1]); + } + + _sizing_eval(obj); + return obj; +} + +/** + * Set the active state of the index programatically + * + * @param obj The index object + * @param active The active starte + * + * @ingroup Index + */ +EAPI void +elm_index_active_set(Evas_Object *obj, Eina_Bool active) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->active == active) return; + wd->active = active; + wd->level = 0; + if (wd->active) + { + _index_box_clear(obj, wd->bx[1], 1); + _index_box_auto_fill(obj, wd->bx[0], 0); + edje_object_signal_emit(wd->base, "elm,state,active", "elm"); + } + else + edje_object_signal_emit(wd->base, "elm,state,inactive", "elm"); +} + +/** + * Sets the level of the item. + * + * @param obj The index object. + * @param level To be documented. + * + * @ingroup Index + */ +EAPI void +elm_index_item_level_set(Evas_Object *obj, int level) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->level == level) return; + wd->level = level; +} + +/** + * Gets the level of the item. + * + * @param obj The index object + * + * @ingroup Index + */ +EAPI int +elm_index_item_level_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->level; +} + +/** + * Returns the selected item. + * + * @param obj The index object. + * @param level to be documented. + * + * @ingroup Index + */ +EAPI void * +elm_index_item_selected_get(const Evas_Object *obj, int level) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Elm_Index_Item *it; + if (!wd) return NULL; + EINA_LIST_FOREACH(wd->items, l, it) + if ((it->selected) && (it->level == level)) + return elm_widget_item_data_get(it); + return NULL; +} + +/** + * Appends a new item. + * + * @param obj The index object. + * @param letter Letter under which the item should be indexed + * @param item The item to put in the index + * + * @ingroup Index + */ +EAPI void +elm_index_item_append(Evas_Object *obj, const char *letter, const void *item) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Index_Item *it; + if (!wd) return; + it = _item_new(obj, letter, item); + if (!it) return; + wd->items = eina_list_append(wd->items, it); + _index_box_clear(obj, wd->bx[wd->level], wd->level); +} + +/** + * Prepends a new item. + * + * @param obj The index object. + * @param letter Letter under which the item should be indexed + * @param item The item to put in the index + * + * @ingroup Index + */ +EAPI void +elm_index_item_prepend(Evas_Object *obj, const char *letter, const void *item) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Index_Item *it; + + if (!wd) return; + it = _item_new(obj, letter, item); + if (!it) return; + wd->items = eina_list_prepend(wd->items, it); + _index_box_clear(obj, wd->bx[wd->level], wd->level); +} + +/** + * Append an item after @p relative in letter @p letter. + * + * @param obj The index object + * @param letter Letter under which the item should be indexed + * @param item The item to put in the index + * @param relative The item to put @p item after + * + * @ingroup Index + */ +EAPI void +elm_index_item_append_relative(Evas_Object *obj, const char *letter, const void *item, const void *relative) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Index_Item *it, *it_rel; + if (!wd) return; + if (!relative) + { + elm_index_item_append(obj, letter, item); + return; + } + it = _item_new(obj, letter, item); + it_rel = _item_find(obj, relative); + if (!it_rel) + { + elm_index_item_append(obj, letter, item); + return; + } + if (!it) return; + wd->items = eina_list_append_relative(wd->items, it, it_rel); + _index_box_clear(obj, wd->bx[wd->level], wd->level); +} + +/** + * Prepend an item before @p relative in letter @p letter. + * + * @param obj The index object + * @param letter Letter under which the item should be indexed + * @param item The item to put in the index + * @param relative The item to put @p item before + * + * @ingroup Index + */ +EAPI void +elm_index_item_prepend_relative(Evas_Object *obj, const char *letter, const void *item, const void *relative) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Index_Item *it, *it_rel; + if (!wd) return; + if (!relative) + { + elm_index_item_prepend(obj, letter, item); + return; + } + it = _item_new(obj, letter, item); + it_rel = _item_find(obj, relative); + if (!it_rel) + { + elm_index_item_append(obj, letter, item); + return; + } + if (!it) return; + wd->items = eina_list_prepend_relative(wd->items, it, it_rel); + _index_box_clear(obj, wd->bx[wd->level], wd->level); +} + +/** + * Insert a new @p item into the sorted index @p obj in @p letter. + * + * @param obj The index object + * @param letter Letter under which the item should be indexed + * @param item The item to put in the index + * @param cmp_func The function called for the sort of index items. + * @param cmp_data_func The function called for the sort of the data. It will + * be used when cmp_func return 0. It means the index item already exists. + * So, to decide which data item should be pointed by the index item, a function + * to compare them is needed. If this function is not provided, index items + * will be duplicated. If cmp_data_func returns a non-negative value, the + * previous index item data will be replaced by the inserted @p item. So + * if the previous data need to be free, it should be done in this function, + * because the reference will be lost. + * + * @ingroup Index + */ +EAPI void +elm_index_item_sorted_insert(Evas_Object *obj, const char *letter, const void *item, Eina_Compare_Cb cmp_func, Eina_Compare_Cb cmp_data_func) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *lnear; + Elm_Index_Item *it; + int cmp; + + if (!wd) return; + if (!(wd->items)) + { + elm_index_item_append(obj, letter, item); + return; + } + + it = _item_new(obj, letter, item); + if (!it) return; + + lnear = eina_list_search_sorted_near_list(wd->items, cmp_func, it, &cmp); + if (cmp < 0) + wd->items = eina_list_append_relative_list(wd->items, it, lnear); + else if (cmp > 0) + wd->items = eina_list_prepend_relative_list(wd->items, it, lnear); + else + { + /* If cmp_data_func is not provided, append a duplicated item */ + if (!cmp_data_func) + wd->items = eina_list_append_relative_list(wd->items, it, lnear); + else + { + Elm_Index_Item *p_it = eina_list_data_get(lnear); + if (cmp_data_func(p_it->base.data, it->base.data) >= 0) + p_it->base.data = it->base.data; + _item_free(it); + } + } + + _index_box_clear(obj, wd->bx[wd->level], wd->level); +} + +/** + * Remove an item from the index. + * + * @param obj The index object + * @param item The item to remove from the index + * + * @ingroup Index + */ +EAPI void +elm_index_item_del(Evas_Object *obj, const void *item) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Index_Item *it; + if (!wd) return; + it = _item_find(obj, item); + if (!it) return; + _item_free(it); + _index_box_clear(obj, wd->bx[wd->level], wd->level); +} + +/** + * Find an index item using item data. + * + * @param obj The index object + * @param item The item pointed by index item + * @return The index item pointing to @p item + * + * @ingroup Index + */ +EAPI Elm_Index_Item * +elm_index_item_find(Evas_Object *obj, const void *item) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return _item_find(obj, item); +} + +/** + * Clears an index of its items. + * + * @param obj The index object. + * + * @ingroup Index + */ +EAPI void +elm_index_item_clear(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Index_Item *it; + Eina_List *l, *clear = NULL; + if (!wd) return; + _index_box_clear(obj, wd->bx[wd->level], wd->level); + EINA_LIST_FOREACH(wd->items, l, it) + { + if (it->level != wd->level) continue; + clear = eina_list_append(clear, it); + } + EINA_LIST_FREE(clear, it) _item_free(it); +} + +/** + * Go to item at @p level + * + * @param obj The index object + * @param level The index level + * + * @ingroup Index + */ +EAPI void +elm_index_item_go(Evas_Object *obj, int level __UNUSED__) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _index_box_auto_fill(obj, wd->bx[0], 0); + if (wd->level == 1) _index_box_auto_fill(obj, wd->bx[1], 1); +} + +/** + * Returns the data associated with the item. + * + * @param it The list item + * @return The data associated with @p it + * + * @ingroup Index + */ +EAPI void * +elm_index_item_data_get(const Elm_Index_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, NULL); + return elm_widget_item_data_get(it); +} + +/** + * Set the data item from the index item + * + * This set a new data value. + * + * @param it The item + * @param data The new data pointer to set + * + * @ingroup Index + */ +EAPI void +elm_index_item_data_set(Elm_Index_Item *it, const void *data) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + elm_widget_item_data_set(it, data); +} + +/** + * Set the function called when a index item is freed. + * + * @param it The item to set the callback on + * @param func The function called + * + * @ingroup Index + */ +EAPI void +elm_index_item_del_cb_set(Elm_Index_Item *it, Evas_Smart_Cb func) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + elm_widget_item_del_cb_set(it, func); +} + +/** + * Gets the letter of the item. + * + * @param it The list item + * @return The letter of @p it + * + * @ingroup Index + */ +EAPI const char * +elm_index_item_letter_get(const Elm_Index_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, NULL); + return it->letter; +} + diff --git a/src/lib/elm_label.c b/src/lib/elm_label.c new file mode 100644 index 0000000..5240cec --- /dev/null +++ b/src/lib/elm_label.c @@ -0,0 +1,1064 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Label Label + * + * Display text, with simple html-like markup. The theme of course + * can invent new markup tags and style them any way it likes + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *lbl; + Evas_Object *bg; + const char *label; + Ecore_Job *deferred_recalc_job; + double slide_duration; + Evas_Coord lastw; + Evas_Coord wrap_w; + Evas_Coord wrap_h; + Eina_Bool linewrap : 1; + Eina_Bool changed : 1; + Eina_Bool bgcolor : 1; + Eina_Bool ellipsis : 1; + Eina_Bool slidingmode : 1; + Eina_Bool slidingellipsis : 1; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static int _get_value_in_key_string(const char *oldstring, const char *key, char **value); +static int _strbuf_key_value_replace(Eina_Strbuf *srcbuf, const char *key, const char *value, int deleteflag); +static int _stringshare_key_value_replace(const char **srcstring, const char *key, const char *value, int deleteflag); +static int _is_width_over(Evas_Object *obj, Eina_Bool multiline); +static void _ellipsis_label_to_width(Evas_Object *obj, Eina_Bool multiline); +static void _label_sliding_change(Evas_Object *obj); + +static void +_elm_win_recalc_job(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord minw = -1, minh = -1, maxh = -1; + Evas_Coord resw, resh, minminw; + if (!wd) return; + wd->deferred_recalc_job = NULL; + evas_object_geometry_get(wd->lbl, NULL, NULL, &resw, &resh); + resh = 0; + edje_object_size_min_restricted_calc(wd->lbl, &minw, &minh, 0, 0); + minminw = minw; + if (wd->wrap_w >= resw) + { + resw = wd->wrap_w; + edje_object_size_min_restricted_calc(wd->lbl, &minw, &minh, resw, 0); + evas_object_size_hint_min_set(data, minw, minh); + } + else + { + if (wd->wrap_w > minminw) minminw = wd->wrap_w; + edje_object_size_min_restricted_calc(wd->lbl, &minw, &minh, resw, 0); + evas_object_size_hint_min_set(data, minminw, minh); + } + + if ((wd->ellipsis) && (wd->linewrap) && (wd->wrap_h > 0) && + (_is_width_over(data, 1) == 1)) + _ellipsis_label_to_width(data, 1); + + maxh = minh; + evas_object_size_hint_max_set(data, -1, maxh); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->deferred_recalc_job) ecore_job_del(wd->deferred_recalc_job); + if (wd->label) eina_stringshare_del(wd->label); + if (wd->bg) evas_object_del(wd->bg); + free(wd); +} + +static void +_theme_change(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (wd->linewrap) + { + if (wd->ellipsis) + _elm_theme_object_set(obj, wd->lbl, "label", "base_wrap_ellipsis", + elm_widget_style_get(obj)); + else + _elm_theme_object_set(obj, wd->lbl, "label", "base_wrap", + elm_widget_style_get(obj)); + } + else + _elm_theme_object_set(obj, wd->lbl, "label", "base", + elm_widget_style_get(obj)); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _theme_change(obj); + edje_object_part_text_set(wd->lbl, "elm.text", wd->label); + edje_object_scale_set(wd->lbl, elm_widget_scale_get(obj) * + _elm_config->scale); + _label_sliding_change(obj); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + Evas_Coord resw, resh; + if (!wd) return; + if (wd->linewrap) + { + evas_object_geometry_get(wd->lbl, NULL, NULL, &resw, &resh); + if ((resw == wd->lastw) && (!wd->changed)) return; + wd->changed = EINA_FALSE; + wd->lastw = resw; + _elm_win_recalc_job(obj); +// FIXME: works ok. but NOT for genlist. what should genlist do? +// if (wd->deferred_recalc_job) ecore_job_del(wd->deferred_recalc_job); +// wd->deferred_recalc_job = ecore_job_add(_elm_win_recalc_job, obj); + } + else + { + evas_object_geometry_get(wd->lbl, NULL, NULL, &resw, &resh); + edje_object_size_min_calc(wd->lbl, &minw, &minh); + if (wd->wrap_w > 0 && minw > wd->wrap_w) minw = wd->wrap_w; + evas_object_size_hint_min_set(obj, minw, minh); + maxh = minh; + evas_object_size_hint_max_set(obj, maxw, maxh); + if ((wd->ellipsis) && (_is_width_over(obj, 0) == 1)) + _ellipsis_label_to_width(obj, 0); + } +} + +static void +_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (wd->linewrap) _sizing_eval(data); +} + +static int +_get_value_in_key_string(const char *oldstring, const char *key, char **value) +{ + char *curlocater, *starttag, *endtag; + int firstindex = 0, foundflag = -1; + + curlocater = strstr(oldstring, key); + if (curlocater) + { + int key_len = strlen(key); + starttag = curlocater; + endtag = curlocater + key_len; + if ((!endtag) || (*endtag != '=')) + { + foundflag = 0; + return -1; + } + firstindex = abs(oldstring - curlocater); + firstindex += key_len + 1; // strlen("key") + strlen("=") + *value = (char *)oldstring + firstindex; + + while (oldstring != starttag) + { + if (*starttag == '>') + { + foundflag = 0; + break; + } + if (*starttag == '<') + break; + else + starttag--; + if (!starttag) break; + } + + while (endtag) + { + if (*endtag == '<') + { + foundflag = 0; + break; + } + if (*endtag == '>') + break; + else + endtag++; + if (!endtag) break; + } + + if ((foundflag) && (*starttag == '<') && (*endtag == '>')) + foundflag = 1; + else + foundflag = 0; + } + else + { + foundflag = 0; + } + + if (foundflag == 1) return 0; + + return -1; +} + + +static int +_strbuf_key_value_replace(Eina_Strbuf *srcbuf, const char *key, const char *value, int deleteflag) +{ + const char *srcstring = NULL; + Eina_Strbuf *repbuf = NULL, *diffbuf = NULL; + char *curlocater, *replocater; + char *starttag, *endtag; + int tagtxtlen = 0, insertflag = 0; + + srcstring = eina_strbuf_string_get(srcbuf); + curlocater = strstr(srcstring, key); + + if (!curlocater) + insertflag = 1; + else + { + int key_len = strlen(key); + do + { + starttag = strchr(srcstring, '<'); + endtag = strchr(srcstring, '>'); + tagtxtlen = endtag - starttag; + if (tagtxtlen <= 0) tagtxtlen = 0; + if ((starttag < curlocater) && (curlocater < endtag)) break; + if ((endtag) && ((endtag + 1))) + srcstring = endtag + 1; + else + break; + } while (strlen(srcstring) > 1); + + if ((starttag) && (endtag) && (tagtxtlen > key_len)) + { + repbuf = eina_strbuf_new(); + diffbuf = eina_strbuf_new(); + eina_strbuf_append_n(repbuf, starttag, tagtxtlen); + srcstring = eina_strbuf_string_get(repbuf); + curlocater = strstr(srcstring, key); + if (curlocater) + { + replocater = curlocater + key_len + 1; + while ((*replocater != '=') && (replocater)) + replocater++; + + while ((*replocater) && + (*replocater != ' ') && + (*replocater != '>')) + replocater++; + + if ((replocater - curlocater) > (key_len + 1)) + { + replocater--; + eina_strbuf_append_n(diffbuf, curlocater, + replocater-curlocater); + } + else + insertflag = 1; + } + else + insertflag = 1; + eina_strbuf_reset(repbuf); + } + else + insertflag = 1; + } + + if (!repbuf) repbuf = eina_strbuf_new(); + if (!diffbuf) diffbuf = eina_strbuf_new(); + + if (insertflag) + { + eina_strbuf_append_printf(repbuf, "<%s=%s>", key, value); + eina_strbuf_prepend(srcbuf, eina_strbuf_string_get(repbuf)); + } + else + { + if (deleteflag) + { + eina_strbuf_prepend(diffbuf, "<"); + eina_strbuf_append(diffbuf, ">"); + eina_strbuf_replace_first(srcbuf, eina_strbuf_string_get(diffbuf), ""); + } + else + { + eina_strbuf_append_printf(repbuf, "%s=%s", key, value); + eina_strbuf_replace_first(srcbuf, eina_strbuf_string_get(diffbuf), eina_strbuf_string_get(repbuf)); + } + } + + if (repbuf) eina_strbuf_free(repbuf); + if (diffbuf) eina_strbuf_free(diffbuf); + + return 0; +} + +static int +_stringshare_key_value_replace(const char **srcstring, const char *key, const char *value, int deleteflag) +{ + Eina_Strbuf *sharebuf = NULL; + + sharebuf = eina_strbuf_new(); + eina_strbuf_append(sharebuf, *srcstring); + _strbuf_key_value_replace(sharebuf, key, value, deleteflag); + eina_stringshare_del(*srcstring); + *srcstring = eina_stringshare_add(eina_strbuf_string_get(sharebuf)); + eina_strbuf_free(sharebuf); + + return 0; +} + +static int +_is_width_over(Evas_Object *obj, Eina_Bool multiline) +{ + Evas_Coord x, y, w, h; + Evas_Coord vx, vy, vw, vh; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + const char *ellipsis_string = "..."; + int mincount = sizeof(ellipsis_string) - 1; + char *plaintxt; + int plainlen = 0; + + plaintxt = _elm_util_mkup_to_text(edje_object_part_text_get(wd->lbl, "elm.text")); + if (plaintxt) + { + plainlen = strlen(plaintxt); + free(plaintxt); + } + // too short to ellipsis + if (plainlen <= mincount) return 0; + + edje_object_part_geometry_get(wd->lbl, "elm.text", &x, &y, &w, &h); + evas_object_geometry_get(obj, &vx, &vy, &vw, &vh); + + if (!multiline) // single line + { + // skip if too early to check widget size + if ((w < 0) && (h < 0)) return 0; + // if string fits at widget + if ((x >= 0) && (y >= 0)) + { + if ((wd->wrap_w > 0) && (wd->wrap_w < w)) + { + Evas_Coord minw, minh; + + edje_object_size_min_calc(wd->lbl, &minw, &minh); + if (minw < wd->wrap_w) return 0; // min insufficient + else return 1; + } + else return 0; + } + if ((0 < wd->wrap_w) && (w > wd->wrap_w)) return 1; + } + else // multiline + { + if (((x >= 0) || (y >= 0)) && (h > wd->wrap_h)) return 1; + } + + return 0; +} + +static void +_ellipsis_fontsize_set(Evas_Object *obj, int fontsize) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + Eina_Strbuf *fontbuf = NULL; + Eina_Strbuf *txtbuf = NULL; + txtbuf = eina_strbuf_new(); + fontbuf = eina_strbuf_new(); + eina_strbuf_append(txtbuf, edje_object_part_text_get(wd->lbl, "elm.text")); + eina_strbuf_append_printf(fontbuf, "%d", fontsize); + _strbuf_key_value_replace(txtbuf, "font_size", eina_strbuf_string_get(fontbuf), 0); + edje_object_part_text_set(wd->lbl, "elm.text", eina_strbuf_string_get(txtbuf)); + eina_strbuf_free(fontbuf); + eina_strbuf_free(txtbuf); +} + +static Eina_Bool +_ellipsis_cut_chars_to_widget(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + const char *ellipsis_string = "..."; + int mincount = sizeof(ellipsis_string) - 1; + Evas_Coord w, h; + Evas_Textblock_Cursor *tc1, *tc2; + char *cutstr, *elstr; + int limitw = 0; + int lencutstr = 0; + int i = 0; + + edje_object_part_geometry_get(wd->lbl, "elm.text", NULL, NULL, &w, &h); + if (w <= 0) return EINA_FALSE; + tc1 = evas_object_textblock_cursor_new((Evas_Object *)edje_object_part_object_get(wd->lbl, "elm.text")); + tc2 = evas_object_textblock_cursor_new((Evas_Object *)edje_object_part_object_get(wd->lbl, "elm.text")); + + if ((wd->wrap_w > 0) && (wd->wrap_w < w)) limitw = wd->wrap_w; + else limitw = w; + evas_textblock_cursor_pos_set(tc1, 0); + evas_textblock_cursor_char_coord_set(tc2, limitw, 0); + + // if too small to cut,(is it bug? or any other reasons?) + // then fallback to one step mode + if (evas_textblock_cursor_pos_get(tc2) < mincount) + { + Evas_Coord cx, cy, cw, ch; + int eolpos = evas_textblock_cursor_paragraph_text_length_get(tc1); + + for (i = eolpos; i > mincount; i--) + { + evas_textblock_cursor_pos_set(tc2, i); + evas_textblock_cursor_char_geometry_get(tc2, &cx, &cy, &cw, &ch); + if (cx <= limitw) break; + } + + if (evas_textblock_cursor_pos_get(tc2) < mincount) + { + evas_textblock_cursor_free(tc1); + evas_textblock_cursor_free(tc2); + return EINA_FALSE; + } + } + + for (i = 0; i <= mincount; i++) evas_textblock_cursor_char_prev(tc2); + cutstr = evas_textblock_cursor_range_text_get(tc1, tc2, EVAS_TEXTBLOCK_TEXT_PLAIN); + if (!cutstr) return EINA_FALSE; + + lencutstr = strlen(cutstr); + elstr = alloca(sizeof(char) * (lencutstr + mincount + 1)); + strcpy(elstr, cutstr); + free(cutstr); + strcat(elstr, ellipsis_string); + edje_object_part_text_set(wd->lbl, "elm.text", elstr); + + evas_textblock_cursor_free(tc1); + evas_textblock_cursor_free(tc2); + + return EINA_TRUE; +} + +static Eina_Bool +_ellipsis_cut_lines_to_widget(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + const char *ellipsis_string = "..."; + int mincount = sizeof(ellipsis_string) - 1; + Evas_Coord w, h; + Evas_Textblock_Cursor *tc1, *tc2; + int linenum = 0, cutline = 0; + double lineheight = 0.0; + char *cutstr, *elstr; + int lencutstr = 0; + int limith = 0; + int i; + + edje_object_part_geometry_get(wd->lbl, "elm.text", NULL, NULL, &w, &h); + + tc1 = evas_object_textblock_cursor_new((Evas_Object *)edje_object_part_object_get(wd->lbl, "elm.text")); + tc2 = evas_object_textblock_cursor_new((Evas_Object *)edje_object_part_object_get(wd->lbl, "elm.text")); + // goto last paragraph + while (evas_textblock_cursor_paragraph_next(tc2) == EINA_TRUE); + + evas_textblock_cursor_paragraph_last(tc2); + // get total linenumber + linenum = evas_textblock_cursor_line_geometry_get(tc2, NULL, NULL, NULL, NULL); + lineheight = (double)h / (double)linenum; + if ((wd->wrap_h > 0) && (wd->wrap_h < h)) limith = wd->wrap_h; + else limith = h; + cutline = limith / lineheight; + if (cutline < 1) cutline = 1; + + evas_textblock_cursor_pos_set(tc1, 0); + evas_textblock_cursor_line_set(tc2, cutline - 1); + evas_textblock_cursor_line_char_last(tc2); + for (i = 0; i <= mincount; i++) evas_textblock_cursor_char_prev(tc2); + cutstr = evas_textblock_cursor_range_text_get(tc1, tc2, EVAS_TEXTBLOCK_TEXT_PLAIN); + if (!cutstr) return EINA_FALSE; + + lencutstr = strlen(cutstr); + elstr = alloca(sizeof(char) * (lencutstr + mincount + 1)); + strcpy(elstr, cutstr); + free(cutstr); + strcat(elstr, ellipsis_string); + edje_object_part_text_set(wd->lbl, "elm.text", elstr); + + evas_textblock_cursor_free(tc1); + evas_textblock_cursor_free(tc2); + + return EINA_TRUE; +} + +static void +_ellipsis_label_to_width(Evas_Object *obj, Eina_Bool multiline) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + int cur_fontsize = 0; + char *kvalue; + const char *minfont, *deffont, *maxfont; + int minfontsize, maxfontsize; + + minfont = edje_object_data_get(wd->lbl, "min_font_size"); + if (minfont) minfontsize = atoi(minfont); + else minfontsize = 1; + maxfont = edje_object_data_get(wd->lbl, "max_font_size"); + if (maxfont) maxfontsize = atoi(maxfont); + else maxfontsize = 1; + deffont = edje_object_data_get(wd->lbl, "default_font_size"); + if (deffont) cur_fontsize = atoi(deffont); + else cur_fontsize = 1; + if (minfontsize > maxfontsize || cur_fontsize == 1) return; // theme is not ready for ellipsis + if (eina_stringshare_strlen(wd->label) <= 0) return; + + if (_get_value_in_key_string(wd->label, "font_size", &kvalue) == 0) + { + if (kvalue != NULL) cur_fontsize = atoi(kvalue); + } + + while (_is_width_over(obj, multiline)) + { + if (cur_fontsize > minfontsize) + { + cur_fontsize -= 3; + if (cur_fontsize < minfontsize) cur_fontsize = minfontsize; + _ellipsis_fontsize_set(obj, cur_fontsize); + } + else + { + if (!multiline) // single line + { + _ellipsis_cut_chars_to_widget(obj); + break; + } + else // multiline + { + _ellipsis_cut_lines_to_widget(obj); + break; + } + } + } +} + +static void +_label_sliding_change(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + char *plaintxt; + int plainlen = 0; + + // dosen't support multiline sliding effect + if (wd->linewrap) + { + wd->slidingmode = EINA_FALSE; + return; + } + + plaintxt = _elm_util_mkup_to_text(edje_object_part_text_get(wd->lbl, "elm.text")); + if (plaintxt != NULL) + { + plainlen = strlen(plaintxt); + free(plaintxt); + } + // too short to slide label + if (plainlen < 1) + { + wd->slidingmode = EINA_TRUE; + return; + } + + if (wd->slidingmode) + { + Edje_Message_Float_Set *msg = alloca(sizeof(Edje_Message_Float_Set) + (sizeof(double))); + + if (wd->ellipsis) + { + wd->slidingellipsis = EINA_TRUE; + elm_label_ellipsis_set(obj, EINA_FALSE); + } + + msg->count = 1; + msg->val[0] = wd->slide_duration; + + edje_object_message_send(wd->lbl, EDJE_MESSAGE_FLOAT_SET, 0, msg); + edje_object_signal_emit(wd->lbl, "elm,state,slide,start", "elm"); + } + else + { + edje_object_signal_emit(wd->lbl, "elm,state,slide,stop", "elm"); + if (wd->slidingellipsis) + { + wd->slidingellipsis = EINA_FALSE; + elm_label_ellipsis_set(obj, EINA_TRUE); + } + } +} + +/** + * Add a new label to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Label + */ +EAPI Evas_Object * +elm_label_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + wd->bgcolor = EINA_FALSE; + wd->bg = evas_object_rectangle_add(e); + evas_object_color_set(wd->bg, 0, 0, 0, 0); + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "label"); + elm_widget_type_set(obj, "label"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->linewrap = EINA_FALSE; + wd->ellipsis = EINA_FALSE; + wd->slidingmode = EINA_FALSE; + wd->slidingellipsis = EINA_FALSE; + wd->wrap_w = 0; + wd->wrap_h = 0; + wd->slide_duration = 10; + + wd->lbl = edje_object_add(e); + _elm_theme_object_set(obj, wd->lbl, "label", "base", "default"); + wd->label = eina_stringshare_add("
    "); + edje_object_part_text_set(wd->lbl, "elm.text", "
    "); + elm_widget_resize_object_set(obj, wd->lbl); + + evas_object_event_callback_add(wd->lbl, EVAS_CALLBACK_RESIZE, _resize, obj); + + wd->changed = 1; + _sizing_eval(obj); + return obj; +} + +/** + * Set the label on the label object + * + * @param obj The label object + * @param label The label will be used on the label object + * + * @ingroup Label + */ +EAPI void +elm_label_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (!label) label = ""; + eina_stringshare_replace(&wd->label, label); + edje_object_part_text_set(wd->lbl, "elm.text", label); + wd->changed = 1; + _sizing_eval(obj); +} + +/** + * Get the label used on the label object + * + * @param obj The label object + * @return The string inside the label + * @ingroup Label + */ +EAPI const char * +elm_label_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the wrapping behavior of the label + * + * @param obj The label object + * @param wrap To wrap text or not + * @ingroup Label + */ +EAPI void +elm_label_line_wrap_set(Evas_Object *obj, Eina_Bool wrap) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + const char *t; + if (wd->linewrap == wrap) return; + wd->linewrap = wrap; + t = eina_stringshare_add(elm_label_label_get(obj)); + _theme_change(obj); + elm_label_label_set(obj, t); + eina_stringshare_del(t); + wd->changed = 1; + _sizing_eval(obj); +} + +/** + * Get the wrapping behavior of the label + * + * @param obj The label object + * @return To wrap text or not + * @ingroup Label + */ +EAPI Eina_Bool +elm_label_line_wrap_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->linewrap; +} + +/** + * Set wrap width of the label + * + * @param obj The label object + * @param w The wrap width in pixels at a minimum where words need to wrap + * @ingroup Label + */ +EAPI void +elm_label_wrap_width_set(Evas_Object *obj, Evas_Coord w) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (w < 0) w = 0; + if (wd->wrap_w == w) return; + if (wd->ellipsis) edje_object_part_text_set(wd->lbl, "elm.text", wd->label); + wd->wrap_w = w; + _sizing_eval(obj); +} + +/** + * get wrap width of the label + * + * @param obj The label object + * @return The wrap width in pixels at a minimum where words need to wrap + * @ingroup Label + */ +EAPI Evas_Coord +elm_label_wrap_width_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->wrap_w; +} + +/** + * Set wrap height of the label + * + * @param obj The label object + * @param w The wrap width in pixels at a minimum where words need to wrap + * @ingroup Label + */ +EAPI void +elm_label_wrap_height_set(Evas_Object *obj, + Evas_Coord h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (h < 0) h = 0; + if (wd->wrap_h == h) return; + if (wd->ellipsis) edje_object_part_text_set(wd->lbl, "elm.text", wd->label); + wd->wrap_h = h; + _sizing_eval(obj); +} + +/** + * get wrap width of the label + * + * @param obj The label object + * @return The wrap height in pixels at a minimum where words need to wrap + * @ingroup Label + */ +EAPI Evas_Coord +elm_label_wrap_height_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->wrap_h; +} + +/** + * Set the font size on the label object. + * + * NEVER use this. It is for hyper-special cases only. use styles instead. e.g. + * "big", "medium", "small" - or better name them by use: + * "title", "footnote", "quote" etc. + * + * @param obj The label object + * @param size font size + * + * @ingroup Label + */ +EAPI void +elm_label_fontsize_set(Evas_Object *obj, int fontsize) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_Strbuf *fontbuf = NULL; + int len, removeflag = 0; + + if (!wd) return; + _elm_dangerous_call_check(__FUNCTION__); + len = strlen(wd->label); + if (len <= 0) return; + fontbuf = eina_strbuf_new(); + eina_strbuf_append_printf(fontbuf, "%d", fontsize); + + if (fontsize == 0) removeflag = 1; // remove fontsize tag + + if (_stringshare_key_value_replace(&wd->label, "font_size", eina_strbuf_string_get(fontbuf), removeflag) == 0) + { + edje_object_part_text_set(wd->lbl, "elm.text", wd->label); + wd->changed = 1; + _sizing_eval(obj); + } + eina_strbuf_free(fontbuf); +} + +/** + * Set the text align on the label object + * + * NEVER use this. It is for hyper-special cases only. use styles instead. e.g. + * "big", "medium", "small" - or better name them by use: + * "title", "footnote", "quote" etc. + * + * @param obj The label object + * @param align align mode ("left", "center", "right") + * + * @ingroup Label + */ +EAPI void +elm_label_text_align_set(Evas_Object *obj, const char *alignmode) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + int len; + + if (!wd) return; + _elm_dangerous_call_check(__FUNCTION__); + len = strlen(wd->label); + if (len <= 0) return; + + if (_stringshare_key_value_replace(&wd->label, "align", alignmode, 0) == 0) + edje_object_part_text_set(wd->lbl, "elm.text", wd->label); + + wd->changed = 1; + _sizing_eval(obj); +} + +/** + * Set the text color on the label object + * + * @param obj The label object + * @param r Red property background color of The label object + * @param g Green property background color of The label object + * @param b Blue property background color of The label object + * @param a Alpha property background color of The label object + * + * @ingroup Label + */ +EAPI void +elm_label_text_color_set(Evas_Object *obj, + unsigned int r, + unsigned int g, + unsigned int b, + unsigned int a) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_Strbuf *colorbuf = NULL; + int len; + + if (!wd) return; + _elm_dangerous_call_check(__FUNCTION__); + len = strlen(wd->label); + if (len <= 0) return; + colorbuf = eina_strbuf_new(); + eina_strbuf_append_printf(colorbuf, "#%02X%02X%02X%02X", r, g, b, a); + + if (_stringshare_key_value_replace(&wd->label, "color", eina_strbuf_string_get(colorbuf), 0) == 0) + { + edje_object_part_text_set(wd->lbl, "elm.text", wd->label); + wd->changed = 1; + _sizing_eval(obj); + } + eina_strbuf_free(colorbuf); +} + +/** + * Set background color of the label + * + * NEVER use this. It is for hyper-special cases only. use styles instead. e.g. + * "big", "medium", "small" - or better name them by use: + * "title", "footnote", "quote" etc. + * + * @param obj The label object + * @param r Red property background color of The label object + * @param g Green property background color of The label object + * @param b Blue property background color of The label object + * @param a Alpha property background alpha of The label object + * + * @ingroup Label + */ +EAPI void +elm_label_background_color_set(Evas_Object *obj, + unsigned int r, + unsigned int g, + unsigned int b, + unsigned int a) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_color_set(wd->bg, r, g, b, a); + + if (!wd) return; + _elm_dangerous_call_check(__FUNCTION__); + if (wd->bgcolor == EINA_FALSE) + { + wd->bgcolor = 1; + edje_object_part_swallow(wd->lbl, "label.swallow.background", wd->bg); + } +} + +/** + * Set the ellipsis behavior of the label + * + * @param obj The label object + * @param ellipsis To ellipsis text or not + * @ingroup Label + */ +EAPI void +elm_label_ellipsis_set(Evas_Object *obj, Eina_Bool ellipsis) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->ellipsis == ellipsis) return; + wd->ellipsis = ellipsis; + if (wd->linewrap) _theme_change(obj); + edje_object_part_text_set(wd->lbl, "elm.text", wd->label); + wd->changed = 1; + _sizing_eval(obj); +} + +/** + * Set the text slide of the label + * + * @param obj The label object + * @param slide To start slide or stop + * @ingroup Label + */ +EAPI void +elm_label_slide_set(Evas_Object *obj, + Eina_Bool slide) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (wd->slidingmode == slide) return; + wd->slidingmode = slide; + _label_sliding_change(obj); + wd->changed = 1; + _sizing_eval(obj); +} + +/** + * get the text slide mode of the label + * + * @param obj The label object + * @return slide slide mode value + * @ingroup Label + */ +EAPI Eina_Bool +elm_label_slide_get(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->slidingmode; +} + +/** + * set the slide duration(speed) of the label + * + * @param obj The label object + * @return The duration time in moving text from slide begin position to slide end position + * @ingroup Label + */ +EAPI void +elm_label_slide_duration_set(Evas_Object *obj, double duration) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Edje_Message_Float_Set *msg = alloca(sizeof(Edje_Message_Float_Set) + (sizeof(double))); + + if (!wd) return; + wd->slide_duration = duration; + msg->count = 1; + msg->val[0] = wd->slide_duration; + edje_object_message_send(wd->lbl, EDJE_MESSAGE_FLOAT_SET, 0, msg); +} + +/** + * get the slide duration(speed) of the label + * + * @param obj The label object + * @return The duration time in moving text from slide begin position to slide end position + * @ingroup Label + */ +EAPI double +elm_label_slide_duration_get(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->slide_duration; +} + diff --git a/src/lib/elm_layout.c b/src/lib/elm_layout.c new file mode 100644 index 0000000..a398af4 --- /dev/null +++ b/src/lib/elm_layout.c @@ -0,0 +1,1274 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Layout Layout + * + * This takes a standard Edje design file and wraps it very thinly + * in a widget and handles swallowing widgets into swallow regions + * in the Edje object, allowing Edje to be used as a design and + * layout tool + */ + +typedef struct _Widget_Data Widget_Data; +typedef struct _Subinfo Subinfo; +typedef struct _Part_Cursor Part_Cursor; + +struct _Widget_Data +{ + Evas_Object *obj; + Evas_Object *lay; + Eina_List *subs; + Eina_List *parts_cursors; + Eina_Bool needs_size_calc:1; +}; + +struct _Subinfo +{ + const char *part; + Evas_Object *obj; + enum { + SWALLOW, + BOX_APPEND, + BOX_PREPEND, + BOX_INSERT_BEFORE, + BOX_INSERT_AT, + TABLE_PACK, + TEXT + } type; + union { + union { + const Evas_Object *reference; + unsigned int pos; + } box; + struct { + unsigned short col, row, colspan, rowspan; + } table; + struct { + const char *text; + } text; + } p; +}; + +struct _Part_Cursor +{ + Evas_Object *obj; + const char *part; + const char *cursor; + const char *style; + Eina_Bool engine_only:1; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Widget_Data *wd); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _part_cursor_free(Part_Cursor *pc); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + Part_Cursor *pc; + + if (!wd) return; + EINA_LIST_FREE(wd->subs, si) + { + eina_stringshare_del(si->part); + if (si->type == TEXT) + eina_stringshare_del(si->p.text.text); + free(si); + } + EINA_LIST_FREE(wd->parts_cursors, pc) _part_cursor_free(pc); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_scale_set(wd->lay, elm_widget_scale_get(obj) * + _elm_config->scale); + _sizing_eval(wd); +} + +static void +_changed_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->needs_size_calc) + { + _sizing_eval(wd); + wd->needs_size_calc = 0; + } +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_emit(wd->lay, emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_add(wd->lay, emission, source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_del_full(wd->lay, emission, source, func_cb, + data); +} + + +static void * +_elm_layout_list_data_get(const Eina_List *list) +{ + Subinfo *si = eina_list_data_get(list); + return si->obj; +} + +static Eina_Bool +_elm_layout_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const Eina_List *items; + void *(*list_data_get) (const Eina_List *list); + + if ((!wd) || (!wd->subs)) + return EINA_FALSE; + + /* Focus chain (This block is diferent of elm_win cycle)*/ + if ((items = elm_widget_focus_custom_chain_get(obj))) + list_data_get = eina_list_data_get; + else + { + items = wd->subs; + list_data_get = _elm_layout_list_data_get; + + if (!items) return EINA_FALSE; + } + + return elm_widget_focus_list_next_get(obj, items, list_data_get, dir, + next); +} + +static void +_sizing_eval(Widget_Data *wd) +{ + Evas_Coord minw = -1, minh = -1; + edje_object_size_min_calc(wd->lay, &minw, &minh); + evas_object_size_hint_min_set(wd->obj, minw, minh); + evas_object_size_hint_max_set(wd->obj, -1, -1); +} + +static void +_request_sizing_eval(Widget_Data *wd) +{ + if (wd->needs_size_calc) return; + wd->needs_size_calc = 1; + evas_object_smart_changed(wd->obj); +} + +static void +_part_cursor_free(Part_Cursor *pc) +{ + eina_stringshare_del(pc->part); + eina_stringshare_del(pc->style); + eina_stringshare_del(pc->cursor); + free(pc); +} + +static void +_part_cursor_part_apply(const Part_Cursor *pc) +{ + elm_object_cursor_set(pc->obj, pc->cursor); + elm_object_cursor_style_set(pc->obj, pc->style); + elm_object_cursor_engine_only_set(pc->obj, pc->engine_only); +} + +static Part_Cursor * +_parts_cursors_find(Widget_Data *wd, const char *part) +{ + const Eina_List *l; + Part_Cursor *pc; + EINA_LIST_FOREACH(wd->parts_cursors, l, pc) + { + if (!strcmp(pc->part, part)) + return pc; + } + return NULL; +} + +static void +_parts_cursors_apply(Widget_Data *wd) +{ + const char *file, *group; + const Eina_List *l; + Part_Cursor *pc; + + edje_object_file_get(wd->lay, &file, &group); + + EINA_LIST_FOREACH(wd->parts_cursors, l, pc) + { + Evas_Object *obj = (Evas_Object *)edje_object_part_object_get + (wd->lay, pc->part); + + if (!obj) + { + pc->obj = NULL; + WRN("no part '%s' in group '%s' of file '%s'. " + "Cannot set cursor '%s'", + pc->part, group, file, pc->cursor); + continue; + } + else if (evas_object_pass_events_get(obj)) + { + pc->obj = NULL; + WRN("part '%s' in group '%s' of file '%s' has mouse_events: 0. " + "Cannot set cursor '%s'", + pc->part, group, file, pc->cursor); + continue; + } + + pc->obj = obj; + _part_cursor_part_apply(pc); + } +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _request_sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + Eina_List *l; + Subinfo *si; + if (!wd) return; + EINA_LIST_FOREACH(wd->subs, l, si) + { + if (si->obj == sub) + { + evas_object_event_callback_del_full(sub, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, + wd); + wd->subs = eina_list_remove_list(wd->subs, l); + eina_stringshare_del(si->part); + free(si); + break; + } + } +} + +static void +_signal_size_eval(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + _request_sizing_eval(data); +} + +static void +_parts_text_fix(Widget_Data *wd) +{ + const Eina_List *l; + Subinfo *si; + + EINA_LIST_FOREACH(wd->subs, l, si) + { + if (si->type == TEXT) + edje_object_part_text_set(wd->lay, si->part, si->p.text.text); + } +} + +/** + * Add a new layout to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Layout + */ +EAPI Evas_Object * +elm_layout_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + wd->obj = obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "layout"); + elm_widget_type_set(obj, "layout"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_changed_hook_set(obj, _changed_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + elm_widget_focus_next_hook_set(obj, _elm_layout_focus_next_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + + wd->lay = edje_object_add(e); + elm_widget_resize_object_set(obj, wd->lay); + edje_object_signal_callback_add(wd->lay, "size,eval", "elm", + _signal_size_eval, wd); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + _request_sizing_eval(wd); + return obj; +} + +/** + * Set the file that will be used as layout + * + * @param obj The layout object + * @param file The path to file (edj) that will be used as layout + * @param group The group that the layout belongs in edje file + * + * @return (1 = success, 0 = error) + * + * @ingroup Layout + */ +EAPI Eina_Bool +elm_layout_file_set(Evas_Object *obj, const char *file, const char *group) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + Eina_Bool ret = edje_object_file_set(wd->lay, file, group); + if (ret) + { + _parts_text_fix(wd); + _request_sizing_eval(wd); + _parts_cursors_apply(wd); + } + else DBG("failed to set edje file '%s', group '%s': %s", + file, group, + edje_load_error_str(edje_object_load_error_get(wd->lay))); + return ret; +} + +/** + * Set the edje group from the elementary theme that will be used as layout + * + * @param obj The layout object + * @param clas the clas of the group + * @param group the group + * @param style the style to used + * + * @return (1 = success, 0 = error) + * + * @ingroup Layout + */ +EAPI Eina_Bool +elm_layout_theme_set(Evas_Object *obj, const char *clas, const char *group, const char *style) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + Eina_Bool ret = _elm_theme_object_set(obj, wd->lay, clas, group, style); + if (ret) + { + _parts_text_fix(wd); + _request_sizing_eval(wd); + _parts_cursors_apply(wd); + } + return ret; +} + +/** + * Set the layout content + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_layout_content_unset() function. + * + * @param obj The layout object + * @param swallow The swallow group name in the edje file + * @param content The content will be filled in this layout object + * + * @ingroup Layout + */ +EAPI void +elm_layout_content_set(Evas_Object *obj, const char *swallow, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + const Eina_List *l; + if (!wd) return; + EINA_LIST_FOREACH(wd->subs, l, si) + { + if ((si->type == SWALLOW) && (!strcmp(swallow, si->part))) + { + if (content == si->obj) return; + evas_object_del(si->obj); + break; + } + } + if (content) + { + elm_widget_sub_object_add(obj, content); + evas_object_event_callback_add(content, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, wd); + if (!edje_object_part_swallow(wd->lay, swallow, content)) + WRN("could not swallow %p into part '%s'", content, swallow); + si = ELM_NEW(Subinfo); + si->type = SWALLOW; + si->part = eina_stringshare_add(swallow); + si->obj = content; + wd->subs = eina_list_append(wd->subs, si); + } + _request_sizing_eval(wd); +} + +/** + * Get the swallowed object in the given part + * + * @param obj The layout object + * @param swallow The SWALLOW part to get its content + * + * @return The swallowed object or NULL if none or an error occurred + * + * @ingroup Layout + */ +EAPI const Evas_Object * +elm_layout_content_get(const Evas_Object *obj, const char *swallow) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const Eina_List *l; + Subinfo *si; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + EINA_LIST_FOREACH(wd->subs, l, si) + { + if ((si->type == SWALLOW) && !strcmp(swallow, si->part)) + return si->obj; + } + return NULL; +} + +/** + * Unset the layout content + * + * Unparent and return the content object which was set for this widget + * + * @param obj The layout object + * @param swallow The swallow group name in the edje file + * @return The content that was being used + * + * @ingroup Layout + */ +EAPI Evas_Object * +elm_layout_content_unset(Evas_Object *obj, const char *swallow) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + const Eina_List *l; + if (!wd) return NULL; + EINA_LIST_FOREACH(wd->subs, l, si) + { + if ((si->type == SWALLOW) && (!strcmp(swallow, si->part))) + { + Evas_Object *content; + if (!si->obj) return NULL; + content = si->obj; /* si will die in _sub_del due elm_widget_sub_object_del() */ + elm_widget_sub_object_del(obj, content); + edje_object_part_unswallow(wd->lay, content); + return content; + } + } + return NULL; +} + +/** + * Set the text of the given part + * + * @param obj The layout object + * @param part The TEXT part where to set the text + * @param text The text to set + * + * @ingroup Layout + */ +EAPI void +elm_layout_text_set(Evas_Object *obj, const char *part, const char *text) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si = NULL; + Eina_List *l; + ELM_CHECK_WIDTYPE(obj, widtype); + + EINA_LIST_FOREACH(wd->subs, l, si) + { + if ((si->type == TEXT) && (!strcmp(part, si->part))) + { + if (!text) + { + eina_stringshare_del(si->part); + eina_stringshare_del(si->p.text.text); + free(si); + edje_object_part_text_set(wd->lay, part, NULL); + wd->subs = eina_list_remove_list(wd->subs, l); + return; + } + else + break; + } + si = NULL; + } + + if (!si) + { + si = ELM_NEW(Subinfo); + if (!si) return; + si->type = TEXT; + si->part = eina_stringshare_add(part); + wd->subs = eina_list_append(wd->subs, si); + } + + eina_stringshare_replace(&si->p.text.text, text); + edje_object_part_text_set(wd->lay, part, text); + _request_sizing_eval(wd); +} + +/** + * Get the text set in the given part + * + * @param obj The layout object + * @param part The TEXT part to retrieve the text off + * + * @return The text set in @p part + * + * @ingroup Layout + */ +EAPI const char * +elm_layout_text_get(const Evas_Object *obj, const char *part) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + return edje_object_part_text_get(wd->lay, part); +} + +/** + * Append child to layout box part. + * + * Once the object is appended, its lifetime will be bound to the + * layout, whenever the layout dies the child will be deleted + * automatically. One should use elm_layout_box_remove() to make this + * layout forget about the object. + * + * @param obj the layout object + * @param part the box part to append. + * @param child the child object to append to box. + * + * @ingroup Layout + */ +EAPI void +elm_layout_box_append(Evas_Object *obj, const char *part, Evas_Object *child) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + if (!wd) return; + + if (!edje_object_part_box_append(wd->lay, part, child)) + WRN("child %p could not be appended to box part '%s'", child, part); + elm_widget_sub_object_add(obj, child); + evas_object_event_callback_add + (child, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, wd); + + si = ELM_NEW(Subinfo); + si->type = BOX_APPEND; + si->part = eina_stringshare_add(part); + si->obj = child; + wd->subs = eina_list_append(wd->subs, si); + _request_sizing_eval(wd); +} + +/** + * Prepend child to layout box part. + * + * Once the object is prepended, its lifetime will be bound to the + * layout, whenever the layout dies the child will be deleted + * automatically. One should use elm_layout_box_remove() to make this + * layout forget about the object. + * + * @param obj the layout object + * @param part the box part to prepend. + * @param child the child object to prepend to box. + * + * @ingroup Layout + */ +EAPI void +elm_layout_box_prepend(Evas_Object *obj, const char *part, Evas_Object *child) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + if (!wd) return; + + if (!edje_object_part_box_prepend(wd->lay, part, child)) + WRN("child %p could not be prepended to box part '%s'", child, part); + elm_widget_sub_object_add(obj, child); + evas_object_event_callback_add + (child, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, wd); + + si = ELM_NEW(Subinfo); + si->type = BOX_PREPEND; + si->part = eina_stringshare_add(part); + si->obj = child; + wd->subs = eina_list_prepend(wd->subs, si); + _request_sizing_eval(wd); +} + +static void +_box_reference_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Subinfo *si = data; + si->p.box.reference = NULL; +} + +/** + * Insert child to layout box part before a reference object. + * + * Once the object is inserted, its lifetime will be bound to the + * layout, whenever the layout dies the child will be deleted + * automatically. One should use elm_layout_box_remove() to make this + * layout forget about the object. + * + * @param obj the layout object + * @param part the box part to insert. + * @param child the child object to insert into box. + * @param reference another reference object to insert before in box. + * + * @ingroup Layout + */ +EAPI void +elm_layout_box_insert_before(Evas_Object *obj, const char *part, Evas_Object *child, const Evas_Object *reference) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + if (!wd) return; + + if (!edje_object_part_box_insert_before(wd->lay, part, child, reference)) + WRN("child %p could not be inserted before %p inf box part '%s'", + child, reference, part); + + si = ELM_NEW(Subinfo); + si->type = BOX_INSERT_BEFORE; + si->part = eina_stringshare_add(part); + si->obj = child; + si->p.box.reference = reference; + + elm_widget_sub_object_add(obj, child); + evas_object_event_callback_add + (child, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, wd); + evas_object_event_callback_add + ((Evas_Object *)reference, EVAS_CALLBACK_DEL, _box_reference_del, si); + + wd->subs = eina_list_append(wd->subs, si); + _request_sizing_eval(wd); +} + +/** + * Insert child to layout box part at a given position. + * + * Once the object is inserted, its lifetime will be bound to the + * layout, whenever the layout dies the child will be deleted + * automatically. One should use elm_layout_box_remove() to make this + * layout forget about the object. + * + * @param obj the layout object + * @param part the box part to insert. + * @param child the child object to insert into box. + * @param pos the numeric position >=0 to insert the child. + * + * @ingroup Layout + */ +EAPI void +elm_layout_box_insert_at(Evas_Object *obj, const char *part, Evas_Object *child, unsigned int pos) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + if (!wd) return; + + if (!edje_object_part_box_insert_at(wd->lay, part, child, pos)) + WRN("child %p could not be inserted at %u to box part '%s'", + child, pos, part); + + elm_widget_sub_object_add(obj, child); + evas_object_event_callback_add + (child, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, wd); + + si = ELM_NEW(Subinfo); + si->type = BOX_INSERT_AT; + si->part = eina_stringshare_add(part); + si->obj = child; + si->p.box.pos = pos; + wd->subs = eina_list_append(wd->subs, si); + _request_sizing_eval(wd); +} + +static Evas_Object * +_sub_box_remove(Widget_Data *wd, Subinfo *si) +{ + Evas_Object *child; + + if (si->type == BOX_INSERT_BEFORE) + evas_object_event_callback_del_full + ((Evas_Object *)si->p.box.reference, + EVAS_CALLBACK_DEL, _box_reference_del, si); + + child = si->obj; /* si will die in _sub_del due elm_widget_sub_object_del() */ + edje_object_part_box_remove(wd->lay, si->part, child); + elm_widget_sub_object_del(wd->obj, child); + return child; +} + +static Evas_Object * +_sub_table_remove(Widget_Data *wd, Subinfo *si) +{ + Evas_Object *child; + + child = si->obj; /* si will die in _sub_del due elm_widget_sub_object_del() */ + edje_object_part_table_unpack(wd->lay, si->part, child); + elm_widget_sub_object_del(wd->obj, child); + return child; +} + +static Eina_Bool +_sub_box_is(const Subinfo *si) +{ + switch (si->type) + { + case BOX_APPEND: + case BOX_PREPEND: + case BOX_INSERT_BEFORE: + case BOX_INSERT_AT: + return EINA_TRUE; + default: + return EINA_FALSE; + } +} + +/** + * Remove a child of the given part box. + * + * The object will be removed from the box part and its lifetime will + * not be handled by the layout anymore. This is equivalent to + * elm_layout_content_unset() for box. + * + * @param obj The layout object + * @param part The box part name to remove child. + * @param child The object to remove from box. + * @return The object that was being used, or NULL if not found. + * + * @ingroup Layout + */ +EAPI Evas_Object * +elm_layout_box_remove(Evas_Object *obj, const char *part, Evas_Object *child) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + const Eina_List *l; + Subinfo *si; + + if (!wd) return NULL; + + EINA_SAFETY_ON_NULL_RETURN_VAL(part, NULL); + EINA_SAFETY_ON_NULL_RETURN_VAL(child, NULL); + EINA_LIST_FOREACH(wd->subs, l, si) + { + if (!_sub_box_is(si)) continue; + if ((si->obj == child) && (!strcmp(si->part, part))) + return _sub_box_remove(wd, si); + } + return NULL; +} + +/** + * Remove all child of the given part box. + * + * The objects will be removed from the box part and their lifetime will + * not be handled by the layout anymore. This is equivalent to + * elm_layout_content_unset() for all box children. + * + * @param obj The layout object + * @param part The box part name to remove child. + * @param clear If EINA_TRUE, then all objects will be deleted as + * well, otherwise they will just be removed and will be + * dangling on the canvas. + * + * @ingroup Layout + */ +EAPI void +elm_layout_box_remove_all(Evas_Object *obj, const char *part, Eina_Bool clear) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + Eina_List *lst; + + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(part); + + lst = eina_list_clone(wd->subs); + EINA_LIST_FREE(lst, si) + { + if (!_sub_box_is(si)) continue; + if (!strcmp(si->part, part)) + { + Evas_Object *child = _sub_box_remove(wd, si); + if ((clear) && (child)) evas_object_del(child); + } + } + /* eventually something may not be added with layout, del them as well */ + edje_object_part_box_remove_all(wd->lay, part, clear); +} + +/** + * Insert child to layout table part. + * + * Once the object is inserted, its lifetime will be bound to the + * layout, whenever the layout dies the child will be deleted + * automatically. One should use elm_layout_box_remove() to make this + * layout forget about the object. + * + * @param obj the layout object + * @param part the box part to pack child. + * @param child the child object to pack into table. + * @param reference another reference object to insert before in box. + * + * @ingroup Layout + */ +EAPI void +elm_layout_table_pack(Evas_Object *obj, const char *part, Evas_Object *child, unsigned short col, unsigned short row, unsigned short colspan, unsigned short rowspan) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + if (!wd) return; + + if (!edje_object_part_table_pack + (wd->lay, part, child, col, row, colspan, rowspan)) + WRN("child %p could not be packed into box part '%s' col=%uh, row=%hu, " + "colspan=%hu, rowspan=%hu", child, part, col, row, colspan, rowspan); + + elm_widget_sub_object_add(obj, child); + evas_object_event_callback_add + (child, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, wd); + + si = ELM_NEW(Subinfo); + si->type = TABLE_PACK; + si->part = eina_stringshare_add(part); + si->obj = child; + si->p.table.col = col; + si->p.table.row = row; + si->p.table.colspan = colspan; + si->p.table.rowspan = rowspan; + wd->subs = eina_list_append(wd->subs, si); + _request_sizing_eval(wd); +} + +/** + * Unpack (remove) a child of the given part table. + * + * The object will be unpacked from the table part and its lifetime + * will not be handled by the layout anymore. This is equivalent to + * elm_layout_content_unset() for table. + * + * @param obj The layout object + * @param part The table part name to remove child. + * @param child The object to remove from table. + * @return The object that was being used, or NULL if not found. + * + * @ingroup Layout + */ +EAPI Evas_Object * +elm_layout_table_unpack(Evas_Object *obj, const char *part, Evas_Object *child) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + const Eina_List *l; + Subinfo *si; + + if (!wd) return NULL; + + EINA_SAFETY_ON_NULL_RETURN_VAL(part, NULL); + EINA_SAFETY_ON_NULL_RETURN_VAL(child, NULL); + EINA_LIST_FOREACH(wd->subs, l, si) + { + if (si->type != TABLE_PACK) continue; + if ((si->obj == child) && (!strcmp(si->part, part))) + return _sub_table_remove(wd, si); + } + return NULL; +} + +/** + * Remove all child of the given part table. + * + * The objects will be removed from the table part and their lifetime will + * not be handled by the layout anymore. This is equivalent to + * elm_layout_content_unset() for all table children. + * + * @param obj The layout object + * @param part The table part name to remove child. + * @param clear If EINA_TRUE, then all objects will be deleted as + * well, otherwise they will just be removed and will be + * dangling on the canvas. + * + * @ingroup Layout + */ +EAPI void +elm_layout_table_clear(Evas_Object *obj, const char *part, Eina_Bool clear) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Subinfo *si; + Eina_List *lst; + + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(part); + + lst = eina_list_clone(wd->subs); + EINA_LIST_FREE(lst, si) + { + if (si->type != TABLE_PACK) continue; + if (!strcmp(si->part, part)) + { + Evas_Object *child = _sub_table_remove(wd, si); + if ((clear) && (child)) evas_object_del(child); + } + } + /* eventually something may not be added with layout, del them as well */ + edje_object_part_table_clear(wd->lay, part, clear); +} + +/** + * Get the edje layout + * + * @param obj The layout object + * + * This returns the edje object. It is not expected to be used to then swallow + * objects via edje_object_part_swallow() for example. Use + * elm_layout_content_set() instead so child object handling and sizing is + * done properly. This is more intended for setting text, emitting signals, + * hooking to signal callbacks etc. + * + * @return A Evas_Object with the edje layout settings loaded + * with function elm_layout_file_set + * + * @ingroup Layout + */ +EAPI Evas_Object * +elm_layout_edje_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->lay; +} + +/** + * Get the edje data of the given layout + * + * @param obj The layout object + * @param key The data key + * + * @return The edje data string + * + * This function fetches data specified at the object level. + * This function return NULL if data is not found. + * + * In EDC this comes from a data block within the group block that @a + * obj was loaded from. E.g. + * + * @code + * collections { + * group { + * name: "a_group"; + * data { + * item: "key1" "value1"; + * item: "key2" "value2"; + * } + * } + * } + * @endcode + * + * @ingroup Layout + */ +EAPI const char * +elm_layout_data_get(const Evas_Object *obj, const char *key) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + return edje_object_data_get(wd->lay, key); +} + +/** + * Eval sizing + * + * Manually forms a sizing re-evaluation when contents changed state so that + * minimum size might have changed and needs re-evaluation. Also note that + * a standard signal of "size,eval" "elm" emitted by the edje object will + * cause this to happen too + * + * @param obj The layout object + * + * @ingroup Layout + */ +EAPI void +elm_layout_sizing_eval(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + EINA_SAFETY_ON_NULL_RETURN(wd); + _request_sizing_eval(wd); +} + +/** + * Sets a specific cursor for an edje part. + * + * @param obj The layout object. + * @param part_name a part from loaded edje group. + * @param cursor cursor name to use, see Elementary_Cursor.h + * + * @return EINA_TRUE on success or EINA_FALSE on failure, that may be + * part not exists or it has "mouse_events: 0". + * + * @ingroup Layout + */ +EAPI Eina_Bool +elm_layout_part_cursor_set(Evas_Object *obj, const char *part_name, const char *cursor) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + EINA_SAFETY_ON_NULL_RETURN_VAL(part_name, EINA_FALSE); + Widget_Data *wd = elm_widget_data_get(obj); + EINA_SAFETY_ON_NULL_RETURN_VAL(wd, EINA_FALSE); + Evas_Object *part_obj; + Part_Cursor *pc; + + part_obj = (Evas_Object *)edje_object_part_object_get(wd->lay, part_name); + if (!part_obj) + { + const char *group, *file; + edje_object_file_get(wd->lay, &file, &group); + WRN("no part '%s' in group '%s' of file '%s'. Cannot set cursor '%s'", + part_name, group, file, cursor); + return EINA_FALSE; + } + if (evas_object_pass_events_get(part_obj)) + { + const char *group, *file; + edje_object_file_get(wd->lay, &file, &group); + WRN("part '%s' in group '%s' of file '%s' has mouse_events: 0. " + "Cannot set cursor '%s'", + part_name, group, file, cursor); + return EINA_FALSE; + } + + pc = _parts_cursors_find(wd, part_name); + if (pc) eina_stringshare_replace(&pc->cursor, cursor); + else + { + pc = calloc(1, sizeof(*pc)); + pc->part = eina_stringshare_add(part_name); + pc->cursor = eina_stringshare_add(cursor); + } + + pc->obj = part_obj; + elm_object_sub_cursor_set(part_obj, obj, pc->cursor); + return EINA_TRUE; +} + +/** + * Get the cursor to be shown when mouse is over an edje part + * + * @param obj The layout object. + * @param part_name a part from loaded edje group. + * @return the cursor name. + * + * @ingroup Layout + */ +EAPI const char * +elm_layout_part_cursor_get(const Evas_Object *obj, const char *part_name) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + EINA_SAFETY_ON_NULL_RETURN_VAL(part_name, NULL); + Widget_Data *wd = elm_widget_data_get(obj); + EINA_SAFETY_ON_NULL_RETURN_VAL(wd, NULL); + Part_Cursor *pc = _parts_cursors_find(wd, part_name); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc, NULL); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc->obj, NULL); + return elm_object_cursor_get(pc->obj); +} + +/** + * Unsets a cursor previously set with elm_layout_part_cursor_set(). + * + * @param obj The layout object. + * @param part_name a part from loaded edje group, that had a cursor set + * with elm_layout_part_cursor_set(). + * + * @ingroup Layout + */ +EAPI void +elm_layout_part_cursor_unset(Evas_Object *obj, const char *part_name) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + EINA_SAFETY_ON_NULL_RETURN(part_name); + Widget_Data *wd = elm_widget_data_get(obj); + EINA_SAFETY_ON_NULL_RETURN(wd); + Eina_List *l; + Part_Cursor *pc; + + EINA_LIST_FOREACH(wd->parts_cursors, l, pc) + { + if (!strcmp(part_name, pc->part)) + { + if (pc->obj) elm_object_cursor_unset(pc->obj); + _part_cursor_free(pc); + wd->parts_cursors = eina_list_remove_list(wd->parts_cursors, l); + return; + } + } +} + +/** + * Sets a specific cursor style for an edje part. + * + * @param obj The layout object. + * @param part_name a part from loaded edje group. + * @param style the theme style to use (default, transparent, ...) + * + * @return EINA_TRUE on success or EINA_FALSE on failure, that may be + * part not exists or it did not had a cursor set. + * + * @ingroup Layout + */ +EAPI Eina_Bool +elm_layout_part_cursor_style_set(Evas_Object *obj, const char *part_name, const char *style) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + EINA_SAFETY_ON_NULL_RETURN_VAL(part_name, EINA_FALSE); + Widget_Data *wd = elm_widget_data_get(obj); + EINA_SAFETY_ON_NULL_RETURN_VAL(wd, EINA_FALSE); + Part_Cursor *pc = _parts_cursors_find(wd, part_name); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc, EINA_FALSE); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc->obj, EINA_FALSE); + + eina_stringshare_replace(&pc->style, style); + elm_object_cursor_style_set(pc->obj, pc->style); + return EINA_TRUE; +} + +/** + * Gets a specific cursor style for an edje part. + * + * @param obj The layout object. + * @param part_name a part from loaded edje group. + * + * @return the theme style in use, defaults to "default". If the + * object does not have a cursor set, then NULL is returned. + * + * @ingroup Layout + */ +EAPI const char * +elm_layout_part_cursor_style_get(const Evas_Object *obj, const char *part_name) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + EINA_SAFETY_ON_NULL_RETURN_VAL(part_name, NULL); + Widget_Data *wd = elm_widget_data_get(obj); + EINA_SAFETY_ON_NULL_RETURN_VAL(wd, NULL); + Part_Cursor *pc = _parts_cursors_find(wd, part_name); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc, NULL); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc->obj, NULL); + return elm_object_cursor_style_get(pc->obj); +} + +/** + * Sets if the cursor set should be searched on the theme or should use + * the provided by the engine, only. + * + * @note before you set if should look on theme you should define a + * cursor with elm_layout_part_cursor_set(). By default it will only + * look for cursors provided by the engine. + * + * @param obj The layout object. + * @param part_name a part from loaded edje group. + * @param engine_only if cursors should be just provided by the engine + * or should also search on widget's theme as well + * + * @return EINA_TRUE on success or EINA_FALSE on failure, that may be + * part not exists or it did not had a cursor set. + * + * @ingroup Layout + */ +EAPI Eina_Bool +elm_layout_part_cursor_engine_only_set(Evas_Object *obj, const char *part_name, Eina_Bool engine_only) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + EINA_SAFETY_ON_NULL_RETURN_VAL(part_name, EINA_FALSE); + Widget_Data *wd = elm_widget_data_get(obj); + EINA_SAFETY_ON_NULL_RETURN_VAL(wd, EINA_FALSE); + Part_Cursor *pc = _parts_cursors_find(wd, part_name); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc, EINA_FALSE); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc->obj, EINA_FALSE); + + pc->engine_only = !!engine_only; + elm_object_cursor_engine_only_set(pc->obj, pc->engine_only); + return EINA_TRUE; +} + +/** + * Gets a specific cursor engine_only for an edje part. + * + * @param obj The layout object. + * @param part_name a part from loaded edje group. + * + * @return whenever the cursor is just provided by engine or also from theme. + * + * @ingroup Layout + */ +EAPI Eina_Bool +elm_layout_part_cursor_engine_only_get(const Evas_Object *obj, const char *part_name) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + EINA_SAFETY_ON_NULL_RETURN_VAL(part_name, EINA_FALSE); + Widget_Data *wd = elm_widget_data_get(obj); + EINA_SAFETY_ON_NULL_RETURN_VAL(wd, EINA_FALSE); + Part_Cursor *pc = _parts_cursors_find(wd, part_name); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc, EINA_FALSE); + EINA_SAFETY_ON_NULL_RETURN_VAL(pc->obj, EINA_FALSE); + return elm_object_cursor_engine_only_get(pc->obj); +} + + + diff --git a/src/lib/elm_list.c b/src/lib/elm_list.c new file mode 100644 index 0000000..73906bc --- /dev/null +++ b/src/lib/elm_list.c @@ -0,0 +1,2497 @@ +#include +#include "elm_priv.h" + +#define SWIPE_MOVES 12 + +/** + * @defgroup List List + * + * A list is a very simple type of list widget. For more robust + * lists, @ref Genlist should probably be used. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *scr, *box, *self; + Eina_List *items, *selected, *to_delete; + Elm_List_Item *last_selected_item; + Elm_List_Mode mode; + Elm_List_Mode h_mode; + Evas_Coord minw[2], minh[2]; + Eina_Bool scr_minw : 1; + Eina_Bool scr_minh : 1; + int walking; + int movements; + struct + { + Evas_Coord x, y; + } history[SWIPE_MOVES]; + Eina_Bool swipe : 1; + Eina_Bool fix_pending : 1; + Eina_Bool on_hold : 1; + Eina_Bool multi : 1; + Eina_Bool always_select : 1; + Eina_Bool longpressed : 1; + Eina_Bool wasselected : 1; +}; + +struct _Elm_List_Item +{ + Elm_Widget_Item base; + Widget_Data *wd; + Eina_List *node; + const char *label; + Evas_Object *icon, *end; + Evas_Smart_Cb func; + Ecore_Timer *long_timer; + Ecore_Timer *swipe_timer; + Eina_Bool deleted : 1; + Eina_Bool disabled : 1; + Eina_Bool even : 1; + Eina_Bool is_even : 1; + Eina_Bool is_separator : 1; + Eina_Bool fixed : 1; + Eina_Bool selected : 1; + Eina_Bool hilighted : 1; + Eina_Bool dummy_icon : 1; + Eina_Bool dummy_end : 1; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _on_focus_hook(void *data, Evas_Object *obj); +static void _signal_emit_hook(Evas_Object *obj, const char *emission, const char *source); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _fix_items(Evas_Object *obj); +static void _mouse_down(void *data, Evas *evas, Evas_Object *obj, void *event_info); +static void _mouse_up(void *data, Evas *evas, Evas_Object *obj, void *event_info); +static void _mouse_move(void *data, Evas *evas, Evas_Object *obj, void *event_info); +static void _scroll_edge_left(void *data, Evas_Object *scr, void *event_info); +static void _scroll_edge_right(void *data, Evas_Object *scr, void *event_info); +static void _scroll_edge_top(void *data, Evas_Object *scr, void *event_info); +static void _scroll_edge_bottom(void *data, Evas_Object *scr, void *event_info); +static Eina_Bool _item_multi_select_up(Widget_Data *wd); +static Eina_Bool _item_multi_select_down(Widget_Data *wd); +static Eina_Bool _item_single_select_up(Widget_Data *wd); +static Eina_Bool _item_single_select_down(Widget_Data *wd); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); +static Eina_Bool _deselect_all_items(Widget_Data *wd); + +#define ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, ...) \ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, __VA_ARGS__); \ + if (it->deleted) \ + { \ + ERR("ERROR: "#it" has been DELETED.\n"); \ + return __VA_ARGS__; \ + } + +static inline void +_elm_list_item_free(Elm_List_Item *it) +{ + evas_object_event_callback_del_full + (it->base.view, EVAS_CALLBACK_MOUSE_DOWN, _mouse_down, it); + evas_object_event_callback_del_full + (it->base.view, EVAS_CALLBACK_MOUSE_UP, _mouse_up, it); + evas_object_event_callback_del_full + (it->base.view, EVAS_CALLBACK_MOUSE_MOVE, _mouse_move, it); + + if (it->icon) + evas_object_event_callback_del_full + (it->icon, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, it->base.widget); + + if (it->end) + evas_object_event_callback_del_full + (it->end, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, it->base.widget); + + eina_stringshare_del(it->label); + + if (it->swipe_timer) ecore_timer_del(it->swipe_timer); + if (it->long_timer) ecore_timer_del(it->long_timer); + if (it->icon) evas_object_del(it->icon); + if (it->end) evas_object_del(it->end); + + elm_widget_item_del(it); +} + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (!wd->items) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + + Elm_List_Item *it = NULL; + Evas_Coord x = 0; + Evas_Coord y = 0; + Evas_Coord step_x = 0; + Evas_Coord step_y = 0; + Evas_Coord v_w = 0; + Evas_Coord v_h = 0; + Evas_Coord page_x = 0; + Evas_Coord page_y = 0; + + elm_smart_scroller_child_pos_get(wd->scr, &x, &y); + elm_smart_scroller_step_size_get(wd->scr, &step_x, &step_y); + elm_smart_scroller_page_size_get(wd->scr, &page_x, &page_y); + elm_smart_scroller_child_viewport_size_get(wd->scr, &v_w, &v_h); + + /* TODO: fix logic for horizontal mode */ + if ((!strcmp(ev->keyname, "Left")) || + (!strcmp(ev->keyname, "KP_Left"))) + { + if ((wd->h_mode) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_up(wd))) + || (_item_single_select_up(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + x -= step_x; + } + else if ((!strcmp(ev->keyname, "Right")) || + (!strcmp(ev->keyname, "KP_Right"))) + { + if ((wd->h_mode) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_down(wd))) + || (_item_single_select_down(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + x += step_x; + } + else if ((!strcmp(ev->keyname, "Up")) || + (!strcmp(ev->keyname, "KP_Up"))) + { + if ((!wd->h_mode) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_up(wd))) + || (_item_single_select_up(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + y -= step_y; + } + else if ((!strcmp(ev->keyname, "Down")) || + (!strcmp(ev->keyname, "KP_Down"))) + { + if ((!wd->h_mode) && + (((evas_key_modifier_is_set(ev->modifiers, "Shift")) && + (_item_multi_select_down(wd))) + || (_item_single_select_down(wd)))) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else + y += step_y; + } + else if ((!strcmp(ev->keyname, "Home")) || + (!strcmp(ev->keyname, "KP_Home"))) + { + it = eina_list_data_get(wd->items); + elm_list_item_bring_in(it); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "End")) || + (!strcmp(ev->keyname, "KP_End"))) + { + it = eina_list_data_get(eina_list_last(wd->items)); + elm_list_item_bring_in(it); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "Prior")) || + (!strcmp(ev->keyname, "KP_Prior"))) + { + if (wd->h_mode) + { + if (page_x < 0) + x -= -(page_x * v_w) / 100; + else + x -= page_x; + } + else + { + if (page_y < 0) + y -= -(page_y * v_h) / 100; + else + y -= page_y; + } + } + else if ((!strcmp(ev->keyname, "Next")) || + (!strcmp(ev->keyname, "KP_Next"))) + { + if (wd->h_mode) + { + if (page_x < 0) + x += -(page_x * v_w) / 100; + else + x += page_x; + } + else + { + if (page_y < 0) + y += -(page_y * v_h) / 100; + else + y += page_y; + } + } + else if (!strcmp(ev->keyname, "Escape")) + { + if (!_deselect_all_items(wd)) return EINA_FALSE; + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else return EINA_FALSE; + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + elm_smart_scroller_child_pos_set(wd->scr, x, y); + return EINA_TRUE; +} + +static Eina_Bool +_deselect_all_items(Widget_Data *wd) +{ + if (!wd->selected) return EINA_FALSE; + while(wd->selected) + elm_list_item_selected_set(wd->selected->data, EINA_FALSE); + + return EINA_TRUE; +} + +static Eina_Bool +_item_multi_select_up(Widget_Data *wd) +{ + if (!wd->selected) return EINA_FALSE; + if (!wd->multi) return EINA_FALSE; + + Elm_List_Item *prev = elm_list_item_prev(wd->last_selected_item); + if (!prev) return EINA_TRUE; + + if (elm_list_item_selected_get(prev)) + { + elm_list_item_selected_set(wd->last_selected_item, EINA_FALSE); + wd->last_selected_item = prev; + elm_list_item_show(wd->last_selected_item); + } + else + { + elm_list_item_selected_set(prev, EINA_TRUE); + elm_list_item_show(prev); + } + return EINA_TRUE; +} + +static Eina_Bool +_item_multi_select_down(Widget_Data *wd) +{ + if (!wd->selected) return EINA_FALSE; + if (!wd->multi) return EINA_FALSE; + + Elm_List_Item *next = elm_list_item_next(wd->last_selected_item); + if (!next) return EINA_TRUE; + + if (elm_list_item_selected_get(next)) + { + elm_list_item_selected_set(wd->last_selected_item, EINA_FALSE); + wd->last_selected_item = next; + elm_list_item_show(wd->last_selected_item); + } + else + { + elm_list_item_selected_set(next, EINA_TRUE); + elm_list_item_show(next); + } + return EINA_TRUE; +} + +static Eina_Bool +_item_single_select_up(Widget_Data *wd) +{ + Elm_List_Item *prev; + + if (!wd->selected) prev = eina_list_data_get(eina_list_last(wd->items)); + else prev = elm_list_item_prev(wd->last_selected_item); + + if (!prev) return EINA_FALSE; + + _deselect_all_items(wd); + + elm_list_item_selected_set(prev, EINA_TRUE); + elm_list_item_show(prev); + return EINA_TRUE; +} + +static Eina_Bool +_item_single_select_down(Widget_Data *wd) +{ + Elm_List_Item *next; + + if (!wd->selected) next = eina_list_data_get(wd->items); + else next = elm_list_item_next(wd->last_selected_item); + + if (!next) return EINA_FALSE; + + _deselect_all_items(wd); + + elm_list_item_selected_set(next, EINA_TRUE); + elm_list_item_show(next); + return EINA_TRUE; +} + +static void +_elm_list_process_deletions(Widget_Data *wd) +{ + Elm_List_Item *it; + + wd->walking++; // avoid nested deletion and also _sub_del() fix_items + + EINA_LIST_FREE(wd->to_delete, it) + { + elm_widget_item_pre_notify_del(it); + + wd->items = eina_list_remove_list(wd->items, it->node); + _elm_list_item_free(it); + } + + wd->walking--; +} + +static inline void +_elm_list_walk(Widget_Data *wd) +{ + if (wd->walking < 0) + { + ERR("ERROR: walking was negative. fixed!\n"); + wd->walking = 0; + } + wd->walking++; +} + +static inline void +_elm_list_unwalk(Widget_Data *wd) +{ + wd->walking--; + if (wd->walking < 0) + { + ERR("ERROR: walking became negative. fixed!\n"); + wd->walking = 0; + } + + if (wd->walking) + return; + + if (wd->to_delete) + _elm_list_process_deletions(wd); + + if (wd->fix_pending) + { + wd->fix_pending = EINA_FALSE; + _fix_items(wd->self); + _sizing_eval(wd->self); + } +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_List_Item *it; + Eina_List *n; + + if (!wd) return; + if (wd->walking) + ERR("ERROR: list deleted while walking.\n"); + + _elm_list_walk(wd); + EINA_LIST_FOREACH(wd->items, n, it) elm_widget_item_pre_notify_del(it); + _elm_list_unwalk(wd); + if (wd->to_delete) + ERR("ERROR: leaking nodes!\n"); + + EINA_LIST_FREE(wd->items, it) _elm_list_item_free(it); + eina_list_free(wd->selected); + free(wd); +} + +static void +_show_region_hook(void *data, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord x, y, w, h; + if (!wd) return; + elm_widget_show_region_get(obj, &x, &y, &w, &h); + elm_smart_scroller_child_region_set(wd->scr, x, y, w, h); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_disabled_get(obj)) + { + _signal_emit_hook(obj, "elm,state,disabled", "elm"); + elm_widget_scroll_freeze_push(obj); + elm_widget_scroll_hold_push(obj); + /* FIXME: if we get to have a way to only un-hilight items + * in the future, keeping them selected... */ + _deselect_all_items(wd); + } + else + { + _signal_emit_hook(obj, "elm,state,enabled", "elm"); + elm_widget_scroll_freeze_pop(obj); + elm_widget_scroll_hold_pop(obj); + } +} + +static void +_sizing_eval(Evas_Object *obj) +{ + + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + Evas_Coord vw, vh, minw, minh, maxw, maxh, w, h, vmw, vmh; + double xw, yw; + + evas_object_size_hint_min_get(wd->box, &minw, &minh); + evas_object_size_hint_max_get(wd->box, &maxw, &maxh); + evas_object_size_hint_weight_get(wd->box, &xw, &yw); + if (!wd->scr) return; + elm_smart_scroller_child_viewport_size_get(wd->scr, &vw, &vh); + if (xw > 0.0) + { + if ((minw > 0) && (vw < minw)) vw = minw; + else if ((maxw > 0) && (vw > maxw)) vw = maxw; + } + else if (minw > 0) vw = minw; + if (yw > 0.0) + { + if ((minh > 0) && (vh < minh)) vh = minh; + else if ((maxh > 0) && (vh > maxh)) vh = maxh; + } + else if (minh > 0) vh = minh; + evas_object_resize(wd->box, vw, vh); + w = -1; + h = -1; + edje_object_size_min_calc(elm_smart_scroller_edje_object_get(wd->scr), + &vmw, &vmh); + if (wd->scr_minw) w = vmw + minw; + if (wd->scr_minh) h = vmh + minh; + + evas_object_size_hint_max_get(obj, &maxw, &maxh); + if ((maxw > 0) && (w > maxw)) + w = maxw; + if ((maxh > 0) && (h > maxh)) + h = maxh; + + evas_object_size_hint_min_set(obj, w, h); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_add(elm_smart_scroller_edje_object_get(wd->scr), + emission, source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_del_full( + elm_smart_scroller_edje_object_get(wd->scr), + emission, source, func_cb, data); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_List_Item *it; + Eina_List *n; + + if (!wd) return; + if (wd->scr) + { + Evas_Object *edj; + const char *str; + + elm_smart_scroller_object_theme_set(obj, wd->scr, "list", "base", + elm_widget_style_get(obj)); +// edje_object_scale_set(wd->scr, elm_widget_scale_get(obj) * _elm_config->scale); + edj = elm_smart_scroller_edje_object_get(wd->scr); + str = edje_object_data_get(edj, "focus_highlight"); + if ((str) && (!strcmp(str, "on"))) + elm_widget_highlight_in_theme_set(obj, EINA_TRUE); + else + elm_widget_highlight_in_theme_set(obj, EINA_FALSE); + elm_object_style_set(wd->scr, elm_widget_style_get(obj)); + } + EINA_LIST_FOREACH(wd->items, n, it) + { + edje_object_scale_set(it->base.view, elm_widget_scale_get(obj) * _elm_config->scale); + it->fixed = 0; + } + _fix_items(obj); + _sizing_eval(obj); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->self, "elm,action,focus", "elm"); + evas_object_focus_set(wd->self, EINA_TRUE); + + if ((wd->selected) && (!wd->last_selected_item)) + wd->last_selected_item = eina_list_data_get(wd->selected); + } + else + { + edje_object_signal_emit(wd->self, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->self, EINA_FALSE); + } +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + _fix_items(data); + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + const Eina_List *l; + Elm_List_Item *it; + + if (!wd) return; + if (!sub) abort(); + if (sub == wd->scr) + wd->scr = NULL; + else + { + EINA_LIST_FOREACH(wd->items, l, it) + { + if ((sub == it->icon) || (sub == it->end)) + { + if (it->icon == sub) it->icon = NULL; + if (it->end == sub) it->end = NULL; + evas_object_event_callback_del_full + (sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, + obj); + if (!wd->walking) + { + _fix_items(obj); + _sizing_eval(obj); + } + else + wd->fix_pending = EINA_TRUE; + break; + } + } + } +} + +static void +_item_hilight(Elm_List_Item *it) +{ + Widget_Data *wd = elm_widget_data_get(it->base.widget); + const char *selectraise; + + if (!wd) return; + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (it->hilighted) return; + _elm_list_walk(wd); + + edje_object_signal_emit(it->base.view, "elm,state,selected", "elm"); + selectraise = edje_object_data_get(it->base.view, "selectraise"); + if ((selectraise) && (!strcmp(selectraise, "on"))) + evas_object_raise(it->base.view); + it->hilighted = EINA_TRUE; + + _elm_list_unwalk(wd); +} + +static void +_item_select(Elm_List_Item *it) +{ + Widget_Data *wd = elm_widget_data_get(it->base.widget); + + if (!wd) return; + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (it->selected) + { + if (wd->always_select) goto call; + return; + } + it->selected = EINA_TRUE; + wd->selected = eina_list_append(wd->selected, it); + call: + _elm_list_walk(wd); + + if (it->func) it->func((void *)it->base.data, it->base.widget, it); + evas_object_smart_callback_call(it->base.widget, "selected", it); + + _elm_list_unwalk(wd); + it->wd->last_selected_item = it; +} + +static void +_item_unselect(Elm_List_Item *it) +{ + Widget_Data *wd = elm_widget_data_get(it->base.widget); + const char *stacking, *selectraise; + + if (!wd) return; + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (!it->hilighted) return; + _elm_list_walk(wd); + + edje_object_signal_emit(it->base.view, "elm,state,unselected", "elm"); + stacking = edje_object_data_get(it->base.view, "stacking"); + selectraise = edje_object_data_get(it->base.view, "selectraise"); + if ((selectraise) && (!strcmp(selectraise, "on"))) + { + if ((stacking) && (!strcmp(stacking, "below"))) + evas_object_lower(it->base.view); + } + it->hilighted = EINA_FALSE; + if (it->selected) + { + it->selected = EINA_FALSE; + wd->selected = eina_list_remove(wd->selected, it); + evas_object_smart_callback_call(it->base.widget, "unselected", it); + } + + _elm_list_unwalk(wd); +} + +static Eina_Bool +_swipe_cancel(void *data) +{ + Elm_List_Item *it = data; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + + if (!wd) return ECORE_CALLBACK_CANCEL; + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, ECORE_CALLBACK_CANCEL); + wd->swipe = EINA_FALSE; + wd->movements = 0; + return ECORE_CALLBACK_RENEW; +} + +static void +_mouse_move(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_List_Item *it = data; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + Evas_Event_Mouse_Move *ev = event_info; + + if (!wd) return; + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + { + if (!wd->on_hold) + { + wd->on_hold = EINA_TRUE; + if (it->long_timer) + { + ecore_timer_del(it->long_timer); + it->long_timer = NULL; + } + if (!wd->wasselected) + _item_unselect(it); + } + if (wd->movements == SWIPE_MOVES) wd->swipe = EINA_TRUE; + else + { + wd->history[wd->movements].x = ev->cur.canvas.x; + wd->history[wd->movements].y = ev->cur.canvas.y; + if (abs((wd->history[wd->movements].x - wd->history[0].x)) > 40) + wd->swipe = EINA_TRUE; + else + wd->movements++; + } + } +} + +static void +_scroll_edge_left(void *data, Evas_Object *scr __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *obj = data; + evas_object_smart_callback_call(obj, "scroll,edge,left", NULL); +} + +static void +_scroll_edge_right(void *data, Evas_Object *scr __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *obj = data; + evas_object_smart_callback_call(obj, "scroll,edge,right", NULL); +} + +static void +_scroll_edge_top(void *data, Evas_Object *scr __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *obj = data; + evas_object_smart_callback_call(obj, "scroll,edge,top", NULL); +} + +static void +_scroll_edge_bottom(void *data, Evas_Object *scr __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *obj = data; + evas_object_smart_callback_call(obj, "scroll,edge,bottom", NULL); +} + +static Eina_Bool +_long_press(void *data) +{ + Elm_List_Item *it = data; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + + if (!wd) + goto end; + + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, ECORE_CALLBACK_CANCEL); + + it->long_timer = NULL; + + if (it->disabled) + goto end; + + wd->longpressed = EINA_TRUE; + evas_object_smart_callback_call(it->base.widget, "longpressed", it); + + end: + return ECORE_CALLBACK_CANCEL; +} + +static void +_swipe(Elm_List_Item *it) +{ + int i, sum = 0; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (!wd) return; + wd->swipe = EINA_FALSE; + for (i = 0; i < wd->movements; i++) + { + sum += wd->history[i].x; + if (abs(wd->history[0].y - wd->history[i].y) > 10) return; + } + + sum /= wd->movements; + if (abs(sum - wd->history[0].x) <= 10) return; + evas_object_smart_callback_call(it->base.widget, "swipe", it); +} + +static void +_mouse_down(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_List_Item *it = data; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + Evas_Event_Mouse_Down *ev = event_info; + + if (!wd) return; + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (ev->button != 1) return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) wd->on_hold = EINA_TRUE; + else wd->on_hold = EINA_FALSE; + if (wd->on_hold) return; + wd->wasselected = it->selected; + _item_hilight(it); + wd->longpressed = EINA_FALSE; + if (it->long_timer) ecore_timer_del(it->long_timer); + it->long_timer = ecore_timer_add(_elm_config->longpress_timeout, _long_press, it); + if (it->swipe_timer) ecore_timer_del(it->swipe_timer); + it->swipe_timer = ecore_timer_add(0.4, _swipe_cancel, it); + /* Always call the callbacks last - the user may delete our context! */ + if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK) + evas_object_smart_callback_call(it->base.widget, "clicked", it); + wd->swipe = EINA_FALSE; + wd->movements = 0; +} + +static void +_mouse_up(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_List_Item *it = data; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + Evas_Event_Mouse_Up *ev = event_info; + + if (!wd) return; + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (ev->button != 1) return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) wd->on_hold = EINA_TRUE; + else wd->on_hold = EINA_FALSE; + wd->longpressed = EINA_FALSE; + if (it->long_timer) + { + ecore_timer_del(it->long_timer); + it->long_timer = NULL; + } + if (it->swipe_timer) + { + ecore_timer_del(it->swipe_timer); + it->swipe_timer = NULL; + } + if (wd->on_hold) + { + if (wd->swipe) _swipe(data); + wd->on_hold = EINA_FALSE; + return; + } + if (wd->longpressed) + { + if (!wd->wasselected) _item_unselect(it); + wd->wasselected = 0; + return; + } + + if (it->disabled) + return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return; + + _elm_list_walk(wd); // watch out "return" before unwalk! + + if (wd->multi) + { + if (!it->selected) + { + _item_hilight(it); + _item_select(it); + } + else _item_unselect(it); + } + else + { + if (!it->selected) + { + while (wd->selected) + _item_unselect(wd->selected->data); + _item_hilight(it); + _item_select(it); + } + else + { + const Eina_List *l, *l_next; + Elm_List_Item *it2; + + EINA_LIST_FOREACH_SAFE(wd->selected, l, l_next, it2) + if (it2 != it) _item_unselect(it2); + _item_hilight(it); + _item_select(it); + } + } + + _elm_list_unwalk(wd); +} + +static Elm_List_Item * +_item_new(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_List_Item *it; + + if (!wd) return NULL; + it = elm_widget_item_new(obj, Elm_List_Item); + it->wd = wd; + it->label = eina_stringshare_add(label); + it->icon = icon; + it->end = end; + it->func = func; + it->base.data = data; + it->base.view = edje_object_add(evas_object_evas_get(obj)); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MOUSE_DOWN, + _mouse_down, it); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, it); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MOUSE_MOVE, + _mouse_move, it); + evas_object_size_hint_weight_set(it->base.view, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(it->base.view, EVAS_HINT_FILL, EVAS_HINT_FILL); + if (it->icon) + { + elm_widget_sub_object_add(obj, it->icon); + evas_object_event_callback_add(it->icon, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + } + if (it->end) + { + elm_widget_sub_object_add(obj, it->end); + evas_object_event_callback_add(it->end, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + } + return it; +} + +static void +_elm_list_mode_set_internal(Widget_Data *wd) +{ + if (!wd->scr) + return; + + if (wd->mode == ELM_LIST_LIMIT) + { + if (!wd->h_mode) + { + wd->scr_minw = EINA_TRUE; + wd->scr_minh = EINA_FALSE; + } + else + { + wd->scr_minw = EINA_FALSE; + wd->scr_minh = EINA_TRUE; + } + } + else if (wd->mode == ELM_LIST_EXPAND) + { + wd->scr_minw = EINA_TRUE; + wd->scr_minh = EINA_TRUE; + } + else + { + wd->scr_minw = EINA_FALSE; + wd->scr_minh = EINA_FALSE; + } + + _sizing_eval(wd->self); +} + +static void +_fix_items(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const Eina_List *l; + Elm_List_Item *it; + Evas_Coord minw[2] = { 0, 0 }, minh[2] = { 0, 0 }; + Evas_Coord mw, mh; + int i, redo = 0; + const char *style = elm_widget_style_get(obj); + const char *it_plain = wd->h_mode ? "h_item" : "item"; + const char *it_odd = wd->h_mode ? "h_item_odd" : "item_odd"; + const char *it_compress = wd->h_mode ? "h_item_compress" : "item_compress"; + const char *it_compress_odd = wd->h_mode ? "h_item_compress_odd" : "item_compress_odd"; + + if (!wd) return; + if (wd->walking) + { + wd->fix_pending = EINA_TRUE; + return; + } + + _elm_list_walk(wd); // watch out "return" before unwalk! + + EINA_LIST_FOREACH(wd->items, l, it) + { + if (it->deleted) continue; + if (it->icon) + { + evas_object_size_hint_min_get(it->icon, &mw, &mh); + if (mw > minw[0]) minw[0] = mw; + if (mh > minh[0]) minh[0] = mh; + } + if (it->end) + { + evas_object_size_hint_min_get(it->end, &mw, &mh); + if (mw > minw[1]) minw[1] = mw; + if (mh > minh[1]) minh[1] = mh; + } + } + + if ((minw[0] != wd->minw[0]) || (minw[1] != wd->minw[1]) || + (minw[0] != wd->minh[0]) || (minh[1] != wd->minh[1])) + { + wd->minw[0] = minw[0]; + wd->minw[1] = minw[1]; + wd->minh[0] = minh[0]; + wd->minh[1] = minh[1]; + redo = 1; + } + i = 0; + EINA_LIST_FOREACH(wd->items, l, it) + { + if (it->deleted) + continue; + + it->even = i & 0x1; + if ((it->even != it->is_even) || (!it->fixed) || (redo)) + { + const char *stacking; + + /* FIXME: separators' themes seem to be b0rked */ + if (it->is_separator) + _elm_theme_object_set(obj, it->base.view, "separator", + wd->h_mode ? "horizontal" : "vertical", + style); + else if (wd->mode == ELM_LIST_COMPRESS) + { + if (it->even) + _elm_theme_object_set(obj, it->base.view, "list", + it_compress, style); + else + _elm_theme_object_set(obj, it->base.view, "list", + it_compress_odd, style); + } + else + { + if (it->even) + _elm_theme_object_set(obj, it->base.view, "list", it_plain, + style); + else + _elm_theme_object_set(obj, it->base.view, "list", it_odd, + style); + } + stacking = edje_object_data_get(it->base.view, "stacking"); + if (stacking) + { + if (!strcmp(stacking, "below")) + evas_object_lower(it->base.view); + else if (!strcmp(stacking, "above")) + evas_object_raise(it->base.view); + } + edje_object_part_text_set(it->base.view, "elm.text", it->label); + + if ((!it->icon) && (minh[0] > 0)) + { + it->icon = evas_object_rectangle_add(evas_object_evas_get(it->base.view)); + evas_object_color_set(it->icon, 0, 0, 0, 0); + it->dummy_icon = EINA_TRUE; + } + if ((!it->end) && (minh[1] > 0)) + { + it->end = evas_object_rectangle_add(evas_object_evas_get(it->base.view)); + evas_object_color_set(it->end, 0, 0, 0, 0); + it->dummy_end = EINA_TRUE; + } + if (it->icon) + { + evas_object_size_hint_min_set(it->icon, minw[0], minh[0]); + evas_object_size_hint_max_set(it->icon, 99999, 99999); + edje_object_part_swallow(it->base.view, "elm.swallow.icon", it->icon); + } + if (it->end) + { + evas_object_size_hint_min_set(it->end, minw[1], minh[1]); + evas_object_size_hint_max_set(it->end, 99999, 99999); + edje_object_part_swallow(it->base.view, "elm.swallow.end", it->end); + } + if (!it->fixed) + { + // this may call up user and it may modify the list item + // but we're safe as we're flagged as walking. + // just don't process further + edje_object_message_signal_process(it->base.view); + if (it->deleted) + continue; + mw = mh = -1; + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + edje_object_size_min_restricted_calc(it->base.view, &mw, &mh, mw, mh); + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + evas_object_size_hint_min_set(it->base.view, mw, mh); + evas_object_show(it->base.view); + } + if ((it->selected) || (it->hilighted)) + { + const char *selectraise; + + // this may call up user and it may modify the list item + // but we're safe as we're flagged as walking. + // just don't process further + edje_object_signal_emit(it->base.view, "elm,state,selected", "elm"); + if (it->deleted) + continue; + + selectraise = edje_object_data_get(it->base.view, "selectraise"); + if ((selectraise) && (!strcmp(selectraise, "on"))) + evas_object_raise(it->base.view); + } + if (it->disabled) + edje_object_signal_emit(it->base.view, "elm,state,disabled", + "elm"); + + it->fixed = EINA_TRUE; + it->is_even = it->even; + } + i++; + } + + _elm_list_unwalk(wd); + + mw = 0; mh = 0; + evas_object_size_hint_min_get(wd->box, &mw, &mh); + + _elm_list_mode_set_internal(wd); +} + +static void +_hold_on(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->scr) + elm_smart_scroller_hold_set(wd->scr, EINA_TRUE); +} + +static void +_hold_off(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->scr) + elm_smart_scroller_hold_set(wd->scr, EINA_FALSE); +} + +static void +_freeze_on(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->scr) + elm_smart_scroller_freeze_set(wd->scr, EINA_TRUE); +} + +static void +_freeze_off(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->scr) + elm_smart_scroller_freeze_set(wd->scr, EINA_FALSE); +} + +static void +_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +/** + * Adds a list object. + * + * @param parent The parent object + * @return The created object or NULL upon failure + * + * @ingroup List + */ +EAPI Evas_Object * +elm_list_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + Evas_Coord minw, minh; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + wd->self = obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "list"); + elm_widget_type_set(obj, "list"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + elm_widget_event_hook_set(obj, _event_hook); + + wd->scr = elm_smart_scroller_add(e); + elm_smart_scroller_widget_set(wd->scr, obj); + _theme_hook(obj); + elm_widget_resize_object_set(obj, wd->scr); + evas_object_event_callback_add(wd->scr, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_size_min_calc(elm_smart_scroller_edje_object_get(wd->scr), &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_event_callback_add(obj, EVAS_CALLBACK_RESIZE, _resize, obj); + + elm_smart_scroller_bounce_allow_set(wd->scr, EINA_FALSE, + _elm_config->thumbscroll_bounce_enable); + + wd->box = elm_box_add(parent); + elm_box_homogenous_set(wd->box, 1); + evas_object_size_hint_weight_set(wd->box, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(wd->box, EVAS_HINT_FILL, 0.0); + elm_widget_on_show_region_hook_set(wd->box, _show_region_hook, obj); + elm_widget_sub_object_add(obj, wd->box); + elm_smart_scroller_child_set(wd->scr, wd->box); + evas_object_event_callback_add(wd->box, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + + evas_object_show(wd->box); + + wd->mode = ELM_LIST_SCROLL; + + evas_object_smart_callback_add(wd->scr, "edge,left", _scroll_edge_left, obj); + evas_object_smart_callback_add(wd->scr, "edge,right", _scroll_edge_right, obj); + evas_object_smart_callback_add(wd->scr, "edge,top", _scroll_edge_top, obj); + evas_object_smart_callback_add(wd->scr, "edge,bottom", _scroll_edge_bottom, obj); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + evas_object_smart_callback_add(obj, "scroll-hold-on", _hold_on, obj); + evas_object_smart_callback_add(obj, "scroll-hold-off", _hold_off, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-on", _freeze_on, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-off", _freeze_off, obj); + + _sizing_eval(obj); + return obj; +} + +/** + * Appends an item to the list object. + * + * @param obj The list object + * @param label The label of the list item + * @param icon The icon object to use for the left side of the item + * @param end The icon object to use for the right side of the item + * @param func The function to call when the item is clicked + * @param data The data to associate with the item for related callbacks + * + * @return The created item or NULL upon failure + * + * @ingroup List + */ +EAPI Elm_List_Item * +elm_list_item_append(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Elm_List_Item *it = _item_new(obj, label, icon, end, func, data); + + wd->items = eina_list_append(wd->items, it); + it->node = eina_list_last(wd->items); + elm_box_pack_end(wd->box, it->base.view); + return it; +} + +/** + * Prepends an item to the list object. + * + * @param obj The list object + * @param label The label of the list item + * @param icon The icon object to use for the left side of the item + * @param end The icon object to use for the right side of the item + * @param func The function to call when the item is clicked + * @param data The data to associate with the item for related callbacks + * + * @return The created item or NULL upon failure + * + * @ingroup List + */ +EAPI Elm_List_Item * +elm_list_item_prepend(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Elm_List_Item *it = _item_new(obj, label, icon, end, func, data); + + wd->items = eina_list_prepend(wd->items, it); + it->node = wd->items; + elm_box_pack_start(wd->box, it->base.view); + return it; +} + +/** + * Inserts an item into the list object before @p before. + * + * @param obj The list object + * @param before The list item to insert before + * @param label The label of the list item + * @param icon The icon object to use for the left side of the item + * @param end The icon object to use for the right side of the item + * @param func The function to call when the item is clicked + * @param data The data to associate with the item for related callbacks + * + * @return The created item or NULL upon failure + * + * @ingroup List + */ +EAPI Elm_List_Item * +elm_list_item_insert_before(Evas_Object *obj, Elm_List_Item *before, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data) +{ + Widget_Data *wd; + Elm_List_Item *it; + + EINA_SAFETY_ON_NULL_RETURN_VAL(before, NULL); + if (!before->node) return NULL; + ELM_LIST_ITEM_CHECK_DELETED_RETURN(before, NULL); + + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + wd = elm_widget_data_get(obj); + if (!wd) return NULL; + it = _item_new(obj, label, icon, end, func, data); + wd->items = eina_list_prepend_relative_list(wd->items, it, before->node); + it->node = before->node->prev; + elm_box_pack_before(wd->box, it->base.view, before->base.view); + return it; +} + +/** + * Inserts an item into the list object after @p after. + * + * @param obj The list object + * @param after The list item to insert after + * @param label The label of the list item + * @param icon The icon object to use for the left side of the item + * @param end The icon object to use for the right side of the item + * @param func The function to call when the item is clicked + * @param data The data to associate with the item for related callbacks + * + * @return The created item or NULL upon failure + * + * @ingroup List + */ +EAPI Elm_List_Item * +elm_list_item_insert_after(Evas_Object *obj, Elm_List_Item *after, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data) +{ + Widget_Data *wd; + Elm_List_Item *it; + + EINA_SAFETY_ON_NULL_RETURN_VAL(after, NULL); + if (!after->node) return NULL; + ELM_LIST_ITEM_CHECK_DELETED_RETURN(after, NULL); + + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + wd = elm_widget_data_get(obj); + if (!wd) return NULL; + it = _item_new(obj, label, icon, end, func, data); + wd->items = eina_list_append_relative_list(wd->items, it, after->node); + it->node = after->node->next; + elm_box_pack_after(wd->box, it->base.view, after->base.view); + return it; +} + +/** + * Insert a new item into the sorted list object. + * + * @param obj The list object + * @param label The label of the list item + * @param icon The icon object to use for the left side of the item + * @param end The icon object to use for the right side of the item + * @param func The function to call when the item is clicked + * @param data The data to associate with the item for related callbacks + * @param cmp_func The function called for the sort. + * + * @return The created item or NULL upon failure + * + * @ingroup List + */ +EAPI Elm_List_Item * +elm_list_item_sorted_insert(Evas_Object *obj, const char *label, Evas_Object *icon, Evas_Object *end, Evas_Smart_Cb func, const void *data, Eina_Compare_Cb cmp_func) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Elm_List_Item *it = _item_new(obj, label, icon, end, func, data); + Eina_List *l; + + wd->items = eina_list_sorted_insert(wd->items, cmp_func, it); + l = eina_list_data_find_list(wd->items, it); + l = eina_list_next(l); + if (!l) + { + it->node = eina_list_last(wd->items); + elm_box_pack_end(wd->box, it->base.view); + } + else + { + Elm_List_Item *before = eina_list_data_get(l); + it->node = before->node->prev; + elm_box_pack_before(wd->box, it->base.view, before->base.view); + } + return it; +} + +/** + * Clears a list of all items. + * + * @param obj The list object + * + * @ingroup List + */ +EAPI void +elm_list_clear(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_List_Item *it; + + if (!wd) return; + if (!wd->items) return; + + eina_list_free(wd->selected); + wd->selected = NULL; + + if (wd->walking > 0) + { + Eina_List *n; + + EINA_LIST_FOREACH(wd->items, n, it) + { + if (it->deleted) continue; + it->deleted = EINA_TRUE; + wd->to_delete = eina_list_append(wd->to_delete, it); + } + return; + } + + _elm_list_walk(wd); + + EINA_LIST_FREE(wd->items, it) + { + elm_widget_item_pre_notify_del(it); + _elm_list_item_free(it); + } + + _elm_list_unwalk(wd); + + _fix_items(obj); + _sizing_eval(obj); +} + +/** + * Starts the list. Call before running show() on the list object. + * + * @param obj The list object + * + * @ingroup List + */ +EAPI void +elm_list_go(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _fix_items(obj); +} + +/** + * Enables/disables the state of multi-select on the list object. + * + * @param obj The list object + * @param multi If true, multi-select is enabled + * + * @ingroup List + */ +EAPI void +elm_list_multi_select_set(Evas_Object *obj, Eina_Bool multi) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->multi = multi; +} + +/** + * Gets the state of multi-select on the list object. + * + * @param obj The list object + * @return If true, multi-select is enabled + * + * @ingroup List + */ +EAPI Eina_Bool +elm_list_multi_select_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->multi; +} + +/** + * Set which mode to use for the list with. + * + * @param obj The list object + * @param mode One of @c ELM_LIST_COMPRESS, @c ELM_LIST_SCROLL, @c + * ELM_LIST_LIMIT or @c ELM_LIST_EXPAND. + * + * @note Default value is @c ELM_LIST_SCROLL. At this mode, the list + * object won't set any of its size hints to inform how a possible + * container should resize it. Then, if it's not created as a "resize + * object", it might end with zero dimensions. The list will respect + * the container's geometry and, if any of its items won't fit into + * its transverse axis, one will be able to scroll it in that + * direction. @c ELM_LIST_COMPRESS is the same as the previous, except + * that it won't let one scroll in the transverse axis, on + * those cases (large items will get cropped). @c ELM_LIST_LIMIT will + * actually set a minimun size hint on the list object, so that + * containers may respect it (and resize itself to fit the child + * properly). More specifically, a minimum size hint will be set for + * its transverse axis, so that the largest item in that + * direction fits well. @c ELM_LIST_EXPAND, besides setting a minimum + * size on the transverse axis, just like the previous mode, will set + * a minimum size on the longitudinal axis too, trying to reserve + * space to all its children to be visible at a time. The last two + * modes can always have effects bounded by setting the list object's + * maximum size hints, though. + * + * @ingroup List + */ +EAPI void +elm_list_mode_set(Evas_Object *obj, Elm_List_Mode mode) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + if (wd->mode == mode) + return; + wd->mode = mode; + + _elm_list_mode_set_internal(wd); +} + +/** + * Get the mode the list is at. + * + * @param obj The list object + * @return mode One of @c ELM_LIST_COMPRESS, @c ELM_LIST_SCROLL or @c + * ELM_LIST_LIMIT (@c ELM_LIST_LAST on errors). + * + * @note see elm_list_mode_set() for more information. + * + * @ingroup List + */ +EAPI Elm_List_Mode +elm_list_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_LIST_LAST; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_LIST_LAST; + return wd->mode; +} + +/** + * Enables/disables horizontal mode of the list. + * + * @param obj The list object + * @param mode If true, horizontale mode is enabled + * + * @note Bounce options for the list will be reset to default values + * with this funcion. Re-call elm_list_bounce_set() once more after + * this one, if you had custom values. + * + * @ingroup List + */ +EAPI void +elm_list_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + + Widget_Data *wd; + Eina_Bool bounce = _elm_config->thumbscroll_bounce_enable; + + wd = elm_widget_data_get(obj); + if (!wd) + return; + + if (wd->h_mode == horizontal) + return; + + wd->h_mode = horizontal; + elm_box_horizontal_set(wd->box, horizontal); + + if (horizontal) + { + evas_object_size_hint_weight_set(wd->box, 0.0, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(wd->box, 0.0, EVAS_HINT_FILL); + elm_smart_scroller_bounce_allow_set(wd->scr, bounce, EINA_FALSE); + } + else + { + evas_object_size_hint_weight_set(wd->box, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(wd->box, EVAS_HINT_FILL, 0.0); + elm_smart_scroller_bounce_allow_set(wd->scr, EINA_FALSE, bounce); + } + + _elm_list_mode_set_internal(wd); +} + +/** + * Retrieve whether horizontal mode is enabled for a list. + * + * @param obj The list object + * @return @c EINA_TRUE, if horizontal mode is enabled and @c + * EINA_FALSE, otherwise. + * + * @note see elm_list_horizontal_set() for more information. + * + * @ingroup List + */ +EAPI Eina_Bool +elm_list_horizontal_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) + return EINA_FALSE; + + return wd->h_mode; +} + +/** + * Enables/disables the state of always_select, meaning that + * an item will always be selected. + * + * @param obj The list object + * @param always_select If true, always_select is enabled + * + * @ingroup List + */ +EAPI void +elm_list_always_select_mode_set(Evas_Object *obj, Eina_Bool always_select) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->always_select = always_select; +} + +/** + * Gets the state of always_select. + * See also elm_list_always_select_mode_set() + * + * @param obj The list object + * @return If true, always_select is enabled + * + * @ingroup List + */ +EAPI Eina_Bool +elm_list_always_select_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->always_select; +} + +/** + * Returns a list of all the list items. + * + * @param obj The list object + * @return An Eina_List* of the list items, or NULL on failure + * + * @ingroup List + */ +EAPI const Eina_List * +elm_list_items_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->items; +} + +/** + * Returns the currently selected list item. + * + * @param obj The list object + * @return The selected list item, or NULL on failure + * + * @ingroup List + */ +EAPI Elm_List_Item * +elm_list_selected_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (wd->selected) return wd->selected->data; + return NULL; +} + +/** + * Returns a list of the currently selected list items. + * + * @param obj The list object + * @return An Eina_List* of the selected list items, or NULL on failure + * + * @ingroup List + */ +EAPI const Eina_List * +elm_list_selected_items_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->selected; +} + +/** + * Sets if item is a separator. + * + * @param it The list item object + * @param setting + */ +EAPI void +elm_list_item_separator_set(Elm_List_Item *it, Eina_Bool setting) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + it->is_separator = !!setting; +} + +/** + * Returns EINA_TRUE if Elm_List_Item is a separator. + * + * @param it The list item object + */ +EAPI Eina_Bool +elm_list_item_separator_get(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, EINA_FALSE); + return it->is_separator; +} + + +/** + * Sets the selected state of @p it. + * + * @param it The list item + * @param selected Enables/disables the selected state + * + * @ingroup List + */ +EAPI void +elm_list_item_selected_set(Elm_List_Item *it, Eina_Bool selected) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + + Widget_Data *wd = elm_widget_data_get(it->base.widget); + if (!wd) return; + + selected = !!selected; + if (it->selected == selected) return; + + _elm_list_walk(wd); + + if (selected) + { + if (!wd->multi) + { + while (wd->selected) + _item_unselect(wd->selected->data); + } + _item_hilight(it); + _item_select(it); + } + else + _item_unselect(it); + + _elm_list_unwalk(wd); +} + +/** + * Gets the selected state of @p it. + * + * @param it The list item + * @return If true, the item is selected + * + * @ingroup List + */ +EAPI Eina_Bool +elm_list_item_selected_get(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, EINA_FALSE); + return it->selected; +} + +/** + * Brings @p it to the center of the list view. + * + * @param it The list item + * + * @ingroup List + */ +EAPI void +elm_list_item_show(Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + Widget_Data *wd = elm_widget_data_get(it->base.widget); + Evas_Coord bx, by, bw, bh; + Evas_Coord x, y, w, h; + + evas_object_geometry_get(wd->box, &bx, &by, &bw, &bh); + evas_object_geometry_get(it->base.view, &x, &y, &w, &h); + x -= bx; + y -= by; + if (wd->scr) + elm_smart_scroller_child_region_show(wd->scr, x, y, w, h); +} + +/** + * Bring in the given item + * + * This causes list to jump to the given item @p it and show it (by scrolling), + * if it is not fully visible. This may use animation to do so and take a + * period of time + * + * @param it The item + * + * @ingroup List + */ +EAPI void +elm_list_item_bring_in(Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + Widget_Data *wd = elm_widget_data_get(it->base.widget); + Evas_Coord bx, by, bw, bh; + Evas_Coord x, y, w, h; + + evas_object_geometry_get(wd->box, &bx, &by, &bw, &bh); + evas_object_geometry_get(it->base.view, &x, &y, &w, &h); + x -= bx; + y -= by; + if (wd->scr) + elm_smart_scroller_region_bring_in(wd->scr, x, y, w, h); +} + +/** + * Deletes item @p it from the list. + * + * @param it The list item to delete + * + * @ingroup List + */ +EAPI void +elm_list_item_del(Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + Widget_Data *wd = elm_widget_data_get(it->base.widget); + if (!wd) return; + + if (it->selected) _item_unselect(it); + + if (wd->walking > 0) + { + if (it->deleted) return; + it->deleted = EINA_TRUE; + wd->to_delete = eina_list_append(wd->to_delete, it); + return; + } + + wd->items = eina_list_remove_list(wd->items, it->node); + + _elm_list_walk(wd); + + elm_widget_item_pre_notify_del(it); + _elm_list_item_free(it); + + _elm_list_unwalk(wd); +} + +/** + * Set the function called when a list item is freed. + * + * @param it The item to set the callback on + * @param func The function called + * + * @ingroup List + */ +EAPI void +elm_list_item_del_cb_set(Elm_List_Item *it, Evas_Smart_Cb func) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + elm_widget_item_del_cb_set(it, func); +} + +/** + * Returns the data associated with the item. + * + * @param it The list item + * @return The data associated with @p it + * + * @ingroup List + */ +EAPI void * +elm_list_item_data_get(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, NULL); + return elm_widget_item_data_get(it); +} + +/** + * Returns the left side icon associated with the item. + * + * @param it The list item + * @return The left side icon associated with @p it + * + * @ingroup List + */ +EAPI Evas_Object * +elm_list_item_icon_get(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, NULL); + if (it->dummy_icon) return NULL; + return it->icon; +} + +/** + * Sets the left side icon associated with the item. + * + * Once the icon object is set, a previously set one will be deleted. + * You probably don't want, then, to have the same icon object set + * for more than one item of the list. + * + * @param it The list item + * @param icon The left side icon object to associate with @p it + * + * @ingroup List + */ +EAPI void +elm_list_item_icon_set(Elm_List_Item *it, Evas_Object *icon) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (it->icon == icon) return; + if ((it->dummy_icon) && (!icon)) return; + if (it->dummy_icon) + { + evas_object_del(it->icon); + it->dummy_icon = EINA_FALSE; + } + if (!icon) + { + icon = evas_object_rectangle_add(evas_object_evas_get(it->base.widget)); + evas_object_color_set(icon, 0, 0, 0, 0); + it->dummy_icon = EINA_TRUE; + } + if (it->icon) + { + evas_object_del(it->icon); + it->icon = NULL; + } + it->icon = icon; + if (it->base.view) + edje_object_part_swallow(it->base.view, "elm.swallow.icon", icon); +} + +/** + * Gets the right side icon associated with the item. + * + * @param it The list item + * @return The right side icon object associated with @p it + * + * @ingroup List + */ +EAPI Evas_Object * +elm_list_item_end_get(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, NULL); + if (it->dummy_end) return NULL; + return it->end; +} + +/** + * Sets the right side icon associated with the item. + * + * Once the icon object is set, a previously set one will be deleted. + * You probably don't want, then, to have the same icon object set + * for more than one item of the list. + * + * @param it The list item + * @param icon The right side icon object to associate with @p it + * + * @ingroup List + */ +EAPI void +elm_list_item_end_set(Elm_List_Item *it, Evas_Object *end) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (it->end == end) return; + if ((it->dummy_end) && (!end)) return; + if (it->dummy_end) + { + evas_object_del(it->end); + it->dummy_icon = EINA_FALSE; + } + if (!end) + { + end = evas_object_rectangle_add(evas_object_evas_get(it->base.widget)); + evas_object_color_set(end, 0, 0, 0, 0); + it->dummy_end = EINA_TRUE; + } + if (it->end) + { + evas_object_del(it->end); + it->end = NULL; + } + it->end = end; + if (it->base.view) + edje_object_part_swallow(it->base.view, "elm.swallow.end", end); +} + +/** + * Gets the base object of the item. + * + * @param it The list item + * @return The base object associated with @p it + * + * @ingroup List + */ +EAPI Evas_Object * +elm_list_item_base_get(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, NULL); + return it->base.view; +} + +/** + * Gets the label of the item. + * + * @param it The list item + * @return The label of @p it + * + * @ingroup List + */ +EAPI const char * +elm_list_item_label_get(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, NULL); + return it->label; +} + +/** + * Sets the label of the item. + * + * @param it The list item + * @param text The label of @p it + * + * @ingroup List + */ +EAPI void +elm_list_item_label_set(Elm_List_Item *it, const char *text) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + if (!eina_stringshare_replace(&it->label, text)) return; + if (it->base.view) + edje_object_part_text_set(it->base.view, "elm.text", it->label); +} + +/** + * Gets the item before @p it in the list. + * + * @param it The list item + * @return The item before @p it, or NULL on failure + * + * @ingroup List + */ +EAPI Elm_List_Item * +elm_list_item_prev(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, NULL); + if (it->node->prev) return it->node->prev->data; + else return NULL; +} + +/** + * Gets the item after @p it in the list. + * + * @param it The list item + * @return The item after @p it, or NULL on failure + * + * @ingroup List + */ +EAPI Elm_List_Item * +elm_list_item_next(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, NULL); + if (it->node->next) return it->node->next->data; + else return NULL; +} + +/** + * Set the text to be shown in the list item. + * + * @param item Target item + * @param text The text to set in the content + * + * Setup the text as tooltip to object. The item can have only one tooltip, + * so any previous tooltip data is removed. + * + * @ingroup List + */ +EAPI void +elm_list_item_tooltip_text_set(Elm_List_Item *item, const char *text) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item); + elm_widget_item_tooltip_text_set(item, text); +} + +/** + * Set the content to be shown in the tooltip item + * + * Setup the tooltip to item. The item can have only one tooltip, + * so any previous tooltip data is removed. @p func(with @p data) will + * be called every time that need show the tooltip and it should + * return a valid Evas_Object. This object is then managed fully by + * tooltip system and is deleted when the tooltip is gone. + * + * @param item the list item being attached a tooltip. + * @param func the function used to create the tooltip contents. + * @param data what to provide to @a func as callback data/context. + * @param del_cb called when data is not needed anymore, either when + * another callback replaces @func, the tooltip is unset with + * elm_list_item_tooltip_unset() or the owner @a item + * dies. This callback receives as the first parameter the + * given @a data, and @c event_info is the item. + * + * @ingroup List + */ +EAPI void +elm_list_item_tooltip_content_cb_set(Elm_List_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item); + elm_widget_item_tooltip_content_cb_set(item, func, data, del_cb); +} + +/** + * Unset tooltip from item + * + * @param item list item to remove previously set tooltip. + * + * Remove tooltip from item. The callback provided as del_cb to + * elm_list_item_tooltip_content_cb_set() will be called to notify + * it is not used anymore. + * + * @see elm_list_item_tooltip_content_cb_set() + * + * @ingroup List + */ +EAPI void +elm_list_item_tooltip_unset(Elm_List_Item *item) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item); + elm_widget_item_tooltip_unset(item); +} + +/** + * Sets a different style for this item tooltip. + * + * @note before you set a style you should define a tooltip with + * elm_list_item_tooltip_content_cb_set() or + * elm_list_item_tooltip_text_set() + * + * @param item list item with tooltip already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup List + */ +EAPI void +elm_list_item_tooltip_style_set(Elm_List_Item *item, const char *style) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item); + elm_widget_item_tooltip_style_set(item, style); +} + +/** + * Get the style for this item tooltip. + * + * @param item list item with tooltip already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a tooltip set, then NULL is returned. + * + * @ingroup List + */ +EAPI const char * +elm_list_item_tooltip_style_get(const Elm_List_Item *item) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item, NULL); + return elm_widget_item_tooltip_style_get(item); +} + +/** + * Set the cursor to be shown when mouse is over the list item + * + * @param item Target item + * @param cursor the cursor name to be used. + * + * @see elm_object_cursor_set() + * @ingroup List + */ +EAPI void +elm_list_item_cursor_set(Elm_List_Item *item, const char *cursor) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item); + elm_widget_item_cursor_set(item, cursor); +} + +/** + * Get the cursor to be shown when mouse is over the list item + * + * @param item list item with cursor already set. + * @return the cursor name. + * + * @ingroup List + */ +EAPI const char * +elm_list_item_cursor_get(const Elm_List_Item *item) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item, NULL); + return elm_widget_item_cursor_get(item); +} + +/** + * Unset the cursor to be shown when mouse is over the list item + * + * @param item Target item + * + * @see elm_object_cursor_unset() + * @ingroup List + */ +EAPI void +elm_list_item_cursor_unset(Elm_List_Item *item) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item); + elm_widget_item_cursor_unset(item); +} + +/** + * Sets a different style for this item cursor. + * + * @note before you set a style you should define a cursor with + * elm_list_item_cursor_set() + * + * @param item list item with cursor already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup List + */ +EAPI void +elm_list_item_cursor_style_set(Elm_List_Item *item, const char *style) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item); + elm_widget_item_cursor_style_set(item, style); +} + +/** + * Get the style for this item cursor. + * + * @param item list item with cursor already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a cursor set, then NULL is returned. + * + * @ingroup List + */ +EAPI const char * +elm_list_item_cursor_style_get(const Elm_List_Item *item) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item, NULL); + return elm_widget_item_cursor_style_get(item); +} + +/** + * Set if the cursor set should be searched on the theme or should use + * the provided by the engine, only. + * + * @note before you set if should look on theme you should define a cursor + * with elm_object_cursor_set(). By default it will only look for cursors + * provided by the engine. + * + * @param item widget item with cursor already set. + * @param engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. + * + * @ingroup List + */ +EAPI void +elm_list_item_cursor_engine_only_set(Elm_List_Item *item, Eina_Bool engine_only) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item); + elm_widget_item_cursor_engine_only_set(item, engine_only); +} + +/** + * Get the cursor engine only usage for this item cursor. + * + * @param item widget item with cursor already set. + * @return engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. If + * the object does not have a cursor set, then EINA_FALSE is returned. + * + * @ingroup List + */ +EAPI Eina_Bool +elm_list_item_cursor_engine_only_get(const Elm_List_Item *item) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(item, EINA_FALSE); + return elm_widget_item_cursor_engine_only_get(item); +} + +/** + * Set bounce mode + * + * This will enable or disable the scroller bounce mode for the list. See + * elm_scroller_bounce_set() for details + * + * @param obj The list object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup List + */ +EAPI void +elm_list_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->scr) + elm_smart_scroller_bounce_allow_set(wd->scr, h_bounce, v_bounce); +} + +/** + * Get the bounce mode + * + * @param obj The List object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup List + */ +EAPI void +elm_list_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_bounce_allow_get(wd->scr, h_bounce, v_bounce); +} + +/** + * Set the scrollbar policy + * + * This sets the scrollbar visibility policy for the given list scroller. + * ELM_SMART_SCROLLER_POLICY_AUTO means the scrollber is made visible if it + * is needed, and otherwise kept hidden. ELM_SMART_SCROLLER_POLICY_ON turns + * it on all the time, and ELM_SMART_SCROLLER_POLICY_OFF always keeps it off. + * This applies respectively for the horizontal and vertical scrollbars. + * + * @param obj The list object + * @param policy_h Horizontal scrollbar policy + * @param policy_v Vertical scrollbar policy + * + * @ingroup List + */ +EAPI void +elm_list_scroller_policy_set(Evas_Object *obj, Elm_Scroller_Policy policy_h, Elm_Scroller_Policy policy_v) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if ((policy_h >= ELM_SCROLLER_POLICY_LAST) || + (policy_v >= ELM_SCROLLER_POLICY_LAST)) + if (wd->scr) + elm_smart_scroller_policy_set(wd->scr, policy_h, policy_v); +} + +EAPI void +elm_list_scroller_policy_get(const Evas_Object *obj, Elm_Scroller_Policy *policy_h, Elm_Scroller_Policy *policy_v) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Smart_Scroller_Policy s_policy_h, s_policy_v; + if ((!wd) || (!wd->scr)) return; + elm_smart_scroller_policy_get(wd->scr, &s_policy_h, &s_policy_v); + if (policy_h) *policy_h = (Elm_Scroller_Policy) s_policy_h; + if (policy_v) *policy_v = (Elm_Scroller_Policy) s_policy_v; +} + +/** + * Sets the disabled/enabled state of a list item. + * + * A disabled item cannot be selected or unselected. It will also + * change its appearance (generally greyed out). This sets the + * disabled state (@c EINA_TRUE for disabled, @c EINA_FALSE for + * enabled). + * + * @param it The item + * @param disabled The disabled state + * + * @ingroup List + */ +EAPI void +elm_list_item_disabled_set(Elm_List_Item *it, Eina_Bool disabled) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it); + + if (it->disabled == disabled) + return; + + it->disabled = !!disabled; + + if (it->disabled) + edje_object_signal_emit(it->base.view, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(it->base.view, "elm,state,enabled", "elm"); +} + +/** + * Get the disabled/enabled state of a list item + * + * @param it The item + * @return The disabled state + * + * See elm_list_item_disabled_set(). + * + * @ingroup List + */ +EAPI Eina_Bool +elm_list_item_disabled_get(const Elm_List_Item *it) +{ + ELM_LIST_ITEM_CHECK_DELETED_RETURN(it, EINA_FALSE); + + return it->disabled; +} diff --git a/src/lib/elm_main.c b/src/lib/elm_main.c new file mode 100644 index 0000000..6237ec8 --- /dev/null +++ b/src/lib/elm_main.c @@ -0,0 +1,3430 @@ +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif + +#include /* dlopen,dlclose,etc */ + +#ifdef HAVE_CRT_EXTERNS_H +# include +#endif + +#ifdef HAVE_EVIL +# include +#endif + +#include +#include "elm_priv.h" + +#define SEMI_BROKEN_QUICKLAUNCH 1 + +static Elm_Version _version = { VMAJ, VMIN, VMIC, VREV }; +EAPI Elm_Version *elm_version = &_version; + +Eina_Bool +_elm_dangerous_call_check(const char *call) +{ + char buf[256]; + const char *eval; + + snprintf(buf, sizeof(buf), "%i.%i.%i.%i", VMAJ, VMIN, VMIC, VREV); + eval = getenv("ELM_NO_FINGER_WAGGLING"); + if ((eval) && (!strcmp(eval, buf))) + return 0; + printf("ELEMENTARY FINGER WAGGLE!!!!!!!!!!\n" + "\n" + " %s() used.\n" + "PLEASE see the API documentation for this function. This call\n" + "should almost never be used. Only in very special cases.\n" + "\n" + "To remove this warning please set the environment variable:\n" + " ELM_NO_FINGER_WAGGLING\n" + "To the value of the Elementary version + revision number. e.g.:\n" + " 1.2.5.40295\n" + "\n" + , + call); + return 1; +} + +/** + * @defgroup Start Getting Started + * + * To write an Elementary app, you can get started with the following: + * + * @code + * #include + * #ifndef ELM_LIB_QUICKLAUNCH + * EAPI int + * elm_main(int argc, char **argv) + * { + * // create window(s) here and do any application init + * elm_run(); // run main loop + * elm_shutdown(); // after mainloop finishes running, shutdown + * return 0; // exit 0 for exit code + * } + * #endif + * ELM_MAIN() + * @endcode + * + * To take full advantage of the quicklaunch architecture for launching + * processes as quickly as possible (saving time at startup time like + * connecting to X11, loading and linking shared libraries) you may want to + * use the following configure.in/configure.ac and Makefile.am and autogen.sh + * script to generate your files. It is assumed your application uses the + * main.c file for its code. + * + * configure.in/configure.ac: + * +@verbatim +AC_INIT(myapp, 0.0.0, myname@mydomain.com) +AC_PREREQ(2.52) +AC_CONFIG_SRCDIR(configure.in) + +AM_INIT_AUTOMAKE(1.6 dist-bzip2) +AM_CONFIG_HEADER(config.h) + +AC_C_BIGENDIAN +AC_ISC_POSIX +AC_PROG_CC +AM_PROG_CC_STDC +AC_HEADER_STDC +AC_C_CONST + +AC_LIBTOOL_WIN32_DLL +define([AC_LIBTOOL_LANG_CXX_CONFIG], [:])dnl +define([AC_LIBTOOL_LANG_F77_CONFIG], [:])dnl +AC_PROG_LIBTOOL + +PKG_CHECK_MODULES([ELEMENTARY], elementary) + +AC_OUTPUT(Makefile) +@endverbatim + * + * Makefile.am: + * +@verbatim +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +INCLUDES = -I$(top_srcdir) @ELEMENTARY_CFLAGS@ + +bin_PROGRAMS = myapp +myapp_LTLIBRARIES = myapp.la + +myappdir = $(libdir) + +myapp_la_SOURCES = main.c +myapp_la_LIBADD = @ELEMENTARY_LIBS@ +myapp_la_CFLAGS = +myapp_la_LDFLAGS = -module -avoid-version -no-undefined + +myapp_SOURCES = main.c +myapp_LDADD = @ELEMENTARY_LIBS@ +myapp_CFLAGS = -DELM_LIB_QUICKLAUNCH=1 +@endverbatim + * + * autogen.sh: + * +@verbatim +#!/bin/sh +rm -rf autom4te.cache +rm -f aclocal.m4 ltmain.sh +rm -rf m4 +mkdir m4 + +touch README +echo "Running aclocal..." ; aclocal $ACLOCAL_FLAGS -I m4 || exit 1 +echo "Running autoheader..." ; autoheader || exit 1 +echo "Running autoconf..." ; autoconf || exit 1 +echo "Running libtoolize..." ; (libtoolize --copy --automake || glibtoolize --automake) || exit 1 +echo "Running automake..." ; automake --add-missing --copy --gnu || exit 1 + +if [ -z "$NOCONFIGURE" ]; then + ./configure "$@" +fi +@endverbatim + * + * To gnerate all the things needed to bootstrap just run: + * +@verbatim +./autogen.sh +@endverbatim + * + * This will generate Makefile.in's, the confgure script and everything else. + * After this it works like all normal autotools projects: +@verbatim +./configure +make +sudo make install +@endverbatim + * + * Note sudo was assumed to get root permissions, as this would install in + * /usr/local which is system-owned. Ue any way you like to gain root, or + * specify a different prefix with configure: + * +@verbatim +./confiugre --prefix=$HOME/mysoftware +@endverbatim + * + * Also remember that autotools buys you some useful commands like: +@verbatim +make uninstall +@endverbatim + * + * This uninstalls the software after it was installed with "make install". + * It is very useful to clear up what you built if you wish to clean the + * system. + * +@verbatim +make distcheck +@endverbatim + * + * This firstly checks if your build tree is "clean" and ready for + * distribution. It also builds a tarball (myapp-0.0.0.tar.gz) that is + * ready to upload and distribute to the world, that contains the generated + * Makefile.in's and configure script. The users do not need to run + * autogen.sh - just configure and on. They don't need autotools installed. + * This tarball also builds cleanly, has all the sources it needs to build + * included (that is sources for your application, not libraries it depends + * on like Elementary). It builds cleanly in a buildroot and does not + * contain any files that are temporarily generated like binaries and other + * build-gnerated files, so the tarball is clean, and no need to worry + * about cleaning up your tree before packaging. + * +@verbatim +make clean +@endverbatim + * + * This cleans up all build files (binaries, objects etc.) from the tree. + * +@verbatim +make distclean +@endverbatim + * + * This cleans out all files from the build and from configure's output too. + * +@verbatim +make maintainer-clean +@endverbatim + * + * This deletes all the files autogen.sh will produce so the tree is clean + * to be put into a revision-control system (like CVS, SVN or GIT for example). + * + * The above will build a library - libmyapp.so and install in the target + * library directory (default is /usr/local/lib). You will also get a + * myapp.a and myapp.la - these are useless and can be deleted. Libtool likes + * to generate these all the time. You will also get a binary in the target + * binary directory (default is /usr/local/bin). This is a "debug binary". + * This will run and dlopen() the myapp.so and then jump to it's elm_main + * function. This allows for easy debugging with GDB and Valgrind. When you + * are ready to go to production do the following: + * + * 1. delete the myapp binary. i.e. rm /usr/local/bin/myapp + * + * 2. symlink the myapp binary to elementary_run (supplied by elementary). + * i.e. ln -s elmentary_run /usr/local/bin/myapp + * + * 3. run elementary_quicklaunch as part of your graphical login session and + * keep it running. + * + * This will man elementary_quicklaunch does pre-initialization before the + * application needs to be run, saving the effort at the time the application + * is needed, thus speeding up the time it takes to appear. + * + * If you don't want to use the quicklaunch infrastructure (which is + * optional), you can execute the old fashioned way by just running the + * myapp binary loader than will load the myapp.so for you, or you can + * remove the split-file binary and put it into one binary as things always + * have been with the following configure.in/configure.ac and Makfile.am + * files: + * + * configure.in/configure.ac: + * +@verbatim +AC_INIT(myapp, 0.0.0, myname@mydomain.com) +AC_PREREQ(2.52) +AC_CONFIG_SRCDIR(configure.in) + +AM_INIT_AUTOMAKE(1.6 dist-bzip2) +AM_CONFIG_HEADER(config.h) + +AC_C_BIGENDIAN +AC_ISC_POSIX +AC_PROG_CC +AM_PROG_CC_STDC +AC_HEADER_STDC +AC_C_CONST + +PKG_CHECK_MODULES([ELEMENTARY], elementary) + +AC_OUTPUT(Makefile) +@endverbatim + * + * Makefile.am: + * +@verbatim +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +INCLUDES = -I$(top_srcdir) @ELEMENTARY_CFLAGS@ + +bin_PROGRAMS = myapp + +myapp_SOURCES = main.c +myapp_LDADD = @ELEMENTARY_LIBS@ +myapp_CFLAGS = +@endverbatim + * + * Notice that they are the same as before, just with libtool and library + * building sections removed. Both ways work for building elementary + * applications. It is up to you to decide what is best for you. If you just + * follow the template above, you can do it both ways and can decide at build + * time. The more advanced of you may suggest making it a configure option. + * That is perfectly valid, but has been left out here for simplicity, as our + * aim to have an Elementary (and EFL) tutorial, not an autoconf & automake + * document. + * + */ + +static Eina_Bool _elm_signal_exit(void *data, + int ev_type, + void *ev); + +char *_elm_appname = NULL; +const char *_elm_data_dir = NULL; +const char *_elm_lib_dir = NULL; +int _elm_log_dom = -1; + +EAPI int ELM_EVENT_POLICY_CHANGED = 0; + +static int _elm_init_count = 0; +static int _elm_sub_init_count = 0; +static int _elm_ql_init_count = 0; +static int _elm_policies[ELM_POLICY_LAST]; +static Ecore_Event_Handler *_elm_exit_handler = NULL; +static Eina_Bool quicklaunch_on = 0; + +static Eina_Bool +_elm_signal_exit(void *data __UNUSED__, + int ev_type __UNUSED__, + void *ev __UNUSED__) +{ + elm_exit(); + return ECORE_CALLBACK_PASS_ON; +} + +void +_elm_rescale(void) +{ + edje_scale_set(_elm_config->scale); + _elm_win_rescale(NULL, EINA_FALSE); +} + +/** + * @defgroup General General + */ + +/** + * Inititalise Elementary + * + * @return The init counter value. + * + * This call is exported only for use by the ELM_MAIN() macro. There is no + * need to use this if you use this macro (which is highly advisable). + * @ingroup General + */ +EAPI int +elm_init(int argc, + char **argv) +{ + _elm_init_count++; + if (_elm_init_count > 1) return _elm_init_count; + elm_quicklaunch_init(argc, argv); + elm_quicklaunch_sub_init(argc, argv); + return _elm_init_count; +} + +/** + * Shut down Elementary + * + * @return The init counter value. + * + * This should be called at the end of your application just before it ceases + * to do any more processing. This will clean up any permanent resources your + * application may have allocated via Elementary that would otherwise persist + * on an exit without this call. + * @ingroup General + */ +EAPI int +elm_shutdown(void) +{ + _elm_init_count--; + if (_elm_init_count > 0) return _elm_init_count; + elm_quicklaunch_sub_shutdown(); + elm_quicklaunch_shutdown(); + return _elm_init_count; +} + +#ifdef ELM_EDBUS +static int _elm_need_e_dbus = 0; +#endif +EAPI Eina_Bool +elm_need_e_dbus(void) +{ +#ifdef ELM_EDBUS + if (_elm_need_e_dbus++) return EINA_TRUE; + e_dbus_init(); + return EINA_TRUE; +#else + return EINA_FALSE; +#endif +} + +static void +_elm_unneed_e_dbus(void) +{ +#ifdef ELM_EDBUS + if (--_elm_need_e_dbus) return; + + _elm_need_e_dbus = 0; + e_dbus_shutdown(); +#endif +} + +#ifdef ELM_EFREET +static int _elm_need_efreet = 0; +#endif +EAPI Eina_Bool +elm_need_efreet(void) +{ +#ifdef ELM_EFREET + if (_elm_need_efreet++) return EINA_TRUE; + efreet_init(); + efreet_mime_init(); + efreet_trash_init(); + /* + { + Eina_List **list; + + list = efreet_icon_extra_list_get(); + if (list) + { + e_user_dir_concat_static(buf, "icons"); + *list = eina_list_prepend(*list, (void *)eina_stringshare_add(buf)); + e_prefix_data_concat_static(buf, "data/icons"); + *list = eina_list_prepend(*list, (void *)eina_stringshare_add(buf)); + } + } + */ + return EINA_TRUE; +#else + return EINA_FALSE; +#endif +} + +static void +_elm_unneed_efreet(void) +{ +#ifdef ELM_EFREET + if (--_elm_need_efreet) return; + + _elm_need_efreet = 0; + efreet_trash_shutdown(); + efreet_mime_shutdown(); + efreet_shutdown(); +#endif +} + +EAPI void +elm_quicklaunch_mode_set(Eina_Bool ql_on) +{ + quicklaunch_on = ql_on; +} + +EAPI Eina_Bool +elm_quicklaunch_mode_get(void) +{ + return quicklaunch_on; +} + +EAPI int +elm_quicklaunch_init(int argc, + char **argv) +{ + char buf[PATH_MAX], *s; + + _elm_ql_init_count++; + if (_elm_ql_init_count > 1) return _elm_ql_init_count; + eina_init(); + _elm_log_dom = eina_log_domain_register("elementary", EINA_COLOR_LIGHTBLUE); + if (!_elm_log_dom) + { + EINA_LOG_ERR("could not register elementary log domain."); + _elm_log_dom = EINA_LOG_DOMAIN_GLOBAL; + } + + eet_init(); + ecore_init(); + ecore_app_args_set(argc, (const char **)argv); + + memset(_elm_policies, 0, sizeof(_elm_policies)); + if (!ELM_EVENT_POLICY_CHANGED) + ELM_EVENT_POLICY_CHANGED = ecore_event_type_new(); + + ecore_file_init(); + + _elm_exit_handler = ecore_event_handler_add(ECORE_EVENT_SIGNAL_EXIT, _elm_signal_exit, NULL); + + if (argv) _elm_appname = strdup(ecore_file_file_get(argv[0])); + + if (!_elm_data_dir) + { + s = getenv("ELM_DATA_DIR"); + _elm_data_dir = eina_stringshare_add(s); + } + if (!_elm_data_dir) + { + s = getenv("ELM_PREFIX"); + if (s) + { + snprintf(buf, sizeof(buf), "%s/share/elementary", s); + _elm_data_dir = eina_stringshare_add(buf); + } + } + if (!_elm_lib_dir) + { + s = getenv("ELM_LIB_DIR"); + _elm_lib_dir = eina_stringshare_add(s); + } + if (!_elm_lib_dir) + { + s = getenv("ELM_PREFIX"); + if (s) + { + snprintf(buf, sizeof(buf), "%s/lib", s); + _elm_lib_dir = eina_stringshare_add(buf); + } + } +#ifdef HAVE_DLADDR + if ((!_elm_data_dir) || (!_elm_lib_dir)) + { + Dl_info elementary_dl; + // libelementary.so/../../share/elementary/ + if (dladdr(elm_init, &elementary_dl)) + { + char *dir, *dir2; + + dir = ecore_file_dir_get(elementary_dl.dli_fname); + if (dir) + { + if (!_elm_lib_dir) + { + if (ecore_file_is_dir(dir)) + _elm_lib_dir = eina_stringshare_add(dir); + } + if (!_elm_data_dir) + { + dir2 = ecore_file_dir_get(dir); + if (dir2) + { + snprintf(buf, sizeof(buf), "%s/share/elementary", dir2); + if (ecore_file_is_dir(buf)) + _elm_data_dir = eina_stringshare_add(buf); + free(dir2); + } + } + free(dir); + } + } + } +#endif + if (!_elm_data_dir) + _elm_data_dir = eina_stringshare_add(PACKAGE_DATA_DIR); + if (!_elm_data_dir) + _elm_data_dir = eina_stringshare_add("/"); + if (!_elm_lib_dir) + _elm_lib_dir = eina_stringshare_add(PACKAGE_LIB_DIR); + if (!_elm_lib_dir) + _elm_lib_dir = eina_stringshare_add("/"); + + _elm_config_init(); + return _elm_ql_init_count; +} + +EAPI int +elm_quicklaunch_sub_init(int argc, + char **argv) +{ + _elm_sub_init_count++; + if (_elm_sub_init_count > 1) return _elm_sub_init_count; + if (quicklaunch_on) + { +#ifdef SEMI_BROKEN_QUICKLAUNCH + return _elm_sub_init_count; +#endif + } + if (!quicklaunch_on) + { + ecore_app_args_set(argc, (const char **)argv); + evas_init(); + edje_init(); + _elm_module_init(); + _elm_config_sub_init(); +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_X11) || + ENGINE_COMPARE(ELM_SOFTWARE_16_X11) || + ENGINE_COMPARE(ELM_XRENDER_X11) || + ENGINE_COMPARE(ELM_OPENGL_X11)) +#undef ENGINE_COMPARE + { +#ifdef HAVE_ELEMENTARY_X + ecore_x_init(NULL); +#endif + } + ecore_evas_init(); // FIXME: check errors + ecore_imf_init(); + } + return _elm_sub_init_count; +} + +EAPI int +elm_quicklaunch_sub_shutdown(void) +{ + _elm_sub_init_count--; + if (_elm_sub_init_count > 0) return _elm_sub_init_count; + if (quicklaunch_on) + { +#ifdef SEMI_BROKEN_QUICKLAUNCH + return _elm_sub_init_count; +#endif + } + if (!quicklaunch_on) + { + _elm_win_shutdown(); + _elm_module_shutdown(); + ecore_imf_shutdown(); + ecore_evas_shutdown(); +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_X11) || + ENGINE_COMPARE(ELM_SOFTWARE_16_X11) || + ENGINE_COMPARE(ELM_XRENDER_X11) || + ENGINE_COMPARE(ELM_OPENGL_X11)) +#undef ENGINE_COMPARE + { +#ifdef HAVE_ELEMENTARY_X + ecore_x_disconnect(); +#endif + } +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_X11) || + ENGINE_COMPARE(ELM_SOFTWARE_16_X11) || + ENGINE_COMPARE(ELM_XRENDER_X11) || + ENGINE_COMPARE(ELM_OPENGL_X11) || + ENGINE_COMPARE(ELM_SOFTWARE_SDL) || + ENGINE_COMPARE(ELM_SOFTWARE_16_SDL) || + ENGINE_COMPARE(ELM_OPENGL_SDL) || + ENGINE_COMPARE(ELM_SOFTWARE_WIN32) || + ENGINE_COMPARE(ELM_SOFTWARE_16_WINCE)) +#undef ENGINE_COMPARE + evas_cserve_disconnect(); + edje_shutdown(); + evas_shutdown(); + } + return _elm_sub_init_count; +} + +EAPI int +elm_quicklaunch_shutdown(void) +{ + _elm_ql_init_count--; + if (_elm_ql_init_count > 0) return _elm_ql_init_count; + eina_stringshare_del(_elm_data_dir); + _elm_data_dir = NULL; + eina_stringshare_del(_elm_lib_dir); + _elm_lib_dir = NULL; + + free(_elm_appname); + _elm_appname = NULL; + + _elm_config_shutdown(); + + ecore_event_handler_del(_elm_exit_handler); + _elm_exit_handler = NULL; + + _elm_theme_shutdown(); + _elm_unneed_efreet(); + _elm_unneed_e_dbus(); + _elm_unneed_ethumb(); + ecore_file_shutdown(); + ecore_shutdown(); + eet_shutdown(); + + if ((_elm_log_dom > -1) && (_elm_log_dom != EINA_LOG_DOMAIN_GLOBAL)) + { + eina_log_domain_unregister(_elm_log_dom); + _elm_log_dom = -1; + } + + _elm_widget_type_clear(); + + eina_shutdown(); + return _elm_ql_init_count; +} + +EAPI void +elm_quicklaunch_seed(void) +{ +#ifndef SEMI_BROKEN_QUICKLAUNCH + if (quicklaunch_on) + { + Evas_Object *win, *bg, *bt; + + win = elm_win_add(NULL, "seed", ELM_WIN_BASIC); + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_show(bg); + bt = elm_button_add(win); + elm_button_label_set(bt, " abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789~-_=+\\|]}[{;:'\",<.>/?"); + elm_win_resize_object_add(win, bt); + ecore_main_loop_iterate(); + evas_object_del(win); + ecore_main_loop_iterate(); +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_X11) || + ENGINE_COMPARE(ELM_SOFTWARE_16_X11) || + ENGINE_COMPARE(ELM_XRENDER_X11) || + ENGINE_COMPARE(ELM_OPENGL_X11)) +#undef ENGINE_COMPARE + { +# ifdef HAVE_ELEMENTARY_X + ecore_x_sync(); +# endif + } + ecore_main_loop_iterate(); + } +#endif +} + +static void *qr_handle = NULL; +static int (*qr_main)(int argc, + char **argv) = NULL; + +EAPI Eina_Bool +elm_quicklaunch_prepare(int argc __UNUSED__, + char **argv) +{ +#ifdef HAVE_FORK + char *exe = elm_quicklaunch_exe_path_get(argv[0]); + if (!exe) + { + ERR("requested quicklaunch binary '%s' does not exist\n", argv[0]); + return EINA_FALSE; + } + else + { + char *exe2, *p; + char *exename; + + exe2 = malloc(strlen(exe) + 1 + 10); + strcpy(exe2, exe); + p = strrchr(exe2, '/'); + if (p) p++; + else p = exe2; + exename = alloca(strlen(p) + 1); + strcpy(exename, p); + *p = 0; + strcat(p, "../lib/"); + strcat(p, exename); + strcat(p, ".so"); + if (!access(exe2, R_OK | X_OK)) + { + free(exe); + exe = exe2; + } + else + free(exe2); + } + qr_handle = dlopen(exe, RTLD_NOW | RTLD_GLOBAL); + if (!qr_handle) + { + fprintf(stderr, "dlerr: %s\n", dlerror()); + WRN("dlopen('%s') failed: %s", exe, dlerror()); + free(exe); + return EINA_FALSE; + } + INF("dlopen('%s') = %p", exe, qr_handle); + qr_main = dlsym(qr_handle, "elm_main"); + INF("dlsym(%p, 'elm_main') = %p", qr_handle, qr_main); + if (!qr_main) + { + WRN("not quicklauncher capable: no elm_main in '%s'", exe); + dlclose(qr_handle); + qr_handle = NULL; + free(exe); + return EINA_FALSE; + } + free(exe); + return EINA_TRUE; +#else + return EINA_FALSE; + (void)argv; +#endif +} + +#ifdef HAVE_FORK +static void +save_env(void) +{ + int i, size; + extern char **environ; + char **oldenv, **p; + + oldenv = environ; + + for (i = 0, size = 0; environ[i]; i++) + size += strlen(environ[i]) + 1; + + p = malloc((i + 1) * sizeof(char *)); + if (!p) return; + + environ = p; + + for (i = 0; oldenv[i]; i++) + environ[i] = strdup(oldenv[i]); + environ[i] = NULL; +} + +#endif + +EAPI Eina_Bool +elm_quicklaunch_fork(int argc, + char **argv, + char *cwd, + void (postfork_func) (void *data), + void *postfork_data) +{ +#ifdef HAVE_FORK + pid_t child; + int ret; + int real_argc; + char **real_argv; + + // FIXME: + // need to accept current environment from elementary_run + if (!qr_main) + { + int i; + char **args; + + child = fork(); + if (child > 0) return EINA_TRUE; + else if (child < 0) + { + perror("could not fork"); + return EINA_FALSE; + } + setsid(); + if (chdir(cwd) != 0) + perror("could not chdir"); + args = alloca((argc + 1) * sizeof(char *)); + for (i = 0; i < argc; i++) args[i] = argv[i]; + args[argc] = NULL; + WRN("%s not quicklaunch capable, fallback...", argv[0]); + execvp(argv[0], args); + ERR("failed to execute '%s': %s", argv[0], strerror(errno)); + exit(-1); + } + child = fork(); + if (child > 0) return EINA_TRUE; + else if (child < 0) + { + perror("could not fork"); + return EINA_FALSE; + } + if (postfork_func) postfork_func(postfork_data); + + if (quicklaunch_on) + { +#ifdef SEMI_BROKEN_QUICKLAUNCH + ecore_app_args_set(argc, (const char **)argv); + evas_init(); + edje_init(); + _elm_config_sub_init(); +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_X11) || + ENGINE_COMPARE(ELM_SOFTWARE_16_X11) || + ENGINE_COMPARE(ELM_XRENDER_X11) || + ENGINE_COMPARE(ELM_OPENGL_X11)) +#undef ENGINE_COMPARE + { +# ifdef HAVE_ELEMENTARY_X + ecore_x_init(NULL); +# endif + } + ecore_evas_init(); // FIXME: check errors + ecore_imf_init(); + _elm_module_init(); +#endif + } + + setsid(); + if (chdir(cwd) != 0) + perror("could not chdir"); + // FIXME: this is very linux specific. it changes argv[0] of the process + // so ps etc. report what you'd expect. for other unixes and os's this + // may just not work + save_env(); + if (argv) + { + char *lastarg, *p; + + ecore_app_args_get(&real_argc, &real_argv); + lastarg = real_argv[real_argc - 1] + strlen(real_argv[real_argc - 1]); + for (p = real_argv[0]; p < lastarg; p++) *p = 0; + strcpy(real_argv[0], argv[0]); + } + ecore_app_args_set(argc, (const char **)argv); + ret = qr_main(argc, argv); + exit(ret); + return EINA_TRUE; +#else + return EINA_FALSE; + (void)argc; + (void)argv; + (void)cwd; + (void)postfork_func; + (void)postfork_data; +#endif +} + +EAPI void +elm_quicklaunch_cleanup(void) +{ +#ifdef HAVE_FORK + if (qr_handle) + { + dlclose(qr_handle); + qr_handle = NULL; + qr_main = NULL; + } +#endif +} + +EAPI int +elm_quicklaunch_fallback(int argc, + char **argv) +{ + int ret; + elm_quicklaunch_init(argc, argv); + elm_quicklaunch_sub_init(argc, argv); + elm_quicklaunch_prepare(argc, argv); + ret = qr_main(argc, argv); + exit(ret); + return ret; +} + +EAPI char * +elm_quicklaunch_exe_path_get(const char *exe) +{ + static char *path = NULL; + static Eina_List *pathlist = NULL; + const char *pathitr; + const Eina_List *l; + char buf[PATH_MAX]; + if (exe[0] == '/') return strdup(exe); + if ((exe[0] == '.') && (exe[1] == '/')) return strdup(exe); + if ((exe[0] == '.') && (exe[1] == '.') && (exe[2] == '/')) return strdup(exe); + if (!path) + { + const char *p, *pp; + char *buf2; + path = getenv("PATH"); + buf2 = alloca(strlen(path) + 1); + p = path; + pp = p; + for (;; ) + { + if ((*p == ':') || (!*p)) + { + int len; + + len = p - pp; + strncpy(buf2, pp, len); + buf2[len] = 0; + pathlist = eina_list_append(pathlist, eina_stringshare_add(buf2)); + if (!*p) break; + p++; + pp = p; + } + else + { + if (!*p) break; + p++; + } + } + } + EINA_LIST_FOREACH(pathlist, l, pathitr) + { + snprintf(buf, sizeof(buf), "%s/%s", pathitr, exe); + if (!access(buf, R_OK | X_OK)) return strdup(buf); + } + return NULL; +} + +/** + * Run the main loop + * + * This call should be called just after all initialization is complete. This + * function will not return until elm_exit() is called. It will keep looping + * running the main event/processing loop for Elementary. + * @ingroup General + */ +EAPI void +elm_run(void) +{ + ecore_main_loop_begin(); +} + +/** + * Exit the main loop + * + * If this call is called, it will flag the main loop to cease processing and + * return back to its parent function. + * @ingroup General + */ +EAPI void +elm_exit(void) +{ + ecore_main_loop_quit(); +} + +/** + * Set new policy value. + * + * This will emit the ecore event ELM_EVENT_POLICY_CHANGED in the main + * loop giving the event information Elm_Event_Policy_Changed with + * policy identifier, new and old values. + * + * @param policy policy identifier as in Elm_Policy. + * @param value policy value, depends on identifiers, usually there is + * an enumeration with the same prefix as the policy name, for + * example: ELM_POLICY_QUIT and Elm_Policy_Quit + * (ELM_POLICY_QUIT_NONE, ELM_POLICY_QUIT_LAST_WINDOW_CLOSED). + * @ingroup General + * + * @return @c EINA_TRUE on success or @c EINA_FALSE on error (right + * now just invalid policy identifier, but in future policy + * value might be enforced). + */ +EAPI Eina_Bool +elm_policy_set(unsigned int policy, + int value) +{ + Elm_Event_Policy_Changed *ev; + + if (policy >= ELM_POLICY_LAST) + return EINA_FALSE; + + if (value == _elm_policies[policy]) + return EINA_TRUE; + + /* TODO: validade policy? */ + + ev = malloc(sizeof(*ev)); + ev->policy = policy; + ev->new_value = value; + ev->old_value = _elm_policies[policy]; + + _elm_policies[policy] = value; + + ecore_event_add(ELM_EVENT_POLICY_CHANGED, ev, NULL, NULL); + + return EINA_TRUE; +} + +/** + * Gets the policy value set for given identifier. + * + * @param policy policy identifier as in Elm_Policy. + * @ingroup General + * + * @return policy value. Will be 0 if policy identifier is invalid. + */ +EAPI int +elm_policy_get(unsigned int policy) +{ + if (policy >= ELM_POLICY_LAST) + return 0; + return _elm_policies[policy]; +} + +/** + * @defgroup Scaling Selective Widget Scaling + * + * Different widgets can be scaled independently. These functions allow you to + * manipulate this scaling on a per-widget basis. The object and all its + * children get their scaling factors multiplied by the scale factor set. + * This is multiplicative, in that if a child also has a scale size set it is + * in turn multiplied by its parent's scale size. 1.0 means “don't scale”, + * 2.0 is double size, 0.5 is half etc. + */ + +/** + * Set the scaling factor + * + * @param obj The object + * @param scale Scale factor (from 0.0 up, with 1.0 == no scaling) + * @ingroup Scaling + */ +EAPI void +elm_object_scale_set(Evas_Object *obj, + double scale) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_scale_set(obj, scale); +} + +/** + * Get the scaling factor + * + * @param obj The object + * @return The scaling factor set by elm_object_scale_set() + * @ingroup Scaling + */ +EAPI double +elm_object_scale_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, 0.0); + return elm_widget_scale_get(obj); +} + +/** + * Get the global scaling factor + * + * This gets the globally configured scaling factor that is applied to all + * objects. + * + * @return The scaling factor + * @ingroup Scaling + */ +EAPI double +elm_scale_get(void) +{ + return _elm_config->scale; +} + +/** + * Set the global scaling factor + * + * This sets the globally configured scaling factor that is applied to all + * objects. + * + * @param scale The scaling factor to set + * @ingroup Scaling + */ +EAPI void +elm_scale_set(double scale) +{ + if (_elm_config->scale == scale) return; + _elm_config->scale = scale; + _elm_rescale(); +} + +/** + * Set the global scaling factor for all applications on the display + * + * This sets the globally configured scaling factor that is applied to all + * objects for all applications. + * @param scale The scaling factor to set + * @ingroup Scaling + */ +EAPI void +elm_scale_all_set(double scale) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int scale_i = (unsigned int)(scale * 1000.0); + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_SCALE"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &scale_i, 1); +#endif +} + +/** + * @defgroup Styles Styles + * + * Widgets can have different styles of look. These generic API's set + * styles of widgets, if they support them (and if the theme(s) do). + */ + +/** + * Set the style + * + * This sets the name of the style + * @param obj The object + * @param style The style name to use + * @ingroup Styles + */ +EAPI void +elm_object_style_set(Evas_Object *obj, + const char *style) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_style_set(obj, style); +} + +/** + * Get the style + * + * This gets the style being used for that widget. Note that the string + * pointer is only valid as longas the object is valid and the style doesn't + * change. + * + * @param obj The object + * @return The style name + * @ingroup Styles + */ +EAPI const char * +elm_object_style_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL); + return elm_widget_style_get(obj); +} + +/** + * Set the disable state + * + * This sets the disable state for the widget. + * + * @param obj The object + * @param disabled The state + * @ingroup Styles + */ +EAPI void +elm_object_disabled_set(Evas_Object *obj, + Eina_Bool disabled) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_disabled_set(obj, disabled); +} + +/** + * Get the disable state + * + * This gets the disable state for the widget. + * + * @param obj The object + * @return True, if the widget is disabled + * @ingroup Styles + */ +EAPI Eina_Bool +elm_object_disabled_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE); + return elm_widget_disabled_get(obj); +} + +/** + * @defgroup Config Elementary Config + * + * Elementary configuration is formed by a set options bounded to a + * given @ref Profile profile, like @ref Theme theme, @ref Fingers + * "finger size", etc. These are functions with which one syncronizes + * changes made to those values to the configuration storing files, de + * facto. You most probably don't want to use the functions in this + * group unlees you're writing an elementary configuration manager. + */ + +/** + * Save back Elementary's configuration, so that it will persist on + * future sessions. + * + * @return @c EINA_TRUE, when sucessful. @c EINA_FALSE, otherwise. + * @ingroup Config + * + * This function will take effect -- thus, do I/O -- immediately. Use + * it when you want to apply all configuration changes at once. The + * current configuration set will get saved onto the current profile + * configuration file. + * + */ +EAPI Eina_Bool +elm_config_save(void) +{ + return _elm_config_save(); +} + +/** + * Reload Elementary's configuration, bounded to current selected + * profile. + * + * @return @c EINA_TRUE, when sucessful. @c EINA_FALSE, otherwise. + * @ingroup Config + * + * Useful when you want to force reloading of configuration values for + * a profile. If one removes user custom configuration directories, + * for example, it will force a reload with system values insted. + * + */ +EAPI void +elm_config_reload(void) +{ + _elm_config_reload(); +} + +/** + * @defgroup Profile Elementary Profile + * + * Profiles are pre-set options that affect the whole look-and-feel of + * Elementary-based applications. There are, for example, profiles + * aimed at desktop computer applications and others aimed at mobile, + * touchscreen-based ones. You most probably don't want to use the + * functions in this group unlees you're writing an elementary + * configuration manager. + */ + +/** + * Get Elementary's profile in use. + * + * This gets the global profile that is applied to all Elementary + * applications. + * + * @return The profile's name + * @ingroup Profile + */ +EAPI const char * +elm_profile_current_get(void) +{ + return _elm_config_current_profile_get(); +} + +/** + * Get an Elementary's profile directory path in the filesystem. One + * may want to fetch a system profile's dir or an user one (fetched + * inside $HOME). + * + * @param profile The profile's name + * @param is_user Whether to lookup for an user profile (@c EINA_TRUE) + * or a system one (@c EINA_FALSE) + * @return The profile's directory path. + * @ingroup Profile + * + * @note You must free it with elm_profile_dir_free(). + */ +EAPI const char * +elm_profile_dir_get(const char *profile, + Eina_Bool is_user) +{ + return _elm_config_profile_dir_get(profile, is_user); +} + +/** + * Free an Elementary's profile directory path, as returned by + * elm_profile_dir_get(). + * + * @param p_dir The profile's path + * @ingroup Profile + * + */ +EAPI void +elm_profile_dir_free(const char *p_dir) +{ + free((void *)p_dir); +} + +/** + * Get Elementary's list of available profiles. + * + * @return The profiles list. List node data are the profile name + * strings. + * @ingroup Profile + * + * @note One must free this list, after usage, with the function + * elm_profile_list_free(). + */ +EAPI Eina_List * +elm_profile_list_get(void) +{ + return _elm_config_profiles_list(); +} + +/** + * Free Elementary's list of available profiles. + * + * @param The profiles list, as returned by elm_profile_list_get(). + * @ingroup Profile + * + */ +EAPI void +elm_profile_list_free(Eina_List *l) +{ + const char *dir; + + EINA_LIST_FREE(l, dir) + eina_stringshare_del(dir); +} + +/** + * Set Elementary's profile. + * + * This sets the global profile that is applied to Elementary + * applications. Just the process the call comes from will be + * affected. + * + * @param profile The profile's name + * @ingroup Profile + * + */ +EAPI void +elm_profile_set(const char *profile) +{ + EINA_SAFETY_ON_NULL_RETURN(profile); + _elm_config_profile_set(profile); +} + +/** + * Set Elementary's profile. + * + * This sets the global profile that is applied to all Elementary + * applications. All running Elementary windows will be affected. + * + * @param profile The profile's name + * @ingroup Profile + * + */ +EAPI void +elm_profile_all_set(const char *profile) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_PROFILE"); + ecore_x_window_prop_string_set(ecore_x_window_root_first_get(), + atom, profile); +#endif +} + +/** + * @defgroup Engine Elementary Engine + * + * These are functions setting and querying which rendering engine + * Elementary will use for drawing its windows' pixels. + */ + +/** + * Get Elementary's rendering engine in use. + * + * This gets the global rendering engine that is applied to all + * Elementary applications. + * + * @return The rendering engine's name + * @ingroup Engine + * + * @note there's no need to free the returned string, here. + */ +EAPI const char * +elm_engine_current_get(void) +{ + return _elm_config->engine; +} + +/** + * Set Elementary's rendering engine for use. + * + * This gets sets global rendering engine that is applied to all + * Elementary applications. Note that it will take effect only to + * subsequent Elementary window creations. + * + * @param The rendering engine's name + * @ingroup Engine + * + * @note there's no need to free the returned string, here. + */ +EAPI void +elm_engine_set(const char *engine) +{ + EINA_SAFETY_ON_NULL_RETURN(engine); + + _elm_config_engine_set(engine); +} + +/** + * @defgroup Fonts Elementary Fonts + * + * These are functions dealing with font rendering, selection and the + * like for Elementary applications. One might fetch which system + * fonts are there to use and set custom fonts for individual classes + * of UI items containing text (text classes). + */ + +/** + * Get Elementary's list of supported text classes. + * + * @return The text classes list, with @c Elm_Text_Class blobs as data. + * @ingroup Fonts + * + * Release the list with elm_text_classes_list_free(). + */ +EAPI const Eina_List * +elm_text_classes_list_get(void) +{ + return _elm_config_text_classes_get(); +} + +/** + * Free Elementary's list of supported text classes. + * + * @ingroup Fonts + * + * @see elm_text_classes_list_get(). + */ +EAPI void +elm_text_classes_list_free(const Eina_List *list) +{ + _elm_config_text_classes_free((Eina_List *)list); +} + +/** + * Get Elementary's list of font overlays, set with + * elm_font_overlay_set(). + * + * @return The font overlays list, with @c Elm_Font_Overlay blobs as + * data. + * + * @ingroup Fonts + * + * For each text class, one can set a font overlay for it, + * overriding the default font properties for that class coming from + * the theme in use. There is no need to free this list. + * + * @see elm_font_overlay_set() and elm_font_overlay_unset(). + */ +EAPI const Eina_List * +elm_font_overlay_list_get(void) +{ + return _elm_config_font_overlays_list(); +} + +/** + * Set a font overlay for a given Elementary text class. + * + * @param text_class Text class name + * @param font Font name and style string + * @param size Font size + * + * @ingroup Fonts + * + * @p font has to be in the format returned by + * elm_font_fontconfig_name_get(). @see elm_font_overlay_list_get() + * and @elm_font_overlay_unset(). + */ +EAPI void +elm_font_overlay_set(const char *text_class, + const char *font, + Evas_Font_Size size) +{ + _elm_config_font_overlay_set(text_class, font, size); +} + +/** + * Unset a font overlay for a given Elementary text class. + * + * @param text_class Text class name + * + * @ingroup Fonts + * + * This will bring back text elements belonging to text class @p + * text_class back to their default font settings. + */ +EAPI void +elm_font_overlay_unset(const char *text_class) +{ + _elm_config_font_overlay_remove(text_class); +} + +/** + * Apply the changes made with elm_font_overlay_set() and + * elm_font_overlay_unset() on the current Elementary window. + * + * @ingroup Fonts + * + * This applies all font overlays set to all objects in the UI. + */ +EAPI void +elm_font_overlay_apply(void) +{ + _elm_config_font_overlay_apply(); +} + +/** + * Apply the changes made with elm_font_overlay_set() and + * elm_font_overlay_unset() on all Elementary application windows. + * + * @ingroup Fonts + * + * This applies all font overlays set to all objects in the UI. + */ +EAPI void +elm_font_overlay_all_apply(void) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int dummy = (unsigned int)(1 * 1000.0); + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_FONT_OVERLAY"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), atom, &dummy, + 1); +#endif +} + +/** + * Translate a font (family) name string in fontconfig's font names + * syntax into an @c Elm_Font_Properties struct. + * + * @param font The font name and styles string + * @return the font properties struct + * + * @ingroup Fonts + * + * @note The reverse translation can be achived with + * elm_font_fontconfig_name_get(), for one style only (single font + * instance, not family). + */ +EAPI Elm_Font_Properties * +elm_font_properties_get(const char *font) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(font, NULL); + return _elm_font_properties_get(NULL, font); +} + +/** + * Free font properties return by elm_font_properties_get(). + * + * @param efp the font properties struct + * + * @ingroup Fonts + */ +EAPI void +elm_font_properties_free(Elm_Font_Properties *efp) +{ + const char *str; + + EINA_SAFETY_ON_NULL_RETURN(efp); + EINA_LIST_FREE(efp->styles, str) + if (str) eina_stringshare_del(str); + if (efp->name) eina_stringshare_del(efp->name); + free(efp); +} + +/** + * Translate a font name, bound to a style, into fontconfig's font names + * syntax. + * + * @param name The font (family) name + * @param style The given style (may be @c NULL) + * + * @return the font name and style string + * + * @ingroup Fonts + * + * @note The reverse translation can be achived with + * elm_font_properties_get(), for one style only (single font + * instance, not family). + */ +EAPI const char * +elm_font_fontconfig_name_get(const char *name, + const char *style) +{ + char buf[256]; + + EINA_SAFETY_ON_NULL_RETURN_VAL(name, NULL); + if (!style || style[0] == 0) return eina_stringshare_add(name); + snprintf(buf, 256, "%s" ELM_FONT_TOKEN_STYLE "%s", name, style); + return eina_stringshare_add(buf); +} + +/** + * Free the font string return by elm_font_fontconfig_name_get(). + * + * @param efp the font properties struct + * + * @ingroup Fonts + */ +EAPI void +elm_font_fontconfig_name_free(const char *name) +{ + eina_stringshare_del(name); +} + +/** + * Create a font hash table of available system fonts. + * + * One must call it with @p list being the return value of + * evas_font_available_list(). The hash will be indexed by font + * (family) names, being its values @c Elm_Font_Properties blobs. + * + * @param list The list of available system fonts, as returned by + * evas_font_available_list(). + * @return the font hash. + * + * @ingroup Fonts + * + * @note The user is supposed to get it populated at least with 3 + * default font families (Sans, Serif, Monospace), which should be + * present on most systems. + */ +EAPI Eina_Hash * +elm_font_available_hash_add(Eina_List *list) +{ + Eina_Hash *font_hash; + Eina_List *l; + void *key; + + font_hash = NULL; + + /* populate with default font families */ + font_hash = _elm_font_available_hash_add(font_hash, "Sans:style=Regular"); + font_hash = _elm_font_available_hash_add(font_hash, "Sans:style=Bold"); + font_hash = _elm_font_available_hash_add(font_hash, "Sans:style=Oblique"); + font_hash = _elm_font_available_hash_add(font_hash, + "Sans:style=Bold Oblique"); + + font_hash = _elm_font_available_hash_add(font_hash, "Serif:style=Regular"); + font_hash = _elm_font_available_hash_add(font_hash, "Serif:style=Bold"); + font_hash = _elm_font_available_hash_add(font_hash, "Serif:style=Oblique"); + font_hash = _elm_font_available_hash_add(font_hash, + "Serif:style=Bold Oblique"); + + font_hash = _elm_font_available_hash_add(font_hash, + "Monospace:style=Regular"); + font_hash = _elm_font_available_hash_add(font_hash, + "Monospace:style=Bold"); + font_hash = _elm_font_available_hash_add(font_hash, + "Monospace:style=Oblique"); + font_hash = _elm_font_available_hash_add(font_hash, + "Monospace:style=Bold Oblique"); + + EINA_LIST_FOREACH(list, l, key) + font_hash = _elm_font_available_hash_add(font_hash, key); + + return font_hash; +} + +/** + * Free the hash return by elm_font_available_hash_add(). + * + * @param hash the hash to be freed. + * + * @ingroup Fonts + */ +EAPI void +elm_font_available_hash_del(Eina_Hash *hash) +{ + _elm_font_available_hash_del(hash); +} + +/** + * @defgroup Fingers Fingers + * + * Elementary is designed to be finger-friendly for touchscreens, and so in + * addition to scaling for display resolution, it can also scale based on + * finger "resolution" (or size). + */ + +/** + * Get the configured finger size + * + * This gets the globally configured finger size in pixels + * + * @return The finger size + * @ingroup Fingers + */ +EAPI Evas_Coord +elm_finger_size_get(void) +{ + return _elm_config->finger_size; +} + +/** + * Set the configured finger size + * + * This sets the globally configured finger size in pixels + * + * @param size The finger size + * @ingroup Fingers + */ +EAPI void +elm_finger_size_set(Evas_Coord size) +{ + if (_elm_config->finger_size == size) return; + _elm_config->finger_size = size; + _elm_rescale(); +} + +/** + * Set the configured finger size for all applications on the display + * + * This sets the globally configured finger size in pixels for all applications + * on the display + * + * @param size The finger size + * @ingroup Fingers + */ +EAPI void +elm_finger_size_all_set(Evas_Coord size) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int size_i = (unsigned int)size; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_FINGER_SIZE"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &size_i, 1); +#endif +} + +/** + * Adjust size of an element for finger usage + * + * This takes width and height sizes (in pixels) as input and a size multiple + * (which is how many fingers you want to place within the area), and adjusts + * the size tobe large enough to accommodate finger. On return the w and h + * sizes poiner do by these parameters will be modified. + * + * @param times_w How many fingers should fit horizontally + * @param w Pointer to the width size to adjust + * @param times_h How many fingers should fit vertically + * @param h Pointer to the height size to adjust + * @ingroup Fingers + */ +EAPI void +elm_coords_finger_size_adjust(int times_w, + Evas_Coord *w, + int times_h, + Evas_Coord *h) +{ + if ((w) && (*w < (_elm_config->finger_size * times_w))) + *w = _elm_config->finger_size * times_w; + if ((h) && (*h < (_elm_config->finger_size * times_h))) + *h = _elm_config->finger_size * times_h; +} + +/** + * @defgroup Caches Caches + * + * These are functions which let one fine-tune some cache values for + * Elementary applications, thus allowing for performance adjustments. + */ + +/** + * Flush all caches & dump all data that can be to lean down to use + * less memory + * + * @ingroup Caches + */ +EAPI void +elm_all_flush(void) +{ + const Eina_List *l; + Evas_Object *obj; + + EINA_LIST_FOREACH(_elm_win_list, l, obj) + { + Evas *e = evas_object_evas_get(obj); + edje_file_cache_flush(); + edje_collection_cache_flush(); + eet_clearcache(); + evas_image_cache_flush(e); + evas_font_cache_flush(e); + evas_render_dump(e); + } +} + +/** + * Get the configured cache flush interval time + * + * This gets the globally configured cache flush interval time, in + * ticks + * + * @return The cache flush interval time + * @ingroup Caches + * + * @see elm_all_flush() + */ +EAPI int +elm_cache_flush_interval_get(void) +{ + return _elm_config->cache_flush_poll_interval; +} + +/** + * Set the configured cache flush interval time + * + * This sets the globally configured cache flush interval time, in ticks + * + * @param size The cache flush interval time + * @ingroup Caches + * + * @see elm_all_flush() + */ +EAPI void +elm_cache_flush_interval_set(int size) +{ + if (_elm_config->cache_flush_poll_interval == size) return; + _elm_config->cache_flush_poll_interval = size; + + _elm_recache(); +} + +/** + * Set the configured cache flush interval time for all applications on the + * display + * + * This sets the globally configured cache flush interval time -- in ticks + * -- for all applications on the display. + * + * @param size The cache flush interval time + * @ingroup Caches + */ +EAPI void +elm_cache_flush_interval_all_set(int size) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int size_i = (unsigned int)size; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_CACHE_FLUSH_INTERVAL"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &size_i, 1); +#endif +} + +/** + * Get the configured cache flush enabled state + * + * This gets the globally configured cache flush state - if it is enabled + * or not. When cache flushing is enabled, elementary will regularly + * (see elm_cache_flush_interval_get() ) flush caches and dump data out of + * memory and allow usage to re-seed caches and data in memory where it + * can do so. An idle application will thus minimise its memory usage as + * data will be freed from memory and not be re-loaded as it is idle and + * not rendering or doing anything graphically right now. + * + * @return The cache flush state + * @ingroup Caches + * + * @see elm_all_flush() + */ +EAPI Eina_Bool +elm_cache_flush_enmabled_get(void) +{ + return _elm_config->cache_flush_enable; +} + +/** + * Set the configured cache flush enabled state + * + * This sets the globally configured cache flush enabled state + * + * @param size The cache flush enabled state + * @ingroup Caches + * + * @see elm_all_flush() + */ +EAPI void +elm_cache_flush_enabled_set(Eina_Bool enabled) +{ + enabled = !!enabled; + if (_elm_config->cache_flush_enable == enabled) return; + _elm_config->cache_flush_enable = enabled; + + _elm_recache(); +} + +/** + * Set the configured cache flush enabled state for all applications on the + * display + * + * This sets the globally configured cache flush enabled state for all + * applications on the display. + * + * @param size The cache flush enabled state + * @ingroup Caches + */ +EAPI void +elm_cache_flush_enabled_all_set(Eina_Bool enabled) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int enabled_i = (unsigned int)enabled; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_CACHE_FLUSH_ENABLE"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &enabled_i, 1); +#endif +} + +/** + * Get the configured font cache size + * + * This gets the globally configured font cache size, in bytes + * + * @return The font cache size + * @ingroup Caches + */ +EAPI int +elm_font_cache_get(void) +{ + return _elm_config->font_cache; +} + +/** + * Set the configured font cache size + * + * This sets the globally configured font cache size, in bytes + * + * @param size The font cache size + * @ingroup Caches + */ +EAPI void +elm_font_cache_set(int size) +{ + if (_elm_config->font_cache == size) return; + _elm_config->font_cache = size; + + _elm_recache(); +} + +/** + * Set the configured font cache size for all applications on the + * display + * + * This sets the globally configured font cache size -- in bytes + * -- for all applications on the display. + * + * @param size The font cache size + * @ingroup Caches + */ +EAPI void +elm_font_cache_all_set(int size) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int size_i = (unsigned int)size; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_FONT_CACHE"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &size_i, 1); +#endif +} + +/** + * Get the configured image cache size + * + * This gets the globally configured image cache size, in bytes + * + * @return The image cache size + * @ingroup Caches + */ +EAPI int +elm_image_cache_get(void) +{ + return _elm_config->image_cache; +} + +/** + * Set the configured image cache size + * + * This sets the globally configured image cache size, in bytes + * + * @param size The image cache size + * @ingroup Caches + */ +EAPI void +elm_image_cache_set(int size) +{ + if (_elm_config->image_cache == size) return; + _elm_config->image_cache = size; + + _elm_recache(); +} + +/** + * Set the configured image cache size for all applications on the + * display + * + * This sets the globally configured image cache size -- in bytes + * -- for all applications on the display. + * + * @param size The image cache size + * @ingroup Caches + */ +EAPI void +elm_image_cache_all_set(int size) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int size_i = (unsigned int)size; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_IMAGE_CACHE"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &size_i, 1); +#endif +} + +/** + * Get the configured edje file cache size. + * + * This gets the globally configured edje file cache size, in number + * of files. + * + * @return The edje file cache size + * @ingroup Caches + */ +EAPI int +elm_edje_file_cache_get(void) +{ + return _elm_config->edje_cache; +} + +/** + * Set the configured edje file cache size + * + * This sets the globally configured edje file cache size, in number + * of files. + * + * @param size The edje file cache size + * @ingroup Caches + */ +EAPI void +elm_edje_file_cache_set(int size) +{ + if (_elm_config->edje_cache == size) return; + _elm_config->edje_cache = size; + + _elm_recache(); +} + +/** + * Set the configured edje file cache size for all applications on the + * display + * + * This sets the globally configured edje file cache size -- in number + * of files -- for all applications on the display. + * + * @param size The edje file cache size + * @ingroup Caches + */ +EAPI void +elm_edje_file_cache_all_set(int size) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int size_i = (unsigned int)size; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_EDJE_FILE_CACHE"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &size_i, 1); +#endif +} + +/** + * Get the configured edje collections (groups) cache size. + * + * This gets the globally configured edje collections cache size, in + * number of collections. + * + * @return The edje collections cache size + * @ingroup Caches + */ +EAPI int +elm_edje_collection_cache_get(void) +{ + return _elm_config->edje_collection_cache; +} + +/** + * Set the configured edje collections (groups) cache size + * + * This sets the globally configured edje collections cache size, in + * number of collections. + * + * @param size The edje collections cache size + * @ingroup Caches + */ +EAPI void +elm_edje_collection_cache_set(int size) +{ + if (_elm_config->edje_collection_cache == size) return; + _elm_config->edje_collection_cache = size; + + _elm_recache(); +} + +/** + * Set the configured edje collections (groups) cache size for all + * applications on the display + * + * This sets the globally configured edje collections cache size -- in + * number of collections -- for all applications on the display. + * + * @param size The edje collections cache size + * @ingroup Caches + */ +EAPI void +elm_edje_collection_cache_all_set(int size) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int size_i = (unsigned int)size; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_EDJE_COLLECTION_CACHE"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &size_i, 1); +#endif +} + +/** + * @defgroup Focus Focus + * + * Objects have focus. This is what determines where the keyboard input goes to + * within the application window. + */ + +/** + * Get the focus of the object + * + * This gets the focused property of the object. + * + * @param obj The object + * @return 1 if the object is focused, 0 if not. + * @ingroup Focus + */ +EAPI Eina_Bool +elm_object_focus_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE); + return elm_widget_focus_get(obj); +} + +/** + * Set the focus to the object + * + * This sets the focus target for keyboard input to be the object indicated. + * + * @param obj The object + * @ingroup Focus + */ +EAPI void +elm_object_focus(Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + if (elm_widget_focus_get(obj)) + return; + + elm_widget_focus_cycle(obj, ELM_FOCUS_NEXT); +} + +/** + * Remove the focus from the object + * + * This removes the focus target for keyboard input from be the object + * indicated. + * + * @param obj The object + * @ingroup Focus + */ +EAPI void +elm_object_unfocus(Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + if (!elm_widget_can_focus_get(obj)) return; + elm_widget_focused_object_clear(obj); +} + +/** + * Set the ability for the object to focus + * + * This sets the ability for the object to be able to get keyboard focus or + * not. By default all objects are able to be focused. + * + * @param obj The object + * @param enable 1 if the object can be focused, 0 if not + * @ingroup Focus + */ +EAPI void +elm_object_focus_allow_set(Evas_Object *obj, + Eina_Bool enable) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_can_focus_set(obj, enable); +} + +/** + * Get the ability for the object to focus + * + * This gets the ability for the object to be able to get keyboard focus or + * not. By default all objects are able to be focused. + * + * @param obj The object + * @return 1 if the object is allowed to be focused, 0 if not. + * @ingroup Focus + */ +EAPI Eina_Bool +elm_object_focus_allow_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE); + return (elm_widget_can_focus_get(obj)) || (elm_widget_child_can_focus_get(obj)); +} + +/** + * Set custom focus chain. + * + * This function i set one new and overwrite any previous custom focus chain + * with the list of objects. The previous list will be deleted and this list + * will be managed. After setted, don't modity it. + * + * @note On focus cycle, only will be evaluated children of this container. + * + * @param obj The container object + * @param objs Chain of objects to pass focus + * @ingroup Focus + */ +EAPI void +elm_object_focus_custom_chain_set(Evas_Object *obj, + Eina_List *objs) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_focus_custom_chain_set(obj, objs); +} + +/** + * Unset custom focus chain + * + * @param obj The container object + * @ingroup Focus + */ +EAPI void +elm_object_focus_custom_chain_unset(Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_focus_custom_chain_unset(obj); +} + +/** + * Get custom focus chain + * + * @param obj The container object + * @ingroup Focus + */ +EAPI const Eina_List * +elm_object_focus_custom_chain_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL); + return elm_widget_focus_custom_chain_get(obj); +} + +/** + * Append object to custom focus chain. + * + * @note If relative_child equal to NULL or not in custom chain, the object + * will be added in end. + * + * @note On focus cycle, only will be evaluated children of this container. + * + * @param obj The container object + * @param child The child to be added in custom chain + * @param relative_child The relative object to position the child + * @ingroup Focus + */ +EAPI void +elm_object_focus_custom_chain_append(Evas_Object *obj, + Evas_Object *child, + Evas_Object *relative_child) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + EINA_SAFETY_ON_NULL_RETURN(child); + elm_widget_focus_custom_chain_append(obj, child, relative_child); +} + +/** + * Prepend object to custom focus chain. + * + * @note If relative_child equal to NULL or not in custom chain, the object + * will be added in begin. + * + * @note On focus cycle, only will be evaluated children of this container. + * + * @param obj The container object + * @param child The child to be added in custom chain + * @param relative_child The relative object to position the child + * @ingroup Focus + */ +EAPI void +elm_object_focus_custom_chain_prepend(Evas_Object *obj, + Evas_Object *child, + Evas_Object *relative_child) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + EINA_SAFETY_ON_NULL_RETURN(child); + elm_widget_focus_custom_chain_prepend(obj, child, relative_child); +} + +/** + * Give focus to next object in object tree. + * + * Give focus to next object in focus chain of one object sub-tree. + * If the last object of chain already have focus, the focus will go to the + * first object of chain. + * + * @param obj The object root of sub-tree + * @param dir Direction to cycle the focus + * + * @ingroup Focus + */ +EAPI void +elm_object_focus_cycle(Evas_Object *obj, + Elm_Focus_Direction dir) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_focus_cycle(obj, dir); +} + +/** + * Give focus to near object in one direction. + * + * Give focus to near object in direction of one object. + * If none focusable object in given direction, the focus will not change. + * + * @param obj The reference object + * @param x Horizontal component of direction to focus + * @param y Vertical component of direction to focus + * + * @ingroup Focus + */ +EAPI void +elm_object_focus_direction_go(Evas_Object *obj, + int x, + int y) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_focus_direction_go(obj, x, y); +} + +/** + * Get the enable status of the focus highlight + * + * This gets whether the highlight on focused objects is enabled or not + * @ingroup Focus + */ +EAPI Eina_Bool +elm_focus_highlight_enabled_get(void) +{ + return _elm_config->focus_highlight_enable; +} + +/** + * Set the enable status of the focus highlight + * + * Set whether to show or not the highlight on focused objects + * @param enable Enable highlight if EINA_TRUE, disable otherwise + * @ingroup Focus + */ +EAPI void +elm_focus_highlight_enabled_set(Eina_Bool enable) +{ + _elm_config->focus_highlight_enable = !!enable; +} + +/** + * Get the enable status of the highlight animation + * + * Get whether the focus highlight, if enabled, will animate its switch from + * one object to the next + * @ingroup Focus + */ +EAPI Eina_Bool +elm_focus_highlight_animate_get(void) +{ + return _elm_config->focus_highlight_animate; +} + +/** + * Set the enable status of the highlight animation + * + * Set whether the focus highlight, if enabled, will animate its switch from + * one object to the next + * @param animate Enable animation if EINA_TRUE, disable otherwise + * @ingroup Focus + */ +EAPI void +elm_focus_highlight_animate_set(Eina_Bool animate) +{ + _elm_config->focus_highlight_animate = !!animate; +} + +/** + * @defgroup Scrolling Scrolling + * + * These are functions setting how scrollable views in Elementary + * widgets should behave on user interaction. + */ + +/** + * Get whether scrollers should bounce when they reach their + * viewport's edge during a scroll. + * + * @return the thumb scroll bouncing state + * + * This is the default behavior for touch screens, in general. + * @ingroup Scrolling + */ +EAPI Eina_Bool +elm_scroll_bounce_enabled_get(void) +{ + return _elm_config->thumbscroll_bounce_enable; +} + +/** + * Set whether scrollers should bounce when they reach their + * viewport's edge during a scroll. + * + * @param enabled the thumb scroll bouncing state + * + * @see elm_thumbscroll_bounce_enabled_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_bounce_enabled_set(Eina_Bool enabled) +{ + _elm_config->thumbscroll_bounce_enable = enabled; +} + +/** + * Set whether scrollers should bounce when they reach their + * viewport's edge during a scroll, for all Elementary application + * windows. + * + * @param enabled the thumb scroll bouncing state + * + * @see elm_thumbscroll_bounce_enabled_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_bounce_enabled_all_set(Eina_Bool enabled) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int bounce_enable_i = (unsigned int)enabled; + + if (!atom) + atom = ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_BOUNCE_ENABLE"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &bounce_enable_i, 1); +#endif +} + +/** + * Get the amount of inertia a scroller will impose at bounce + * animations. + * + * @return the thumb scroll bounce friction + * + * @ingroup Scrolling + */ +EAPI double +elm_scroll_bounce_friction_get(void) +{ + return _elm_config->thumbscroll_bounce_friction; +} + +/** + * Set the amount of inertia a scroller will impose at bounce + * animations. + * + * @param friction the thumb scroll bounce friction + * + * @see elm_thumbscroll_bounce_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_bounce_friction_set(double friction) +{ + _elm_config->thumbscroll_bounce_friction = friction; +} + +/** + * Set the amount of inertia a scroller will impose at bounce + * animations, for all Elementary application windows. + * + * @param friction the thumb scroll bounce friction + * + * @see elm_thumbscroll_bounce_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_bounce_friction_all_set(double friction) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int bounce_friction_i = (unsigned int)(friction * 1000.0); + + if (!atom) + atom = ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_BOUNCE_FRICTION"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &bounce_friction_i, 1); +#endif +} + +/** + * Get the amount of inertia a paged scroller will impose at + * page fitting animations. + * + * @return the page scroll friction + * + * @ingroup Scrolling + */ +EAPI double +elm_scroll_page_scroll_friction_get(void) +{ + return _elm_config->page_scroll_friction; +} + +/** + * Set the amount of inertia a paged scroller will impose at + * page fitting animations. + * + * @param friction the page scroll friction + * + * @see elm_thumbscroll_page_scroll_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_page_scroll_friction_set(double friction) +{ + _elm_config->page_scroll_friction = friction; +} + +/** + * Set the amount of inertia a paged scroller will impose at + * page fitting animations, for all Elementary application windows. + * + * @param friction the page scroll friction + * + * @see elm_thumbscroll_page_scroll_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_page_scroll_friction_all_set(double friction) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int page_scroll_friction_i = (unsigned int)(friction * 1000.0); + + if (!atom) + atom = ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_PAGE_SCROLL_FRICTION"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &page_scroll_friction_i, 1); +#endif +} + +/** + * Get the amount of inertia a scroller will impose at region bring + * animations. + * + * @return the bring in scroll friction + * + * @ingroup Scrolling + */ +EAPI double +elm_scroll_bring_in_scroll_friction_get(void) +{ + return _elm_config->bring_in_scroll_friction; +} + +/** + * Set the amount of inertia a scroller will impose at region bring + * animations. + * + * @param friction the bring in scroll friction + * + * @see elm_thumbscroll_bring_in_scroll_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_bring_in_scroll_friction_set(double friction) +{ + _elm_config->bring_in_scroll_friction = friction; +} + +/** + * Set the amount of inertia a scroller will impose at region bring + * animations, for all Elementary application windows. + * + * @param friction the bring in scroll friction + * + * @see elm_thumbscroll_bring_in_scroll_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_bring_in_scroll_friction_all_set(double friction) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int bring_in_scroll_friction_i = (unsigned int)(friction * 1000.0); + + if (!atom) + atom = + ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_BRING_IN_SCROLL_FRICTION"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &bring_in_scroll_friction_i, 1); +#endif +} + +/** + * Get the amount of inertia scrollers will impose at animations + * triggered by Elementary widgets' zooming API. + * + * @return the zoom friction + * + * @ingroup Scrolling + */ +EAPI double +elm_scroll_zoom_friction_get(void) +{ + return _elm_config->zoom_friction; +} + +/** + * Set the amount of inertia scrollers will impose at animations + * triggered by Elementary widgets' zooming API. + * + * @param friction the zoom friction + * + * @see elm_thumbscroll_zoom_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_zoom_friction_set(double friction) +{ + _elm_config->zoom_friction = friction; +} + +/** + * Set the amount of inertia scrollers will impose at animations + * triggered by Elementary widgets' zooming API, for all Elementary + * application windows. + * + * @param friction the zoom friction + * + * @see elm_thumbscroll_zoom_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_zoom_friction_all_set(double friction) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int zoom_friction_i = (unsigned int)(friction * 1000.0); + + if (!atom) + atom = ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_ZOOM_FRICTION"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &zoom_friction_i, 1); +#endif +} + +/** + * Get whether scrollers should be draggable from any point in their + * views. + * + * @return the thumb scroll state + * + * @note This is the default behavior for touch screens, in general. + * @note All other functions namespaced with "thumbscroll" will only + * have effect if this mode is enabled. + * + * @ingroup Scrolling + */ +EAPI Eina_Bool +elm_scroll_thumbscroll_enabled_get(void) +{ + return _elm_config->thumbscroll_enable; +} + +/** + * Set whether scrollers should be draggable from any point in their + * views. + * + * @param enabled the thumb scroll state + * + * @see elm_thumbscroll_enabled_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_enabled_set(Eina_Bool enabled) +{ + _elm_config->thumbscroll_enable = enabled; +} + +/** + * Set whether scrollers should be draggable from any point in their + * views, for all Elementary application windows. + * + * @param enabled the thumb scroll state + * + * @see elm_thumbscroll_enabled_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_enabled_all_set(Eina_Bool enabled) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int ts_enable_i = (unsigned int)enabled; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_ENABLE"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &ts_enable_i, 1); +#endif +} + +/** + * Get the number of pixels one should travel while dragging a + * scroller's view to actually trigger scrolling. + * + * @return the thumb scroll threshould + * + * One would use higher values for touch screens, in general, because + * of their inherent imprecision. + * @ingroup Scrolling + */ +EAPI unsigned int +elm_scroll_thumbscroll_threshold_get(void) +{ + return _elm_config->thumbscroll_threshold; +} + +/** + * Set the number of pixels one should travel while dragging a + * scroller's view to actually trigger scrolling. + * + * @param threshold the thumb scroll threshould + * + * @see elm_thumbscroll_threshould_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_threshold_set(unsigned int threshold) +{ + _elm_config->thumbscroll_threshold = threshold; +} + +/** + * Set the number of pixels one should travel while dragging a + * scroller's view to actually trigger scrolling, for all Elementary + * application windows. + * + * @param threshold the thumb scroll threshould + * + * @see elm_thumbscroll_threshould_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_threshold_all_set(unsigned int threshold) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int ts_threshold_i = (unsigned int)threshold; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_THRESHOLD"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &ts_threshold_i, 1); +#endif +} + +/** + * Get the minimum speed of mouse cursor movement which will trigger + * list self scrolling animation after a mouse up event + * (pixels/second). + * + * @return the thumb scroll momentum threshould + * + * @ingroup Scrolling + */ +EAPI double +elm_scroll_thumbscroll_momentum_threshold_get(void) +{ + return _elm_config->thumbscroll_momentum_threshold; +} + +/** + * Set the minimum speed of mouse cursor movement which will trigger + * list self scrolling animation after a mouse up event + * (pixels/second). + * + * @param threshold the thumb scroll momentum threshould + * + * @see elm_thumbscroll_momentum_threshould_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_momentum_threshold_set(double threshold) +{ + _elm_config->thumbscroll_momentum_threshold = threshold; +} + +/** + * Set the minimum speed of mouse cursor movement which will trigger + * list self scrolling animation after a mouse up event + * (pixels/second), for all Elementary application windows. + * + * @param threshold the thumb scroll momentum threshould + * + * @see elm_thumbscroll_momentum_threshould_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_momentum_threshold_all_set(double threshold) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int ts_momentum_threshold_i = (unsigned int)(threshold * 1000.0); + + if (!atom) + atom = ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_MOMENTUM_THRESHOLD"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &ts_momentum_threshold_i, 1); +#endif +} + +/** + * Get the amount of inertia a scroller will impose at self scrolling + * animations. + * + * @return the thumb scroll friction + * + * @ingroup Scrolling + */ +EAPI double +elm_scroll_thumbscroll_friction_get(void) +{ + return _elm_config->thumbscroll_friction; +} + +/** + * Set the amount of inertia a scroller will impose at self scrolling + * animations. + * + * @param friction the thumb scroll friction + * + * @see elm_thumbscroll_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_friction_set(double friction) +{ + _elm_config->thumbscroll_friction = friction; +} + +/** + * Set the amount of inertia a scroller will impose at self scrolling + * animations, for all Elementary application windows. + * + * @param friction the thumb scroll friction + * + * @see elm_thumbscroll_friction_get() + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_friction_all_set(double friction) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int ts_friction_i = (unsigned int)(friction * 1000.0); + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_FRICTION"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &ts_friction_i, 1); +#endif +} + +/** + * Get the amount of lag between your actual mouse cursor dragging + * movement and a scroller's view movement itself, while pushing it + * into bounce state manually. + * + * @return the thumb scroll border friction + * + * @ingroup Scrolling + */ +EAPI double +elm_scroll_thumbscroll_border_friction_get(void) +{ + return _elm_config->thumbscroll_border_friction; +} + +/** + * Set the amount of lag between your actual mouse cursor dragging + * movement and a scroller's view movement itself, while pushing it + * into bounce state manually. + * + * @param friction the thumb scroll border friction. @c 0.0 for + * perfect synchrony between two movements, @c 1.0 for maximum + * lag. + * + * @see elm_thumbscroll_border_friction_get() + * @note parameter value will get bound to 0.0 - 1.0 interval, always + * + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_border_friction_set(double friction) +{ + if (friction < 0.0) + friction = 0.0; + + if (friction > 1.0) + friction = 1.0; + + _elm_config->thumbscroll_friction = friction; +} + +/** + * Set the amount of lag between your actual mouse cursor dragging + * movement and a scroller's view movement itself, while pushing it + * into bounce state manually, for all Elementary application windows. + * + * @param friction the thumb scroll border friction. @c 0.0 for + * perfect synchrony between two movements, @c 1.0 for maximum + * lag. + * + * @see elm_thumbscroll_border_friction_get() + * @note parameter value will get bound to 0.0 - 1.0 interval, always + * + * @ingroup Scrolling + */ +EAPI void +elm_scroll_thumbscroll_border_friction_all_set(double friction) +{ + if (friction < 0.0) + friction = 0.0; + + if (friction > 1.0) + friction = 1.0; + +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + unsigned int border_friction_i = (unsigned int)(friction * 1000.0); + + if (!atom) + atom = ecore_x_atom_get("ENLIGHTENMENT_THUMBSCROLL_BORDER_FRICTION"); + ecore_x_window_prop_card32_set(ecore_x_window_root_first_get(), + atom, &border_friction_i, 1); +#endif +} + +/** + * @defgroup Scrollhints Scrollhints + * + * Objects when inside a scroller can scroll, but this may not always be + * desirable in certain situations. This allows an object to hint to itself + * and parents to "not scroll" in one of 2 ways. + * + * 1. To hold on scrolling. This means just flicking and dragging may no + * longer scroll, but pressing/dragging near an edge of the scroller will + * still scroll. This is automastically used by the entry object when + * selecting text. + * 2. To totally freeze scrolling. This means it stops. until popped/released. + */ + +/** + * Push the scroll hold by 1 + * + * This increments the scroll hold count by one. If it is more than 0 it will + * take effect on the parents of the indicated object. + * + * @param obj The object + * @ingroup Scrollhints + */ +EAPI void +elm_object_scroll_hold_push(Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_scroll_hold_push(obj); +} + +/** + * Pop the scroll hold by 1 + * + * This decrements the scroll hold count by one. If it is more than 0 it will + * take effect on the parents of the indicated object. + * + * @param obj The object + * @ingroup Scrollhints + */ +EAPI void +elm_object_scroll_hold_pop(Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_scroll_hold_pop(obj); +} + +/** + * Push the scroll freeze by 1 + * + * This increments the scroll freeze count by one. If it is more than 0 it will + * take effect on the parents of the indicated object. + * + * @param obj The object + * @ingroup Scrollhints + */ +EAPI void +elm_object_scroll_freeze_push(Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_scroll_freeze_push(obj); +} + +/** + * Lock the scrolling of the given widget (and thus all parents) + * + * This locks the given object from scrolling in the X axis (and implicitly + * also locks all parent scrollers too from doing the same). + * + * @param obj The object + * @param lock The lock state (1 == locked, 0 == unlocked) + * @ingroup Scrollhints + */ +EAPI void +elm_object_scroll_lock_x_set(Evas_Object *obj, + Eina_Bool lock) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_drag_lock_x_set(obj, lock); +} + +/** + * Lock the scrolling of the given widget (and thus all parents) + * + * This locks the given object from scrolling in the Y axis (and implicitly + * also locks all parent scrollers too from doing the same). + * + * @param obj The object + * @param lock The lock state (1 == locked, 0 == unlocked) + * @ingroup Scrollhints + */ +EAPI void +elm_object_scroll_lock_y_set(Evas_Object *obj, + Eina_Bool lock) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_drag_lock_y_set(obj, lock); +} + +/** + * Get the scrolling lock of the given widget + * + * This gets the lock for X axis scrolling. + * + * @param obj The object + * @ingroup Scrollhints + */ +EAPI Eina_Bool +elm_object_scroll_lock_x_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE); + return elm_widget_drag_lock_x_get(obj); +} + +/** + * Get the scrolling lock of the given widget + * + * This gets the lock for X axis scrolling. + * + * @param obj The object + * @ingroup Scrollhints + */ +EAPI Eina_Bool +elm_object_scroll_lock_y_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE); + return elm_widget_drag_lock_y_get(obj); +} + +/** + * Pop the scroll freeze by 1 + * + * This decrements the scroll freeze count by one. If it is more than 0 it will + * take effect on the parents of the indicated object. + * + * @param obj The object + * @ingroup Scrollhints + */ +EAPI void +elm_object_scroll_freeze_pop(Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_scroll_freeze_pop(obj); +} + +/** + * @defgroup WidgetNavigation Widget Tree Navigation. + * + * How to check if an Evas Object is an Elementary widget? How to get + * the first elementary widget that is parent of the given object? + * These are all covered in widget tree navigation. + */ + +/** + * Check if the given Evas Object is an Elementary widget. + * + * @param obj the object to query. + * @return @c EINA_TRUE if it is an elementary widget variant, + * @c EINA_FALSE otherwise + * @ingroup WidgetNavigation + */ +EAPI Eina_Bool +elm_object_widget_check(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE); + return elm_widget_is(obj); +} + +/** + * Get the first parent of the given object that is an Elementary widget. + * + * @param obj the object to query. + * @return the parent object that is an Elementary widget, or @c NULL + * if no parent is, or no parents at all. + * @ingroup WidgetNavigation + */ +EAPI Evas_Object * +elm_object_parent_widget_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL); + return elm_widget_parent_widget_get(obj); +} + +/** + * Get the top level parent of an Elementary widget. + * + * @param obj The object to query. + * @return The top level Elementary widget, or @c NULL if parent cannot be + * found. + * @ingroup WidgetNavigation + */ +EAPI Evas_Object * +elm_object_top_widget_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL); + return elm_widget_top_get(obj); +} + +/** + * Get the string that represents this Elementary widget. + * + * @note Elementary is weird and exposes itself as a single + * Evas_Object_Smart_Class of type "elm_widget", so + * evas_object_type_get() always return that, making debug and + * language bindings hard. This function tries to mitigate this + * problem, but the solution is to change Elementary to use + * proper inheritance. + * + * @param obj the object to query. + * @return Elementary widget name, or @c NULL if not a valid widget. + * @ingroup WidgetNavigation + */ +EAPI const char * +elm_object_widget_type_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL); + return elm_widget_type_get(obj); +} + +/** + * Send a signal to the widget edje object. + * + * This function sends a signal to the edje object of the obj. An edje program + * can respond to a signal by specifying matching 'signal' and + * 'source' fields. + * + * @param obj The object + * @param emission The signal's name. + * @param source The signal's source. + * @ingroup General + */ +EAPI void +elm_object_signal_emit(Evas_Object *obj, + const char *emission, + const char *source) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_signal_emit(obj, emission, source); +} + +/** + * Add a callback for a signal emitted by widget edje object. + * + * This function connects a callback function to a signal emitted by the + * edje object of the obj. + * Globs can occur in either the emission or source name. + * + * @param obj The object + * @param emission The signal's name. + * @param source The signal's source. + * @param func The callback function to be executed when the signal is + * emitted. + * @param data A pointer to data to pass in to the callback function. + * @ingroup General + */ +EAPI void +elm_object_signal_callback_add(Evas_Object *obj, const char *emission, const char *source, void (*func) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + EINA_SAFETY_ON_NULL_RETURN(func); + elm_widget_signal_callback_add(obj, emission, source, func, data); +} + +/** + * Remove a signal-triggered callback from an widget edje object. + * + * This function removes a callback, previoulsy attached to a signal emitted + * by the edje object of the obj. + * The parameters emission, source and func must match exactly those passed to + * a previous call to elm_object_signal_callback_add(). The data pointer that + * was passed to this call will be returned. + * + * @param obj The object + * @param emission The signal's name. + * @param source The signal's source. + * @param func The callback function to be executed when the signal is + * emitted. + * @return The data pointer + * @ingroup General + */ +EAPI void * +elm_object_signal_callback_del(Evas_Object *obj, const char *emission, const char *source, void (*func) (void *data, Evas_Object *o, const char *emission, const char *source)) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL); + EINA_SAFETY_ON_NULL_RETURN_VAL(func, NULL); + return elm_widget_signal_callback_del(obj, emission, source, func); +} + +/** + * Add a callback for a event emitted by widget or their children. + * + * This function connects a callback function to any key_down key_up event + * emitted by the @p obj or their children. + * This only will be called if no other callback has consumed the event. + * If you want consume the event, and no other get it, func should return + * EINA_TRUE and put EVAS_EVENT_FLAG_ON_HOLD in event_flags. + * + * @warning Accept duplicated callback addition. + * + * @param obj The object + * @param func The callback function to be executed when the event is + * emitted. + * @param data Data to pass in to the callback function. + * @ingroup General + */ +EAPI void +elm_object_event_callback_add(Evas_Object *obj, Elm_Event_Cb func, const void *data) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + EINA_SAFETY_ON_NULL_RETURN(func); + elm_widget_event_callback_add(obj, func, data); +} + +/** + * Remove a event callback from an widget. + * + * This function removes a callback, previoulsy attached to event emission + * by the @p obj. + * The parameters func and data must match exactly those passed to + * a previous call to elm_object_event_callback_add(). The data pointer that + * was passed to this call will be returned. + * + * @param obj The object + * @param func The callback function to be executed when the event is + * emitted. + * @param data Data to pass in to the callback function. + * @return The data pointer + * @ingroup General + */ +EAPI void * +elm_object_event_callback_del(Evas_Object *obj, Elm_Event_Cb func, const void *data) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL); + EINA_SAFETY_ON_NULL_RETURN_VAL(func, NULL); + return elm_widget_event_callback_del(obj, func, data); +} + + +/** + * @defgroup Debug Debug + */ + +/** + * Print Tree object hierarchy in stdout + * + * @param obj The root object + * @ingroup Debug + */ +EAPI void +elm_object_tree_dump(const Evas_Object *top) +{ +#ifdef ELM_DEBUG + elm_widget_tree_dump(top); +#else + return; + (void)top; +#endif +} + +/** + * Print Elm Objects tree hierarchy in file as dot(graphviz) syntax. + * + * @param obj The root object + * @param file The path of output file + * @ingroup Debug + */ +EAPI void +elm_object_tree_dot_dump(const Evas_Object *top, + const char *file) +{ +#ifdef ELM_DEBUG + FILE *f = fopen(file, "w"); + elm_widget_tree_dot_dump(top, f); + fclose(f); +#else + return; + (void)top; + (void)file; +#endif +} + +/** + * Set the duration for occuring long press event. + * + * @param lonpress_timeout Timeout for long press event + * @ingroup Longpress + */ +EAPI void +elm_longpress_timeout_set(double longpress_timeout) +{ + _elm_config->longpress_timeout = longpress_timeout; +} + +/** + * Get the duration for occuring long press event. + * + * @return Timeout for long press event + * @ingroup Longpress + */ +EAPI double +elm_longpress_timeout_get(void) +{ + return _elm_config->longpress_timeout; +} diff --git a/src/lib/elm_map.c b/src/lib/elm_map.c new file mode 100644 index 0000000..11fadad --- /dev/null +++ b/src/lib/elm_map.c @@ -0,0 +1,3627 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Map Map + * @ingroup Elementary + * + * This is a widget specifically for displaying the free map OpenStreetMap. + * + * Signals that you can add callbacks for are: + * + * clicked - This is called when a user has clicked the map without dragging + * around. + * + * press - This is called when a user has pressed down on the map. + * + * longpressed - This is called when a user has pressed down on the map for + * a long time without dragging around. + * + * clicked,double - This is called when a user has double-clicked the photo. + * + * load,detail - Map detailed data load begins. + * + * loaded,detail - This is called when all parts of the map are loaded. + * + * zoom,start - Zoom animation started. + * + * zoom,stop - Zoom animation stopped. + * + * zoom,change - Zoom changed when using an auto zoom mode. + * + * scroll - the content has been scrolled (moved) + * + * scroll,anim,start - scrolling animation has started + * + * scroll,anim,stop - scrolling animation has stopped + * + * scroll,drag,start - dragging the contents around has started + * + * scroll,drag,stop - dragging the contents around has stopped + * + * downloaded - This is called when map images are downloaded + * + * TODO : doxygen + */ + + +typedef struct _Widget_Data Widget_Data; +typedef struct _Pan Pan; +typedef struct _Grid Grid; +typedef struct _Grid_Item Grid_Item; +typedef struct _Marker_Group Marker_Group; +typedef struct _Mod_Api Mod_Api; +typedef struct _Event Event; + +#define DEST_DIR_ZOOM_PATH "/tmp/elm_map/%d/%d/" +#define DEST_DIR_PATH DEST_DIR_ZOOM_PATH"%d/" +#define DEST_FILE_PATH "%s%d.png" + +// Map sources +// Currently the size of a tile must be 256*256 +// and the size of the map must be pow(2.0, z)*tile_size +typedef struct _Map_Sources_Tab +{ + Elm_Map_Sources source; + const char *name; + int zoom_min; + int zoom_max; + ElmMapSourceURLFunc url_cb; +} Map_Sources_Tab; + +#define ZOOM_MAX 18 + +//Zemm min is supposed to be 0 +static char *_mapnik_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); +static char *_osmarender_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); +static char *_cyclemap_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); +static char *_maplint_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); +static char *_module_url_cb(Evas_Object *obj, int x, int y, int zoom); +static char * _custom1_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); +static char * _custom2_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); +static char * _custom3_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); +static char * _custom4_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); +static char * _custom5_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); +static char * _custom6_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom); + +static Map_Sources_Tab map_sources_tab[] = +{ + {ELM_MAP_SOURCE_MAPNIK, "Mapnik", 0, 18, _mapnik_url_cb}, + {ELM_MAP_SOURCE_OSMARENDER, "Osmarender", 0, 17, _osmarender_url_cb}, + {ELM_MAP_SOURCE_CYCLEMAP, "Cycle Map", 0, 17, _cyclemap_url_cb}, + {ELM_MAP_SOURCE_MAPLINT, "Maplint", 12, 16, _maplint_url_cb}, + {ELM_MAP_SOURCE_CUSTOM_1, "Custom 1", 0, 18, _custom1_url_cb}, + {ELM_MAP_SOURCE_CUSTOM_2, "Custom 2", 0, 18, _custom2_url_cb}, + {ELM_MAP_SOURCE_CUSTOM_3, "Custom 3", 0, 18, _custom3_url_cb}, + {ELM_MAP_SOURCE_CUSTOM_4, "Custom 4", 0, 18, _custom4_url_cb}, + {ELM_MAP_SOURCE_CUSTOM_5, "Custom 5", 0, 18, _custom5_url_cb}, + {ELM_MAP_SOURCE_CUSTOM_6, "Custom 6", 0, 18, _custom6_url_cb}, + {ELM_MAP_SOURCE_MODULE, "Module", 0, 18, _module_url_cb} +}; + +struct _Elm_Map_Marker_Class +{ + const char *style; + int zoom_displayed; + + struct _Elm_Map_Marker_Class_Func { + ElmMapMarkerGetFunc get; + ElmMapMarkerDelFunc del; //if NULL the object will be destroyed with evas_object_del() + ElmMapMarkerIconGetFunc icon_get; + } func; + + struct { //this part is private, do not modify these values + Eina_Bool set : 1; + Evas_Coord edje_w, edje_h; + } priv; +}; + +struct _Elm_Map_Marker +{ + Widget_Data *wd; + Elm_Map_Marker_Class *clas; + Elm_Map_Group_Class *clas_group; + double longitude, latitude; + + Evas_Coord map_size; + Evas_Coord x[ZOOM_MAX+1], y[ZOOM_MAX+1]; + void *data; + + Marker_Group *groups[ZOOM_MAX+1]; + + Evas_Object *content; +}; + +struct _Elm_Map_Group_Class +{ + const char *style; + void *data; + int zoom_displayed; // display the group if the zoom is >= to zoom_display + int zoom_grouped; // group the markers only if the zoom is <= to zoom_groups + Eina_Bool hide : 1; + + struct { + ElmMapGroupIconGetFunc icon_get; + } func; + + struct { //this part is private, do not modify these values + Eina_Bool set : 1; + Evas_Coord edje_w, edje_h; + Evas_Coord edje_max_w, edje_max_h; + + Eina_List *objs_used; + Eina_List *objs_notused; + } priv; +}; + +struct _Marker_Group +{ + Widget_Data *wd; + Eina_Matrixsparse_Cell *cell; + Elm_Map_Group_Class *clas; + + Eina_List *markers; + long long sum_x, sum_y; + Evas_Coord x, y; + Evas_Coord w, h; + + Evas_Object *obj, *bubble, *sc, *bx, *rect; + Eina_Bool open : 1; + Eina_Bool bringin : 1; + Eina_Bool update_nbelems : 1; + Eina_Bool update_resize : 1; + Eina_Bool update_raise : 1; + Eina_Bool delete_object : 1; +}; + +struct _Grid_Item +{ + Widget_Data *wd; + Evas_Object *img; + //Evas_Object *txt; + const char *file; + struct { + int x, y, w, h; + } src, out; + Eina_Bool want : 1; + Eina_Bool download : 1; + Eina_Bool have : 1; + Ecore_File_Download_Job *job; + int try_num; +}; + +struct _Grid +{ + Widget_Data *wd; + int tsize; // size of tile (tsize x tsize pixels) + int zoom; // zoom level tiles want for optimal display (1, 2, 4, 8) + int iw, ih; // size of image in pixels + int w, h; // size of grid image in pixels (represented by grid) + int gw, gh; // size of grid in tiles + Eina_Matrixsparse *grid; +}; + +struct _Widget_Data +{ + Evas_Object *obj; + Evas_Object *scr; + Evas_Object *pan_smart; + Evas_Object *rect; + Evas_Object *sep_maps_markers; //map objects are below this object and marker objects are on top + Pan *pan; + Evas_Coord pan_x, pan_y, minw, minh; + + int id; + int zoom; + Elm_Map_Zoom_Mode mode; + + Ecore_Job *calc_job; + Ecore_Timer *scr_timer; + Ecore_Timer *long_timer; + Ecore_Animator *zoom_animator; + double t_start, t_end; + struct { + int w, h; + int ow, oh, nw, nh; + struct { + double x, y; + } spos; + } size; + struct { + Eina_Bool show : 1; + Evas_Coord x, y ,w ,h; + } show; + int tsize; + int nosmooth; + int preload_num; + Eina_List *grids; + Eina_Bool resized : 1; + Eina_Bool longpressed : 1; + Eina_Bool on_hold : 1; + Eina_Bool paused : 1; + Eina_Bool paused_markers : 1; + Eina_Bool pinch_zoom : 1; + + struct { + Eina_Bool enabled; + double lon, lat; + } center_on; + + Ecore_Job *markers_place_job; + Eina_Matrixsparse *markers[ZOOM_MAX+1]; + Eina_List *cells_displayed; // list of Eina_Matrixsparse_Cell + Evas_Coord markers_max_num; + int marker_max_w, marker_max_h; + int marker_zoom; + Eina_List *opened_bubbles; //opened bubbles, list of Map_Group * + + Eina_List *groups_clas; // list of Elm_Map_Group_Class* + Eina_List *markers_clas; // list of Elm_Map_Markers_Class* + + Elm_Map_Sources source; + Mod_Api *api; + Eina_List *s_event_list; + int try_num; + int finish_num; +}; + +struct _Mod_Api +{ + Eina_Bool (*obj_hook) (Evas_Object *obj); + Eina_Bool (*obj_unhook) (Evas_Object *obj); + char * (*obj_url_request) (Evas_Object *obj, int x, int y, int zoom); + Eina_Bool (*obj_convert_coord_into_geo) (const Evas_Object *obj, int zoom, int x, int y, int size, double *lon, double *lat); + Eina_Bool (*obj_convert_geo_into_coord) (const Evas_Object *obj, int zoom, double lon, double lat, int size, int *x, int *y); +}; +struct _Pan +{ + Evas_Object_Smart_Clipped_Data __clipped_data; + Widget_Data *wd; +}; + +struct _Event +{ + int device; + + struct { + Evas_Coord x, y; + } prev; + + Evas_Coord x, y, w, h; + + Evas_Object *object; + Ecore_Timer *hold_timer; + + int pinch_dis; +}; + +static int dis_old = 0; +static const char *widtype = NULL; + +static const char SIG_CHANGED[] = "changed"; +static const char SIG_CLICKED[] = "clicked"; +static const char SIG_CLICKED_DOUBLE[] = "clicked,double"; +static const char SIG_LOADED_DETAIL[] = "loaded,detail"; +static const char SIG_LOAD_DETAIL[] = "load,detail"; +static const char SIG_LONGPRESSED[] = "longpressed"; +static const char SIG_PRESS[] = "press"; +static const char SIG_SCROLL[] = "scroll"; +static const char SIG_SCROLL_DRAG_START[] = "scroll,drag,start"; +static const char SIG_SCROLL_DRAG_STOP[] = "scroll,drag,stop"; +static const char SIG_ZOOM_CHANGE[] = "zoom,change"; +static const char SIG_ZOOM_START[] = "zoom,start"; +static const char SIG_ZOOM_STOP[] = "zoom,stop"; +static const char SIG_DOWNLOADED[] = "downloaded"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_CHANGED, ""}, + {SIG_CLICKED, ""}, + {SIG_CLICKED_DOUBLE, ""}, + {SIG_LOADED_DETAIL, ""}, + {SIG_LOAD_DETAIL, ""}, + {SIG_LONGPRESSED, ""}, + {SIG_PRESS, ""}, + {SIG_SCROLL, ""}, + {SIG_SCROLL_DRAG_START, ""}, + {SIG_SCROLL_DRAG_STOP, ""}, + {SIG_ZOOM_CHANGE, ""}, + {SIG_ZOOM_START, ""}, + {SIG_ZOOM_STOP, ""}, + {SIG_DOWNLOADED, ""}, + {NULL, NULL} +}; + +static void _pan_calculate(Evas_Object *obj); + +static Eina_Bool _hold_timer_cb(void *data); +static void _rect_resize_cb(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _on_focus_hook(void *data, Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _calc_job(void *data); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); +static void grid_place(Evas_Object *obj, Grid *g, Evas_Coord px, Evas_Coord py, Evas_Coord ox, Evas_Coord oy, Evas_Coord ow, Evas_Coord oh); +static void grid_clear(Evas_Object *obj, Grid *g); +static Grid *grid_create(Evas_Object *obj); +static void grid_load(Evas_Object *obj, Grid *g); + + +static void _group_object_create(Marker_Group *group); +static void _group_object_free(Marker_Group *group); +static void _group_open_cb(void *data, Evas_Object *obj, const char *emission, const char *soure); +static void _group_bringin_cb(void *data, Evas_Object *obj, const char *emission, const char *soure); +static void _group_bubble_create(Marker_Group *group); +static void _group_bubble_free(Marker_Group *group); +static void _group_bubble_place(Marker_Group *group); + +static int _group_bubble_content_update(Marker_Group *group); +static void _group_bubble_content_free(Marker_Group *group); +static void marker_place(Evas_Object *obj, Grid *g, Evas_Coord px, Evas_Coord py, Evas_Coord ox, Evas_Coord oy, Evas_Coord ow, Evas_Coord oh); +static void _bubble_sc_hits_changed_cb(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static void _mouse_down(void *data, Evas *evas, Evas_Object *obj, void *event_info); +static void _mouse_up(void *data, Evas *evas, Evas_Object *obj, void *event_info); +static void _mouse_move(void *data, Evas *evas, Evas_Object *obj, void *event_info); + +static void _mouse_multi_down(void *data, Evas *evas, Evas_Object *obj, void *event_info); +static void _mouse_multi_up(void *data, Evas *evas, Evas_Object *obj, void *event_info); +static void _mouse_multi_move(void *data, Evas *evas, Evas_Object *obj, void *event_info); + +static int +get_multi_device(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Event *ev; + + EINA_LIST_FOREACH(wd->s_event_list, l, ev) + { + if (ev->device) return ev->device; + } + return 0; +} + +static int +get_distance(Evas_Coord x1, Evas_Coord y1, Evas_Coord x2, Evas_Coord y2) +{ + int dx = x1 - x2; + int dy = y1 - y2; + return sqrt((dx * dx) + (dy * dy)); +} + +static Event * +create_event_object(void *data, Evas_Object *obj, int device) +{ + Widget_Data *wd = elm_widget_data_get(data); + Event *ev = calloc(1, sizeof(Event)); + + EINA_SAFETY_ON_NULL_RETURN_VAL(ev, NULL); + + ev->object = obj; + ev->device = device; + evas_object_geometry_get(obj, &ev->x, &ev->y, &ev->w, &ev->h); + wd->s_event_list = eina_list_append(wd->s_event_list, ev); + return ev; +} + +static Event* +get_event_object(void *data, int device) +{ + Widget_Data *wd = elm_widget_data_get(data); + Eina_List *l; + Event *ev; + + EINA_LIST_FOREACH(wd->s_event_list, l, ev) + { + if (ev->device == device) break; + ev = NULL; + } + return ev; +} + +static void +destroy_event_object(void *data, Event *ev) +{ + Widget_Data *wd = elm_widget_data_get(data); + EINA_SAFETY_ON_NULL_RETURN(ev); + ev->pinch_dis = 0; + wd->s_event_list = eina_list_remove(wd->s_event_list, ev); + if (ev->hold_timer) + { + ecore_timer_del(ev->hold_timer); + ev->hold_timer = NULL; + } + free(ev); +} + +static Mod_Api * +module(Evas_Object *obj __UNUSED__) +{ + static Elm_Module *m = NULL; + if (m) goto ok; + if (!(m = _elm_module_find_as("map/api"))) return NULL; + + m->api = malloc(sizeof(Mod_Api)); + if (!m->api) return NULL; + ((Mod_Api *)(m->api) )->obj_hook = + _elm_module_symbol_get(m, "obj_hook"); + ((Mod_Api *)(m->api) )->obj_unhook = + _elm_module_symbol_get(m, "obj_unhook"); + ((Mod_Api *)(m->api) )->obj_url_request = + _elm_module_symbol_get(m, "obj_url_request"); + ((Mod_Api *)(m->api) )->obj_convert_coord_into_geo = + _elm_module_symbol_get(m, "obj_convert_coord_into_geo"); + ((Mod_Api *)(m->api) )->obj_convert_geo_into_coord = + _elm_module_symbol_get(m, "obj_convert_geo_into_coord"); + ok: + return m->api; +} + +static void +rect_place(Evas_Object *obj, Evas_Coord px, Evas_Coord py, Evas_Coord ox, Evas_Coord oy, Evas_Coord ow, Evas_Coord oh) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord ax, ay, gw, gh, hh, ww; + if (!wd) return; + evas_object_geometry_get(wd->rect, NULL, NULL, &ww, &hh); + + ax = 0; + ay = 0; + gw = wd->size.w; + gh = wd->size.h; + + if ((ww == gw) && (hh == gh)) return; + + if (ow > gw) ax = (ow - gw) / 2; + if (oh > gh) ay = (oh - gh) / 2; + evas_object_move(wd->rect, + ox + 0 - px + ax, + oy + 0 - py + ay); + evas_object_resize(wd->rect, gw, gh); + + if (wd->show.show) + { + wd->show.show = EINA_FALSE; + elm_smart_scroller_child_region_show(wd->scr, wd->show.x, wd->show.y, wd->show.w, wd->show.h); + } +} + +static void +marker_place(Evas_Object *obj, Grid *g, Evas_Coord px, Evas_Coord py, Evas_Coord ox, Evas_Coord oy, Evas_Coord ow, Evas_Coord oh) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord ax, ay, gw, gh, tx, ty; + Eina_List *l, *markers; + Eina_Matrixsparse_Cell *cell; + Marker_Group *group; + int xx, yy, ww, hh; + char buf[PATH_MAX]; + int y, x; + int g_xx, g_yy, g_hh, g_ww; + + if (!wd) return; + if (g != eina_list_data_get(wd->grids)) return; + + ax = 0; + ay = 0; + gw = wd->size.w; + gh = wd->size.h; + if (ow > gw) ax = (ow - gw) / 2; + if (oh > gh) ay = (oh - gh) / 2; + + if (wd->zoom != wd->marker_zoom) + { + EINA_LIST_FREE(wd->cells_displayed, cell) + { + EINA_LIST_FOREACH(eina_matrixsparse_cell_data_get(cell), l, group) + { + if (group->obj) _group_object_free(group); + } + } + } + wd->marker_zoom = wd->zoom; + + if ((wd->paused_markers) + && ((wd->size.nw != wd->size.w) || (wd->size.nh != wd->size.h)) ) + return; + + g_xx = wd->pan_x / wd->tsize; + if (g_xx < 0) g_xx = 0; + g_yy = wd->pan_y / wd->tsize; + if (g_yy < 0) g_yy = 0; + g_ww = ow / wd->tsize + 1; + if (g_xx + g_ww >= g->gw) g_ww = g->gw - g_xx - 1; + g_hh = oh / wd->tsize + 1; + if (g_yy + g_hh >= g->gh) g_hh = g->gh - g_yy - 1; + + //hide groups no more displayed + EINA_LIST_FREE(wd->cells_displayed, cell) + { + eina_matrixsparse_cell_position_get(cell, (unsigned long *)&y, (unsigned long *)&x); + if ((y < g_yy) || (y > g_yy + g_hh) || (x < g_xx) || (x > g_xx + g_ww)) + { + EINA_LIST_FOREACH(eina_matrixsparse_cell_data_get(cell), l, group) + { + if (group->obj) _group_object_free(group); + } + } + } + + for (y = g_yy; y <= g_yy + g_hh; y++) + { + for (x = g_xx; x <= g_xx + g_ww; x++) + { + if (!wd->markers[wd->zoom]) continue; + eina_matrixsparse_cell_idx_get(wd->markers[wd->zoom], y, x, &cell); + if (!cell) continue; + wd->cells_displayed = eina_list_append(wd->cells_displayed, cell); + markers = eina_matrixsparse_cell_data_get(cell); + EINA_LIST_FOREACH(markers, l, group) + { + if (!group->markers) continue; + if (group->clas->zoom_displayed > wd->zoom) continue; + + xx = group->x; + yy = group->y; + ww = group->w; + hh = group->h; + + if (eina_list_count(group->markers) == 1) + { + Elm_Map_Marker *m = eina_list_data_get(group->markers); + ww = m->clas->priv.edje_w; + hh = m->clas->priv.edje_h; + } + + if (ww <= 0) ww = 1; + if (hh <= 0) hh = 1; + + if ((gw != g->w) && (g->w > 0)) + { + tx = xx; + xx = ((long long )gw * xx) / g->w; + ww = (((long long)gw * (tx + ww)) / g->w) - xx; + } + if ((gh != g->h) && (g->h > 0)) + { + ty = yy; + yy = ((long long)gh * yy) / g->h; + hh = (((long long)gh * (ty + hh)) / g->h) - yy; + } + + if ((!group->clas->hide) + && (xx-px+ax+ox >= ox) && (xx-px+ax+ox<= ox+ow) + && (yy-py+ay+oy >= oy) && (yy-py+ay+oy<= oy+oh)) + { + if (!group->obj) _group_object_create(group); + + if (group->update_nbelems) + { + group->update_nbelems = EINA_FALSE; + if (eina_list_count(group->markers) > 1) + { + snprintf(buf, sizeof(buf), "%d", eina_list_count(group->markers)); + edje_object_part_text_set(elm_layout_edje_get(group->obj), "elm.text", buf); + } + else + edje_object_part_text_set(elm_layout_edje_get(group->obj), "elm.text", ""); + } + evas_object_move(group->obj, + xx - px + ax + ox - ww/2, + yy - py + ay + oy - hh/2); + if ((!wd->paused_markers) || (group->update_resize)) + { + group->update_resize = EINA_FALSE; + evas_object_resize(group->obj, ww, hh); + } + if (group->update_raise) + { + group->update_raise = EINA_FALSE; + evas_object_raise(group->obj); + evas_object_show(group->obj); + } + if (group->bubble) _group_bubble_place(group); + } + else if (group->obj) + { + _group_object_free(group); + } + } + } + } +} + +static void +grid_place(Evas_Object *obj, Grid *g, Evas_Coord px, Evas_Coord py, Evas_Coord ox, Evas_Coord oy, Evas_Coord ow, Evas_Coord oh) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord ax, ay, gw, gh, tx, ty; + int xx, yy, ww, hh; + + if (!wd) return; + + ax = 0; + ay = 0; + gw = wd->size.w; + gh = wd->size.h; + if (ow > gw) ax = (ow - gw) / 2; + if (oh > gh) ay = (oh - gh) / 2; + + Eina_Iterator *it = eina_matrixsparse_iterator_new(g->grid); + Eina_Matrixsparse_Cell *cell; + + EINA_ITERATOR_FOREACH(it, cell) + { + Grid_Item *gi = eina_matrixsparse_cell_data_get(cell); + + xx = gi->out.x; + yy = gi->out.y; + ww = gi->out.w; + hh = gi->out.h; + if ((gw != g->w) && (g->w > 0)) + { + tx = xx; + xx = ((long long )gw * xx) / g->w; + ww = (((long long)gw * (tx + ww)) / g->w) - xx; + } + if ((gh != g->h) && (g->h > 0)) + { + ty = yy; + yy = ((long long)gh * yy) / g->h; + hh = (((long long)gh * (ty + hh)) / g->h) - yy; + } + evas_object_move(gi->img, + xx - px + ax + ox, + yy - py + ay + oy); + + evas_object_resize(gi->img, ww, hh); + + /*evas_object_move(gi->txt, + xx - px + ax + ox, + yy - py + ay + oy); + + evas_object_resize(gi->txt, ww, hh); + */ + } + eina_iterator_free(it); +} + +static void +grid_clear(Evas_Object *obj, Grid *g) +{ + Widget_Data *wd = elm_widget_data_get(obj); + char buf[PATH_MAX]; + + if (!wd) return; + if (!g->grid) return; + + Eina_Iterator *it = eina_matrixsparse_iterator_new(g->grid); + Eina_Matrixsparse_Cell *cell; + + snprintf(buf, sizeof(buf), DEST_DIR_ZOOM_PATH, wd->id, g->zoom); + ecore_file_recursive_rm(buf); + + EINA_ITERATOR_FOREACH(it, cell) + { + Grid_Item *gi = eina_matrixsparse_cell_data_get(cell); + evas_object_del(gi->img); + //evas_object_del(gi->txt); + + if (gi->want) + { + gi->want = EINA_FALSE; + wd->preload_num--; + if (!wd->preload_num) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,state,busy,stop", "elm"); + evas_object_smart_callback_call(obj, SIG_LOADED_DETAIL, NULL); + } + } + + if (gi->job) + { + DBG("DOWNLOAD abort %s", gi->file); + ecore_file_download_abort(gi->job); + ecore_file_remove(gi->file); + gi->job = NULL; + wd->try_num--; + } + if (gi->file) + eina_stringshare_del(gi->file); + + free(gi); + } + eina_matrixsparse_free(g->grid); + eina_iterator_free(it); + g->grid = NULL; + g->gw = 0; + g->gh = 0; +} + +static void +_tile_update(Grid_Item *gi) +{ + gi->want = EINA_FALSE; + gi->download = EINA_FALSE; + evas_object_image_file_set(gi->img, gi->file, NULL); + if (evas_object_image_load_error_get(gi->img) != EVAS_LOAD_ERROR_NONE) + ecore_file_remove(gi->file); + + evas_object_show(gi->img); + + //evas_object_text_text_set(gi->txt, gi->file); + //evas_object_show(gi->txt); + + gi->have = EINA_TRUE; + gi->wd->preload_num--; + if (!gi->wd->preload_num) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(gi->wd->scr), + "elm,state,busy,stop", "elm"); + evas_object_smart_callback_call(gi->wd->obj, SIG_LOADED_DETAIL, NULL); + } +} + + +static void +_tile_downloaded(void *data, const char *file __UNUSED__, int status) +{ + Grid_Item *gi = data; + + gi->download = EINA_FALSE; + gi->job = NULL; + + DBG("DOWNLOAD done %s", gi->file); + if ((gi->want) && (!status)) _tile_update(gi); + + if (status) + { + DBG("Download failed %s (%d) ", gi->file, status); + ecore_file_remove(gi->file); + } + else + gi->wd->finish_num++; + + evas_object_smart_callback_call(gi->wd->obj, SIG_DOWNLOADED, NULL); +} + +static Grid * +grid_create(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Grid *g; + + g = calloc(1, sizeof(Grid)); + + g->zoom = wd->zoom; + g->tsize = wd->tsize; + g->wd = wd; + + if (g->zoom > map_sources_tab[wd->source].zoom_max) return NULL; + if (g->zoom < map_sources_tab[wd->source].zoom_min) return NULL; + + int size = pow(2.0, wd->zoom); + g->gw = size; + g->gh = size; + + g->w = g->tsize * g->gw; + g->h = g->tsize * g->gh; + + g->grid = eina_matrixsparse_new(g->gh, g->gw, NULL, NULL); + + return g; +} + +static void +grid_load(Evas_Object *obj, Grid *g) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int x, y; + int size; + Evas_Coord ox, oy, ow, oh, cvx, cvy, cvw, cvh, tx, ty, gw, gh, xx, yy, ww, hh; + Eina_Iterator *it; + Eina_Matrixsparse_Cell *cell; + Grid_Item *gi; + + if (!wd) return; + evas_object_geometry_get(wd->pan_smart, &ox, &oy, &ow, &oh); + evas_output_viewport_get(evas_object_evas_get(wd->obj), &cvx, &cvy, &cvw, &cvh); + + gw = wd->size.w; + gh = wd->size.h; + + if ((gw <= 0) || (gh <= 0)) return; + + size = g->tsize; + if ((gw != g->w) && (g->w > 0)) + size = ((long long)gw * size) / g->w; + if (size < (g->tsize / 2)) return; // else we will load to much tiles + + it = eina_matrixsparse_iterator_new(g->grid); + + EINA_ITERATOR_FOREACH(it, cell) + { + gi = eina_matrixsparse_cell_data_get(cell); + + xx = gi->out.x; + yy = gi->out.y; + ww = gi->out.w; + hh = gi->out.h; + + if ((gw != g->w) && (g->w > 0)) + { + tx = xx; + xx = ((long long )gw * xx) / g->w; + ww = (((long long)gw * (tx + ww)) / g->w) - xx; + } + if ((gh != g->h) && (g->h > 0)) + { + ty = yy; + yy = ((long long)gh * yy) / g->h; + hh = (((long long)gh * (ty + hh)) / g->h) - yy; + } + + if (!ELM_RECTS_INTERSECT(xx - wd->pan_x + ox, + yy - wd->pan_y + oy, + ww, hh, + cvx, cvy, cvw, cvh)) + { + if (gi->want) + { + evas_object_hide(gi->img); + //evas_object_hide(gi->txt); + evas_object_image_file_set(gi->img, NULL, NULL); + gi->want = EINA_FALSE; + gi->have = EINA_FALSE; + + if (gi->job) + { + DBG("DOWNLOAD abort %s", gi->file); + ecore_file_download_abort(gi->job); + ecore_file_remove(gi->file); + gi->job = NULL; + wd->try_num--; + } + gi->download = EINA_FALSE; + wd->preload_num--; + if (!wd->preload_num) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,state,busy,stop", "elm"); + evas_object_smart_callback_call(obj, SIG_LOADED_DETAIL, + NULL); + } + + } + else if (gi->have) + { + evas_object_hide(gi->img); + //evas_object_hide(gi->txt); + evas_object_image_preload(gi->img, 1); + evas_object_image_file_set(gi->img, NULL, NULL); + gi->have = EINA_FALSE; + gi->want = EINA_FALSE; + } + } + } + eina_iterator_free(it); + + xx = wd->pan_x / size; + if (xx < 0) xx = 0; + + yy = wd->pan_y / size; + if (yy < 0) yy = 0; + + ww = ow / size + 1; + if (xx + ww >= g->gw) ww = g->gw - xx - 1; + + hh = oh / size + 1; + if (yy + hh >= g->gh) hh = g->gh - yy - 1; + + for (y = yy; y <= yy + hh; y++) + { + for (x = xx; x <= xx + ww; x++) + { + gi = eina_matrixsparse_data_idx_get(g->grid, y, x); + + if ((!gi) && (g != eina_list_data_get(wd->grids))) + continue; + + if (!gi) + { + gi = calloc(1, sizeof(Grid_Item)); + gi->src.x = x * g->tsize; + gi->src.y = y * g->tsize; + gi->src.w = g->tsize; + gi->src.h = g->tsize; + + gi->out.x = gi->src.x; + gi->out.y = gi->src.y; + gi->out.w = gi->src.w; + gi->out.h = gi->src.h; + + gi->wd = wd; + + gi->img = evas_object_image_add(evas_object_evas_get(obj)); + evas_object_image_scale_hint_set + (gi->img, EVAS_IMAGE_SCALE_HINT_DYNAMIC); + evas_object_image_filled_set(gi->img, 1); + + evas_object_smart_member_add(gi->img, wd->pan_smart); + elm_widget_sub_object_add(obj, gi->img); + evas_object_pass_events_set(gi->img, EINA_TRUE); + evas_object_stack_below(gi->img, wd->sep_maps_markers); + + /*gi->txt = evas_object_text_add(evas_object_evas_get(obj)); + evas_object_text_font_set(gi->txt, "Vera", 12); + evas_object_color_set(gi->txt, 100, 100, 100, 255); + evas_object_smart_member_add(gi->txt, + wd->pan_smart); + elm_widget_sub_object_add(obj, gi->txt); + evas_object_pass_events_set(gi->txt, EINA_TRUE); + */ + eina_matrixsparse_data_idx_set(g->grid, y, x, gi); + } + + if ((!gi->have) && (!gi->download)) + { + char buf[PATH_MAX], buf2[PATH_MAX]; + char *source; + + gi->want = EINA_TRUE; + + snprintf(buf, sizeof(buf), DEST_DIR_PATH, wd->id, g->zoom, x); + if (!ecore_file_exists(buf)) + ecore_file_mkpath(buf); + + snprintf(buf2, sizeof(buf2), DEST_FILE_PATH, buf, y); + + source = map_sources_tab[wd->source].url_cb(obj, x, y, g->zoom); + if ((!source) || (strlen(source)==0)) continue; + + eina_stringshare_replace(&gi->file, buf2); + + if ((ecore_file_exists(buf2)) || (g == eina_list_data_get(wd->grids))) + { + gi->download = EINA_TRUE; + wd->preload_num++; + if (wd->preload_num == 1) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,state,busy,start", "elm"); + evas_object_smart_callback_call(obj, + SIG_LOAD_DETAIL, + NULL); + } + + if (ecore_file_exists(buf2)) + _tile_update(gi); + else + { + DBG("DOWNLOAD %s \t in %s", source, buf2); + ecore_file_download(source, buf2, _tile_downloaded, NULL, gi, &(gi->job)); + if (!gi->job) + DBG("Can't start to download %s", buf); + else + wd->try_num++; + } + } + if (source) free(source); + } + else if (gi->have) + evas_object_show(gi->img); + } + } +} + +static void +grid_clearall(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Grid *g; + + if (!wd) return; + EINA_LIST_FREE(wd->grids, g) + { + grid_clear(obj, g); + free(g); + } +} + +static void +_smooth_update(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Grid *g; + + if (!wd) return; + EINA_LIST_FOREACH(wd->grids, l, g) + { + Eina_Iterator *it = eina_matrixsparse_iterator_new(g->grid); + Eina_Matrixsparse_Cell *cell; + + EINA_ITERATOR_FOREACH(it, cell) + { + Grid_Item *gi = eina_matrixsparse_cell_data_get(cell); + evas_object_image_smooth_scale_set(gi->img, (!wd->nosmooth)); + } + eina_iterator_free(it); + } +} + +static void +_grid_raise(Grid *g) +{ + Eina_Iterator *it = eina_matrixsparse_iterator_new(g->grid); + Eina_Matrixsparse_Cell *cell; + + g->wd->size.w = g->w; + g->wd->size.h = g->h; + + EINA_ITERATOR_FOREACH(it, cell) + { + Grid_Item *gi = eina_matrixsparse_cell_data_get(cell); + evas_object_raise(gi->img); + //evas_object_raise(gi->txt); + } + eina_iterator_free(it); +} + +static Eina_Bool +_scr_timeout(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->nosmooth--; + if (!wd->nosmooth) _smooth_update(data); + wd->scr_timer = NULL; + return ECORE_CALLBACK_CANCEL; +} + +static void +_scr(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (!wd->scr_timer) + { + wd->nosmooth++; + if (wd->nosmooth == 1) _smooth_update(data); + } + if (wd->scr_timer) ecore_timer_del(wd->scr_timer); + wd->scr_timer = ecore_timer_add(0.5, _scr_timeout, data); +} + +static Eina_Bool +zoom_do(Evas_Object *obj, double t) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord xx, yy, ow, oh; + + if (!wd) return 0; + if (t > 1.0) t = 1.0; + + wd->size.w = (wd->size.ow * (1.0 - t)) + (wd->size.nw * t); + wd->size.h = (wd->size.oh * (1.0 - t)) + (wd->size.nh * t); + + elm_smart_scroller_child_viewport_size_get(wd->scr, &ow, &oh); + + if (wd->center_on.enabled) + { + elm_map_utils_convert_geo_into_coord(obj, wd->center_on.lon, wd->center_on.lat, wd->size.w, &xx, &yy); + xx -= ow / 2; + yy -= oh / 2; + } + else + { + xx = (wd->size.spos.x * wd->size.w) - (ow / 2); + yy = (wd->size.spos.y * wd->size.h) - (oh / 2); + } + + if (xx < 0) xx = 0; + else if (xx > (wd->size.w - ow)) xx = wd->size.w - ow; + if (yy < 0) yy = 0; + else if (yy > (wd->size.h - oh)) yy = wd->size.h - oh; + + wd->show.show = EINA_TRUE; + wd->show.x = xx; + wd->show.y = yy; + wd->show.w = ow; + wd->show.h = oh; + + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + if (t >= 1.0) + { + return ECORE_CALLBACK_CANCEL; + } + return ECORE_CALLBACK_RENEW; +} + +static Eina_Bool +_zoom_anim(void *data) +{ + Evas_Object *obj = data; + Widget_Data *wd = elm_widget_data_get(obj); + double t; + int go; + + if (!wd) return ECORE_CALLBACK_CANCEL; + t = ecore_loop_time_get(); + if (t >= wd->t_end) + t = 1.0; + else if (wd->t_end > wd->t_start) + t = (t - wd->t_start) / (wd->t_end - wd->t_start); + else + t = 1.0; + t = 1.0 - t; + t = 1.0 - (t * t); + go = zoom_do(obj, t); + if (!go) + { + wd->nosmooth--; + if (!wd->nosmooth) _smooth_update(data); + wd->zoom_animator = NULL; + evas_object_smart_callback_call(obj, SIG_ZOOM_STOP, NULL); + } + return go; +} + +static Eina_Bool +_long_press(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->long_timer = NULL; + wd->longpressed = EINA_TRUE; + evas_object_smart_callback_call(data, SIG_LONGPRESSED, NULL); + return ECORE_CALLBACK_CANCEL; +} + +static void +_mouse_down(void *data, Evas *evas __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Down *ev = event_info; + Event *ev0; + + ev0 = get_event_object(data, 0); + if (ev0) return; + ev0 = create_event_object(data, obj, 0); + if (!ev0) return; + + ev0->hold_timer = NULL; + ev0->prev.x = ev->output.x; + ev0->prev.y = ev->output.y; + + if (!wd) return; + if (ev->button != 1) return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) wd->on_hold = EINA_TRUE; + else wd->on_hold = EINA_FALSE; + if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK) + evas_object_smart_callback_call(data, SIG_CLICKED_DOUBLE, ev); + else + evas_object_smart_callback_call(data, SIG_PRESS, ev); + wd->longpressed = EINA_FALSE; + if (wd->long_timer) ecore_timer_del(wd->long_timer); + wd->long_timer = ecore_timer_add(_elm_config->longpress_timeout, _long_press, data); +} + +static void +_mouse_move(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Move *move = event_info; + Event *ev0; + + if (wd->pinch_zoom) return; + ev0 = get_event_object(data, 0); + if (!ev0) return; + ev0->prev.x = move->cur.output.x; + ev0->prev.y = move->cur.output.y; +} + +static void +_mouse_up(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Up *ev = event_info; + int mdevice; + Event *ev0; + Event *ev1; + + ev0 = get_event_object(data, 0); + if (ev0) + { + mdevice = get_multi_device(data); + if (mdevice == 0) + { + if (ev0->hold_timer) + { + ecore_timer_del(ev0->hold_timer); + ev0->hold_timer = NULL; + } + elm_smart_scroller_hold_set(wd->scr, 0); + elm_smart_scroller_freeze_set(wd->scr, 0); + wd->pinch_zoom = EINA_FALSE; + } + else + { + ev1 = get_event_object(data, mdevice); + if (ev1) + ev1->hold_timer = ecore_timer_add(0.35, _hold_timer_cb, ev1); + } + destroy_event_object(data, ev0); + } + + if (!wd) return; + if (ev->button != 1) return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) wd->on_hold = EINA_TRUE; + else wd->on_hold = EINA_FALSE; + if (wd->long_timer) + { + ecore_timer_del(wd->long_timer); + wd->long_timer = NULL; + } + if (!wd->on_hold) evas_object_smart_callback_call(data, SIG_CLICKED, ev); + wd->on_hold = EINA_FALSE; +} + +static void +_mouse_multi_down(void *data, Evas *evas __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Event *ev; + Evas_Event_Multi_Down *down = event_info; + + elm_smart_scroller_hold_set(wd->scr, 1); + elm_smart_scroller_freeze_set(wd->scr, 1); + + ev = get_event_object(data, down->device); + if (ev) goto done; + + ev = create_event_object(data, obj, down->device); + if (!ev) + { + DBG("Failed : create_event_object"); + goto done; + } + + wd->pinch_zoom = EINA_FALSE; + + ev->hold_timer = NULL; + ev->prev.x = down->output.x; + ev->prev.y = down->output.y; + +done: + return; +} + +static void +_mouse_multi_move(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Multi_Move *move = event_info; + int dis_new, zoom; + Event *ev0; + Event *ev; + + if (wd->pinch_zoom) return; + ev = get_event_object(data, move->device); + if (!ev) return; + + ev->prev.x = move->cur.output.x; + ev->prev.y = move->cur.output.y; + + ev0 = get_event_object(data, 0); + if (!ev0) return; + + dis_new = get_distance(ev0->prev.x, ev0->prev.y, ev->prev.x, ev->prev.y); + zoom = wd->zoom; + + if (dis_old) + { + if (((dis_old - dis_new) > 0) && + (ev->pinch_dis > elm_finger_size_get())) + { + wd->pinch_zoom = EINA_TRUE; + zoom--; + elm_map_zoom_set(data, zoom); + ev->pinch_dis = 0; + } + else if (((dis_old - dis_new) < 0) && + (ev->pinch_dis < -elm_finger_size_get())) + { + wd->pinch_zoom = EINA_TRUE; + zoom++; + elm_map_zoom_set(data, zoom); + ev->pinch_dis = 0; + } + ev->pinch_dis += (dis_old - dis_new); + } + dis_old = dis_new; +} + +static void +_mouse_multi_up(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Event_Multi_Up *up = event_info; + Event *ev0; + Event *ev; + + ev = get_event_object(data, up->device); + if (!ev) + { + DBG("Cannot get multi device"); + return; + } + dis_old = 0; + + ev0 = get_event_object(data, 0); + if (ev0) + ev0->hold_timer = ecore_timer_add(0.35, _hold_timer_cb, ev0); + else + { + if (ev->hold_timer) + { + ecore_timer_del(ev->hold_timer); + ev->hold_timer = NULL; + } + } + destroy_event_object(data, ev); +} + +static Evas_Smart_Class _pan_sc = EVAS_SMART_CLASS_INIT_NULL; + +static Eina_Bool +_hold_timer_cb(void *data) +{ + Event *ev0 = data; + + ev0->hold_timer = NULL; + return ECORE_CALLBACK_CANCEL; +} + +static void +_rect_resize_cb(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + int x, y, w, h; + + evas_object_geometry_get(wd->rect, &x, &y, &w, &h); + evas_object_geometry_get(wd->pan_smart, &x, &y, &w, &h); + evas_object_resize(wd->rect, w, h); + evas_object_move(wd->rect, x, y); +} + +static void +_del_hook(Evas_Object *obj) +{ + Elm_Map_Group_Class *group_clas; + Elm_Map_Marker_Class *marker_clas; + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Event *ev; + + if (!wd) return; + + EINA_LIST_FREE(wd->groups_clas, group_clas) + { + if (group_clas->style) + eina_stringshare_del(group_clas->style); + free(group_clas); + } + + EINA_LIST_FREE(wd->markers_clas, marker_clas) + { + if (marker_clas->style) + eina_stringshare_del(marker_clas->style); + free(marker_clas); + } + + EINA_LIST_FOREACH(wd->s_event_list, l, ev) + { + destroy_event_object(obj, ev); + } + + if (wd->calc_job) ecore_job_del(wd->calc_job); + if (wd->scr_timer) ecore_timer_del(wd->scr_timer); + if (wd->zoom_animator) ecore_animator_del(wd->zoom_animator); + if (wd->long_timer) ecore_timer_del(wd->long_timer); + if ((wd->api) && (wd->api->obj_unhook)) wd->api->obj_unhook(obj); + + free(wd); +} + +static void +_del_pre_hook(Evas_Object *obj) +{ + Marker_Group *group; + Elm_Map_Marker *marker; + int i; + Eina_Bool free_marker = EINA_TRUE; + Eina_List *l; + Widget_Data *wd = elm_widget_data_get(obj); + grid_clearall(obj); + + if (!wd) return; + for (i = 0; i < ZOOM_MAX + 1; i++) + { + if (!wd->markers[i]) continue; + Eina_Iterator *it = eina_matrixsparse_iterator_new(wd->markers[i]); + Eina_Matrixsparse_Cell *cell; + + EINA_ITERATOR_FOREACH(it, cell) + { + l = eina_matrixsparse_cell_data_get(cell); + EINA_LIST_FREE(l, group) + { + EINA_LIST_FREE(group->markers, marker) + { + evas_object_event_callback_del_full(group->sc, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _bubble_sc_hits_changed_cb, group); + if (free_marker) free(marker); + } + free(group); + } + free_marker = EINA_FALSE; + } + eina_iterator_free(it); + eina_matrixsparse_free(wd->markers[i]); + } + + evas_object_del(wd->sep_maps_markers); + evas_object_del(wd->pan_smart); + wd->pan_smart = NULL; +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->obj, "elm,action,focus", "elm"); + evas_object_focus_set(wd->obj, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->obj, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->obj, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_object_theme_set(obj, wd->scr, "map", "base", elm_widget_style_get(obj)); +// edje_object_scale_set(wd->scr, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + evas_object_size_hint_max_get(wd->scr, &maxw, &maxh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_calc_job(void *data) +{ + Widget_Data *wd = data; + Evas_Coord minw, minh; + + minw = wd->size.w; + minh = wd->size.h; + if (wd->resized) + { + wd->resized = 0; + if (wd->mode != ELM_MAP_ZOOM_MODE_MANUAL) + { + double tz = wd->zoom; + wd->zoom = 0.0; + elm_map_zoom_set(wd->obj, tz); + } + } + if ((minw != wd->minw) || (minh != wd->minh)) + { + wd->minw = minw; + wd->minh = minh; + evas_object_smart_callback_call(wd->pan_smart, SIG_CHANGED, NULL); + _sizing_eval(wd->obj); + } + wd->calc_job = NULL; + evas_object_smart_changed(wd->pan_smart); +} + +static void +_pan_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if ((x == sd->wd->pan_x) && (y == sd->wd->pan_y)) return; + sd->wd->pan_x = x; + sd->wd->pan_y = y; + evas_object_smart_changed(obj); +} + +static void +_pan_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (x) *x = sd->wd->pan_x; + if (y) *y = sd->wd->pan_y; +} + +static void +_pan_max_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ow, oh; + if (!sd) return; + evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); + ow = sd->wd->minw - ow; + if (ow < 0) ow = 0; + oh = sd->wd->minh - oh; + if (oh < 0) oh = 0; + if (x) *x = ow; + if (y) *y = oh; +} + +static void +_pan_min_get(Evas_Object *obj __UNUSED__, Evas_Coord *x, Evas_Coord *y) +{ + if (x) *x = 0; + if (y) *y = 0; +} + +static void +_pan_child_size_get(Evas_Object *obj, Evas_Coord *w, Evas_Coord *h) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (w) *w = sd->wd->minw; + if (h) *h = sd->wd->minh; +} + +static void +_pan_add(Evas_Object *obj) +{ + Pan *sd; + Evas_Object_Smart_Clipped_Data *cd; + _pan_sc.add(obj); + cd = evas_object_smart_data_get(obj); + if (!cd) return; + sd = calloc(1, sizeof(Pan)); + if (!sd) return; + sd->__clipped_data = *cd; + free(cd); + evas_object_smart_data_set(obj, sd); +} + +static void +_pan_del(Evas_Object *obj) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + _pan_sc.del(obj); +} + +static void +_pan_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ow, oh; + if (!sd) return; + evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); + if ((ow == w) && (oh == h)) return; + sd->wd->resized = 1; + if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job); + sd->wd->calc_job = ecore_job_add(_calc_job, sd->wd); +} + +static void +_pan_calculate(Evas_Object *obj) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ox, oy, ow, oh; + Eina_List *l; + Grid *g; + if (!sd) return; + evas_object_geometry_get(obj, &ox, &oy, &ow, &oh); + rect_place(sd->wd->obj, sd->wd->pan_x, sd->wd->pan_y, ox, oy, ow, oh); + EINA_LIST_FOREACH(sd->wd->grids, l, g) + { + grid_load(sd->wd->obj, g); + grid_place(sd->wd->obj, g, sd->wd->pan_x, sd->wd->pan_y, ox, oy, ow, oh); + marker_place(sd->wd->obj, g, sd->wd->pan_x, sd->wd->pan_y, ox, oy, ow, oh); + } +} + +static void +_pan_move(Evas_Object *obj, Evas_Coord x __UNUSED__, Evas_Coord y __UNUSED__) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job); + sd->wd->calc_job = ecore_job_add(_calc_job, sd->wd); +} + +static void +_hold_on(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_hold_set(wd->scr, 1); +} + +static void +_hold_off(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_hold_set(wd->scr, 0); +} + +static void +_freeze_on(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_freeze_set(wd->scr, 1); +} + +static void +_freeze_off(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_freeze_set(wd->scr, 0); +} + +static void +_scr_anim_start(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll,anim,start", NULL); +} + +static void +_scr_anim_stop(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll,anim,stop", NULL); +} + +static void +_scr_drag_start(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + wd->center_on.enabled = EINA_FALSE; + evas_object_smart_callback_call(data, SIG_SCROLL_DRAG_START, NULL); +} + +static void +_scr_drag_stop(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_SCROLL_DRAG_STOP, NULL); +} + +static void +_scr_scroll(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_SCROLL, NULL); +} + + +static void +_group_object_create(Marker_Group *group) +{ + const char *style = "radio"; + Evas_Object *icon = NULL; + + if (group->obj) return; + if ((!group->clas->priv.objs_notused) || (eina_list_count(group->markers) == 1)) + { + //set icon and style + if (eina_list_count(group->markers) == 1) + { + Elm_Map_Marker *m = eina_list_data_get(group->markers); + if (m->clas->style) + style = m->clas->style; + + if (m->clas->func.icon_get) + icon = m->clas->func.icon_get(group->wd->obj, m, m->data); + + group->delete_object = EINA_TRUE; + } + else + { + if (group->clas->style) + style = group->clas->style; + + if (group->clas->func.icon_get) + icon = group->clas->func.icon_get(group->wd->obj, group->clas->data); + + group->delete_object = EINA_FALSE; + } + + group->obj = elm_layout_add(group->wd->obj); + elm_layout_theme_set(group->obj, "map/marker", style, elm_widget_style_get(group->wd->obj)); + + if (icon) elm_layout_content_set(group->obj, "elm.icon", icon); + + evas_object_smart_member_add(group->obj, group->wd->pan_smart); + elm_widget_sub_object_add(group->wd->obj, group->obj); + evas_object_stack_above(group->obj, group->wd->sep_maps_markers); + + if (!group->delete_object) + group->clas->priv.objs_used = eina_list_append(group->clas->priv.objs_used, group->obj); + } + else + { + group->delete_object = EINA_FALSE; + + group->obj = eina_list_data_get(group->clas->priv.objs_notused); + group->clas->priv.objs_used = eina_list_append(group->clas->priv.objs_used, group->obj); + group->clas->priv.objs_notused = eina_list_remove(group->clas->priv.objs_notused, group->obj); + evas_object_show(group->obj); + } + + edje_object_signal_callback_add(elm_layout_edje_get(group->obj), "open", "elm", _group_open_cb, group); + edje_object_signal_callback_add(elm_layout_edje_get(group->obj), "bringin", "elm", _group_bringin_cb, group); + + group->update_nbelems = EINA_TRUE; + group->update_resize = EINA_TRUE; + group->update_raise = EINA_TRUE; + + if (group->open) _group_bubble_create(group); +} + +static void +_group_object_free(Marker_Group *group) +{ + if (!group->obj) return; + if (!group->delete_object) + { + group->clas->priv.objs_notused = eina_list_append(group->clas->priv.objs_notused, group->obj); + group->clas->priv.objs_used = eina_list_remove(group->clas->priv.objs_used, group->obj); + evas_object_hide(group->obj); + + edje_object_signal_callback_del(elm_layout_edje_get(group->obj), "open", "elm", _group_open_cb); + edje_object_signal_callback_del(elm_layout_edje_get(group->obj), "bringin", "elm", _group_bringin_cb); + } + else + evas_object_del(group->obj); + + group->obj = NULL; + _group_bubble_free(group); +} + +static void +_group_bubble_mouse_up_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Marker_Group *group = data; + + if (!evas_object_above_get(group->rect)) return; + evas_object_raise(group->bubble); + evas_object_raise(group->sc); + evas_object_raise(group->rect); +} + +static void +_group_bubble_create(Marker_Group *group) +{ + if (group->bubble) return; + + group->wd->opened_bubbles = eina_list_append(group->wd->opened_bubbles, group); + group->bubble = edje_object_add(evas_object_evas_get(group->obj)); + _elm_theme_object_set(group->wd->obj, group->bubble, "map", "marker_bubble", + elm_widget_style_get(group->wd->obj)); + evas_object_smart_member_add(group->bubble, + group->wd->obj); + elm_widget_sub_object_add(group->wd->obj, group->bubble); + + _group_bubble_content_free(group); + if (!_group_bubble_content_update(group)) + { + //no content, we can delete the bubble + _group_bubble_free(group); + return; + } + + group->rect = evas_object_rectangle_add(evas_object_evas_get(group->obj)); + evas_object_color_set(group->rect, 0, 0, 0, 0); + evas_object_repeat_events_set(group->rect, EINA_TRUE); + evas_object_smart_member_add(group->rect, group->wd->obj); + elm_widget_sub_object_add(group->wd->obj, group->rect); + + evas_object_event_callback_add(group->rect, EVAS_CALLBACK_MOUSE_UP, _group_bubble_mouse_up_cb, group); + + _group_bubble_place(group); +} + +static void _bubble_sc_hits_changed_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _group_bubble_place(data); +} + +static int +_group_bubble_content_update(Marker_Group *group) +{ + Eina_List *l; + Elm_Map_Marker *marker; + int i = 0; + + if (!group->bubble) return 1; + + if (!group->sc) + { + group->sc = elm_scroller_add(group->bubble); + elm_scroller_content_min_limit(group->sc, EINA_FALSE, EINA_TRUE); + elm_scroller_policy_set(group->sc, ELM_SCROLLER_POLICY_AUTO, ELM_SCROLLER_POLICY_OFF); + elm_scroller_bounce_set(group->sc, _elm_config->thumbscroll_bounce_enable, EINA_FALSE); + edje_object_part_swallow(group->bubble, "elm.swallow.content", group->sc); + evas_object_show(group->sc); + evas_object_smart_member_add(group->sc, + group->wd->obj); + elm_widget_sub_object_add(group->wd->obj, group->sc); + + group->bx = elm_box_add(group->bubble); + evas_object_size_hint_align_set(group->bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(group->bx, 0.5, 0.5); + elm_box_horizontal_set(group->bx, EINA_TRUE); + evas_object_show(group->bx); + + elm_scroller_content_set(group->sc, group->bx); + + evas_object_event_callback_add(group->sc, EVAS_CALLBACK_RESIZE, + _bubble_sc_hits_changed_cb, group); + } + + EINA_LIST_FOREACH(group->markers, l, marker) + { + if (i >= group->wd->markers_max_num) break; + if ((!marker->content) && (marker->clas->func.get)) + marker->content = marker->clas->func.get(group->wd->obj, marker, marker->data); + else if (marker->content) + elm_box_unpack(group->bx, marker->content); + if (marker->content) + { + elm_box_pack_end(group->bx, marker->content); + i++; + } + } + return i; +} + +static void +_group_bubble_content_free(Marker_Group *group) +{ + Eina_List *l; + Elm_Map_Marker *marker; + + if (!group->sc) return; + EINA_LIST_FOREACH(group->markers, l, marker) + { + if ((marker->content) && (marker->clas->func.del)) + marker->clas->func.del(group->wd->obj, marker, marker->data, marker->content); + else if (marker->content) + evas_object_del(marker->content); + marker->content = NULL; + } + evas_object_del(group->sc); + group->sc = NULL; +} + +static void +_group_bubble_free(Marker_Group *group) +{ + if (!group->bubble) return; + group->wd->opened_bubbles = eina_list_remove(group->wd->opened_bubbles, group); + evas_object_event_callback_del_full(group->sc, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _bubble_sc_hits_changed_cb, group); + evas_object_del(group->bubble); + evas_object_del(group->rect); + group->bubble = NULL; + _group_bubble_content_free(group); +} + +static void +_group_bubble_place(Marker_Group *group) +{ + Evas_Coord x, y, w; + Evas_Coord xx, yy, ww, hh; + const char *s; + + if ((!group->bubble) || (!group->obj)) return; + + evas_object_geometry_get(group->obj, &x, &y, &w, NULL); + edje_object_size_min_calc(group->bubble, NULL, &hh); + + s = edje_object_data_get(group->bubble, "size_w"); + ww = atoi(s); + xx = x + w / 2 - ww / 2; + yy = y-hh; + + evas_object_move(group->bubble, xx, yy); + evas_object_resize(group->bubble, ww, hh); + evas_object_show(group->bubble); + + evas_object_move(group->rect, xx, yy); + evas_object_resize(group->rect, ww, hh); + evas_object_show(group->rect); +} + +static void +_group_bringin_cb(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *soure __UNUSED__) +{ + Marker_Group *group = data; + Elm_Map_Marker *marker = eina_list_data_get(group->markers); + if (!marker) return; + group->bringin = EINA_TRUE; + elm_map_geo_region_bring_in(group->wd->obj, marker->longitude, marker->latitude); +} + +static void +_group_open_cb(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *soure __UNUSED__) +{ + Marker_Group *group = data; + + if (group->bringin) + { + group->bringin = EINA_FALSE; + return; + } + + if (group->bubble) + { + group->open = EINA_FALSE; + _group_bubble_free(group); + return; + } + group->open = EINA_TRUE; + _group_bubble_create(group); +} + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + double zoom; + Evas_Coord x = 0; + Evas_Coord y = 0; + Evas_Coord step_x = 0; + Evas_Coord step_y = 0; + Evas_Coord v_w = 0; + Evas_Coord v_h = 0; + Evas_Coord page_x = 0; + Evas_Coord page_y = 0; + + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + + elm_smart_scroller_child_pos_get(wd->scr, &x, &y); + elm_smart_scroller_step_size_get(wd->scr, &step_x, &step_y); + elm_smart_scroller_page_size_get(wd->scr, &page_x, &page_y); + elm_smart_scroller_child_viewport_size_get(wd->scr, &v_w, &v_h); + + if ((!strcmp(ev->keyname, "Left")) || (!strcmp(ev->keyname, "KP_Left"))) + { + x -= step_x; + } + else if ((!strcmp(ev->keyname, "Right")) || (!strcmp(ev->keyname, "KP_Right"))) + { + x += step_x; + } + else if ((!strcmp(ev->keyname, "Up")) || (!strcmp(ev->keyname, "KP_Up"))) + { + y -= step_y; + } + else if ((!strcmp(ev->keyname, "Down")) || (!strcmp(ev->keyname, "KP_Down"))) + { + y += step_y; + } + else if ((!strcmp(ev->keyname, "Prior")) || (!strcmp(ev->keyname, "KP_Prior"))) + { + if (page_y < 0) + y -= -(page_y * v_h) / 100; + else + y -= page_y; + } + else if ((!strcmp(ev->keyname, "Next")) || (!strcmp(ev->keyname, "KP_Next"))) + { + if (page_y < 0) + y += -(page_y * v_h) / 100; + else + y += page_y; + } + else if (!strcmp(ev->keyname, "KP_Add")) + { + zoom = elm_map_zoom_get(obj); + zoom += 1; + elm_map_zoom_mode_set(obj, ELM_MAP_ZOOM_MODE_MANUAL); + elm_map_zoom_set(obj, zoom); + return EINA_TRUE; + } + else if (!strcmp(ev->keyname, "KP_Subtract")) + { + zoom = elm_map_zoom_get(obj); + zoom -= 1; + elm_map_zoom_mode_set(obj, ELM_MAP_ZOOM_MODE_MANUAL); + elm_map_zoom_set(obj, zoom); + return EINA_TRUE; + } + else return EINA_FALSE; + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + elm_smart_scroller_child_pos_set(wd->scr, x, y); + + return EINA_TRUE; +} + +static int idnum = 1; + +/** + * Add a new Map object + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Map + */ +EAPI Evas_Object * +elm_map_add(Evas_Object *parent) +{ + Evas *e; + Widget_Data *wd; + Evas_Coord minw, minh; + Evas_Object *obj; + static Evas_Smart *smart = NULL; + Eina_Bool bounce = _elm_config->thumbscroll_bounce_enable; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + if (!ecore_file_download_protocol_available("http://")) + { + ERR("Ecore must be built with the support of HTTP for the widget map !"); + return NULL; + } + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "map"); + elm_widget_type_set(obj, "map"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->scr = elm_smart_scroller_add(e); + elm_smart_scroller_widget_set(wd->scr, obj); + elm_smart_scroller_object_theme_set(obj, wd->scr, "map", "base", "default"); + evas_object_smart_callback_add(wd->scr, "scroll", _scr, obj); + evas_object_smart_callback_add(wd->scr, "drag", _scr, obj); + elm_widget_resize_object_set(obj, wd->scr); + + evas_object_smart_callback_add(wd->scr, "animate,start", _scr_anim_start, obj); + evas_object_smart_callback_add(wd->scr, "animate,stop", _scr_anim_stop, obj); + evas_object_smart_callback_add(wd->scr, "drag,start", _scr_drag_start, obj); + evas_object_smart_callback_add(wd->scr, "drag,stop", _scr_drag_stop, obj); + evas_object_smart_callback_add(wd->scr, "scroll", _scr_scroll, obj); + + elm_smart_scroller_bounce_allow_set(wd->scr, bounce, bounce); + + wd->api = module(obj); + if ((wd->api) && (wd->api->obj_hook)) wd->api->obj_hook(obj); + + wd->obj = obj; + + wd->markers_max_num = 30; + wd->source = ELM_MAP_SOURCE_MAPNIK; + + evas_object_smart_callback_add(obj, "scroll-hold-on", _hold_on, obj); + evas_object_smart_callback_add(obj, "scroll-hold-off", _hold_off, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-on", _freeze_on, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-off", _freeze_off, obj); + + if (!smart) + { + static Evas_Smart_Class sc; + + evas_object_smart_clipped_smart_set(&_pan_sc); + sc = _pan_sc; + sc.name = "elm_map_pan"; + sc.version = EVAS_SMART_CLASS_VERSION; + sc.add = _pan_add; + sc.del = _pan_del; + sc.resize = _pan_resize; + sc.move = _pan_move; + sc.calculate = _pan_calculate; + smart = evas_smart_class_new(&sc); + } + if (smart) + { + wd->pan_smart = evas_object_smart_add(e, smart); + wd->pan = evas_object_smart_data_get(wd->pan_smart); + wd->pan->wd = wd; + } + + elm_smart_scroller_extern_pan_set(wd->scr, wd->pan_smart, + _pan_set, _pan_get, _pan_max_get, + _pan_min_get, _pan_child_size_get); + + wd->rect = evas_object_rectangle_add(e); + evas_object_event_callback_add(wd->rect, EVAS_CALLBACK_RESIZE, + _rect_resize_cb, obj); + evas_object_event_callback_add(wd->rect, EVAS_CALLBACK_MOUSE_DOWN, + _mouse_down, obj); + evas_object_event_callback_add(wd->rect, EVAS_CALLBACK_MOUSE_MOVE, + _mouse_move, obj); + evas_object_event_callback_add(wd->rect, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, obj); + evas_object_event_callback_add(wd->rect, EVAS_CALLBACK_MULTI_DOWN, + _mouse_multi_down, obj); + evas_object_event_callback_add(wd->rect, EVAS_CALLBACK_MULTI_MOVE, + _mouse_multi_move, obj); + evas_object_event_callback_add(wd->rect, EVAS_CALLBACK_MULTI_UP, + _mouse_multi_up, obj); + + evas_object_smart_member_add(wd->rect, wd->pan_smart); + elm_widget_sub_object_add(obj, wd->rect); + evas_object_show(wd->rect); + evas_object_color_set(wd->rect, 0, 0, 0, 0); + + wd->zoom = -1; + wd->mode = ELM_MAP_ZOOM_MODE_MANUAL; + wd->id = ((int)getpid() << 16) | idnum; + idnum++; + + wd->tsize = 256; + + edje_object_size_min_calc(elm_smart_scroller_edje_object_get(wd->scr), + &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + + wd->paused = EINA_TRUE; + elm_map_zoom_set(obj, 0); + wd->paused = EINA_FALSE; + + _sizing_eval(obj); + + wd->calc_job = ecore_job_add(_calc_job, wd); + + wd->sep_maps_markers = evas_object_rectangle_add(evas_object_evas_get(obj)); + evas_object_smart_member_add(wd->sep_maps_markers, wd->pan_smart); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the zoom level of the map + * + * This sets the zoom level. 0 is the world map and 18 is the maximum zoom. + * + * @param obj The map object + * @param zoom The zoom level to set + * + * @ingroup Map + */ +EAPI void +elm_map_zoom_set(Evas_Object *obj, int zoom) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Grid *g, *g_zoom = NULL; + Evas_Coord rx, ry, rw, rh; + int z; + int zoom_changed = 0, started = 0; + + if (!wd) return; + if (zoom < 0 ) zoom = 0; + if (zoom > map_sources_tab[wd->source].zoom_max) + zoom = map_sources_tab[wd->source].zoom_max; + if (zoom < map_sources_tab[wd->source].zoom_min) + zoom = map_sources_tab[wd->source].zoom_min; + if (zoom == wd->zoom) return; + + wd->zoom = zoom; + wd->size.ow = wd->size.w; + wd->size.oh = wd->size.h; + elm_smart_scroller_child_pos_get(wd->scr, &rx, &ry); + elm_smart_scroller_child_viewport_size_get(wd->scr, &rw, &rh); + + if (wd->mode == ELM_MAP_ZOOM_MODE_MANUAL) + { + wd->size.nw = pow(2.0, wd->zoom) * wd->tsize; + wd->size.nh = pow(2.0, wd->zoom) * wd->tsize; + } + else if (wd->mode == ELM_MAP_ZOOM_MODE_AUTO_FIT) + { + int p2w, p2h; + int cumulw, cumulh; + + cumulw = wd->tsize; + p2w = 0; + while (cumulw <= rw) + { + p2w++; + cumulw *= 2; + } + p2w--; + + cumulh = wd->tsize; + p2h = 0; + while (cumulh <= rh) + { + p2h++; + cumulh *= 2; + } + p2h--; + + if (p2w < p2h) + z = p2w; + else + z = p2h; + + wd->zoom = z; + wd->size.nw = pow(2.0, wd->zoom) * wd->tsize; + wd->size.nh = pow(2.0, wd->zoom) * wd->tsize; + } + else if (wd->mode == ELM_MAP_ZOOM_MODE_AUTO_FILL) + { + int p2w, p2h; + int cumulw, cumulh; + + cumulw = wd->tsize; + p2w = 0; + while (cumulw <= rw) + { + p2w++; + cumulw *= 2; + } + p2w--; + + cumulh = wd->tsize; + p2h = 0; + while (cumulh <= rh) + { + p2h++; + cumulh *= 2; + } + p2h--; + + if (p2w > p2h) + z = p2w; + else + z = p2h; + + wd->zoom = z; + wd->size.nw = pow(2.0, wd->zoom) * wd->tsize; + wd->size.nh = pow(2.0, wd->zoom) * wd->tsize; + } + + EINA_LIST_FOREACH(wd->grids, l, g) + { + if (g->zoom == wd->zoom) + { + wd->grids = eina_list_remove(wd->grids, g); + wd->grids = eina_list_prepend(wd->grids, g); + _grid_raise(g); + goto done; + } + } + g = grid_create(obj); + if (g) + { + if (eina_list_count(wd->grids) > 1) + { + g_zoom = eina_list_last(wd->grids)->data; + wd->grids = eina_list_remove(wd->grids, g_zoom); + grid_clear(obj, g_zoom); + free(g_zoom); + } + wd->grids = eina_list_prepend(wd->grids, g); + } + else + { + EINA_LIST_FREE(wd->grids, g) + { + grid_clear(obj, g); + free(g); + } + } +done: + + wd->t_start = ecore_loop_time_get(); + wd->t_end = wd->t_start + _elm_config->zoom_friction; + if ((wd->size.w > 0) && (wd->size.h > 0)) + { + wd->size.spos.x = (double)(rx + (rw / 2)) / (double)wd->size.ow; + wd->size.spos.y = (double)(ry + (rh / 2)) / (double)wd->size.oh; + } + else + { + wd->size.spos.x = 0.5; + wd->size.spos.y = 0.5; + } + if (rw > wd->size.ow) wd->size.spos.x = 0.5; + if (rh > wd->size.oh) wd->size.spos.y = 0.5; + if (wd->size.spos.x > 1.0) wd->size.spos.x = 1.0; + if (wd->size.spos.y > 1.0) wd->size.spos.y = 1.0; + if (wd->paused) + { + zoom_do(obj, 1.0); + } + else + { + if (!wd->zoom_animator) + { + wd->zoom_animator = ecore_animator_add(_zoom_anim, obj); + wd->nosmooth++; + if (wd->nosmooth == 1) _smooth_update(obj); + started = 1; + } + } + if (wd->zoom_animator) + { + if (!_zoom_anim(obj)) + { + ecore_animator_del(wd->zoom_animator); + wd->zoom_animator = NULL; + } + } + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + if (!wd->paused) + { + if (started) + evas_object_smart_callback_call(obj, SIG_ZOOM_START, NULL); + if (!wd->zoom_animator) + evas_object_smart_callback_call(obj, SIG_ZOOM_STOP, NULL); + } + + if (zoom_changed) + evas_object_smart_callback_call(obj, SIG_ZOOM_CHANGE, NULL); +} + +/** + * Get the zoom level of the photo + * + * This returns the current zoom level of the map object. Note that if + * you set the fill mode to other than ELM_MAP_ZOOM_MODE_MANUAL + * (which is the default), the zoom level may be changed at any time by the + * map object itself to account for map size and map viewpoer size + * + * @param obj The map object + * @return The current zoom level + * + * @ingroup Map + */ +EAPI double +elm_map_zoom_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 1.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 1.0; + return wd->zoom; +} + +/** + * Set the zoom mode + * + * This sets the zoom mode to manual or one of several automatic levels. + * Manual (ELM_MAP_ZOOM_MODE_MANUAL) means that zoom is set manually by + * elm_map_zoom_set() and will stay at that level until changed by code + * or until zoom mode is changed. This is the default mode. + * The Automatic modes will allow the map object to automatically + * adjust zoom mode based on properties. ELM_MAP_ZOOM_MODE_AUTO_FIT) will + * adjust zoom so the photo fits inside the scroll frame with no pixels + * outside this area. ELM_MAP_ZOOM_MODE_AUTO_FILL will be similar but + * ensure no pixels within the frame are left unfilled. Do not forget that the valid sizes are 2^zoom, consequently the map may be smaller than the scroller view. + * + * @param obj The map object + * @param mode The desired mode + * + * @ingroup Map + */ +EAPI void +elm_map_zoom_mode_set(Evas_Object *obj, Elm_Map_Zoom_Mode mode) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->mode == mode) return; + wd->mode = mode; + { + double tz = wd->zoom; + wd->zoom = 0.0; + elm_map_zoom_set(wd->obj, tz); + } +} + +/** + * Get the zoom mode + * + * This gets the current zoom mode of the map object + * + * @param obj The map object + * @return The current zoom mode + * + * @ingroup Map + */ +EAPI Elm_Map_Zoom_Mode +elm_map_zoom_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_MAP_ZOOM_MODE_MANUAL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_MAP_ZOOM_MODE_MANUAL; + return wd->mode; +} + +/** + * Centers the map at @p lon @p lat using an animation to scroll. + * + * @param obj The map object + * @param lon Longitude to center at + * @param lon Latitude to center at + * + * @ingroup Map + */ +EAPI void +elm_map_geo_region_bring_in(Evas_Object *obj, double lon, double lat) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + int rx, ry, rw, rh; + + if (!wd) return; + elm_map_utils_convert_geo_into_coord(obj, lon, lat, wd->size.w, &rx, &ry); + elm_smart_scroller_child_viewport_size_get(wd->scr, &rw, &rh); + + rx = rx - rw / 2; + ry = ry - rh / 2; + + if (wd->zoom_animator) + { + wd->nosmooth--; + if (!wd->nosmooth) _smooth_update(obj); + ecore_animator_del(wd->zoom_animator); + wd->zoom_animator = NULL; + zoom_do(obj, 1.0); + evas_object_smart_callback_call(obj, SIG_ZOOM_STOP, NULL); + } + elm_smart_scroller_region_bring_in(wd->scr, rx, ry, rw, rh); + + wd->center_on.enabled = EINA_TRUE; + wd->center_on.lon = lon; + wd->center_on.lat = lat; +} + +/** + * Move the map to the current coordinates. + * + * This move the map to the current coordinates. The map will be centered on these coordinates. + * + * @param obj The map object + * @param lat The latitude. + * @param lon The longitude. + * + * @ingroup Map + */ +EAPI void +elm_map_geo_region_show(Evas_Object *obj, double lon, double lat) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + int rx, ry, rw, rh; + + if (!wd) return; + elm_map_utils_convert_geo_into_coord(obj, lon, lat, wd->size.w, &rx, &ry); + elm_smart_scroller_child_viewport_size_get(wd->scr, &rw, &rh); + + rx = rx - rw / 2; + ry = ry - rh / 2; + + if (wd->zoom_animator) + { + wd->nosmooth--; + ecore_animator_del(wd->zoom_animator); + wd->zoom_animator = NULL; + zoom_do(obj, 1.0); + evas_object_smart_callback_call(obj, SIG_ZOOM_STOP, NULL); + } + elm_smart_scroller_child_region_show(wd->scr, rx, ry, rw, rh); + + wd->center_on.enabled = EINA_TRUE; + wd->center_on.lon = lon; + wd->center_on.lat = lat; +} + +/** + * Get the current coordinates of the map. + * + * This gets the current coordinates of the map object. + * + * @param obj The map object + * @param lat The latitude. + * @param lon The longitude. + * + * @ingroup Map + */ +EAPI void +elm_map_geo_region_get(const Evas_Object *obj, double *lon, double *lat) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord sx, sy, sw, sh; + + if (!wd) return; + elm_smart_scroller_child_pos_get(wd->scr, &sx, &sy); + elm_smart_scroller_child_viewport_size_get(wd->scr, &sw, &sh); + sx += sw / 2; + sy += sh / 2; + + elm_map_utils_convert_coord_into_geo(obj, sx, sy, wd->size.w, lon, lat); +} + +/** + * Set the paused state for map + * + * This sets the paused state to on (1) or off (0) for map. The default + * is off. This will stop zooming using animation change zoom levels and + * change instantly. This will stop any existing animations that are running. + * + * @param obj The map object + * @param paused The pause state to set + * + * @ingroup Map + */ +EAPI void +elm_map_paused_set(Evas_Object *obj, Eina_Bool paused) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->paused == !!paused) return; + wd->paused = paused; + if (wd->paused) + { + if (wd->zoom_animator) + { + ecore_animator_del(wd->zoom_animator); + wd->zoom_animator = NULL; + zoom_do(obj, 1.0); + evas_object_smart_callback_call(obj, SIG_ZOOM_STOP, NULL); + } + } +} + +/** + * Set the paused state for the markers + * + * This sets the paused state to on (1) or off (0) for the markers. The default + * is off. This will stop displaying the markers during change zoom levels. Set + * to on if you have a large number of markers. + * + * @param obj The map object + * @param paused The pause state to set + * + * @ingroup Map + */ +EAPI void +elm_map_paused_markers_set(Evas_Object *obj, Eina_Bool paused) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->paused_markers == !!paused) return; + wd->paused_markers = paused; +} + +/** + * Get the paused state for map + * + * This gets the current paused state for the map object. + * + * @param obj The map object + * @return The current paused state + * + * @ingroup Map + */ +EAPI Eina_Bool +elm_map_paused_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->paused; +} + +/** + * Get the paused state for the markers + * + * This gets the current paused state for the markers object. + * + * @param obj The map object + * @return The current paused state + * + * @ingroup Map + */ +EAPI Eina_Bool +elm_map_paused_markers_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->paused_markers; +} + +/** + * Get the information of downloading status + * + * This gets the current downloading status for the map object. + * + * @param obj The map object + * @param try_num the number of download trying map + * @param finish_num the number of downloaded map + * + * @ingroup Map + */ + +EAPI void +elm_map_utils_downloading_status_get(const Evas_Object *obj, int *try_num, int *finish_num) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (try_num) + { + *try_num = wd->try_num; + } + + if (finish_num) + { + *finish_num = wd->finish_num; + } +} +/** + * Convert a pixel coordinate (x,y) into a geographic coordinate (longitude, latitude). + * + * @param obj The map object + * @param x the coordinate + * @param y the coordinate + * @param size the size in pixels of the map. The map is a square and generally his size is : pow(2.0, zoom)*256. + * @param lon the longitude correspond to x + * @param lat the latitude correspond to y + * + * @ingroup Map + */ +EAPI void +elm_map_utils_convert_coord_into_geo(const Evas_Object *obj, int x, int y, int size, double *lon, double *lat) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int zoom = floor(log2(size/256)); + + if (elm_map_source_get(obj) == ELM_MAP_SOURCE_MODULE) + if ((wd->api) && (wd->api->obj_convert_coord_into_geo)) + if (wd->api->obj_convert_coord_into_geo(obj, zoom, x, y, size, lon, lat)) return; + + if (lon) + { + *lon = x / (double)size * 360.0 - 180; + } + if (lat) + { + double n = ELM_PI - 2.0 * ELM_PI * y / size; + *lat = 180.0 / ELM_PI * atan(0.5 * (exp(n) - exp(-n))); + } +} + +/** + * Convert a geographic coordinate (longitude, latitude) into a pixel coordinate (x, y). + * + * @param obj The map object + * @param lon the longitude + * @param lat the latitude + * @param size the size in pixels of the map. The map is a square and generally his size is : pow(2.0, zoom)*256. + * @param x the coordinate correspond to the longitude + * @param y the coordinate correspond to the latitude + * + * @ingroup Map + */ +EAPI void +elm_map_utils_convert_geo_into_coord(const Evas_Object *obj, double lon, double lat, int size, int *x, int *y) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int zoom = floor(log2(size/256)); + + if (elm_map_source_get(obj) == ELM_MAP_SOURCE_MODULE) + if ((wd->api) && (wd->api->obj_convert_geo_into_coord)) + if (wd->api->obj_convert_geo_into_coord(obj, zoom, lon, lat, size, x, y)) return; + + if (x) + *x = floor((lon + 180.0) / 360.0 * size); + if (y) + *y = floor((1.0 - log( tan(lat * ELM_PI/180.0) + 1.0 / cos(lat * ELM_PI/180.0)) / ELM_PI) / 2.0 * size); +} + + + +/** + * Add a marker on the map + * + * @param obj The map object + * @param lon the longitude + * @param lat the latitude + * @param clas the class to use + * @param data the data passed to the callbacks + * + * @return The marker object + * + * @ingroup Map + */ +EAPI Elm_Map_Marker * +elm_map_marker_add(Evas_Object *obj, double lon, double lat, Elm_Map_Marker_Class *clas, Elm_Map_Group_Class *clas_group, void *data) +{ + int i, j; + Eina_List *l; + Marker_Group *group; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + int mpi, mpj; + int tabi[9]; + int tabj[9]; + const char *s; + const char *style; + Evas_Object *o; + + if (!wd) return NULL; + EINA_SAFETY_ON_NULL_RETURN_VAL(clas_group, NULL); + EINA_SAFETY_ON_NULL_RETURN_VAL(clas, NULL); + + Elm_Map_Marker *marker = ELM_NEW(Elm_Map_Marker); + + marker->wd = wd; + marker->clas = clas; + marker->clas_group = clas_group; + marker->longitude = lon; + marker->latitude = lat; + marker->data = data; + + tabi[1] = tabi[4] = tabi[6] = -1; + tabi[2] = tabi[0] = tabi[7] = 0; + tabi[3] = tabi[5] = tabi[8] = 1; + + tabj[1] = tabj[2] = tabj[3] = -1; + tabj[4] = tabj[0] = tabj[5] = 0; + tabj[6] = tabj[7] = tabj[8] = 1; + + if (!clas_group->priv.set) + { + style = "radio"; + if (marker->clas_group && marker->clas_group->style) + style = marker->clas_group->style; + + o = edje_object_add(evas_object_evas_get(obj)); + _elm_theme_object_set(obj, o, "map/marker", style, elm_widget_style_get(obj)); + s = edje_object_data_get(o, "size_w"); + clas_group->priv.edje_w = atoi(s); + s = edje_object_data_get(o, "size_h"); + clas_group->priv.edje_h = atoi(s); + s = edje_object_data_get(o, "size_max_w"); + clas_group->priv.edje_max_w = atoi(s); + s = edje_object_data_get(o, "size_max_h"); + clas_group->priv.edje_max_h = atoi(s); + evas_object_del(o); + + clas_group->priv.set = EINA_TRUE; + } + + if (!clas->priv.set) + { + style = "radio"; + if (marker->clas && marker->clas->style) + style = marker->clas->style; + + o = edje_object_add(evas_object_evas_get(obj)); + _elm_theme_object_set(obj, o, "map/marker", style, elm_widget_style_get(obj)); + s = edje_object_data_get(o, "size_w"); + clas->priv.edje_w = atoi(s); + s = edje_object_data_get(o, "size_h"); + clas->priv.edje_h = atoi(s); + evas_object_del(o); + + clas->priv.set = EINA_TRUE; + } + + for (i = clas_group->zoom_displayed; i <= ZOOM_MAX; i++) + { + elm_map_utils_convert_geo_into_coord(obj, lon, lat, pow(2.0, i)*wd->tsize, + &(marker->x[i]), &(marker->y[i])); + + //search in the matrixsparse the region where the marker will be + mpi = marker->x[i] / wd->tsize; + mpj = marker->y[i] / wd->tsize; + + if (!wd->markers[i]) + { + int size = pow(2.0, i); + wd->markers[i] = eina_matrixsparse_new(size, size, NULL, NULL); + } + + group = NULL; + if (i <= clas_group->zoom_grouped) + { + for (j = 0, group = NULL; j < 9 && !group; j++) + { + EINA_LIST_FOREACH(eina_matrixsparse_data_idx_get(wd->markers[i], mpj + tabj[j], mpi + tabi[j]), + l, group) + { + if (group->clas == marker->clas_group + && ELM_RECTS_INTERSECT(marker->x[i]-clas->priv.edje_w/4, + marker->y[i]-clas->priv.edje_h/4, clas->priv.edje_w, clas->priv.edje_h, + group->x-group->w/4, group->y-group->h/4, group->w, group->h)) + { + group->markers = eina_list_append(group->markers, marker); + group->update_nbelems = EINA_TRUE; + group->update_resize = EINA_TRUE; + + group->sum_x += marker->x[i]; + group->sum_y += marker->y[i]; + group->x = group->sum_x / eina_list_count(group->markers); + group->y = group->sum_y / eina_list_count(group->markers); + + group->w = group->clas->priv.edje_w + group->clas->priv.edje_w/8. + * eina_list_count(group->markers); + group->h = group->clas->priv.edje_h + group->clas->priv.edje_h/8. + * eina_list_count(group->markers); + if (group->w > group->clas->priv.edje_max_w) group->w = group->clas->priv.edje_max_w; + if (group->h > group->clas->priv.edje_max_h) group->h = group->clas->priv.edje_max_h; + + if (group->obj && eina_list_count(group->markers) == 2) + { + _group_object_free(group); + _group_object_create(group); + } + if (group->bubble) + _group_bubble_content_update(group); + + break; + } + } + } + } + if (!group) + { + group = calloc(1, sizeof(Marker_Group)); + group->wd = wd; + group->sum_x = marker->x[i]; + group->sum_y = marker->y[i]; + group->x = marker->x[i]; + group->y = marker->y[i]; + group->w = clas_group->priv.edje_w; + group->h = clas_group->priv.edje_h; + group->clas = clas_group; + + group->markers = eina_list_append(group->markers, marker); + group->update_nbelems = EINA_TRUE; + group->update_resize = EINA_TRUE; + + eina_matrixsparse_cell_idx_get(wd->markers[i], mpj, mpi, &(group->cell)); + + if (!group->cell) + { + l = eina_list_append(NULL, group); + eina_matrixsparse_data_idx_set(wd->markers[i], mpj, mpi, l); + eina_matrixsparse_cell_idx_get(wd->markers[i], mpj, mpi, &(group->cell)); + } + else + { + l = eina_matrixsparse_cell_data_get(group->cell); + l = eina_list_append(l, group); + eina_matrixsparse_cell_data_set(group->cell, l); + } + } + marker->groups[i] = group; + } + + if (wd->grids) + { + Evas_Coord ox, oy, ow, oh; + evas_object_geometry_get(obj, &ox, &oy, &ow, &oh); + marker_place(obj, eina_list_data_get(wd->grids), wd->pan_x, wd->pan_y, ox, oy, ow, oh); + } + + return marker; +} + +/** + * Remove a marker from the map + * + * @param marker The marker to remove + * + * @ingroup Map + */ +EAPI void +elm_map_marker_remove(Elm_Map_Marker *marker) +{ + int i; + Eina_List *groups; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN(marker); + wd = marker->wd; + if (!wd) return; + for (i = 0; i <= ZOOM_MAX; i++) + { + marker->groups[i]->markers = eina_list_remove(marker->groups[i]->markers, marker); + if (!eina_list_count(marker->groups[i]->markers)) + { + groups = eina_matrixsparse_cell_data_get(marker->groups[i]->cell); + groups = eina_list_remove(groups, marker->groups[i]); + eina_matrixsparse_cell_data_set(marker->groups[i]->cell, groups); + + _group_object_free(marker->groups[i]); + _group_bubble_free(marker->groups[i]); + free(marker->groups[i]); + } + else + { + marker->groups[i]->sum_x -= marker->x[i]; + marker->groups[i]->sum_y -= marker->y[i]; + + marker->groups[i]->x = marker->groups[i]->sum_x / eina_list_count(marker->groups[i]->markers); + marker->groups[i]->y = marker->groups[i]->sum_y / eina_list_count(marker->groups[i]->markers); + + marker->groups[i]->w = marker->groups[i]->clas->priv.edje_w + + marker->groups[i]->clas->priv.edje_w/8. * eina_list_count(marker->groups[i]->markers); + marker->groups[i]->h = marker->groups[i]->clas->priv.edje_h + + marker->groups[i]->clas->priv.edje_h/8. * eina_list_count(marker->groups[i]->markers); + if (marker->groups[i]->w > marker->groups[i]->clas->priv.edje_max_w) + marker->groups[i]->w = marker->groups[i]->clas->priv.edje_max_w; + if (marker->groups[i]->h > marker->groups[i]->clas->priv.edje_max_h) + marker->groups[i]->h = marker->groups[i]->clas->priv.edje_max_h; + } + if ((marker->groups[i]->obj) && (eina_list_count(marker->groups[i]->markers) == 1)) + { + _group_object_free(marker->groups[i]); + _group_object_create(marker->groups[i]); + } + } + + if ((marker->content) && (marker->clas->func.del)) + marker->clas->func.del(marker->wd->obj, marker, marker->data, marker->content); + else if (marker->content) + evas_object_del(marker->content); + + free(marker); + + if (wd->grids) + { + Evas_Coord ox, oy, ow, oh; + evas_object_geometry_get(wd->obj, &ox, &oy, &ow, &oh); + marker_place(wd->obj, eina_list_data_get(wd->grids), wd->pan_x, wd->pan_y, ox, oy, ow, oh); + } +} + +/** + * Move the map to the coordinate of the marker. + * + * @param marker The marker where the map will be center. + * + * @ingroup Map + */ +EAPI void +elm_map_marker_bring_in(Elm_Map_Marker *marker) +{ + EINA_SAFETY_ON_NULL_RETURN(marker); + elm_map_geo_region_bring_in(marker->wd->obj, marker->longitude, marker->latitude); +} + + +/** + * Move the map to the coordinate of the marker. + * + * @param marker The marker where the map will be center. + * + * @ingroup Map + */ +EAPI void +elm_map_marker_show(Elm_Map_Marker *marker) +{ + EINA_SAFETY_ON_NULL_RETURN(marker); + elm_map_geo_region_show(marker->wd->obj, marker->longitude, marker->latitude); +} + +/** + * Move and zoom the map to display a list of markers. + * + * The map will be centered on the center point of the markers in the list. Then + * the map will be zoomed in order to fit the markers using the maximum zoom which + * allows display of all the markers. + * + * @param markers The list of markers (list of Elm_Map_Marker *) + * + * @ingroup Map + */ +EAPI void +elm_map_markers_list_show(Eina_List *markers) +{ + int zoom; + double lon, lat; + Eina_List *l; + Elm_Map_Marker *marker, *m_max_lon = NULL, *m_max_lat = NULL, *m_min_lon = NULL, *m_min_lat = NULL; + Evas_Coord rw, rh, xc, yc; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN(markers); + + EINA_LIST_FOREACH(markers, l, marker) + { + wd = marker->wd; + + if ((!m_min_lon) || (marker->longitude < m_min_lon->longitude)) + m_min_lon = marker; + + if ((!m_max_lon) || (marker->longitude > m_max_lon->longitude)) + m_max_lon = marker; + + if ((!m_min_lat) || (marker->latitude > m_min_lat->latitude)) + m_min_lat = marker; + + if ((!m_max_lat) || (marker->latitude < m_max_lat->latitude)) + m_max_lat = marker; + } + + lon = (m_max_lon->longitude - m_min_lon->longitude) / 2. + m_min_lon->longitude; + lat = (m_max_lat->latitude - m_min_lat->latitude) / 2. + m_min_lat->latitude; + + elm_smart_scroller_child_viewport_size_get(wd->scr, &rw, &rh); + for (zoom = map_sources_tab[wd->source].zoom_max; zoom>map_sources_tab[wd->source].zoom_min; zoom--) + { + Evas_Coord size = pow(2.0, zoom)*wd->tsize; + elm_map_utils_convert_geo_into_coord(wd->obj, lon, lat, size, &xc, &yc); + + if ((m_min_lon->x[zoom] - wd->marker_max_w >= xc-rw/2) + && (m_min_lat->y[zoom] - wd->marker_max_h >= yc-rh/2) + && (m_max_lon->x[zoom] + wd->marker_max_w <= xc+rw/2) + && (m_max_lat->y[zoom] + wd->marker_max_h <= yc+rh/2)) + break; + } + + elm_map_geo_region_show(wd->obj, lon, lat); + elm_map_zoom_set(wd->obj, zoom); +} + +/** + * Set the maximum numbers of markers display in a group. + * + * A group can have a long list of markers, consequently the creation of the content + * of the bubble can be very slow. In order to avoid this, a maximum number of items + * is displayed in a bubble. By default this number is 30. + * + * @param obj The map object. + * @param max The maximum numbers of items displayed in a bubble. + * + * @ingroup Map + */ +EAPI void +elm_map_max_marker_per_group_set(Evas_Object *obj, int max) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->markers_max_num = max; +} + +/** + * Return the evas object getting from the ElmMapMarkerGetFunc callback + * + * @param marker The marker. + * @return Return the evas object if it exists, else NULL. + * + * @ingroup Map + */ +EAPI Evas_Object * +elm_map_marker_object_get(const Elm_Map_Marker *marker) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(marker, NULL); + return marker->content; +} + +/** + * Update the marker + * + * @param marker The marker. + * + * @ingroup Map + */ +EAPI void +elm_map_marker_update(Elm_Map_Marker *marker) +{ + EINA_SAFETY_ON_NULL_RETURN(marker); + if (marker->content) + { + if (marker->clas->func.del) + marker->clas->func.del(marker->wd->obj, marker, marker->data, marker->content); + else + evas_object_del(marker->content); + marker->content = NULL; + _group_bubble_content_update(marker->groups[marker->wd->zoom]); + } +} + +/** + * Close all opened bubbles + * + * @param obj The map object + * + * @ingroup Map + */ +EAPI void +elm_map_bubbles_close(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Marker_Group *group; + Eina_List *l, *l_next; + if (!wd) return; + EINA_LIST_FOREACH_SAFE(wd->opened_bubbles, l, l_next, group) + _group_bubble_free(group); +} + + +/** + * Create a group class. + * + * Each marker must be associated to a group class. Marker with the same group are grouped if they are close. + * The group class defines the style of the marker when a marker is grouped to others markers. + * + * @param obj The map object + * @return Returns the new group class + * + * @ingroup Map + */ +EAPI Elm_Map_Group_Class * +elm_map_group_class_new(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + Elm_Map_Group_Class *clas = calloc(1, sizeof(Elm_Map_Group_Class)); + clas->zoom_grouped = ZOOM_MAX; + wd->groups_clas = eina_list_append(wd->groups_clas, clas); + return clas; +} + +/** + * Set the style of a group class (radio, radio2 or empty) + * + * @param clas the group class + * @param style the new style + * + * @ingroup Map + */ +EAPI void +elm_map_group_class_style_set(Elm_Map_Group_Class *clas, const char *style) +{ + EINA_SAFETY_ON_NULL_RETURN(clas); + eina_stringshare_replace(&clas->style, style); +} + +/** + * Set the icon callback of a group class. + * + * A custom icon can be displayed in a marker. The function @ref icon_get must return this icon. + * + * @param clas the group class + * @param icon_get the callback to create the icon + * + * @ingroup Map + */ +EAPI void +elm_map_group_class_icon_cb_set(Elm_Map_Group_Class *clas, ElmMapGroupIconGetFunc icon_get) +{ + EINA_SAFETY_ON_NULL_RETURN(clas); + clas->func.icon_get = icon_get; +} + +/** + * Set the data associated to the group class (radio, radio2 or empty) + * + * @param clas the group class + * @param data the new user data + * + * @ingroup Map + */ +EAPI void +elm_map_group_class_data_set(Elm_Map_Group_Class *clas, void *data) +{ + EINA_SAFETY_ON_NULL_RETURN(clas); + clas->data = data; +} + +/** + * Set the zoom from where the markers are displayed. + * + * Markers will not be displayed for a zoom less than @ref zoom + * + * @param clas the group class + * @param zoom the zoom + * + * @ingroup Map + */ +EAPI void +elm_map_group_class_zoom_displayed_set(Elm_Map_Group_Class *clas, int zoom) +{ + EINA_SAFETY_ON_NULL_RETURN(clas); + clas->zoom_displayed = zoom; +} + +/** + * Set the zoom from where the markers are no more grouped. + * + * @param clas the group class + * @param zoom the zoom + * + * @ingroup Map + */ +EAPI void +elm_map_group_class_zoom_grouped_set(Elm_Map_Group_Class *clas, int zoom) +{ + EINA_SAFETY_ON_NULL_RETURN(clas); + clas->zoom_grouped = zoom; +} + +/** + * Set if the markers associated to the group class @clas are hidden or not. + * If @ref hide is true the markers will be hidden. + * + * @param clas the group class + * @param hide if true the markers will be hidden, else they will be displayed. + * + * @ingroup Map + */ +EAPI void +elm_map_group_class_hide_set(Evas_Object *obj, Elm_Map_Group_Class *clas, Eina_Bool hide) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(clas); + if (clas->hide == hide) return; + clas->hide = hide; + if (wd->grids) + { + Evas_Coord ox, oy, ow, oh; + evas_object_geometry_get(obj, &ox, &oy, &ow, &oh); + marker_place(obj, eina_list_data_get(wd->grids), wd->pan_x, wd->pan_y, ox, oy, ow, oh); + } +} + + +/** + * Create a marker class. + * + * Each marker must be associated to a class. + * The class defines the style of the marker when a marker is displayed alone (not grouped). + * + * @param obj The map object + * @return Returns the new class + * + * @ingroup Map + */ +EAPI Elm_Map_Marker_Class * +elm_map_marker_class_new(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + Elm_Map_Marker_Class *clas = calloc(1, sizeof(Elm_Map_Marker_Class)); + wd->markers_clas = eina_list_append(wd->markers_clas, clas); + return clas; +} + +/** + * Set the style of a class (radio, radio2 or empty) + * + * @param clas the group class + * @param style the new style + * + * @ingroup Map + */ +EAPI void +elm_map_marker_class_style_set(Elm_Map_Marker_Class *clas, const char *style) +{ + EINA_SAFETY_ON_NULL_RETURN(clas); + eina_stringshare_replace(&clas->style, style); +} + +/** + * Set the icon callback of a class. + * + * A custom icon can be displayed in a marker. The function @ref icon_get must return this icon. + * + * @param clas the group class + * @param icon_get the callback to create the icon + * + * @ingroup Map + */ +EAPI void +elm_map_marker_class_icon_cb_set(Elm_Map_Marker_Class *clas, ElmMapMarkerIconGetFunc icon_get) +{ + EINA_SAFETY_ON_NULL_RETURN(clas); + clas->func.icon_get = icon_get; +} + +/** + * + * Set the callback of the content of the bubble. + * + * When the user click on a marker, a bubble is displayed with a content. + * The callback @ref get musst return this content. It can be NULL. + * + * @param clas the group class + * @param get the callback to create the content + * + * @ingroup Map + */ +EAPI void +elm_map_marker_class_get_cb_set(Elm_Map_Marker_Class *clas, ElmMapMarkerGetFunc get) +{ + EINA_SAFETY_ON_NULL_RETURN(clas); + clas->func.get = get; +} + +/** + * Set the callback of the content of delete the object created by the callback "get". + * + * If this callback is defined the user will have to delete (or not) the object inside. + * If the callback is not defined the object will be destroyed with evas_object_del() + * + * @param clas the group class + * @param del the callback to delete the content + * + * @ingroup Map + */ +EAPI void +elm_map_marker_class_del_cb_set(Elm_Map_Marker_Class *clas, ElmMapMarkerDelFunc del) +{ + EINA_SAFETY_ON_NULL_RETURN(clas); + clas->func.del = del; +} + +/** + * Set the source of the map. + * + * Elm_Map retrieves the image which composed the map from a web service. This web service can + * be set with this method. A different service can return a different maps with different + * information and it can use different zoom value. + * + * @param clas the group class + * @param source the new source + * + * @ingroup Map + */ +EAPI void +elm_map_source_set(Evas_Object *obj, Elm_Map_Sources source) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Grid *grid; + int zoom; + if (!wd) return; + if (wd->source == source ) return; + if (!map_sources_tab[source].url_cb) return; + + EINA_LIST_FREE(wd->grids, grid) grid_clear(obj, grid); + + wd->source = source; + zoom = wd->zoom; + wd->zoom = -1; + + if (map_sources_tab[wd->source].zoom_max < zoom) + zoom = map_sources_tab[wd->source].zoom_max; + if (map_sources_tab[wd->source].zoom_min > zoom) + zoom = map_sources_tab[wd->source].zoom_min; + + elm_map_zoom_set(obj, zoom); +} + +/** + * Get the current source + * + * @param obj the map object + * @return Returns the maximum zoom of the source + * + * @ingroup Map + */ +EAPI Elm_Map_Sources +elm_map_source_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_MAP_SOURCE_MAPNIK; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_MAP_SOURCE_MAPNIK; + return wd->source; +} + +/** + * Set the API of a custom source. + * + * A custom web service can be associated to the source ELM_MAP_SOURCE_CUSTOM_(1..7). + * + * @param source the source ID (ELM_MAP_SOURCE_CUSTOM_(1..7)) + * @param name the name of the source + * @param zoom_min the minimum zoom of the source, must be >= 0 + * @param zoom_max the maximum zoom of the source, must be <= ZOOM_MAX + * @param url_cb the callback used to create the url from where a tile (png or jpeg file) is downloaded. + * + * @ingroup Map + */ +EAPI void +elm_map_source_custom_api_set(Elm_Map_Sources source, const char *name, int zoom_min, int zoom_max, ElmMapSourceURLFunc url_cb) +{ + EINA_SAFETY_ON_NULL_RETURN(name); + EINA_SAFETY_ON_NULL_RETURN(url_cb); + map_sources_tab[source].name = name; + map_sources_tab[source].zoom_min = zoom_min; + map_sources_tab[source].zoom_max = zoom_max; + map_sources_tab[source].url_cb = url_cb; +} + +/** + * Get the maximum zoom of the source. + * + * @param source the source + * @return Returns the maximum zoom of the source + * + * @ingroup Map + */ +EAPI int +elm_map_source_zoom_max_get(Elm_Map_Sources source) +{ + return map_sources_tab[source].zoom_max; +} + +/** + * Get the minimum zoom of the source. + * + * @param source the source + * @return Returns the minimum zoom of the source + * + * @ingroup Map + */ +EAPI int +elm_map_source_zoom_min_get(Elm_Map_Sources source) +{ + return map_sources_tab[source].zoom_min; +} + +/** + * Get the name of a source. + * + * @param source the source + * @return Returns the name of the source + * + * @ingroup Map + */ +EAPI const char * +elm_map_source_name_get(Elm_Map_Sources source) +{ + return map_sources_tab[source].name; +} + + +static char * +_mapnik_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom) +{ + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), "http://tile.openstreetmap.org/%d/%d/%d.png", + zoom, x, y); + return strdup(buf); +} + +static char * +_osmarender_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom) +{ + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), + "http://tah.openstreetmap.org/Tiles/tile/%d/%d/%d.png", + zoom, x, y); + return strdup(buf); +} + +static char * +_cyclemap_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom) +{ + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), + "http://andy.sandbox.cloudmade.com/tiles/cycle/%d/%d/%d.png", + zoom, x, y); + return strdup(buf); +} + +static char * +_maplint_url_cb(Evas_Object *obj __UNUSED__, int x, int y, int zoom) +{ + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), + "http://tah.openstreetmap.org/Tiles/maplint/%d/%d/%d.png", + zoom, x, y); + return strdup(buf); +} + +static char * +_custom1_url_cb(Evas_Object *obj __UNUSED__, int x __UNUSED__, int y __UNUSED__, int zoom __UNUSED__) +{ + return strdup(""); +} + +static char * +_custom2_url_cb(Evas_Object *obj __UNUSED__, int x __UNUSED__, int y __UNUSED__, int zoom __UNUSED__) +{ + return strdup(""); +} + +static char * +_custom3_url_cb(Evas_Object *obj __UNUSED__, int x __UNUSED__, int y __UNUSED__, int zoom __UNUSED__) +{ + return strdup(""); +} + +static char * +_custom4_url_cb(Evas_Object *obj __UNUSED__, int x __UNUSED__, int y __UNUSED__, int zoom __UNUSED__) +{ + return strdup(""); +} + +static char * +_custom5_url_cb(Evas_Object *obj __UNUSED__, int x __UNUSED__, int y __UNUSED__, int zoom __UNUSED__) +{ + return strdup(""); +} + +static char * +_custom6_url_cb(Evas_Object *obj __UNUSED__, int x __UNUSED__, int y __UNUSED__, int zoom __UNUSED__) +{ + return strdup(""); +} + +static char * +_module_url_cb(Evas_Object *obj, int x, int y, int zoom) +{ + char *buf = NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (elm_map_source_get(obj) == ELM_MAP_SOURCE_MODULE) + if ((wd->api) && (wd->api->obj_url_request)) + buf = wd->api->obj_url_request(obj, x, y, zoom); + + if (!buf) buf = strdup(""); + + return buf; +} + diff --git a/src/lib/elm_mapbuf.c b/src/lib/elm_mapbuf.c new file mode 100644 index 0000000..fc4d6ac --- /dev/null +++ b/src/lib/elm_mapbuf.c @@ -0,0 +1,395 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Mapbuf Mapbuf + * + * This holds 1 content object and uses an Evas Map to move/resize etc. it. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *content, *clip; + Eina_Bool enabled : 1; + Eina_Bool alpha : 1; + Eina_Bool smooth : 1; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + Evas_Coord maxw = -1, maxh = -1; + if (!wd) return; + if (wd->content) + { + evas_object_size_hint_min_get(wd->content, &minw, &minh); + evas_object_size_hint_max_get(wd->content, &maxw, &maxh); + } + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->content) + { + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->content = NULL; + _sizing_eval(obj); + } +} + +static void +_mapbuf(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord x, y, w, h; + if (!wd) return; + evas_object_geometry_get(wd->clip, &x, &y, &w, &h); + if (wd->enabled) + { + Evas_Map *m; + + m = evas_map_new(4); + evas_map_util_points_populate_from_geometry(m, x, y, w, h, 0); + evas_map_smooth_set(m, wd->smooth); + evas_map_alpha_set(m, wd->alpha); + evas_object_map_set(wd->content, m); + evas_object_map_enable_set(wd->content, wd->enabled); + evas_map_free(m); + } + else + { + evas_object_map_set(wd->content, NULL); + evas_object_map_enable_set(wd->content, 0); + evas_object_move(wd->content, x, y); + evas_object_resize(wd->content, w, h); + } +} + +static void +_configure(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->content) + { + Evas_Coord x, y, w, h, x2, y2; + + evas_object_geometry_get(wd->clip, &x, &y, &w, &h); + evas_object_geometry_get(wd->content, &x2, &y2, NULL, NULL); + if ((x != x2) || (y != y2)) + { + if (!wd->enabled) + evas_object_move(wd->content, x, y); + else + { + + Evas *e = evas_object_evas_get(obj); + evas_smart_objects_calculate(e); + evas_nochange_push(e); +// printf("x-------------------- %i %i\n", x, y); + evas_object_move(wd->content, x, y); + evas_smart_objects_calculate(e); +// printf("y--------------------\n"); + evas_nochange_pop(e); + } + } + evas_object_resize(wd->content, w, h); + _mapbuf(obj); + } +} + +static void +_move(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _configure(data); +} + +static void +_resize(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _configure(data); +} + +/** + * Add a new mapbuf to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Mapbuf + */ +EAPI Evas_Object * +elm_mapbuf_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "mapbuf"); + elm_widget_type_set(obj, "mapbuf"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->clip = evas_object_rectangle_add(e); + evas_object_static_clip_set(wd->clip, EINA_TRUE); + evas_object_pass_events_set(wd->clip, EINA_TRUE); + evas_object_color_set(wd->clip, 0, 0, 0, 0); + + evas_object_event_callback_add(wd->clip, EVAS_CALLBACK_MOVE, _move, obj); + evas_object_event_callback_add(wd->clip, EVAS_CALLBACK_RESIZE, _resize, obj); + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + elm_widget_resize_object_set(obj, wd->clip); + + wd->enabled = 0; + wd->alpha = 1; + wd->smooth = 1; + + _sizing_eval(obj); + return obj; +} + +/** + * Set the mapbuf front content + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_mapbuf_content_unset() function. + * + * @param obj The mapbuf object + * @param content The content will be filled in this mapbuf object + * + * @ingroup Mapbuf + */ +EAPI void +elm_mapbuf_content_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->content == content) return; + if (wd->content) evas_object_del(wd->content); + wd->content = content; + if (content) + { + evas_object_data_set(content, "_elm_leaveme", (void *)1); + elm_widget_sub_object_add(content, obj); + evas_object_smart_member_add(content, obj); + evas_object_clip_set(content, wd->clip); + evas_object_color_set(wd->clip, 255, 255, 255, 255); + evas_object_event_callback_add(content, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + } + else + evas_object_color_set(wd->clip, 0, 0, 0, 0); + _sizing_eval(obj); + _configure(obj); +} + +/** + * Get the mapbuf front content + * + * Return the content object which is set for this widget. + * + * @param obj The mapbuf object + * @return The content that is being used + * + * @ingroup Mapbuf + */ +EAPI Evas_Object * +elm_mapbuf_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->content; +} + +/** + * Unset the mapbuf front content + * + * Unparent and return the content object which was set for this widget. + * + * @param obj The mapbuf object + * @return The content that was being used + * + * @ingroup Mapbuf + */ +EAPI Evas_Object * +elm_mapbuf_content_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *content; + if (!wd) return NULL; + if (!wd->content) return NULL; + content = wd->content; + elm_widget_sub_object_del(obj, content); + evas_object_smart_member_del(content); + evas_object_color_set(wd->clip, 0, 0, 0, 0); + evas_object_clip_unset(content); + evas_object_data_del(content, "_elm_leaveme"); + wd->content = NULL; + return content; +} + +/** + * Set the mapbuf enabled state + * + * @param obj The mapbuf object + * @param enabled The value to set the enabled state to + * + * @ingroup Mapbuf + */ +EAPI void +elm_mapbuf_enabled_set(Evas_Object *obj, Eina_Bool enabled) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->enabled == enabled) return; + wd->enabled = enabled; + if (wd->content) evas_object_static_clip_set(wd->content, wd->enabled); + _configure(obj); +} + +/** + * Get the mapbuf enabled state + * + * @param obj The mapbuf object + * @return The value that the enabled state is set to + * + * @ingroup Mapbuf + */ +EAPI Eina_Bool +elm_mapbuf_enabled_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->enabled; +} + +/** + * Sets the mapbuf smooth state + * + * @param obj The mapbuf object + * @param smooth The value of the smooth state of @p obj + * + * @ingroup Mapbuf + */ +EAPI void +elm_mapbuf_smooth_set(Evas_Object *obj, Eina_Bool smooth) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->smooth == smooth) return; + wd->smooth = smooth; + _configure(obj); +} + +/** + * Gets the mapbuf smooth state + * + * @param obj The mapbuf object + * @return The value of the smooth state of @p obj + * + * @ingroup Mapbuf + */ +EAPI Eina_Bool +elm_mapbuf_smooth_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->smooth; +} + +/** + * Enables/disables the mapbuf alpha channel + * + * @param obj The mapbuf object + * @param alpha The state of the alpha channel + * + * @ingroup Mapbuf + */ +EAPI void +elm_mapbuf_alpha_set(Evas_Object *obj, Eina_Bool alpha) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->alpha == alpha) return; + wd->alpha = alpha; + _configure(obj); +} + +/** + * Gets the state of the mapbuf alpha channel + * + * @param obj The mapbuf object + * @return The state of the alpha channel + * + * @ingroup Mapbuf + */ +EAPI Eina_Bool +elm_mapbuf_alpha_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->alpha; +} diff --git a/src/lib/elm_menu.c b/src/lib/elm_menu.c new file mode 100644 index 0000000..06606ab --- /dev/null +++ b/src/lib/elm_menu.c @@ -0,0 +1,928 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Menu Menu + * + * A menu is a list of items displayed above the window. Each item can + * have a sub-menu. The menu object can be used to display a menu on right + * click, in a toolbar, anywhere. + * + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Elm_Menu_Item +{ + Elm_Widget_Item base; + Elm_Menu_Item *parent; + Evas_Object *icon; + const char *icon_str; + const char *label; + Evas_Smart_Cb func; + + struct { + Evas_Object *hv, *bx, *location; + Eina_List *items; + Eina_Bool open : 1; + } submenu; + + Eina_Bool separator : 1; + Eina_Bool disabled : 1; +}; + +struct _Widget_Data +{ + Evas_Object *hv, *bx, *location, *parent, *obj; + Eina_List *items; + Evas_Coord xloc, yloc; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _submenu_sizing_eval(Elm_Menu_Item *parent); +static void _item_sizing_eval(Elm_Menu_Item *item); +static void _submenu_hide(Elm_Menu_Item *item); +static void _submenu_open(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _parent_resize(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _parent_del(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _menu_hide(void *data, Evas_Object *obj, void *event_info); + +static void +_del_item(Elm_Menu_Item *item) +{ + Elm_Menu_Item *child; + + elm_widget_item_pre_notify_del(item); + + EINA_LIST_FREE(item->submenu.items, child) + _del_item(child); + + if (item->label) eina_stringshare_del(item->label); + if (item->submenu.hv) evas_object_del(item->submenu.hv); + if (item->submenu.location) evas_object_del(item->submenu.location); + if (item->icon_str) eina_stringshare_del(item->icon_str); + elm_widget_item_del(item); +} + +static void +_del_pre_hook(Evas_Object *obj) +{ + Elm_Menu_Item *item; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_RESIZE, _parent_resize, obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_DEL, _parent_del, wd); + + EINA_LIST_FREE(wd->items, item) + _del_item(item); + + if (wd->hv) evas_object_del(wd->hv); + if (wd->location) evas_object_del(wd->location); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Eina_List *l, *_l, *_ll, *ll = NULL; + Elm_Menu_Item *item; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + ll = eina_list_append(ll, wd->items); + EINA_LIST_FOREACH(ll, _ll, l) + { + EINA_LIST_FOREACH(l, _l, item) + { + ll = eina_list_append(ll, item->submenu.items); + if (item->separator) + _elm_theme_object_set(obj, item->base.view, "menu", "separator", + elm_widget_style_get(obj)); + else if (item->submenu.bx) + { + _elm_theme_object_set + (obj, item->base.view, "menu", "item_with_submenu", + elm_widget_style_get(obj)); + elm_menu_item_label_set(item, item->label); + elm_menu_item_icon_set(item, item->icon_str); + } + else + { + _elm_theme_object_set(obj, item->base.view, "menu", "item", + elm_widget_style_get(obj)); + elm_menu_item_label_set(item, item->label); + elm_menu_item_icon_set(item, item->icon_str); + } + if (item->disabled) + edje_object_signal_emit + (item->base.view, "elm,state,disabled", "elm"); + else + edje_object_signal_emit + (item->base.view, "elm,state,enabled", "elm"); + edje_object_message_signal_process(item->base.view); + edje_object_scale_set(item->base.view, elm_widget_scale_get(obj) * + _elm_config->scale); + } + } + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Eina_List *l; + Elm_Menu_Item *item; + Evas_Coord x_p, y_p, w_p, h_p, x2, y2, w2, h2, bx, by, bw, bh; + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->parent)) return; + EINA_LIST_FOREACH(wd->items,l,item) _item_sizing_eval(item); + evas_object_geometry_get(wd->location, &x_p, &y_p, &w_p, &h_p); + evas_object_geometry_get(wd->parent, &x2, &y2, &w2, &h2); + evas_object_geometry_get(wd->bx, &bx, &by, &bw, &bh); + + x_p = wd->xloc; + y_p = wd->yloc; + + if (x_p+bw > x2+w2) x_p -= x_p+bw - (x2+w2); + if (x_p < x2) x_p += x2 - x_p; + + if (y_p+h_p+bh > y2+h2) y_p -= y_p+h_p+bh - (y2+h2); + if (y_p < y2) y_p += y2 - y_p; + + evas_object_move(wd->location, x_p, y_p); + evas_object_resize(wd->location, bw, h_p); + evas_object_size_hint_min_set(wd->location, bw, h_p); + evas_object_size_hint_max_set(wd->location, bw, h_p); + elm_hover_target_set(wd->hv, wd->location); + + EINA_LIST_FOREACH(wd->items,l,item) + { + if (item->submenu.open) _submenu_sizing_eval(item); + } +} + +static void +_submenu_sizing_eval(Elm_Menu_Item *parent) +{ + Eina_List *l; + Elm_Menu_Item *item; + Evas_Coord x_p, y_p, w_p, h_p, x2, y2, w2, h2, bx, by, bw, bh, px, py, pw, ph; + Widget_Data *wd = elm_widget_data_get(parent->base.widget); + if (!wd) return; + EINA_LIST_FOREACH(parent->submenu.items, l, item) _item_sizing_eval(item); + evas_object_geometry_get(parent->submenu.location, &x_p, &y_p, &w_p, &h_p); + evas_object_geometry_get(parent->base.view, &x2, &y2, &w2, &h2); + evas_object_geometry_get(parent->submenu.bx, &bx, &by, &bw, &bh); + evas_object_geometry_get(wd->parent, &px, &py, &pw, &ph); + + x_p = x2+w2; + y_p = y2; + + if (x_p + bw > px + pw) + x_p = x2-bw; + + if (y_p+bh > py+ph) + y_p -= y_p+bh - (py+ph); + if (y_p < py) + y_p += y_p - y_p; + + evas_object_move(parent->submenu.location, x_p, y_p); + evas_object_resize(parent->submenu.location, bw, h_p); + evas_object_size_hint_min_set(parent->submenu.location, bw, h_p); + evas_object_size_hint_max_set(parent->submenu.location, bw, h_p); + elm_hover_target_set(parent->submenu.hv, parent->submenu.location); + + EINA_LIST_FOREACH(parent->submenu.items, l, item) + { + if (item->submenu.open) + _submenu_sizing_eval(item); + } +} + +static void +_item_sizing_eval(Elm_Menu_Item *item) +{ + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!item->separator) + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(item->base.view, &minw, &minh, minw, minh); + if (!item->separator) + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(item->base.view, minw, minh); + evas_object_size_hint_max_set(item->base.view, maxw, maxh); +} + +static void +_menu_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_parent_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_parent_del(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = data; + evas_object_event_callback_del_full(obj, EVAS_CALLBACK_RESIZE, _parent_resize, wd->obj); + wd->parent = NULL; +} + +static void +_item_move_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Menu_Item *item = data; + if (item->submenu.open) _submenu_sizing_eval(item); +} + +static void +_hover_clicked_cb(void *data, Evas_Object *obj, void *event_info) +{ + _menu_hide(data, obj, event_info); + evas_object_smart_callback_call(data, "clicked", NULL); +} + +static void +_menu_hide(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Eina_List *l; + Elm_Menu_Item *item2; + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_hide(wd->hv); + evas_object_hide(data); + + EINA_LIST_FOREACH(wd->items, l, item2) + { + if (item2->submenu.open) _submenu_hide(item2); + } +} + +static void +_submenu_hide(Elm_Menu_Item *item) +{ + Eina_List *l; + Elm_Menu_Item *item2; + evas_object_hide(item->submenu.hv); + item->submenu.open = EINA_FALSE; + EINA_LIST_FOREACH(item->submenu.items, l, item2) + { + if (item2->submenu.open) _submenu_hide(item2); + } +} + +static void +_menu_item_select(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Elm_Menu_Item *item = data; + if (item->submenu.items) + { + if (!item->submenu.open) _submenu_open(item, NULL, NULL, NULL); + else _submenu_hide(item); + } + else + _menu_hide(item->base.widget, NULL, NULL); + + if (item->func) item->func((void *)(item->base.data), item->base.widget, item); +} + +static void +_menu_item_activate(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Eina_List *l; + Elm_Menu_Item *item2; + Elm_Menu_Item *item = data; + if (item->parent) + { + EINA_LIST_FOREACH(item->parent->submenu.items, l, item2) + { + if ((item2->submenu.open) && (item2 != item)) _submenu_hide(item2); + } + } + else + { + Widget_Data *wd = elm_widget_data_get(item->base.widget); + EINA_LIST_FOREACH(wd->items, l, item2) + { + if ((item2->submenu.open) && (item2 != item)) _submenu_hide(item2); + } + } +} + +static void +_submenu_open(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Elm_Menu_Item *item = data; + item->submenu.open = EINA_TRUE; + evas_object_show(item->submenu.hv); + _sizing_eval(item->base.widget); +} + +static void +_show(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_show(wd->hv); +} + +static void +_item_obj_create(Elm_Menu_Item *item) +{ + Widget_Data *wd = elm_widget_data_get(item->base.widget); + if (!wd) return; + item->base.view = edje_object_add(evas_object_evas_get(wd->bx)); + evas_object_size_hint_weight_set(item->base.view, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(item->base.view, EVAS_HINT_FILL, EVAS_HINT_FILL); + _elm_theme_object_set(item->base.widget, item->base.view, "menu", "item", elm_widget_style_get(item->base.widget)); + edje_object_signal_callback_add(item->base.view, "elm,action,click", "", + _menu_item_select, item); + edje_object_signal_callback_add(item->base.view, "elm,action,activate", "", + _menu_item_activate, item); + evas_object_show(item->base.view); +} + +static void +_item_separator_obj_create(Elm_Menu_Item *item) +{ + Widget_Data *wd = elm_widget_data_get(item->base.widget); + if (!wd) return; + item->base.view = edje_object_add(evas_object_evas_get(wd->bx)); + evas_object_size_hint_weight_set(item->base.view, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_fill_set(item->base.view, EVAS_HINT_FILL, EVAS_HINT_FILL); + _elm_theme_object_set(item->base.widget, item->base.view, "menu", "separator", elm_widget_style_get(item->base.widget)); + edje_object_signal_callback_add(item->base.view, "elm,action,activate", "", + _menu_item_activate, item); + evas_object_show(item->base.view); +} + +static void +_item_submenu_obj_create(Elm_Menu_Item *item) +{ + Widget_Data *wd = elm_widget_data_get(item->base.widget); + if (!wd) return; + item->submenu.location = elm_icon_add(wd->bx); + item->submenu.hv = elm_hover_add(wd->bx); + elm_hover_target_set(item->submenu.hv, item->submenu.location); + elm_hover_parent_set(item->submenu.hv, wd->parent); + elm_object_style_set(item->submenu.hv, "submenu"); + + item->submenu.bx = elm_box_add(wd->bx); + evas_object_size_hint_weight_set(item->submenu.bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(item->submenu.bx); + elm_hover_content_set(item->submenu.hv, elm_hover_best_content_location_get(item->submenu.hv, ELM_HOVER_AXIS_VERTICAL), item->submenu.bx); + + _elm_theme_object_set(item->base.widget, item->base.view, "menu", "item_with_submenu", elm_widget_style_get(item->base.widget)); + elm_menu_item_label_set(item, item->label); + elm_menu_item_icon_set(item, item->icon_str); + + edje_object_signal_callback_add(item->base.view, "elm,action,open", "", + _submenu_open, item); + evas_object_event_callback_add(item->base.view, EVAS_CALLBACK_MOVE, _item_move_resize, item); + evas_object_event_callback_add(item->base.view, EVAS_CALLBACK_RESIZE, _item_move_resize, item); + + evas_object_event_callback_add(item->submenu.bx, EVAS_CALLBACK_RESIZE, _menu_resize, item->base.widget); +} + +/** + * Add a new menu to the parent + * + * @param parent The parent object. + * @return The new object or NULL if it cannot be created. + * + * @ingroup Menu + */ +EAPI Evas_Object * +elm_menu_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "menu"); + elm_widget_type_set(obj, "menu"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->location = elm_icon_add(obj); + wd->parent = parent; + wd->obj = obj; + + wd->hv = elm_hover_add(obj); + elm_hover_parent_set(wd->hv, parent); + elm_hover_target_set(wd->hv, wd->location); + elm_object_style_set(wd->hv, "menu"); + evas_object_smart_callback_add(wd->hv, "clicked", _hover_clicked_cb, obj); + + wd->bx = elm_box_add(obj); + evas_object_size_hint_weight_set(wd->bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(wd->bx); + elm_hover_content_set(wd->hv, elm_hover_best_content_location_get(wd->hv, ELM_HOVER_AXIS_VERTICAL), wd->bx); + + evas_object_event_callback_add(wd->parent, EVAS_CALLBACK_RESIZE, _parent_resize, wd->obj); + evas_object_event_callback_add(wd->parent, EVAS_CALLBACK_DEL, _parent_del, wd); + + evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, _show, obj); + + evas_object_event_callback_add(wd->bx, EVAS_CALLBACK_RESIZE, _menu_resize, obj); + + _sizing_eval(obj); + return obj; +} + +/** + * Set the parent + * + * @param obj The menu object. + * @param parent The new parent. + * + * @ingroup Menu + */ +EAPI void +elm_menu_parent_set(Evas_Object *obj, Evas_Object *parent) +{ + Eina_List *l, *_l, *_ll, *ll = NULL; + Elm_Menu_Item *item; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + if (wd->parent == parent) return; + if (wd->parent) + { + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_RESIZE, _parent_resize, wd->obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_DEL, _parent_del, wd); + } + wd->parent = parent; + if (wd->parent) + { + evas_object_event_callback_add(wd->parent, EVAS_CALLBACK_RESIZE, _parent_resize, wd->obj); + evas_object_event_callback_add(wd->parent, EVAS_CALLBACK_DEL, _parent_del, wd); + } + elm_hover_parent_set(wd->hv, parent); + + ll = eina_list_append(ll, wd->items); + EINA_LIST_FOREACH(ll, _ll, l) + { + EINA_LIST_FOREACH(l, _l, item) + { + if (item->submenu.hv) + { + elm_hover_parent_set(item->submenu.hv, parent); + ll = eina_list_append(ll, item->submenu.items); + } + } + } + _sizing_eval(obj); +} + +/** + * Get the parent + * + * @param obj The menu object. + * @return The parent. + * + * @ingroup Menu + */ +EAPI Evas_Object * +elm_menu_parent_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->parent; +} + +/** + * Move the menu to a new position + * + * @param obj The menu object. + * @param x The new position. + * @param y The new position. + * + * @ingroup Menu + */ +EAPI void +elm_menu_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->xloc = x; + wd->yloc = y; + _sizing_eval(obj); +} + +/** + * Get the Evas_Object of an Elm_Menu_Item + * + * @param item The menu item object. + * + * @ingroup Menu + */ +EAPI Evas_Object * +elm_menu_object_get(const Elm_Menu_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->base.view; +} + +static void +_item_clone(Evas_Object *obj, Elm_Menu_Item *parent, Elm_Menu_Item *item) +{ + Elm_Menu_Item *new_item, *subitem; + Eina_List *iter; + + if (item->separator) + new_item = elm_menu_item_separator_add(obj, parent); + else + new_item = elm_menu_item_add(obj, parent, item->icon_str, item->label, item->func, item->base.data); + elm_menu_item_disabled_set(new_item, item->disabled); + + EINA_LIST_FOREACH(item->submenu.items, iter, subitem) + _item_clone(obj, new_item, subitem); +} + +void +elm_menu_clone(Evas_Object *from_menu, Evas_Object *to_menu, Elm_Menu_Item *parent) +{ + ELM_CHECK_WIDTYPE(from_menu, widtype); + ELM_CHECK_WIDTYPE(to_menu, widtype); + Widget_Data *from_wd = elm_widget_data_get(from_menu); + Eina_List *iter; + Elm_Menu_Item *item; + + if (!from_wd) return; + EINA_LIST_FOREACH(from_wd->items, iter, item) + _item_clone(to_menu, parent, item); +} + +/** + * Add an item at the end + * + * @param obj The menu object. + * @param icon A icon display on the item. The icon will be destryed by the menu. + * @param label The label of the item. + * @param func Function called when the user select the item. + * @param data Data sent by the callback. + * @return Returns the new item. + * + * @ingroup Menu + */ +EAPI Elm_Menu_Item * +elm_menu_item_add(Evas_Object *obj, Elm_Menu_Item *parent, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) +{ + Elm_Menu_Item *subitem; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *icon_obj; + + if (!wd) return NULL; + icon_obj = elm_icon_add(obj); + if (!icon_obj) return NULL; + subitem = elm_widget_item_new(obj, Elm_Menu_Item); + if (!subitem) + { + evas_object_del(icon_obj); + return NULL; + } + subitem->base.data = data; + subitem->func = func; + subitem->parent = parent; + subitem->icon = icon_obj; + + _item_obj_create(subitem); + elm_menu_item_label_set(subitem, label); + + elm_widget_sub_object_add(subitem->base.widget, subitem->icon); + edje_object_part_swallow(subitem->base.view, "elm.swallow.content", subitem->icon); + if (icon) elm_menu_item_icon_set(subitem, icon); + + if (parent) + { + if (!parent->submenu.bx) _item_submenu_obj_create(parent); + elm_box_pack_end(parent->submenu.bx, subitem->base.view); + parent->submenu.items = eina_list_append(parent->submenu.items, subitem); + } + else + { + elm_box_pack_end(wd->bx, subitem->base.view); + wd->items = eina_list_append(wd->items, subitem); + } + + _sizing_eval(obj); + return subitem; +} + +/** + * Set the label of a menu item + * + * @param item The menu item object. + * @param label The label to set for @p item + * + * @ingroup Menu + */ +EAPI void +elm_menu_item_label_set(Elm_Menu_Item *item, const char *label) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + eina_stringshare_replace(&item->label, label); + + if (label) + edje_object_signal_emit(item->base.view, "elm,state,text,visible", "elm"); + else + edje_object_signal_emit(item->base.view, "elm,state,text,hidden", "elm"); + + edje_object_message_signal_process(item->base.view); + edje_object_part_text_set(item->base.view, "elm.text", label); + _sizing_eval(item->base.widget); +} + +/** + * Get the label of a menu item + * + * @param item The menu item object. + * @return The label of @p item + * + * @ingroup Menu + */ +EAPI const char * +elm_menu_item_label_get(const Elm_Menu_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->label; +} + +/** + * Set the icon of a menu item + * + * Once the icon object is set, a previously set one will be deleted. + * + * @param item The menu item object. + * @param icon The icon object to set for @p item + * + * @ingroup Menu + */ +EAPI void +elm_menu_item_icon_set(Elm_Menu_Item *item, const char *icon) +{ + char icon_tmp[512]; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + EINA_SAFETY_ON_NULL_RETURN(icon); + if (!*icon) return; + if ((item->icon_str) && (!strcmp(item->icon_str, icon))) return; + if ((snprintf(icon_tmp, sizeof(icon_tmp), "menu/%s", icon) > 0) && + (elm_icon_standard_set(item->icon, icon_tmp))) + { + eina_stringshare_replace(&item->icon_str, icon); + edje_object_signal_emit(item->base.view, "elm,state,icon,visible", "elm"); + } + else + edje_object_signal_emit(item->base.view, "elm,state,icon,hidden", "elm"); + edje_object_message_signal_process(item->base.view); + _sizing_eval(item->base.widget); +} + +/** + * Set the disabled state of @p item. + * + * @param item The menu item object. + * @param disabled The enabled/disabled state of the item + * + * @ingroup Menu + */ +EAPI void +elm_menu_item_disabled_set(Elm_Menu_Item *item, Eina_Bool disabled) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (disabled == item->disabled) return; + item->disabled = disabled; + if (disabled) + { + edje_object_signal_emit(item->base.view, "elm,state,disabled", "elm"); + if (item->submenu.open) _submenu_hide(item); + } + else + edje_object_signal_emit(item->base.view, "elm,state,enabled", "elm"); + edje_object_message_signal_process(item->base.view); +} + +/** + * Get the disabled state of @p item. + * + * @param item The menu item object. + * @return The enabled/disabled state of the item + * + * @ingroup Menu + */ +EAPI Eina_Bool +elm_menu_item_disabled_get(const Elm_Menu_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + if (!item) return EINA_FALSE; + return item->disabled; +} + +/** + * Add a separator item to menu @p obj under @p parent. + * + * @param obj The menu object + * @param parent The item to add the separator under + * + * @return The created item or NULL on failure + * + * @ingroup Menu + */ +EAPI Elm_Menu_Item * +elm_menu_item_separator_add(Evas_Object *obj, Elm_Menu_Item *parent) +{ + Elm_Menu_Item *subitem; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + /* don't add a separator as the first item */ + if (!wd->items) return NULL; + /* don't allow adding more than one separator in a row */ + if (parent) subitem = eina_list_last(parent->submenu.items)->data; + else subitem = eina_list_last(wd->items)->data; + if (subitem->separator) return NULL; + + subitem = elm_widget_item_new(obj, Elm_Menu_Item); + if (!subitem) return NULL; + subitem->base.widget = obj; + subitem->separator = 1; + _item_separator_obj_create(subitem); + if (!parent) + { + elm_box_pack_end(wd->bx, subitem->base.view); + wd->items = eina_list_append(wd->items, subitem); + } + else + { + if (!parent->submenu.bx) _item_submenu_obj_create(parent); + elm_box_pack_end(parent->submenu.bx, subitem->base.view); + parent->submenu.items = eina_list_append(parent->submenu.items, subitem); + } + _sizing_eval(obj); + return subitem; +} + +/** + * Get the icon object from a menu item + * + * @param item The menu item object + * @return The icon object or NULL if there's no icon + * + * @ingroup Menu + */ +EAPI const Evas_Object * +elm_menu_item_object_icon_get(const Elm_Menu_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return (const Evas_Object *)item->icon; +} + +/** + * Get the string representation from the icon of a menu item + * + * @param item The menu item object. + * @return The string representation of @p item's icon or NULL + * + * @ingroup Menu + */ +EAPI const char * +elm_menu_item_icon_get(const Elm_Menu_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->icon_str; +} + +/** + * Returns whether @p item is a separator. + * + * @param item The item to check + * @return If true, @p item is a separator + * + * @ingroup Menu + */ +EAPI Eina_Bool +elm_menu_item_is_separator(Elm_Menu_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + return item->separator; +} + +/** + * Deletes an item from the menu. + * + * @param item The item to delete. + * + * @ingroup Menu + */ +EAPI void +elm_menu_item_del(Elm_Menu_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + Elm_Menu_Item *_item; + + elm_widget_item_pre_notify_del(item); + + EINA_LIST_FREE(item->submenu.items, _item) elm_menu_item_del(_item); + if (item->label) eina_stringshare_del(item->label); + if (item->icon) evas_object_del(item->icon); + if (item->submenu.hv) evas_object_del(item->submenu.hv); + if (item->submenu.location) evas_object_del(item->submenu.location); + + if (item->parent) + item->parent->submenu.items = eina_list_remove(item->parent->submenu.items, item); + else + { + Widget_Data *wd = elm_widget_data_get(item->base.widget); + wd->items = eina_list_remove(wd->items, item); + } + + elm_widget_item_del(item); +} + +/** + * Set the function called when a menu item is freed. + * + * @param item The item to set the callback on + * @param func The function called + * + * @ingroup Menu + */ +EAPI void +elm_menu_item_del_cb_set(Elm_Menu_Item *item, Evas_Smart_Cb func) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_del_cb_set(item, func); +} + +/** + * Returns the data associated with menu item @p item. + * + * @param item The item + * @return The data associated with @p item + * + * @ingroup Menu + */ +EAPI void * +elm_menu_item_data_get(const Elm_Menu_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_data_get(item); +} + +/** + * Sets the data to be associated with menu item @p item. + * + * @param item The item + * @param data The data to be associated with @p item + * + * @ingroup Menu + */ +EAPI void +elm_menu_item_data_set(Elm_Menu_Item *item, const void *data) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_data_set(item, data); +} + +/** + * Returns a list of @p item's subitems. + * + * @param item The item + * @return An Eina_List* of @p item's subitems + * + * @ingroup Menu + */ +EAPI const Eina_List * +elm_menu_item_subitems_get(const Elm_Menu_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->submenu.items; +} diff --git a/src/lib/elm_module.c b/src/lib/elm_module.c new file mode 100644 index 0000000..ad78943 --- /dev/null +++ b/src/lib/elm_module.c @@ -0,0 +1,216 @@ +#include +#include "elm_priv.h" + +/* what are moodules in elementary for? for modularising behavior and features + * so they can be plugged in and out where you dont want the core source to + * always behave like that or do it that way. plug it at runtime! + * + * they have module names (in config) and "slots" to plug that module into + * to server a purpose. eg you plug plugin "xx" into the "entry-copy-paste" + * slot so it would provide replacement copy & paste ui functionality and + * specific symbols + * + * config is something like: + * + * export ELM_MODULES="xx>slot1:yy>slot2" + * + * where a module named xx is plugged into slot1 & yy is plugged into slot2 + * + * real examples: + * + * export ELM_MODULES="my_module>entry/api" + * + * this loads the module called "my_module" into the slot "entry/api" which + * is an api slot for entry modules to modify behavior and hook to + * creation/deletion of the entry as well as replace the longpress behavior. + */ + +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif + +#include /* dlopen,dlclose,etc */ + +static Eina_Hash *modules = NULL; +static Eina_Hash *modules_as = NULL; + +void +_elm_module_init(void) +{ + modules = eina_hash_string_small_new(NULL); + modules_as = eina_hash_string_small_new(NULL); +} + +void +_elm_module_shutdown(void) +{ + // FIXME: unload all modules + if (modules) eina_hash_free(modules); + modules = NULL; + if (modules_as) eina_hash_free(modules_as); + modules_as = NULL; +} + +void +_elm_module_parse(const char *s) +{ + const char *p, *pe; + + p = s; + pe = p; + for (;;) + { + if ((*pe == ':') || (!*pe)) + { // p -> pe == 'name:' + if (pe > p) + { + char *n = malloc(pe - p + 1); + if (n) + { + char *nn; + + strncpy(n, p, pe - p); + n[pe - p] = 0; + nn = strchr(n, '>'); + if (nn) + { + *nn = 0; + nn++; + _elm_module_add(n, nn); + } + free(n); + } + } + if (!*pe) break; + p = pe + 1; + pe = p; + } + else + pe++; + } +} + +Elm_Module * +_elm_module_find_as(const char *as) +{ + Elm_Module *m; + + m = eina_hash_find(modules_as, as); + return m; +} + +Elm_Module * +_elm_module_add(const char *name, const char *as) +{ + Elm_Module *m; + char buf[PATH_MAX]; + + m = eina_hash_find(modules, name); + if (m) + { + m->references++; + return m; + } + m = calloc(1, sizeof(Elm_Module)); + if (!m) return NULL; + m->version = 1; + if (name[0] != '/') + { + const char *home = getenv("HOME"); + + if (home) + { + snprintf(buf, sizeof(buf), "%s/.elementary/modules/%s/%s/module" EFL_SHARED_EXTENSION, home, name, MODULE_ARCH); + m->handle = dlopen(buf, RTLD_NOW | RTLD_GLOBAL); + if (m->handle) + { + m->init_func = dlsym(m->handle, "elm_modapi_init"); + if (m->init_func) + { + m->shutdown_func = dlsym(m->handle, "elm_modapi_shutdown"); + m->so_path = eina_stringshare_add(buf); + m->name = eina_stringshare_add(name); + snprintf(buf, sizeof(buf), "%s/.elementary/modules/%s/%s", home, name, MODULE_ARCH); + m->bin_dir = eina_stringshare_add(buf); + snprintf(buf, sizeof(buf), "%s/.elementary/modules/%s", home, name); + m->data_dir = eina_stringshare_add(buf); + } + else + { + dlclose(m->handle); + free(m); + return NULL; + } + } + } + if (!m->handle) + { + snprintf(buf, sizeof(buf), "%s/elementary/modules/%s/%s/module" EFL_SHARED_EXTENSION, _elm_lib_dir, name, MODULE_ARCH); + m->handle = dlopen(buf, RTLD_NOW | RTLD_GLOBAL); + if (m->handle) + { + m->init_func = dlsym(m->handle, "elm_modapi_init"); + if (m->init_func) + { + m->shutdown_func = dlsym(m->handle, "elm_modapi_shutdown"); + m->so_path = eina_stringshare_add(buf); + m->name = eina_stringshare_add(name); + snprintf(buf, sizeof(buf), "%s/elementary/modules/%s/%s", _elm_lib_dir, name, MODULE_ARCH); + m->bin_dir = eina_stringshare_add(buf); + snprintf(buf, sizeof(buf), "%s/elementary/modules/%s", _elm_lib_dir, name); + m->data_dir = eina_stringshare_add(buf); + } + else + { + dlclose(m->handle); + free(m); + return NULL; + } + } + } + } + if (!m->handle) + { + free(m); + return NULL; + } + if (!m->init_func(m)) + { + dlclose(m->handle); + eina_stringshare_del(m->name); + eina_stringshare_del(m->so_path); + eina_stringshare_del(m->data_dir); + eina_stringshare_del(m->bin_dir); + free(m); + return NULL; + } + m->references = 1; + eina_hash_direct_add(modules, m->name, m); + m->as = eina_stringshare_add(as); + eina_hash_direct_add(modules_as, m->as, m); + return m; +} + +void +_elm_module_del(Elm_Module *m) +{ + m->references--; + if (m->references > 0) return; + if (m->shutdown_func) m->shutdown_func(m); + eina_hash_del(modules, m->name, m); + eina_hash_del(modules_as, m->as, m); + if (m->api) free(m->api); + eina_stringshare_del(m->name); + eina_stringshare_del(m->as); + eina_stringshare_del(m->so_path); + eina_stringshare_del(m->data_dir); + eina_stringshare_del(m->bin_dir); + dlclose(m->handle); + free(m); +} + +const void * +_elm_module_symbol_get(Elm_Module *m, const char *name) +{ + return dlsym(m->handle, name); +} diff --git a/src/lib/elm_notify.c b/src/lib/elm_notify.c new file mode 100644 index 0000000..18c407d --- /dev/null +++ b/src/lib/elm_notify.c @@ -0,0 +1,625 @@ +#include +#include "elm_priv.h" + + +/** + * @defgroup Notify notify + * + * Display a window in a particular region of the application (top, + * bottom, etc. A timeout can be set to automatically close the + * window. This is so that, after an evas_object_show() on a notify + * object, if a timeout was set on it, it will automatically + * get hidden after that time. + * + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *notify, *content, *parent; + + Elm_Notify_Orient orient; + Eina_Bool repeat_events; + Evas_Object *block_events; + + double timeout; + Ecore_Timer *timer; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _signal_block_clicked(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _calc(Evas_Object *obj); +static void _content_resize(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _show(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _hide(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _resize(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static const char SIG_BLOCK_CLICKED[] = "block,clicked"; +static const char SIG_TIMEOUT[] = "timeout"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_BLOCK_CLICKED, ""}, + {SIG_TIMEOUT, ""}, + {NULL, NULL} +}; + +static void +_del_pre_hook(Evas_Object *obj) +{ + evas_object_event_callback_del_full(obj, EVAS_CALLBACK_RESIZE, _resize, obj); + evas_object_event_callback_del_full(obj, EVAS_CALLBACK_MOVE, _resize, obj); + evas_object_event_callback_del_full(obj, EVAS_CALLBACK_SHOW, _show, obj); + evas_object_event_callback_del_full(obj, EVAS_CALLBACK_HIDE, _hide, obj); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_notify_parent_set(obj, NULL); + elm_notify_repeat_events_set(obj, EINA_TRUE); + if (wd->timer) + { + ecore_timer_del(wd->timer); + wd->timer = NULL; + } + free(wd); +} + +static void +_notify_theme_apply(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const char *style = elm_widget_style_get(obj); + + switch (wd->orient) + { + case ELM_NOTIFY_ORIENT_TOP: + _elm_theme_object_set(obj, wd->notify, "notify", "top", style); + break; + case ELM_NOTIFY_ORIENT_CENTER: + _elm_theme_object_set(obj, wd->notify, "notify", "center", style); + break; + case ELM_NOTIFY_ORIENT_BOTTOM: + _elm_theme_object_set(obj, wd->notify, "notify", "bottom", style); + break; + case ELM_NOTIFY_ORIENT_LEFT: + _elm_theme_object_set(obj, wd->notify, "notify", "left", style); + break; + case ELM_NOTIFY_ORIENT_RIGHT: + _elm_theme_object_set(obj, wd->notify, "notify", "right", style); + break; + case ELM_NOTIFY_ORIENT_TOP_LEFT: + _elm_theme_object_set(obj, wd->notify, "notify", "top_left", style); + break; + case ELM_NOTIFY_ORIENT_TOP_RIGHT: + _elm_theme_object_set(obj, wd->notify, "notify", "top_right", style); + break; + case ELM_NOTIFY_ORIENT_BOTTOM_LEFT: + _elm_theme_object_set(obj, wd->notify, "notify", "bottom_left", style); + break; + case ELM_NOTIFY_ORIENT_BOTTOM_RIGHT: + _elm_theme_object_set(obj, wd->notify, "notify", "bottom_right", style); + break; + case ELM_NOTIFY_ORIENT_LAST: + break; + } +} + +static void +_block_events_theme_apply(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const char *style = elm_widget_style_get(obj); + _elm_theme_object_set(obj, wd->block_events, "notify", "block_events", style); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _notify_theme_apply(obj); + if (wd->block_events) _block_events_theme_apply(obj); + edje_object_scale_set(wd->notify, elm_widget_scale_get(obj) * + _elm_config->scale); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord x,y,w,h; + if (!wd) return; + if (!wd->parent) return; + evas_object_geometry_get(wd->parent, &x, &y, &w, &h); + evas_object_move(obj, x, y); + evas_object_resize(obj, w, h); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _calc(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + + if (sub == wd->content) + { + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_RESIZE, + _content_resize, obj); + wd->content = NULL; + } +} + +static void +_signal_block_clicked(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + evas_object_smart_callback_call(data, SIG_BLOCK_CLICKED, NULL); +} + +static void +_resize(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + _calc(obj); +} + +static void +_content_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _calc(data); +} + +static void +_calc(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + Evas_Coord x, y, w, h; + + if (!wd) return; + evas_object_geometry_get(obj, &x, &y, &w, &h); + edje_object_size_min_get(wd->notify, &minw, &minh); + edje_object_size_min_restricted_calc(wd->notify, &minw, &minh, minw, minh); + + if (wd->content) + { + int offx = (w - minw) / 2; + int offy = (h - minh) / 2; + + switch (wd->orient) + { + case ELM_NOTIFY_ORIENT_TOP: + evas_object_move(wd->notify, x + offx, y); + break; + case ELM_NOTIFY_ORIENT_CENTER: + evas_object_move(wd->notify, x + offx, y + offy); + break; + case ELM_NOTIFY_ORIENT_BOTTOM: + evas_object_move(wd->notify, x + offx, y + h - minh); + break; + case ELM_NOTIFY_ORIENT_LEFT: + evas_object_move(wd->notify, x, y + offy); + break; + case ELM_NOTIFY_ORIENT_RIGHT: + evas_object_move(wd->notify, x + w - minw, y + offy); + break; + case ELM_NOTIFY_ORIENT_TOP_LEFT: + evas_object_move(wd->notify, x, y); + break; + case ELM_NOTIFY_ORIENT_TOP_RIGHT: + evas_object_move(wd->notify, x + w - minw, y); + break; + case ELM_NOTIFY_ORIENT_BOTTOM_LEFT: + evas_object_move(wd->notify, x, y + h - minh); + break; + case ELM_NOTIFY_ORIENT_BOTTOM_RIGHT: + evas_object_move(wd->notify, x + w - minw, y + h - minh); + break; + case ELM_NOTIFY_ORIENT_LAST: + break; + } + evas_object_resize(wd->notify, minw, minh); + } + _sizing_eval(obj); +} + +static Eina_Bool +_timer_cb(void *data) +{ + Evas_Object *obj = data; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->timer = NULL; + evas_object_hide(obj); + evas_object_smart_callback_call(obj, SIG_TIMEOUT, NULL); + return ECORE_CALLBACK_CANCEL; +} + +static void +_timer_init(Evas_Object *obj, Widget_Data *wd) +{ + if (wd->timer) + { + ecore_timer_del(wd->timer); + wd->timer = NULL; + } + if ((evas_object_visible_get(obj)) && (wd->timeout > 0.0)) + wd->timer = ecore_timer_add(wd->timeout, _timer_cb, obj); +} + +static void +_show(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_show(wd->notify); + if (!wd->repeat_events) + evas_object_show(wd->block_events); + _timer_init(obj, wd); +} + +static void +_hide(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_hide(wd->notify); + if (!wd->repeat_events) + evas_object_hide(wd->block_events); + if (wd->timer) + { + ecore_timer_del(wd->timer); + wd->timer = NULL; + } +} + +static void +_parent_del(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->parent = NULL; + evas_object_hide(obj); +} + +static void +_parent_hide(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->parent = NULL; + evas_object_hide(obj); +} + +/** + * Add a new notify to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Notify + */ +EAPI Evas_Object * +elm_notify_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "notify"); + elm_widget_type_set(obj, "notify"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->repeat_events = EINA_TRUE; + + wd->notify = edje_object_add(e); + wd->orient = -1; + elm_notify_orient_set(obj, ELM_NOTIFY_ORIENT_TOP); + + elm_notify_parent_set(obj, parent); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + evas_object_event_callback_add(obj, EVAS_CALLBACK_RESIZE, _resize, obj); + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOVE, _resize, obj); + evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, _show, obj); + evas_object_event_callback_add(obj, EVAS_CALLBACK_HIDE, _hide, obj); + + _sizing_eval(obj); + + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the content of the notify widget + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_notify_content_unset() function. + * + * @param obj The notify object + * @param content The content will be filled in this notify object + * + * @ingroup Notify + */ +EAPI void +elm_notify_content_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->content == content) return; + if (wd->content) evas_object_del(wd->content); + wd->content = content; + + if (content) + { + elm_widget_sub_object_add(obj, content); + evas_object_event_callback_add(content, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + evas_object_event_callback_add(content, EVAS_CALLBACK_RESIZE, + _content_resize, obj); + edje_object_part_swallow(wd->notify, "elm.swallow.content", content); + } + _sizing_eval(obj); + _calc(obj); +} + +/** + * Unset the content of the notify widget + * + * Unparent and return the content object which was set for this widget + * + * @param obj The notify object + * @return The content that was being used + * + * @ingroup Notify + */ +EAPI Evas_Object * +elm_notify_content_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *content; + if (!wd) return NULL; + if (!wd->content) return NULL; + content = wd->content; + elm_widget_sub_object_del(obj, wd->content); + edje_object_part_unswallow(wd->notify, wd->content); + wd->content = NULL; + return content; +} + +/** + * Return the content of the notify widget + * + * @param obj The notify object + * @return The content that is being used + * + * @ingroup Notify + */ +EAPI Evas_Object * +elm_notify_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return NULL; + return wd->content; +} + +/** + * Set the notify parent + * + * Once the parent object is set, a previously set one will be desconected + * and replaced. + * + * @param obj The notify object + * @param content The new parent + * + * @ingroup Notify + */ +EAPI void +elm_notify_parent_set(Evas_Object *obj, Evas_Object *parent) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->parent) + { + evas_object_event_callback_del_full(wd->parent, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_RESIZE, + _changed_size_hints, obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_MOVE, + _changed_size_hints, obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_DEL, + _parent_del, obj); + evas_object_event_callback_del_full(wd->parent, EVAS_CALLBACK_HIDE, + _parent_hide, obj); + wd->parent = NULL; + } + + if (parent) + { + wd->parent = parent; + evas_object_event_callback_add(parent, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + evas_object_event_callback_add(parent, EVAS_CALLBACK_RESIZE, + _changed_size_hints, obj); + evas_object_event_callback_add(parent, EVAS_CALLBACK_MOVE, + _changed_size_hints, obj); + evas_object_event_callback_add(parent, EVAS_CALLBACK_DEL, + _parent_del, obj); + evas_object_event_callback_add(parent, EVAS_CALLBACK_HIDE, + _parent_hide, obj); + edje_object_part_swallow(wd->notify, "elm.swallow.parent", parent); + _sizing_eval(obj); + } + _calc(obj); +} + +/** + * Get the notify parent + * + * @param obj The notify object + * @return The parent + * + * @ingroup Notify + */ +EAPI Evas_Object * +elm_notify_parent_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->parent; +} + +/** + * Set the orientation + * + * @param obj The notify object + * @param orient The new orientation + */ +EAPI void +elm_notify_orient_set(Evas_Object *obj, Elm_Notify_Orient orient) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->orient == orient) return; + wd->orient = orient; + _notify_theme_apply(obj); + _resize(obj, NULL, obj, NULL); +} + +/** + * Return the orientation + * @param obj the notify objects + */ +EAPI Elm_Notify_Orient +elm_notify_orient_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) -1; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return -1; + return wd->orient; +} + +/** + * Set the time interval after which the notify window is going to be + * hidden. + * + * @param obj The notify object + * @param time The new timeout + * + * As said previously, an evas_object_show() on a notify object which + * had a timeout set by this function will trigger a timer to + * automatically hide it again. So, any order one calls + * elm_notify_timeout_set() and evas_object_show() on the same object + * (at hidden state) will behave the same. + * + * @note Set a value <= 0.0 to disable a running timer. + * + * @note If the value > 0.0 and the notify is previously visible, the + * timer will be started with this value, canceling any running timer. + * + */ +EAPI void +elm_notify_timeout_set(Evas_Object *obj, double timeout) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->timeout = timeout; + _timer_init(obj, wd); +} + +/** + * Return the timeout value (in seconds) + * @param obj the notify object + */ +EAPI double +elm_notify_timeout_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->timeout; +} + +/** + * When true if the user clicks outside the window the events will be + * catch by the others widgets, else the events are block and the signal + * dismiss will be sent when the user click outside the window. + * + * @note The default value is EINA_TRUE. + * + * @param obj The notify object + * @param repeats EINA_TRUE Events are repeats, else no + */ +EAPI void +elm_notify_repeat_events_set(Evas_Object *obj, Eina_Bool repeat) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (repeat == wd->repeat_events) return; + wd->repeat_events = repeat; + if (!repeat) + { + wd->block_events = edje_object_add(evas_object_evas_get(obj)); + _block_events_theme_apply(obj); + elm_widget_resize_object_set(obj, wd->block_events); + edje_object_signal_callback_add(wd->block_events, "elm,action,clicked", + "elm", _signal_block_clicked, obj); + } + else + evas_object_del(wd->block_events); +} + +/** + * Return true if events are repeat below the notify object + * @param obj the notify object + */ +EAPI Eina_Bool +elm_notify_repeat_events_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->repeat_events; +} + diff --git a/src/lib/elm_pager.c b/src/lib/elm_pager.c new file mode 100644 index 0000000..0c6c67e --- /dev/null +++ b/src/lib/elm_pager.c @@ -0,0 +1,442 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Pager Pager + * + * The pager is an object that allows flipping (with animation) between 1 or + * more “pages” of objects, much like a stack of windows within the window. + * + * Objects can be pushed or popped from the stack or deleted as normal. + * Pushes and pops will animate (and a pop will delete the object once the + * animation is finished). Any object in the pager can be promoted to the top + * (from its current stacking position) as well. Objects are pushed to the + * top with elm_pager_content_push() and when the top item is no longer + * wanted, simply pop it with elm_pager_content_pop() and it will also be + * deleted. Any object you wish to promote to the top that is already in the + * pager, simply use elm_pager_content_promote(). If an object is no longer + * needed and is not the top item, just delete it as normal. You can query + * which objects are the top and bottom with elm_pager_content_bottom_get() + * and elm_pager_content_top_get(). + */ + +typedef struct _Widget_Data Widget_Data; +typedef struct _Item Item; + +struct _Widget_Data +{ + Eina_List *stack; + Item *top, *oldtop; + Evas_Object *rect, *clip; +}; + +struct _Item +{ + Evas_Object *obj, *base, *content; + Evas_Coord minw, minh; + Eina_Bool popme : 1; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Item *it; + if (!wd) return; + EINA_LIST_FOREACH(wd->stack, l, it) + { + _elm_theme_object_set(obj, it->base, "pager", "base", + elm_widget_style_get(obj)); + edje_object_scale_set(it->base, elm_widget_scale_get(obj) * + _elm_config->scale); + } + _sizing_eval(obj); +} + +static Eina_Bool +_elm_pager_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *cur; + + if ((!wd) || (!wd->top)) + return EINA_FALSE; + + cur = wd->top->content; + + /* Try Focus cycle in subitem */ + return elm_widget_focus_next_get(cur, dir, next); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + Eina_List *l; + Item *it; + if (!wd) return; + EINA_LIST_FOREACH(wd->stack, l, it) + { + if (it->minw > minw) minw = it->minw; + if (it->minh > minh) minh = it->minh; + } + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Item *it = data; + Evas_Coord minw = -1, minh = -1; + evas_object_size_hint_min_get(it->content, &minw, &minh); + // FIXME: why is this needed? how does edje get this unswallowed or + // lose its callbacks to edje + edje_object_part_swallow(it->base, "elm.swallow.content", it->content); + edje_object_size_min_calc(it->base, &it->minw, &it->minh); + _sizing_eval(it->obj); +} + +static void +_eval_top(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Item *ittop; + if (!wd) return; + if (!wd->stack) return; + ittop = eina_list_last(wd->stack)->data; + if (ittop != wd->top) + { + Evas_Object *o; + const char *onshow, *onhide; + + if (wd->top) + { + o = wd->top->base; + if (wd->top->popme) + edje_object_signal_emit(o, "elm,action,pop", "elm"); + else + edje_object_signal_emit(o, "elm,action,hide", "elm"); + onhide = edje_object_data_get(o, "onhide"); + if (onhide) + { + if (!strcmp(onhide, "raise")) evas_object_raise(o); + else if (!strcmp(onhide, "lower")) evas_object_lower(o); + } + } + wd->oldtop = wd->top; + wd->top = ittop; + o = wd->top->base; + evas_object_show(o); + if (wd->oldtop) + { + if (elm_object_focus_get(wd->oldtop->content)) + elm_object_focus(wd->top->content); + if (wd->oldtop->popme) + edje_object_signal_emit(o, "elm,action,show", "elm"); + else + edje_object_signal_emit(o, "elm,action,push", "elm"); + } + else + edje_object_signal_emit(o, "elm,action,push", "elm"); + onshow = edje_object_data_get(o, "onshow"); + if (onshow) + { + if (!strcmp(onshow, "raise")) evas_object_raise(o); + else if (!strcmp(onshow, "lower")) evas_object_lower(o); + } + } +} + +static void +_move(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord x, y; + Eina_List *l; + Item *it; + if (!wd) return; + evas_object_geometry_get(obj, &x, &y, NULL, NULL); + EINA_LIST_FOREACH(wd->stack, l, it) + evas_object_move(it->base, x, y); +} + +static void +_sub_del(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Object *sub = event_info; + Eina_List *l; + Item *it; + if (!wd) return; + EINA_LIST_FOREACH(wd->stack, l, it) + { + if (it->content == sub) + { + wd->stack = eina_list_remove_list(wd->stack, l); + evas_object_event_callback_del_full + (sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, it); + evas_object_del(it->base); + _eval_top(it->obj); + free(it); + return; + } + } +} + +static void +_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord w, h; + Eina_List *l; + Item *it; + if (!wd) return; + evas_object_geometry_get(obj, NULL, NULL, &w, &h); + EINA_LIST_FOREACH(wd->stack, l, it) evas_object_resize(it->base, w, h); +} + +static void +_signal_hide_finished(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Item *it = data; + Evas_Object *obj2 = it->obj; + evas_object_hide(it->base); + edje_object_signal_emit(it->base, "elm,action,reset", "elm"); + evas_object_smart_callback_call(obj2, "hide,finished", it->content); + edje_object_message_signal_process(it->base); + evas_object_hide(it->content); + if (it->popme) evas_object_del(it->content); + _sizing_eval(obj2); +} + +/** + * Add a new pager to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Pager + */ +EAPI Evas_Object * +elm_pager_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "pager"); + elm_widget_type_set(obj, "pager"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_focus_next_hook_set(obj, _elm_pager_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->clip = evas_object_rectangle_add(e); + elm_widget_resize_object_set(obj, wd->clip); + elm_widget_sub_object_add(obj, wd->clip); + + wd->rect = evas_object_rectangle_add(e); + elm_widget_sub_object_add(obj, wd->rect); + evas_object_color_set(wd->rect, 255, 255, 255, 0); + evas_object_clip_set(wd->rect, wd->clip); + + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOVE, _move, obj); + evas_object_event_callback_add(obj, EVAS_CALLBACK_RESIZE, _resize, obj); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + _sizing_eval(obj); + return obj; +} + +/** + * Push an object to the top of the pager stack (and show it) + * + * The object pushed becomes a child of the pager and will be controlled + * it and deleted when the pager is deleted. + * + * @param obj The pager object + * @param content The object to push + * + * @ingroup Pager + */ +EAPI void +elm_pager_content_push(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Item *it = ELM_NEW(Item); + Evas_Coord x, y, w, h; + if (!wd) return; + if (!it) return; + it->obj = obj; + it->content = content; + it->base = edje_object_add(evas_object_evas_get(obj)); + evas_object_smart_member_add(it->base, obj); + evas_object_geometry_get(obj, &x, &y, &w, &h); + evas_object_move(it->base, x, y); + evas_object_resize(it->base, w, h); + evas_object_clip_set(it->base, wd->clip); + elm_widget_sub_object_add(obj, it->base); + elm_widget_sub_object_add(obj, it->content); + _elm_theme_object_set(obj, it->base, "pager", "base", elm_widget_style_get(obj)); + edje_object_signal_callback_add(it->base, "elm,action,hide,finished", "", + _signal_hide_finished, it); + evas_object_event_callback_add(it->content, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, it); + edje_object_part_swallow(it->base, "elm.swallow.content", it->content); + edje_object_size_min_calc(it->base, &it->minw, &it->minh); + evas_object_data_set(it->base, "_elm_leaveme", obj); + evas_object_show(it->content); + wd->stack = eina_list_append(wd->stack, it); + _eval_top(obj); + _sizing_eval(obj); +} + +/** + * Pop the object that is on top of the stack + * + * This pops the object that is on top (visible) in the pager, makes it + * disappear, then deletes the object. The object that was underneath it + * on the stack will become visible. + * + * @param obj The pager object + * + * @ingroup Pager + */ +EAPI void +elm_pager_content_pop(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *ll; + Item *it; + if (!wd) return; + if (!wd->stack) return; + it = eina_list_last(wd->stack)->data; + it->popme = EINA_TRUE; + ll = eina_list_last(wd->stack); + if (ll) + { + ll = ll->prev; + if (!ll) + { + Evas_Object *o; + const char *onhide; + + wd->top = it; + o = wd->top->base; + edje_object_signal_emit(o, "elm,action,pop", "elm"); + onhide = edje_object_data_get(o, "onhide"); + if (onhide) + { + if (!strcmp(onhide, "raise")) evas_object_raise(o); + else if (!strcmp(onhide, "lower")) evas_object_lower(o); + } + wd->top = NULL; + } + else + { + it = ll->data; + elm_pager_content_promote(obj, it->content); + } + } +} + +/** + * Promote an object already in the pager stack to the top of the stack + * + * This will take the indicated object and promote it to the top of the stack + * as if it had been pushed there. The object must already be inside the + * pager stack to work. + * + * @param obj The pager object + * @param content The object to promote + * + * @ingroup Pager + */ +EAPI void +elm_pager_content_promote(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Item *it; + if (!wd) return; + EINA_LIST_FOREACH(wd->stack, l, it) + { + if (it->content == content) + { + wd->stack = eina_list_remove_list(wd->stack, l); + wd->stack = eina_list_append(wd->stack, it); + _eval_top(obj); + return; + } + } +} + +/** + * Return the object at the bottom of the pager stack + * + * @param obj The pager object + * @return The bottom object or NULL if none + * + * @ingroup Pager + */ +EAPI Evas_Object * +elm_pager_content_bottom_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Item *it; + if (!wd) return NULL; + if (!wd->stack) return NULL; + it = wd->stack->data; + return it->content; +} + +/** + * Return the object at the top of the pager stack + * + * @param obj The pager object + * @return The top object or NULL if none + * + * @ingroup Pager + */ +EAPI Evas_Object * +elm_pager_content_top_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->top) return NULL; + return wd->top->content; +} + diff --git a/src/lib/elm_panel.c b/src/lib/elm_panel.c new file mode 100644 index 0000000..c6b7a9f --- /dev/null +++ b/src/lib/elm_panel.c @@ -0,0 +1,469 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Panel Panel + * + * A panel is a type of animated container that contains subobjects. It + * can be expanded or contracted. + * + * Orientations are as follows: + * ELM_PANEL_ORIENT_TOP + * ELM_PANEL_ORIENT_BOTTOM + * ELM_PANEL_ORIENT_LEFT + * ELM_PANEL_ORIENT_RIGHT + * NOTE: Only LEFT and RIGHT orientations are implemented. + * + * THIS WIDGET IS UNDER CONSTRUCTION! + */ + +typedef struct _Widget_Data Widget_Data; +struct _Widget_Data +{ + Evas_Object *scr, *bx, *content; + Elm_Panel_Orient orient; + Eina_Bool hidden : 1; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _on_focus_hook(void *data, Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _resize(void *data, Evas *evas, Evas_Object *obj, void *event); +static void _layout(Evas_Object *o, Evas_Object_Box_Data *priv, void *data); +static void _toggle_panel(void *data, Evas_Object *obj, const char *emission, const char *source); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->scr) + { + Evas_Object *edj; + const char *str; + + elm_smart_scroller_object_theme_set(obj, wd->scr, "panel", "base", + elm_widget_style_get(obj)); + // scale = (elm_widget_scale_get(obj) * _elm_config->scale); + // edje_object_scale_set(wd->scr, scale); + edj = elm_smart_scroller_edje_object_get(wd->scr); + str = edje_object_data_get(edj, "focus_highlight"); + if ((str) && (!strcmp(str, "on"))) + elm_widget_highlight_in_theme_set(obj, EINA_TRUE); + else + elm_widget_highlight_in_theme_set(obj, EINA_FALSE); + } + _sizing_eval(obj); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + evas_object_focus_set(obj, EINA_TRUE); + else + evas_object_focus_set(obj, EINA_FALSE); +} + +static Eina_Bool +_elm_panel_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *cur; + + if ((!wd) || (!wd->content)) + return EINA_FALSE; + + cur = wd->content; + + /* Try Focus cycle in subitem */ + if (!wd->hidden) + return elm_widget_focus_next_get(cur, dir, next); + + /* Return */ + *next = (Evas_Object *)obj; + return !elm_widget_focus_get(obj); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_callback_add(elm_smart_scroller_edje_object_get(wd->scr), + emission, source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_del_full( + elm_smart_scroller_edje_object_get(wd->scr), emission, source, + func_cb, data); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord mw = -1, mh = -1; + Evas_Coord vw = 0, vh = 0; + Evas_Coord w, h; + if (!wd) return; + evas_object_smart_calculate(wd->bx); + edje_object_size_min_calc(elm_smart_scroller_edje_object_get(wd->scr), + &mw, &mh); + evas_object_geometry_get(obj, NULL, NULL, &w, &h); + if (w < mw) w = mw; + if (h < mh) h = mh; + evas_object_resize(wd->scr, w, h); + + evas_object_size_hint_min_get(wd->bx, &mw, &mh); + if (w > mw) mw = w; + if (h > mh) mh = h; + evas_object_resize(wd->bx, mw, mh); + + elm_smart_scroller_child_viewport_size_get(wd->scr, &vw, &vh); + mw = mw + (w - vw); + mh = mh + (h - vh); + evas_object_size_hint_min_set(obj, mw, mh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_resize(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord mw, mh, vw, vh, w, h; + if (!wd) return; + elm_smart_scroller_child_viewport_size_get(wd->scr, &vw, &vh); + evas_object_size_hint_min_get(wd->bx, &mw, &mh); + evas_object_geometry_get(wd->bx, NULL, NULL, &w, &h); + if ((vw >= mw) || (vh >= mh)) + { + if ((w != vw) || (h != vh)) evas_object_resize(wd->bx, vw, vh); + } +} + +static void +_layout(Evas_Object *o, Evas_Object_Box_Data *priv, void *data) +{ + Widget_Data *wd = data; + if (!wd) return; + _els_box_layout(o, priv, EINA_TRUE, EINA_FALSE); +} + +static void +_toggle_panel(void *data, Evas_Object *obj, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (wd->hidden) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,action,show", "elm"); + wd->hidden = EINA_FALSE; + evas_object_repeat_events_set(obj, EINA_FALSE); + } + else + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,action,hide", "elm"); + wd->hidden = EINA_TRUE; + evas_object_repeat_events_set(obj, EINA_TRUE); + if (elm_widget_focus_get(wd->content)) + { + elm_widget_focused_object_clear(obj); + elm_widget_focus_steal(obj); + } + } +} + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if ((src != obj) || (type != EVAS_CALLBACK_KEY_DOWN)) return EINA_FALSE; + + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + + if ((strcmp(ev->keyname, "Return")) && + (strcmp(ev->keyname, "KP_Enter")) && + (strcmp(ev->keyname, "space"))) + return EINA_FALSE; + + _toggle_panel(obj, NULL, "elm,action,panel,toggle", "*"); + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; +} + +/** + * Adds a panel object + * + * @param parent The parent object + * + * @return The panel object, or NULL on failure + * + * @ingroup Panel + */ +EAPI Evas_Object * +elm_panel_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *evas; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + evas = evas_object_evas_get(parent); + if (!evas) return NULL; + obj = elm_widget_add(evas); + ELM_SET_WIDTYPE(widtype, "panel"); + elm_widget_type_set(obj, "panel"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + elm_widget_focus_next_hook_set(obj, _elm_panel_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->scr = elm_smart_scroller_add(evas); + elm_smart_scroller_widget_set(wd->scr, obj); + _theme_hook(obj); + elm_smart_scroller_bounce_allow_set(wd->scr, EINA_FALSE, EINA_FALSE); + elm_widget_resize_object_set(obj, wd->scr); + elm_smart_scroller_policy_set(wd->scr, ELM_SMART_SCROLLER_POLICY_OFF, + ELM_SMART_SCROLLER_POLICY_OFF); + + wd->hidden = EINA_FALSE; + wd->orient = ELM_PANEL_ORIENT_LEFT; + + wd->bx = evas_object_box_add(evas); + evas_object_size_hint_align_set(wd->bx, 0.5, 0.5); + evas_object_box_layout_set(wd->bx, _layout, wd, NULL); + elm_widget_sub_object_add(obj, wd->bx); + elm_smart_scroller_child_set(wd->scr, wd->bx); + evas_object_show(wd->bx); + + edje_object_signal_callback_add(elm_smart_scroller_edje_object_get(wd->scr), + "elm,action,panel,toggle", "*", + _toggle_panel, obj); + + evas_object_event_callback_add(wd->scr, EVAS_CALLBACK_RESIZE, _resize, obj); + + _sizing_eval(obj); + return obj; +} + +/** + * Sets the orientation of the panel + * + * @param parent The parent object + * @param orient The panel orientation. Can be one of the following: + * ELM_PANEL_ORIENT_TOP + * ELM_PANEL_ORIENT_BOTTOM + * ELM_PANEL_ORIENT_LEFT + * ELM_PANEL_ORIENT_RIGHT + * + * NOTE: Only LEFT and RIGHT orientations are implemented. + * + * @ingroup Panel + */ +EAPI void +elm_panel_orient_set(Evas_Object *obj, Elm_Panel_Orient orient) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->orient = orient; + switch (orient) + { + case ELM_PANEL_ORIENT_TOP: + elm_smart_scroller_object_theme_set(obj, wd->scr, "panel", "base", "top"); + break; + case ELM_PANEL_ORIENT_BOTTOM: + elm_smart_scroller_object_theme_set(obj, wd->scr, "panel", "base", "bottom"); + break; + case ELM_PANEL_ORIENT_LEFT: + elm_smart_scroller_object_theme_set(obj, wd->scr, "panel", "base", "left"); + break; + case ELM_PANEL_ORIENT_RIGHT: + elm_smart_scroller_object_theme_set(obj, wd->scr, "panel", "base", "right"); + break; + } + _sizing_eval(obj); +} + +/** + * Get the orientation of the panel. + * + * @param obj The panel object + * @return The Elm_Panel_Orient, or ELM_PANEL_ORIENT_LEFT on failure. + * + * @ingroup Panel + */ +EAPI Elm_Panel_Orient +elm_panel_orient_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_PANEL_ORIENT_LEFT; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_PANEL_ORIENT_LEFT; + return wd->orient; +} + +/** + * Set the content of the panel. + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_panel_content_unset() function. + * + * @param obj The panel object + * @param content The panel content + * + * @ingroup Panel + */ +EAPI void +elm_panel_content_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->content == content) return; + if (wd->content) + evas_object_box_remove_all(wd->bx, EINA_TRUE); + wd->content = content; + if (content) + { + evas_object_box_append(wd->bx, wd->content); + evas_object_show(wd->content); + } + _sizing_eval(obj); +} + +/** + * Get the content of the panel. + * + * Return the content object which is set for this widget. + * + * @param obj The panel object + * @return The content that is being used + * + * @ingroup Panel + */ +EAPI Evas_Object * +elm_panel_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->content; +} + +/** + * Unset the content of the panel. + * + * Unparent and return the content object which was set for this widget. + * + * @param obj The panel object + * @return The content that was being used + * + * @ingroup Panel + */ +EAPI Evas_Object * +elm_panel_content_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *content; + if (!wd) return NULL; + if (!wd->content) return NULL; + content = wd->content; + evas_object_box_remove_all(wd->bx, EINA_FALSE); + wd->content = NULL; + return content; +} + +/** + * Set the state of the panel. + * + * @param obj The panel object + * @param hidden If true, the panel will run the edje animation to contract + * + * @ingroup Panel + */ +EAPI void +elm_panel_hidden_set(Evas_Object *obj, Eina_Bool hidden) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->hidden == hidden) return; + _toggle_panel(obj, NULL, "elm,action,panel,toggle", "*"); +} + +/** + * Get the state of the panel. + * + * @param obj The panel object + * @param hidden If true, the panel is in the "hide" state + * + * @ingroup Panel + */ +EAPI Eina_Bool +elm_panel_hidden_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->hidden; +} + +/** + * Toggle the state of the panel from code + * + * @param obj The panel object + * + * @ingroup Panel + */ +EAPI void +elm_panel_toggle(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->hidden = !(wd->hidden); + _toggle_panel(obj, NULL, "elm,action,panel,toggle", "*"); +} diff --git a/src/lib/elm_panes.c b/src/lib/elm_panes.c new file mode 100644 index 0000000..be82d21 --- /dev/null +++ b/src/lib/elm_panes.c @@ -0,0 +1,429 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Panes panes + * + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *panes; + + struct + { + Evas_Object *left; + Evas_Object *right; + } contents; + + struct + { + int x_diff; + int y_diff; + Eina_Bool move; + } move; + + Eina_Bool clicked_double; + Eina_Bool horizontal; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const char *style = elm_widget_style_get(obj); + double size; + + if (!wd) return; + size = elm_panes_content_left_size_get(obj); + + if (wd->horizontal) + _elm_theme_object_set(obj, wd->panes, "panes", "horizontal", style); + else + _elm_theme_object_set(obj, wd->panes, "panes", "vertical", style); + + if (wd->contents.left) + edje_object_part_swallow(wd->panes, "elm.swallow.left", wd->contents.left); + if (wd->contents.right) + edje_object_part_swallow(wd->panes, "elm.swallow.right", wd->contents.right); + + edje_object_scale_set(wd->panes, elm_widget_scale_get(obj) * + _elm_config->scale); + _sizing_eval(obj); + elm_panes_content_left_size_set(obj, size); +} + +static Eina_Bool +_elm_panes_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return EINA_FALSE; + + double w, h; + edje_object_part_drag_value_get(wd->panes, "elm.bar", &w, &h); + if (((wd->horizontal) && ( h == 0.0 )) || ((!wd->horizontal) && ( w == 0.0 ))) + return elm_widget_focus_next_get(wd->contents.right, dir, next); + + Evas_Object *chain[2]; + + /* Direction */ + if (dir == ELM_FOCUS_PREVIOUS) + { + chain[0] = wd->contents.right; + chain[1] = wd->contents.left; + } + else if (dir == ELM_FOCUS_NEXT) + { + chain[0] = wd->contents.left; + chain[1] = wd->contents.right; + } + else + return EINA_FALSE; + + unsigned char i = elm_widget_focus_get(chain[1]); + + if (elm_widget_focus_next_get(chain[i], dir, next)) + return EINA_TRUE; + + i = !i; + + Evas_Object *to_focus; + if (elm_widget_focus_next_get(chain[i], dir, &to_focus)) + { + *next = to_focus; + return !!i; + } + + return EINA_FALSE; +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + + if (!wd) return; + if (sub == wd->contents.left) + { + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->contents.left = NULL; + _sizing_eval(obj); + } + else if (sub == wd->contents.right) + { + evas_object_event_callback_del_full(sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->contents.right= NULL; + _sizing_eval(obj); + } +} + +static void +_clicked(void *data, Evas_Object *obj __UNUSED__ , const char *emission __UNUSED__, const char *source __UNUSED__) +{ + evas_object_smart_callback_call(data, "clicked", NULL); +} + +static void +_clicked_double(void *data, Evas_Object *obj __UNUSED__ , const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + + wd->clicked_double = EINA_TRUE; +} + +static void +_press(void *data, Evas_Object *obj __UNUSED__ , const char *emission __UNUSED__, const char *source __UNUSED__) +{ + evas_object_smart_callback_call(data, "press", NULL); +} + +static void +_unpress(void *data, Evas_Object *obj __UNUSED__ , const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + evas_object_smart_callback_call(data, "unpress", NULL); + + if (wd->clicked_double) + { + evas_object_smart_callback_call(data, "clicked,double", NULL); + wd->clicked_double = EINA_FALSE; + } +} + +/** + * Add a new panes to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Panel + */ +EAPI Evas_Object * +elm_panes_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "panes"); + elm_widget_type_set(obj, "panes"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_focus_next_hook_set(obj, _elm_panes_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->panes = edje_object_add(e); + _elm_theme_object_set(obj, wd->panes, "panes", "vertical", "default"); + elm_widget_resize_object_set(obj, wd->panes); + evas_object_show(wd->panes); + + elm_panes_content_left_size_set(obj, 0.5); + + edje_object_signal_callback_add(wd->panes, "elm,action,click", "", + _clicked, obj); + edje_object_signal_callback_add(wd->panes, "elm,action,click,double", "", + _clicked_double, obj); + edje_object_signal_callback_add(wd->panes, "elm,action,press", "", + _press, obj); + edje_object_signal_callback_add(wd->panes, "elm,action,unpress", "", + _unpress, obj); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + evas_object_event_callback_add(obj, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + + _sizing_eval(obj); + return obj; +} + + +/** + * Set the left content of the panes widget. + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_panes_content_left_unset() function. + * + * @param obj The panes object + * @param content The new left content object + * + * @ingroup Panes + */ +EAPI void +elm_panes_content_left_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (wd->contents.left) + { + evas_object_del(wd->contents.left); + wd->contents.left = NULL; + } + if (content) + { + wd->contents.left = content; + elm_widget_sub_object_add(obj, content); + edje_object_part_swallow(wd->panes, "elm.swallow.left", content); + } +} + +/** + * Set the right content of the panes widget. + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_panes_content_right_unset() function. + * + * @param obj The panes object + * @param content The new right content object + * + * @ingroup Panes + */ +EAPI void +elm_panes_content_right_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (wd->contents.right) + { + evas_object_del(wd->contents.right); + wd->contents.right = NULL; + } + if (content) + { + wd->contents.right = content; + elm_widget_sub_object_add(obj, content); + edje_object_part_swallow(wd->panes, "elm.swallow.right", content); + } +} + +/** + * Get the left content used for the panes + * + * Return the left content object which is set for this widget. + * + * @param obj The panes object + * @return The left content object that is being used + * + * @ingroup Panes + */ +EAPI Evas_Object * +elm_panes_content_left_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + return wd->contents.left; +} + +/** + * Get the right content used for the panes + * + * Return the right content object which is set for this widget. + * + * @param obj The panes object + * @return The right content object that is being used + * + * @ingroup Panes + */ +EAPI Evas_Object * +elm_panes_content_right_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + return wd->contents.right; +} + +/** + * Unset the left content used for the panes + * + * Unparent and return the left content object which was set for this widget. + * + * @param obj The panes object + * @return The left content object that was being used + * + * @ingroup Panes + */ +EAPI Evas_Object * +elm_panes_content_left_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->contents.left) return NULL; + Evas_Object *content = wd->contents.left; + elm_widget_sub_object_del(obj, content); + edje_object_part_unswallow(wd->panes, content); + wd->contents.left = NULL; + return content; +} + +/** + * Unset the right content used for the panes + * + * Unparent and return the right content object which was set for this widget. + * + * @param obj The panes object + * @return The right content object that was being used + * + * @ingroup Panes + */ +EAPI Evas_Object * +elm_panes_content_right_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->contents.right) return NULL; + Evas_Object *content = wd->contents.right; + elm_widget_sub_object_del(obj, content); + edje_object_part_unswallow(wd->panes, content); + wd->contents.right = NULL; + return content; +} + +EAPI double +elm_panes_content_left_size_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + double w, h; + + edje_object_part_drag_value_get(wd->panes, "elm.bar", &w, &h); + if (wd->horizontal) return h; + else return w; +} + +EAPI void +elm_panes_content_left_size_set(Evas_Object *obj, double size) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (size < 0.0) size = 0.0; + else if (size > 1.0) size = 1.0; + if (wd->horizontal) + edje_object_part_drag_value_set(wd->panes, "elm.bar", 0.0, size); + else + edje_object_part_drag_value_set(wd->panes, "elm.bar", size, 0.0); +} + +EAPI void +elm_panes_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + wd->horizontal = horizontal; + _theme_hook(obj); + elm_panes_content_left_size_set(obj, 0.5); +} + +EAPI Eina_Bool +elm_panes_horizontal_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + return wd->horizontal; +} diff --git a/src/lib/elm_photo.c b/src/lib/elm_photo.c new file mode 100644 index 0000000..c69ed79 --- /dev/null +++ b/src/lib/elm_photo.c @@ -0,0 +1,342 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Photo Photo + * + * For displaying the photo of a person (contact). Simple yet + * with a very specific purpose. + * + * Signals that you can add callbacks for are: + * + * - clicked: This is called when a user has clicked the photo + * - drop: Something was dropped on the widget + * - drag,start: Someone started dragging the image out of the object + * - drag,end: Dragged item was dropped (somewhere) + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *frm; + Evas_Object *img; + int size; + Eina_Bool fill; + Ecore_Timer *longtimer; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _mouse_up(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _mouse_move(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->frm, "photo", "base", + elm_widget_style_get(obj)); + edje_object_part_swallow(wd->frm, "elm.swallow.content", wd->img); + edje_object_scale_set(wd->frm, elm_widget_scale_get(obj) * + _elm_config->scale); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + + if (!wd) return; + if (wd->size > 0) + { + double scale = 0.0; + + scale = (wd->size * elm_widget_scale_get(obj) * _elm_config->scale); + evas_object_size_hint_min_set(wd->img, scale, scale); + edje_object_part_swallow(wd->frm, "elm.swallow.content", wd->img); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->frm, &minw, &minh, minw, minh); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + maxw = minw; + maxh = minh; + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); + } +} + +static void +_icon_move_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Coord w, h; + Widget_Data *wd = elm_widget_data_get(data); + + if (!wd) return; + if (wd->fill) + { + Edje_Message_Int_Set *msg; + Evas_Object *icon = _els_smart_icon_object_get(wd->img); + + evas_object_geometry_get(icon, NULL, NULL, &w, &h); + msg = alloca(sizeof(Edje_Message_Int_Set) + (sizeof(int))); + msg->count=2; + msg->val[0] = (int)w; + msg->val[1] = (int)h; + + edje_object_message_send(wd->frm, EDJE_MESSAGE_INT_SET, 0, msg); + } +} + + +static void +_drag_done_cb(void *unused __UNUSED__, Evas_Object *obj) +{ + elm_object_scroll_freeze_pop(obj); + evas_object_smart_callback_call(obj, "drag,end", NULL); +} + +static Eina_Bool +_longpress(void *objv) +{ + Widget_Data *wd = elm_widget_data_get(objv); + Evas_Object *tmp; + const char *file; + char *buf; + + DBG("Long press: start drag!"); + wd->longtimer = NULL; /* clear: must return NULL now */ + evas_object_event_callback_del(objv, EVAS_CALLBACK_MOUSE_MOVE, _mouse_move); + + tmp = _els_smart_icon_object_get(wd->img); + file = NULL; + evas_object_image_file_get(tmp,&file,NULL); + if (file) + { + /* FIXME: Deal with relative paths */ + buf = malloc(strlen(file) + strlen("file://") + 1); + sprintf(buf, "%s%s","file://",file); + elm_drag_start(objv, ELM_SEL_FORMAT_IMAGE, buf, _drag_done_cb, NULL); + free(buf); + } + elm_object_scroll_freeze_push(objv); + + evas_object_smart_callback_call(objv, "drag,start", NULL); + + return 0; /* Don't call again */ +} + +static void +_mouse_move(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Move *move = event; + + /* Sanity */ + if (!wd->longtimer) + { + evas_object_event_callback_del(obj, EVAS_CALLBACK_MOUSE_MOVE, _mouse_move); + return; + } + + /* if the event is held, stop waiting */ + if (move->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + { + /* Moved too far: No longpress for you! */ + ecore_timer_del(wd->longtimer); + wd->longtimer = NULL; + evas_object_event_callback_del(obj, EVAS_CALLBACK_MOUSE_MOVE, + _mouse_move); + } +} + +static void +_mouse_down(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + + if (wd->longtimer) ecore_timer_del(wd->longtimer); + + /* FIXME: Hard coded timeout */ + wd->longtimer = ecore_timer_add(0.7, _longpress, data); + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOUSE_MOVE, + _mouse_move, data); +} + +static void +_mouse_up(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + + if ((wd) && (wd->longtimer)) + { + ecore_timer_del(wd->longtimer); + wd->longtimer = NULL; + } + + evas_object_smart_callback_call(data, "clicked", NULL); +} + + +/** + * Add a new photo to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Photo + */ +EAPI Evas_Object * +elm_photo_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + Evas_Object *icon; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "photo"); + elm_widget_type_set(obj, "photo"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->frm = edje_object_add(e); + _elm_theme_object_set(obj, wd->frm, "photo", "base", "default"); + elm_widget_resize_object_set(obj, wd->frm); + + wd->img = _els_smart_icon_add(e); + _els_smart_icon_scale_up_set(wd->img, 1); + _els_smart_icon_scale_down_set(wd->img, 1); + _els_smart_icon_smooth_scale_set(wd->img, 1); + _els_smart_icon_fill_inside_set(wd->img, 0); + _els_smart_icon_scale_size_set(wd->img, 0); + wd->fill = EINA_FALSE; + _els_smart_icon_scale_set(wd->img, + elm_widget_scale_get(obj) * _elm_config->scale); + evas_object_event_callback_add(wd->img, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, obj); + evas_object_event_callback_add(wd->img, EVAS_CALLBACK_MOUSE_DOWN, + _mouse_down, obj); + evas_object_repeat_events_set(wd->img, 1); + edje_object_part_swallow(wd->frm, "elm.swallow.content", wd->img); + evas_object_show(wd->img); + elm_widget_sub_object_add(obj, wd->img); + + wd->longtimer = NULL; + + icon = _els_smart_icon_object_get(wd->img); + evas_object_event_callback_add(icon, EVAS_CALLBACK_MOVE, + _icon_move_resize, obj); + evas_object_event_callback_add(icon, EVAS_CALLBACK_RESIZE, + _icon_move_resize, obj); + _sizing_eval(obj); + return obj; +} + +/** + * Set the file that will be used as photo + * + * @param obj The photo object + * @param file The path to file that will be used as photo + * + * @return (1 = success, 0 = error) + * + * @ingroup Photo + */ +EAPI Eina_Bool +elm_photo_file_set(Evas_Object *obj, const char *file) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + if (!_els_smart_icon_file_key_set(wd->img, file, NULL)) + return EINA_FALSE; + + _sizing_eval(obj); + return EINA_TRUE; +} + +/** + * Set the size that will be used on the photo + * + * @param obj The photo object + * @param size The size that the photo will be + * + * @ingroup Photo + */ +EAPI void +elm_photo_size_set(Evas_Object *obj, int size) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->size = (size > 0) ? size : 0; + + _els_smart_icon_scale_size_set(wd->img, wd->size); + + _sizing_eval(obj); +} + +/** + * Set if the photo should be completely visible or not. + * + * @param obj The photo object + * @param fill if true the photo will be completely visible + * + * @ingroup Photo + */ +EAPI void +elm_photo_fill_inside_set(Evas_Object *obj, Eina_Bool fill) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + _els_smart_icon_fill_inside_set(wd->img, fill); + wd->fill = fill; + _sizing_eval(obj); +} + +/** + * Set editability of the photo. + * + * An editable photo can be dragged to or from, and can be cut or pasted too. + * Note that pasting an image or dropping an item on the image will delete the + * existing content. + * + * @param obj The photo object. + * @param set To set of clear editablity. + */ +EAPI void +elm_photo_editable_set(Evas_Object *obj, Eina_Bool set) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return;; + _els_smart_icon_edit_set(wd->img, set, obj); +} + +/* vim:set ts=8 sw=3 sts=3 expandtab cino=>5n-2f0^-2{2(0W1st0 :*/ diff --git a/src/lib/elm_photocam.c b/src/lib/elm_photocam.c new file mode 100644 index 0000000..78042ad --- /dev/null +++ b/src/lib/elm_photocam.c @@ -0,0 +1,1780 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Photocam Photocam + * + * This is a widget specifically for displaying high-resolution digital + * camera photos giving speedy feedback (fast load), low memory footprint + * and zooming and panning as well as fitting logic. It is entirely focused + * on jpeg images, and takes advantage of properties of the jpeg format (via + * evas loader features in the jpeg loader). + * + * Signals that you can add callbacks for are: + * + * clicked - This is called when a user has clicked the photo without dragging + * around. + * + * press - This is called when a user has pressed down on the photo. + * + * longpressed - This is called when a user has pressed down on the photo for + * a long time without dragging around. + * + * clicked,double - This is called when a user has double-clicked the photo. + * + * load - Photo load begins. + * + * loaded - This is called when the image file load is complete for the first + * view (low resolution blurry version). + * + * load,details - Photo detailed data load begins. + * + * loaded,details - This is called when the image file load is complete for the + * detailed image data (full resolution needed). + * + * zoom,start - Zoom animation started. + * + * zoom,stop - Zoom animation stopped. + * + * zoom,change - Zoom changed when using an auto zoom mode. + * + * scroll - the content has been scrolled (moved) + * + * scroll,anim,start - scrolling animation has started + * + * scroll,anim,stop - scrolling animation has stopped + * + * scroll,drag,start - dragging the contents around has started + * + * scroll,drag,stop - dragging the contents around has stopped + * + * --- + * + * TODO (maybe - optional future stuff): + * + * 1. wrap photo in theme edje so u can have styling around photo (like white + * photo bordering). + * 2. exif handling + * 3. rotation flags in exif handling (nasty! should have rot in evas) + * + */ +typedef struct _Widget_Data Widget_Data; +typedef struct _Pan Pan; +typedef struct _Grid Grid; +typedef struct _Grid_Item Grid_Item; + +struct _Grid_Item +{ + Widget_Data *wd; + Evas_Object *img; + struct + { + int x, y, w, h; + } src, out; + Eina_Bool want : 1; + Eina_Bool have : 1; +}; + +struct _Grid +{ + int tsize; // size of tile (tsize x tsize pixels) + int zoom; // zoom level tiles want for optimal display (1, 2, 4, 8) + int iw, ih; // size of image in pixels + int w, h; // size of grid image in pixels (represented by grid) + int gw, gh; // size of grid in tiles + Grid_Item *grid; // the grid (gw * gh items) + Eina_Bool dead : 1; // old grid. will die as soon as anim is over +}; + +struct _Widget_Data +{ + Evas_Object *obj; + Evas_Object *scr; + Evas_Object *pan_smart; + Pan *pan; + Evas_Coord pan_x, pan_y, minw, minh; + + double zoom; + Elm_Photocam_Zoom_Mode mode; + const char *file; + + Ecore_Job *calc_job; + Ecore_Timer *scr_timer; + Ecore_Timer *long_timer; + Ecore_Animator *zoom_animator; + double t_start, t_end; + struct + { + int imw, imh; + int w, h; + int ow, oh, nw, nh; + struct + { + double x, y; + } spos; + } size; + struct + { + Eina_Bool show : 1; + Evas_Coord x, y ,w ,h; + } show; + int tsize; + Evas_Object *img; // low res version of image (scale down == 8) + int nosmooth; + int preload_num; + Eina_List *grids; + Eina_Bool main_load_pending : 1; + Eina_Bool resized : 1; + Eina_Bool longpressed : 1; + Eina_Bool on_hold : 1; + Eina_Bool paused : 1; +}; + +struct _Pan +{ + Evas_Object_Smart_Clipped_Data __clipped_data; + Widget_Data *wd; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _on_focus_hook(void *data, Evas_Object *obj); +//static void _show_region_hook(void *data, Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _calc_job(void *data); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, + Evas_Callback_Type type, void *event_info); +static void grid_place(Evas_Object *obj, Grid *g, Evas_Coord px, Evas_Coord py, Evas_Coord ox, Evas_Coord oy, Evas_Coord ow, Evas_Coord oh); +static void grid_clear(Evas_Object *obj, Grid *g); +static Grid *grid_create(Evas_Object *obj); +static void grid_load(Evas_Object *obj, Grid *g); + +static int +nearest_pow2(int num) +{ + unsigned int n = num - 1; + n |= n >> 1; + n |= n >> 2; + n |= n >> 4; + n |= n >> 8; + n |= n >> 16; + return n + 1; +} + +static void +img_place(Evas_Object *obj, Evas_Coord px, Evas_Coord py, Evas_Coord ox, Evas_Coord oy, Evas_Coord ow, Evas_Coord oh) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord ax, ay, gw, gh; + if (!wd) return; + ax = 0; + ay = 0; + gw = wd->size.w; + gh = wd->size.h; + if (ow > gw) ax = (ow - gw) / 2; + if (oh > gh) ay = (oh - gh) / 2; + evas_object_move(wd->img, ox + 0 - px + ax, oy + 0 - py + ay); + evas_object_resize(wd->img, gw, gh); + + if (wd->show.show) + { + wd->show.show = EINA_FALSE; + elm_smart_scroller_child_region_show(wd->scr, wd->show.x, wd->show.y, wd->show.w, wd->show.h); + } +} + +static void +grid_place(Evas_Object *obj, Grid *g, Evas_Coord px, Evas_Coord py, Evas_Coord ox, Evas_Coord oy, Evas_Coord ow, Evas_Coord oh) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord ax, ay, gw, gh, tx, ty; + int x, y; + if (!wd) return; + ax = 0; + ay = 0; + gw = wd->size.w; + gh = wd->size.h; + if (ow > gw) ax = (ow - gw) / 2; + if (oh > gh) ay = (oh - gh) / 2; + for (y = 0; y < g->gh; y++) + { + for (x = 0; x < g->gw; x++) + { + int tn, xx, yy, ww, hh; + + tn = (y * g->gw) + x; + xx = g->grid[tn].out.x; + yy = g->grid[tn].out.y; + ww = g->grid[tn].out.w; + hh = g->grid[tn].out.h; + if ((gw != g->w) && (g->w > 0)) + { + tx = xx; + xx = (gw * xx) / g->w; + ww = ((gw * (tx + ww)) / g->w) - xx; + } + if ((gh != g->h) && (g->h > 0)) + { + ty = yy; + yy = (gh * yy) / g->h; + hh = ((gh * (ty + hh)) / g->h) - yy; + } + evas_object_move(g->grid[tn].img, + ox + xx - px + ax, + oy + yy - py + ay); + evas_object_resize(g->grid[tn].img, ww, hh); + } + } +} + +static void +grid_clear(Evas_Object *obj, Grid *g) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int x, y; + if (!wd) return; + if (!g->grid) return; + for (y = 0; y < g->gh; y++) + { + for (x = 0; x < g->gw; x++) + { + int tn; + + tn = (y * g->gw) + x; + evas_object_del(g->grid[tn].img); + if (g->grid[tn].want) + { + wd->preload_num--; + if (!wd->preload_num) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,state,busy,stop", "elm"); + evas_object_smart_callback_call(obj, "loaded,detail", NULL); + } + } + } + } + free(g->grid); + g->grid = NULL; + g->gw = 0; + g->gh = 0; +} + +static void +_tile_preloaded(void *data, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) +{ + Grid_Item *git = data; + + if (git->want) + { + git->want = 0; + evas_object_show(git->img); + git->have = 1; + git->wd->preload_num--; + if (!git->wd->preload_num) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(git->wd->scr), + "elm,state,busy,stop", "elm"); + evas_object_smart_callback_call(git->wd->obj, "loaded,detail", NULL); + } + } +} + +static int +grid_zoom_calc(double zoom) +{ + int z = zoom; + if (z < 1) z = 1; + return nearest_pow2(z); +} + +static Grid * +grid_create(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int x, y; + Grid *g; + + if (!wd) return NULL; + g = calloc(1, sizeof(Grid)); + + g->zoom = grid_zoom_calc(wd->zoom); + g->tsize = wd->tsize; + g->iw = wd->size.imw; + g->ih = wd->size.imh; + + g->w = g->iw / g->zoom; + g->h = g->ih / g->zoom; + if (g->zoom >= 8) return NULL; + g->gw = (g->w + g->tsize - 1) / g->tsize; + g->gh = (g->h + g->tsize - 1) / g->tsize; + g->grid = calloc(1, sizeof(Grid_Item) * g->gw * g->gh); + if (!g->grid) + { + g->gw = 0; + g->gh = 0; + return g; + } + for (y = 0; y < g->gh; y++) + { + for (x = 0; x < g->gw; x++) + { + int tn; + + tn = (y * g->gw) + x; + g->grid[tn].src.x = x * g->tsize; + if (x == (g->gw - 1)) + g->grid[tn].src.w = g->w - ((g->gw - 1) * g->tsize); + else + g->grid[tn].src.w = g->tsize; + g->grid[tn].src.y = y * g->tsize; + if (y == (g->gh - 1)) + g->grid[tn].src.h = g->h - ((g->gh - 1) * g->tsize); + else + g->grid[tn].src.h = g->tsize; + + g->grid[tn].out.x = g->grid[tn].src.x; + g->grid[tn].out.y = g->grid[tn].src.y; + g->grid[tn].out.w = g->grid[tn].src.w; + g->grid[tn].out.h = g->grid[tn].src.h; + + g->grid[tn].wd = wd; + g->grid[tn].img = + evas_object_image_add(evas_object_evas_get(obj)); + evas_object_image_scale_hint_set + (g->grid[tn].img, EVAS_IMAGE_SCALE_HINT_DYNAMIC); + evas_object_pass_events_set(g->grid[tn].img, EINA_TRUE); + evas_object_smart_member_add(g->grid[tn].img, + wd->pan_smart); + elm_widget_sub_object_add(obj, g->grid[tn].img); + evas_object_image_filled_set(g->grid[tn].img, 1); + evas_object_event_callback_add(g->grid[tn].img, + EVAS_CALLBACK_IMAGE_PRELOADED, + _tile_preloaded, + &(g->grid[tn])); + } + } + return g; +} + +static void +grid_load(Evas_Object *obj, Grid *g) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int x, y; + Evas_Coord ox, oy, ow, oh, cvx, cvy, cvw, cvh, gw, gh, tx, ty; + if (!wd) return; + evas_object_geometry_get(wd->pan_smart, &ox, &oy, &ow, &oh); + evas_output_viewport_get(evas_object_evas_get(wd->obj), &cvx, &cvy, &cvw, &cvh); + gw = wd->size.w; + gh = wd->size.h; + for (y = 0; y < g->gh; y++) + { + for (x = 0; x < g->gw; x++) + { + int tn, xx, yy, ww, hh; + Eina_Bool visible = EINA_FALSE; + + tn = (y * g->gw) + x; + xx = g->grid[tn].out.x; + yy = g->grid[tn].out.y; + ww = g->grid[tn].out.w; + hh = g->grid[tn].out.h; + if ((gw != g->w) && (g->w > 0)) + { + tx = xx; + xx = (gw * xx) / g->w; + ww = ((gw * (tx + ww)) / g->w) - xx; + } + if ((gh != g->h) && (g->h > 0)) + { + ty = yy; + yy = (gh * yy) / g->h; + hh = ((gh * (ty + hh)) / g->h) - yy; + } + if (ELM_RECTS_INTERSECT(xx - wd->pan_x + ox, + yy - wd->pan_y + oy, + ww, hh, + cvx, cvy, cvw, cvh)) + visible = 1; + if ((visible) && (!g->grid[tn].have) && (!g->grid[tn].want)) + { + g->grid[tn].want = 1; + evas_object_hide(g->grid[tn].img); + evas_object_image_file_set(g->grid[tn].img, NULL, NULL); + evas_object_image_load_scale_down_set(g->grid[tn].img, g->zoom); + evas_object_image_load_region_set(g->grid[tn].img, + g->grid[tn].src.x, + g->grid[tn].src.y, + g->grid[tn].src.w, + g->grid[tn].src.h); + evas_object_image_file_set(g->grid[tn].img, wd->file, NULL); + evas_object_image_preload(g->grid[tn].img, 0); + wd->preload_num++; + if (wd->preload_num == 1) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,state,busy,start", "elm"); + evas_object_smart_callback_call(obj, "load,detail", NULL); + } + } + else if ((g->grid[tn].want) && (!visible)) + { + wd->preload_num--; + if (!wd->preload_num) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,state,busy,stop", "elm"); + evas_object_smart_callback_call(obj, "loaded,detail", NULL); + } + g->grid[tn].want = 0; + evas_object_hide(g->grid[tn].img); + evas_object_image_preload(g->grid[tn].img, 1); + evas_object_image_file_set(g->grid[tn].img, NULL, NULL); + } + else if ((g->grid[tn].have) && (!visible)) + { + g->grid[tn].have = 0; + evas_object_hide(g->grid[tn].img); + evas_object_image_preload(g->grid[tn].img, 1); + evas_object_image_file_set(g->grid[tn].img, NULL, NULL); + } + } + } +} + +static void +grid_clearall(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Grid *g; + if (!wd) return; + EINA_LIST_FREE(wd->grids, g) + { + grid_clear(obj, g); + free(g); + } +} + +static void +_smooth_update(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + int x, y; + Eina_List *l; + Grid *g; + if (!wd) return; + EINA_LIST_FOREACH(wd->grids, l, g) + { + for (y = 0; y < g->gh; y++) + { + for (x = 0; x < g->gw; x++) + { + int tn; + + tn = (y * g->gw) + x; + evas_object_image_smooth_scale_set(g->grid[tn].img, (!wd->nosmooth)); + } + } + } + evas_object_image_smooth_scale_set(wd->img, (!wd->nosmooth)); +} + +static void +_grid_raise(Grid *g) +{ + int x, y; + + for (y = 0; y < g->gh; y++) + { + for (x = 0; x < g->gw; x++) + { + int tn; + + tn = (y * g->gw) + x; + evas_object_raise(g->grid[tn].img); + } + } +} + +static Eina_Bool +_scr_timeout(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->nosmooth--; + if (!wd->nosmooth) _smooth_update(data); + wd->scr_timer = NULL; + return ECORE_CALLBACK_CANCEL; +} + +static void +_scr(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (!wd->scr_timer) + { + wd->nosmooth++; + if (wd->nosmooth == 1) _smooth_update(data); + } + if (wd->scr_timer) ecore_timer_del(wd->scr_timer); + wd->scr_timer = ecore_timer_add(0.5, _scr_timeout, data); +} + +static void +_main_preloaded(void *data, Evas *e __UNUSED__, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *obj = data; + Widget_Data *wd = elm_widget_data_get(obj); + Grid *g; + if (!wd) return; + evas_object_show(wd->img); + wd->main_load_pending = 0; + g = grid_create(obj); + if (g) + { + wd->grids = eina_list_prepend(wd->grids, g); + grid_load(wd->obj, g); + } + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + evas_object_smart_callback_call(data, "loaded", NULL); + wd->preload_num--; + if (!wd->preload_num) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,state,busy,stop", "elm"); + evas_object_smart_callback_call(obj, "loaded,detail", NULL); + } +} + +static Eina_Bool +zoom_do(Evas_Object *obj, double t) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord xx, yy, ow, oh; + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->size.w = (wd->size.ow * (1.0 - t)) + (wd->size.nw * t); + wd->size.h = (wd->size.oh * (1.0 - t)) + (wd->size.nh * t); + elm_smart_scroller_child_viewport_size_get(wd->scr, &ow, &oh); + xx = (wd->size.spos.x * wd->size.w) - (ow / 2); + yy = (wd->size.spos.y * wd->size.h) - (oh / 2); + if (xx < 0) xx = 0; + else if (xx > (wd->size.w - ow)) xx = wd->size.w - ow; + if (yy < 0) yy = 0; + else if (yy > (wd->size.h - oh)) yy = wd->size.h - oh; + + wd->show.show = EINA_TRUE; + wd->show.x = xx; + wd->show.y = yy; + wd->show.w = ow; + wd->show.h = oh; + + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + if (t >= 1.0) + { + Eina_List *l, *l_next; + Grid *g; + + EINA_LIST_FOREACH_SAFE(wd->grids, l, l_next, g) + { + if (g->dead) + { + wd->grids = eina_list_remove_list(wd->grids, l); + grid_clear(obj, g); + free(g); + } + } + return ECORE_CALLBACK_CANCEL; + } + return ECORE_CALLBACK_RENEW; +} + + +static Eina_Bool +_zoom_anim(void *data) +{ + Evas_Object *obj = data; + Widget_Data *wd = elm_widget_data_get(obj); + double t; + Eina_Bool go; + if (!wd) return ECORE_CALLBACK_CANCEL; + t = ecore_loop_time_get(); + if (t >= wd->t_end) + t = 1.0; + else if (wd->t_end > wd->t_start) + t = (t - wd->t_start) / (wd->t_end - wd->t_start); + else + t = 1.0; + t = 1.0 - t; + t = 1.0 - (t * t); + go = zoom_do(obj, t); + if (!go) + { + wd->nosmooth--; + if (!wd->nosmooth) _smooth_update(data); + wd->zoom_animator = NULL; + evas_object_smart_callback_call(obj, "zoom,stop", NULL); + } + return go; +} + +static void +_mouse_move(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); +// Evas_Event_Mouse_Move *ev = event_info; + if (!wd) return; +} + +static Eina_Bool +_long_press(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->long_timer = NULL; + wd->longpressed = EINA_TRUE; + evas_object_smart_callback_call(data, "longpressed", NULL); + return ECORE_CALLBACK_CANCEL; +} + +static void +_mouse_down(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Down *ev = event_info; + if (!wd) return; + if (ev->button != 1) return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) wd->on_hold = EINA_TRUE; + else wd->on_hold = EINA_FALSE; + if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK) + evas_object_smart_callback_call(data, "clicked,double", NULL); + else + evas_object_smart_callback_call(data, "press", NULL); + wd->longpressed = EINA_FALSE; + if (wd->long_timer) ecore_timer_del(wd->long_timer); + wd->long_timer = ecore_timer_add(_elm_config->longpress_timeout, _long_press, data); +} + +static void +_mouse_up(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Up *ev = event_info; + if (!wd) return; + if (ev->button != 1) return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) wd->on_hold = EINA_TRUE; + else wd->on_hold = EINA_FALSE; + if (wd->long_timer) + { + ecore_timer_del(wd->long_timer); + wd->long_timer = NULL; + } + if (!wd->on_hold) + evas_object_smart_callback_call(data, "clicked", NULL); + wd->on_hold = EINA_FALSE; +} + +static Evas_Smart_Class _pan_sc = EVAS_SMART_CLASS_INIT_NULL; + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Grid *g; + if (!wd) return; + EINA_LIST_FREE(wd->grids, g) + { + if (g->grid) free(g->grid); + free(g); + } + evas_object_del(wd->pan_smart); + wd->pan_smart = NULL; + if (wd->file) eina_stringshare_del(wd->file); + if (wd->calc_job) ecore_job_del(wd->calc_job); + if (wd->scr_timer) ecore_timer_del(wd->scr_timer); + if (wd->zoom_animator) ecore_animator_del(wd->zoom_animator); + if (wd->long_timer) ecore_timer_del(wd->long_timer); + free(wd); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->obj, "elm,action,focus", "elm"); + evas_object_focus_set(wd->obj, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->obj, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->obj, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_object_theme_set(obj, wd->scr, "photocam", "base", elm_widget_style_get(obj)); +// edje_object_scale_set(wd->scr, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +/* +static void +_show_region_hook(void *data, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord x, y, w, h; + if (!wd) return; + elm_widget_show_region_get(obj, &x, &y, &w, &h); + elm_smart_scroller_child_region_show(wd->scr, x, y, w, h); +} +*/ + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; +// evas_object_size_hint_min_get(wd->scr, &minw, &minh); + evas_object_size_hint_max_get(wd->scr, &maxw, &maxh); +// minw = -1; +// minh = -1; +// if (wd->mode != ELM_LIST_LIMIT) minw = -1; + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_calc_job(void *data) +{ + Widget_Data *wd = data; + Evas_Coord minw, minh; + if (!wd) return; + minw = wd->size.w; + minh = wd->size.h; + if (wd->resized) + { + wd->resized = 0; + if (wd->mode != ELM_PHOTOCAM_ZOOM_MODE_MANUAL) + { + double tz = wd->zoom; + wd->zoom = 0.0; + elm_photocam_zoom_set(wd->obj, tz); + } + } + if ((minw != wd->minw) || (minh != wd->minh)) + { + wd->minw = minw; + wd->minh = minh; + evas_object_smart_callback_call(wd->pan_smart, "changed", NULL); + _sizing_eval(wd->obj); + } + wd->calc_job = NULL; + evas_object_smart_changed(wd->pan_smart); +} + +static void +_pan_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if ((x == sd->wd->pan_x) && (y == sd->wd->pan_y)) return; + sd->wd->pan_x = x; + sd->wd->pan_y = y; + evas_object_smart_changed(obj); +} + +static void +_pan_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (x) *x = sd->wd->pan_x; + if (y) *y = sd->wd->pan_y; +} + +static void +_pan_max_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ow, oh; + if (!sd) return; + evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); + ow = sd->wd->minw - ow; + if (ow < 0) ow = 0; + oh = sd->wd->minh - oh; + if (oh < 0) oh = 0; + if (x) *x = ow; + if (y) *y = oh; +} + +static void +_pan_min_get(Evas_Object *obj __UNUSED__, Evas_Coord *x, Evas_Coord *y) +{ + if (x) *x = 0; + if (y) *y = 0; +} + +static void +_pan_child_size_get(Evas_Object *obj, Evas_Coord *w, Evas_Coord *h) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (w) *w = sd->wd->minw; + if (h) *h = sd->wd->minh; +} + +static void +_pan_add(Evas_Object *obj) +{ + Pan *sd; + Evas_Object_Smart_Clipped_Data *cd; + _pan_sc.add(obj); + cd = evas_object_smart_data_get(obj); + if (!cd) return; + sd = calloc(1, sizeof(Pan)); + if (!sd) return; + sd->__clipped_data = *cd; + free(cd); + evas_object_smart_data_set(obj, sd); +} + +static void +_pan_del(Evas_Object *obj) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + _pan_sc.del(obj); +} + +static void +_pan_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ow, oh; + if (!sd) return; + evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); + if ((ow == w) && (oh == h)) return; + sd->wd->resized = 1; + if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job); + sd->wd->calc_job = ecore_job_add(_calc_job, sd->wd); +} + +static void +_pan_calculate(Evas_Object *obj) +{ + Pan *sd = evas_object_smart_data_get(obj); + Evas_Coord ox, oy, ow, oh; + Eina_List *l; + Grid *g; + if (!sd) return; + evas_object_geometry_get(obj, &ox, &oy, &ow, &oh); + img_place(sd->wd->obj, sd->wd->pan_x, sd->wd->pan_y, ox, oy, ow, oh); + EINA_LIST_FOREACH(sd->wd->grids, l, g) + { + grid_load(sd->wd->obj, g); + grid_place(sd->wd->obj, g, sd->wd->pan_x, sd->wd->pan_y, ox, oy, ow, oh); + } +} + +static void +_pan_move(Evas_Object *obj, Evas_Coord x __UNUSED__, Evas_Coord y __UNUSED__) +{ + Pan *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job); + sd->wd->calc_job = ecore_job_add(_calc_job, sd->wd); +} + +static void +_hold_on(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_hold_set(wd->scr, 1); +} + +static void +_hold_off(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_hold_set(wd->scr, 0); +} + +static void +_freeze_on(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_freeze_set(wd->scr, 1); +} + +static void +_freeze_off(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_freeze_set(wd->scr, 0); +} + +static void +_scr_anim_start(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll,anim,start", NULL); +} + +static void +_scr_anim_stop(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll,anim,stop", NULL); +} + +static void +_scr_drag_start(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll,drag,start", NULL); +} + +static void +_scr_drag_stop(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll,drag,stop", NULL); +} + +static void +_scr_scroll(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, "scroll", NULL); +} + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, + Evas_Callback_Type type, void *event_info) +{ + double zoom; + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + + Evas_Coord x = 0; + Evas_Coord y = 0; + Evas_Coord step_x = 0; + Evas_Coord step_y = 0; + Evas_Coord v_w = 0; + Evas_Coord v_h = 0; + Evas_Coord page_x = 0; + Evas_Coord page_y = 0; + + elm_smart_scroller_child_pos_get(wd->scr, &x, &y); + elm_smart_scroller_step_size_get(wd->scr, &step_x, &step_y); + elm_smart_scroller_page_size_get(wd->scr, &page_x, &page_y); + elm_smart_scroller_child_viewport_size_get(wd->scr, &v_w, &v_h); + + if ((!strcmp(ev->keyname, "Left")) || + (!strcmp(ev->keyname, "KP_Left"))) + { + x -= step_x; + } + else if ((!strcmp(ev->keyname, "Right")) || + (!strcmp(ev->keyname, "KP_Right"))) + { + x += step_x; + } + else if ((!strcmp(ev->keyname, "Up")) || + (!strcmp(ev->keyname, "KP_Up"))) + { + y -= step_y; + } + else if ((!strcmp(ev->keyname, "Down")) || + (!strcmp(ev->keyname, "KP_Down"))) + { + y += step_y; + } + else if ((!strcmp(ev->keyname, "Prior")) || + (!strcmp(ev->keyname, "KP_Prior"))) + { + if (page_y < 0) + y -= -(page_y * v_h) / 100; + else + y -= page_y; + } + else if ((!strcmp(ev->keyname, "Next")) || + (!strcmp(ev->keyname, "KP_Next"))) + { + if (page_y < 0) + y += -(page_y * v_h) / 100; + else + y += page_y; + } + else if ((!strcmp(ev->keyname, "KP_Add"))) + { + zoom = elm_photocam_zoom_get(obj); + zoom -= 0.5; + elm_photocam_zoom_mode_set(obj, ELM_PHOTOCAM_ZOOM_MODE_MANUAL); + elm_photocam_zoom_set(obj, zoom); + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "KP_Subtract"))) + { + zoom = elm_photocam_zoom_get(obj); + zoom += 0.5; + elm_photocam_zoom_mode_set(obj, ELM_PHOTOCAM_ZOOM_MODE_MANUAL); + elm_photocam_zoom_set(obj, zoom); + return EINA_TRUE; + } + else return EINA_FALSE; + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + elm_smart_scroller_child_pos_set(wd->scr, x, y); + + return EINA_TRUE; +} + +/** + * Add a new Photocam object + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Photocam + */ +EAPI Evas_Object * +elm_photocam_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + Evas_Coord minw, minh; + static Evas_Smart *smart = NULL; + Eina_Bool bounce = _elm_config->thumbscroll_bounce_enable; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "photocam"); + elm_widget_type_set(obj, "photocam"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->scr = elm_smart_scroller_add(e); + elm_smart_scroller_widget_set(wd->scr, obj); + elm_smart_scroller_object_theme_set(obj, wd->scr, "photocam", "base", "default"); + evas_object_smart_callback_add(wd->scr, "scroll", _scr, obj); + evas_object_smart_callback_add(wd->scr, "drag", _scr, obj); + elm_widget_resize_object_set(obj, wd->scr); + + evas_object_smart_callback_add(wd->scr, "animate,start", _scr_anim_start, obj); + evas_object_smart_callback_add(wd->scr, "animate,stop", _scr_anim_stop, obj); + evas_object_smart_callback_add(wd->scr, "drag,start", _scr_drag_start, obj); + evas_object_smart_callback_add(wd->scr, "drag,stop", _scr_drag_stop, obj); + evas_object_smart_callback_add(wd->scr, "scroll", _scr_scroll, obj); + + elm_smart_scroller_bounce_allow_set(wd->scr, bounce, bounce); + + wd->obj = obj; + + evas_object_smart_callback_add(obj, "scroll-hold-on", _hold_on, obj); + evas_object_smart_callback_add(obj, "scroll-hold-off", _hold_off, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-on", _freeze_on, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-off", _freeze_off, obj); + + if (!smart) + { + static Evas_Smart_Class sc; + + evas_object_smart_clipped_smart_set(&_pan_sc); + sc = _pan_sc; + sc.name = "elm_photocam_pan"; + sc.version = EVAS_SMART_CLASS_VERSION; + sc.add = _pan_add; + sc.del = _pan_del; + sc.resize = _pan_resize; + sc.move = _pan_move; + sc.calculate = _pan_calculate; + smart = evas_smart_class_new(&sc); + } + if (smart) + { + wd->pan_smart = evas_object_smart_add(e, smart); + wd->pan = evas_object_smart_data_get(wd->pan_smart); + wd->pan->wd = wd; + } + + elm_smart_scroller_extern_pan_set(wd->scr, wd->pan_smart, + _pan_set, _pan_get, _pan_max_get, + _pan_min_get, _pan_child_size_get); + + wd->zoom = 1; + wd->mode = ELM_PHOTOCAM_ZOOM_MODE_MANUAL; + + wd->tsize = 512; + + wd->img = evas_object_image_add(e); + evas_object_image_scale_hint_set(wd->img, EVAS_IMAGE_SCALE_HINT_DYNAMIC); + evas_object_event_callback_add(wd->img, EVAS_CALLBACK_MOUSE_DOWN, + _mouse_down, obj); + evas_object_event_callback_add(wd->img, EVAS_CALLBACK_MOUSE_UP, + _mouse_up, obj); + evas_object_event_callback_add(wd->img, EVAS_CALLBACK_MOUSE_MOVE, + _mouse_move, obj); + evas_object_image_scale_hint_set(wd->img, EVAS_IMAGE_SCALE_HINT_STATIC); + evas_object_smart_member_add(wd->img, wd->pan_smart); + elm_widget_sub_object_add(obj, wd->img); + evas_object_image_filled_set(wd->img, 1); + evas_object_event_callback_add(wd->img, EVAS_CALLBACK_IMAGE_PRELOADED, + _main_preloaded, obj); + + edje_object_size_min_calc(elm_smart_scroller_edje_object_get(wd->scr), + &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + + _sizing_eval(obj); + return obj; +} + +/** + * Set the photo file to be shown + * + * This sets (and shows) the specified file (with a relative or absolute path) + * and will return a load error (same error that + * evas_object_image_load_error_get() will return). The image will change and + * adjust its size at this point and begin a background load process for this + * photo that at some time in the future will be displayed at the full quality + * needed. + * + * @param obj The photocam object + * @param file The photo file + * @return The return error (see EVAS_LOAD_ERROR_NONE, EVAS_LOAD_ERROR_GENERIC etc.) + * + * @ingroup Photocam + */ +EAPI Evas_Load_Error +elm_photocam_file_set(Evas_Object *obj, const char *file) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EVAS_LOAD_ERROR_NONE; + Widget_Data *wd = elm_widget_data_get(obj); + int w, h; + if (!wd) return EVAS_LOAD_ERROR_GENERIC; + if (!eina_stringshare_replace(&wd->file, file)) return EVAS_LOAD_ERROR_NONE; + evas_object_hide(wd->img); + evas_object_image_smooth_scale_set(wd->img, (wd->nosmooth == 0)); + evas_object_image_file_set(wd->img, NULL, NULL); + evas_object_image_load_scale_down_set(wd->img, 0); + evas_object_image_file_set(wd->img, wd->file, NULL); + evas_object_image_size_get(wd->img, &w, &h); + wd->size.imw = w; + wd->size.imh = h; + wd->size.w = wd->size.imw / wd->zoom; + wd->size.h = wd->size.imh / wd->zoom; + if (wd->zoom_animator) + { + wd->nosmooth--; + if (wd->nosmooth == 0) _smooth_update(obj); + ecore_animator_del(wd->zoom_animator); + wd->zoom_animator = NULL; + } + evas_object_image_file_set(wd->img, NULL, NULL); + evas_object_image_load_scale_down_set(wd->img, 8); + evas_object_image_file_set(wd->img, wd->file, NULL); + evas_object_image_preload(wd->img, 0); + wd->main_load_pending = 1; + grid_clearall(obj); + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + evas_object_smart_callback_call(obj, "load", NULL); + wd->preload_num++; + if (wd->preload_num == 1) + { + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + "elm,state,busy,start", "elm"); + evas_object_smart_callback_call(obj, "load,detail", NULL); + } + { + double tz = wd->zoom; + wd->zoom = 0.0; + elm_photocam_zoom_set(wd->obj, tz); + } + return evas_object_image_load_error_get(wd->img); +} + +/* + * Returns the path of the current image file + * + * @param obj The photocam object + * @return Returns the path + * + * @ingroup Photocam + */ +EAPI const char * +elm_photocam_file_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->file; +} + +/** + * Set the zoom level of the photo + * + * This sets the zoom level. 1 will be 1:1 pixel for pixel. 2 will be 2:1 + * (that is 2x2 photo pixels will display as 1 on-screen pixel). 4:1 will be + * 4x4 photo pixels as 1 screen pixel, and so on. The @p zoom parameter must + * be greater than 0. It is usggested to stick to powers of 2. (1, 2, 4, 8, + * 16, 32, etc.). + * + * @param obj The photocam object + * @param zoom The zoom level to set + * + * @ingroup Photocam + */ +EAPI void +elm_photocam_zoom_set(Evas_Object *obj, double zoom) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_List *l; + Grid *g, *g_zoom = NULL; + Evas_Coord pw, ph, rx, ry, rw, rh; + int z; + int zoom_changed = 0, started = 0; + Ecore_Animator *an; + if (!wd) return; + if (zoom <= (1.0 / 256.0)) zoom = (1.0 / 256.0); + if (zoom == wd->zoom) return; + wd->zoom = zoom; + wd->size.ow = wd->size.w; + wd->size.oh = wd->size.h; + elm_smart_scroller_child_pos_get(wd->scr, &rx, &ry); + elm_smart_scroller_child_viewport_size_get(wd->scr, &rw, &rh); + if ((rw <= 0) || (rh <= 0)) return; + + if (wd->mode == ELM_PHOTOCAM_ZOOM_MODE_MANUAL) + { + wd->size.nw = (double)wd->size.imw / wd->zoom; + wd->size.nh = (double)wd->size.imh / wd->zoom; + } + else if (wd->mode == ELM_PHOTOCAM_ZOOM_MODE_AUTO_FIT) + { + if ((wd->size.imw < 1) || (wd->size.imh < 1)) + { + wd->size.nw = 0; + wd->size.nw = 0; + } + else + { + ph = (wd->size.imh * rw) / wd->size.imw; + if (ph > rh) + { + pw = (wd->size.imw * rh) / wd->size.imh; + ph = rh; + } + else + { + pw = rw; + } + if (wd->size.imw > wd->size.imh) + z = wd->size.imw / pw; + else + z = wd->size.imh / ph; + if (z >= 8) z = 8; + else if (z >= 4) z = 4; + else if (z >= 2) z = 2; + else z = 1; + if (z != wd->zoom) zoom_changed = 1; + wd->zoom = z; + wd->size.nw = pw; + wd->size.nh = ph; + } + } + else if (wd->mode == ELM_PHOTOCAM_ZOOM_MODE_AUTO_FILL) + { + if ((wd->size.imw < 1) || (wd->size.imh < 1)) + { + wd->size.nw = 0; + wd->size.nw = 0; + } + else + { + ph = (wd->size.imh * rw) / wd->size.imw; + if (ph < rh) + { + pw = (wd->size.imw * rh) / wd->size.imh; + ph = rh; + } + else + { + pw = rw; + } + if (wd->size.imw > wd->size.imh) + z = wd->size.imw / pw; + else + z = wd->size.imh / ph; + if (z >= 8) z = 8; + else if (z >= 4) z = 4; + else if (z >= 2) z = 2; + else z = 1; + if (z != wd->zoom) zoom_changed = 1; + wd->zoom = z; + wd->size.nw = pw; + wd->size.nh = ph; + } + } + if (wd->main_load_pending) + { + wd->size.w = wd->size.nw; + wd->size.h = wd->size.nh; + goto done; + } + EINA_LIST_FOREACH(wd->grids, l, g) + { + if (g->zoom == grid_zoom_calc(wd->zoom)) + { + wd->grids = eina_list_remove(wd->grids, g); + wd->grids = eina_list_prepend(wd->grids, g); + _grid_raise(g); + goto done; + } + } + g = grid_create(obj); + if (g) + { + if (eina_list_count(wd->grids) > 1) + { + g_zoom = eina_list_last(wd->grids)->data; + wd->grids = eina_list_remove(wd->grids, g_zoom); + grid_clear(obj, g_zoom); + free(g_zoom); + EINA_LIST_FOREACH(wd->grids, l, g_zoom) + { + g_zoom->dead = 1; + } + } + wd->grids = eina_list_prepend(wd->grids, g); + } + else + { + EINA_LIST_FREE(wd->grids, g) + { + grid_clear(obj, g); + free(g); + } + } + done: + wd->t_start = ecore_loop_time_get(); + wd->t_end = wd->t_start + _elm_config->zoom_friction; + if ((wd->size.w > 0) && (wd->size.h > 0)) + { + wd->size.spos.x = (double)(rx + (rw / 2)) / (double)wd->size.w; + wd->size.spos.y = (double)(ry + (rh / 2)) / (double)wd->size.h; + } + else + { + wd->size.spos.x = 0.5; + wd->size.spos.y = 0.5; + } + if (rw > wd->size.w) wd->size.spos.x = 0.5; + if (rh > wd->size.h) wd->size.spos.y = 0.5; + if (wd->size.spos.x > 1.0) wd->size.spos.x = 1.0; + if (wd->size.spos.y > 1.0) wd->size.spos.y = 1.0; + if (wd->paused) + { + zoom_do(obj, 1.0); + } + else + { + if (!wd->zoom_animator) + { + wd->zoom_animator = ecore_animator_add(_zoom_anim, obj); + wd->nosmooth++; + if (wd->nosmooth == 1) _smooth_update(obj); + started = 1; + } + } + an = wd->zoom_animator; + if (an) + { + if (!_zoom_anim(obj)) + { + ecore_animator_del(an); + an = NULL; + } + } + if (wd->calc_job) ecore_job_del(wd->calc_job); + wd->calc_job = ecore_job_add(_calc_job, wd); + if (!wd->paused) + { + if (started) + evas_object_smart_callback_call(obj, "zoom,start", NULL); + if (!an) + evas_object_smart_callback_call(obj, "zoom,stop", NULL); + } + if (zoom_changed) + evas_object_smart_callback_call(obj, "zoom,change", NULL); +} + +/** + * Get the zoom level of the photo + * + * This returns the current zoom level of the photocam object. Note that if + * you set the fill mode to other than ELM_PHOTOCAM_ZOOM_MODE_MANUAL + * (which is the default), the zoom level may be changed at any time by the + * photocam object itself to account for photo size and photocam viewpoer size + * + * @param obj The photocam object + * @return The current zoom level + * + * @ingroup Photocam + */ +EAPI double +elm_photocam_zoom_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 1.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 1.0; + return wd->zoom; +} + +/** + * Set the zoom mode + * + * This sets the zoom mode to manual or one of several automatic levels. + * Manual (ELM_PHOTOCAM_ZOOM_MODE_MANUAL) means that zoom is set manually by + * elm_photocam_zoom_set() and will stay at that level until changed by code + * or until zoom mode is changed. This is the default mode. + * The Automatic modes will allow the photocam object to automatically + * adjust zoom mode based on properties. ELM_PHOTOCAM_ZOOM_MODE_AUTO_FIT) will + * adjust zoom so the photo fits EXACTLY inside the scroll frame with no pixels + * outside this area. ELM_PHOTOCAM_ZOOM_MODE_AUTO_FILL will be similar but + * ensure no pixels within the frame are left unfilled. + * + * @param obj The photocam object + * @param mode The desired mode + * + * @ingroup Photocam + */ +EAPI void +elm_photocam_zoom_mode_set(Evas_Object *obj, Elm_Photocam_Zoom_Mode mode) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->mode == mode) return; + wd->mode = mode; + { + double tz = wd->zoom; + wd->zoom = 0.0; + elm_photocam_zoom_set(wd->obj, tz); + } +} + +/** + * Get the zoom mode + * + * This gets the current zoom mode of the photocam object + * + * @param obj The photocam object + * @return The current zoom mode + * + * @ingroup Photocam + */ +EAPI Elm_Photocam_Zoom_Mode +elm_photocam_zoom_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_PHOTOCAM_ZOOM_MODE_LAST; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_PHOTOCAM_ZOOM_MODE_LAST; + return wd->mode; +} + +/** + * Get the current image pixel width and height + * + * This gets the current photo pixel width and height (for the original). + * The size will be returned in the integers @p w and @p h that are pointed + * to. + * + * @param obj The photocam object + * @param w A pointer to the width return + * @param h A pointer to the height return + * + * @ingroup Photocam + */ +EAPI void +elm_photocam_image_size_get(const Evas_Object *obj, int *w, int *h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (w) *w = wd->size.imw; + if (h) *h = wd->size.imh; +} + +/** + * Get the current area of the image that is currently shown + * + * This gets the region + * + */ +EAPI void +elm_photocam_region_get(const Evas_Object *obj, int *x, int *y, int *w, int *h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord sx, sy, sw, sh; + if (!wd) return; + elm_smart_scroller_child_pos_get(wd->scr, &sx, &sy); + elm_smart_scroller_child_viewport_size_get(wd->scr, &sw, &sh); + if (wd->size.w > 0) + { + if (x) + { + *x = (wd->size.imw * sx) / wd->size.w; + if (*x > wd->size.imw) *x = wd->size.imw; + else if (*x < 0) *x = 0; + } + if (w) + { + *w = (wd->size.imw * sw) / wd->size.w; + if (*w > wd->size.imw) *w = wd->size.imw; + else if (*w < 0) *w = 0; + } + } + else + { + if (x) *x = 0; + if (w) *w = 0; + } + + if (wd->size.h > 0) + { + if (y) + { + *y = (wd->size.imh * sy) / wd->size.h; + if (*y > wd->size.imh) *y = wd->size.imh; + else if (*y < 0) *y = 0; + } + if (h) + { + *h = (wd->size.imh * sh) / wd->size.h; + if (*h > wd->size.imh) *h = wd->size.imh; + else if (*h < 0) *h = 0; + } + } + else + { + if (y) *y = 0; + if (h) *h = 0; + } +} + +/** + * Set the viewed portion of the image + * + * This sets the region of the image to be viewed + * + * @param obj The photocam object + * @param x X-coordinate of region in image original pixels + * @param y Y-coordinate of region in image original pixels + * @param w Width of region in image original pixels + * @param h Height of region in image original pixels + * + * @ingroup Photocam + */ +EAPI void +elm_photocam_image_region_show(Evas_Object *obj, int x, int y, int w, int h __UNUSED__) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + int rx, ry, rw, rh; + if (!wd) return; + if ((wd->size.imw < 1) || (wd->size.imh < 1)) return; + rx = (x * wd->size.w) / wd->size.imw; + ry = (y * wd->size.h) / wd->size.imh; + rw = (w * wd->size.w) / wd->size.imw; + rh = (w * wd->size.h) / wd->size.imh; + if (rw < 1) rw = 1; + if (rh < 1) rh = 1; + if ((rx + rw) > wd->size.w) rx = wd->size.w - rw; + if ((ry + rh) > wd->size.h) ry = wd->size.h - rh; + if (wd->zoom_animator) + { + wd->nosmooth--; + ecore_animator_del(wd->zoom_animator); + wd->zoom_animator = NULL; + zoom_do(obj, 1.0); + evas_object_smart_callback_call(obj, "zoom,stop", NULL); + } + elm_smart_scroller_child_region_show(wd->scr, rx, ry, rw, rh); +} + +/** + * Bring in the viewed portion of the image + * + * This brings in the region of the image over time + * + * @param obj The photocam object + * @param x X-coordinate of region in image original pixels + * @param y Y-coordinate of region in image original pixels + * @param w Width of region in image original pixels + * @param h Height of region in image original pixels + * + * @ingroup Photocam + */ +EAPI void +elm_photocam_image_region_bring_in(Evas_Object *obj, int x, int y, int w, int h __UNUSED__) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + int rx, ry, rw, rh; + if (!wd) return; + if ((wd->size.imw < 1) || (wd->size.imh < 1)) return; + rx = (x * wd->size.w) / wd->size.imw; + ry = (y * wd->size.h) / wd->size.imh; + rw = (w * wd->size.w) / wd->size.imw; + rh = (w * wd->size.h) / wd->size.imh; + if (rw < 1) rw = 1; + if (rh < 1) rh = 1; + if ((rx + rw) > wd->size.w) rx = wd->size.w - rw; + if ((ry + rh) > wd->size.h) ry = wd->size.h - rh; + if (wd->zoom_animator) + { + wd->nosmooth--; + if (!wd->nosmooth) _smooth_update(obj); + ecore_animator_del(wd->zoom_animator); + wd->zoom_animator = NULL; + zoom_do(obj, 1.0); + evas_object_smart_callback_call(obj, "zoom,stop", NULL); + } + elm_smart_scroller_region_bring_in(wd->scr, rx, ry, rw, rh); +} + +/** + * Set the paused state for photocam + * + * This sets the paused state to on (1) or off (0) for photocam. The default + * is on. This will stop zooming using animation ch change zoom levels and + * change instantly. This will stop any existing animations that are running. + * + * @param obj The photocam object + * @param paused The pause state to set + * + * @ingroup Photocam + */ +EAPI void +elm_photocam_paused_set(Evas_Object *obj, Eina_Bool paused) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->paused == !!paused) return; + wd->paused = paused; + if (wd->paused) + { + if (wd->zoom_animator) + { + ecore_animator_del(wd->zoom_animator); + wd->zoom_animator = NULL; + zoom_do(obj, 1.0); + evas_object_smart_callback_call(obj, "zoom,stop", NULL); + } + } +} + +/** + * Get the paused state for photocam + * + * This gets the current paused state for the photocam object. + * + * @param obj The photocam object + * @return The current paused state + * + * @ingroup Photocam + */ +EAPI Eina_Bool +elm_photocam_paused_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->paused; +} + +/** + * Get the internal low-res image used for photocam + * + * This gets the internal image object inside photocam. Do not modify it. It + * is for inspection only, and hooking callbacks to. Nothing else. It may be + * deleted at any time as well. + * + * @param obj The photocam object + * @return The internal image object handle, or NULL if none exists + * + * @ingroup Photocam + */ +EAPI Evas_Object * +elm_photocam_internal_image_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->img; +} + +/** + * Set the photocam scrolling bouncing. + * + * @param obj The photocam object + * @param h_bounce bouncing for horizontal + * @param v_bounce bouncing for vertical + * @ingroup Photocam + */ +EAPI void +elm_photocam_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_bounce_allow_set(wd->scr, h_bounce, v_bounce); +} + + +/** + * Get the photocam scrolling bouncing. + * + * @param obj The photocam object + * @param h_bounce bouncing for horizontal + * @param v_bounce bouncing for vertical + * @ingroup Photocam + */ +EAPI void +elm_photocam_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_bounce_allow_get(wd->scr, h_bounce, v_bounce); +} + diff --git a/src/lib/elm_priv.h b/src/lib/elm_priv.h new file mode 100644 index 0000000..90686c9 --- /dev/null +++ b/src/lib/elm_priv.h @@ -0,0 +1,204 @@ +#ifndef ELM_PRIV_H +#define ELM_PRIV_H +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#ifdef HAVE_ELEMENTARY_X +# include +#endif +#ifdef HAVE_ELEMENTARY_FB +# include +#endif +#ifdef HAVE_ELEMENTARY_WINCE +# include +#endif + +#include "els_pan.h" +#include "els_scroller.h" +#include "els_box.h" +#include "els_icon.h" + +#include "elm_widget.h" + +#define CRITICAL(...) EINA_LOG_DOM_CRIT(_elm_log_dom, __VA_ARGS__) +#define ERR(...) EINA_LOG_DOM_ERR (_elm_log_dom, __VA_ARGS__) +#define WRN(...) EINA_LOG_DOM_WARN(_elm_log_dom, __VA_ARGS__) +#define INF(...) EINA_LOG_DOM_INFO(_elm_log_dom, __VA_ARGS__) +#define DBG(...) EINA_LOG_DOM_DBG (_elm_log_dom, __VA_ARGS__) + +typedef struct _Elm_Config Elm_Config; +typedef struct _Elm_Module Elm_Module; + +struct _Elm_Theme +{ + Eina_List *overlay; + Eina_List *themes; + Eina_List *extension; + Eina_Hash *cache; + Elm_Theme *ref_theme; + Eina_List *referrers; + const char *theme; + int ref; +}; + +/* increment this whenever we change config enough that you need new + * defaults for elm to work. + */ +#define ELM_CONFIG_EPOCH 0x0001 +/* increment this whenever a new set of config values are added but the users + * config doesn't need to be wiped - simply new values need to be put in + */ +#define ELM_CONFIG_FILE_GENERATION 0x0003 +#define ELM_CONFIG_VERSION ((ELM_CONFIG_EPOCH << 16) | ELM_CONFIG_FILE_GENERATION) +/* NB: profile configuration files (.src) must have their + * "config_version" entry's value up-to-date with ELM_CONFIG_VERSION + * (in decimal)!! */ + +/* note: always remember to sync it with elm_config.c */ +extern const char *_elm_engines[]; + +#define ELM_SOFTWARE_X11 (_elm_engines[0]) +#define ELM_SOFTWARE_FB (_elm_engines[1]) +#define ELM_SOFTWARE_DIRECTFB (_elm_engines[2]) +#define ELM_SOFTWARE_16_X11 (_elm_engines[3]) +#define ELM_SOFTWARE_8_X11 (_elm_engines[4]) +#define ELM_XRENDER_X11 (_elm_engines[5]) +#define ELM_OPENGL_X11 (_elm_engines[6]) +#define ELM_SOFTWARE_WIN32 (_elm_engines[7]) +#define ELM_SOFTWARE_16_WINCE (_elm_engines[8]) +#define ELM_SOFTWARE_SDL (_elm_engines[9]) +#define ELM_SOFTWARE_16_SDL (_elm_engines[10]) +#define ELM_OPENGL_SDL (_elm_engines[11]) + +#define ELM_FONT_TOKEN_STYLE ":style=" + +struct _Elm_Config +{ + int config_version; + const char *engine; + Eina_Bool thumbscroll_enable; + int thumbscroll_threshold; + double thumbscroll_momentum_threshold; + double thumbscroll_friction; + double thumbscroll_bounce_friction; + double page_scroll_friction; + double bring_in_scroll_friction; + double zoom_friction; + Eina_Bool thumbscroll_bounce_enable; + double thumbscroll_border_friction; + double scale; + int bgpixmap; + int compositing; + Eina_List *font_dirs; + Eina_List *font_overlays; + int font_hinting; + int cache_flush_poll_interval; + Eina_Bool cache_flush_enable; + int image_cache; + int font_cache; + int edje_cache; + int edje_collection_cache; + int finger_size; + double fps; + const char *theme; + const char *modules; + double tooltip_delay; + Eina_Bool cursor_engine_only; + Eina_Bool focus_highlight_enable; + Eina_Bool focus_highlight_animate; + int toolbar_shrink_mode; + Eina_Bool fileselector_expand_enable; + Eina_Bool inwin_dialogs_enable; + int icon_size; + double longpress_timeout; +}; + +struct _Elm_Module +{ + int version; + const char *name; + const char *as; + const char *so_path; + const char *data_dir; + const char *bin_dir; + void *handle; + void *data; + void *api; + int (*init_func) (Elm_Module *m); + int (*shutdown_func) (Elm_Module *m); + int references; +}; + +void _elm_win_shutdown(void); +void _elm_win_rescale(Elm_Theme *th, Eina_Bool use_theme); + +Eina_Bool _elm_theme_object_set(Evas_Object *parent, Evas_Object *o, const char *clas, const char *group, const char *style); +Eina_Bool _elm_theme_object_icon_set(Evas_Object *parent, Evas_Object *o, const char *group, const char *style); +Eina_Bool _elm_theme_set(Elm_Theme *th, Evas_Object *o, const char *clas, const char *group, const char *style); +Eina_Bool _elm_theme_icon_set(Elm_Theme *th, Evas_Object *o, const char *group, const char *style); +Eina_Bool _elm_theme_parse(Elm_Theme *th, const char *theme); +void _elm_theme_shutdown(void); + +void _elm_module_init(void); +void _elm_module_shutdown(void); +void _elm_module_parse(const char *s); +Elm_Module *_elm_module_find_as(const char *as); +Elm_Module *_elm_module_add(const char *name, const char *as); +void _elm_module_del(Elm_Module *m); +const void *_elm_module_symbol_get(Elm_Module *m, const char *name); + +void _elm_widget_type_clear(void); +void _elm_widget_focus_region_show(const Evas_Object *obj); + +void _elm_unneed_ethumb(void); + +void _elm_rescale(void); + +void _elm_config_init(void); +void _elm_config_sub_init(void); +void _elm_config_shutdown(void); +Eina_Bool _elm_config_save(void); +void _elm_config_reload(void); + +void _elm_recache(void); + +const char *_elm_config_current_profile_get(void); +const char *_elm_config_profile_dir_get(const char *prof, Eina_Bool is_user); +Eina_List *_elm_config_profiles_list(void); +void _elm_config_profile_set(const char *profile); + +void _elm_config_engine_set(const char *engine); + +Eina_List *_elm_config_font_overlays_list(void); +void _elm_config_font_overlay_set(const char *text_class, const char *font, Evas_Font_Size size); +void _elm_config_font_overlay_remove(const char *text_class); +void _elm_config_font_overlay_apply(void); +Eina_List *_elm_config_text_classes_get(void); +void _elm_config_text_classes_free(Eina_List *l); + +Elm_Font_Properties *_elm_font_properties_get(Eina_Hash **font_hash, const char *font); +Eina_Hash *_elm_font_available_hash_add(Eina_Hash *font_hash, const char *full_name); +void _elm_font_available_hash_del(Eina_Hash *hash); + +void elm_tooltip_theme(Elm_Tooltip *tt); +void elm_object_sub_tooltip_content_cb_set(Evas_Object *eventarea, Evas_Object *owner, Elm_Tooltip_Content_Cb func, const void *data, Evas_Smart_Cb del_cb); +void elm_cursor_theme(Elm_Cursor *cur); +void elm_object_sub_cursor_set(Evas_Object *eventarea, Evas_Object *owner, const char *cursor); + +void elm_menu_clone(Evas_Object *from_menu, Evas_Object *to_menu, Elm_Menu_Item *parent); + +Eina_Bool _elm_dangerous_call_check(const char *call); + +Evas_Object *_elm_scroller_edje_object_get(Evas_Object *obj); + +char *_elm_util_mkup_to_text(const char *mkup); +char *_elm_util_text_to_mkup(const char *text); + +extern char *_elm_appname; +extern Elm_Config *_elm_config; +extern const char *_elm_data_dir; +extern const char *_elm_lib_dir; +extern int _elm_log_dom; +extern Eina_List *_elm_win_list; + +#endif diff --git a/src/lib/elm_progressbar.c b/src/lib/elm_progressbar.c new file mode 100644 index 0000000..b7e112f --- /dev/null +++ b/src/lib/elm_progressbar.c @@ -0,0 +1,635 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Progressbar Progressbar + * + * The progressbar adds a widget for representing current progress + * of a job status + * + * A progressbar can be horizontal or vertical. It can contain an Icon and has a + * primary label as well as a units label (that is formatted with floating + * point values and thus accepts a printf-style format string, like + * “%1.2f units”. + * + * Label, Icon and Unit strings/objects are optional. + * + * A progressbar may be inverted which means values invert, with high vales being + * on the left or top and low values on the right or bottom (as opposed to + * normally being low on the left or top and high on the bottom and right). + * + * The span of the progressbar is its length (horizontally or vertically). + * This will be scaled by the object or applications scaling factor. At any point + * code can query the progressbar for its value with elm_progressbar_value_get(). + */ + +#define MIN_RATIO_LVL 0.0 +#define MAX_RATIO_LVL 1.0 + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *progressbar; + Evas_Object *spacer; + Evas_Object *icon; + Evas_Coord size; + Eina_Bool horizontal : 1; + Eina_Bool inverted : 1; + Eina_Bool pulse : 1; + Eina_Bool pulse_state : 1; + const char *units; + const char *label; + double val; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _units_set(Evas_Object *obj); +static void _val_set(Evas_Object *obj); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->label) eina_stringshare_del(wd->label); + if (wd->units) eina_stringshare_del(wd->units); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->horizontal) + _elm_theme_object_set(obj, wd->progressbar, "progressbar", "horizontal", elm_widget_style_get(obj)); + else + _elm_theme_object_set(obj, wd->progressbar, "progressbar", "vertical", elm_widget_style_get(obj)); + + if (wd->icon) + { + edje_object_part_swallow(wd->progressbar, "elm.swallow.content", wd->icon); + edje_object_signal_emit(wd->progressbar, "elm,state,icon,visible", "elm"); + } + if (wd->label) + { + edje_object_part_text_set(wd->progressbar, "elm.text", wd->label); + edje_object_signal_emit(wd->progressbar, "elm,state,text,visible", "elm"); + } + if (wd->pulse) + edje_object_signal_emit(wd->progressbar, "elm,state,pulse", "elm"); + else + edje_object_signal_emit(wd->progressbar, "elm,state,fraction", "elm"); + if (wd->pulse_state) + edje_object_signal_emit(wd->progressbar, "elm,state,pulse,start", "elm"); + + if ((wd->units) && (!wd->pulse)) + edje_object_signal_emit(wd->progressbar, "elm,state,units,visible", "elm"); + + if (wd->horizontal) + evas_object_size_hint_min_set(wd->spacer, (double)wd->size * elm_widget_scale_get(obj) * _elm_config->scale, 1); + else + evas_object_size_hint_min_set(wd->spacer, 1, (double)wd->size * elm_widget_scale_get(obj) * _elm_config->scale); + + edje_object_part_swallow(wd->progressbar, "elm.swallow.bar", wd->spacer); + + if (wd->inverted) + edje_object_signal_emit(wd->progressbar, "elm,state,inverted,on", "elm"); + + _units_set(obj); + edje_object_message_signal_process(wd->progressbar); + edje_object_scale_set(wd->progressbar, elm_widget_scale_get(obj) * _elm_config->scale); + _val_set(obj); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + if (!wd) return; + edje_object_size_min_restricted_calc(wd->progressbar, &minw, &minh, minw, minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (obj != wd->icon) return; + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->icon) + { + edje_object_signal_emit(wd->progressbar, "elm,state,icon,hidden", "elm"); + evas_object_event_callback_del_full + (sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + wd->icon = NULL; + edje_object_message_signal_process(wd->progressbar); + _sizing_eval(obj); + } +} + +static void +_val_set(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + double pos; + if (!wd) return; + pos = wd->val; + if (wd->inverted) pos = MAX_RATIO_LVL - pos; + edje_object_part_drag_value_set(wd->progressbar, "elm.cur.progressbar", pos, pos); +} + +static void +_units_set(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->units) + { + char buf[1024]; + snprintf(buf, sizeof(buf), wd->units, 100 * wd->val); + edje_object_part_text_set(wd->progressbar, "elm.text.status", buf); + } + else + edje_object_part_text_set(wd->progressbar, "elm.text.status", NULL); +} + +/** + * Add a new progressbar to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Progressbar + */ +EAPI Evas_Object * +elm_progressbar_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "progressbar"); + elm_widget_type_set(obj, "progressbar"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->horizontal = EINA_TRUE; + wd->inverted = EINA_FALSE; + wd->pulse = EINA_FALSE; + wd->pulse_state = EINA_FALSE; + wd->units = eina_stringshare_add("%.0f %%"); + wd->val = MIN_RATIO_LVL; + + wd->progressbar = edje_object_add(e); + _elm_theme_object_set(obj, wd->progressbar, "progressbar", "horizontal", "default"); + elm_widget_resize_object_set(obj, wd->progressbar); + + wd->spacer = evas_object_rectangle_add(e); + evas_object_color_set(wd->spacer, 0, 0, 0, 0); + evas_object_pass_events_set(wd->spacer, EINA_TRUE); + elm_widget_sub_object_add(obj, wd->spacer); + edje_object_part_swallow(wd->progressbar, "elm.swallow.bar", wd->spacer); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + _units_set(obj); + _val_set(obj); + _sizing_eval(obj); + return obj; +} + +/** + * Normally the progressbar will display and interpret values from low to high. + * This display a progressbar for jobs with unknow state of progression, + * (the cursor pulse right to left and left to right, and loop) if pulse is set to 1. + * + * @param obj The progressbar object + * @param pulse The pulse flag. 1 == pulse, 0 == normal + * + * @ingroup Progressbar + */ +EAPI void +elm_progressbar_pulse_set(Evas_Object *obj, Eina_Bool pulse) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + pulse = !!pulse; + if (wd->pulse == pulse) return; + wd->pulse = pulse; + _theme_hook(obj); +} + +/** + * Normally the progressbar will display and interpret values from low to high. + * This display a progressbar for jobs with unknow state of progression, + * (the cursor pulse right to left and left to right, and loop) if pulse is set to 1. + * + * @param obj The progressbar object + * @return The pulse flag + * (1 == pulse, 0 == normal) + * + * @ingroup Progressbar + */ +EAPI Eina_Bool +elm_progressbar_pulse_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->pulse; +} + +/** + * Stat/Stop de pulse action + * + * @param obj The progressbar object + * @param state The pulse flag. 1 == start pulse, 0 == stop pulse + * + * @ingroup Progressbar + */ +EAPI void +elm_progressbar_pulse(Evas_Object *obj, Eina_Bool state) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + state = !!state; + if ((!wd->pulse) && (wd->pulse_state == state)) return; + wd->pulse_state = state; + if (wd->pulse_state) + edje_object_signal_emit(wd->progressbar, "elm,state,pulse,start", "elm"); + else + edje_object_signal_emit(wd->progressbar, "elm,state,pulse,stop", "elm"); +} + +/** + * Set the value the progressbar indicates + * + * @param obj The progressbar object + * @param val The fraction value (must be between 0.0 and 1.0) + * + * @ingroup Progressbar + */ +EAPI void +elm_progressbar_value_set(Evas_Object *obj, double val) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->val == val) return; + wd->val = val; + if (wd->val < MIN_RATIO_LVL) wd->val = MIN_RATIO_LVL; + if (wd->val > MAX_RATIO_LVL) wd->val = MAX_RATIO_LVL; + _val_set(obj); + _units_set(obj); +} + + +/** + * Get the value the progressbar has + * + * @param obj The progressbar object + * @return The value of the progressbar + * + * @ingroup Progressbar + */ +EAPI double +elm_progressbar_value_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->val; +} + +/** + * Set the label of the progressbar + * + * @param obj The progressbar object + * @param label The text label string in UTF-8 + * + * @ingroup Progressbar + */ +EAPI void +elm_progressbar_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->label, label); + if (label) + { + edje_object_signal_emit(wd->progressbar, "elm,state,text,visible", "elm"); + edje_object_message_signal_process(wd->progressbar); + } + else + { + edje_object_signal_emit(wd->progressbar, "elm,state,text,hidden", "elm"); + edje_object_message_signal_process(wd->progressbar); + } + edje_object_part_text_set(wd->progressbar, "elm.text", label); + _sizing_eval(obj); +} + +/** + * Get the label of the progressbar + * + * @param obj The progressbar object + * @return The text label string in UTF-8 + * + * @ingroup Progressbar + */ +EAPI const char * +elm_progressbar_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the icon object of the progressbar object + * + * Once the icon object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_progressbar_icon_unset() function. + * + * @param obj The progressbar object + * @param icon The icon object + * + * @ingroup Progressbar + */ +EAPI void +elm_progressbar_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->icon == icon) return; + if (wd->icon) evas_object_del(wd->icon); + wd->icon = icon; + if (icon) + { + elm_widget_sub_object_add(obj, icon); + evas_object_event_callback_add(icon, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->progressbar, "elm.swallow.content", icon); + edje_object_signal_emit(wd->progressbar, "elm,state,icon,visible", "elm"); + edje_object_message_signal_process(wd->progressbar); + } + _sizing_eval(obj); +} + +/** + * Get the icon object of the progressbar object + * + * @param obj The progressbar object + * @return The icon object + * + * @ingroup Progressbar + */ +EAPI Evas_Object * +elm_progressbar_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->icon; +} + +/** + * Unset the icon used for the progressbar object + * + * Unparent and return the icon object which was set for this widget. + * + * @param obj The progressbar object + * @return The icon object that was being used + * + * @ingroup Progressbar + */ +EAPI Evas_Object * +elm_progressbar_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->icon) return NULL; + Evas_Object *icon = wd->icon; + elm_widget_sub_object_del(obj, wd->icon); + edje_object_part_unswallow(wd->progressbar, wd->icon); + wd->icon = NULL; + return icon; +} + +/** + * Set the length of the progression region of the progressbar + * + * This sets the minimum width or height (depending on orientation) of the + * area of the progressbar that allows the progressbar to be dragged around. This in + * turn affects the objects minimum size (along with icon label and unit + * text). + * + * @param obj The progressbar object + * @param size The length of the progressbar area + * + * @ingroup Progressbar + */ +EAPI void +elm_progressbar_span_size_set(Evas_Object *obj, Evas_Coord size) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->size == size) return; + wd->size = size; + if (wd->horizontal) + evas_object_size_hint_min_set(wd->spacer, (double)wd->size * elm_widget_scale_get(obj) * _elm_config->scale, 1); + else + evas_object_size_hint_min_set(wd->spacer, 1, (double)wd->size * elm_widget_scale_get(obj) * _elm_config->scale); + edje_object_part_swallow(wd->progressbar, "elm.swallow.bar", wd->spacer); + _sizing_eval(obj); +} + +/** + * Get the length of the progression region of the progressbar + * + * @param obj The progressbar object + * @return The length of the progressbar area + * + * @ingroup Progressbar + */ +EAPI Evas_Coord +elm_progressbar_span_size_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->size; +} + +/** + * Set the format string of the unit area + * + * If NULL, this disabls the unit area display. If not it sets the format + * string for the unit text. The unit text is provided a floating point + * value, so the unit text can display up to 1 floating point falue. Note that + * this is optional. Use a format string such as "%1.2f meters" for example. + * + * @param obj The progressbar object + * @param units The format string for the units display + * + * @ingroup Progressbar + */ +EAPI void +elm_progressbar_unit_format_set(Evas_Object *obj, const char *units) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->units, units); + if (units) + { + edje_object_signal_emit(wd->progressbar, "elm,state,units,visible", "elm"); + edje_object_message_signal_process(wd->progressbar); + } + else + { + edje_object_signal_emit(wd->progressbar, "elm,state,units,hidden", "elm"); + edje_object_message_signal_process(wd->progressbar); + } + _units_set(obj); + _sizing_eval(obj); +} + +/** + * Get the format string of the unit area + * + * @param obj The progressbar object + * @return The format string for the units display + * + * @ingroup Progressbar + */ +EAPI const char * +elm_progressbar_unit_format_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->units; +} + +/** + * Set orientation of the progressbar + * + * @param obj The progressbar object + * @param horizontal If set, the progressbar will be horizontal + * + * @ingroup Progressbar + */ +EAPI void +elm_progressbar_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + horizontal = !!horizontal; + if (wd->horizontal == horizontal) return; + wd->horizontal = horizontal; + _theme_hook(obj); +} + +/** + * Gets orientation of the progressbar + * + * @param obj The progressbar object + * @return The orientation + * (0 = vertical, 1 = horizontal) + * + * @ingroup Progressbar + */ +EAPI Eina_Bool +elm_progressbar_horizontal_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->horizontal; +} + +/** + * Invert the progressbar display + * + * Normally the progressbar will display and interpret values from low to high + * and when horizontal that is left to right. When vertical that is top + * to bottom. This inverts this (so from right to left or bottom to top) if + * inverted is set to 1. + * + * @param obj The progressbar object + * @param inverted The inverted flag. 1 == inverted, 0 == normal + * + * @ingroup Progressbar + */ +EAPI void +elm_progressbar_inverted_set(Evas_Object *obj, Eina_Bool inverted) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + inverted = !!inverted; + if (wd->inverted == inverted) return; + wd->inverted = inverted; + if (wd->inverted) + edje_object_signal_emit(wd->progressbar, "elm,state,inverted,on", "elm"); + else + edje_object_signal_emit(wd->progressbar, "elm,state,inverted,off", "elm"); + edje_object_message_signal_process(wd->progressbar); + _val_set(obj); + _units_set(obj); +} + +/** + * Gets if the progressbar will displayed inverted + * + * @param obj The progressbar object + * @return The inverted flag + * (1 == inverted, 0 == normal) + * + * @ingroup Progressbar + */ +EAPI Eina_Bool +elm_progressbar_inverted_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->inverted; +} diff --git a/src/lib/elm_radio.c b/src/lib/elm_radio.c new file mode 100644 index 0000000..c01572f --- /dev/null +++ b/src/lib/elm_radio.c @@ -0,0 +1,587 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Radio Radio + * + * The radio button allows for 1 or more selectors to be created to select 1 + * of a set of options. + * + * Signals that you can add callbacks for are: + * + * changed - This is called whenever the user changes the state of one of the + * radio objects within the group of radio objects that work together. + * + * A radio object contains an indicator, an optional Label and an optional + * icon object. They work normally in groups of 2 or more. When you create a + * radio (if it is not the first member of the group), simply add it to the + * group by adding it to any other member of the group that already exists + * (or the first member) with elm_radio_group_add() with the second parameter + * being the existing group member. The radio object(s) will select from one + * of a set of integer values, so any value they are configuring needs to be + * mapped to a set of integers. To configure what value that radio object + * represents, use elm_radio_state_value_set() to set the integer it + * represents. To set the value the whole group is to indicate use + * elm_radio_value_set() on any group member, and to get the groups value use + * elm_radio_value_get(). For convenience the radio objects are also able to + * directly set an integer (int) to the value that is selected. To specify + * the pointer to this integer to modify, use elm_radio_value_pointer_set(). + * The radio objects will modify this directly. That implies the pointer must + * point to valid memory for as long as the radio objects exist. + */ + +typedef struct _Widget_Data Widget_Data; +typedef struct _Group Group; + +struct _Group +{ + int value; + int *valuep; + Eina_List *radios; +}; + +struct _Widget_Data +{ + Evas_Object *radio; + Evas_Object *icon; + int value; + const char *label; + Eina_Bool state; + Group *group; +}; + +static const char *widtype = NULL; +static void _state_set(Evas_Object *obj, Eina_Bool state); +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _signal_radio_on(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _on_focus_hook(void *data, Evas_Object *obj); +static void _activate(Evas_Object *obj); +static void _activate_hook(Evas_Object *obj); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); + +static const char SIG_CHANGED[] = "changed"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_CHANGED, ""}, + {NULL, NULL} +}; + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + + if ((strcmp(ev->keyname, "Return")) && + (strcmp(ev->keyname, "KP_Enter")) && + (strcmp(ev->keyname, "space"))) + return EINA_FALSE; + _activate(obj); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->label) eina_stringshare_del(wd->label); + wd->group->radios = eina_list_remove(wd->group->radios, obj); + if (!wd->group->radios) free(wd->group); + wd->group = NULL; + free(wd); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->radio, "elm,action,focus", "elm"); + evas_object_focus_set(wd->radio, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->radio, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->radio, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->radio, "radio", "base", elm_widget_style_get(obj)); + if (wd->icon) + edje_object_signal_emit(wd->radio, "elm,state,icon,visible", "elm"); + else + edje_object_signal_emit(wd->radio, "elm,state,icon,hidden", "elm"); + if (wd->state) + edje_object_signal_emit(wd->radio, "elm,state,radio,on", "elm"); + else + edje_object_signal_emit(wd->radio, "elm,state,radio,off", "elm"); + if (wd->label) + edje_object_signal_emit(wd->radio, "elm,state,text,visible", "elm"); + else + edje_object_signal_emit(wd->radio, "elm,state,text,hidden", "elm"); + edje_object_part_text_set(wd->radio, "elm.text", wd->label); + if (elm_widget_disabled_get(obj)) + { + edje_object_signal_emit(wd->radio, "elm,state,disabled", "elm"); + if (wd->state) _state_set(obj, 0); + } + edje_object_message_signal_process(wd->radio); + edje_object_scale_set(wd->radio, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_disabled_get(obj)) + { + edje_object_signal_emit(wd->radio, "elm,state,disabled", "elm"); + if (wd->state) _state_set(obj, 0); + } + else + edje_object_signal_emit(wd->radio, "elm,state,enabled", "elm"); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->radio, &minw, &minh, minw, minh); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (obj != wd->icon) return; + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->icon) + { + edje_object_signal_emit(wd->radio, "elm,state,icon,hidden", "elm"); + evas_object_event_callback_del_full + (sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + wd->icon = NULL; + _sizing_eval(obj); + } +} + +static void +_state_set(Evas_Object *obj, Eina_Bool state) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if ((state != wd->state) && (!elm_widget_disabled_get(obj))) + { + wd->state = state; + if (wd->state) + edje_object_signal_emit(wd->radio, "elm,state,radio,on", "elm"); + else + edje_object_signal_emit(wd->radio, "elm,state,radio,off", "elm"); + } +} + +static void +_state_set_all(Widget_Data *wd) +{ + const Eina_List *l; + Evas_Object *child, *selected = NULL; + Eina_Bool disabled = EINA_FALSE; + EINA_LIST_FOREACH(wd->group->radios, l, child) + { + Widget_Data *wd2 = elm_widget_data_get(child); + if (wd2->state) selected = child; + if (wd2->value == wd->group->value) + { + _state_set(child, 1); + if (!wd2->state) disabled = EINA_TRUE; + } + else _state_set(child, 0); + } + if ((disabled) && (selected)) _state_set(selected, 1); +} + +static void +_activate(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->group->value == wd->value) return; + wd->group->value = wd->value; + if (wd->group->valuep) *(wd->group->valuep) = wd->group->value; + _state_set_all(wd); + evas_object_smart_callback_call(obj, SIG_CHANGED, NULL); +} + +static void +_activate_hook(Evas_Object *obj) +{ + _activate(obj); +} + +static void +_signal_radio_on(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + _activate(data); +} + +/** + * Add a new radio to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Radio + */ +EAPI Evas_Object * +elm_radio_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "radio"); + elm_widget_type_set(obj, "radio"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_activate_hook_set(obj, _activate_hook); + elm_widget_event_hook_set(obj, _event_hook); + + wd->radio = edje_object_add(e); + _elm_theme_object_set(obj, wd->radio, "radio", "base", "default"); + edje_object_signal_callback_add(wd->radio, "elm,action,radio,on", "", _signal_radio_on, obj); + edje_object_signal_callback_add(wd->radio, "elm,action,radio,toggle", "", _signal_radio_on, obj); + elm_widget_resize_object_set(obj, wd->radio); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + wd->group = calloc(1, sizeof(Group)); + wd->group->radios = eina_list_append(wd->group->radios, obj); + wd->state = 0; + + _sizing_eval(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the text label of the radio object + * + * @param obj The radio object + * @param label The text label string in UTF-8 + * + * @ingroup Radio + */ +EAPI void +elm_radio_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->label, label); + if (label) + { + edje_object_signal_emit(wd->radio, "elm,state,text,visible", "elm"); + edje_object_message_signal_process(wd->radio); + } + else + { + edje_object_signal_emit(wd->radio, "elm,state,text,hidden", "elm"); + edje_object_message_signal_process(wd->radio); + } + edje_object_part_text_set(wd->radio, "elm.text", label); + _sizing_eval(obj); +} + +/** + * Get the text label of the radio object + * + * @param obj The radio object + * @return The text label string in UTF-8 + * + * @ingroup Radio + */ +EAPI const char * +elm_radio_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the icon object of the radio object + * + * Once the icon object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_radio_icon_unset() function. + * + * @param obj The radio object + * @param icon The icon object + * + * @ingroup Radio + */ +EAPI void +elm_radio_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->icon == icon) return; + if (wd->icon) evas_object_del(wd->icon); + wd->icon = icon; + if (icon) + { + elm_widget_sub_object_add(obj, icon); + evas_object_event_callback_add(icon, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->radio, "elm.swallow.content", icon); + edje_object_signal_emit(wd->radio, "elm,state,icon,visible", "elm"); + edje_object_message_signal_process(wd->radio); + } + _sizing_eval(obj); +} + +/** + * Get the icon object of the radio object + * + * @param obj The radio object + * @return The icon object + * + * @ingroup Radio + */ +EAPI Evas_Object * +elm_radio_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->icon; +} + +/** + * Unset the icon used for the radio object + * + * Unparent and return the icon object which was set for this widget. + * + * @param obj The radio object + * @return The icon object that was being used + * + * @ingroup Radio + */ +EAPI Evas_Object * +elm_radio_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->icon) return NULL; + Evas_Object *icon = wd->icon; + elm_widget_sub_object_del(obj, wd->icon); + edje_object_part_unswallow(wd->radio, wd->icon); + wd->icon = NULL; + return icon; +} + +/** + * Add this radio to a group of other radio objects + * + * Radio objects work in groups. Each member should have a different integer + * value assigned. In order ro have them work as a group, they need to know + * about eacthother. This adds the given radio object to the group of which + * the group object indicated is a member. + * + * @param obj The radio object + * @param group The object whose group the object is to join + * + * @ingroup Radio + */ +EAPI void +elm_radio_group_add(Evas_Object *obj, Evas_Object *group) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Widget_Data *wd2 = elm_widget_data_get(group); + if (!wd) return; + if (!wd2) + { + if (eina_list_count(wd->group->radios) == 1) + return; + wd->group->radios = eina_list_remove(wd->group->radios, obj); + wd->group = calloc(1, sizeof(Group)); + wd->group->radios = eina_list_append(wd->group->radios, obj); + } + else if (wd->group == wd2->group) return; + else + { + wd->group->radios = eina_list_remove(wd->group->radios, obj); + if (!wd->group->radios) free(wd->group); + wd->group = wd2->group; + wd->group->radios = eina_list_append(wd->group->radios, obj); + } + if (wd->value == wd->group->value) _state_set(obj, 1); + else _state_set(obj, 0); +} + +/** + * Set the integer value that this radio object represents + * + * This sets the value of the radio. + * + * @param obj The radio object + * @param value The value to use if this radio object is selected + * + * @ingroup Radio + */ +EAPI void +elm_radio_state_value_set(Evas_Object *obj, int value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->value = value; + if (wd->value == wd->group->value) _state_set(obj, 1); + else _state_set(obj, 0); +} + +/** + * Get the integer value that this radio object represents + * + * This gets the value of the radio. + * + * @param obj The radio object + * @return The value used if this radio object is selected + * + * @ingroup Radio + */ +EAPI int +elm_radio_state_value_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->value; +} + +/** + * Set the value of the radio. + * + * This sets the value of the radio group and will also set the value if + * pointed to, to the value supplied, but will not call any callbacks. + * + * @param obj The radio object + * @param value The value to use for the group + * + * @ingroup Radio + */ +EAPI void +elm_radio_value_set(Evas_Object *obj, int value) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (value == wd->group->value) return; + wd->group->value = value; + if (wd->group->valuep) *(wd->group->valuep) = wd->group->value; + _state_set_all(wd); +} + +/** + * Get the state of the radio object + * + * @param obj The radio object + * @return The integer state + * + * @ingroup Radio + */ +EAPI int +elm_radio_value_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->group->value; +} + +/** + * Set a convenience pointer to a integer to change + * + * This sets a pointer to a integer, that, in addition to the radio objects + * state will also be modified directly. To stop setting the object pointed + * to simply use NULL as the valuep parameter. If valuep is not NULL, then + * when this is called, the radio objects state will also be modified to + * reflect the value of the integer valuep points to, just like calling + * elm_radio_value_set(). + * + * @param obj The radio object + * @param valuep Pointer to the integer to modify + * + * @ingroup Radio + */ +EAPI void +elm_radio_value_pointer_set(Evas_Object *obj, int *valuep) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (valuep) + { + wd->group->valuep = valuep; + if (*(wd->group->valuep) != wd->group->value) + { + wd->group->value = *(wd->group->valuep); + _state_set_all(wd); + } + } + else + { + wd->group->valuep = NULL; + } +} diff --git a/src/lib/elm_scroller.c b/src/lib/elm_scroller.c new file mode 100644 index 0000000..1bd94a0 --- /dev/null +++ b/src/lib/elm_scroller.c @@ -0,0 +1,919 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Scroller Scroller + * + * A scroller holds a single object and "scrolls it around". This means that + * it allows the user to use a scrollbar (or a finger) to drag the viewable + * region around, allowing to move through a much larger object that is + * contained in the scroller. The scroiller will always have a small minimum + * size by default as it won't be limited by the contents of the scroller. + * + * Signals that you can add callbacks for are: + * + * edge,left - the left edge of the content has been reached + * + * edge,right - the right edge of the content has been reached + * + * edge,top - the top edge of the content has been reached + * + * edge,bottom - the bottom edge of the content has been reached + * + * scroll - the content has been scrolled (moved) + * + * scroll,anim,start - scrolling animation has started + * + * scroll,anim,stop - scrolling animation has stopped + * + * scroll,drag,start - dragging the contents around has started + * + * scroll,drag,stop - dragging the contents around has stopped + */ +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *scr; + Evas_Object *content; + const char *widget_name, *widget_base; + Eina_Bool min_w : 1; + Eina_Bool min_h : 1; + double pagerel_h, pagerel_v; + Evas_Coord pagesize_h, pagesize_v; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _show_region_hook(void *data, Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _on_focus_hook(void *data, Evas_Object *obj); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); + + +static const char SIG_SCROLL[] = "scroll"; +static const char SIG_SCROLL_ANIM_START[] = "scroll,anim,start"; +static const char SIG_SCROLL_ANIM_STOP[] = "scroll,anim,stop"; +static const char SIG_SCROLL_DRAG_START[] = "scroll,drag,start"; +static const char SIG_SCROLL_DRAG_STOP[] = "scroll,drag,stop"; +static const char SIG_EDGE_LEFT[] = "edge,left"; +static const char SIG_EDGE_RIGHT[] = "edge,right"; +static const char SIG_EDGE_TOP[] = "edge,top"; +static const char SIG_EDGE_BOTTOM[] = "edge,bottom"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_SCROLL, ""}, + {SIG_SCROLL_ANIM_START, ""}, + {SIG_SCROLL_ANIM_STOP, ""}, + {SIG_SCROLL_DRAG_START, ""}, + {SIG_SCROLL_DRAG_STOP, ""}, + {SIG_EDGE_LEFT, ""}, + {SIG_EDGE_RIGHT, ""}, + {SIG_EDGE_TOP, ""}, + {SIG_EDGE_BOTTOM, ""}, + {NULL, NULL} +}; + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + + Evas_Coord x = 0; + Evas_Coord y = 0; + Evas_Coord step_x = 0; + Evas_Coord step_y = 0; + Evas_Coord max_x = 0; + Evas_Coord max_y = 0; + Evas_Coord v_w = 0; + Evas_Coord v_h = 0; + Evas_Coord page_x = 0; + Evas_Coord page_y = 0; + + elm_smart_scroller_child_pos_get(wd->scr, &x, &y); + elm_smart_scroller_step_size_get(wd->scr, &step_x, &step_y); + elm_smart_scroller_page_size_get(wd->scr, &page_x, &page_y); + elm_smart_scroller_child_viewport_size_get(wd->scr, &v_w, &v_h); + elm_scroller_child_size_get(obj, &max_x, &max_y); + + if ((!strcmp(ev->keyname, "Left")) || (!strcmp(ev->keyname, "KP_Left"))) + { + x -= step_x; + } + else if ((!strcmp(ev->keyname, "Right")) || (!strcmp(ev->keyname, "KP_Right"))) + { + x += step_x; + } + else if ((!strcmp(ev->keyname, "Up")) || (!strcmp(ev->keyname, "KP_Up"))) + { + y -= step_y; + } + else if ((!strcmp(ev->keyname, "Down")) || (!strcmp(ev->keyname, "KP_Down"))) + { + y += step_y; + } + else if ((!strcmp(ev->keyname, "Home")) || (!strcmp(ev->keyname, "KP_Home"))) + { + y = 0; + } + else if ((!strcmp(ev->keyname, "End")) || (!strcmp(ev->keyname, "KP_End"))) + { + y = max_y - v_h; + } + else if ((!strcmp(ev->keyname, "Prior")) || (!strcmp(ev->keyname, "KP_Prior"))) + { + if (page_y < 0) + y -= -(page_y * v_h) / 100; + else + y -= page_y; + } + else if ((!strcmp(ev->keyname, "Next")) || (!strcmp(ev->keyname, "KP_Next"))) + { + if (page_y < 0) + y += -(page_y * v_h) / 100; + else + y += page_y; + } + else return EINA_FALSE; + + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + elm_smart_scroller_child_pos_set(wd->scr, x, y); + return EINA_TRUE; +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->scr, "elm,action,focus", "elm"); + evas_object_focus_set(wd->scr, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->scr, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->scr, EINA_FALSE); + } +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->scr) + { + Evas_Object *edj; + const char *str; + + elm_smart_scroller_object_theme_set(obj, wd->scr, + wd->widget_name, wd->widget_base, + elm_widget_style_get(obj)); +// edje_object_scale_set(wd->scr, elm_widget_scale_get(obj) * _elm_config->scale); + edj = elm_smart_scroller_edje_object_get(wd->scr); + str = edje_object_data_get(edj, "focus_highlight"); + if ((str) && (!strcmp(str, "on"))) + elm_widget_highlight_in_theme_set(obj, EINA_TRUE); + else + elm_widget_highlight_in_theme_set(obj, EINA_FALSE); + } + _sizing_eval(obj); +} + +static Eina_Bool +_elm_scroller_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *cur; + + if ((!wd) || (!wd->content)) + return EINA_FALSE; + + cur = wd->content; + + /* Try Focus cycle in subitem */ + if ((elm_widget_can_focus_get(cur)) || (elm_widget_child_can_focus_get(cur))) + return elm_widget_focus_next_get(cur, dir, next); + + /* Return */ + *next = (Evas_Object *)obj; + return !elm_widget_focus_get(obj); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_emit(elm_smart_scroller_edje_object_get(wd->scr), + emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_callback_add(elm_smart_scroller_edje_object_get(wd->scr), + emission, source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_del_full( + elm_smart_scroller_edje_object_get(wd->scr), emission, source, + func_cb, data); +} + +static void +_show_region_hook(void *data, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord x, y, w, h; + if (!wd) return; + elm_widget_show_region_get(obj, &x, &y, &w, &h); + if (wd->scr) + elm_smart_scroller_child_region_show(wd->scr, x, y, w, h); +} + +static void +_focus_region_hook(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (wd->scr) + elm_smart_scroller_child_region_show(wd->scr, x, y, w, h); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord vw, vh, minw, minh, maxw, maxh, w, h, vmw, vmh; + double xw, yw; + + if (!wd) return; + evas_object_size_hint_min_get(wd->content, &minw, &minh); + evas_object_size_hint_max_get(wd->content, &maxw, &maxh); + evas_object_size_hint_weight_get(wd->content, &xw, &yw); + if (wd->scr) + { + elm_smart_scroller_child_viewport_size_get(wd->scr, &vw, &vh); + if (xw > 0.0) + { + if ((minw > 0) && (vw < minw)) vw = minw; + else if ((maxw > 0) && (vw > maxw)) vw = maxw; + } + else if (minw > 0) vw = minw; + if (yw > 0.0) + { + if ((minh > 0) && (vh < minh)) vh = minh; + else if ((maxh > 0) && (vh > maxh)) vh = maxh; + } + else if (minh > 0) vh = minh; + evas_object_resize(wd->content, vw, vh); + w = -1; + h = -1; + edje_object_size_min_calc(elm_smart_scroller_edje_object_get(wd->scr), &vmw, &vmh); + if (wd->min_w) w = vmw + minw; + if (wd->min_h) h = vmh + minh; + evas_object_size_hint_max_get(obj, &maxw, &maxh); + if ((maxw > 0) && (w > maxw)) w = maxw; + if ((maxh > 0) && (h > maxh)) h = maxh; + evas_object_size_hint_min_set(obj, w, h); + } +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + + if (!wd) return; + if (sub == wd->content) + { + elm_widget_on_show_region_hook_set(wd->content, NULL, NULL); + evas_object_event_callback_del_full (sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->content = NULL; + _sizing_eval(obj); + } + else if (sub == wd->scr) + wd->scr = NULL; +} + +static void +_hold_on(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + if (wd->scr) + elm_smart_scroller_hold_set(wd->scr, 1); +} + +static void +_hold_off(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + if (wd->scr) + elm_smart_scroller_hold_set(wd->scr, 0); +} + +static void +_freeze_on(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + if (wd->scr) + elm_smart_scroller_freeze_set(wd->scr, 1); +} + +static void +_freeze_off(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + if (wd->scr) + elm_smart_scroller_freeze_set(wd->scr, 0); +} + +static void +_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_edge_left(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_EDGE_LEFT, NULL); +} + +static void +_edge_right(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_EDGE_RIGHT, NULL); +} + +static void +_edge_top(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_EDGE_TOP, NULL); +} + +static void +_edge_bottom(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_EDGE_BOTTOM, NULL); +} + +static void +_scroll(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_SCROLL, NULL); +} + +static void +_scroll_anim_start(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_SCROLL_ANIM_START, NULL); +} + +static void +_scroll_anim_stop(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_SCROLL_ANIM_STOP, NULL); +} + +static void +_scroll_drag_start(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_SCROLL_DRAG_START, NULL); +} + +static void +_scroll_drag_stop(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + evas_object_smart_callback_call(data, SIG_SCROLL_DRAG_STOP, NULL); +} + +/** + * Add a new scroller to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Scroller + */ +EAPI Evas_Object * +elm_scroller_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + Evas_Coord minw, minh; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "scroller"); + elm_widget_type_set(obj, "scroller"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + elm_widget_focus_next_hook_set(obj, _elm_scroller_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + elm_widget_focus_region_hook_set(obj, _focus_region_hook); + + wd->widget_name = eina_stringshare_add("scroller"); + wd->widget_base = eina_stringshare_add("base"); + + wd->scr = elm_smart_scroller_add(e); + elm_smart_scroller_widget_set(wd->scr, obj); + _theme_hook(obj); + elm_widget_resize_object_set(obj, wd->scr); + evas_object_event_callback_add(wd->scr, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + + edje_object_size_min_calc(elm_smart_scroller_edje_object_get(wd->scr), &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_event_callback_add(obj, EVAS_CALLBACK_RESIZE, _resize, obj); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + evas_object_smart_callback_add(obj, "scroll-hold-on", _hold_on, obj); + evas_object_smart_callback_add(obj, "scroll-hold-off", _hold_off, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-on", _freeze_on, obj); + evas_object_smart_callback_add(obj, "scroll-freeze-off", _freeze_off, obj); + + evas_object_smart_callback_add(wd->scr, "edge,left", _edge_left, obj); + evas_object_smart_callback_add(wd->scr, "edge,right", _edge_right, obj); + evas_object_smart_callback_add(wd->scr, "edge,top", _edge_top, obj); + evas_object_smart_callback_add(wd->scr, "edge,bottom", _edge_bottom, obj); + evas_object_smart_callback_add(wd->scr, "scroll", _scroll, obj); + evas_object_smart_callback_add(wd->scr, "animate,start", _scroll_anim_start, obj); + evas_object_smart_callback_add(wd->scr, "animate,stop", _scroll_anim_stop, obj); + evas_object_smart_callback_add(wd->scr, "drag,start", _scroll_drag_start, obj); + evas_object_smart_callback_add(wd->scr, "drag,stop", _scroll_drag_stop, obj); + + _sizing_eval(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +Evas_Object * +_elm_scroller_edje_object_get(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return elm_smart_scroller_edje_object_get(wd->scr); +} + +/** + * Set the content of the scroller widget (the object to be scrolled around). + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_scroller_content_unset() function. + * + * @param obj The scroller object + * @param content The new content object + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_content_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->content == content) return; + if (wd->content) evas_object_del(wd->content); + wd->content = content; + if (content) + { + elm_widget_on_show_region_hook_set(content, _show_region_hook, obj); + elm_widget_sub_object_add(obj, content); + if (wd->scr) + elm_smart_scroller_child_set(wd->scr, content); + evas_object_event_callback_add(content, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + } + _sizing_eval(obj); +} + +/** + * Get the content of the scroller widget + * + * Return the content object which is set for this widget + * + * @param obj The slider object + * @return The content that is being used + * + * @ingroup Scroller + */ +EAPI Evas_Object * +elm_scroller_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->content; +} + +/** + * Unset the content of the scroller widget + * + * Unparent and return the content object which was set for this widget + * + * @param obj The slider object + * @return The content that was being used + * + * @ingroup Scroller + */ +EAPI Evas_Object * +elm_scroller_content_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *content; + if (!wd) return NULL; + if (!wd->content) return NULL; + content = wd->content; + elm_widget_sub_object_del(obj, wd->content); + edje_object_part_unswallow(wd->scr, wd->content); + wd->content = NULL; + return content; +} + +/** + * Set custom theme elements for the scroller + * + * @param obj The scroller object + * @param widget The widget name to use (default is "scroller") + * @param base The base name to use (default is "base") + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_custom_widget_base_theme_set(Evas_Object *obj, const char *widget, const char *base) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(widget); + EINA_SAFETY_ON_NULL_RETURN(base); + if (eina_stringshare_replace(&wd->widget_name, widget) | + eina_stringshare_replace(&wd->widget_base, base)) + _theme_hook(obj); +} + +/** + * Make the scroller minimum size limited to the minimum size of the content + * + * By default the scroller will be as small as its design allows, irrespective + * of its content. This will make the scroller minimum size the right size + * horizontally and/or vertically to perfectly fit its content. + * + * @param obj The scroller object + * @param w Enable limiting minimum size horizontally + * @param h Enable limiting minimum size vertically + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_content_min_limit(Evas_Object *obj, Eina_Bool w, Eina_Bool h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->min_w = w; + wd->min_h = h; + _sizing_eval(obj); +} + +/** + * Show a specific virtual region within the scroller content object + * + * This will ensure all (or part if it does not fit) of the designated + * region in the virtual content object (0, 0 starting at the top-left of the + * virtual content object) is shown within the scroller. + * + * @param obj The scroller object + * @param x X coordinate of the region + * @param y Y coordinate of the region + * @param w Width of the region + * @param h Height of the region + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_region_show(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->scr)) return; + elm_smart_scroller_child_region_show(wd->scr, x, y, w, h); +} + +/** + * Set the scroller scrollbar policy + * + * This sets the scrollbar visibility policy for the given scroller. + * ELM_SMART_SCROLLER_POLICY_AUTO means the scrollber is made visible if it + * is needed, and otherwise kept hidden. ELM_SMART_SCROLLER_POLICY_ON turns + * it on all the time, and ELM_SMART_SCROLLER_POLICY_OFF always keeps it off. + * This applies respectively for the horizontal and vertical scrollbars. + * + * @param obj The scroller object + * @param policy_h Horizontal scrollbar policy + * @param policy_v Vertical scrollbar policy + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_policy_set(Evas_Object *obj, Elm_Scroller_Policy policy_h, Elm_Scroller_Policy policy_v) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + const Elm_Scroller_Policy map[3] = + { + ELM_SMART_SCROLLER_POLICY_AUTO, + ELM_SMART_SCROLLER_POLICY_ON, + ELM_SMART_SCROLLER_POLICY_OFF + }; + if ((!wd) || (!wd->scr)) return; + if ((policy_h >= 3) || (policy_v >= 3)) return; + elm_smart_scroller_policy_set(wd->scr, map[policy_h], map[policy_v]); +} + +EAPI void +elm_scroller_policy_get(const Evas_Object *obj, Elm_Scroller_Policy *policy_h, Elm_Scroller_Policy *policy_v) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->scr)) return; + elm_smart_scroller_policy_get(wd->scr, + (Elm_Smart_Scroller_Policy *) policy_h, + (Elm_Smart_Scroller_Policy *) policy_v); +} + +/** + * Get the currently visible content region + * + * This gets the current region in the content object that is visible through + * the scroller. Also see elm_scroller_region_show(). The region co-ordinates + * are returned in the @p x, @p y, @p w, @p h values pointed to. + * + * @param obj The scroller object + * @param x X coordinate of the region + * @param y Y coordinate of the region + * @param w Width of the region + * @param h Height of the region + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_region_get(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->scr)) return; + if ((x) || (y)) elm_smart_scroller_child_pos_get(wd->scr, x, y); + if ((w) || (h)) elm_smart_scroller_child_viewport_size_get(wd->scr, w, h); +} + +/** + * Get the size of the content child object + * + * This gets the size of the child object of the scroller. Actually the + * content of a scroller doesn't specifically need to be an actual object + * as it can be virtual and defined purely by callbacks. + * + * @param obj The scroller object + * @param w Width return + * @param h Height return + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_child_size_get(const Evas_Object *obj, Evas_Coord *w, Evas_Coord *h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_geometry_get(wd->content, NULL, NULL, w, h); +} + +/** + * Set bouncing behavior + * + * When scrolling, the scroller may "bounce" when reaching an edge of the child + * object. This is a visual way to indicate the end has been reached. This is + * enabled by default for both axes. This will set if it is enabled for that + * axis with the boolean parameters for each axis. + * + * @param obj The scroller object + * @param h_bounce Will the scroller bounce horizontally or not + * @param v_bounce Will the scroller bounce vertically or not + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->scr)) return; + elm_smart_scroller_bounce_allow_set(wd->scr, h_bounce, v_bounce); +} + +/** + * Get the bounce mode + * + * @param obj The Scroller object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_bounce_get(const Evas_Object *obj, Eina_Bool *h_bounce, Eina_Bool *v_bounce) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_smart_scroller_bounce_allow_get(wd->scr, h_bounce, v_bounce); +} + +/** + * Set scroll page size relative to viewport size. + * + * The scroller is capable of limiting scrolling by the user to "pages". That + * is to jump by and only show a "whole page" at a time as if the continuous + * area of the scroller content is split into page sized pieces. This sets + * the size of a page relative to the viewport of the scroller. 1.0 is "1 + * viewport" is size (horizontally or vertically). 0.0 turns it off in that + * axis. This is mutually exclusive with page size + * (see elm_scroller_page_size_set() for more information). Likewise 0.5 + * is "half a viewport". Sane usable valus are normally between 0.0 and 1.0 + * including 1.0. If you only want 1 axis to be page "limited", use 0.0 for + * the other axis. + * + * @param obj The scroller object + * @param h_pagerel The horizontal page relative size + * @param v_pagerel The vertical page relative size + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_page_relative_set(Evas_Object *obj, double h_pagerel, double v_pagerel) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->pagerel_h = h_pagerel; + wd->pagerel_v = v_pagerel; + if (wd->scr) + elm_smart_scroller_paging_set(wd->scr, wd->pagerel_h, wd->pagerel_v, + wd->pagesize_h, wd->pagesize_v); +} + +/** + * Set scroll page size. + * + * See also elm_scroller_page_relative_set(). This, instead of a page size + * being relative to the viewport, sets it to an absolute fixed value, with + * 0 turning it off for that axis. + * + * @param obj The scroller object + * @param h_pagesize The horizontal page size + * @param v_pagesize The vertical page size + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_page_size_set(Evas_Object *obj, Evas_Coord h_pagesize, Evas_Coord v_pagesize) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->pagesize_h = h_pagesize; + wd->pagesize_v = v_pagesize; + if (wd->scr) + elm_smart_scroller_paging_set(wd->scr, wd->pagerel_h, wd->pagerel_v, + wd->pagesize_h, wd->pagesize_v); +} + +/** + * Show a specific virtual region within the scroller content object. + * + * This will ensure all (or part if it does not fit) of the designated + * region in the virtual content object (0, 0 starting at the top-left of the + * virtual content object) is shown within the scroller. Unlike + * elm_scroller_region_show(), this allow the scroller to "smoothly slide" + * to this location (if configuration in general calls for transitions). It + * may not jump immediately to the new location and make take a while and + * show other content along the way. + * + * @param obj The scroller object + * @param x X coordinate of the region + * @param y Y coordinate of the region + * @param w Width of the region + * @param h Height of the region + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_region_bring_in(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if ((!wd) || (!wd->scr)) return; + elm_smart_scroller_region_bring_in(wd->scr, x, y, w, h); +} + + +/** + * Set event propagation on a scroller + * + * This enables or disabled event propagation from the scroller content to + * the scroller and its parent. By default event propagation is disabled. + * + * @param obj The scroller object + * @param propagation If propagation is enabled or not + * + * @ingroup Scroller + */ +EAPI void +elm_scroller_propagate_events_set(Evas_Object *obj, Eina_Bool propagation) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + evas_object_propagate_events_set(wd->scr, propagation); +} + +/** + * Get event propagation for a scroller + * + * This gets the event propagation for a scroller. See + * elm_scroller_propagate_events_set() for more information + * + * @param obj The scroller object + * @return The propagation state + * + * @ingroup Scroller + */ +EAPI Eina_Bool +elm_scroller_propagate_events_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + + return evas_object_propagate_events_get(wd->scr); +} diff --git a/src/lib/elm_separator.c b/src/lib/elm_separator.c new file mode 100644 index 0000000..6580bd3 --- /dev/null +++ b/src/lib/elm_separator.c @@ -0,0 +1,130 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Separator Separator + * + * A separator is a widget that adds a very thin object to separate other objects. + * A separator can be vertical or horizontal. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *sep; + Eina_Bool horizontal; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->horizontal) + _elm_theme_object_set(obj, wd->sep, "separator", "horizontal", elm_widget_style_get(obj)); + else + _elm_theme_object_set(obj, wd->sep, "separator", "vertical", elm_widget_style_get(obj)); + edje_object_scale_set(wd->sep, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + edje_object_size_min_calc(wd->sep, &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); + evas_object_size_hint_align_set(obj, maxw, maxh); +} + +/** + * Add a separator object to @p parent + * + * @param parent The parent object + * + * @return The separator object, or NULL upon failure + * + * @ingroup Separator + */ +EAPI Evas_Object * +elm_separator_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "separator"); + wd->horizontal = EINA_FALSE; + elm_widget_type_set(obj, "separator"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->sep = edje_object_add(e); + _elm_theme_object_set(obj, wd->sep, "separator", "vertical", "default"); + elm_widget_resize_object_set(obj, wd->sep); + _sizing_eval(obj); + return obj; +} + +/** + * Set the horizontal mode of a separator object + * + * @param obj The separator object + * @param horizontal If true, the separator is horizontal + * + * @ingroup Separator + */ +EAPI void +elm_separator_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + horizontal = !!horizontal; + if (wd->horizontal == horizontal) return; + wd->horizontal = horizontal; + _theme_hook(obj); +} + +/** + * Get the horizontal mode of a separator object + * + * @param obj The separator object + * @return If true, the separator is horizontal + * + * @ingroup Separator + */ +EAPI Eina_Bool +elm_separator_horizontal_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->horizontal; +} diff --git a/src/lib/elm_slider.c b/src/lib/elm_slider.c new file mode 100644 index 0000000..681298b --- /dev/null +++ b/src/lib/elm_slider.c @@ -0,0 +1,1142 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Slider Slider + * + * The slider adds a dragable “slider” widget for selecting the value of + * something within a range. + * + * Signals that you can add callbacks for are: + * + * changed - Whenever the slider value is changed by the user. + * + * delay,changed - A short time after the value is changed by the user. + * This will be called only when the user stops dragging for a very short + * period or when they release their finger/mouse, so it avoids possibly + * expensive reactions to the value change. + * + * slider,drag,start - dragging the slider indicator around has started + * + * slider,drag,stop - dragging the slider indicator around has stopped + * + * A slider can be horizontal or vertical. It can contain an Icon and has a + * primary label as well as a units label (that is formatted with floating + * point values and thus accepts a printf-style format string, like + * “%1.2f units”. There is also an indicator string that may be somewhere + * else (like on the slider itself) that also accepts a format string like + * units. Label, Icon Unit and Indicator strings/objects are optional. + * + * A slider may be inverted which means values invert, with high vales being + * on the left or top and low values on the right or bottom (as opposed to + * normally being low on the left or top and high on the bottom and right). + * + * The slider should have its minimum and maximum values set by the + * application with elm_slider_min_max_set() and value should also be set by + * the application before use with elm_slider_value_set(). The span of the + * slider is its length (horizontally or vertically). This will be scaled by + * the object or applications scaling factor. At any point code can query the + * slider for its value with elm_slider_value_get(). + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *slider; + Evas_Object *icon; + Evas_Object *end; + Evas_Object *spacer; + const char *label; + const char *units; + const char *indicator; + const char *(*indicator_format_func)(double val); + Eina_Bool horizontal : 1; + Eina_Bool inverted : 1; + Eina_Bool indicator_show : 1; + double val, val_min, val_max; + Ecore_Timer *delay; + Evas_Coord size; +}; + +#define ELM_SLIDER_INVERTED_FACTOR (-1.0) + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _units_set(Evas_Object *obj); +static void _val_set(Evas_Object *obj); +static void _indicator_set(Evas_Object *obj); +static void _on_focus_hook(void *data, Evas_Object *obj); +static void _drag_up(void *data, Evas_Object *obj, + const char *emission, const char *source); +static void _drag_down(void *data, Evas_Object *obj, + const char *emission, const char *source); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); +static void _spacer_cb(void *data, Evas * e, Evas_Object * obj, void *event_info); + +static const char SIG_CHANGED[] = "changed"; +static const char SIG_DELAY_CHANGED[] = "delay,changed"; +static const char SIG_DRAG_START[] = "slider,drag,start"; +static const char SIG_DRAG_STOP[] = "slider,drag,stop"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_CHANGED, ""}, + {SIG_DELAY_CHANGED, ""}, + {SIG_DRAG_START, ""}, + {SIG_DRAG_STOP, ""}, + {NULL, NULL} +}; + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + Evas_Event_Mouse_Wheel *mev; + Evas_Event_Key_Down *ev; + Widget_Data *wd; + + wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + + if (type == EVAS_CALLBACK_KEY_DOWN) goto key_down; + else if (type != EVAS_CALLBACK_MOUSE_WHEEL) return EINA_FALSE; + + mev = event_info; + if (mev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + + if (mev->z < 0) _drag_up(obj, NULL, NULL, NULL); + else _drag_down(obj, NULL, NULL, NULL); + mev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + + key_down: + ev = event_info; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + if ((!strcmp(ev->keyname, "Left")) + || (!strcmp(ev->keyname, "KP_Left"))) + { + if (!wd->horizontal) return EINA_FALSE; + if (!wd->inverted) _drag_down(obj, NULL, NULL, NULL); + else _drag_up(obj, NULL, NULL, NULL); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "Right")) + || (!strcmp(ev->keyname, "KP_Right"))) + { + if (!wd->horizontal) return EINA_FALSE; + if (!wd->inverted) _drag_up(obj, NULL, NULL, NULL); + else _drag_down(obj, NULL, NULL, NULL); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "Up")) || (!strcmp(ev->keyname, "KP_Up"))) + { + if (wd->horizontal) return EINA_FALSE; + if (wd->inverted) _drag_up(obj, NULL, NULL, NULL); + else _drag_down(obj, NULL, NULL, NULL); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if ((!strcmp(ev->keyname, "Down")) || (!strcmp(ev->keyname, "KP_Down"))) + { + if (wd->horizontal) return EINA_FALSE; + if (wd->inverted) _drag_down(obj, NULL, NULL, NULL); + else _drag_up(obj, NULL, NULL, NULL); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else return EINA_FALSE; +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->label) eina_stringshare_del(wd->label); + if (wd->indicator) eina_stringshare_del(wd->units); + if (wd->delay) ecore_timer_del(wd->delay); + free(wd); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->slider, "elm,action,focus", "elm"); + evas_object_focus_set(wd->slider, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->slider, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->slider, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->horizontal) + _elm_theme_object_set(obj, wd->slider, "slider", "horizontal", elm_widget_style_get(obj)); + else + _elm_theme_object_set(obj, wd->slider, "slider", "vertical", elm_widget_style_get(obj)); + if (wd->icon) + { + edje_object_part_swallow(wd->slider, "elm.swallow.content", wd->icon); + edje_object_signal_emit(wd->slider, "elm,state,icon,visible", "elm"); + } + if (wd->end) + edje_object_signal_emit(wd->slider, "elm,state,end,visible", "elm"); + else + edje_object_signal_emit(wd->slider, "elm,state,end,hidden", "elm"); + if (wd->label) + { + edje_object_part_text_set(wd->slider, "elm.text", wd->label); + edje_object_signal_emit(wd->slider, "elm,state,text,visible", "elm"); + } + + if (wd->units) + edje_object_signal_emit(wd->slider, "elm,state,units,visible", "elm"); + + if (wd->horizontal) + evas_object_size_hint_min_set(wd->spacer, (double)wd->size * elm_widget_scale_get(obj) * _elm_config->scale, 1); + else + evas_object_size_hint_min_set(wd->spacer, 1, (double)wd->size * elm_widget_scale_get(obj) * _elm_config->scale); + + if (wd->inverted) + edje_object_signal_emit(wd->slider, "elm,state,inverted,on", "elm"); + + edje_object_part_swallow(wd->slider, "elm.swallow.bar", wd->spacer); + _units_set(obj); + _indicator_set(obj); + edje_object_message_signal_process(wd->slider); + edje_object_scale_set(wd->slider, elm_widget_scale_get(obj) * _elm_config->scale); + _val_set(obj); + _sizing_eval(obj); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_disabled_get(obj)) + edje_object_signal_emit(wd->slider, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(wd->slider, "elm,state,enabled", "elm"); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->slider, &minw, &minh, minw, minh); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if ((obj != wd->icon) && (obj != wd->end)) return; + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->icon) + { + edje_object_signal_emit(wd->slider, "elm,state,icon,hidden", "elm"); + evas_object_event_callback_del_full + (sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + wd->icon = NULL; + edje_object_message_signal_process(wd->slider); + _sizing_eval(obj); + } + if (sub == wd->end) + { + edje_object_signal_emit(wd->slider, "elm,state,end,hidden", "elm"); + evas_object_event_callback_del_full(sub, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + wd->end = NULL; + edje_object_message_signal_process(wd->slider); + _sizing_eval(obj); + } +} + +static Eina_Bool +_delay_change(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->delay = NULL; + evas_object_smart_callback_call(data, SIG_DELAY_CHANGED, NULL); + return ECORE_CALLBACK_CANCEL; +} + +static void +_val_fetch(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + double posx = 0.0, posy = 0.0, pos = 0.0, val; + if (!wd) return; + edje_object_part_drag_value_get(wd->slider, "elm.dragable.slider", + &posx, &posy); + if (wd->horizontal) pos = posx; + else pos = posy; + if (wd->inverted) pos = 1.0 - pos; + val = (pos * (wd->val_max - wd->val_min)) + wd->val_min; + if (val != wd->val) + { + wd->val = val; + evas_object_smart_callback_call(obj, SIG_CHANGED, NULL); + if (wd->delay) ecore_timer_del(wd->delay); + wd->delay = ecore_timer_add(0.2, _delay_change, obj); + } +} + +static void +_val_set(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + double pos; + if (!wd) return; + if (wd->val_max > wd->val_min) + pos = (wd->val - wd->val_min) / (wd->val_max - wd->val_min); + else + pos = 0.0; + if (pos < 0.0) pos = 0.0; + else if (pos > 1.0) pos = 1.0; + if (wd->inverted) pos = 1.0 - pos; + edje_object_part_drag_value_set(wd->slider, "elm.dragable.slider", pos, pos); +} + +static void +_units_set(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->units) + { + char buf[1024]; + + snprintf(buf, sizeof(buf), wd->units, wd->val); + edje_object_part_text_set(wd->slider, "elm.units", buf); + } + else + edje_object_part_text_set(wd->slider, "elm.units", NULL); +} + +static void +_indicator_set(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->indicator_format_func) + { + const char *buf; + buf = wd->indicator_format_func(wd->val); + edje_object_part_text_set(wd->slider, "elm.indicator", buf); + } + else if (wd->indicator) + { + char buf[1024]; + snprintf(buf, sizeof(buf), wd->indicator, wd->val); + edje_object_part_text_set(wd->slider, "elm.indicator", buf); + } + else + edje_object_part_text_set(wd->slider, "elm.indicator", NULL); +} + +static void +_drag(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + _val_fetch(data); + _units_set(data); + _indicator_set(data); +} + +static void +_drag_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + _val_fetch(data); + evas_object_smart_callback_call(data, SIG_DRAG_START, NULL); + _units_set(data); + _indicator_set(data); + elm_widget_scroll_hold_push(data); +} + +static void +_drag_stop(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + _val_fetch(data); + evas_object_smart_callback_call(data, SIG_DRAG_STOP, NULL); + _units_set(data); + _indicator_set(data); + elm_widget_scroll_hold_pop(data); +} + +static void +_drag_step(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + _val_fetch(data); + _units_set(data); + _indicator_set(data); +} + +static void +_drag_up(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + double step; + Widget_Data *wd; + + wd = elm_widget_data_get(data); + step = 0.05; + + if (wd->inverted) step *= ELM_SLIDER_INVERTED_FACTOR; + + edje_object_part_drag_step(wd->slider, "elm.dragable.slider", step, step); +} + +static void +_drag_down(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + double step; + Widget_Data *wd; + + wd = elm_widget_data_get(data); + step = -0.05; + + if (wd->inverted) step *= ELM_SLIDER_INVERTED_FACTOR; + + edje_object_part_drag_step(wd->slider, "elm.dragable.slider", step, step); +} + +static void +_spacer_cb(void *data, Evas *e, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Event_Mouse_Down *ev = event_info; + Evas_Coord x, y, w, h; + double button_x, button_y; + + evas_object_geometry_get(wd->spacer, &x, &y, &w, &h); + edje_object_part_drag_value_get(wd->slider, "elm.dragable.slider", &button_x, &button_y); + if (wd->horizontal) + { + button_x = ((double)ev->output.x - (double)x) / (double)w; + if (button_x > 1) button_x = 1; + if (button_x < 0) button_x = 0; + } + else + { + button_y = ((double)ev->output.y - (double)y) / (double)h; + if (button_y > 1) button_y = 1; + if (button_y < 0) button_y = 0; + } + edje_object_part_drag_value_set(wd->slider, "elm.dragable.slider", button_x, button_y); + evas_event_feed_mouse_cancel(e, 0, NULL); + evas_event_feed_mouse_down(e, 1, EVAS_BUTTON_NONE, 0, NULL); +} + +/** + * Add a new slider to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Slider + */ +EAPI Evas_Object * +elm_slider_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "slider"); + elm_widget_type_set(obj, "slider"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->horizontal = EINA_TRUE; + wd->indicator_show = EINA_TRUE; + wd->val = 0.0; + wd->val_min = 0.0; + wd->val_max = 1.0; + + wd->slider = edje_object_add(e); + _elm_theme_object_set(obj, wd->slider, "slider", "horizontal", "default"); + elm_widget_resize_object_set(obj, wd->slider); + edje_object_signal_callback_add(wd->slider, "drag", "*", _drag, obj); + edje_object_signal_callback_add(wd->slider, "drag,start", "*", _drag_start, obj); + edje_object_signal_callback_add(wd->slider, "drag,stop", "*", _drag_stop, obj); + edje_object_signal_callback_add(wd->slider, "drag,step", "*", _drag_step, obj); + edje_object_signal_callback_add(wd->slider, "drag,page", "*", _drag_stop, obj); +// edje_object_signal_callback_add(wd->slider, "drag,set", "*", _drag_stop, obj); + edje_object_part_drag_value_set(wd->slider, "elm.dragable.slider", 0.0, 0.0); + + wd->spacer = evas_object_rectangle_add(e); + evas_object_color_set(wd->spacer, 0, 0, 0, 0); + evas_object_pass_events_set(wd->spacer, EINA_TRUE); + elm_widget_sub_object_add(obj, wd->spacer); + edje_object_part_swallow(wd->slider, "elm.swallow.bar", wd->spacer); + evas_object_event_callback_add(wd->spacer, EVAS_CALLBACK_MOUSE_DOWN, _spacer_cb, obj); + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + _sizing_eval(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Set the label of the slider + * + * @param obj The slider object + * @param label The text label string in UTF-8 + * + * @ingroup Slider + */ +EAPI void +elm_slider_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->label, label); + if (label) + { + edje_object_signal_emit(wd->slider, "elm,state,text,visible", "elm"); + edje_object_message_signal_process(wd->slider); + } + else + { + edje_object_signal_emit(wd->slider, "elm,state,text,hidden", "elm"); + edje_object_message_signal_process(wd->slider); + } + edje_object_part_text_set(wd->slider, "elm.text", label); + _sizing_eval(obj); +} + +/** + * Get the label of the slider + * + * @param obj The slider object + * @return The text label string in UTF-8 + * + * @ingroup Slider + */ +EAPI const char * +elm_slider_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the icon object (leftmost widget) of the slider object. + * + * Once the icon object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_slider_icon_unset() function. + * + * @param obj The slider object + * @param icon The icon object + * + * @note If the object being set does not have minimum size hints set, + * it won't get properly displayed. + * + * @ingroup Slider + */ +EAPI void +elm_slider_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->icon == icon) return; + if (wd->icon) evas_object_del(wd->icon); + wd->icon = icon; + if (icon) + { + elm_widget_sub_object_add(obj, icon); + evas_object_event_callback_add(icon, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->slider, "elm.swallow.icon", icon); + edje_object_signal_emit(wd->slider, "elm,state,icon,visible", "elm"); + edje_object_message_signal_process(wd->slider); + } + _sizing_eval(obj); +} + +/** + * Unset the leftmost widget of the slider, unparenting and + * returning it. + * + * @param obj The slider object + * @return the previously set icon sub-object of this slider, on + * success. + * + * @see elm_slider_icon_set() + * + * @ingroup Slider + */ +EAPI Evas_Object * +elm_slider_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *ret = NULL; + if (!wd) return NULL; + if (wd->icon) + { + elm_widget_sub_object_del(obj, wd->icon); + ret = wd->icon; + edje_object_part_unswallow(wd->slider, wd->icon); + edje_object_signal_emit(wd->slider, "elm,state,icon,hidden", "elm"); + wd->icon = NULL; + _sizing_eval(obj); + } + return ret; +} + +/** + * Get the icon object of the slider object. This object is owned by + * the scrolled entry and should not be modified. + * + * @param obj The slider object + * @return The icon object + * + * @ingroup Slider + */ +EAPI Evas_Object * +elm_slider_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->icon; +} + +/** + * Set the length of the dragable region of the slider + * + * This sets the minimum width or height (depending on orientation) of the + * area of the slider that allows the slider to be dragged around. This in + * turn affects the objects minimum size (along with icon label and unit + * text). Note that this will also get multiplied by the scale factor. + * + * @param obj The slider object + * @param size The length of the slider area + * + * @ingroup Slider + */ +EAPI void +elm_slider_span_size_set(Evas_Object *obj, Evas_Coord size) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->size == size) return; + wd->size = size; + if (wd->horizontal) + evas_object_size_hint_min_set(wd->spacer, (double)wd->size * elm_widget_scale_get(obj) * _elm_config->scale, 1); + else + evas_object_size_hint_min_set(wd->spacer, 1, (double)wd->size * elm_widget_scale_get(obj) * _elm_config->scale); + if (wd->indicator_show) + edje_object_signal_emit(wd->slider, "elm,state,val,show", "elm"); + else + edje_object_signal_emit(wd->slider, "elm,state,val,hide", "elm"); + edje_object_part_swallow(wd->slider, "elm.swallow.bar", wd->spacer); + _sizing_eval(obj); +} + +/** + * Get the length of the dragable region of the slider + * + * This gets the minimum width or height (depending on orientation) of + * the area of the slider that allows the slider to be dragged + * around. Note that this will also get multiplied by the scale + * factor. + * + * @param obj The slider object + * @return The length of the slider area + * + * @ingroup Slider + */ +EAPI Evas_Coord +elm_slider_span_size_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->size; +} + +/** + * Set the format string of the unit area + * + * If NULL, this disabls the unit area display. If not it sets the format + * string for the unit text. The unit text is provided a floating point + * value, so the unit text can display up to 1 floating point value. Note that + * this is optional. Use a format string such as "%1.2f meters" for example. + * + * @param obj The slider object + * @param units The format string for the units display + * + * @ingroup Slider + */ +EAPI void +elm_slider_unit_format_set(Evas_Object *obj, const char *units) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->units, units); + if (units) + { + edje_object_signal_emit(wd->slider, "elm,state,units,visible", "elm"); + edje_object_message_signal_process(wd->slider); + } + else + { + edje_object_signal_emit(wd->slider, "elm,state,units,hidden", "elm"); + edje_object_message_signal_process(wd->slider); + } + _units_set(obj); + _sizing_eval(obj); +} + +/** + * Get the format string for the unit area + * + * The slider may also display a value (the value of the slider) somewhere + * (for example above the slider knob that is dragged around). This sets the + * format string for this. See elm_slider_unit_format_set() for more + * information on how this works. + * + * @param obj The slider object + * @return The format string for the unit display. + * + * @ingroup Slider + */ +EAPI const char * +elm_slider_unit_format_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->units; +} + +/** + * Set the format string for the indicator area + * + * The slider may also display a value (the value of the slider) somewhere + * (for example above the slider knob that is dragged around). This sets the + * format string for this. See elm_slider_unit_format_set() for more + * information on how this works. + * + * @param obj The slider object + * @param indicator The format string for the indicator display + * + * @ingroup Slider + */ +EAPI void +elm_slider_indicator_format_set(Evas_Object *obj, const char *indicator) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->indicator, indicator); + _indicator_set(obj); +} + +/** + * Get the format string for the indicator area + * + * The slider may also display a value (the value of the slider) somewhere + * (for example above the slider knob that is dragged around). This sets the + * format string for this. See elm_slider_indicator_format_set() for more + * information on how this works. + * + * @param obj The slider object + * @return The format string for the indicator display. + * + * @ingroup Slider + */ +EAPI const char * +elm_slider_indicator_format_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->indicator; +} + +/** + * Set orientation of the slider + * + * @param obj The slider object + * @param horizontal If set, the slider will be horizontal + * + * @ingroup Slider + */ +EAPI void +elm_slider_horizontal_set(Evas_Object *obj, Eina_Bool horizontal) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + horizontal = !!horizontal; + if (wd->horizontal == horizontal) return; + wd->horizontal = horizontal; + _theme_hook(obj); +} + +/** + * Get orientation of the slider + * + * @param obj The slider object + * @return If @c EINA_TRUE the slider will be horizontal, else it is + * vertical. + * @ingroup Slider + */ +EAPI Eina_Bool +elm_slider_horizontal_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->horizontal; +} + +/** + * Set the minimum and maximum values for the slider + * + * Maximum mut be greater than minimum. + * + * @param obj The slider object + * @param min The minimum value + * @param max The maximum value + * + * @ingroup Slider + */ +EAPI void +elm_slider_min_max_set(Evas_Object *obj, double min, double max) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if ((wd->val_min == min) && (wd->val_max == max)) return; + wd->val_min = min; + wd->val_max = max; + if (wd->val < wd->val_min) wd->val = wd->val_min; + if (wd->val > wd->val_max) wd->val = wd->val_max; + _val_set(obj); + _units_set(obj); + _indicator_set(obj); +} + +/** + * Get the minimum and maximum values for the slider + * + * @param obj The slider object + * @param min The pointer to store minimum value, may be @c NULL. + * @param max The pointer to store maximum value, may be @c NULL. + * + * @ingroup Slider + */ +EAPI void +elm_slider_min_max_get(const Evas_Object *obj, double *min, double *max) +{ + if (min) *min = 0.0; + if (max) *max = 0.0; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (min) *min = wd->val_min; + if (max) *max = wd->val_max; +} + +/** + * Set the value the slider indicates + * + * @param obj The slider object + * @param val The value (must be between min and max for the slider) + * + * @ingroup Slider + */ +EAPI void +elm_slider_value_set(Evas_Object *obj, double val) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->val == val) return; + wd->val = val; + if (wd->val < wd->val_min) wd->val = wd->val_min; + if (wd->val > wd->val_max) wd->val = wd->val_max; + _val_set(obj); + _units_set(obj); + _indicator_set(obj); +} + +/** + * Get the value the slider has + * + * @param obj The slider object + * @return The value of the slider + * + * @ingroup Slider + */ +EAPI double +elm_slider_value_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->val; +} + +/** + * Invert the slider display + * + * Normally the slider will display and interpret values from low to high + * and when horizontal that is left to right. When vertical that is top + * to bottom. This inverts this (so from right to left or bottom to top) if + * inverted is set to 1. + * + * @param obj The slider object + * @param inverted The inverted flag. 1 == inverted, 0 == normal + * + * @ingroup Slider + */ +EAPI void +elm_slider_inverted_set(Evas_Object *obj, Eina_Bool inverted) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + inverted = !!inverted; + if (wd->inverted == inverted) return; + wd->inverted = inverted; + if (wd->inverted) + edje_object_signal_emit(wd->slider, "elm,state,inverted,on", "elm"); + else + edje_object_signal_emit(wd->slider, "elm,state,inverted,off", "elm"); + edje_object_message_signal_process(wd->slider); + _val_set(obj); + _units_set(obj); + _indicator_set(obj); +} + +/** + * Get if the slider display is inverted (backwards) + * + * @param obj The slider object + * @return If @c EINA_TRUE the slider will be inverted. + * @ingroup Slider + */ +EAPI Eina_Bool +elm_slider_inverted_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->inverted; +} + +/** + * Set the format function pointer for the inducator area + * + * Set the callback function to format the indicator string. + * See elm_slider_indicator_format_set() for more info on how this works. + * + * @param obj The slider object + * @param indicator The format string for the indicator display + * @param func The indicator format function + * + * @ingroup Slider + */ +EAPI void +elm_slider_indicator_format_function_set(Evas_Object *obj, const char *(*func)(double val)) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->indicator_format_func = func; + _indicator_set(obj); +} + +/** + * Set the end object (rightmost widget) of the slider object. + * + * Once the end object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_button_end_unset() function. + * + * @param obj The slider object + * @param end The end object + * + * @note If the object being set does not have minimum size hints set, + * it won't get properly displayed. + * + * @ingroup Slider + */ +EAPI void +elm_slider_end_set(Evas_Object *obj, Evas_Object *end) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->end == end) return; + if (wd->end) evas_object_del(wd->end); + wd->end = end; + if (end) + { + elm_widget_sub_object_add(obj, end); + evas_object_event_callback_add(end, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->slider, "elm.swallow.end", end); + edje_object_signal_emit(wd->slider, "elm,state,end,visible", "elm"); + edje_object_message_signal_process(wd->slider); + } + _sizing_eval(obj); +} + +/** + * Unset the rightmost widget of the slider, unparenting and + * returning it. + * + * @param obj The slider object + * @return the previously set end sub-object of this slider, on + * success. + * + * @see elm_slider_end_set() + * + * @ingroup Slider + */ +EAPI Evas_Object * +elm_slider_end_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *ret = NULL; + if (!wd) return NULL; + if (wd->end) + { + elm_widget_sub_object_del(obj, wd->end); + ret = wd->end; + edje_object_part_unswallow(wd->slider, wd->end); + edje_object_signal_emit(wd->slider, "elm,state,end,hidden", "elm"); + wd->end = NULL; + _sizing_eval(obj); + } + return ret; +} + +/** + * Get the end icon object of the slider object. This object is owned + * by the scrolled entry and should not be modified. + * + * @param obj The slider object + * @return The end icon object + * + * @ingroup Slider + */ +EAPI Evas_Object * +elm_slider_end_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->end; +} + +/** + * Set whether to the slider indicator (augmented knob) at all. + * + * @param obj The slider object + * @param show @c EINA_TRUE will make it show it, @c EINA_FALSE will + * let the knob alwayes at default size. + * + * @note It will conflict with elm_slider_indicator_format_set(), if + * you wanted those effects. + * + * @ingroup Slider + */ +EAPI void +elm_slider_indicator_show_set(Evas_Object *obj, Eina_Bool show) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (show) { + wd->indicator_show = EINA_TRUE; + edje_object_signal_emit(wd->slider, "elm,state,val,show", "elm"); + } + else { + wd->indicator_show = EINA_FALSE; + edje_object_signal_emit(wd->slider, "elm,state,val,hide", "elm"); + } +} + +/** + * Get the state of indicator in the slider (if it's being shown or + * not). + * + * @param obj The slider object + * @return @c EINA_TRUE if the indicator is being shown, @c EINA_FALSE + * otherwise. + * + * @ingroup Slider + */ +EAPI Eina_Bool +elm_slider_indicator_show_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->indicator_show; +} + diff --git a/src/lib/elm_slideshow.c b/src/lib/elm_slideshow.c new file mode 100644 index 0000000..79a2b80 --- /dev/null +++ b/src/lib/elm_slideshow.c @@ -0,0 +1,798 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Slideshow slideshow + * + * This object display a list of object (generally a list of images) and some actions like + * next/previous are used to navigate. The animations are defined in the theme, + * consequently new animations can be added without having to update the + * applications. + * + * The slideshow use 2 callbacks to create and delete the objects displayed. When an item + * is displayed the function itc->func.get() is called. This function should create the object, + * for example the object can be an evas_object_image or a photocam. When a object is no more + * displayed the function itc->func.del() is called, the user can delete the dana associated to the item. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Elm_Slideshow_Item +{ + Elm_Widget_Item base; + + Eina_List *l, *l_built; + + const Elm_Slideshow_Item_Class *itc; +}; + +struct _Widget_Data +{ + Evas_Object *slideshow; + + // list of Elm_Slideshow_Item* + Eina_List *items; + Eina_List *items_built; + + Elm_Slideshow_Item *current; + Elm_Slideshow_Item *previous; + + Eina_List *transitions; + const char *transition; + + Ecore_Timer *timer; + double timeout; + Eina_Bool loop:1; + + struct { + const char *current; + Eina_List *list; //list of const char * + } layout; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static Eina_Bool _timer_cb(void *data); +static void _on_focus_hook(void *data, Evas_Object *obj); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + if ((!strcmp(ev->keyname, "Left")) || (!strcmp(ev->keyname, "KP_Left"))) + { + elm_slideshow_previous(obj); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + if ((!strcmp(ev->keyname, "Right")) || (!strcmp(ev->keyname, "KP_Right"))) + { + elm_slideshow_next(obj); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + if ((!strcmp(ev->keyname, "Return")) || + (!strcmp(ev->keyname, "KP_Enter")) || + (!strcmp(ev->keyname, "space"))) + { + if (wd->timeout) + { + if (wd->timer) + { + ecore_timer_del(wd->timer); + wd->timer = NULL; + } + else + elm_slideshow_timeout_set(obj, wd->timeout); + } + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + return EINA_FALSE; +} + +static void +_del_hook(Evas_Object *obj) +{ + const char *layout; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_slideshow_clear(obj); + elm_widget_stringlist_free(wd->transitions); + if (wd->timer) ecore_timer_del(wd->timer); + EINA_LIST_FREE(wd->layout.list, layout) + eina_stringshare_del(layout); + free(wd); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->slideshow, "elm,action,focus", "elm"); + evas_object_focus_set(wd->slideshow, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->slideshow, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->slideshow, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->slideshow, "slideshow", "base", elm_widget_style_get(obj)); + edje_object_scale_set(wd->slideshow, elm_widget_scale_get(obj) * + _elm_config->scale); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + if (!wd) return; + edje_object_size_min_calc(wd->slideshow, &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, minw, minh); +} + + +static Elm_Slideshow_Item* _item_prev_get(Elm_Slideshow_Item* item) +{ + Widget_Data *wd = elm_widget_data_get(item->base.widget); + Elm_Slideshow_Item* prev = eina_list_data_get(eina_list_prev(item->l)); + if((!prev) && (wd->loop)) + prev = eina_list_data_get(eina_list_last(item->l)); + return prev; +} +static Elm_Slideshow_Item* _item_next_get(Elm_Slideshow_Item* item) +{ + Widget_Data *wd = elm_widget_data_get(item->base.widget); + Elm_Slideshow_Item* next = eina_list_data_get(eina_list_next(item->l)); + if((!next) && (wd->loop)) + next = eina_list_data_get(wd->items); + return next; +} + + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + ; +} + +static void +_item_realize(Elm_Slideshow_Item *item) +{ + Elm_Slideshow_Item *_item; + Evas_Object *obj = item->base.widget; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + if ((!item->base.view) && (item->itc->func.get)) + { + item->base.view = item->itc->func.get((void*)item->base.data, obj); + evas_object_smart_member_add(item->base.view, obj); + item->l_built = eina_list_append(NULL, item); + wd->items_built = eina_list_merge(wd->items_built, item->l_built); + evas_object_hide(item->base.view); + } + else if (item->l_built) + wd->items_built = eina_list_demote_list(wd->items_built, item->l_built); + + //pre-create previous and next item + _item = _item_next_get(item); + if ((_item) && (!_item->base.view) && (_item->itc->func.get)) + { + _item->base.view = _item->itc->func.get((void*)_item->base.data, obj); + evas_object_smart_member_add(_item->base.view, obj); + _item->l_built = eina_list_append(NULL, _item); + wd->items_built = eina_list_merge(wd->items_built, _item->l_built); + evas_object_hide(_item->base.view); + } + else if ((_item) && (_item->l_built)) + wd->items_built = eina_list_demote_list(wd->items_built, _item->l_built); + + _item = _item_prev_get(item); + if ((_item) && (!_item->base.view) && (_item->itc->func.get)) + { + _item->base.view = _item->itc->func.get((void*)_item->base.data, obj); + evas_object_smart_member_add(_item->base.view, obj); + _item->l_built = eina_list_append(NULL, _item); + wd->items_built = eina_list_merge(wd->items_built, _item->l_built); + evas_object_hide(_item->base.view); + } + else if ((_item) && (_item->l_built)) + wd->items_built = eina_list_demote_list(wd->items_built, _item->l_built); + + //delete unused items + while (eina_list_count(wd->items_built) > 3) + { + _item = eina_list_data_get(wd->items_built); + wd->items_built = eina_list_remove_list(wd->items_built, wd->items_built); + if(item->itc->func.del) + item->itc->func.del((void*)item->base.data, _item->base.view); + evas_object_del(_item->base.view); + _item->base.view = NULL; + } +} + +static void +_end(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Elm_Slideshow_Item *item; + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + + item = wd->previous; + if(item) + { + edje_object_part_unswallow(NULL, item->base.view); + evas_object_hide(item->base.view); + wd->previous = NULL; + } + + + item = wd->current; + if ((!item) || (!item->base.view)) return; + + _item_realize(item); + edje_object_part_unswallow(NULL, item->base.view); + evas_object_show(item->base.view); + + edje_object_signal_emit(wd->slideshow, "anim,end", "slideshow"); + edje_object_part_swallow(wd->slideshow, "elm.swallow.1", item->base.view); +} + + +static Eina_Bool +_timer_cb(void *data) +{ + Evas_Object *obj = data; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->timer = NULL; + elm_slideshow_next(obj); + return ECORE_CALLBACK_CANCEL; +} + + + +/** + * Add a new slideshow to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Slideshow + */ +EAPI Evas_Object * +elm_slideshow_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "slideshow"); + elm_widget_type_set(obj, "slideshow"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->current = NULL; + wd->previous = NULL; + + wd->slideshow = edje_object_add(e); + _elm_theme_object_set(obj, wd->slideshow, "slideshow", "base", "default"); + evas_object_smart_member_add(wd->slideshow, obj); + elm_widget_resize_object_set(obj, wd->slideshow); + evas_object_show(wd->slideshow); + + wd->transitions = elm_widget_stringlist_get(edje_object_data_get(wd->slideshow, "transitions")); + if (eina_list_count(wd->transitions) > 0) + wd->transition = eina_stringshare_add(eina_list_data_get(wd->transitions)); + + wd->layout.list = elm_widget_stringlist_get(edje_object_data_get(wd->slideshow, "layouts")); + if (eina_list_count(wd->layout.list) > 0) + wd->layout.current = eina_list_data_get(wd->layout.list); + + edje_object_signal_callback_add(wd->slideshow, "end", "slideshow", _end, obj); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + evas_object_event_callback_add(obj, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + + _sizing_eval(obj); + return obj; +} + +/** + * Add a object in the list. The object can be a evas object image or a elm photo for example. + * + * @param obj The slideshow object + * @aram itc Callbacks used to create the object and delete the data associated when the item is deleted. + * @param data Data used by the user to identified the item + * @return Returns The slideshow item + * + * @ingroup Slideshow + */ +EAPI Elm_Slideshow_Item* +elm_slideshow_item_add(Evas_Object *obj, const Elm_Slideshow_Item_Class *itc, const void *data) +{ + Elm_Slideshow_Item *item; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return NULL; + item = elm_widget_item_new(obj, Elm_Slideshow_Item); + item->base.data = data; + item->itc = itc; + item->l = eina_list_append(item->l, item); + + wd->items = eina_list_merge(wd->items, item->l); + + if (!wd->current) elm_slideshow_show(item); + + return item; +} + +/** + * Go to the item + * + * @param obj The slideshow object + * @param item The item + * + * @ingroup Slideshow + */ +EAPI void +elm_slideshow_show(Elm_Slideshow_Item *item) +{ + char buf[1024]; + Elm_Slideshow_Item *next = NULL; + Widget_Data *wd; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + wd = elm_widget_data_get(item->base.widget); + if (!wd) + return; + if (item == wd->current) + return; + + next = item; + evas_object_smart_callback_call(item->base.widget, "changed", next); + _end(item->base.widget, item->base.widget, NULL, NULL); + + if (wd->timer) ecore_timer_del(wd->timer); + if (wd->timeout > 0.0) + wd->timer = ecore_timer_add(wd->timeout, _timer_cb, item->base.widget); + _item_realize(next); + edje_object_part_swallow(wd->slideshow, "elm.swallow.2", next->base.view); + evas_object_show(next->base.view); + snprintf(buf, sizeof(buf), "%s,next", wd->transition); + edje_object_signal_emit(wd->slideshow, buf, "slideshow"); + wd->previous = wd->current; + wd->current = next; +} + +/** + * Go to the next item + * + * @param obj The slideshow object + * + * @ingroup Slideshow + */ +EAPI void +elm_slideshow_next(Evas_Object *obj) +{ + char buf[1024]; + Elm_Slideshow_Item *next = NULL; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + + if (wd->current) + next = _item_next_get(wd->current); + + if ((!next) || (next == wd->current)) return; + evas_object_smart_callback_call(obj, "changed", next); + + _end(obj, obj, NULL, NULL); + + if (wd->timer) ecore_timer_del(wd->timer); + if (wd->timeout > 0.0) + wd->timer = ecore_timer_add(wd->timeout, _timer_cb, obj); + + _item_realize(next); + + edje_object_part_swallow(wd->slideshow, "elm.swallow.2", next->base.view); + evas_object_show(next->base.view); + + snprintf(buf, sizeof(buf), "%s,next", wd->transition); + edje_object_signal_emit(wd->slideshow, buf, "slideshow"); + + wd->previous = wd->current; + wd->current = next; +} + +/** + * Go to the previous item + * + * @param obj The slideshow object + * + * @ingroup Slideshow + */ +EAPI void +elm_slideshow_previous(Evas_Object *obj) +{ + char buf[1024]; + Elm_Slideshow_Item *prev = NULL; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + + if (wd->current) + prev = _item_prev_get(wd->current); + + if ((!prev) || (prev == wd->current)) return; + evas_object_smart_callback_call(obj, "changed", prev); + + _end(obj, obj, NULL, NULL); + + if (wd->timer) ecore_timer_del(wd->timer); + if (wd->timeout > 0.0) + wd->timer = ecore_timer_add(wd->timeout, _timer_cb, obj); + + _item_realize(prev); + + edje_object_part_swallow(wd->slideshow, "elm.swallow.2", prev->base.view); + evas_object_show(prev->base.view); + + snprintf(buf, 1024, "%s,previous", wd->transition); + edje_object_signal_emit(wd->slideshow, buf, "slideshow"); + + wd->previous = wd->current; + wd->current = prev; +} + +/** + * Returns the list of transitions available. + * + * @param obj The slideshow object + * @return Returns the list of transitions (list of const char*) + * + * @ingroup Slideshow + */ +EAPI const Eina_List * +elm_slideshow_transitions_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->transitions; +} + +/** + * Returns the list of layouts available. + * + * @param obj The slideshow object + * @return Returns the list of layout (list of const char*) + * + * @ingroup Slideshow + */ +EAPI const Eina_List * +elm_slideshow_layouts_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->layout.list; +} + +/** + * Set the transition to use + * + * @param obj The slideshow object + * @param transition the new transition + * + * @ingroup Slideshow + */ +EAPI void +elm_slideshow_transition_set(Evas_Object *obj, const char *transition) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->transition, transition); +} + +/** + * Returns the transition to use + * + * @param obj The slideshow object + * @return the transition set + * + * @ingroup Slideshow + */ +EAPI const char * +elm_slideshow_transition_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->transition; +} + +/** + * The slideshow can go to the next item automatically after a few seconds. + * This method set the timeout to use. A timeout <=0 disable the timer. + * + * @param obj The slideshow object + * @param timeout The new timeout + * + * @ingroup Slideshow + */ +EAPI void +elm_slideshow_timeout_set(Evas_Object *obj, double timeout) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->timeout = timeout; + if (wd->timer) ecore_timer_del(wd->timer); + wd->timer = NULL; + if (timeout > 0.0) + wd->timer = ecore_timer_add(timeout, _timer_cb, obj); +} + +/** + * Returns the timeout value + * + * @param obj The slideshow object + * @return Returns the timeout + * + * @ingroup Slideshow + */ +EAPI double +elm_slideshow_timeout_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) -1.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return -1.0; + return wd->timeout; +} + +/** + * Set if the first item should follow the last and vice versa + * + * @param obj The slideshow object + * @param loop if EINA_TRUE, the first item will follow the last and vice versa + * + * @ingroup Slideshow + */ +EAPI void +elm_slideshow_loop_set(Evas_Object *obj, Eina_Bool loop) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->loop = loop; +} + +/** + * Returns the current layout name + * + * @param obj The slideshow object + * @returns Returns the layout name + * + * @ingroup Slideshow + */ +EAPI const char * +elm_slideshow_layout_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->layout.current; +} + +/** + * Set the layout + * + * @param obj The slideshow object + * @param layout the new layout + * + * @ingroup Slideshow + */ +EAPI void +elm_slideshow_layout_set(Evas_Object *obj, const char *layout) +{ + char buf[PATH_MAX]; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + wd->layout.current = layout; + snprintf(buf, sizeof(buf), "layout,%s", layout); + edje_object_signal_emit(wd->slideshow, buf, "slideshow"); +} + +/** + * Return if the first item should follow the last and vice versa + * + * @param obj The slideshow object + * @returns Returns the loop flag + * + * @ingroup Slideshow + */ +EAPI Eina_Bool +elm_slideshow_loop_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->loop; +} + +/** + * Delete all the items + * + * @param obj The slideshow object + * + * @ingroup Slideshow + */ +EAPI void +elm_slideshow_clear(Evas_Object *obj) +{ + Elm_Slideshow_Item *item; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->previous = NULL; + wd->current = NULL; + EINA_LIST_FREE(wd->items_built, item) + { + if (item->itc->func.del) + item->itc->func.del((void*)item->base.data, item->base.view); + evas_object_del(item->base.view); + item->base.view = NULL; + } + + EINA_LIST_FREE(wd->items, item) + { + elm_widget_item_del(item); + } +} + + +/** + * Delete the item + * + * @param item The slideshow item + * + * @ingroup Slideshow + */ +EAPI void +elm_slideshow_item_del(Elm_Slideshow_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + Widget_Data *wd = elm_widget_data_get(item->base.widget); + if (!wd) return; + if (wd->previous == item) wd->previous = NULL; + if (wd->current == item) + { + Eina_List *l = eina_list_data_find_list(wd->items, item); + Eina_List *l2 = eina_list_next(l); + wd->current = NULL; + if (!l2) + l2 = eina_list_nth_list(wd->items, eina_list_count(wd->items) - 1); + if (l2) + elm_slideshow_show(eina_list_data_get(l2)); + } + + wd->items = eina_list_remove_list(wd->items, item->l); + wd->items_built = eina_list_remove_list(wd->items_built, item->l_built); + + if ((item->base.view) && (item->itc->func.del)) + item->itc->func.del((void*)item->base.data, item->base.view); + if (item->base.view) + evas_object_del(item->base.view); + free(item); +} + +/** + * Returns the list of items + * @param obj The slideshow object + * @return Returns the list of items (list of Elm_Slideshow_Item). + * + * @ingroup Slideshow + */ +EAPI const Eina_List * +elm_slideshow_items_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->items; +} + + +/** + * Returns the current item displayed + * + * @param obj The slideshow object + * @return Returns the current item displayed + * + * @ingroup Slideshow + */ +EAPI Elm_Slideshow_Item * +elm_slideshow_item_current_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->current; +} + +/** + * Returns the evas object associated to an item + * + * @param item The slideshow item + * @return Returns the evas object associated to this item + * + * @ingroup Slideshow + */ +EAPI Evas_Object * +elm_slideshow_item_object_get(const Elm_Slideshow_Item * item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->base.view; +} + +/** + * Returns the data associated to an item + * + * @param item The slideshow item + * @return Returns the data associated to this item + * + * @ingroup Slideshow + */ +EAPI void * +elm_slideshow_item_data_get(const Elm_Slideshow_Item * item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_data_get(item); +} diff --git a/src/lib/elm_spinner.c b/src/lib/elm_spinner.c new file mode 100644 index 0000000..3ce2ea3 --- /dev/null +++ b/src/lib/elm_spinner.c @@ -0,0 +1,924 @@ +#include +#include "elm_priv.h" +#include + +/** + * @defgroup Spinner + * + * A spinner is a widget which allows the user to increase or decrease + * numeric values. By default the spinner will not wrap and has a label + * of "%.0f" (just showing the integer value of the double). + * + * A spinner has a label that is formatted with floating + * point values and thus accepts a printf-style format string, like + * “%1.2f units”. + * + * Signals that you can add callbacks for are: + * + * changed - Whenever the spinner value is changed by the user. + * + * delay,changed - A short time after the value is changed by the user. + * This will be called only when the user stops dragging for a very short + * period or when they release their finger/mouse, so it avoids possibly + * expensive reactions to the value change. + */ +typedef struct _Widget_Data Widget_Data; +typedef struct _Elm_Spinner_Special_Value Elm_Spinner_Special_Value; + +struct _Widget_Data +{ + Evas_Object *spinner, *ent; + const char *label; + double val, val_min, val_max, orig_val, step; + double drag_start_pos, spin_speed, interval, first_interval; + Ecore_Timer *delay, *spin; + Eina_List *special_values; + Eina_Bool wrap : 1; + Eina_Bool entry_visible : 1; + Eina_Bool dragging : 1; + Eina_Bool editable : 1; +}; + +struct _Elm_Spinner_Special_Value +{ + double value; + const char *label; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _write_label(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +//static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static Eina_Bool _value_set(Evas_Object *obj, double delta); +static void _on_focus_hook(void *data, Evas_Object *obj); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); + +static void +_del_hook(Evas_Object *obj) +{ + Elm_Spinner_Special_Value *sv; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->label) eina_stringshare_del(wd->label); + if (wd->delay) ecore_timer_del(wd->delay); + if (wd->spin) ecore_timer_del(wd->spin); + if (wd->special_values) + { + EINA_LIST_FREE(wd->special_values, sv) + { + eina_stringshare_del(sv->label); + free(sv); + } + } + free(wd); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_disabled_get(obj)) + edje_object_signal_emit(wd->spinner, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(wd->spinner, "elm,state,enabled", "elm"); +} + +static void +_signal_emit_hook(Evas_Object *obj, const char *emission, const char *source) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_emit(wd->spinner, emission, source); +} + +static void +_signal_callback_add_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_callback_add(wd->spinner, emission, + source, func_cb, data); +} + +static void +_signal_callback_del_hook(Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + edje_object_signal_callback_del_full(wd->spinner, emission, source, + func_cb, data); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->spinner, "spinner", "base", elm_widget_style_get(obj)); + edje_object_part_swallow(wd->spinner, "elm.swallow.entry", wd->ent); + _write_label(obj); + if (elm_widget_focus_get(obj)) + edje_object_signal_emit(wd->spinner, "elm,action,focus", "elm"); + else + edje_object_signal_emit(wd->spinner, "elm,action,unfocus", "elm"); + if (elm_widget_disabled_get(obj)) + edje_object_signal_emit(wd->spinner, "elm,state,disabled", "elm"); + edje_object_message_signal_process(wd->spinner); + edje_object_scale_set(wd->spinner, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->spinner, "elm,action,focus", "elm"); + evas_object_focus_set(wd->spinner, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->spinner, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->spinner, EINA_FALSE); + } +} + +static Eina_Bool +_delay_change(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + wd->delay = NULL; + evas_object_smart_callback_call(data, "delay,changed", NULL); + return ECORE_CALLBACK_CANCEL; +} + +static void +_entry_show(Widget_Data *wd) +{ + char buf[32], fmt[32] = "%0.f"; + + /* try to construct just the format from given label + * completely ignoring pre/post words + */ + if (wd->label) + { + const char *start = strchr(wd->label, '%'); + while (start) + { + /* handle %% */ + if (start[1] != '%') + break; + else + start = strchr(start + 2, '%'); + } + + if (start) + { + const char *itr, *end = NULL; + for (itr = start + 1; *itr != '\0'; itr++) + { + /* allowing '%d' is quite dangerous, remove it? */ + if ((*itr == 'd') || (*itr == 'f')) + { + end = itr + 1; + break; + } + } + + if ((end) && ((size_t)(end - start + 1) < sizeof(fmt))) + { + memcpy(fmt, start, end - start); + fmt[end - start] = '\0'; + } + } + } + snprintf(buf, sizeof(buf), fmt, wd->val); + elm_entry_entry_set(wd->ent, buf); +} + +static void +_write_label(Evas_Object *obj) +{ + Eina_List *l; + Elm_Spinner_Special_Value *sv; + Widget_Data *wd = elm_widget_data_get(obj); + char buf[1024]; + if (!wd) return; + EINA_LIST_FOREACH(wd->special_values, l, sv) + { + if (sv->value == wd->val) + { + snprintf(buf, sizeof(buf), "%s", sv->label); + goto apply; + } + } + if (wd->label) + snprintf(buf, sizeof(buf), wd->label, wd->val); + else + snprintf(buf, sizeof(buf), "%.0f", wd->val); + +apply: + edje_object_part_text_set(wd->spinner, "elm.text", buf); + if (wd->entry_visible) _entry_show(wd); +} + +static Eina_Bool +_value_set(Evas_Object *obj, double delta) +{ + Widget_Data *wd = elm_widget_data_get(obj); + double new_val; + if (!wd) return EINA_FALSE; + new_val = wd->val + delta; + if (wd->wrap) + { + while (new_val < wd->val_min) + new_val = wd->val_max + new_val + 1 - wd->val_min; + while (new_val > wd->val_max) + new_val = wd->val_min + new_val - wd->val_max - 1; + } + else + { + if (new_val < wd->val_min) + new_val = wd->val_min; + else if (new_val > wd->val_max) + new_val = wd->val_max; + } + + if (new_val == wd->val) return EINA_FALSE; + wd->val = new_val; + + evas_object_smart_callback_call(obj, "changed", NULL); + if (wd->delay) ecore_timer_del(wd->delay); + wd->delay = ecore_timer_add(0.2, _delay_change, obj); + + return EINA_TRUE; +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->spinner, &minw, &minh, minw, minh); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +/* +static void +_changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + _sizing_eval(data); +} +*/ + +static void +_val_set(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + double pos = 0.0; + if (!wd) return; + if (wd->val_max > wd->val_min) + pos = ((wd->val - wd->val_min) / (wd->val_max - wd->val_min)); + if (pos < 0.0) pos = 0.0; + else if (pos > 1.0) pos = 1.0; + edje_object_part_drag_value_set(wd->spinner, "elm.dragable.slider", + pos, pos); +} + +static void +_drag(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + double pos = 0.0, offset, delta; + if (!wd) return; + if (wd->entry_visible) return; + edje_object_part_drag_value_get(wd->spinner, "elm.dragable.slider", + &pos, NULL); + offset = wd->step; + delta = (pos - wd->drag_start_pos) * offset; + if (_value_set(data, delta)) _write_label(data); + wd->drag_start_pos = pos; + wd->dragging = 1; +} + +static void +_drag_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + double pos; + if (!wd) return; + edje_object_part_drag_value_get(wd->spinner, "elm.dragable.slider", + &pos, NULL); + wd->drag_start_pos = pos; +} + +static void +_drag_stop(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->drag_start_pos = 0; + edje_object_part_drag_value_set(wd->spinner, "elm.dragable.slider", 0.0, 0.0); +} + +static void +_hide_entry(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + edje_object_signal_emit(wd->spinner, "elm,state,inactive", "elm"); + wd->entry_visible = 0; +} + +static void +_reset_value(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _hide_entry(obj); + elm_spinner_value_set(obj, wd->orig_val); +} + +static void +_apply_entry_value(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const char *str; + char *end; + double val; + + if (!wd) return; + _hide_entry(obj); + str = elm_entry_entry_get(wd->ent); + if (!str) return; + val = strtod(str, &end); + if ((*end != '\0') && (!isspace(*end))) return; + elm_spinner_value_set(obj, val); +} + +static void +_toggle_entry(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (wd->dragging) + { + wd->dragging = 0; + return; + } + if (elm_widget_disabled_get(data)) return; + if (!wd->editable) return; + if (wd->entry_visible) _apply_entry_value(data); + else + { + wd->orig_val = wd->val; + edje_object_signal_emit(wd->spinner, "elm,state,active", "elm"); + _entry_show(wd); + elm_entry_select_all(wd->ent); + elm_widget_focus_set(wd->ent, 1); + wd->entry_visible = 1; + } +} + +static Eina_Bool +_spin_value(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return ECORE_CALLBACK_CANCEL; + if (_value_set(data, wd->spin_speed)) _write_label(data); + wd->interval = wd->interval / 1.05; + ecore_timer_interval_set(wd->spin, wd->interval); + return ECORE_CALLBACK_RENEW; +} + +static void +_val_inc_start(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->interval = wd->first_interval; + wd->spin_speed = wd->step; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = ecore_timer_add(wd->interval, _spin_value, obj); + _spin_value(obj); +} + +static void +_val_inc_stop(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->interval = wd->first_interval; + wd->spin_speed = 0; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = NULL; +} + +static void +_val_dec_start(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->interval = wd->first_interval; + wd->spin_speed = -wd->step; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = ecore_timer_add(wd->interval, _spin_value, obj); + _spin_value(obj); +} + +static void +_val_dec_stop(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->interval = wd->first_interval; + wd->spin_speed = 0; + if (wd->spin) ecore_timer_del(wd->spin); + wd->spin = NULL; +} + +static void +_button_inc_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (wd->entry_visible) + { + _reset_value(data); + return; + } + _val_inc_start(data); +} + +static void +_button_inc_stop(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + _val_inc_stop(data); +} + +static void +_button_dec_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (wd->entry_visible) + { + _reset_value(data); + return; + } + _val_dec_start(data); +} + +static void +_button_dec_stop(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + _val_dec_stop(data); +} + +static void +_entry_activated(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + _apply_entry_value(data); + evas_object_smart_callback_call(data, "changed", NULL); + if (wd->delay) ecore_timer_del(wd->delay); + wd->delay = ecore_timer_add(0.2, _delay_change, data); +} + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + if (type == EVAS_CALLBACK_KEY_DOWN) + { + Evas_Event_Key_Down *ev = event_info; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + else if (!strcmp(ev->keyname, "Left") || !strcmp(ev->keyname, "KP_Left") + || !strcmp(ev->keyname, "Down") || !strcmp(ev->keyname, "KP_Down")) + { + _val_dec_start(obj); + edje_object_signal_emit(wd->spinner, "elm,left,anim,activate", "elm"); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + else if (!strcmp(ev->keyname, "Right") || !strcmp(ev->keyname, "KP_Right") + || !strcmp(ev->keyname, "Up") || !strcmp(ev->keyname, "KP_Up")) + { + _val_inc_start(obj); + edje_object_signal_emit(wd->spinner, "elm,right,anim,activate", "elm"); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + } + else if (type == EVAS_CALLBACK_KEY_UP) + { + Evas_Event_Key_Down *ev = event_info; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (!strcmp(ev->keyname, "Right") || !strcmp(ev->keyname, "KP_Right") + || !strcmp(ev->keyname, "Up") || !strcmp(ev->keyname, "KP_Up")) + _val_inc_stop(obj); + else if (!strcmp(ev->keyname, "Left") || !strcmp(ev->keyname, "KP_Left") + || !strcmp(ev->keyname, "Down") || !strcmp(ev->keyname, "KP_Down")) + _val_dec_stop(obj); + else return EINA_FALSE; + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + return EINA_FALSE; +} + +/** + * Add a new spinner to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Spinner + */ +EAPI Evas_Object * +elm_spinner_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "spinner"); + elm_widget_type_set(obj, "spinner"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_signal_emit_hook_set(obj, _signal_emit_hook); + elm_widget_signal_callback_add_hook_set(obj, _signal_callback_add_hook); + elm_widget_signal_callback_del_hook_set(obj, _signal_callback_del_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->val = 0.0; + wd->val_min = 0.0; + wd->val_max = 100.0; + wd->wrap = 0; + wd->step = 1.0; + wd->first_interval = 0.85; + wd->entry_visible = 0; + wd->editable = EINA_TRUE; + + wd->spinner = edje_object_add(e); + _elm_theme_object_set(obj, wd->spinner, "spinner", "base", "default"); + elm_widget_resize_object_set(obj, wd->spinner); + edje_object_signal_callback_add(wd->spinner, "drag", "*", _drag, obj); + edje_object_signal_callback_add(wd->spinner, "drag,start", "*", + _drag_start, obj); + edje_object_signal_callback_add(wd->spinner, "drag,stop", "*", + _drag_stop, obj); + edje_object_signal_callback_add(wd->spinner, "drag,step", "*", + _drag_stop, obj); + edje_object_signal_callback_add(wd->spinner, "drag,page", "*", + _drag_stop, obj); + + edje_object_signal_callback_add(wd->spinner, "elm,action,increment,start", + "*", _button_inc_start, obj); + edje_object_signal_callback_add(wd->spinner, "elm,action,increment,stop", + "*", _button_inc_stop, obj); + edje_object_signal_callback_add(wd->spinner, "elm,action,decrement,start", + "*", _button_dec_start, obj); + edje_object_signal_callback_add(wd->spinner, "elm,action,decrement,stop", + "*", _button_dec_stop, obj); + edje_object_part_drag_value_set(wd->spinner, "elm.dragable.slider", + 0.0, 0.0); + + wd->ent = elm_entry_add(obj); + elm_entry_single_line_set(wd->ent, 1); + evas_object_smart_callback_add(wd->ent, "activated", _entry_activated, obj); + edje_object_part_swallow(wd->spinner, "elm.swallow.entry", wd->ent); + edje_object_signal_callback_add(wd->spinner, "elm,action,entry,toggle", + "*", _toggle_entry, obj); + + _write_label(obj); + _sizing_eval(obj); + return obj; +} + +/** + * Set the format string of the label area + * + * If NULL, this sets the format to "%.0f". If not it sets the format + * string for the label text. The label text is provided a floating point + * value, so the label text can display up to 1 floating point value. Note that + * this is optional. Use a format string such as "%1.2f meters" for example. + * + * @param obj The spinner object + * @param fmt The format string for the label display + * + * @ingroup Spinner + */ +EAPI void +elm_spinner_label_format_set(Evas_Object *obj, const char *fmt) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->label, fmt); + _write_label(obj); + _sizing_eval(obj); +} + +/** + * Get the label format of the spinner + * + * @param obj The spinner object + * @return The text label format string in UTF-8 + * + * @ingroup Spinner + */ +EAPI const char * +elm_spinner_label_format_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the minimum and maximum values for the spinner + * + * Maximum must be greater than minimum. + * + * @param obj The spinner object + * @param min The minimum value + * @param max The maximum value + * + * @ingroup Spinner + */ +EAPI void +elm_spinner_min_max_set(Evas_Object *obj, double min, double max) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if ((wd->val_min == min) && (wd->val_max == max)) return; + wd->val_min = min; + wd->val_max = max; + if (wd->val < wd->val_min) wd->val = wd->val_min; + if (wd->val > wd->val_max) wd->val = wd->val_max; + _val_set(obj); + _write_label(obj); +} + +/** + * Get the minimum and maximum values of the spinner + * + * @param obj The spinner object + * @param min The minimum value + * @param max The maximum value + * + * @ingroup Spinner + */ +EAPI void +elm_spinner_min_max_get(const Evas_Object *obj, double *min, double *max) +{ + if (min) *min = 0.0; + if (max) *max = 0.0; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (min) *min = wd->val_min; + if (max) *max = wd->val_max; +} + +/** + * Set the step for the spinner + * + * @param obj The spinner object + * @param step The step value + * + * @ingroup Spinner + */ +EAPI void +elm_spinner_step_set(Evas_Object *obj, double step) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->step = step; +} + +/** + * Get the step of the spinner + * + * @param obj The spinner object + * @return The step value + * + * @ingroup Spinner + */ +EAPI double +elm_spinner_step_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->step; +} +/** + * Set the value the spinner indicates + * + * @param obj The spinner object + * @param val The value (must be between min and max for the spinner) + * + * @ingroup Spinner + */ +EAPI void +elm_spinner_value_set(Evas_Object *obj, double val) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->val == val) return; + wd->val = val; + if (wd->val < wd->val_min) wd->val = wd->val_min; + if (wd->val > wd->val_max) wd->val = wd->val_max; + _val_set(obj); + _write_label(obj); +} + +/** + * Get the value the spinner has + * + * @param obj The spinner object + * @return The value of the spinner + * + * @ingroup Spinner + */ +EAPI double +elm_spinner_value_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->val; +} + +/** + * Sets whether the spinner should wrap when it reaches its + * minimum/maximum value + * + * @param obj The spinner object + * @param wrap True if it should wrap, false otherwise + * + * @ingroup Spinner + */ +EAPI void +elm_spinner_wrap_set(Evas_Object *obj, Eina_Bool wrap) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->wrap = wrap; +} + +/** + * Gets whether the spinner should wrap when it reaches its + * minimum/maximum value + * + * @param obj The spinner object + * @return Bool value of wrap option + * (0 = disabled, 1 = enabled) + * + * @ingroup Spinner + */ +EAPI Eina_Bool +elm_spinner_wrap_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->wrap; +} + +/** + * Set a special value to display in the place of the numerical one. + * + * @param obj The spinner object + * @param value The value to be replaced + * @param label The label to be used + * + * @ingroup Spinner + */ +EAPI void +elm_spinner_special_value_add(Evas_Object *obj, double value, const char *label) +{ + Elm_Spinner_Special_Value *sv; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + sv = calloc(1, sizeof(*sv)); + if (!sv) return; + sv->value = value; + sv->label = eina_stringshare_add(label); + + wd->special_values = eina_list_append(wd->special_values, sv); + _write_label(obj); +} + +/** + * Set whether the spinner can be directly edited by the user or not. + * Default is editable. + * + * @param obj The spinner object + * @param editable Bool value of the edit option + * (EINA_FALSE = not editable, EINA_TRUE = editable) + */ +EAPI void +elm_spinner_editable_set(Evas_Object *obj, Eina_Bool editable) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->editable = editable; +} + +/** + * Gets whether the spinner is editable. + * + * @param obj The spinner object + * @return Bool value of edit option + * (EINA_FALSE = not editable, EINA_TRUE = editable) + */ +EAPI Eina_Bool +elm_spinner_editable_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->editable; +} + +/** + * Set the interval for the spinner + * + * @param obj The spinner object + * @param interval The interval value in seconds + * + * The interval value is decreased while the user increments or decrements + * the spinner value. The next interval value is the previous interval / 1.05, + * so it speed up a bit. Default value is 0.85 seconds. + * + * @ingroup Spinner + */ +EAPI void +elm_spinner_interval_set(Evas_Object *obj, double interval) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->first_interval = interval; +} + +/** + * Get the interval of the spinner + * + * @param obj The spinner object + * @return The value of the first interval in seconds + * + * The interval value is decreased while the user increments or decrements + * the spinner value. The next interval value is the previous interval / 1.05, + * so it speed up a bit. Default value is 0.85 seconds. + * + * @ingroup Spinner + */ +EAPI double +elm_spinner_interval_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0.0; + return wd->first_interval; +} diff --git a/src/lib/elm_store.c b/src/lib/elm_store.c new file mode 100644 index 0000000..dba552b --- /dev/null +++ b/src/lib/elm_store.c @@ -0,0 +1,754 @@ +#include +#include +#include "elm_priv.h" + +#ifndef EFL_HAVE_THREADS +# error "No thread support. Required." +#endif + +#ifdef EFL_HAVE_POSIX_THREADS +# include +# define LK(x) pthread_mutex_t x +# define LKI(x) pthread_mutex_init(&(x), NULL); +# define LKD(x) pthread_mutex_destroy(&(x)); +# define LKL(x) pthread_mutex_lock(&(x)); +# define LKU(x) pthread_mutex_unlock(&(x)); +#else /* EFL_HAVE_WIN32_THREADS */ +# define WIN32_LEAN_AND_MEAN +# include +# undef WIN32_LEAN_AND_MEAN +# define LK(x) HANDLE x +# define LKI(x) x = CreateMutex(NULL, FALSE, NULL) +# define LKD(x) CloseHandle(x) +# define LKL(x) WaitForSingleObject(x, INFINITE) +# define LKU(x) ReleaseMutex(x) +#endif + +#define ELM_STORE_MAGIC 0x3f89ea56 +#define ELM_STORE_FILESYSTEM_MAGIC 0x3f89ea57 +#define ELM_STORE_ITEM_MAGIC 0x5afe8c1d + +struct _Elm_Store +{ + EINA_MAGIC; + void (*free)(Elm_Store *store); + struct { + void (*free)(Elm_Store_Item *item); + } item; + Evas_Object *genlist; + Ecore_Thread *list_th; + Eina_Inlist *items; + Eina_List *realized; + int realized_count; + int cache_max; + struct { + struct { + Elm_Store_Item_List_Cb func; + void *data; + } list; + struct { + Elm_Store_Item_Fetch_Cb func; + void *data; + } fetch; + struct { + Elm_Store_Item_Unfetch_Cb func; + void *data; + } unfetch; + } cb; + Eina_Bool sorted : 1; + Eina_Bool fetch_thread : 1; +}; + +struct _Elm_Store_Item +{ + EINA_INLIST; + EINA_MAGIC; + Elm_Store *store; + Elm_Genlist_Item *item; + Ecore_Thread *fetch_th; + Ecore_Job *eval_job; + const Elm_Store_Item_Mapping *mapping; + void *data; + LK(lock); + Eina_Bool live : 1; + Eina_Bool was_live : 1; + Eina_Bool realized : 1; + Eina_Bool fetched : 1; +}; + +struct _Elm_Store_Filesystem +{ + Elm_Store base; + EINA_MAGIC; + const char *dir; +}; + +struct _Elm_Store_Item_Filesystem +{ + Elm_Store_Item base; + const char *path; +}; + +static Elm_Genlist_Item_Class _store_item_class; + +static void +_store_cache_trim(Elm_Store *st) +{ + while ((st->realized ) && + (((int)eina_list_count(st->realized) - st->realized_count) + > st->cache_max)) + { + Elm_Store_Item *sti = st->realized->data; + if (sti->realized) + { + st->realized = eina_list_remove_list(st->realized, st->realized); + sti->realized = EINA_FALSE; + } + LKL(sti->lock); + if (!sti->fetched) + { + LKU(sti->lock); + if (sti->fetch_th) + { + ecore_thread_cancel(sti->fetch_th); + sti->fetch_th = NULL; + } + LKL(sti->lock); + } + sti->fetched = EINA_FALSE; + LKU(sti->lock); + if (st->cb.unfetch.func) + st->cb.unfetch.func(st->cb.unfetch.data, sti); + LKL(sti->lock); + sti->data = NULL; + LKU(sti->lock); + } +} + +static void +_store_genlist_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Store *st = data; + st->genlist = NULL; + if (st->list_th) + { + ecore_thread_cancel(st->list_th); + st->list_th = NULL; + } + eina_list_free(st->realized); + while (st->items) + { + Elm_Store_Item *sti = (Elm_Store_Item *)st->items; + if (sti->eval_job) ecore_job_del(sti->eval_job); + if (sti->fetch_th) + { + ecore_thread_cancel(sti->fetch_th); + sti->fetch_th = NULL; + } + if (sti->store->item.free) sti->store->item.free(sti); + if (sti->data) + { + if (st->cb.unfetch.func) + st->cb.unfetch.func(st->cb.unfetch.data, sti); + sti->data = NULL; + } + LKD(sti->lock); + free(sti); + } + // FIXME: kill threads and more +} + +////// **** WARNING *********************************************************** +//// * This function runs inside a thread outside efl mainloop. Be careful! * +// ************************************************************************ +/* TODO: refactor lock part into core? this does not depend on filesystm part */ +static void +_store_filesystem_fetch_do(void *data, Ecore_Thread *th __UNUSED__) +{ + Elm_Store_Item *sti = data; + LKL(sti->lock); + if (sti->data) + { + LKU(sti->lock); + return; + } + if (!sti->fetched) + { + LKU(sti->lock); + if (sti->store->cb.fetch.func) + sti->store->cb.fetch.func(sti->store->cb.fetch.data, sti); + LKL(sti->lock); + sti->fetched = EINA_TRUE; + } + LKU(sti->lock); +} +// ************************************************************************ +//// * End of separate thread function. * +////// ************************************************************************ +/* TODO: refactor lock part into core? this does not depend on filesystm part */ +static void +_store_filesystem_fetch_end(void *data, Ecore_Thread *th) +{ + Elm_Store_Item *sti = data; + LKL(sti->lock); + if (sti->data) elm_genlist_item_update(sti->item); + LKU(sti->lock); + if (th == sti->fetch_th) sti->fetch_th = NULL; +} + +/* TODO: refactor lock part into core? this does not depend on filesystm part */ +static void +_store_filesystem_fetch_cancel(void *data, Ecore_Thread *th) +{ + Elm_Store_Item *sti = data; + LKL(sti->lock); + if (th == sti->fetch_th) sti->fetch_th = NULL; + if (sti->data) elm_genlist_item_update(sti->item); + LKU(sti->lock); +} + +static void +_store_item_eval(void *data) +{ + Elm_Store_Item *sti = data; + sti->eval_job = NULL; + if (sti->live == sti->was_live) return; + sti->was_live = sti->live; + if (sti->live) + { + _store_cache_trim(sti->store); + if (sti->realized) + sti->store->realized = eina_list_remove(sti->store->realized, sti); + sti->store->realized = eina_list_append(sti->store->realized, sti); + sti->realized = EINA_TRUE; + if ((sti->store->fetch_thread) && (!sti->fetch_th)) + sti->fetch_th = ecore_thread_run(_store_filesystem_fetch_do, + _store_filesystem_fetch_end, + _store_filesystem_fetch_cancel, + sti); + else if ((!sti->store->fetch_thread)) + { + _store_filesystem_fetch_do(sti, NULL); + _store_filesystem_fetch_end(sti, NULL); + } + } + else + { + if (sti->fetch_th) + { + ecore_thread_cancel(sti->fetch_th); + sti->fetch_th = NULL; + } + _store_cache_trim(sti->store); + } +} + +static void +_store_genlist_item_realized(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Store *st = data; + Elm_Genlist_Item *gli = event_info; + Elm_Store_Item *sti = elm_genlist_item_data_get(gli); + if (!sti) return; + st->realized_count++; + sti->live = EINA_TRUE; + if (sti->eval_job) ecore_job_del(sti->eval_job); + sti->eval_job = ecore_job_add(_store_item_eval, sti); +} + +static void +_store_genlist_item_unrealized(void *data, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Store *st = data; + Elm_Genlist_Item *gli = event_info; + Elm_Store_Item *sti = elm_genlist_item_data_get(gli); + if (!sti) return; + st->realized_count--; + sti->live = EINA_FALSE; + if (sti->eval_job) ecore_job_del(sti->eval_job); + sti->eval_job = ecore_job_add(_store_item_eval, sti); +} + +static const Elm_Store_Item_Mapping * +_store_item_mapping_find(Elm_Store_Item *sti, const char *part) +{ + const Elm_Store_Item_Mapping *m; + + for (m = sti->mapping; m; m ++) + { + if (m->type == ELM_STORE_ITEM_MAPPING_NONE) break; + if (!strcmp(part, m->part)) return m; + } + return NULL; +} + +static char * +_store_item_label_get(void *data, Evas_Object *obj __UNUSED__, const char *part) +{ + Elm_Store_Item *sti = data; + const char *s = ""; + LKL(sti->lock); + if (sti->data) + { + const Elm_Store_Item_Mapping *m = _store_item_mapping_find(sti, part); + if (m) + { + switch (m->type) + { + case ELM_STORE_ITEM_MAPPING_LABEL: + s = *(char **)(((unsigned char *)sti->data) + m->offset); + break; + case ELM_STORE_ITEM_MAPPING_CUSTOM: + if (m->details.custom.func) + s = m->details.custom.func(sti->data, sti, part); + break; + default: + break; + } + } + } + LKU(sti->lock); + return strdup(s); +} + +static Evas_Object * +_store_item_icon_get(void *data, Evas_Object *obj, const char *part) +{ + Elm_Store_Item *sti = data; + LKL(sti->lock); + if (sti->data) + { + const Elm_Store_Item_Mapping *m = _store_item_mapping_find(sti, part); + if (m) + { + Evas_Object *ic = NULL; + const char *s = NULL; + + switch (m->type) + { + case ELM_STORE_ITEM_MAPPING_ICON: + ic = elm_icon_add(obj); + s = *(char **)(((unsigned char *)sti->data) + m->offset); + elm_icon_order_lookup_set(ic, m->details.icon.lookup_order); + evas_object_size_hint_aspect_set(ic, + EVAS_ASPECT_CONTROL_VERTICAL, + m->details.icon.w, + m->details.icon.h); + elm_icon_smooth_set(ic, m->details.icon.smooth); + elm_icon_no_scale_set(ic, m->details.icon.no_scale); + elm_icon_scale_set(ic, + m->details.icon.scale_up, + m->details.icon.scale_down); + if (s) + { + if (m->details.icon.standard_name) + elm_icon_standard_set(ic, s); + else + elm_icon_file_set(ic, s, NULL); + } + break; + case ELM_STORE_ITEM_MAPPING_PHOTO: + ic = elm_icon_add(obj); + s = *(char **)(((unsigned char *)sti->data) + m->offset); + elm_photo_size_set(ic, m->details.photo.size); + if (s) + elm_photo_file_set(ic, s); + break; + case ELM_STORE_ITEM_MAPPING_CUSTOM: + if (m->details.custom.func) + ic = m->details.custom.func(sti->data, sti, part); + break; + default: + break; + } + LKU(sti->lock); + return ic; + } + } + LKU(sti->lock); + return NULL; +} + +static void +_store_item_del(void *data __UNUSED__, Evas_Object *obj __UNUSED__) +{ +} + +////// **** WARNING *********************************************************** +//// * This function runs inside a thread outside efl mainloop. Be careful! * +// ************************************************************************ +static int +_store_filesystem_sort_cb(void *d1, void *d2) +{ + Elm_Store_Item_Info *info1 = d1, *info2 = d2; + if ((!info1->sort_id) || (!info2->sort_id)) return 0; + return strcoll(info1->sort_id, info2->sort_id); +} + +static void +_store_filesystem_list_do(void *data, Ecore_Thread *th __UNUSED__) +{ + Elm_Store_Filesystem *st = data; + Eina_Iterator *it; + const Eina_File_Direct_Info *finf; + Eina_List *sorted = NULL; + Elm_Store_Item_Info_Filesystem *info; + + // FIXME: need a way to abstract the open, list, feed items from list + // and maybe get initial sortable key vals etc. + it = eina_file_stat_ls(st->dir); + if (!it) return; + EINA_ITERATOR_FOREACH(it, finf) + { + Eina_Bool ok; + size_t pathsz = finf->path_length + 1; + + info = calloc(1, sizeof(Elm_Store_Item_Info_Filesystem) + pathsz); + if (!info) continue; + info->path = ((char *)info) + sizeof(Elm_Store_Item_Info_Filesystem); + memcpy(info->path, finf->path, pathsz); + ok = EINA_TRUE; + if (st->base.cb.list.func) + ok = st->base.cb.list.func(st->base.cb.list.data, &info->base); + if (ok) + { + if (!st->base.sorted) ecore_thread_feedback(th, info); + else sorted = eina_list_append(sorted, info); + } + else + { + if (info->base.sort_id) free(info->base.sort_id); + free(info); + } + if (ecore_thread_check(th)) break; + } + eina_iterator_free(it); + if (sorted) + { + sorted = eina_list_sort(sorted, 0, + EINA_COMPARE_CB(_store_filesystem_sort_cb)); + EINA_LIST_FREE(sorted, info) + { + if (!ecore_thread_check(th)) ecore_thread_feedback(th, info); + } + } +} +// ************************************************************************ +//// * End of separate thread function. * +////// ************************************************************************ + +static void +_store_filesystem_list_end(void *data, Ecore_Thread *th) +{ + Elm_Store *st = data; + if (th == st->list_th) st->list_th = NULL; +} + +static void +_store_filesystem_list_cancel(void *data, Ecore_Thread *th) +{ + Elm_Store *st = data; + if (th == st->list_th) st->list_th = NULL; +} + +static void +_store_filesystem_list_update(void *data, Ecore_Thread *th __UNUSED__, void *msg) +{ + Elm_Store *st = data; + Elm_Store_Item_Filesystem *sti; + Elm_Genlist_Item_Class *itc; + Elm_Store_Item_Info_Filesystem *info = msg; + + sti = calloc(1, sizeof(Elm_Store_Item_Filesystem)); + if (!sti) goto done; + LKI(sti->base.lock); + EINA_MAGIC_SET(&(sti->base), ELM_STORE_ITEM_MAGIC); + sti->base.store = st; + sti->base.data = info->base.data; + sti->base.mapping = info->base.mapping; + sti->path = eina_stringshare_add(info->path); + + itc = info->base.item_class; + if (!itc) itc = &_store_item_class; + else + { + itc->func.label_get = _store_item_label_get; + itc->func.icon_get = _store_item_icon_get; + itc->func.state_get = NULL; // FIXME: support state gets later + itc->func.del = _store_item_del; + } + + // FIXME: handle being a parent (tree) + sti->base.item = elm_genlist_item_append(st->genlist, itc, + sti/* item data */, + NULL/* parent */, + ELM_GENLIST_ITEM_NONE, + NULL/* func */, + NULL/* func data */); + st->items = eina_inlist_append(st->items, (Eina_Inlist *)sti); +done: + if (info->base.sort_id) free(info->base.sort_id); + free(info); +} + +// public api calls +static Elm_Store * +_elm_store_new(size_t size) +{ + Elm_Store *st = calloc(1, size); + EINA_SAFETY_ON_NULL_RETURN_VAL(st, NULL); + + // TODO: BEGIN - move to elm_store_init() + eina_magic_string_set(ELM_STORE_MAGIC, "Elm_Store"); + eina_magic_string_set(ELM_STORE_FILESYSTEM_MAGIC, "Elm_Store_Filesystem"); + eina_magic_string_set(ELM_STORE_ITEM_MAGIC, "Elm_Store_Item"); + // setup default item class (always the same) if list cb doesnt provide one + _store_item_class.item_style = "default"; + _store_item_class.func.label_get = _store_item_label_get; + _store_item_class.func.icon_get = _store_item_icon_get; + _store_item_class.func.state_get = NULL; // FIXME: support state gets later + _store_item_class.func.del = _store_item_del; + // TODO: END - move to elm_store_init() + + EINA_MAGIC_SET(st, ELM_STORE_MAGIC); + st->cache_max = 128; + st->fetch_thread = EINA_TRUE; + return st; +} +#define elm_store_new(type) (type*)_elm_store_new(sizeof(type)) + +static void +_elm_store_filesystem_free(Elm_Store *store) +{ + Elm_Store_Filesystem *st = (Elm_Store_Filesystem *)store; + eina_stringshare_del(st->dir); +} + +static void +_elm_store_filesystem_item_free(Elm_Store_Item *item) +{ + Elm_Store_Item_Filesystem *sti = (Elm_Store_Item_Filesystem *)item; + eina_stringshare_del(sti->path); +} + +EAPI Elm_Store * +elm_store_filesystem_new(void) +{ + Elm_Store_Filesystem *st = elm_store_new(Elm_Store_Filesystem); + EINA_SAFETY_ON_NULL_RETURN_VAL(st, NULL); + + EINA_MAGIC_SET(st, ELM_STORE_FILESYSTEM_MAGIC); + st->base.free = _elm_store_filesystem_free; + st->base.item.free = _elm_store_filesystem_item_free; + + return &st->base; +} + +EAPI void +elm_store_free(Elm_Store *st) +{ + void (*item_free)(Elm_Store_Item *); + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return; + if (st->list_th) + { + ecore_thread_cancel(st->list_th); + st->list_th = NULL; + } + eina_list_free(st->realized); + item_free = st->item.free; + while (st->items) + { + Elm_Store_Item *sti = (Elm_Store_Item *)st->items; + if (sti->eval_job) ecore_job_del(sti->eval_job); + if (sti->fetch_th) + { + ecore_thread_cancel(sti->fetch_th); + sti->fetch_th = NULL; + } + if (item_free) item_free(sti); + if (sti->data) + { + if (st->cb.unfetch.func) + st->cb.unfetch.func(st->cb.unfetch.data, sti); + sti->data = NULL; + } + LKD(sti->lock); + free(sti); + } + if (st->genlist) + { + evas_object_event_callback_del_full(st->genlist, EVAS_CALLBACK_DEL, _store_genlist_del, st); + evas_object_smart_callback_del(st->genlist, "realized", _store_genlist_item_realized); + evas_object_smart_callback_del(st->genlist, "unrealized", _store_genlist_item_unrealized); + elm_genlist_clear(st->genlist); + st->genlist = NULL; + } + if (st->free) st->free(st); + free(st); +} + +EAPI void +elm_store_target_genlist_set(Elm_Store *st, Evas_Object *obj) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return; + if (st->genlist == obj) return; + if (st->genlist) + { + evas_object_event_callback_del_full(st->genlist, EVAS_CALLBACK_DEL, _store_genlist_del, st); + evas_object_smart_callback_del(st->genlist, "realized", _store_genlist_item_realized); + evas_object_smart_callback_del(st->genlist, "unrealized", _store_genlist_item_unrealized); + elm_genlist_clear(st->genlist); + } + st->genlist = obj; + if (!st->genlist) return; + evas_object_smart_callback_add(st->genlist, "realized", _store_genlist_item_realized, st); + evas_object_smart_callback_add(st->genlist, "unrealized", _store_genlist_item_unrealized, st); + evas_object_event_callback_add(st->genlist, EVAS_CALLBACK_DEL, _store_genlist_del, st); + elm_genlist_clear(st->genlist); +} + +EAPI void +elm_store_filesystem_directory_set(Elm_Store *store, const char *dir) +{ + Elm_Store_Filesystem *st = (Elm_Store_Filesystem *)store; + if (!EINA_MAGIC_CHECK(store, ELM_STORE_MAGIC)) return; + if (!EINA_MAGIC_CHECK(st, ELM_STORE_FILESYSTEM_MAGIC)) return; + if (store->list_th) + { + ecore_thread_cancel(store->list_th); + store->list_th = NULL; + } + if (!eina_stringshare_replace(&st->dir, dir)) return; + store->list_th = ecore_thread_feedback_run(_store_filesystem_list_do, + _store_filesystem_list_update, + _store_filesystem_list_end, + _store_filesystem_list_cancel, + st, EINA_TRUE); +} + +EAPI const char * +elm_store_filesystem_directory_get(const Elm_Store *store) +{ + const Elm_Store_Filesystem *st = (const Elm_Store_Filesystem *)store; + if (!EINA_MAGIC_CHECK(store, ELM_STORE_MAGIC)) return NULL; + if (!EINA_MAGIC_CHECK(st, ELM_STORE_FILESYSTEM_MAGIC)) return NULL; + return st->dir; +} + +EAPI void +elm_store_cache_set(Elm_Store *st, int max) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return; + if (max < 0) max = 0; + st->cache_max = max; + _store_cache_trim(st); +} + +EAPI int +elm_store_cache_get(const Elm_Store *st) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return 0; + return st->cache_max; +} + +EAPI void +elm_store_list_func_set(Elm_Store *st, Elm_Store_Item_List_Cb func, const void *data) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return; + st->cb.list.func = func; + st->cb.list.data = (void *)data; +} + +EAPI void +elm_store_fetch_func_set(Elm_Store *st, Elm_Store_Item_Fetch_Cb func, const void *data) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return; + st->cb.fetch.func = func; + st->cb.fetch.data = (void *)data; +} + +EAPI void +elm_store_fetch_thread_set(Elm_Store *st, Eina_Bool use_thread) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return; + st->fetch_thread = !!use_thread; +} + +EAPI Eina_Bool +elm_store_fetch_thread_get(const Elm_Store *st) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return EINA_FALSE; + return st->fetch_thread; +} + +EAPI void +elm_store_unfetch_func_set(Elm_Store *st, Elm_Store_Item_Unfetch_Cb func, const void *data) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return; + st->cb.unfetch.func = func; + st->cb.unfetch.data = (void *)data; +} + +EAPI void +elm_store_sorted_set(Elm_Store *st, Eina_Bool sorted) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return; + st->sorted = sorted; +} + +EAPI Eina_Bool +elm_store_sorted_get(const Elm_Store *st) +{ + if (!EINA_MAGIC_CHECK(st, ELM_STORE_MAGIC)) return EINA_FALSE; + return st->sorted; +} + +EAPI void +elm_store_item_data_set(Elm_Store_Item *sti, void *data) +{ + if (!EINA_MAGIC_CHECK(sti, ELM_STORE_ITEM_MAGIC)) return; + LKL(sti->lock); + sti->data = data; + LKU(sti->lock); +} + +EAPI void * +elm_store_item_data_get(Elm_Store_Item *sti) +{ + if (!EINA_MAGIC_CHECK(sti, ELM_STORE_ITEM_MAGIC)) return NULL; + void *d; + LKL(sti->lock); + d = sti->data; + LKU(sti->lock); + return d; +} + +EAPI const Elm_Store * +elm_store_item_store_get(const Elm_Store_Item *sti) +{ + if (!EINA_MAGIC_CHECK(sti, ELM_STORE_ITEM_MAGIC)) return NULL; + // dont need lock + return sti->store; +} + +EAPI const Elm_Genlist_Item * +elm_store_item_genlist_item_get(const Elm_Store_Item *sti) +{ + if (!EINA_MAGIC_CHECK(sti, ELM_STORE_ITEM_MAGIC)) return NULL; + // dont need lock + return sti->item; +} + +EAPI const char * +elm_store_item_filesystem_path_get(const Elm_Store_Item *item) +{ + Elm_Store_Item_Filesystem *sti = (Elm_Store_Item_Filesystem *)item; + Elm_Store_Filesystem *st; + if (!EINA_MAGIC_CHECK(item, ELM_STORE_ITEM_MAGIC)) return NULL; + if (!EINA_MAGIC_CHECK(item->store, ELM_STORE_MAGIC)) return NULL; + /* ensure we're dealing with filesystem item */ + st = (Elm_Store_Filesystem *)item->store; + if (!EINA_MAGIC_CHECK(st, ELM_STORE_FILESYSTEM_MAGIC)) return NULL; + // dont need lock + return sti->path; +} diff --git a/src/lib/elm_table.c b/src/lib/elm_table.c new file mode 100644 index 0000000..8e296bc --- /dev/null +++ b/src/lib/elm_table.c @@ -0,0 +1,279 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Table Table + * + * Arranges widgets in a table where items can also span multiple + * columns or rows - even overlap (and then be raised or lowered + * accordingly to adjust stacking if they do overlap). + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *tbl; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_event_callback_del_full + (wd->tbl, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + evas_object_del(wd->tbl); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static Eina_Bool +_elm_table_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + const Eina_List *items; + void *(*list_data_get) (const Eina_List *list); + Eina_List *(*list_free) (Eina_List *list); + + if ((!wd) || (!wd->tbl)) + return EINA_FALSE; + + /* Focus chain */ + /* TODO: Change this to use other chain */ + if ((items = elm_widget_focus_custom_chain_get(obj))) + { + list_data_get = eina_list_data_get; + list_free = NULL; + } + else + { + items = evas_object_table_children_get(wd->tbl); + list_data_get = eina_list_data_get; + list_free = eina_list_free; + + if (!items) return EINA_FALSE; + } + + Eina_Bool ret = elm_widget_focus_list_next_get(obj, items, list_data_get, + dir, next); + + if (list_free) + list_free((Eina_List *)items); + + return ret; +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + Evas_Coord w, h; + if (!wd) return; + evas_object_size_hint_min_get(wd->tbl, &minw, &minh); + evas_object_size_hint_max_get(wd->tbl, &maxw, &maxh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); + evas_object_geometry_get(obj, NULL, NULL, &w, &h); + if (w < minw) w = minw; + if (h < minh) h = minh; + if ((maxw >= 0) && (w > maxw)) w = maxw; + if ((maxh >= 0) && (h > maxh)) h = maxh; + evas_object_resize(obj, w, h); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + _sizing_eval(obj); +} + +/** + * Add a new table to the parent + * + * @param parent The parent object + * @return The new object or NULL if it cannot be created + * + * @ingroup Table + */ +EAPI Evas_Object * +elm_table_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "table"); + elm_widget_type_set(obj, "table"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_focus_next_hook_set(obj, _elm_table_focus_next_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + elm_widget_highlight_ignore_set(obj, EINA_FALSE); + + wd->tbl = evas_object_table_add(e); + evas_object_event_callback_add(wd->tbl, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + elm_widget_resize_object_set(obj, wd->tbl); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + return obj; +} + +/** + * Set the homogenous layout in the table + * + * @param obj The layout object + * @param homogenous A boolean to set (or no) layout homogenous + * in the table + * (1 = homogenous, 0 = no homogenous) + * + * @ingroup Table + */ +EAPI void +elm_table_homogenous_set(Evas_Object *obj, Eina_Bool homogenous) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_table_homogeneous_set(wd->tbl, homogenous); +} + +/** + * Get the current table homogenous mode. + * + * @param obj The table object + * @return a boolean to set (or no) layout homogenous in the table + * (1 = homogenous, 0 = no homogenous) + * + * @ingroup Table + */ +EAPI Eina_Bool +elm_table_homogenous_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return evas_object_table_homogeneous_get(wd->tbl); +} + +/** + * Set padding between cells. + * + * @param obj The layout object. + * @param horizontal set the horizontal padding. + * @param vertical set the vertical padding. + * + * @ingroup Table + */ +EAPI void +elm_table_padding_set(Evas_Object *obj, Evas_Coord horizontal, Evas_Coord vertical) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_table_padding_set(wd->tbl, horizontal, vertical); +} + +/** + * Get padding between cells. + * + * @param obj The layout object. + * @param horizontal set the horizontal padding. + * @param vertical set the vertical padding. + * + * @ingroup Table + */ +EAPI void +elm_table_padding_get(const Evas_Object *obj, Evas_Coord *horizontal, Evas_Coord *vertical) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_table_padding_get(wd->tbl, horizontal, vertical); +} + +/** + * Add a subobject on the table with the coordinates passed + * + * @param obj The table object + * @param subobj The subobject to be added to the table + * @param x Coordinate to X axis + * @param y Coordinate to Y axis + * @param w Horizontal length + * @param h Vertical length + * + * @ingroup Table + */ +EAPI void +elm_table_pack(Evas_Object *obj, Evas_Object *subobj, int x, int y, int w, int h) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_widget_sub_object_add(obj, subobj); + evas_object_table_pack(wd->tbl, subobj, x, y, w, h); +} + +/** + * Remove child from table. + * + * @param obj The table object + * @param subobj The subobject + * + * @ingroup Table + */ +EAPI void +elm_table_unpack(Evas_Object *obj, Evas_Object *subobj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + elm_widget_sub_object_del(obj, subobj); + evas_object_table_unpack(wd->tbl, subobj); +} + +/** + * Faster way to remove all child objects from a table object. + * + * @param obj The table object + * @param clear If true, it will delete just removed children + * + * @ingroup Table + */ +EAPI void +elm_table_clear(Evas_Object *obj, Eina_Bool clear) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_table_clear(wd->tbl, clear); +} diff --git a/src/lib/elm_theme.c b/src/lib/elm_theme.c new file mode 100644 index 0000000..19a794b --- /dev/null +++ b/src/lib/elm_theme.c @@ -0,0 +1,866 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Theme + * + * Functions to modify the theme in the currently running app. + */ + +static Elm_Theme theme_default = +{ + NULL, NULL, NULL, NULL, NULL, NULL, NULL, 1 +}; + +static Eina_List *themes = NULL; + +static void +_elm_theme_clear(Elm_Theme *th) +{ + const char *p; + EINA_LIST_FREE(th->themes, p) + eina_stringshare_del(p); + EINA_LIST_FREE(th->overlay, p) + eina_stringshare_del(p); + EINA_LIST_FREE(th->extension, p) + eina_stringshare_del(p); + if (th->cache) + { + eina_hash_free(th->cache); + th->cache = NULL; + } + if (th->theme) + { + eina_stringshare_del(th->theme); + th->theme = NULL; + } + if (th->ref_theme) + { + th->ref_theme->referrers = + eina_list_remove(th->ref_theme->referrers, th); + elm_theme_free(th->ref_theme); + th->ref_theme = NULL; + } +} + +static const char * +_elm_theme_find_try(Elm_Theme *th, const char *f, const char *group) +{ + const char *file; + + if (edje_file_group_exists(f, group)) + { + file = eina_stringshare_add(f); + if (file) + { + eina_hash_add(th->cache, group, file); + return file; + } + } + return NULL; +} + +static const char * +_elm_theme_theme_element_try(Elm_Theme *th, const char *home, const char *f, const char *group) +{ + char buf[PATH_MAX]; + const char *file = NULL; + + if ((f[0] == '/') || ((f[0] == '.') && (f[1] == '/')) || + ((f[0] == '.') && (f[1] == '.') && (f[2] == '/')) || + ((isalpha(f[0])) && (f[1] == ':'))) + return _elm_theme_find_try(th, f, group); + else if (((f[0] == '~') && (f[1] == '/'))) + { + snprintf(buf, sizeof(buf), "%s/%s", home, f + 2); + return _elm_theme_find_try(th, buf, group); + } + snprintf(buf, sizeof(buf), "%s/.elementary/themes/%s.edj", home, f); + file = _elm_theme_find_try(th, buf, group); + if (file) return file; + snprintf(buf, sizeof(buf), "%s/themes/%s.edj", _elm_data_dir, f); + file = _elm_theme_find_try(th, buf, group); + return file; +} + +static const char * +_elm_theme_group_file_find(Elm_Theme *th, const char *group) +{ + const Eina_List *l; + const char *f; + static const char *home = NULL; + const char *file = eina_hash_find(th->cache, group); + + if (file) return file; + if (!home) + { + home = getenv("HOME"); + if (!home) home = ""; + } + EINA_LIST_FOREACH(th->overlay, l, f) + { + file = _elm_theme_theme_element_try(th, home, f, group); + if (file) return file; + } + EINA_LIST_FOREACH(th->themes, l, f) + { + file = _elm_theme_theme_element_try(th, home, f, group); + if (file) return file; + } + EINA_LIST_FOREACH(th->extension, l, f) + { + file = _elm_theme_theme_element_try(th, home, f, group); + if (file) return file; + } + if (th->ref_theme) return _elm_theme_group_file_find(th->ref_theme, group); + return NULL; +} + +Eina_Bool +_elm_theme_object_set(Evas_Object *parent, Evas_Object *o, const char *clas, const char *group, const char *style) +{ + Elm_Theme *th = NULL; + if (parent) th = elm_widget_theme_get(parent); + return _elm_theme_set(th, o, clas, group, style); +} + +Eina_Bool +_elm_theme_object_icon_set(Evas_Object *parent, Evas_Object *o, const char *group, const char *style) +{ + Elm_Theme *th = NULL; + if (parent) th = elm_widget_theme_get(parent); + return _elm_theme_icon_set(th, o, group, style); +} + +Eina_Bool +_elm_theme_set(Elm_Theme *th, Evas_Object *o, const char *clas, const char *group, const char *style) +{ + const char *file; + char buf2[1024]; + Eina_Bool ok; + + if (!th) th = &(theme_default); + snprintf(buf2, sizeof(buf2), "elm/%s/%s/%s", clas, group, style); + file = _elm_theme_group_file_find(th, buf2); + if (file) + { + ok = edje_object_file_set(o, file, buf2); + if (ok) return EINA_TRUE; + else + DBG("could not set theme group '%s' from file '%s': %s", + buf2, file, edje_load_error_str(edje_object_load_error_get(o))); + } + snprintf(buf2, sizeof(buf2), "elm/%s/%s/default", clas, group); + file = _elm_theme_group_file_find(th, buf2); + if (!file) return EINA_FALSE; + ok = edje_object_file_set(o, file, buf2); + if (!ok) + DBG("could not set theme group '%s' from file '%s': %s", + buf2, file, edje_load_error_str(edje_object_load_error_get(o))); + return ok; +} + +Eina_Bool +_elm_theme_icon_set(Elm_Theme *th, Evas_Object *o, const char *group, const char *style) +{ + const char *file; + char buf2[1024]; + int w, h; + + if (!th) th = &(theme_default); + snprintf(buf2, sizeof(buf2), "elm/icon/%s/%s", group, style); + file = _elm_theme_group_file_find(th, buf2); + if (file) + { + _els_smart_icon_file_edje_set(o, file, buf2); + _els_smart_icon_size_get(o, &w, &h); + if (w > 0) return EINA_TRUE; + } + snprintf(buf2, sizeof(buf2), "elm/icon/%s/default", group); + file = _elm_theme_group_file_find(th, buf2); + if (!file) return EINA_FALSE; + _els_smart_icon_file_edje_set(o, file, buf2); + _els_smart_icon_size_get(o, &w, &h); + return (w > 0); +} + +Eina_Bool +_elm_theme_parse(Elm_Theme *th, const char *theme) +{ + Eina_List *names = NULL; + const char *p, *pe; + + if (!th) th = &(theme_default); + if (theme) + { + p = theme; + pe = p; + for (;;) + { + if ((*pe == ':') || (!*pe)) + { // p -> pe == 'name:' + if (pe > p) + { + char *n = malloc(pe - p + 1); + if (n) + { + const char *nn; + + strncpy(n, p, pe - p); + n[pe - p] = 0; + nn = eina_stringshare_add(n); + if (nn) names = eina_list_append(names, nn); + free(n); + } + } + if (!*pe) break; + p = pe + 1; + pe = p; + } + else + pe++; + } + } + p = eina_list_data_get(eina_list_last(names)); + if ((!p) || ((p) && (strcmp(p, "default")))) + { + p = eina_stringshare_add("default"); + if (p) names = eina_list_append(names, p); + } + if (th->cache) eina_hash_free(th->cache); + th->cache = eina_hash_string_superfast_new(EINA_FREE_CB(eina_stringshare_del)); + + EINA_LIST_FREE(th->themes, p) eina_stringshare_del(p); + + th->themes = names; + return EINA_TRUE; +} + +void +_elm_theme_shutdown(void) +{ + _elm_theme_clear(&(theme_default)); +} + +/** + * Create a new specific theme + * + * This creates an empty specific theme that only uses the default theme. A + * specific theme has its own private set of extensions and overlays too + * (which are empty by default). Specific themes do not fall back to themes + * of parent objects. They are not intended for this use. Use styles, overlays + * and extensions when needed, but avoid specific themes unless there is no + * other way (example: you want to have a preview of a new theme you are + * selecting in a "theme selector" window. The preview is inside a scroller + * and should display what the theme you selected will look like, but not + * actually apply it yet. The child of the scroller will have a specific + * theme set to show this preview before the user decides to apply it to all + * applications). + * + * @ingroup Theme + */ +EAPI Elm_Theme * +elm_theme_new(void) +{ + Elm_Theme *th = calloc(1, sizeof(Elm_Theme)); + if (!th) return NULL; + th->ref = 1; + th->themes = eina_list_append(th->themes, eina_stringshare_add("default")); + themes = eina_list_append(themes, th); + return th; +} + +/** + * Free a specific theme + * + * @param th The theme to free + * + * This frees a theme created with elm_theme_new(). + * + * @ingroup Theme + */ +EAPI void +elm_theme_free(Elm_Theme *th) +{ + EINA_SAFETY_ON_NULL_RETURN(th); + th->ref--; + if (th->ref < 1) + { + _elm_theme_clear(th); + themes = eina_list_remove(themes, th); + free(th); + } +} + +/** + * Copy the theme fom the source to the destination theme + * + * @param th The source theme to copy from + * @param thdst The destination theme to copy data to + * + * This makes a one-time static copy of all the theme config, extensions + * and overlays from @p th to @p thdst. If @p th references a theme, then + * @p thdst is also set to reference it, with all the theme settings, + * overlays and extensions that @p th had. + */ +EAPI void +elm_theme_copy(Elm_Theme *th, Elm_Theme *thdst) +{ + const Eina_List *l; + const char *f; + + if (!th) th = &(theme_default); + if (!thdst) thdst = &(theme_default); + _elm_theme_clear(thdst); + if (th->ref_theme) + { + thdst->ref_theme = th->ref_theme; + thdst->ref_theme->referrers = + eina_list_append(thdst->ref_theme->referrers, thdst); + thdst->ref_theme->ref++; + } + EINA_LIST_FOREACH(th->overlay, l, f) + { + const char *s = eina_stringshare_add(f); + if (s) thdst->overlay = eina_list_append(thdst->overlay, s); + } + EINA_LIST_FOREACH(th->themes, l, f) + { + const char *s = eina_stringshare_add(f); + if (s) thdst->themes = eina_list_append(thdst->themes, s); + } + EINA_LIST_FOREACH(th->extension, l, f) + { + const char *s = eina_stringshare_add(f); + if (s) thdst->extension = eina_list_append(thdst->extension, s); + } + if (th->theme) thdst->theme = eina_stringshare_add(th->theme); + elm_theme_flush(thdst); +} + +/** + * Tell the source theme to reference the ref theme + * + * @param th The theme that will do the referencing + * @param thref The theme that is the reference source + * + * This clears @p th to be empty and then sets it to refer to @p thref + * so @p th acts as an override to @p thdst, but where its overrides + * don't apply, it will fall through to @pthref for configuration. + */ +EAPI void +elm_theme_ref_set(Elm_Theme *th, Elm_Theme *thref) +{ + if (!th) th = &(theme_default); + if (!thref) thref = &(theme_default); + if (th->ref_theme == thref) return; + _elm_theme_clear(th); + if (thref) + { + thref->referrers = eina_list_append(thref->referrers, th); + thref->ref++; + } + th->ref_theme = thref; + elm_theme_flush(th); +} + +/** + * Return the theme referred to + * + * @param th The theme to get the reference from + * @return The referenced theme handle + * + * This gets the theme set as the reference theme by elm_theme_ref_set(). + * If no theme is set as a reference, NULL is returned. + */ +EAPI Elm_Theme * +elm_theme_ref_get(Elm_Theme *th) +{ + if (!th) th = &(theme_default); + return th->ref_theme; +} + +/** + * Return the default theme + * + * @return The default theme handle + * + * This returns the internal default theme setup handle that all widgets + * use implicitly unless a specific theme is set. This is also often use + * as a shorthand of NULL. + */ +EAPI Elm_Theme * +elm_theme_default_get(void) +{ + return &theme_default; +} + +/** + * Prepends a theme overlay to the list of overlays + * + * @param th The theme to add to, or if NULL, the default theme + * @param item The Edje file path to be used + * + * Use this if your application needs to provide some custom overlay theme + * (An Edje file that replaces some default styles of widgets) where adding + * new styles, or changing system theme configuration is not possible. Do + * NOT use this instead of a proper system theme configuration. Use proper + * configuration files, profiles, environment variables etc. to set a theme + * so that the theme can be altered by simple confiugration by a user. Using + * this call to achieve that effect is abusing the API and will create lots + * of trouble. + * + * @ingroup Theme + */ +EAPI void +elm_theme_overlay_add(Elm_Theme *th, const char *item) +{ + const char *f = eina_stringshare_add(item); + + if (!th) th = &(theme_default); + if (f) th->overlay = eina_list_prepend(th->overlay, f); + elm_theme_flush(th); +} + +/** + * Delete a theme overlay from the list of overlays + * + * @param th The theme to delete from, or if NULL, the default theme + * @param item The name of the theme overlay + * + * See elm_theme_overlay_add(). + * + * @ingroup Theme + */ +EAPI void +elm_theme_overlay_del(Elm_Theme *th, const char *item) +{ + const Eina_List *l; + const char *f, *s; + + if (!th) th = &(theme_default); + s = eina_stringshare_add(item); + EINA_LIST_FOREACH(th->overlay, l, f) + if (f == s) + { + eina_stringshare_del(f); + th->overlay = eina_list_remove_list(th->overlay, (Eina_List *)l); + break; + } + eina_stringshare_del(s); + elm_theme_flush(th); +} + +/** + * Appends a theme extension to the list of extensions. + * + * @param th The theme to add to, or if NULL, the default theme + * @param item The Edje file path to be used + * + * This is intended when an application needs more styles of widgets or new + * widget themes that the default does not provide (or may not provide). The + * application has "extended" usage by coming up with new custom style names + * for widgets for specific uses, but as these are not "standard", they are + * not guaranteed to be provided by a default theme. This means the + * application is required to provide these extra elements itself in specific + * Edje files. This call adds one of those Edje files to the theme search + * path to be search after the default theme. The use of this call is + * encouraged when default styles do not meet the needs of the application. + * Use this call instead of elm_theme_overlay_add() for almost all cases. + * + * @ingroup Theme + */ +EAPI void +elm_theme_extension_add(Elm_Theme *th, const char *item) +{ + const char *f = eina_stringshare_add(item); + + if (!th) th = &(theme_default); + if (f) th->extension = eina_list_append(th->extension, f); + elm_theme_flush(th); +} + +/** + * Deletes a theme extension from the list of extensions. + * + * @param th The theme to delete from, or if NULL, the default theme + * @param item The name of the theme extension + * + * See elm_theme_extension_add(). + * + * @ingroup Theme + */ +EAPI void +elm_theme_extension_del(Elm_Theme *th, const char *item) +{ + const Eina_List *l; + const char *f, *s; + + if (!th) th = &(theme_default); + s = eina_stringshare_add(item); + EINA_LIST_FOREACH(th->extension, l, f) + if (f == s) + { + eina_stringshare_del(f); + th->extension = eina_list_remove_list(th->extension, (Eina_List *)l); + break; + } + eina_stringshare_del(s); + elm_theme_flush(th); +} + +/** + * Set the theme search order for the given theme + * + * @param th The theme to set the search order, or if NULL, the default theme + * @param theme Theme search string + * + * This sets the search string for the theme in path-notation from first + * theme to search, to last, delimited by the : character. Example: + * + * "shiny:/path/to/file.edj:default" + * + * See the ELM_THEME environment variable for more information. + * + * @ingroup Theme + */ +EAPI void +elm_theme_set(Elm_Theme *th, const char *theme) +{ + if (!th) th = &(theme_default); + _elm_theme_parse(th, theme); + if (th->theme) + { + eina_stringshare_del(th->theme); + th->theme = NULL; + } + elm_theme_flush(th); +} + +/** + * Return the theme search order + * + * @param th The theme to get the search order, or if NULL, the default theme + * @return The internal search order path + * + * See elm_theme_set() for more information. + * + * @ingroup Theme + */ +EAPI const char * +elm_theme_get(Elm_Theme *th) +{ + if (!th) th = &(theme_default); + if (!th->theme) + { + Eina_List *l; + const char *f; + char *tmp; + int len; + + len = 0; + EINA_LIST_FOREACH(th->themes, l, f) + { + len += strlen(f); + if (l->next) len += 1; + } + tmp = alloca(len + 1); + tmp[0] = 0; + EINA_LIST_FOREACH(th->themes, l, f) + { + strcat(tmp, f); + if (l->next) strcat(tmp, ":"); + } + th->theme = eina_stringshare_add(tmp); + } + return th->theme; +} + +/** + * Return a list of theme elements to be used in a theme. + * + * @param th Theme to get the list of theme elements from. + * @return The internal list of theme elements + * + * This returns the internal list of theme elements (will only be valid as + * long as the theme is not modified by elm_theme_set() or theme is not + * freed by elm_theme_free(). This is a list of strings which must not be + * altered as they are also internal. If @p th is NULL, then the default + * theme element list is returned. + */ +EAPI const Eina_List * +elm_theme_list_get(const Elm_Theme *th) +{ + if (!th) th = &(theme_default); + return th->themes; +} + +/** + * Return the full patrh for a theme element + * + * @param f The theme element name + * @param in_search_path Pointer to a boolean to indicate if item is in the search path or not + * @return The full path to the file found. + * + * This returns a string you should free with free() on success, NULL on + * failure. This will search for the given theme element, and if it is a + * full or relative path element or a simple searchable name. The returned + * path is the full path to the file, if searched, and the file exists, or it + * is simply the full path given in the element or a resolved path if + * relative to home. The @p in_search_path boolean pointed to is set to + * EINA_TRUE if the file was a searchable file andis in the search path, + * and EINA_FALSE otherwise. + */ +EAPI char * +elm_theme_list_item_path_get(const char *f, Eina_Bool *in_search_path) +{ + static const char *home = NULL; + char buf[PATH_MAX]; + + if (!f) + { + if (in_search_path) *in_search_path = EINA_FALSE; + return NULL; + } + + if (!home) + { + home = getenv("HOME"); + if (!home) home = ""; + } + + if ((f[0] == '/') || ((f[0] == '.') && (f[1] == '/')) || + ((f[0] == '.') && (f[1] == '.') && (f[2] == '/')) || + ((isalpha(f[0])) && (f[1] == ':'))) + { + if (in_search_path) *in_search_path = EINA_FALSE; + return strdup(f); + } + else if (((f[0] == '~') && (f[1] == '/'))) + { + if (in_search_path) *in_search_path = EINA_FALSE; + snprintf(buf, sizeof(buf), "%s/%s", home, f + 2); + return strdup(buf); + } + snprintf(buf, sizeof(buf), "%s/.elementary/themes/%s.edj", home, f); + if (ecore_file_exists(buf)) + { + if (in_search_path) *in_search_path = EINA_TRUE; + return strdup(buf); + } + + snprintf(buf, sizeof(buf), "%s/themes/%s.edj", _elm_data_dir, f); + if (ecore_file_exists(buf)) + { + if (in_search_path) *in_search_path = EINA_TRUE; + return strdup(buf); + } + + if (in_search_path) *in_search_path = EINA_FALSE; + return NULL; +} + +/** + * Flush the current theme. + * + * @param th Theme to flush + * + * This flushes caches that let elementary know where to find theme elements + * in the given theme. If @p th is NULL, then the default theme is flushed. + * Call this call if source theme data has changed in such a way as to + * make any caches Elementary kept invalid. + * + * @ingroup Theme + */ +EAPI void +elm_theme_flush(Elm_Theme *th) +{ + if (!th) th = &(theme_default); + if (th->cache) eina_hash_free(th->cache); + th->cache = eina_hash_string_superfast_new(EINA_FREE_CB(eina_stringshare_del)); + _elm_win_rescale(th, EINA_TRUE); + if (th->referrers) + { + Eina_List *l; + Elm_Theme *th2; + + EINA_LIST_FOREACH(th->referrers, l, th2) elm_theme_flush(th2); + } +} + +/** + * This flushes all themes (default and specific ones). + * + * This will flush all themes in the current application context, by calling + * elm_theme_flush() on each of them. + * + * @ingroup Theme + */ +EAPI void +elm_theme_full_flush(void) +{ + Eina_List *l; + Elm_Theme *th; + + EINA_LIST_FOREACH(themes, l, th) + { + elm_theme_flush(th); + } + elm_theme_flush(&(theme_default)); +} + +/** + * Set the theme for all elementary using applications on the current display + * + * @param theme The name of the theme to use. Format same as the ELM_THEME + * environment variable. + * + * @ingroup Theme + */ +EAPI void +elm_theme_all_set(const char *theme) +{ +#ifdef HAVE_ELEMENTARY_X + static Ecore_X_Atom atom = 0; + + if (!atom) atom = ecore_x_atom_get("ENLIGHTENMENT_THEME"); + ecore_x_window_prop_string_set(ecore_x_window_root_first_get(), + atom, theme); +#endif + elm_theme_set(NULL, theme); +} + +/** + * Return a list of theme elements in the theme search path + * + * @return A list of strings that are the theme element names. + * + * This lists all available theme files in the standard Elementary search path + * for theme elements, and returns them in alphabetical order as theme + * element names in a list of strings. Free this with + * elm_theme_name_available_list_free() when you are done with the list. + */ +EAPI Eina_List * +elm_theme_name_available_list_new(void) +{ + Eina_List *list = NULL; + Eina_List *dir, *l; + char buf[PATH_MAX], *file, *s, *th; + static const char *home = NULL; + + if (!home) + { + home = getenv("HOME"); + if (!home) home = ""; + } + + snprintf(buf, sizeof(buf), "%s/.elementary/themes", home); + dir = ecore_file_ls(buf); + EINA_LIST_FREE(dir, file) + { + snprintf(buf, sizeof(buf), "%s/.elementary/themes/%s", home, file); + if ((!ecore_file_is_dir(buf)) && (ecore_file_size(buf) > 0)) + { + s = strchr(file, '.'); + if ((s) && (!strcasecmp(s, ".edj"))) + { + th = strdup(file); + s = strchr(th, '.'); + *s = 0; + list = eina_list_append(list, th); + } + } + free(file); + } + + snprintf(buf, sizeof(buf), "%s/themes", _elm_data_dir); + dir = ecore_file_ls(buf); + EINA_LIST_FREE(dir, file) + { + snprintf(buf, sizeof(buf), "%s/themes/%s", _elm_data_dir, file); + if ((!ecore_file_is_dir(buf)) && (ecore_file_size(buf) > 0)) + { + s = strchr(file, '.'); + if ((s) && (!strcasecmp(s, ".edj"))) + { + int dup; + + th = strdup(file); + s = strchr(th, '.'); + *s = 0; + dup = 0; + EINA_LIST_FOREACH(list, l, s) + { + if (!strcmp(s, th)) + { + dup = 1; + break; + } + } + if (dup) free(th); + else list = eina_list_append(list, th); + } + } + free(file); + } + list = eina_list_sort(list, 0, EINA_COMPARE_CB(strcasecmp)); + return list; +} + +/** + * Free the list returned by elm_theme_name_available_list_new() + * + * This frees the list of themes returned by + * elm_theme_name_available_list_new(). Once freed the list should no longer + * be used. a new list mys be created. + */ +EAPI void +elm_theme_name_available_list_free(Eina_List *list) +{ + char *s; + EINA_LIST_FREE(list, s) free(s); +} + +/** + * Set a specific theme to be used for this object and its children + * + * @param obj The object to set the theme on + * @param th The theme to set + * + * This sets a specific theme that will be used for the given object and any + * child objects it has. If @p th is NULL then the theme to be used is + * cleared and the object will inherit its theme from its parent (which + * ultimately will use the default theme if no specific themes are set). + * + * Use special themes with great care as this will annoy users and make + * configuration difficult. Avoid any custom themes at all if it can be + * helped. + * + * @ingroup Theme + */ +EAPI void +elm_object_theme_set(Evas_Object *obj, Elm_Theme *th) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_widget_theme_set(obj, th); +} + +/** + * Get the specific theme to be used + * + * @param obj The object to get the specific theme from + * @return The specifc theme set. + * + * This will return a specific theme set, or NULL if no specific theme is + * set on that object. It will not return inherited themes from parents, only + * the specific theme set for that specific object. See elm_object_theme_set() + * for more information. + * + * @ingroup Theme + */ +EAPI Elm_Theme * +elm_object_theme_get(const Evas_Object *obj) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL); + return elm_widget_theme_get(obj); +} diff --git a/src/lib/elm_thumb.c b/src/lib/elm_thumb.c new file mode 100644 index 0000000..ecda646 --- /dev/null +++ b/src/lib/elm_thumb.c @@ -0,0 +1,755 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Thumb Thumb + * + * A thumb object is used for displaying the thumbnail of an image or video. + * You must have compiled Elementary with Ethumb_Client support and the DBus + * service must be present and auto-activated in order to have thumbnails to + * be generated. + * + * Signals that you can add callbacks for are: + * + * clicked - This is called when a user has clicked the thumb without dragging + * around. + * + * clicked,double - This is called when a user has double-clicked the thumb. + * + * press - This is called when a user has pressed down the thumb. + * + * generate,start - The thumbnail generation started. + * + * generate,stop - The generation process stopped. + * + * generate,error - The generation failed. + * + * load,error - The thumbnail image loading failed. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *self; + Evas_Object *frame; + Evas_Object *view; + const char *file; + const char *key; + struct + { + int id; + const char *file; + const char *key; + } thumb; + Ecore_Event_Handler *eeh; + Elm_Thumb_Animation_Setting anim_setting; + Eina_Bool on_hold : 1; + Eina_Bool is_video : 1; + Eina_Bool was_video : 1; + Eina_Bool edit : 1; +}; + +static const char *widtype = NULL; + +#define SIG_CLICKED "clicked" +#define SIG_CLICKED_DOUBLE "clicked,double" +#define SIG_GENERATE_ERROR "generate,error" +#define SIG_GENERATE_START "generate,start" +#define SIG_GENERATE_STOP "generate,stop" +#define SIG_LOAD_ERROR "load,error" +#define SIG_PRESS "press" + +static const Evas_Smart_Cb_Description _signals[] = +{ + {SIG_CLICKED, ""}, + {SIG_CLICKED_DOUBLE, ""}, + {SIG_GENERATE_ERROR, ""}, + {SIG_GENERATE_START, ""}, + {SIG_GENERATE_STOP, ""}, + {SIG_LOAD_ERROR, ""}, + {SIG_PRESS, ""}, + {NULL, NULL} +}; + +#define EDJE_SIGNAL_GENERATE_START "elm,thumb,generate,start" +#define EDJE_SIGNAL_GENERATE_STOP "elm,thumb,generate,stop" +#define EDJE_SIGNAL_GENERATE_ERROR "elm,thumb,generate,error" +#define EDJE_SIGNAL_LOAD_ERROR "elm,thumb,load,error" +#define EDJE_SIGNAL_PULSE_START "elm,state,pulse,start" +#define EDJE_SIGNAL_PULSE_STOP "elm,state,pulse,stop" + +struct _Ethumb_Client *_elm_ethumb_client = NULL; +Eina_Bool _elm_ethumb_connected = EINA_FALSE; + +EAPI int ELM_ECORE_EVENT_ETHUMB_CONNECT = 0; + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + +#ifdef HAVE_ELEMENTARY_ETHUMB + if (wd->thumb.id >= 0) + ethumb_client_generate_cancel(_elm_ethumb_client, wd->thumb.id, + NULL, NULL, NULL); +#endif + + eina_stringshare_del(wd->file); + eina_stringshare_del(wd->key); + if (wd->eeh) ecore_event_handler_del(wd->eeh); + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + _elm_theme_object_set(obj, wd->frame, "thumb", "base", + elm_widget_style_get(obj)); +} + +#ifdef HAVE_ELEMENTARY_ETHUMB +static void +_mouse_down_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = data; + Evas_Event_Mouse_Down *ev = event_info; + + if (ev->button != 1) + return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + wd->on_hold = EINA_TRUE; + else + wd->on_hold = EINA_FALSE; + if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK) + evas_object_smart_callback_call(wd->self, SIG_CLICKED_DOUBLE, NULL); + else + evas_object_smart_callback_call(wd->self, SIG_PRESS, NULL); +} + +static void +_mouse_up_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Widget_Data *wd = data; + Evas_Event_Mouse_Up *ev = event_info; + + if (ev->button != 1) + return; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + wd->on_hold = EINA_TRUE; + else + wd->on_hold = EINA_FALSE; + if (!wd->on_hold) + evas_object_smart_callback_call(wd->self, SIG_CLICKED, NULL); + wd->on_hold = EINA_FALSE; +} + +static void +_finished_thumb(Widget_Data *wd, const char *thumb_path, const char *thumb_key) +{ + Eina_Bool new_view = EINA_FALSE; + int r; + Evas_Coord mw, mh; + Evas *evas; + + evas = evas_object_evas_get(wd->self); + if ((wd->view) && (wd->is_video ^ wd->was_video)) + { + evas_object_del(wd->view); + wd->view = NULL; + } + wd->was_video = wd->is_video; + + if ((wd->is_video) && + (ethumb_client_format_get(_elm_ethumb_client) == ETHUMB_THUMB_EET)) + { + if (!wd->view) + { + wd->view = edje_object_add(evas); + if (!wd->view) + { + ERR("could not create edje object"); + goto err; + } + new_view = EINA_TRUE; + } + + if (!edje_object_file_set(wd->view, thumb_path, "movie/thumb")) + { + ERR("could not set file=%s key=%s for %s", thumb_path, thumb_key, + wd->file); + goto view_err; + } + } + else + { + if (!wd->view) + { + wd->view = evas_object_image_filled_add(evas); + if (!wd->view) + { + ERR("could not create image object"); + goto err; + } + new_view = EINA_TRUE; + } + + evas_object_image_file_set(wd->view, thumb_path, thumb_key); + r = evas_object_image_load_error_get(wd->view); + if (r != EVAS_LOAD_ERROR_NONE) + { + ERR("%s: %s", thumb_path, evas_load_error_str(r)); + goto view_err; + } + } + + if (new_view) elm_widget_sub_object_add(wd->self, wd->view); + edje_object_part_swallow(wd->frame, "elm.swallow.content", wd->view); + edje_object_size_min_get(wd->frame, &mw, &mh); + edje_object_size_min_restricted_calc(wd->frame, &mw, &mh, mw, mh); + evas_object_size_hint_min_set(wd->self, mw, mh); + eina_stringshare_replace(&(wd->thumb.file), thumb_path); + eina_stringshare_replace(&(wd->thumb.key), thumb_key); + edje_object_signal_emit(wd->frame, EDJE_SIGNAL_GENERATE_STOP, "elm"); + evas_object_smart_callback_call(wd->self, SIG_GENERATE_STOP, NULL); + return; + +view_err: + evas_object_del(wd->view); + wd->view = NULL; +err: + edje_object_signal_emit(wd->frame, EDJE_SIGNAL_LOAD_ERROR, "elm"); + evas_object_smart_callback_call(wd->self, SIG_LOAD_ERROR, NULL); +} + +static void +_finished_thumb_cb(void *data, Ethumb_Client *c __UNUSED__, int id, const char *file, const char *key, const char *thumb_path, const char *thumb_key, Eina_Bool success) +{ + Widget_Data *wd = data; + + EINA_SAFETY_ON_FALSE_RETURN(wd->thumb.id == id); + wd->thumb.id = -1; + + edje_object_signal_emit(wd->frame, EDJE_SIGNAL_PULSE_STOP, "elm"); + + if (success) + { + _finished_thumb(wd, thumb_path, thumb_key); + return; + } + + ERR("could not generate thumbnail for %s (key: %s)", file, key ? key : ""); + edje_object_signal_emit(wd->frame, EDJE_SIGNAL_GENERATE_ERROR, "elm"); + evas_object_smart_callback_call(wd->self, SIG_GENERATE_ERROR, NULL); +} + +static void +_thumb_apply(Widget_Data *wd) +{ + if (wd->thumb.id > 0) + { + ethumb_client_generate_cancel + (_elm_ethumb_client, wd->thumb.id, NULL, NULL, NULL); + wd->thumb.id = -1; + } + + if (!wd->file) return; + + ethumb_client_file_set(_elm_ethumb_client, wd->file, wd->key); + if (ethumb_client_thumb_exists(_elm_ethumb_client)) + { + const char *thumb_path, *thumb_key; + + wd->thumb.id = -1; + ethumb_client_thumb_path_get(_elm_ethumb_client, &thumb_path, + &thumb_key); + _finished_thumb(wd, thumb_path, thumb_key); + return; + } + else if ((wd->thumb.id = ethumb_client_generate + (_elm_ethumb_client, _finished_thumb_cb, wd, NULL)) != -1) + { + edje_object_signal_emit(wd->frame, EDJE_SIGNAL_PULSE_START, "elm"); + edje_object_signal_emit(wd->frame, EDJE_SIGNAL_GENERATE_START, "elm"); + evas_object_smart_callback_call(wd->self, SIG_GENERATE_START, NULL); + } + else + { + wd->thumb.id = -1; + edje_object_signal_emit(wd->frame, EDJE_SIGNAL_GENERATE_ERROR, "elm"); + evas_object_smart_callback_call(wd->self, SIG_GENERATE_ERROR, NULL); + } +} + +static Eina_Bool +_thumb_apply_cb(void *data, int type __UNUSED__, void *ev __UNUSED__) +{ + _thumb_apply(data); + return ECORE_CALLBACK_RENEW; +} + +static void +_thumb_show(Widget_Data *wd) +{ + evas_object_show(wd->frame); + + if (elm_thumb_ethumb_client_connected()) + { + _thumb_apply(wd); + return; + } + + if (!wd->eeh) + wd->eeh = ecore_event_handler_add(ELM_ECORE_EVENT_ETHUMB_CONNECT, + _thumb_apply_cb, wd); +} + +static void +_thumb_show_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _thumb_show(data); +} + +static void +_thumb_hide_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = data; + + evas_object_hide(wd->frame); + + if (wd->thumb.id >= 0) + { + ethumb_client_generate_cancel + (_elm_ethumb_client, wd->thumb.id, NULL, NULL, NULL); + wd->thumb.id = -1; + + edje_object_signal_emit(wd->frame, EDJE_SIGNAL_GENERATE_STOP, "elm"); + evas_object_smart_callback_call(wd->self, SIG_GENERATE_STOP, NULL); + } + + if (wd->eeh) + { + ecore_event_handler_del(wd->eeh); + wd->eeh = NULL; + } +} + +#endif + +#ifdef ELM_ETHUMB +static int _elm_need_ethumb = 0; + +static void _on_die_cb(void *, Ethumb_Client *); + +static void +_connect_cb(void *data __UNUSED__, Ethumb_Client *c, Eina_Bool success) +{ + if (success) + { + ethumb_client_on_server_die_callback_set(c, _on_die_cb, NULL, NULL); + _elm_ethumb_connected = EINA_TRUE; + ecore_event_add(ELM_ECORE_EVENT_ETHUMB_CONNECT, NULL, NULL, NULL); + } + else + _elm_ethumb_client = NULL; +} + +static void +_on_die_cb(void *data __UNUSED__, Ethumb_Client *c __UNUSED__) +{ + ethumb_client_disconnect(_elm_ethumb_client); + _elm_ethumb_client = NULL; + _elm_ethumb_connected = EINA_FALSE; + _elm_ethumb_client = ethumb_client_connect(_connect_cb, NULL, NULL); +} +#endif + +void +_elm_unneed_ethumb(void) +{ +#ifdef ELM_ETHUMB + if (--_elm_need_ethumb) return; + + ethumb_client_disconnect(_elm_ethumb_client); + _elm_ethumb_client = NULL; + ethumb_client_shutdown(); + ELM_ECORE_EVENT_ETHUMB_CONNECT = 0; +#endif +} + +static Eina_Bool +_elm_thumb_dropcb(void *data __UNUSED__, Evas_Object *o, Elm_Selection_Data *drop) +{ + if ((!o) || (!drop) || (!drop->data)) return EINA_FALSE; + elm_thumb_file_set(o, drop->data, NULL); + return EINA_TRUE; +} + +/** + * This must be called before any other function that handle with + * elm_thumb objects or ethumb_client instances. + * + * @ingroup Thumb + */ +EAPI Eina_Bool +elm_need_ethumb(void) +{ +#ifdef ELM_ETHUMB + if (_elm_need_ethumb++) return EINA_TRUE; + ELM_ECORE_EVENT_ETHUMB_CONNECT = ecore_event_type_new(); + ethumb_client_init(); + _elm_ethumb_client = ethumb_client_connect(_connect_cb, NULL, NULL); + return EINA_TRUE; +#else + return EINA_FALSE; +#endif +} + +/** + * Add a new thumb object to the parent. + * + * @param parent The parent object. + * @return The new object or NULL if it cannot be created. + * + * @see elm_thumb_file_set() + * @see elm_thumb_ethumb_client_get() + * + * @ingroup Thumb + */ +EAPI Evas_Object * +elm_thumb_add(Evas_Object *parent) +{ + Evas *evas; + Widget_Data *wd; + Evas_Object *obj; + Evas_Coord minw, minh; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + evas = evas_object_evas_get(parent); + if (!evas) return NULL; + obj = elm_widget_add(evas); + ELM_SET_WIDTYPE(widtype, "thumb"); + elm_widget_type_set(obj, "thumb"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->frame = edje_object_add(evas); + _elm_theme_object_set(obj, wd->frame, "thumb", "base", "default"); + elm_widget_resize_object_set(obj, wd->frame); + + edje_object_size_min_calc(obj, &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + + wd->self = obj; + wd->view = NULL; + wd->file = NULL; + wd->key = NULL; + wd->eeh = NULL; + wd->thumb.id = -1; + wd->on_hold = EINA_FALSE; + wd->is_video = EINA_FALSE; + wd->was_video = EINA_FALSE; + +#ifdef HAVE_ELEMENTARY_ETHUMB + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOUSE_DOWN, + _mouse_down_cb, wd); + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOUSE_UP, + _mouse_up_cb, wd); + evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, + _thumb_show_cb, wd); + evas_object_event_callback_add(obj, EVAS_CALLBACK_HIDE, + _thumb_hide_cb, wd); +#endif + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Reload thumbnail if it was generated before. + * + * This is useful if the ethumb client configuration changed, like its + * size, aspect or any other property one set in the handle returned + * by elm_thumb_ethumb_client_get(). + * + * @param obj The thumb object to reload + * + * @see elm_thumb_file_set() + * + * @ingroup Thumb + */ +EAPI void +elm_thumb_reload(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + eina_stringshare_replace(&(wd->thumb.file), NULL); + eina_stringshare_replace(&(wd->thumb.key), NULL); + +#ifdef HAVE_ELEMENTARY_ETHUMB + if (evas_object_visible_get(obj)) + _thumb_show(wd); +#endif +} + +/** + * Set the file that will be used as thumbnail. + * + * The file can be an image or a video (in that case, acceptable extensions are: + * avi, mp4, ogv, mov, mpg and wmv). To start the video animation, use the + * function elm_thumb_animate(). + * + * @param obj The thumb object. + * @param file The path to file that will be used as thumb. + * @param key The key used in case of an EET file. + * + * @see elm_thumb_file_get() + * @see elm_thumb_reload() + * @see elm_thumb_animate() + * + * @ingroup Thumb + */ +EAPI void +elm_thumb_file_set(Evas_Object *obj, const char *file, const char *key) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Eina_Bool file_replaced, key_replaced; + Widget_Data *wd = elm_widget_data_get(obj); + + file_replaced = eina_stringshare_replace(&(wd->file), file); + key_replaced = eina_stringshare_replace(&(wd->key), key); + + if (file_replaced) + { + int prefix_size; + const char **ext, *ptr; + static const char *extensions[] = + { + ".avi", ".mp4", ".ogv", ".mov", ".mpg", ".wmv", NULL + }; + + prefix_size = eina_stringshare_strlen(wd->file) - 4; + if (prefix_size >= 0) + { + ptr = wd->file + prefix_size; + wd->is_video = EINA_FALSE; + for (ext = extensions; *ext; ext++) + if (!strcasecmp(ptr, *ext)) + { + wd->is_video = EINA_TRUE; + break; + } + } + } + + eina_stringshare_replace(&(wd->thumb.file), NULL); + eina_stringshare_replace(&(wd->thumb.key), NULL); + +#ifdef HAVE_ELEMENTARY_ETHUMB + if (((file_replaced) || (key_replaced)) && (evas_object_visible_get(obj))) + _thumb_show(wd); +#endif +} + +/** + * Get the image or video path and key used to generate the thumbnail. + * + * @param obj The thumb object. + * @param file Pointer to filename. + * @param key Pointer to key. + * + * @see elm_thumb_file_set() + * @see elm_thumb_path_get() + * @see elm_thumb_animate() + * + * @ingroup Thumb + */ +EAPI void +elm_thumb_file_get(const Evas_Object *obj, const char **file, const char **key) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (file) + *file = wd->file; + if (key) + *key = wd->key; +} + +/** + * Get the path and key to the image or video generated by ethumb. + * + * One just need to make sure that the thumbnail was generated before getting + * its path; otherwise, the path will be NULL. One way to do that is by asking + * for the path when/after the "generate,stop" smart callback is called. + * + * @param obj The thumb object. + * @param file Pointer to thumb path. + * @param key Pointer to thumb key. + * + * @see elm_thumb_file_get() + * + * @ingroup Thumb + */ +EAPI void +elm_thumb_path_get(const Evas_Object *obj, const char **file, const char **key) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (file) + *file = wd->thumb.file; + if (key) + *key = wd->thumb.key; +} + +/** + * Set the animation state for the thumb object. If its content is an animated + * video, you may start/stop the animation or tell it to play continuously and + * looping. + * + * @param obj The thumb object. + * @param setting The animation setting. + * + * @see elm_thumb_file_set() + * + * @ingroup Thumb + */ +EAPI void +elm_thumb_animate_set(Evas_Object *obj, Elm_Thumb_Animation_Setting setting) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + EINA_SAFETY_ON_TRUE_RETURN(setting >= ELM_THUMB_ANIMATION_LAST); + + wd->anim_setting = setting; + if (setting == ELM_THUMB_ANIMATION_LOOP) + edje_object_signal_emit(wd->view, "animate_loop", ""); + else if (setting == ELM_THUMB_ANIMATION_START) + edje_object_signal_emit(wd->view, "animate", ""); + else if (setting == ELM_THUMB_ANIMATION_STOP) + edje_object_signal_emit(wd->view, "animate_stop", ""); +} + +/** + * Get the animation state for the thumb object. + * + * @param obj The thumb object. + * @return getting The animation setting or @c ELM_THUMB_ANIMATION_LAST, + * on errors. + * + * @see elm_thumb_file_get() + * + * @ingroup Thumb + */ +EAPI Elm_Thumb_Animation_Setting +elm_thumb_animate_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_THUMB_ANIMATION_LAST; + Widget_Data *wd = elm_widget_data_get(obj); + + return wd->anim_setting; +} + +/** + * Get the ethumb_client handle so custom configuration can be made. + * This must be called before the objects are created to be sure no object is + * visible and no generation started. + * + * @return Ethumb_Client instance or NULL. + * + * Example of usage: + * + * @code + * #include + * #ifndef ELM_LIB_QUICKLAUNCH + * EAPI int + * elm_main(int argc, char **argv) + * { + * Ethumb_Client *client; + * + * elm_need_ethumb(); + * + * // ... your code + * + * client = elm_thumb_ethumb_client_get(); + * if (!client) + * { + * ERR("could not get ethumb_client"); + * return 1; + * } + * ethumb_client_size_set(client, 100, 100); + * ethumb_client_crop_align_set(client, 0.5, 0.5); + * // ... your code + * + * // Create elm_thumb objects here + * + * elm_run(); + * elm_shutdown(); + * return 0; + * } + * #endif + * ELM_MAIN() + * @endcode + * + * @ingroup Thumb + */ +EAPI void * +elm_thumb_ethumb_client_get(void) +{ + return _elm_ethumb_client; +} + +/** + * Get the ethumb_client connection state. + * + * @return EINA_TRUE if the client is connected to the server or + * EINA_FALSE otherwise. + */ +EAPI Eina_Bool +elm_thumb_ethumb_client_connected(void) +{ + return _elm_ethumb_connected; +} + +EAPI Eina_Bool +elm_thumb_editable_set(Evas_Object *obj, Eina_Bool edit) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + edit = !!edit; + if (wd->edit == edit) return EINA_TRUE; + + wd->edit = edit; + if (wd->edit) + elm_drop_target_add(obj, ELM_SEL_FORMAT_IMAGE, + _elm_thumb_dropcb, obj); + else + elm_drop_target_del(obj); + + return EINA_TRUE; +} + +EAPI Eina_Bool +elm_thumb_editable_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->edit; +} + +/* vim:set ts=8 sw=3 sts=3 expandtab cino=>5n-2f0^-2{2(0W1st0 :*/ diff --git a/src/lib/elm_toggle.c b/src/lib/elm_toggle.c new file mode 100644 index 0000000..bfd2857 --- /dev/null +++ b/src/lib/elm_toggle.c @@ -0,0 +1,480 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Toggle + * + * A toggle is a slider which can be used to toggle between + * two values. It has two states: on and off. + * + * Signals that you can add callbacks for are: + * + * changed - Whenever the toggle value has been changed. Is not called + * until the toggle is released by the cursor (assuming it has been triggered + * by the cursor in the first place). + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *tgl; + Evas_Object *icon; + Eina_Bool state; + Eina_Bool *statep; + const char *label; + const char *ontext, *offtext; +}; + +static const char *widtype = NULL; +static void _del_hook(Evas_Object *obj); +static void _disable_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); +static void _signal_toggle_off(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _signal_toggle_on(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _on_focus_hook(void *data, Evas_Object *obj); +static Eina_Bool _event_hook(Evas_Object *obj, Evas_Object *src, + Evas_Callback_Type type, void *event_info); + +static const char SIG_CHANGED[] = "changed"; +static const Evas_Smart_Cb_Description _signals[] = { + {SIG_CHANGED, ""}, + {NULL, NULL} +}; + +static Eina_Bool +_event_hook(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE; + Evas_Event_Key_Down *ev = event_info; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE; + if (elm_widget_disabled_get(obj)) return EINA_FALSE; + if ((strcmp(ev->keyname, "Return")) && + (strcmp(ev->keyname, "KP_Enter")) && + (strcmp(ev->keyname, "space"))) + return EINA_FALSE; + elm_toggle_state_set(obj, !wd->state); + evas_object_smart_callback_call(obj, SIG_CHANGED, NULL); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->label) eina_stringshare_del(wd->label); + if (wd->ontext) eina_stringshare_del(wd->ontext); + if (wd->offtext) eina_stringshare_del(wd->offtext); + free(wd); +} + +static void +_disable_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_disabled_get(obj)) + edje_object_signal_emit(wd->tgl, "elm,state,disabled", "elm"); + else + edje_object_signal_emit(wd->tgl, "elm,state,enabled", "elm"); +} + +static void +_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (elm_widget_focus_get(obj)) + { + edje_object_signal_emit(wd->tgl, "elm,action,focus", "elm"); + evas_object_focus_set(wd->tgl, EINA_TRUE); + } + else + { + edje_object_signal_emit(wd->tgl, "elm,action,unfocus", "elm"); + evas_object_focus_set(wd->tgl, EINA_FALSE); + } +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + _elm_theme_object_set(obj, wd->tgl, "toggle", "base", elm_widget_style_get(obj)); + if (wd->icon) + edje_object_signal_emit(wd->tgl, "elm,state,icon,visible", "elm"); + else + edje_object_signal_emit(wd->tgl, "elm,state,icon,hidden", "elm"); + if (wd->state) + edje_object_signal_emit(wd->tgl, "elm,state,toggle,on", "elm"); + else + edje_object_signal_emit(wd->tgl, "elm,state,toggle,off", "elm"); + if (wd->label) + edje_object_signal_emit(wd->tgl, "elm,state,text,visible", "elm"); + else + edje_object_signal_emit(wd->tgl, "elm,state,text,hidden", "elm"); + edje_object_part_text_set(wd->tgl, "elm.text", wd->label); + edje_object_part_text_set(wd->tgl, "elm.ontext", wd->ontext); + edje_object_part_text_set(wd->tgl, "elm.offtext", wd->offtext); + if (elm_widget_disabled_get(obj)) + edje_object_signal_emit(wd->tgl, "elm,state,disabled", "elm"); + edje_object_message_signal_process(wd->tgl); + edje_object_scale_set(wd->tgl, elm_widget_scale_get(obj) * _elm_config->scale); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + + if (!wd) return; + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + edje_object_size_min_restricted_calc(wd->tgl, &minw, &minh, minw, minh); + elm_coords_finger_size_adjust(1, &minw, 1, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + if (obj != wd->icon) return; + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (!wd) return; + if (sub == wd->icon) + { + edje_object_signal_emit(wd->tgl, "elm,state,icon,hidden", "elm"); + evas_object_event_callback_del_full + (sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + wd->icon = NULL; + edje_object_message_signal_process(wd->tgl); + _sizing_eval(obj); + } +} + +static void +_signal_toggle_off(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->state = 0; + if (wd->statep) *wd->statep = wd->state; + evas_object_smart_callback_call(data, SIG_CHANGED, NULL); +} + +static void +_signal_toggle_on(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd) return; + wd->state = 1; + if (wd->statep) *wd->statep = wd->state; + evas_object_smart_callback_call(data, SIG_CHANGED, NULL); +} + +/** + * Add a toggle to @p parent. + * + * @param parent The parent object + * + * @return The toggle object + * + * @ingroup Toggle + */ +EAPI Evas_Object * +elm_toggle_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "toggle"); + elm_widget_type_set(obj, "toggle"); + elm_widget_sub_object_add(parent, obj); + elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + elm_widget_data_set(obj, wd); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_disable_hook_set(obj, _disable_hook); + elm_widget_can_focus_set(obj, EINA_TRUE); + elm_widget_event_hook_set(obj, _event_hook); + + wd->tgl = edje_object_add(e); + _elm_theme_object_set(obj, wd->tgl, "toggle", "base", "default"); + wd->ontext = eina_stringshare_add("ON"); + wd->offtext = eina_stringshare_add("OFF"); + edje_object_signal_callback_add(wd->tgl, "elm,action,toggle,on", "", + _signal_toggle_on, obj); + edje_object_signal_callback_add(wd->tgl, "elm,action,toggle,off", "", + _signal_toggle_off, obj); + elm_widget_resize_object_set(obj, wd->tgl); + edje_object_part_text_set(wd->tgl, "elm.ontext", wd->ontext); + edje_object_part_text_set(wd->tgl, "elm.offtext", wd->offtext); + + evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); + + _sizing_eval(obj); + + // TODO: convert Elementary to subclassing of Evas_Smart_Class + // TODO: and save some bytes, making descriptions per-class and not instance! + evas_object_smart_callbacks_descriptions_set(obj, _signals); + return obj; +} + +/** + * Sets the label to be displayed with the toggle. + * + * @param obj The toggle object + * @param label The label to be displayed + * + * @ingroup Toggle + */ +EAPI void +elm_toggle_label_set(Evas_Object *obj, const char *label) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->label, label); + if (label) + edje_object_signal_emit(wd->tgl, "elm,state,text,visible", "elm"); + else + edje_object_signal_emit(wd->tgl, "elm,state,text,hidden", "elm"); + edje_object_message_signal_process(wd->tgl); + edje_object_part_text_set(wd->tgl, "elm.text", label); + _sizing_eval(obj); +} + +/** + * Gets the label of the toggle + * + * @param obj toggleeee object + * @return The label of the toggle + * + * @ingroup Toggle + */ +EAPI const char * +elm_toggle_label_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->label; +} + +/** + * Set the icon used for the toggle + * + * Once the icon object is set, a previously set one will be deleted + * If you want to keep that old content object, use the + * elm_toggle_icon_unset() function. + * + * @param obj The toggle object + * @param icon The icon object for the button + * + * @ingroup Toggle + */ +EAPI void +elm_toggle_icon_set(Evas_Object *obj, Evas_Object *icon) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->icon == icon) return; + if (wd->icon) evas_object_del(wd->icon); + wd->icon = icon; + if (icon) + { + elm_widget_sub_object_add(obj, icon); + evas_object_event_callback_add(icon, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->tgl, "elm.swallow.content", icon); + edje_object_signal_emit(wd->tgl, "elm,state,icon,visible", "elm"); + edje_object_message_signal_process(wd->tgl); + } + _sizing_eval(obj); +} + +/** + * Get the icon used for the toggle + * + * Return the icon object which is set for this widget. + * + * @param obj The toggle object + * @return The icon object that is being used + * + * @ingroup Toggle + */ +EAPI Evas_Object * +elm_toggle_icon_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->icon; +} + +/** + * Unset the icon used for the toggle + * + * Unparent and return the icon object which was set for this widget. + * + * @param obj The toggle object + * @return The icon object that was being used + * + * @ingroup Toggle + */ +EAPI Evas_Object * +elm_toggle_icon_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->icon) return NULL; + Evas_Object *icon = wd->icon; + elm_widget_sub_object_del(obj, wd->icon); + edje_object_part_unswallow(wd->tgl, wd->icon); + wd->icon = NULL; + return icon; +} + +/** + * Sets the labels to be associated with the on and off states of the toggle. + * + * @param obj The toggle object + * @param onlabel The label displayed when the toggle is in the "on" state + * @param offlabel The label displayed when the toggle is in the "off" state + * + * @ingroup Toggle + */ +EAPI void +elm_toggle_states_labels_set(Evas_Object *obj, const char *onlabel, const char *offlabel) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + eina_stringshare_replace(&wd->ontext, onlabel); + eina_stringshare_replace(&wd->offtext, offlabel); + edje_object_part_text_set(wd->tgl, "elm.ontext", onlabel); + edje_object_part_text_set(wd->tgl, "elm.offtext", offlabel); + _sizing_eval(obj); +} + + +/** + * Gets the labels associated with the on and off states of the toggle. + * + * @param obj The toggle object + * @param onlabel A char** to place the onlabel of @p obj into + * @param offlabel A char** to place the offlabel of @p obj into + * + * @ingroup Toggle + */ +EAPI void +elm_toggle_states_labels_get(const Evas_Object *obj, const char **onlabel, const char **offlabel) +{ + if (onlabel) *onlabel = NULL; + if (offlabel) *offlabel = NULL; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (onlabel) *onlabel = wd->ontext; + if (offlabel) *offlabel = wd->offtext; +} + +/** + * Sets the state of the toggle to @p state. + * + * @param obj The toggle object + * @param state The state of @p obj + * + * @ingroup Toggle + */ +EAPI void +elm_toggle_state_set(Evas_Object *obj, Eina_Bool state) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (state != wd->state) + { + wd->state = state; + if (wd->statep) *wd->statep = wd->state; + if (wd->state) + edje_object_signal_emit(wd->tgl, "elm,state,toggle,on", "elm"); + else + edje_object_signal_emit(wd->tgl, "elm,state,toggle,off", "elm"); + } +} + +/** + * Gets the state of the toggle to @p state. + * + * @param obj The toggle object + * @return The state of @p obj + * + * @ingroup Toggle + */ +EAPI Eina_Bool +elm_toggle_state_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->state; +} + +/** + * Sets the state pointer of the toggle to @p statep. + * + * @param obj The toggle object + * @param statep The state pointer of @p obj + * + * @ingroup Toggle + */ +EAPI void +elm_toggle_state_pointer_set(Evas_Object *obj, Eina_Bool *statep) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (statep) + { + wd->statep = statep; + if (*wd->statep != wd->state) + { + wd->state = *wd->statep; + if (wd->state) + edje_object_signal_emit(wd->tgl, "elm,state,toggle,on", "elm"); + else + edje_object_signal_emit(wd->tgl, "elm,state,toggle,off", "elm"); + } + } + else + wd->statep = NULL; +} diff --git a/src/lib/elm_toolbar.c b/src/lib/elm_toolbar.c new file mode 100644 index 0000000..3031216 --- /dev/null +++ b/src/lib/elm_toolbar.c @@ -0,0 +1,2250 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Toolbar Toolbar + * + * A toolbar is a widget that displays a list of buttons inside + * a box. It is scrollable, and only one item can be selected at a time. + */ + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *scr, *bx; + Evas_Object *menu_parent; + Eina_Inlist *items; + Elm_Toolbar_Item *more_item, *selected_item; + Elm_Toolbar_Shrink_Mode shrink_mode; + Elm_Icon_Lookup_Order lookup_order; + int icon_size; + double align; + Eina_Bool homogeneous : 1; + Eina_Bool no_select : 1; + Ecore_Job *resize_job; +}; + +struct _Elm_Toolbar_Item +{ + Elm_Widget_Item base; + EINA_INLIST; + const char *label; + const char *icon_str; + Evas_Object *icon; + Evas_Object *o_menu; + Evas_Smart_Cb func; + struct { + int priority; + Eina_Bool visible : 1; + } prio; + Eina_Bool selected : 1; + Eina_Bool disabled : 1; + Eina_Bool separator : 1; + Eina_Bool menu : 1; + Eina_List *states; + Eina_List *current_state; +}; + +#define ELM_TOOLBAR_ITEM_FROM_INLIST(item) \ + ((item) ? EINA_INLIST_CONTAINER_GET(item, Elm_Toolbar_Item) : NULL) + +struct _Elm_Toolbar_Item_State +{ + const char *label; + const char *icon_str; + Evas_Object *icon; + Evas_Smart_Cb func; + const void *data; +}; + +static const char *widtype = NULL; +static void _item_show(Elm_Toolbar_Item *it); +static void _item_select(Elm_Toolbar_Item *it); +static void _item_unselect(Elm_Toolbar_Item *it); +static void _item_disable(Elm_Toolbar_Item *it, Eina_Bool disabled); +static void _del_pre_hook(Evas_Object *obj); +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _resize(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _menu_move_resize(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _menu_hide(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _layout(Evas_Object *o, Evas_Object_Box_Data *priv, void *data); +static void _elm_toolbar_item_icon_obj_set(Evas_Object *obj, Elm_Toolbar_Item *item, Evas_Object *icon_obj, const char *icon_str, double icon_size, const char *signal); +static void _item_label_set(Elm_Toolbar_Item *item, const char *label, const char *signal); + +static Eina_Bool +_item_icon_set(Evas_Object *icon_obj, const char *type, const char *icon) +{ + char icon_str[512]; + + if ((!type) || (!*type)) goto end; + if ((!icon) || (!*icon)) return EINA_FALSE; + if ((snprintf(icon_str, sizeof(icon_str), "%s%s", type, icon) > 0) + && (elm_icon_standard_set(icon_obj, icon_str))) + return EINA_TRUE; +end: + if (elm_icon_standard_set(icon_obj, icon)) + return EINA_TRUE; + WRN("couldn't find icon definition for '%s'", icon); + return EINA_FALSE; +} + +static int +_elm_toolbar_icon_size_get(Widget_Data *wd) +{ + const char *icon_size = edje_object_data_get( + elm_smart_scroller_edje_object_get(wd->scr), "icon_size"); + if (icon_size) + return atoi(icon_size); + return _elm_config->icon_size; +} + +static void +_item_show(Elm_Toolbar_Item *it) +{ + Widget_Data *wd = elm_widget_data_get(it->base.widget); + Evas_Coord x, y, w, h, bx, by; + + if (!wd) return; + evas_object_geometry_get(wd->bx, &bx, &by, NULL, NULL); + evas_object_geometry_get(it->base.view, &x, &y, &w, &h); + elm_smart_scroller_child_region_show(wd->scr, x - bx, y - by, w, h); +} + +static void +_item_unselect(Elm_Toolbar_Item *item) +{ + Widget_Data *wd; + if ((!item) || (!item->selected)) return; + wd = elm_widget_data_get(item->base.widget); + if (!wd) return; + item->selected = EINA_FALSE; + wd->selected_item = NULL; + edje_object_signal_emit(item->base.view, "elm,state,unselected", "elm"); + elm_widget_signal_emit(item->icon, "elm,state,unselected", "elm"); +} + +static void +_item_select(Elm_Toolbar_Item *it) +{ + Elm_Toolbar_Item *it2; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + Evas_Object *obj2; + + if (!wd) return; + if ((it->selected) || (it->disabled) || (it->separator)) return; + + if (!wd->no_select) + { + it2 = elm_toolbar_selected_item_get(it->base.widget); + _item_unselect(it2); + + it->selected = EINA_TRUE; + wd->selected_item = it; + edje_object_signal_emit(it->base.view, "elm,state,selected", "elm"); + elm_widget_signal_emit(it->icon, "elm,state,selected", "elm"); + _item_show(it); + } + obj2 = it->base.widget; + if (it->menu) + { + evas_object_show(it->o_menu); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_RESIZE, + _menu_move_resize, it); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_MOVE, + _menu_move_resize, it); + + _menu_move_resize(it, NULL, NULL, NULL); + } + if (it->func) it->func((void *)(it->base.data), it->base.widget, it); + evas_object_smart_callback_call(obj2, "clicked", it); +} + +static void +_menu_hide(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Toolbar_Item *selected; + Elm_Toolbar_Item *it = data; + selected = elm_toolbar_selected_item_get(it->base.widget); + _item_unselect(selected); +} + +static void +_menu_del(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + // avoid hide being emitted during object deletion + evas_object_event_callback_del_full + (obj, EVAS_CALLBACK_HIDE, _menu_hide, data); +} + +static void +_menu_move_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Toolbar_Item *it = data; + Evas_Coord x,y,w,h; + Widget_Data *wd = elm_widget_data_get(it->base.widget); + + if ((!wd) || (!wd->menu_parent)) return; + evas_object_geometry_get(it->base.view, &x, &y, &w, &h); + elm_menu_move(it->o_menu, x, y+h); +} + +static void +_item_disable(Elm_Toolbar_Item *it, Eina_Bool disabled) +{ + Widget_Data *wd = elm_widget_data_get(it->base.widget); + + if (!wd) return; + if (it->disabled == disabled) return; + it->disabled = disabled; + if (it->disabled) + { + edje_object_signal_emit(it->base.view, "elm,state,disabled", "elm"); + elm_widget_signal_emit(it->icon, "elm,state,disabled", "elm"); + } + else + { + edje_object_signal_emit(it->base.view, "elm,state,enabled", "elm"); + elm_widget_signal_emit(it->icon, "elm,state,enabled", "elm"); + } +} + +static void +_item_del(Elm_Toolbar_Item *it) +{ + Elm_Toolbar_Item_State *it_state; + _item_unselect(it); + elm_widget_item_pre_notify_del(it); + EINA_LIST_FREE(it->states, it_state) + { + if (it->icon == it_state->icon) + it->icon = NULL; + eina_stringshare_del(it_state->label); + eina_stringshare_del(it_state->icon_str); + if (it_state->icon) evas_object_del(it_state->icon); + free(it_state); + } + eina_stringshare_del(it->label); + eina_stringshare_del(it->icon_str); + if (it->icon) evas_object_del(it->icon); + //TODO: See if checking for wd->menu_parent is necessary before deleting menu + if (it->o_menu) evas_object_del(it->o_menu); + elm_widget_item_del(it); +} + +static void +_del_pre_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Toolbar_Item *it, *next; + + if (!wd) return; + it = ELM_TOOLBAR_ITEM_FROM_INLIST(wd->items); + while(it) + { + next = ELM_TOOLBAR_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->next); + _item_del(it); + it = next; + } + if (wd->more_item) + _item_del(wd->more_item); +} + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + free(wd); +} + + +static void +_theme_hook_item(Evas_Object *obj, Elm_Toolbar_Item *it, double scale, int icon_size) +{ + Evas_Object *view = it->base.view; + Evas_Coord mw, mh; + const char *style = elm_widget_style_get(obj); + + edje_object_scale_set(view, scale); + if (!it->separator) + { + _elm_theme_object_set(obj, view, "toolbar", "item", style); + if (it->selected) + { + edje_object_signal_emit(view, "elm,state,selected", "elm"); + elm_widget_signal_emit(it->icon, "elm,state,selected", "elm"); + } + if (it->disabled) + { + edje_object_signal_emit(view, "elm,state,disabled", "elm"); + elm_widget_signal_emit(it->icon, "elm,state,disabled", "elm"); + } + if (it->icon) + { + int ms = 0; + + ms = ((double)icon_size * scale); + evas_object_size_hint_min_set(it->icon, ms, ms); + evas_object_size_hint_max_set(it->icon, ms, ms); + edje_object_part_swallow(view, "elm.swallow.icon", + it->icon); + } + edje_object_part_text_set(view, "elm.text", it->label); + } + else + _elm_theme_object_set(obj, view, "toolbar", "separator", style); + + mw = mh = -1; + if (!it->separator) + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + edje_object_size_min_restricted_calc(view, &mw, &mh, mw, mh); + if (!it->separator) + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + evas_object_size_hint_min_set(view, mw, mh); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Elm_Toolbar_Item *it; + double scale = 0; + + if (!wd) return; + elm_smart_scroller_object_theme_set(obj, wd->scr, "toolbar", "base", elm_widget_style_get(obj)); + scale = (elm_widget_scale_get(obj) * _elm_config->scale); + edje_object_scale_set(wd->scr, scale); + wd->icon_size = _elm_toolbar_icon_size_get(wd); + EINA_INLIST_FOREACH(wd->items, it) + _theme_hook_item(obj, it, scale, wd->icon_size); + if (wd->more_item) + _theme_hook_item(obj, wd->more_item, scale, wd->icon_size); + _sizing_eval(obj); +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1, minw_bx; + Evas_Coord vw = 0, vh = 0; + Evas_Coord w, h; + + if (!wd) return; + evas_object_smart_calculate(wd->bx); + edje_object_size_min_calc(elm_smart_scroller_edje_object_get(wd->scr), + &minw, &minh); + evas_object_geometry_get(obj, NULL, NULL, &w, &h); + if (w < minw) w = minw; + if (h < minh) h = minh; + + evas_object_resize(wd->scr, w, h); + + evas_object_size_hint_min_get(wd->bx, &minw, &minh); + minw_bx = minw; + if (w > minw) minw = w; + evas_object_resize(wd->bx, minw, minh); + elm_smart_scroller_child_viewport_size_get(wd->scr, &vw, &vh); + switch (wd->shrink_mode) + { + case ELM_TOOLBAR_SHRINK_MENU: /* fallthrough */ + case ELM_TOOLBAR_SHRINK_HIDE: /* fallthrough */ + case ELM_TOOLBAR_SHRINK_SCROLL: minw = w - vw; break; + case ELM_TOOLBAR_SHRINK_NONE: minw = minw_bx + (w - vw); break; + } + minh = minh + (h - vh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_item_menu_create(Widget_Data *wd, Elm_Toolbar_Item *item) +{ + item->o_menu = elm_menu_add(item->base.view); + if (wd->menu_parent) + elm_menu_parent_set(item->o_menu, wd->menu_parent); + evas_object_event_callback_add(item->o_menu, EVAS_CALLBACK_HIDE, + _menu_hide, item); + evas_object_event_callback_add(item->o_menu, EVAS_CALLBACK_DEL, + _menu_del, item); +} + +static void +_item_menu_destroy(Elm_Toolbar_Item *item) +{ + if (item->o_menu) + { + evas_object_del(item->o_menu); + item->o_menu = NULL; + } +} + +static int +_toolbar_item_prio_compare_cb(const void *i1, const void *i2) +{ + const Elm_Toolbar_Item *eti1 = i1; + const Elm_Toolbar_Item *eti2 = i2; + + if (!eti2) return 1; + if (!eti1) return -1; + + return eti2->prio.priority - eti1->prio.priority; +} + +static void +_fix_items_visibility(Widget_Data *wd, Evas_Coord *iw, Evas_Coord vw) +{ + Elm_Toolbar_Item *it; + Eina_List *sorted = NULL; + Evas_Coord ciw; + + EINA_INLIST_FOREACH(wd->items, it) + { + sorted = eina_list_sorted_insert(sorted, + _toolbar_item_prio_compare_cb, it); + } + + if (wd->more_item) + { + evas_object_geometry_get(wd->more_item->base.view, NULL, NULL, &ciw, NULL); + *iw += ciw; + } + EINA_LIST_FREE(sorted, it) + { + evas_object_geometry_get(it->base.view, NULL, NULL, &ciw, NULL); + *iw += ciw; + it->prio.visible = (*iw <= vw); + } +} + +static void +_elm_toolbar_item_menu_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Toolbar_Item *it = data; + if (it->func) it->func((void *)(it->base.data), it->base.widget, it); +} + +static void +_resize_job(void *data) +{ + Widget_Data *wd = elm_widget_data_get(data); + Evas_Coord mw, mh, vw, vh, w, h; + Elm_Toolbar_Item *it; + + if (!wd) return; + wd->resize_job = NULL; + elm_smart_scroller_child_viewport_size_get(wd->scr, &vw, &vh); + evas_object_size_hint_min_get(wd->bx, &mw, &mh); + evas_object_geometry_get(wd->bx, NULL, NULL, &w, &h); + if (wd->shrink_mode == ELM_TOOLBAR_SHRINK_MENU) + { + Evas_Coord iw = 0, more_w; + + evas_object_resize(wd->bx, vw, h); + _fix_items_visibility(wd, &iw, vw); + evas_object_geometry_get(wd->more_item->base.view, NULL, NULL, &more_w, NULL); + if (iw - more_w <= vw) + iw -= more_w; + + /* All items are removed from the box object, since removing individual + * items won't trigger a resize. Items are be readded below. */ + evas_object_box_remove_all(wd->bx, EINA_FALSE); + if (iw > vw) + { + Evas_Object *menu; + + _item_menu_destroy(wd->more_item); + _item_menu_create(wd, wd->more_item); + menu = elm_toolbar_item_menu_get(wd->more_item); + + EINA_INLIST_FOREACH(wd->items, it) + { + if (!it->prio.visible) + { + if (it->separator) + elm_menu_item_separator_add(menu, NULL); + else + { + Elm_Menu_Item *item; + item = elm_menu_item_add(menu, NULL, it->icon_str, it->label, + _elm_toolbar_item_menu_cb, it); + elm_menu_item_disabled_set(item, it->disabled); + if (it->o_menu) elm_menu_clone(it->o_menu, menu, item); + } + evas_object_hide(it->base.view); + } + else + { + evas_object_box_append(wd->bx, it->base.view); + evas_object_show(it->base.view); + } + } + + evas_object_box_append(wd->bx, wd->more_item->base.view); + evas_object_show(wd->more_item->base.view); + } + else + { + /* All items are visible, show them all (except for the "More" + * button, of course). */ + EINA_INLIST_FOREACH(wd->items, it) + { + evas_object_show(it->base.view); + evas_object_box_append(wd->bx, it->base.view); + } + evas_object_hide(wd->more_item->base.view); + } + } + else if (wd->shrink_mode == ELM_TOOLBAR_SHRINK_HIDE) + { + Evas_Coord iw = 0; + + evas_object_resize(wd->bx, vw, h); + _fix_items_visibility(wd, &iw, vw); + evas_object_box_remove_all(wd->bx, EINA_FALSE); + if (iw > vw) + { + EINA_INLIST_FOREACH(wd->items, it) + { + if (!it->prio.visible) + evas_object_hide(it->base.view); + else + { + evas_object_box_append(wd->bx, it->base.view); + evas_object_show(it->base.view); + } + } + } + else + { + /* All items are visible, show them all */ + EINA_INLIST_FOREACH(wd->items, it) + { + evas_object_show(it->base.view); + evas_object_box_append(wd->bx, it->base.view); + } + } + } + else + { + if ((vw >= mw) && (w != vw)) evas_object_resize(wd->bx, vw, h); + EINA_INLIST_FOREACH(wd->items, it) + { + if (it->selected) + { + _item_show(it); + break; + } + } + } +} + +static void +_resize_item(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); + _resize(data, NULL, NULL, NULL); +} + +static void +_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Widget_Data *wd = elm_widget_data_get(data); + if (!wd->resize_job) + wd->resize_job = ecore_job_add(_resize_job, data); +} + +static void +_select(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + _item_select(data); +} + +static void +_mouse_in(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Elm_Toolbar_Item *it = data; + edje_object_signal_emit(it->base.view, "elm,state,highlighted", "elm"); + elm_widget_signal_emit(it->icon, "elm,state,highlighted", "elm"); +} + +static void +_mouse_out(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Elm_Toolbar_Item *it = data; + edje_object_signal_emit(it->base.view, "elm,state,unhighlighted", "elm"); + elm_widget_signal_emit(it->icon, "elm,state,unhighlighted", "elm"); +} + +static void +_layout(Evas_Object *o, Evas_Object_Box_Data *priv, void *data) +{ + Widget_Data *wd = data; + if (!wd) return; + _els_box_layout(o, priv, 1, wd->homogeneous); +} + +static Elm_Toolbar_Item * +_item_new(Evas_Object *obj, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *icon_obj; + Evas_Coord mw, mh; + Elm_Toolbar_Item *it; + + icon_obj = elm_icon_add(obj); + elm_icon_order_lookup_set(icon_obj, wd->lookup_order); + if (!icon_obj) return NULL; + it = elm_widget_item_new(obj, Elm_Toolbar_Item); + if (!it) + { + evas_object_del(icon_obj); + return NULL; + } + it->label = eina_stringshare_add(label); + it->prio.visible = 1; + it->prio.priority = 0; + it->func = func; + it->separator = EINA_FALSE; + it->base.data = data; + it->base.view = edje_object_add(evas_object_evas_get(obj)); + if (_item_icon_set(icon_obj, "toolbar/", icon)) + { + it->icon = icon_obj; + it->icon_str = eina_stringshare_add(icon); + } + else + { + it->icon = NULL; + it->icon_str = NULL; + evas_object_del(icon_obj); + } + + _elm_theme_object_set(obj, it->base.view, "toolbar", "item", + elm_widget_style_get(obj)); + edje_object_signal_callback_add(it->base.view, "elm,action,click", "elm", + _select, it); + edje_object_signal_callback_add(it->base.view, "elm,mouse,in", "elm", + _mouse_in, it); + edje_object_signal_callback_add(it->base.view, "elm,mouse,out", "elm", + _mouse_out, it); + elm_widget_sub_object_add(obj, it->base.view); + if (it->icon) + { + int ms = 0; + + ms = ((double)wd->icon_size * _elm_config->scale); + evas_object_size_hint_min_set(it->icon, ms, ms); + evas_object_size_hint_max_set(it->icon, ms, ms); + edje_object_part_swallow(it->base.view, "elm.swallow.icon", it->icon); + evas_object_show(it->icon); + elm_widget_sub_object_add(obj, it->icon); + } + edje_object_part_text_set(it->base.view, "elm.text", it->label); + mw = mh = -1; + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + edje_object_size_min_restricted_calc(it->base.view, &mw, &mh, mw, mh); + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + evas_object_size_hint_weight_set(it->base.view, -1.0, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(it->base.view, 0.5, EVAS_HINT_FILL); + evas_object_size_hint_min_set(it->base.view, mw, mh); + evas_object_event_callback_add(it->base.view, EVAS_CALLBACK_RESIZE, + _resize_item, obj); + return it; +} + +/** + * Add a toolbar object to @p parent. + * + * @param parent The parent object + * + * @return The created object, or NULL on failure + * + * @ingroup Toolbar + */ +EAPI Evas_Object * +elm_toolbar_add(Evas_Object *parent) +{ + Evas_Object *obj; + Evas *e; + Widget_Data *wd; + + EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL); + + wd = ELM_NEW(Widget_Data); + e = evas_object_evas_get(parent); + if (!e) return NULL; + obj = elm_widget_add(e); + ELM_SET_WIDTYPE(widtype, "toolbar"); + elm_widget_type_set(obj, "toolbar"); + elm_widget_sub_object_add(parent, obj); + elm_widget_data_set(obj, wd); + elm_widget_del_pre_hook_set(obj, _del_pre_hook); + elm_widget_del_hook_set(obj, _del_hook); + elm_widget_theme_hook_set(obj, _theme_hook); + elm_widget_can_focus_set(obj, EINA_FALSE); + + wd->more_item = NULL; + wd->selected_item = NULL; + wd->scr = elm_smart_scroller_add(e); + elm_smart_scroller_widget_set(wd->scr, obj); + elm_smart_scroller_object_theme_set(obj, wd->scr, "toolbar", "base", "default"); + elm_smart_scroller_bounce_allow_set(wd->scr, + _elm_config->thumbscroll_bounce_enable, + EINA_FALSE); + elm_widget_resize_object_set(obj, wd->scr); + elm_smart_scroller_policy_set(wd->scr, + ELM_SMART_SCROLLER_POLICY_AUTO, + ELM_SMART_SCROLLER_POLICY_OFF); + + + wd->icon_size = _elm_toolbar_icon_size_get(wd); + + + wd->homogeneous = EINA_TRUE; + wd->align = 0.5; + + wd->bx = evas_object_box_add(e); + evas_object_size_hint_align_set(wd->bx, wd->align, 0.5); + evas_object_box_layout_set(wd->bx, _layout, wd, NULL); + elm_widget_sub_object_add(obj, wd->bx); + elm_smart_scroller_child_set(wd->scr, wd->bx); + evas_object_show(wd->bx); + + elm_toolbar_mode_shrink_set(obj, _elm_config->toolbar_shrink_mode); + evas_object_event_callback_add(wd->scr, EVAS_CALLBACK_RESIZE, _resize, obj); + evas_object_event_callback_add(wd->bx, EVAS_CALLBACK_RESIZE, _resize, obj); + elm_toolbar_icon_order_lookup_set(obj, ELM_ICON_LOOKUP_THEME_FDO); + + _sizing_eval(obj); + return obj; +} + +/** + * Set the icon size (in pixels) for the toolbar. + * + * @param obj The toolbar object + * @param icon_size The icon size in pixels + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_icon_size_set(Evas_Object *obj, int icon_size) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->icon_size == icon_size) return; + wd->icon_size = icon_size; + _theme_hook(obj); +} + +/** + * Get the icon size (in pixels) for the toolbar. + * + * @param obj The toolbar object + * @return The icon size in pixels + * + * @ingroup Toolbar + */ +EAPI int +elm_toolbar_icon_size_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return 0; + return wd->icon_size; +} + +/** + * Append item to the toolbar + * + * @param obj The toolbar object + * @param icon A string with icon name or the absolute path of an image file. + * @param label The label of the item + * @param func The function to call when the item is clicked + * @param data The data to associate with the item + * @return The toolbar item, or NULL upon failure + * + * @see elm_toolbar_item_icon_set + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_item_append(Evas_Object *obj, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + Elm_Toolbar_Item *it = _item_new(obj, icon, label, func, data); + if (!it) return NULL; + + wd->items = eina_inlist_append(wd->items, EINA_INLIST_GET(it)); + evas_object_box_append(wd->bx, it->base.view); + evas_object_show(it->base.view); + _sizing_eval(obj); + + return it; +} + +static void +_elm_toolbar_item_state_cb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Elm_Toolbar_Item *it = event_info; + Elm_Toolbar_Item_State *it_state; + + it_state = eina_list_data_get(it->current_state); + if (it_state->func) + it_state->func((void *)it_state->data, obj, event_info); +} + +/** + * Sets the next @p item state as the current state. + * + * @param item The item. + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item_State * +elm_toolbar_item_state_next(Elm_Toolbar_Item *item) +{ + Widget_Data *wd; + Evas_Object *obj; + Eina_List *next_state; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + + obj = item->base.widget; + wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!item->states) return NULL; + + next_state = eina_list_next(item->current_state); + if (!next_state) + next_state = eina_list_next(item->states); + return eina_list_data_get(next_state); +} + +/** + * Sets the previous @p item state as the current state. + * + * @param item The item. + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item_State * +elm_toolbar_item_state_prev(Elm_Toolbar_Item *item) +{ + Widget_Data *wd; + Evas_Object *obj; + Eina_List *prev_state; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + + obj = item->base.widget; + wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!item->states) return NULL; + + prev_state = eina_list_prev(item->current_state); + if ((!prev_state) || (prev_state == item->states)) + prev_state = eina_list_last(item->states); + return eina_list_data_get(prev_state); +} + +/** + * Unset the state of @p it + * The default icon and label from this item will be displayed. + * + * @param it The item. + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_state_unset(Elm_Toolbar_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it); + elm_toolbar_item_state_set(it, NULL); +} + +/** + * Sets @p state as the current state of @p it. + * If @p state is NULL, it won't select any state and the default icon and + * label will be used. + * + * @param it The item. + * @param state The state to use. + * + * @return True if the state was correctly set. + * + * @ingroup Toolbar + */ +EAPI Eina_Bool +elm_toolbar_item_state_set(Elm_Toolbar_Item *it, Elm_Toolbar_Item_State *state) +{ + Widget_Data *wd; + Eina_List *next_state; + Elm_Toolbar_Item_State *it_state; + Evas_Object *obj; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, EINA_FALSE); + + obj = it->base.widget; + wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + if (!it->states) return EINA_FALSE; + + if (state) + { + next_state = eina_list_data_find_list(it->states, state); + if (!next_state) return EINA_FALSE; + } + else + next_state = it->states; + + if (next_state == it->current_state) return EINA_TRUE; + + it_state = eina_list_data_get(next_state); + if (eina_list_data_find(it->current_state, state)) + { + _item_label_set(it, it_state->label, "elm,state,label_set,forward"); + _elm_toolbar_item_icon_obj_set(obj, it, it_state->icon, it_state->icon_str, + wd->icon_size, "elm,state,icon_set,forward"); + } + else + { + _item_label_set(it, it_state->label, "elm,state,label_set,backward"); + _elm_toolbar_item_icon_obj_set(obj, it, it_state->icon, it_state->icon_str, + wd->icon_size, "elm,state,icon_set,backward"); + } + if (it->disabled) + elm_widget_signal_emit(it->icon, "elm,state,disabled", "elm"); + else + elm_widget_signal_emit(it->icon, "elm,state,enabled", "elm"); + + it->current_state = next_state; + return EINA_TRUE; +} + +/** + * Get the current state of @p item. + * If no state is selected, returns NULL. + * + * @param item The item. + * + * @return The state. + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item_State * +elm_toolbar_item_state_get(const Elm_Toolbar_Item *it) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, NULL); + if ((!it->states) || (!it->current_state)) return NULL; + if (it->current_state == it->states) return NULL; + + return eina_list_data_get(it->current_state); +} + +static Elm_Toolbar_Item_State * +_item_state_new(const char *label, const char *icon_str, Evas_Object *icon, Evas_Smart_Cb func, const void *data) +{ + Elm_Toolbar_Item_State *it_state; + it_state = ELM_NEW(Elm_Toolbar_Item_State); + it_state->label = eina_stringshare_add(label); + it_state->icon_str = eina_stringshare_add(icon_str); + it_state->icon = icon; + it_state->func = func; + it_state->data = data; + return it_state; +} + +/** + * Add a new state to @p item + * + * @param item The item. + * @param icon The icon string + * @param label The label of the new state + * @param func The function to call when the item is clicked when this state is + * selected. + * @param data The data to associate with the state + * @return The toolbar item state, or NULL upon failure + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item_State * +elm_toolbar_item_state_add(Elm_Toolbar_Item *item, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) +{ + Elm_Toolbar_Item_State *it_state; + Evas_Object *icon_obj; + Evas_Object *obj; + Widget_Data *wd; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + obj = item->base.widget; + wd = elm_widget_data_get(item->base.widget); + if (!wd) return NULL; + + if (!item->states) + { + it_state = _item_state_new(item->label, item->icon_str, item->icon, + item->func, item->base.data); + item->states = eina_list_append(item->states, it_state); + item->current_state = item->states; + } + + icon_obj = elm_icon_add(obj); + elm_icon_order_lookup_set(icon_obj, wd->lookup_order); + if (!icon_obj) goto error_state_add; + + if (!_item_icon_set(icon_obj, "toolbar/", icon)) + { + evas_object_del(icon_obj); + icon_obj = NULL; + icon = NULL; + } + + it_state = _item_state_new(label, icon, icon_obj, func, data); + item->states = eina_list_append(item->states, it_state); + item->func = _elm_toolbar_item_state_cb; + item->base.data = NULL; + + return it_state; + +error_state_add: + if (item->states && !eina_list_next(item->states)) + { + eina_stringshare_del(item->label); + eina_stringshare_del(item->icon_str); + free(eina_list_data_get(item->states)); + eina_list_free(item->states); + item->states = NULL; + } + return NULL; +} + +EAPI Eina_Bool +elm_toolbar_item_state_del(Elm_Toolbar_Item *item, Elm_Toolbar_Item_State *state) +{ + Eina_List *del_state; + Elm_Toolbar_Item_State *it_state; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + + if (!state) return EINA_FALSE; + if (!item->states) return EINA_FALSE; + + del_state = eina_list_data_find_list(item->states, state); + if (del_state == item->states) return EINA_FALSE; + if (del_state == item->current_state) + elm_toolbar_item_state_unset(item); + + eina_stringshare_del(state->label); + eina_stringshare_del(state->icon_str); + if (state->icon) evas_object_del(state->icon); + free(state); + item->states = eina_list_remove_list(item->states, del_state); + if (item->states && !eina_list_next(item->states)) + { + it_state = eina_list_data_get(item->states); + item->base.data = it_state->data; + item->func = it_state->func; + eina_stringshare_del(it_state->label); + eina_stringshare_del(it_state->icon_str); + free(eina_list_data_get(item->states)); + eina_list_free(item->states); + item->states = NULL; + } + return EINA_TRUE; +} + + +/** + * Prepend item to the toolbar + * + * @param obj The toolbar object + * @param icon A string with icon name or the absolute path of an image file. + * @param label The label of the item + * @param func The function to call when the item is clicked + * @param data The data to associate with the item + * @return The toolbar item, or NULL upon failure + * + * @see elm_toolbar_item_icon_set + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_item_prepend(Evas_Object *obj, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + Elm_Toolbar_Item *it = _item_new(obj, icon, label, func, data); + if (!it) return NULL; + + wd->items = eina_inlist_prepend(wd->items, EINA_INLIST_GET(it)); + evas_object_box_prepend(wd->bx, it->base.view); + evas_object_show(it->base.view); + _sizing_eval(obj); + + return it; +} + +/** + * Insert item before another in the toolbar + * + * @param obj The toolbar object + * @param before The item to insert before + * @param icon A string with icon name or the absolute path of an image file. + * @param label The label of the item + * @param func The function to call when the item is clicked + * @param data The data to associate with the item + * @return The toolbar item, or NULL upon failure + * + * @see elm_toolbar_item_icon_set + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_item_insert_before(Evas_Object *obj, Elm_Toolbar_Item *before, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(before, NULL); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + Elm_Toolbar_Item *it = _item_new(obj, icon, label, func, data); + if (!it) return NULL; + + wd->items = eina_inlist_prepend_relative(wd->items, EINA_INLIST_GET(it), + EINA_INLIST_GET(before)); + evas_object_box_insert_before(wd->bx, it->base.view, before->base.view); + evas_object_show(it->base.view); + _sizing_eval(obj); + + return it; +} + +/** + * Insert item after another in the toolbar + * + * @param obj The toolbar object + * @param after The item to insert after + * @param icon A string with icon name or the absolute path of an image file. + * @param label The label of the item + * @param func The function to call when the item is clicked + * @param data The data to associate with the item + * @return The toolbar item, or NULL upon failure + * + * @see elm_toolbar_item_icon_set + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_item_insert_after(Evas_Object *obj, Elm_Toolbar_Item *after, const char *icon, const char *label, Evas_Smart_Cb func, const void *data) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(after, NULL); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + + Elm_Toolbar_Item *it = _item_new(obj, icon, label, func, data); + if (!it) return NULL; + + wd->items = eina_inlist_append_relative(wd->items, EINA_INLIST_GET(it), + EINA_INLIST_GET(after)); + evas_object_box_insert_after(wd->bx, it->base.view, after->base.view); + evas_object_show(it->base.view); + _sizing_eval(obj); + + return it; +} + +/** + * Get the first item in the toolbar + * + * @param obj The toolbar object + * @return The first item, or NULL if none + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_first_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd || !wd->items) return NULL; + Elm_Toolbar_Item *it = ELM_TOOLBAR_ITEM_FROM_INLIST(wd->items); + return it; +} + +/** + * Get the last item in the toolbar + * + * @return The last item, or NULL if none + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_last_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd || !wd->items) return NULL; + Elm_Toolbar_Item *it = ELM_TOOLBAR_ITEM_FROM_INLIST(wd->items->last); + return it; +} + +/** + * Get the next item in the toolbar + * + * This returns the item after the item @p it. + * + * @param item The item + * @return The item after @p it, or NULL if none + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_item_next_get(const Elm_Toolbar_Item *item) +{ + Elm_Toolbar_Item *next; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + next = ELM_TOOLBAR_ITEM_FROM_INLIST(EINA_INLIST_GET(item)->next); + return next; +} + +/** + * Get the previous item in the toolbar + * + * This returns the item before the item @p it. + * + * @param item The item + * @return The item before @p it, or NULL if none + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_item_prev_get(const Elm_Toolbar_Item *item) +{ + Elm_Toolbar_Item *prev; + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + prev = ELM_TOOLBAR_ITEM_FROM_INLIST(EINA_INLIST_GET(item)->prev); + return prev; +} + +/** + * Get the toolbar object from an item + * + * This returns the toolbar object itself that an item belongs to. + * + * @param item The item + * @return The toolbar object + * + * @ingroup Toolbar + */ +EAPI Evas_Object * +elm_toolbar_item_toolbar_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->base.widget; +} + +/** + * Sets the priority of a toolbar item. This is used only when the toolbar + * shrink mode is set to ELM_TOOLBAR_SHRINK_MENU or ELM_TOOLBAR_SHRINK_HIDE: + * when space is at a premium, items with low priority will be removed from + * the toolbar and added to a dynamically-created menu, while items with + * higher priority will remain on the toolbar, with the same order they were + * added. + * + * @param item The toolbar item. + * @param priority The item priority. The default is zero. + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_priority_set(Elm_Toolbar_Item *item, int priority) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (item->prio.priority == priority) return; + item->prio.priority = priority; + _resize(item->base.widget, NULL, NULL, NULL); +} + +/** + * Gets the priority of a toolbar item. + * + * @param item The toolbar item. + * @return The item priority, or 0 if an error occurred. + * + * @ingroup Toolbar + */ +EAPI int +elm_toolbar_item_priority_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, 0); + return item->prio.priority; +} + +/** + * Get the string used to set the icon of @p item. + * + * @param item The toolbar item + * @return The string associated with the icon object. + * + * @see elm_toolbar_item_icon_set() + * + * @ingroup Toolbar + */ +EAPI const char * +elm_toolbar_item_icon_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->icon_str; +} + +/** + * Get the label associated with @p item. + * + * @param item The toolbar item + * @return The label + * + * @ingroup Toolbar + */ +EAPI const char * +elm_toolbar_item_label_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return item->label; +} + +static void +_elm_toolbar_item_label_update(Elm_Toolbar_Item *item) +{ + Evas_Coord mw = -1, mh = -1; + edje_object_part_text_set(item->base.view, "elm.text", item->label); + + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + edje_object_size_min_restricted_calc(item->base.view, &mw, &mh, mw, mh); + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + evas_object_size_hint_weight_set(item->base.view, -1.0, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(item->base.view, 0.5, EVAS_HINT_FILL); + evas_object_size_hint_min_set(item->base.view, mw, mh); +} + +static void +_elm_toolbar_item_label_set_cb (void *data, Evas_Object *obj, const char *emission, const char *source) +{ + Elm_Toolbar_Item *item = data; + _elm_toolbar_item_label_update(item); + edje_object_signal_callback_del(obj, emission, source, + _elm_toolbar_item_label_set_cb); + edje_object_signal_emit (item->base.view, "elm,state,label,reset", "elm"); +} + +static void +_item_label_set(Elm_Toolbar_Item *item, const char *label, const char *signal) +{ + const char *s; + + if ((label) && (item->label) && (!strcmp(label, item->label))) return; + + eina_stringshare_replace(&item->label, label); + s = edje_object_data_get(item->base.view, "transition_animation_on"); + if ((s) && (atoi(s))) + { + edje_object_part_text_set(item->base.view, "elm.text_new", item->label); + edje_object_signal_emit (item->base.view, signal, "elm"); + edje_object_signal_callback_add(item->base.view, + "elm,state,label_set,done", "elm", + _elm_toolbar_item_label_set_cb, item); + } + else + _elm_toolbar_item_label_update(item); + _resize(item->base.widget, NULL, NULL, NULL); +} + +/** + * Set the label associated with @p item. + * + * @param item The toolbar item + * @param label The label of @p item + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_label_set(Elm_Toolbar_Item *item, const char *label) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + _item_label_set(item, label, "elm,state,label_set"); +} + +static void +_elm_toolbar_item_icon_update(Elm_Toolbar_Item *item) +{ + Elm_Toolbar_Item_State *it_state; + Eina_List *l; + Evas_Coord mw = -1, mh = -1; + Evas_Object *old_icon = edje_object_part_swallow_get(item->base.view, + "elm.swallow.icon"); + elm_widget_sub_object_del(item->base.view, old_icon); + evas_object_hide(old_icon); + edje_object_part_swallow(item->base.view, "elm.swallow.icon", item->icon); + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + edje_object_size_min_restricted_calc(item->base.view, &mw, &mh, mw, mh); + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + evas_object_size_hint_weight_set(item->base.view, -1.0, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(item->base.view, 0.5, EVAS_HINT_FILL); + evas_object_size_hint_min_set(item->base.view, mw, mh); + + EINA_LIST_FOREACH(item->states, l, it_state) + if (it_state->icon == old_icon) + return; + evas_object_del(old_icon); +} + +/** + * Get the selected state of @p item. + * + * @param item The toolbar item + * @return If true, the item is selected + * + * @ingroup Toolbar + */ +EAPI Eina_Bool +elm_toolbar_item_selected_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + return item->selected; +} + +/** + * Set the selected state of an item + * + * This sets the selected state (1 selected, 0 not selected) of the given + * item @p it. If a new item is selected the previosly selected will be + * unselected. + * + * @param item The item + * @param selected The selected state + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_selected_set(Elm_Toolbar_Item *item, Eina_Bool selected) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + Widget_Data *wd = elm_widget_data_get(item->base.widget); + if (!wd) return; + + if (item->selected == selected) return; + + if (selected) + _item_select(item); + else + _item_unselect(item); +} + +/** + * Get the selectd item in the toolbar + * + * If no item is selected, NULL is returned. + * + * @param obj The toolbar object + * @return The selected item, or NULL if none. + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_selected_item_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->selected_item; +} + +static void +_elm_toolbar_item_icon_set_cb (void *data, Evas_Object *obj, const char *emission, const char *source) +{ + Elm_Toolbar_Item *item = data; + edje_object_part_unswallow(item->base.view, item->icon); + _elm_toolbar_item_icon_update(item); + edje_object_signal_callback_del(obj, emission, source, + _elm_toolbar_item_icon_set_cb); + edje_object_signal_emit (item->base.view, "elm,state,icon,reset", "elm"); +} + +static void +_elm_toolbar_item_icon_obj_set(Evas_Object *obj, Elm_Toolbar_Item *item, Evas_Object *icon_obj, const char *icon_str, double icon_size, const char *signal) +{ + Evas_Object *old_icon; + int ms = 0; + const char *s; + + if (icon_str) + eina_stringshare_replace(&item->icon_str, icon_str); + else + { + eina_stringshare_del(item->icon_str); + item->icon_str = NULL; + } + item->icon = icon_obj; + if (icon_obj) + { + ms = (icon_size * _elm_config->scale); + evas_object_size_hint_min_set(item->icon, ms, ms); + evas_object_size_hint_max_set(item->icon, ms, ms); + evas_object_show(item->icon); + elm_widget_sub_object_add(obj, item->icon); + } + s = edje_object_data_get(item->base.view, "transition_animation_on"); + if ((s) && (atoi(s))) + { + old_icon = edje_object_part_swallow_get(item->base.view, + "elm.swallow.icon_new"); + if (old_icon) + { + elm_widget_sub_object_del(item->base.view, old_icon); + evas_object_hide(old_icon); + } + edje_object_part_swallow(item->base.view, "elm.swallow.icon_new", + item->icon); + edje_object_signal_emit (item->base.view, signal, "elm"); + edje_object_signal_callback_add(item->base.view, + "elm,state,icon_set,done", "elm", + _elm_toolbar_item_icon_set_cb, item); + } + else + _elm_toolbar_item_icon_update(item); + _resize(obj, NULL, NULL, NULL); +} + +/** + * Set the icon associated with @p item. + * + * Toolbar will load icon image from fdo or current theme. + * This behavior can be set by elm_toolbar_icon_order_lookup_set() function. + * If an absolute path is provided it will load it direct from a file. + * + * @param obj The parent of this item + * @param item The toolbar item + * @param icon A string with icon name or the absolute path of an image file. + * + * @see elm_toolbar_icon_order_lookup_set(), elm_toolbar_icon_order_lookup_get() + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_icon_set(Elm_Toolbar_Item *item, const char *icon) +{ + Evas_Object *icon_obj; + Widget_Data *wd; + Evas_Object *obj = item->base.widget; + + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + wd = elm_widget_data_get(obj); + if (!wd) return; + if ((icon) && (item->icon_str) && (!strcmp(icon, item->icon_str))) return; + + icon_obj = elm_icon_add(obj); + if (!icon_obj) return; + if (_item_icon_set(icon_obj, "toolbar/", icon)) + _elm_toolbar_item_icon_obj_set(obj, item, icon_obj, icon, wd->icon_size, + "elm,state,icon_set"); + else + { + _elm_toolbar_item_icon_obj_set(obj, item, NULL, NULL, 0, + "elm,state,icon_set"); + evas_object_del(icon_obj); + } +} + +/** + * Delete a toolbar item. + * + * @param item The toolbar item + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_del(Elm_Toolbar_Item *item) +{ + Widget_Data *wd; + Evas_Object *obj2; + + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + wd = elm_widget_data_get(item->base.widget); + if (!wd) return; + obj2 = item->base.widget; + wd->items = eina_inlist_remove(wd->items, EINA_INLIST_GET(item)); + _item_del(item); + _theme_hook(obj2); +} + +/** + * Set the function called when a toolbar item is freed. + * + * @param item The item to set the callback on + * @param func The function called + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_del_cb_set(Elm_Toolbar_Item *item, Evas_Smart_Cb func) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_del_cb_set(item, func); +} + +/** + * Get the disabled state of @p item. + * + * @param item The toolbar item + * @return If true, the item is disabled + * + * @ingroup Toolbar + */ +EAPI Eina_Bool +elm_toolbar_item_disabled_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + return item->disabled; +} + +/** + * Set the disabled state of @p item. + * + * @param item The toolbar item + * @param disabled If true, the item is disabled + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_disabled_set(Elm_Toolbar_Item *item, Eina_Bool disabled) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + _item_disable(item, disabled); + _resize(item->base.widget, NULL, NULL, NULL); +} + +/** + * Get the separator state of @p item. + * + * @param item The toolbar item + * @param separator If true, the item is a separator + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_separator_set(Elm_Toolbar_Item *item, Eina_Bool separator) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + if (item->separator == separator) return; + item->separator = separator; + _theme_hook(item->base.view); +} + +/** + * Set the separator state of @p item. + * + * @param item The toolbar item + * @return If true, the item is a separator + * + * @ingroup Toolbar + */ +EAPI Eina_Bool +elm_toolbar_item_separator_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + return item->separator; +} + +/** + * Set the shrink state of toolbar @p obj. + * + * @param obj The toolbar object + * @param shrink_mode The toolbar won't scroll if ELM_TOOLBAR_SHRINK_NONE, + * but will enforce a minimun size so all the items will fit, won't scroll + * and won't show the items that don't fit if ELM_TOOLBAR_SHRINK_HIDE, + * will scroll if ELM_TOOLBAR_SHRINK_SCROLL, and will create a button to + * pop up excess elements with ELM_TOOLBAR_SHRINK_MENU. + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_mode_shrink_set(Evas_Object *obj, Elm_Toolbar_Shrink_Mode shrink_mode) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + Eina_Bool bounce; + + if (!wd) return; + wd->shrink_mode = shrink_mode; + bounce = (_elm_config->thumbscroll_bounce_enable) && + (shrink_mode == ELM_TOOLBAR_SHRINK_SCROLL); + elm_smart_scroller_bounce_allow_set(wd->scr, bounce, EINA_FALSE); + + if (wd->more_item) + { + _item_del(wd->more_item); + wd->more_item = NULL; + } + + if (shrink_mode == ELM_TOOLBAR_SHRINK_MENU) + { + elm_smart_scroller_policy_set(wd->scr, ELM_SMART_SCROLLER_POLICY_OFF, ELM_SMART_SCROLLER_POLICY_OFF); + + wd->more_item = _item_new(obj, "more_menu", "More", + NULL, NULL); + } + else if (shrink_mode == ELM_TOOLBAR_SHRINK_HIDE) + elm_smart_scroller_policy_set(wd->scr, ELM_SMART_SCROLLER_POLICY_OFF, + ELM_SMART_SCROLLER_POLICY_OFF); + else + elm_smart_scroller_policy_set(wd->scr, ELM_SMART_SCROLLER_POLICY_AUTO, + ELM_SMART_SCROLLER_POLICY_OFF); + _sizing_eval(obj); +} + +/** + * Get the shrink mode of toolbar @p obj. + * + * @param obj The toolbar object + * @return See elm_toolbar_mode_shrink_set. + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Shrink_Mode +elm_toolbar_mode_shrink_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_TOOLBAR_SHRINK_NONE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return ELM_TOOLBAR_SHRINK_NONE; + return wd->shrink_mode; +} + +/** + * Set the homogenous mode of toolbar @p obj. + * + * @param obj The toolbar object + * @param homogenous If true, the toolbar items will be uniform in size + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_homogenous_set(Evas_Object *obj, Eina_Bool homogenous) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + wd->homogeneous = !!homogenous; + evas_object_smart_calculate(wd->bx); +} + +/** + * Get the homogenous mode of toolbar @p obj. + * + * @param obj The toolbar object + * @return If true, the toolbar items are uniform in size + * + * @ingroup Toolbar + */ +EAPI Eina_Bool +elm_toolbar_homogenous_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return EINA_FALSE; + return wd->homogeneous; +} + +/** + * Set the parent object of the toolbar menu + * + * @param obj The toolbar object + * @param parent The parent of the menu object + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_menu_parent_set(Evas_Object *obj, Evas_Object *parent) +{ + Elm_Toolbar_Item *it; + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + EINA_SAFETY_ON_NULL_RETURN(parent); + wd->menu_parent = parent; + EINA_INLIST_FOREACH(wd->items, it) + { + if (it->o_menu) + elm_menu_parent_set(it->o_menu, wd->menu_parent); + } + if ((wd->more_item) && (wd->more_item->o_menu)) + elm_menu_parent_set(wd->more_item->o_menu, wd->menu_parent); +} + +/** + * Get the parent object of the toolbar menu + * + * @param obj The toolbar object + * @return The parent of the menu object + * + * @ingroup Toolbar + */ +EAPI Evas_Object * +elm_toolbar_menu_parent_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return NULL; + return wd->menu_parent; +} + +/** + * Set the alignment of the items. + * + * @param obj The toolbar object + * @param align The new alignment. (left) 0.0 ... 1.0 (right) + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_align_set(Evas_Object *obj, double align) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return; + if (wd->align != align) + evas_object_size_hint_align_set(wd->bx, align, 0.5); + wd->align = align; +} + +/** + * Get the alignment of the items. + * + * @param obj The toolbar object + * @return The alignment. (left) 0.0 ... 1.0 (right) + * + * @ingroup Toolbar + */ +EAPI double +elm_toolbar_align_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) 0.0; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return 0.0; + return wd->align; +} + +/** + * Set whether the toolbar item opens a menu. + * + * @param item The toolbar item + * @param menu If true, @p item will open a menu when selected + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_menu_set(Elm_Toolbar_Item *item, Eina_Bool menu) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + Widget_Data *wd = elm_widget_data_get(item->base.widget); + if (!wd) return; + + if (item->menu == menu) return; + item->menu = menu; + if (menu) _item_menu_create(wd, item); + else _item_menu_destroy(item); +} + +/** + * Set the text to be shown in the toolbar item. + * + * @param item Target item + * @param text The text to set in the content + * + * Setup the text as tooltip to object. The item can have only one tooltip, + * so any previous tooltip data is removed. + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_tooltip_text_set(Elm_Toolbar_Item *item, const char *text) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_tooltip_text_set(item, text); +} + +/** + * Set the content to be shown in the tooltip item + * + * Setup the tooltip to item. The item can have only one tooltip, + * so any previous tooltip data is removed. @p func(with @p data) will + * be called every time that need show the tooltip and it should + * return a valid Evas_Object. This object is then managed fully by + * tooltip system and is deleted when the tooltip is gone. + * + * @param item the toolbar item being attached a tooltip. + * @param func the function used to create the tooltip contents. + * @param data what to provide to @a func as callback data/context. + * @param del_cb called when data is not needed anymore, either when + * another callback replaces @func, the tooltip is unset with + * elm_toolbar_item_tooltip_unset() or the owner @a item + * dies. This callback receives as the first parameter the + * given @a data, and @c event_info is the item. + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_tooltip_content_cb_set(Elm_Toolbar_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_tooltip_content_cb_set(item, func, data, del_cb); +} + +/** + * Unset tooltip from item + * + * @param item toolbar item to remove previously set tooltip. + * + * Remove tooltip from item. The callback provided as del_cb to + * elm_toolbar_item_tooltip_content_cb_set() will be called to notify + * it is not used anymore. + * + * @see elm_toolbar_item_tooltip_content_cb_set() + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_tooltip_unset(Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_tooltip_unset(item); +} + +/** + * Sets a different style for this item tooltip. + * + * @note before you set a style you should define a tooltip with + * elm_toolbar_item_tooltip_content_cb_set() or + * elm_toolbar_item_tooltip_text_set() + * + * @param item toolbar item with tooltip already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_tooltip_style_set(Elm_Toolbar_Item *item, const char *style) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_tooltip_style_set(item, style); +} + +/** + * Get the style for this item tooltip. + * + * @param item toolbar item with tooltip already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a tooltip set, then NULL is returned. + * + * @ingroup Toolbar + */ +EAPI const char * +elm_toolbar_item_tooltip_style_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_tooltip_style_get(item); +} + +/** + * Set the cursor to be shown when mouse is over the toolbar item + * + * @param item Target item + * @param cursor the cursor name to be used. + * + * @see elm_object_cursor_set() + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_cursor_set(Elm_Toolbar_Item *item, const char *cursor) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_cursor_set(item, cursor); +} + +/** + * Get the cursor to be shown when mouse is over the toolbar item + * + * @param item toolbar item with cursor already set. + * @return the cursor name. + * + * @ingroup Toolbar + */ +EAPI const char * +elm_toolbar_item_cursor_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_cursor_get(item); +} + +/** + * Unset the cursor to be shown when mouse is over the toolbar item + * + * @param item Target item + * + * @see elm_object_cursor_unset() + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_cursor_unset(Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_cursor_unset(item); +} + +/** + * Sets a different style for this item cursor. + * + * @note before you set a style you should define a cursor with + * elm_toolbar_item_cursor_set() + * + * @param item toolbar item with cursor already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_cursor_style_set(Elm_Toolbar_Item *item, const char *style) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_cursor_style_set(item, style); +} + +/** + * Get the style for this item cursor. + * + * @param item toolbar item with cursor already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a cursor set, then NULL is returned. + * + * @ingroup Toolbar + */ +EAPI const char * +elm_toolbar_item_cursor_style_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_cursor_style_get(item); +} + +/** + * Set if the cursor set should be searched on the theme or should use + * the provided by the engine, only. + * + * @note before you set if should look on theme you should define a cursor + * with elm_object_cursor_set(). By default it will only look for cursors + * provided by the engine. + * + * @param item widget item with cursor already set. + * @param engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_cursor_engine_only_set(Elm_Toolbar_Item *item, Eina_Bool engine_only) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_cursor_engine_only_set(item, engine_only); +} + +/** + * Get the cursor engine only usage for this item cursor. + * + * @param item widget item with cursor already set. + * @return engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. If + * the object does not have a cursor set, then EINA_FALSE is returned. + * + * @ingroup Toolbar + */ +EAPI Eina_Bool +elm_toolbar_item_cursor_engine_only_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, EINA_FALSE); + return elm_widget_item_cursor_engine_only_get(item); +} + +/** + * Get whether the toolbar item opens a menu. + * + * @param item The toolbar item + * @return If true, @p item opens a menu when selected + * + * @ingroup Toolbar + */ +EAPI Evas_Object * +elm_toolbar_item_menu_get(Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + Widget_Data *wd = elm_widget_data_get(item->base.widget); + if (!wd) return NULL; + /* FIXME: It's not ok. This function needs to be reviewed. And should + * receive a const item */ + elm_toolbar_item_menu_set(item, 1); + return item->o_menu; +} + +/** + * Returns a pointer to a toolbar item by its label + * + * @param obj The toolbar object + * @param label The label of the item to find + * + * @return The pointer to the toolbar item matching @p label + * Returns NULL on failure. + * + * @ingroup Toolbar + */ +EAPI Elm_Toolbar_Item * +elm_toolbar_item_find_by_label(const Evas_Object *obj, const char *label) +{ + Elm_Toolbar_Item *it; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) return NULL; + EINA_INLIST_FOREACH(wd->items, it) + { + if (!strcmp(it->label, label)) return it; + } + + return NULL; +} + +/** + * Set the data item from the toolbar item + * + * This set the data value passed on the elm_toolbar_item_append() and + * related item addition calls. + * + * @param item The item + * @param data The new data pointer to set + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_item_data_set(Elm_Toolbar_Item *item, const void *data) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item); + elm_widget_item_data_set(item, data); +} + +/** + * Get the data item from the toolbar item + * + * This returns the data value passed on the elm_toolbar_item_append() and + * related item addition calls. + * + * @param item The item + * @return The data pointer provided when created + * + * @ingroup Toolbar + */ +EAPI void * +elm_toolbar_item_data_get(const Elm_Toolbar_Item *item) +{ + ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(item, NULL); + return elm_widget_item_data_get(item); +} + +/** + * Set no select mode. + * + * This will turn off the ability to select items entirely and they will + * neither appear selected nor emit selected signals. The clicked + * callback function will still be called. + * + * @param obj The Toolbar object + * @param no_select The no select mode (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_no_select_mode_set(Evas_Object *obj, Eina_Bool no_select) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + wd->no_select = no_select; +} + +/** + * Gets no select mode. + * + * @param obj The Toolbar object + * @return The no select mode (EINA_TRUE = on, EINA_FALSE = off) + * + * @ingroup Toolbar + */ +EAPI Eina_Bool +elm_toolbar_no_select_mode_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return EINA_FALSE; + return wd->no_select; +} + +/** + * Sets icon lookup order, for icons used in this toolbar. + * Icons added before calling this function will not be affected. + * The default lookup order is ELM_ICON_LOOKUP_THEME_FDO. + * + * @param obj The toolbar object + * @param order The icon lookup order + * + * @ingroup Toolbar + */ +EAPI void +elm_toolbar_icon_order_lookup_set(Evas_Object *obj, Elm_Icon_Lookup_Order order) +{ + ELM_CHECK_WIDTYPE(obj, widtype); + Elm_Toolbar_Item *it; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + + wd->lookup_order = order; + EINA_INLIST_FOREACH(wd->items, it) + elm_icon_order_lookup_set(it->icon, order); + if (wd->more_item) + elm_icon_order_lookup_set(wd->more_item->icon, order); +} + +/** + * Gets the icon lookup order. + * + * @param obj The Toolbar object + * @return The icon lookup order + * + * @ingroup Toolbar + */ +EAPI Elm_Icon_Lookup_Order +elm_toolbar_icon_order_lookup_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype) ELM_ICON_LOOKUP_THEME_FDO; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return ELM_ICON_LOOKUP_THEME_FDO; + return wd->lookup_order; +} diff --git a/src/lib/elm_transit.c b/src/lib/elm_transit.c new file mode 100644 index 0000000..7319de3 --- /dev/null +++ b/src/lib/elm_transit.c @@ -0,0 +1,2664 @@ +#include +#include "elm_priv.h" + +#define ELM_TRANSIT_CHECK_OR_RETURN(transit, ...) \ + do { \ + if (!transit) { \ + CRITICAL("Elm_Transit " # transit " is NULL!"); \ + return __VA_ARGS__; \ + } \ + if (!EINA_MAGIC_CHECK(transit, ELM_TRANSIT_MAGIC)) { \ + EINA_MAGIC_FAIL(transit, ELM_TRANSIT_MAGIC); \ + return __VA_ARGS__; \ + } \ + if (transit->deleted){ \ + ERR("Elm_Transit " # transit " has already been deleted!"); \ + return __VA_ARGS__; \ + } \ + } while (0) + +/** + * + * @defgroup Transit Transit + * @ingroup Elementary + * + * Transit (see Warning below) is designed to set the various effects for the + * Evas_Object such like translation, rotation, etc. For using Effects, Create + * transit and insert effects which are interesting. + * Once effects are inserted into transit, transit will manage those effects. + * (ex deleting). + * + * Example: + * @code + * Elm_Transit *trans = elm_transit_add(); + * elm_transit_object_add(trans, obj); + * void *effect_context = elm_transit_effect_translation_context_new(0.0, 0.0, + * 280.0, 280.0); + * elm_transit_effect_add(transit, + * elm_transit_effect_translation_op, effect_context, + * elm_transit_effect_translation_context_free); + * elm_transit_duration_set(transit, 5); + * elm_transit_auto_reverse_set(transit, EINA_TRUE); + * elm_transit_tween_mode_set(transit, ELM_TRANSIT_TWEEN_MODE_DECELERATE); + * elm_transit_repeat_times_set(transit, -1); + * @endcode + * + * @warning We strongly recomend to use elm_transit just when edje can not do + * the trick. Edje has more advantage than Elm_Transit, it has more flexibility and + * animations can be manipulated inside the theme. + */ + +static const char _transit_key[] = "_elm_transit"; + +#define FOCAL 2000 + +struct _Elm_Transit +{ +#define ELM_TRANSIT_MAGIC 0xd27f190a + EINA_MAGIC; + + Ecore_Animator *animator; + Eina_List *effect_list; + Eina_List *objs; + Elm_Transit_Tween_Mode tween_mode; + struct { + void (*func) (void *data, Elm_Transit *transit); + void *arg; + } del_data; + struct { + double delayed; + double paused; + double duration; + double begin; + double current; + } time; + struct { + int count; + int current; + Eina_Bool reverse; + } repeat; + double progress; + unsigned int effects_pending_del; + int walking; + Eina_Bool auto_reverse : 1; + Eina_Bool event_enabled : 1; + Eina_Bool deleted : 1; +}; + +struct _Elm_Transit_Effect +{ + void (*animation_op) (void *data, Elm_Transit *transit, double progress); + void (*user_data_free) (void *data, Elm_Transit *transit); + void *user_data; + Eina_Bool deleted : 1; +}; + +struct _Elm_Obj_Data +{ + Eina_Bool state; + Elm_Transit *transit; +}; + +typedef struct _Elm_Transit_Effect Elm_Transit_Effect; +typedef struct _Elm_Obj_Data Elm_Obj_Data; + +static void +_elm_transit_object_remove_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit *transit = data; + + Elm_Obj_Data *obj_data = evas_object_data_del(obj, _transit_key); + evas_object_pass_events_set(obj, obj_data->state); + free(obj_data); + transit->objs = eina_list_remove(transit->objs, obj); + if (!transit->objs) elm_transit_del(transit); +} + +static void +_elm_transit_object_remove(Elm_Transit *transit, Evas_Object *obj) +{ + Elm_Obj_Data *obj_data = evas_object_data_del(obj, _transit_key); + + evas_object_pass_events_set(obj, obj_data->state); + free(obj_data); + transit->objs = eina_list_remove(transit->objs, obj); + evas_object_event_callback_del(obj, EVAS_CALLBACK_DEL, + _elm_transit_object_remove_cb); +} + +static void +_elm_transit_effect_del(Elm_Transit *transit, Elm_Transit_Effect *effect, Eina_List *elist) +{ + if (effect->user_data_free) + effect->user_data_free(effect->user_data, transit); + + transit->effect_list = eina_list_remove_list(transit->effect_list, elist); + free(effect); +} + +static void +_remove_dead_effects(Elm_Transit *transit) +{ + Eina_List *elist, *elist_next; + Elm_Transit_Effect *effect; + + EINA_LIST_FOREACH_SAFE(transit->effect_list, elist, elist_next, effect) + { + if (effect->deleted) + { + _elm_transit_effect_del(transit, effect, elist); + transit->effects_pending_del--; + if (!transit->effects_pending_del) return; + } + } +} + +static void +_elm_transit_del(Elm_Transit *transit) +{ + Eina_List *elist, *elist_next; + Elm_Transit_Effect *effect; + + if (transit->animator) + ecore_animator_del(transit->animator); + + if (transit->del_data.func) + transit->del_data.func(transit->del_data.arg, transit); + + EINA_LIST_FOREACH_SAFE(transit->effect_list, elist, elist_next, effect) + _elm_transit_effect_del(transit, effect, elist); + + while (transit->objs) + _elm_transit_object_remove(transit, eina_list_data_get(transit->objs)); + + EINA_MAGIC_SET(transit, EINA_MAGIC_NONE); + free(transit); +} + +static void +_transit_animate_op(Elm_Transit *transit, double progress) +{ + Eina_List *elist; + Elm_Transit_Effect *effect; + + transit->walking++; + EINA_LIST_FOREACH(transit->effect_list, elist, effect) + { + if (transit->deleted) break; + if (!effect->deleted) + effect->animation_op(effect->user_data, transit, progress); + } + transit->walking--; + + if (transit->walking) return; + + if (transit->deleted) _elm_transit_del(transit); + else if (transit->effects_pending_del) _remove_dead_effects(transit); +} + +static Eina_Bool +_animator_animate_cb(void *data) +{ + Elm_Transit *transit = data; + double elapsed_time, duration; + + transit->time.current = ecore_loop_time_get(); + elapsed_time = transit->time.current - transit->time.begin; + duration = transit->time.duration + transit->time.delayed; + + if (elapsed_time > duration) + elapsed_time = duration; + + transit->progress = elapsed_time / duration; + switch (transit->tween_mode) + { + case ELM_TRANSIT_TWEEN_MODE_ACCELERATE: + transit->progress = 1.0 - sin((ELM_PI / 2.0) + (transit->progress * ELM_PI / 2.0)); + break; + case ELM_TRANSIT_TWEEN_MODE_DECELERATE: + transit->progress = sin(transit->progress * ELM_PI / 2.0); + break; + case ELM_TRANSIT_TWEEN_MODE_SINUSOIDAL: + transit->progress = (1.0 - cos(transit->progress * ELM_PI)) / 2.0; + break; + default: + break; + } + + /* Reverse? */ + if (transit->repeat.reverse) transit->progress = 1 - transit->progress; + + if (transit->time.duration > 0) _transit_animate_op(transit, transit->progress); + + /* Not end. Keep going. */ + if (elapsed_time < duration) return ECORE_CALLBACK_RENEW; + + /* Repeat and reverse and time done! */ + if ((transit->repeat.current == transit->repeat.count) + && (!transit->auto_reverse || transit->repeat.reverse)) + { + elm_transit_del(transit); + return ECORE_CALLBACK_CANCEL; + } + + /* Repeat Case */ + if (!transit->auto_reverse || transit->repeat.reverse) + { + transit->repeat.current++; + transit->repeat.reverse = EINA_FALSE; + } + else transit->repeat.reverse = EINA_TRUE; + + transit->time.begin = ecore_loop_time_get(); + + return ECORE_CALLBACK_RENEW; +} + +/** + * Add new transit. + * + * @note Is not necessary to delete the transit object, it will be deleted at + * the end of its operation. + * @note The transit will start playing when the program enter in the main loop, is not + * necessary to give a start to the transit. + * + * @param duration The duration of the transit in seconds. When transit starts + * to run, it will last a @p duration time. + * @return The transit object. + * + * @ingroup Transit + */ +EAPI Elm_Transit * +elm_transit_add(void) +{ + Elm_Transit *transit = ELM_NEW(Elm_Transit); + if (!transit) return NULL; + + EINA_MAGIC_SET(transit, ELM_TRANSIT_MAGIC); + + elm_transit_tween_mode_set(transit, ELM_TRANSIT_TWEEN_MODE_LINEAR); + + return transit; +} +/** + * Stops the animation and delete the @p transit object. + * + * Call this function if you wants to stop the animation before the duration + * time. Make sure the @p transit object is still alive with + * elm_transit_del_cb_set() function. + * All added effects will be deleted, calling its repective data_free_cb + * functions. The function setted by elm_tansit_del_cb_set() will be called. + * + * @see elm_transit_del_cb_set() + * + * @param transit The transit object to be deleted. + * + * @ingroup Transit + * @warning Just call this function if you are sure the transit is alive. + */ +EAPI void +elm_transit_del(Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + + if (transit->walking) transit->deleted = EINA_TRUE; + else _elm_transit_del(transit); +} + +/** + * Add a new effect to the transit. + * + * @note The cb function and the data are the key to the effect. If you try to + * add an already added effect, nothing is done. + * @note After the first addition of an effect in @p transit, if its + * effect list become empty again, the @p transit will be killed by + * elm_transit_del(transit) function. + * + * Exemple: + * @code + * Elm_Transit *transit = elm_transit_add(); + * elm_transit_effect_add(transit, + * elm_transit_effect_blend_op, + * elm_transit_effect_blend_context_new(), + * elm_transit_effect_blend_context_free); + * @endcode + * + * @param transit The transit object. + * @param cb The operation function. It is called when the animation begins, + * it is the function that actually performs the animation. It is called with + * the @p data, @p transit and the time progression of the animation (a double + * value between 0.0 and 1.0). + * @param data The context data of the effect. + * @param data_free_cb The function to free the context data, it will be called + * at the end of the effect, it must finalize the animation and free the + * @p data. + * + * @ingroup Transit + * @warning The transit free the context data at the and of the transition with + * the data_free_cb function, do not use the context data in another transit. + */ +EAPI void +elm_transit_effect_add(Elm_Transit *transit, void (*cb)(void *data, Elm_Transit *transit, double progress), void *data, void (*data_free_cb)(void *data, Elm_Transit *transit)) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + EINA_SAFETY_ON_NULL_RETURN(cb); + Elm_Transit_Effect *effect; + Eina_List *elist; + + EINA_LIST_FOREACH(transit->effect_list, elist, effect) + { + if ((effect->animation_op == cb) && (effect->user_data == data)) return; + } + + effect = ELM_NEW(Elm_Transit_Effect); + if (!effect) return; + + effect->user_data_free = data_free_cb; + effect->animation_op = cb; + effect->user_data = data; + + transit->effect_list = eina_list_append(transit->effect_list, effect); +} + +/** + * Delete an added effect. + * + * This function will remove the effect from the @p transit, calling the + * data_free_cb to free the @p data. + * + * @see elm_transit_effect_add() + * + * @note If the effect is not found, nothing is done. + * @note If the effect list become empty, this function will call + * elm_transit_del(transit), that is, it will kill the @p transit. + * + * @param transit The transit object. + * @param cb The operation function. + * @param data The context data of the effect. + * + * @ingroup Transit + */ +EAPI void +elm_transit_effect_del(Elm_Transit *transit, void (*cb)(void *data, Elm_Transit *transit, double progress), void *data) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + EINA_SAFETY_ON_NULL_RETURN(cb); + Eina_List *elist, *elist_next; + Elm_Transit_Effect *effect; + + EINA_LIST_FOREACH_SAFE(transit->effect_list, elist, elist_next, effect) + { + if ((effect->animation_op == cb) && (effect->user_data == data)) + { + if (transit->walking) + { + effect->deleted = EINA_TRUE; + transit->effects_pending_del++; + } + else + { + _elm_transit_effect_del(transit, effect, elist); + if (!transit->effect_list) elm_transit_del(transit); + } + return; + } + } +} + +/** + * Add new object to apply the effects. + * + * @note After the first addition of an object in @p transit, if its + * object list become empty again, the @p transit will be killed by + * elm_transit_del(transit) function. + * @note If the @p obj belongs to another transit, the @p obj will be + * removed from it and it will only belong to the @p transit. If the old + * transit stays without objects, it will die. + * @note When you add an object into the @p transit, its state from + * evas_object_pass_events_get(obj) is saved, and it is applied when the + * transit ends, if you change this state whith evas_object_pass_events_set() + * after add the object, this state will change again when @p transit stops to + * run. + * + * @param transit The transit object. + * @param obj Object to be animated. + * + * @ingroup Transit + * @warning See the documentation of the effect if is safe add or remove + * an object after @p transit begins to run. + */ +EAPI void +elm_transit_object_add(Elm_Transit *transit, Evas_Object *obj) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + EINA_SAFETY_ON_NULL_RETURN(obj); + Elm_Obj_Data *obj_data = evas_object_data_get(obj, _transit_key); + + if (obj_data) + { + if (obj_data->transit == transit) return; + elm_transit_object_remove(obj_data->transit, obj); + } + + obj_data = ELM_NEW(Elm_Obj_Data); + obj_data->state = evas_object_pass_events_get(obj); + obj_data->transit = transit; + evas_object_data_set(obj, _transit_key, obj_data); + + transit->objs = eina_list_append(transit->objs, obj); + + if (!transit->event_enabled) + evas_object_pass_events_set(obj, EINA_TRUE); + + evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, + _elm_transit_object_remove_cb, transit); +} + +/** + * Removes an added object from the transit. + * + * @note If the @p obj is not in the @p transit, nothing is done. + * @note If the list become empty, this function will call + * elm_transit_del(transit), that is, it will kill the @p transit. + * + * @param transit The transit object. + * @param obj Object to be removed from @p transit. + * + * @ingroup Transit + * @warning See the documentation of the effect if is safe add or remove + * an object after @p transit begins to run. + */ +EAPI void +elm_transit_object_remove(Elm_Transit *transit, Evas_Object *obj) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + EINA_SAFETY_ON_NULL_RETURN(obj); + Elm_Obj_Data *obj_data = evas_object_data_get(obj, _transit_key); + if ((!obj_data) || (obj_data->transit != transit)) return; + + _elm_transit_object_remove(transit, obj); + if (!transit->objs) elm_transit_del(transit); +} + +/** + * Get the objects of the transit. + * + * @param transit The transit object. + * @return a Eina_List with the objects from the transit. + * + * @ingroup Transit + */ +EAPI const Eina_List * +elm_transit_objects_get(const Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + return transit->objs; +} + +/** + * Set the event enabled when transit is operating. + * + * If @p enabled is EINA_TRUE, the objects of the transit will receives + * events from mouse and keyboard during the animation. + * @note When you add an object with elm_transit_object_add(), its state from + * evas_object_pass_events_get(obj) is saved, and it is applied when the + * transit ends, if you change this state with evas_object_pass_events_set() + * after add the object, this state will change again when @p transit stops to + * run. + * + * @param transit The transit object. + * @param enabled Disable or enable. + * + * @ingroup Transit + */ +EAPI void +elm_transit_event_enabled_set(Elm_Transit *transit, Eina_Bool enabled) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + Evas_Object *obj; + Eina_List *elist; + Elm_Obj_Data *obj_data; + + if (transit->event_enabled == enabled) return; + + transit->event_enabled = enabled; + + if (enabled) + { + EINA_LIST_FOREACH(transit->objs, elist, obj) + { + obj_data = evas_object_data_get(obj, _transit_key); + evas_object_pass_events_set(obj, obj_data->state); + } + } + else + { + EINA_LIST_FOREACH(transit->objs, elist, obj) + evas_object_pass_events_set(obj, EINA_TRUE); + } +} + +/** + * Get the value of event enabled status. + * + * @see elm_transit_event_enabled_set() + * + * @param transit The Transit object + * @return EINA_TRUE, when event is enabled. If @p transit is NULL + * EINA_FALSE is returned + * + * @ingroup Transit + */ +EAPI Eina_Bool +elm_transit_event_enabled_get(const Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, EINA_FALSE); + + return transit->event_enabled; +} + + +/** + * Set the event enabled when transit is operating. + * + * If @p disabled is EINA_TRUE, the objects of the transit will receives + * events from mouse and keyboard during the animation. + * @note When you add an object with elm_transit_object_add(), its state from + * evas_object_pass_events_get(obj) is saved, and it is applied when the + * transit ends, if you change this state with evas_object_pass_events_set() + * after add the object, this state will change again when @p transit stops to + * run. + * + * @see elm_transit_event_enabled_set() + * + * @param transit The transit object. + * @param disabled Disable or enable. + * + * @ingroup Transit + */ +EINA_DEPRECATED EAPI void +elm_transit_event_block_set(Elm_Transit *transit, Eina_Bool disabled) +{ + elm_transit_event_enabled_set(transit, disabled); +} + + +/** + * Get the value of event block enabled status. + * + * @see elm_transit_event_enabled_set(), elm_transit_event_enabled_get() + * + * @param transit The Transit object + * @return EINA_TRUE, when event is enabled. If @p transit is NULL + * EINA_FALSE is returned + * + * @ingroup Transit + */ +EINA_DEPRECATED EAPI Eina_Bool +elm_transit_event_block_get(const Elm_Transit *transit) +{ + return !elm_transit_event_enabled_get(transit); +} + +/** + * Set the user-callback function when the transit is deleted. + * + * @note Using this function twice will overwrite the first function setted. + * @note the @p transit object will be deleted after call @p cb function. + * + * @param transit The transit object. + * @param cb Callback function pointer. This function will be called before + * the deletion of the transit. + * @param data Callback funtion user data. It is the @p op parameter. + * + * @ingroup Transit + */ +EAPI void +elm_transit_del_cb_set(Elm_Transit *transit, void (*cb) (void *data, Elm_Transit *transit), void *data) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + transit->del_data.func = cb; + transit->del_data.arg = data; +} + +/** + * Set reverse effect automatically. + * + * If auto reverse is setted, after running the effects with the progress + * parameter from 0 to 1, it will call the effecs again with the progress + * from 1 to 0. The transit will last for a time iqual to (2 * duration * repeat), + * where the duration was setted with the function elm_transit_add and + * the repeat with the function elm_transit_repeat_times_set(). + * + * @param transit The transit object. + * @param reverse EINA_TRUE means the auto_reverse is on. + * + * @ingroup Transit + */ +EAPI void +elm_transit_auto_reverse_set(Elm_Transit *transit, Eina_Bool reverse) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + transit->auto_reverse = reverse; +} + +/** + * Get if the auto reverse is on. + * + * @see elm_transit_auto_reverse_set() + * + * @param transit The transit object. + * @return EINA_TRUE means auto reverse is on. If @p transit is NULL + * EINA_FALSE is returned + * + * @ingroup Transit + */ +EAPI Eina_Bool +elm_transit_auto_reverse_get(Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, EINA_FALSE); + return transit->auto_reverse; +} + +/** + * Set the transit repeat count. Effect will be repeated by repeat count. + * + * This function sets the number of repetition the transit will run after + * the first one, that is, if @p repeat is 1, the transit will run 2 times. + * If the @p repeat is a negative number, it will repeat infinite times. + * + * @note If this function is called during the transit execution, the transit + * will run @p repeat times, ignoring the times it already performed. + * + * @param transit The transit object + * @param repeat Repeat count + * + * @ingroup Transit + */ +EAPI void +elm_transit_repeat_times_set(Elm_Transit *transit, int repeat) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + transit->repeat.count = repeat; + transit->repeat.current = 0; +} + +/** + * Get the transit repeat count. + * + * @see elm_transit_repeat_times_set() + * + * @param transit The Transit object. + * @return The repeat count. If @p transit is NULL + * 0 is returned + * + * @ingroup Transit + */ +EAPI int +elm_transit_repeat_times_get(Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, 0); + return transit->repeat.count; +} + +/** + * Set the transit animation acceleration type. + * + * This function sets the tween mode of the transit that can be: + * ELM_TRANSIT_TWEEN_MODE_LINEAR - The default mode. + * ELM_TRANSIT_TWEEN_MODE_SINUSOIDAL - Starts in accelerate mode and ends decelerating. + * ELM_TRANSIT_TWEEN_MODE_DECELERATE - The animation will be slowed over time. + * ELM_TRANSIT_TWEEN_MODE_ACCELERATE - The animation will accelerate over time. + * + * @param transit The transit object. + * @param tween_mode The tween type. + * + * @ingroup Transit + */ +EAPI void +elm_transit_tween_mode_set(Elm_Transit *transit, Elm_Transit_Tween_Mode tween_mode) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + + transit->tween_mode = tween_mode; +} + +/** + * Get the transit animation acceleration type. + * + * @note @p transit can not be NULL + * + * @param transit The transit object. + * @return The tween type. If @p transit is NULL + * ELM_TRANSIT_TWEEN_MODE_LINEAR is returned. + * + * @ingroup Transit + */ +EAPI Elm_Transit_Tween_Mode +elm_transit_tween_mode_get(const Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, ELM_TRANSIT_TWEEN_MODE_LINEAR); + return transit->tween_mode; +} + +/** + * Set the transit animation time + * + * @note @p transit can not be NULL + * + * @param transit The transit object. + * @param duration The animation time. + * + * @ingroup Transit + */ +EAPI void +elm_transit_duration_set(Elm_Transit *transit, double duration) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + if (transit->animator) return; + transit->time.duration = duration; +} + +/** + * Get the transit animation time + * + * @note @p transit can not be NULL + * + * @param transit The transit object. + * + * @return The transit animation time. + * + * @ingroup Transit + */ +EAPI double +elm_transit_duration_get(const Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, 0.0); + return transit->time.duration; +} + +/** + * Starts the transition. + * Once this API is called, the transit begins to measure the time. + * + * @note @p transit can not be NULL + * + * @param transit The transit object. + * + * @ingroup Transit + */ +EAPI void +elm_transit_go(Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + + if (transit->animator) + ecore_animator_del(transit->animator); + + transit->time.paused = 0; + transit->time.delayed = 0; + transit->time.begin = ecore_loop_time_get(); + transit->animator = ecore_animator_add(_animator_animate_cb, transit); +} + +/** + * Pause/Resume the transition. + * If you call elm_transit_go again, paused states will affect no anymore. + * + * @note @p transit can not be NULL + * + * @param transit The transit object. + * + * @ingroup Transit + */ +EAPI void +elm_transit_paused_set(Elm_Transit *transit, Eina_Bool paused) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit); + + if (!transit->animator) return; + + if (paused) + { + if (transit->time.paused > 0) + return; + ecore_animator_freeze(transit->animator); + transit->time.paused = ecore_loop_time_get(); + } + else + { + if (transit->time.paused == 0) + return; + ecore_animator_thaw(transit->animator); + transit->time.delayed += (ecore_loop_time_get() - transit->time.paused); + transit->time.paused = 0; + } +} + +/** + * Get the value of paused status. + * + * @see elm_transit_paused_set() + * + * @note @p transit can not be NULL + * + * @param transit The transit object. + * @return EINA_TRUE means transition is paused. If @p transit is NULL + * EINA_FALSE is returned + * + * @ingroup Transit + */ +EAPI Eina_Bool +elm_transit_paused_get(const Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, EINA_FALSE); + + if (transit->time.paused == 0) + return EINA_FALSE; + + return EINA_TRUE; +} + +/** + * Get the time progression of the animation (a double value between 0.0 and 1.0). + * + * @note @p transit can not be NULL + * + * @param transit The transit object. + * + * @return The time progression value. If @p transit is NULL + * 0 is returned + * + * @ingroup Transit + */ +EAPI double +elm_transit_progress_value_get(const Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, 0); + + return transit->progress; +} + +/////////////////////////////////////////////////////////////////////////////// +//Resizing FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Resizing Elm_Transit_Effect_Resizing; + +struct _Elm_Transit_Effect_Resizing +{ + struct _size { + Evas_Coord w, h; + } from, to; +}; + +static void +_transit_effect_resizing_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + free(data); +} + +static void +_transit_effect_resizing_op(void *data, Elm_Transit *transit, double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Evas_Coord w, h; + Evas_Object *obj; + Eina_List *elist; + Elm_Transit_Effect_Resizing *resizing = data; + + w = resizing->from.w + (resizing->to.w * progress); + h = resizing->from.h + (resizing->to.h * progress); + + EINA_LIST_FOREACH(transit->objs, elist, obj) + evas_object_resize(obj, w, h); +} + +static void * +_transit_effect_resizing_context_new(Evas_Coord from_w, Evas_Coord from_h, Evas_Coord to_w, Evas_Coord to_h) +{ + Elm_Transit_Effect_Resizing *resizing; + + resizing = ELM_NEW(Elm_Transit_Effect_Resizing); + if (!resizing) return NULL; + + resizing->from.w = from_w; + resizing->from.h = from_h; + resizing->to.w = to_w - from_w; + resizing->to.h = to_h - from_h; + + return resizing; +} + +/** + * Add the Resizing Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates resizing effect context + * and add it's required APIs to elm_transit_effect_add. + * @note This effect will be applied to the objects that are in the transit, + * @note If you change the set of objects in the transit with elm_transit_object_add() + * or elm_transit_object_remove(), the set of objects affected by this effect + * will be changed too. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @param from_w Object width size when effect begins. + * @param from_h Object height size when effect begins. + * @param to_w Object width size when effect ends. + * @param to_h Object height size when effect ends. + * @return Resizing effect context data. + * + * @ingroup Transit +*/ +EAPI void * +elm_transit_effect_resizing_add(Elm_Transit *transit, Evas_Coord from_w, Evas_Coord from_h, Evas_Coord to_w, Evas_Coord to_h) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_resizing_context_new(from_w, from_h, to_w, to_h); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_resizing_op, effect_context, + _transit_effect_resizing_context_free); + return effect_context; +} + +/////////////////////////////////////////////////////////////////////////////// +//Translation FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Translation Elm_Transit_Effect_Translation; +typedef struct _Elm_Transit_Effect_Translation_Node Elm_Transit_Effect_Translation_Node; + +struct _Elm_Transit_Effect_Translation_Node +{ + Evas_Object *obj; + Evas_Coord x, y; +}; + +struct _Elm_Transit_Effect_Translation +{ + struct _position_variation { + Evas_Coord dx, dy; + } from, to; + Eina_List *nodes; +}; + +static void +_translation_object_del_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit_Effect_Translation *translation = data; + Eina_List *elist; + Elm_Transit_Effect_Translation_Node *translation_node; + + EINA_LIST_FOREACH(translation->nodes, elist, translation_node) + { + if (translation_node->obj != obj) continue; + translation->nodes = eina_list_remove_list(translation->nodes, elist); + free(translation_node); + break; + } +} + +static Eina_List * +_translation_nodes_build(Elm_Transit *transit, Elm_Transit_Effect_Translation *translation) +{ + Elm_Transit_Effect_Translation_Node *translation_node; + const Eina_List *elist; + Evas_Object *obj; + Eina_List *data_list = NULL; + const Eina_List *objs = elm_transit_objects_get(transit); + + EINA_LIST_FOREACH(objs, elist, obj) + { + translation_node = ELM_NEW(Elm_Transit_Effect_Translation_Node); + if (!translation_node) + { + eina_list_free(data_list); + return NULL; + } + translation_node->obj = obj; + evas_object_geometry_get(obj, &(translation_node->x), + &(translation_node->y), NULL, NULL); + data_list = eina_list_append(data_list, translation_node); + evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, + _translation_object_del_cb, translation); + } + return data_list; +} + +void +_transit_effect_translation_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + Elm_Transit_Effect_Translation *translation = data; + Eina_List *elist, *elist_next; + Elm_Transit_Effect_Translation_Node *translation_node; + + EINA_LIST_FOREACH_SAFE(translation->nodes, + elist, elist_next, translation_node) + { + evas_object_event_callback_del(translation_node->obj, + EVAS_CALLBACK_DEL, _translation_object_del_cb); + translation->nodes = eina_list_remove_list(translation->nodes, elist); + free(translation_node); + } + free(translation); +} + +void +_transit_effect_translation_op(void *data, Elm_Transit *transit, double progress __UNUSED__) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Evas_Coord x, y; + Elm_Transit_Effect_Translation *translation = data; + Elm_Transit_Effect_Translation_Node *translation_node; + Eina_List *elist; + + if (!translation->nodes) + translation->nodes = _translation_nodes_build(transit, translation); + + EINA_LIST_FOREACH(translation->nodes, elist, translation_node) + { + x = translation_node->x + translation->from.dx + + (translation->to.dx * progress); + y = translation_node->y + translation->from.dy + + (translation->to.dy * progress); + evas_object_move(translation_node->obj, x, y); + } +} + +static void * +_transit_effect_translation_context_new(Evas_Coord from_dx, Evas_Coord from_dy, Evas_Coord to_dx, Evas_Coord to_dy) +{ + Elm_Transit_Effect_Translation *translation; + + translation = ELM_NEW(Elm_Transit_Effect_Translation); + if (!translation) return NULL; + + translation->from.dx = from_dx; + translation->from.dy = from_dy; + translation->to.dx = to_dx - from_dx; + translation->to.dy = to_dy - from_dy; + + return translation; +} + +/** + * Add the Translation Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates translation effect context + * and add it's required APIs to elm_transit_effect_add. + * @note When this function is called, it gets the current objects in + * the transit, that is, elm_transit_object_remove() and elm_transit_object_add() + * will not cause any changes in the set of objects that this effect is being + * applied. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @param from_dx X Position variation when effect begins. + * @param from_dy Y Position variation when effect begins. + * @param to_dx X Position variation when effect ends. + * @param to_dy Y Position variation when effect ends. + * @return Translation effect context data. + * + * @ingroup Transit + * @warning Is higher recommended just create a transit with this effect when + * the window that the objects of the transit belongs has already been created. + * This is because this effect needs the geometry information about the objects, + * and if the window was not created yet, it can get a wrong information. + * @warning Is not recommended remove or add an object after the transit begins + * to run, because the order of the objects will be affected. + */ +EAPI void * +elm_transit_effect_translation_add(Elm_Transit *transit, Evas_Coord from_dx, Evas_Coord from_dy, Evas_Coord to_dx, Evas_Coord to_dy) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_translation_context_new(from_dx, from_dy, to_dx, to_dy); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_translation_op, effect_context, + _transit_effect_translation_context_free); + return effect_context; +} + + +/////////////////////////////////////////////////////////////////////////////// +//Zoom FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Zoom Elm_Transit_Effect_Zoom; + +struct _Elm_Transit_Effect_Zoom +{ + float from, to; +}; + +void +_transit_effect_zoom_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + free(data); +} + +static void +_transit_effect_zoom_op(void *data, Elm_Transit *transit , double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Evas_Object *obj; + Eina_List *elist; + Elm_Transit_Effect_Zoom *zoom = data; + Evas_Map *map; + Evas_Coord x, y, w, h; + + map = evas_map_new(4); + if (!map) return; + + EINA_LIST_FOREACH(transit->objs, elist, obj) + { + evas_object_geometry_get(obj, &x, &y, &w, &h); + evas_map_smooth_set(map, EINA_TRUE); + evas_map_util_points_populate_from_object_full(map, obj, zoom->from + + (progress * zoom->to)); + evas_map_util_3d_perspective(map, x + (w / 2), y + (h / 2), 0, FOCAL); + evas_object_map_set(obj, map); + evas_object_map_enable_set(obj, EINA_TRUE); + } + evas_map_free(map); +} + +static void * +_transit_effect_zoom_context_new(float from_rate, float to_rate) +{ + Elm_Transit_Effect_Zoom *zoom; + + zoom = ELM_NEW(Elm_Transit_Effect_Zoom); + if (!zoom) return NULL; + + zoom->from = (FOCAL - (from_rate * FOCAL)) * (1 / from_rate); + zoom->to = ((FOCAL - (to_rate * FOCAL)) * (1 / to_rate)) - zoom->from; + + return zoom; +} + +/** + * Add the Zoom Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates zoom effect context + * and add it's required APIs to elm_transit_effect_add. + * @note If you change the set of objects in the transit with elm_transit_object_add() + * or elm_transit_object_remove(), the set of objects affected by this effect + * will be changed too. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @param from_rate Scale rate when effect begins (1 is current rate). + * @param to_rate Scale rate when effect ends. + * @return Zoom effect context data. + * + * @ingroup Transit + * @warning Is higher recommended just create a transit with this effect when + * the window that the objects of the transit belongs has already been created. + * This is because this effect needs the geometry information about the objects, + * and if the window was not created yet, it can get a wrong information. + * @warning Is not recommended remove or add an object after the transit begins + * to run, because the order of the objects will be affected. + */ +EAPI void * +elm_transit_effect_zoom_add(Elm_Transit *transit, float from_rate, float to_rate) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_zoom_context_new(from_rate, to_rate); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_zoom_op, effect_context, + _transit_effect_zoom_context_free); + return effect_context; +} + + +/////////////////////////////////////////////////////////////////////////////// +//Flip FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Flip Elm_Transit_Effect_Flip; + +struct _Elm_Transit_Effect_Flip +{ + Elm_Transit_Effect_Flip_Axis axis; + Eina_Bool cw : 1; +}; + +static void +_transit_effect_flip_context_free(void *data, Elm_Transit *transit) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Evas_Object *front, *back; + int i; + int count = eina_list_count(transit->objs); + + for (i = 0; i < (count - 1); i += 2) + { + front = eina_list_nth(transit->objs, i); + back = eina_list_nth(transit->objs, i+1); + evas_object_map_enable_set(front, EINA_FALSE); + evas_object_map_enable_set(back, EINA_FALSE); + } + free(data); +} + +static void +_transit_effect_flip_op(void *data, Elm_Transit *transit, double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Evas_Object *obj, *front, *back; + int count, i; + Elm_Transit_Effect_Flip *flip = data; + Evas_Map *map; + float degree; + Evas_Coord x, y, w, h; + + map = evas_map_new(4); + if (!map) return; + + if (flip->cw) degree = (float)(progress * 180); + else degree = (float)(progress * -180); + + count = eina_list_count(transit->objs); + for (i = 0; i < (count - 1); i += 2) + { + Evas_Coord half_w, half_h; + + front = eina_list_nth(transit->objs, i); + back = eina_list_nth(transit->objs, i+1); + + if ((degree < 90) && (degree > -90)) + { + obj = front; + if (front != back) + { + evas_object_hide(back); + evas_object_show(front); + } + } + else + { + obj = back; + if (front != back) + { + evas_object_hide(front); + evas_object_show(back); + } + } + + evas_map_smooth_set(map, EINA_TRUE); + evas_map_util_points_populate_from_object_full(map, obj, 0); + evas_object_geometry_get(obj, &x, &y, &w, &h); + half_w = (w / 2); + half_h = (h / 2); + + if (flip->axis == ELM_TRANSIT_EFFECT_FLIP_AXIS_Y) + { + if ((degree >= 90) || (degree <= -90)) + { + evas_map_point_image_uv_set(map, 0, w, 0); + evas_map_point_image_uv_set(map, 1, 0, 0); + evas_map_point_image_uv_set(map, 2, 0, h); + evas_map_point_image_uv_set(map, 3, w, h); + } + evas_map_util_3d_rotate(map, 0, degree, + 0, x + half_w, y + half_h, 0); + } + else + { + if ((degree >= 90) || (degree <= -90)) + { + evas_map_point_image_uv_set(map, 0, 0, h); + evas_map_point_image_uv_set(map, 1, w, h); + evas_map_point_image_uv_set(map, 2, w, 0); + evas_map_point_image_uv_set(map, 3, 0, 0); + } + evas_map_util_3d_rotate(map, degree, + 0, 0, x + half_w, y + half_h, 0); + } + evas_map_util_3d_perspective(map, x + half_w, y + half_h, 0, FOCAL); + evas_object_map_enable_set(front, EINA_TRUE); + evas_object_map_enable_set(back, EINA_TRUE); + evas_object_map_set(obj, map); + } + evas_map_free(map); +} + +static void * +_transit_effect_flip_context_new(Elm_Transit_Effect_Flip_Axis axis, Eina_Bool cw) +{ + Elm_Transit_Effect_Flip *flip; + + flip = ELM_NEW(Elm_Transit_Effect_Flip); + if (!flip) return NULL; + + flip->cw = cw; + flip->axis = axis; + + return flip; +} + +/** + * Add the Flip Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates flip effect context + * and add it's required APIs to elm_transit_effect_add. + * @note This effect is applied to each pair of objects in the order they are listed + * in the transit list of objects. The first object in the pair will be the + * "front" object and the second will be the "back" object. + * @note If you change the set of objects in the transit with elm_transit_object_add() + * or elm_transit_object_remove(), the set of objects affected by this effect + * will be changed too. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @param axis Flipping Axis(X or Y). + * @param cw Flipping Direction. EINA_TRUE is clock-wise. + * @return Flip effect context data. + * + * @ingroup Transit + * @warning Is higher recommended just create a transit with this effect when + * the window that the objects of the transit belongs has already been created. + * This is because this effect needs the geometry information about the objects, + * and if the window was not created yet, it can get a wrong information. + * @warning Is not recommended remove or add an object after the transit begins + * to run, because the order of the objects will be affected. + */ +EAPI void * +elm_transit_effect_flip_add(Elm_Transit *transit, Elm_Transit_Effect_Flip_Axis axis, Eina_Bool cw) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_flip_context_new(axis, cw); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_flip_op, effect_context, + _transit_effect_flip_context_free); + return effect_context; +} + +/////////////////////////////////////////////////////////////////////////////// +//ResizableFlip FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Resizable_Flip Elm_Transit_Effect_ResizableFlip; +typedef struct _Elm_Transit_Effect_Resizable_Flip_Node Elm_Transit_Effect_ResizableFlip_Node; + +struct _Elm_Transit_Effect_Resizable_Flip_Node +{ + Evas_Object *front; + Evas_Object *back; + struct _vector2d { + float x, y; + } from_pos, from_size, to_pos, to_size; +}; + +struct _Elm_Transit_Effect_Resizable_Flip +{ + Eina_List *nodes; + Eina_Bool cw : 1; + Elm_Transit_Effect_Flip_Axis axis; +}; + +static void +_resizable_flip_object_del_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit_Effect_ResizableFlip *resizable_flip = data; + Eina_List *elist; + Elm_Transit_Effect_ResizableFlip_Node *resizable_flip_node; + + EINA_LIST_FOREACH(resizable_flip->nodes, elist, resizable_flip_node) + { + if (resizable_flip_node->front == obj) + evas_object_event_callback_del(resizable_flip_node->back, + EVAS_CALLBACK_DEL, _resizable_flip_object_del_cb); + else if (resizable_flip_node->back == obj) + evas_object_event_callback_del(resizable_flip_node->front, + EVAS_CALLBACK_DEL, _resizable_flip_object_del_cb); + else continue; + + resizable_flip->nodes = eina_list_remove_list(resizable_flip->nodes, + elist); + free(resizable_flip_node); + break; + } +} + +static Eina_List * +_resizable_flip_nodes_build(Elm_Transit *transit, Elm_Transit_Effect_ResizableFlip *resizable_flip) +{ + Elm_Transit_Effect_ResizableFlip_Node *resizable_flip_node; + Eina_List *data_list = NULL; + Evas_Coord front_x, front_y, front_w, front_h; + Evas_Coord back_x, back_y, back_w, back_h; + int i, count; + + count = eina_list_count(transit->objs); + for (i = 0; i < (count - 1); i += 2) + { + resizable_flip_node = ELM_NEW(Elm_Transit_Effect_ResizableFlip_Node); + if (!resizable_flip_node) + { + eina_list_free(data_list); + return NULL; + } + + resizable_flip_node->front = eina_list_nth(transit->objs, i); + resizable_flip_node->back = eina_list_nth(transit->objs, i+1); + + evas_object_geometry_get(resizable_flip_node->front, + &front_x, &front_y, &front_w, &front_h); + evas_object_geometry_get(resizable_flip_node->back, + &back_x, &back_y, &back_w, &back_h); + + resizable_flip_node->from_pos.x = front_x; + resizable_flip_node->from_pos.y = front_y; + resizable_flip_node->to_pos.x = back_x - front_x; + resizable_flip_node->to_pos.y = back_y - front_y; + + resizable_flip_node->from_size.x = front_w; + resizable_flip_node->from_size.y = front_h; + resizable_flip_node->to_size.x = back_w - front_w; + resizable_flip_node->to_size.y = back_h - front_h; + + data_list = eina_list_append(data_list, resizable_flip_node); + + evas_object_event_callback_add(resizable_flip_node->back, + EVAS_CALLBACK_DEL, _resizable_flip_object_del_cb, resizable_flip); + evas_object_event_callback_add(resizable_flip_node->front, + EVAS_CALLBACK_DEL, _resizable_flip_object_del_cb, resizable_flip); + } + + return data_list; +} + +static void +_set_image_uv_by_axis_y(Evas_Map *map, Elm_Transit_Effect_ResizableFlip_Node *flip, float degree) +{ + if ((degree >= 90) || (degree <= -90)) + { + evas_map_point_image_uv_set(map, 0, + (flip->from_size.x * 2) + flip->to_size.x, + 0); + evas_map_point_image_uv_set(map, 1, 0, 0); + evas_map_point_image_uv_set(map, 2, 0, + (flip->from_size.y * 2) + flip->to_size.y); + evas_map_point_image_uv_set(map, 3, + (flip->from_size.x * 2) + flip->to_size.x, + (flip->from_size.y * 2) + flip->to_size.y); + } + else + { + evas_map_point_image_uv_set(map, 0, 0, 0); + evas_map_point_image_uv_set(map, 1, flip->from_size.x, 0); + evas_map_point_image_uv_set(map, 2, flip->from_size.x, + flip->from_size.y); + evas_map_point_image_uv_set(map, 3, 0, flip->from_size.y); + } +} + +static void +_set_image_uv_by_axis_x(Evas_Map *map, Elm_Transit_Effect_ResizableFlip_Node *flip, float degree) +{ + if ((degree >= 90) || (degree <= -90)) + { + evas_map_point_image_uv_set(map, 0, 0, + (flip->from_size.y * 2) + flip->to_size.y); + evas_map_point_image_uv_set(map, 1, + (flip->from_size.x * 2) + flip->to_size.x, + (flip->from_size.y * 2) + flip->to_size.y); + evas_map_point_image_uv_set(map, 2, + (flip->from_size.x * 2) + flip->to_size.x, + 0); + evas_map_point_image_uv_set(map, 3, 0, 0); + } + else + { + evas_map_point_image_uv_set(map, 0, 0, 0); + evas_map_point_image_uv_set(map, 1, flip->from_size.x, 0); + evas_map_point_image_uv_set(map, 2, flip->from_size.x, + flip->from_size.y); + evas_map_point_image_uv_set(map, 3, 0, flip->from_size.y); + } +} + +void +_transit_effect_resizable_flip_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + + Elm_Transit_Effect_ResizableFlip *resizable_flip = data; + Eina_List *elist, *elist_next; + Elm_Transit_Effect_ResizableFlip_Node *resizable_flip_node; + + EINA_LIST_FOREACH_SAFE(resizable_flip->nodes, + elist, elist_next, resizable_flip_node) + { + evas_object_map_enable_set(resizable_flip_node->front, EINA_FALSE); + evas_object_map_enable_set(resizable_flip_node->back, EINA_FALSE); + + resizable_flip->nodes = eina_list_remove_list(resizable_flip->nodes, + elist); + + evas_object_event_callback_del(resizable_flip_node->back, + EVAS_CALLBACK_DEL, _resizable_flip_object_del_cb); + evas_object_event_callback_del(resizable_flip_node->front, + EVAS_CALLBACK_DEL, _resizable_flip_object_del_cb); + free(resizable_flip_node); + } + free(resizable_flip); +} + +void +_transit_effect_resizable_flip_op(void *data, Elm_Transit *transit __UNUSED__, double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + Evas_Map *map; + Evas_Object *obj; + float x, y, w, h; + float degree; + Evas_Coord half_w, half_h; + Elm_Transit_Effect_ResizableFlip *resizable_flip = data; + Elm_Transit_Effect_ResizableFlip_Node *resizable_flip_node; + Eina_List *elist; + + map = evas_map_new(4); + if (!map) return; + + if (resizable_flip->cw) degree = (float)(progress * 180); + else degree = (float)(progress * -180); + + if (!resizable_flip->nodes) + resizable_flip->nodes = _resizable_flip_nodes_build(transit, + resizable_flip); + + EINA_LIST_FOREACH(resizable_flip->nodes, elist, resizable_flip_node) + { + if ((degree < 90) && (degree > -90)) + { + obj = resizable_flip_node->front; + if (resizable_flip_node->front != resizable_flip_node->back) + { + evas_object_hide(resizable_flip_node->back); + evas_object_show(resizable_flip_node->front); + } + } + else + { + obj = resizable_flip_node->back; + if (resizable_flip_node->front != resizable_flip_node->back) + { + evas_object_hide(resizable_flip_node->front); + evas_object_show(resizable_flip_node->back); + } + } + + evas_map_smooth_set(map, EINA_TRUE); + + x = resizable_flip_node->from_pos.x + + (resizable_flip_node->to_pos.x * progress); + y = resizable_flip_node->from_pos.y + + (resizable_flip_node->to_pos.y * progress); + w = resizable_flip_node->from_size.x + + (resizable_flip_node->to_size.x * progress); + h = resizable_flip_node->from_size.y + + (resizable_flip_node->to_size.y * progress); + evas_map_point_coord_set(map, 0, x, y, 0); + evas_map_point_coord_set(map, 1, x + w, y, 0); + evas_map_point_coord_set(map, 2, x + w, y + h, 0); + evas_map_point_coord_set(map, 3, x, y + h, 0); + + half_w = (Evas_Coord)(w / 2); + half_h = (Evas_Coord)(h / 2); + + if (resizable_flip->axis == ELM_TRANSIT_EFFECT_FLIP_AXIS_Y) + { + _set_image_uv_by_axis_y(map, resizable_flip_node, degree); + evas_map_util_3d_rotate(map, 0, degree, + 0, x + half_w, y + half_h, 0); + } + else + { + _set_image_uv_by_axis_x(map, resizable_flip_node, degree); + evas_map_util_3d_rotate(map, degree, 0, + 0, x + half_w, y + half_h, 0); + } + + evas_map_util_3d_perspective(map, x + half_w, y + half_h, 0, FOCAL); + evas_object_map_enable_set(resizable_flip_node->front, EINA_TRUE); + evas_object_map_enable_set(resizable_flip_node->back, EINA_TRUE); + evas_object_map_set(obj, map); + } + evas_map_free(map); +} + +static void * +_transit_effect_resizable_flip_context_new(Elm_Transit_Effect_Flip_Axis axis, Eina_Bool cw) +{ + Elm_Transit_Effect_ResizableFlip *resizable_flip; + + resizable_flip = ELM_NEW(Elm_Transit_Effect_ResizableFlip); + if (!resizable_flip) return NULL; + + resizable_flip->cw = cw; + resizable_flip->axis = axis; + + return resizable_flip; +} + +/** + * Add the Resizable Flip Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates resizable flip effect context + * and add it's required APIs to elm_transit_effect_add. + * @note This effect is applied to each pair of objects in the order they are listed + * in the transit list of objects. The first object in the pair will be the + * "front" object and the second will be the "back" object. + * @note When this function is called, it gets the current objects in + * the transit, that is, elm_transit_object_remove() and elm_transit_object_add() + * will not cause any changes in the set of objects that this effect is being + * applied. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @param axis Flipping Axis(X or Y). + * @param cw Flipping Direction. EINA_TRUE is clock-wise. + * @return Resizable flip effect context data. + * + * @ingroup Transit + * @warning Is higher recommended just create a transit with this effect when + * the window that the objects of the transit belongs has already been created. + * This is because this effect needs the geometry information about the objects, + * and if the window was not created yet, it can get a wrong information. + * @warning Is not recommended remove or add an object after the transit begins + * to run, because the order of the objects will be affected. + */ +EAPI void * +elm_transit_effect_resizable_flip_add(Elm_Transit *transit, Elm_Transit_Effect_Flip_Axis axis, Eina_Bool cw) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_resizable_flip_context_new(axis, cw); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_resizable_flip_op, effect_context, + _transit_effect_resizable_flip_context_free); + return effect_context; +} + + +/////////////////////////////////////////////////////////////////////////////// +//Wipe FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Wipe Elm_Transit_Effect_Wipe; + +struct _Elm_Transit_Effect_Wipe +{ + Elm_Transit_Effect_Wipe_Type type; + Elm_Transit_Effect_Wipe_Dir dir; +}; + +static void +_elm_fx_wipe_hide(Evas_Map * map, Elm_Transit_Effect_Wipe_Dir dir, float x, float y, float w, float h, float progress) +{ + float w2, h2; + + switch (dir) + { + case ELM_TRANSIT_EFFECT_WIPE_DIR_LEFT: + w2 = w - (w * progress); + h2 = (y + h); + evas_map_point_image_uv_set(map, 0, 0, 0); + evas_map_point_image_uv_set(map, 1, w2, 0); + evas_map_point_image_uv_set(map, 2, w2, h); + evas_map_point_image_uv_set(map, 3, 0, h); + evas_map_point_coord_set(map, 0, x, y, 0); + evas_map_point_coord_set(map, 1, x + w2, y, 0); + evas_map_point_coord_set(map, 2, x + w2, h2, 0); + evas_map_point_coord_set(map, 3, x, h2, 0); + break; + case ELM_TRANSIT_EFFECT_WIPE_DIR_RIGHT: + w2 = (w * progress); + h2 = (y + h); + evas_map_point_image_uv_set(map, 0, w2, 0); + evas_map_point_image_uv_set(map, 1, w, 0); + evas_map_point_image_uv_set(map, 2, w, h); + evas_map_point_image_uv_set(map, 3, w2, h); + evas_map_point_coord_set(map, 0, x + w2, y, 0); + evas_map_point_coord_set(map, 1, x + w, y, 0); + evas_map_point_coord_set(map, 2, x + w, h2, 0); + evas_map_point_coord_set(map, 3, x + w2, h2, 0); + break; + case ELM_TRANSIT_EFFECT_WIPE_DIR_UP: + w2 = (x + w); + h2 = h - (h * progress); + evas_map_point_image_uv_set(map, 0, 0, 0); + evas_map_point_image_uv_set(map, 1, w, 0); + evas_map_point_image_uv_set(map, 2, w, h2); + evas_map_point_image_uv_set(map, 3, 0, h2); + evas_map_point_coord_set(map, 0, x, y, 0); + evas_map_point_coord_set(map, 1, w2, y, 0); + evas_map_point_coord_set(map, 2, w2, y+h2, 0); + evas_map_point_coord_set(map, 3, x, y+h2, 0); + break; + case ELM_TRANSIT_EFFECT_WIPE_DIR_DOWN: + w2 = (x + w); + h2 = (h * progress); + evas_map_point_image_uv_set(map, 0, 0, h2); + evas_map_point_image_uv_set(map, 1, w, h2); + evas_map_point_image_uv_set(map, 2, w, h); + evas_map_point_image_uv_set(map, 3, 0, h); + evas_map_point_coord_set(map, 0, x, y + h2, 0); + evas_map_point_coord_set(map, 1, w2, y + h2, 0); + evas_map_point_coord_set(map, 2, w2, y + h, 0); + evas_map_point_coord_set(map, 3, x, y + h, 0); + break; + default: + break; + } + evas_map_util_3d_perspective(map, x + (w / 2), y + (h / 2), 0, FOCAL); +} + +static void +_elm_fx_wipe_show(Evas_Map *map, Elm_Transit_Effect_Wipe_Dir dir, float x, float y, float w, float h, float progress) +{ + float w2, h2; + + switch (dir) + { + case ELM_TRANSIT_EFFECT_WIPE_DIR_LEFT: + w2 = (w - (w * progress)); + h2 = (y + h); + evas_map_point_image_uv_set(map, 0, w2, 0); + evas_map_point_image_uv_set(map, 1, w, 0); + evas_map_point_image_uv_set(map, 2, w, h); + evas_map_point_image_uv_set(map, 3, w2, h); + evas_map_point_coord_set(map, 0, x + w2, y, 0); + evas_map_point_coord_set(map, 1, w, y, 0); + evas_map_point_coord_set(map, 2, w, h2, 0); + evas_map_point_coord_set(map, 3, x + w2, h2, 0); + break; + case ELM_TRANSIT_EFFECT_WIPE_DIR_RIGHT: + w2 = (w * progress); + h2 = (y + h); + evas_map_point_image_uv_set(map, 0, 0, 0); + evas_map_point_image_uv_set(map, 1, w2, 0); + evas_map_point_image_uv_set(map, 2, w2, h); + evas_map_point_image_uv_set(map, 3, 0, h); + evas_map_point_coord_set(map, 0, x, y, 0); + evas_map_point_coord_set(map, 1, x + w2, y, 0); + evas_map_point_coord_set(map, 2, x + w2, h2, 0); + evas_map_point_coord_set(map, 3, x, h2, 0); + break; + case ELM_TRANSIT_EFFECT_WIPE_DIR_UP: + w2 = (x + w); + h2 = (h - (h * progress)); + evas_map_point_image_uv_set(map, 0, 0, h2); + evas_map_point_image_uv_set(map, 1, w, h2); + evas_map_point_image_uv_set(map, 2, w, h); + evas_map_point_image_uv_set(map, 3, 0, h); + evas_map_point_coord_set(map, 0, x, y + h2, 0); + evas_map_point_coord_set(map, 1, w2, y + h2, 0); + evas_map_point_coord_set(map, 2, w2, y + h, 0); + evas_map_point_coord_set(map, 3, x, y + h, 0); + break; + case ELM_TRANSIT_EFFECT_WIPE_DIR_DOWN: + w2 = (x + w); + h2 = (h * progress); + evas_map_point_image_uv_set(map, 0, 0, 0); + evas_map_point_image_uv_set(map, 1, w, 0); + evas_map_point_image_uv_set(map, 2, w, h2); + evas_map_point_image_uv_set(map, 3, 0, h2); + evas_map_point_coord_set(map, 0, x, y, 0); + evas_map_point_coord_set(map, 1, w2, y, 0); + evas_map_point_coord_set(map, 2, w2, y + h2, 0); + evas_map_point_coord_set(map, 3, x, y + h2, 0); + break; + default: + break; + } + evas_map_util_3d_perspective(map, x + (w / 2), y + (h / 2), 0, FOCAL); +} + +static void +_transit_effect_wipe_context_free(void *data, Elm_Transit *transit) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Eina_List *elist; + Evas_Object *obj; + Elm_Transit_Effect_Wipe *wipe = data; + Eina_Bool reverse = elm_transit_auto_reverse_get(transit); + + EINA_LIST_FOREACH(transit->objs, elist, obj) + { + if ((wipe->type == ELM_TRANSIT_EFFECT_WIPE_TYPE_SHOW && !reverse) + || (wipe->type == ELM_TRANSIT_EFFECT_WIPE_TYPE_HIDE && reverse)) + evas_object_show(obj); + else evas_object_hide(obj); + evas_object_map_enable_set(obj, EINA_FALSE); + } + + free(wipe); +} + +static void +_transit_effect_wipe_op(void *data, Elm_Transit *transit, double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Elm_Transit_Effect_Wipe *wipe = data; + Evas_Map *map; + Evas_Coord _x, _y, _w, _h; + Eina_List *elist; + Evas_Object *obj; + + map = evas_map_new(4); + if (!map) return; + + evas_map_smooth_set(map, EINA_TRUE); + + EINA_LIST_FOREACH(transit->objs, elist, obj) + { + evas_object_geometry_get(obj, &_x, &_y, &_w, &_h); + + if (wipe->type == ELM_TRANSIT_EFFECT_WIPE_TYPE_SHOW) + _elm_fx_wipe_show(map, wipe->dir, _x, _y, _w, _h, (float)progress); + else + _elm_fx_wipe_hide(map, wipe->dir, _x, _y, _w, _h, (float)progress); + + evas_object_map_enable_set(obj, EINA_TRUE); + evas_object_map_set(obj, map); + } + evas_map_free(map); +} + +static void * +_transit_effect_wipe_context_new(Elm_Transit_Effect_Wipe_Type type, Elm_Transit_Effect_Wipe_Dir dir) +{ + Elm_Transit_Effect_Wipe *wipe; + + wipe = ELM_NEW(Elm_Transit_Effect_Wipe); + if (!wipe) return NULL; + + wipe->type = type; + wipe->dir = dir; + + return wipe; +} + +/** + * Add the Wipe Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates wipe effect context + * and add it's required APIs to elm_transit_effect_add. + * @note This effect will be applied to the objects that are in the transit, + * If you change the set of objects in the transit with elm_transit_object_add() + * or elm_transit_object_remove(), the set of objects affected by this effect + * will be changed too. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @param type Wipe type. Hide or show. + * @param dir Wipe Direction. + * @return Wipe effect context data. + * + * @ingroup Transit + * @warning Is higher recommended just create a transit with this effect when + * the window that the objects of the transit belongs has already been created. + * This is because this effect needs the geometry information about the objects, + * and if the window was not created yet, it can get a wrong information. + * @warning Is not recommended remove or add an object after the transit begins + * to run, because the order of the objects will be affected. + */ +EAPI void * +elm_transit_effect_wipe_add(Elm_Transit *transit, Elm_Transit_Effect_Wipe_Type type, Elm_Transit_Effect_Wipe_Dir dir) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_wipe_context_new(type, dir); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_wipe_op, effect_context, + _transit_effect_wipe_context_free); + return effect_context; +} + + +/////////////////////////////////////////////////////////////////////////////// +//Color FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Color Elm_Transit_Effect_Color; + +struct _Elm_Transit_Effect_Color +{ + struct _unsigned_color { + unsigned int r, g, b, a; + } from; + struct _signed_color { + int r, g, b, a; + } to; +}; + +static void +_transit_effect_color_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + free(data); +} + +static void +_transit_effect_color_op(void *data, Elm_Transit *transit, double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Elm_Transit_Effect_Color *color = data; + Evas_Object *obj; + Eina_List *elist; + unsigned int r, g, b, a; + + r = (color->from.r + (int)((float)color->to.r * progress)); + g = (color->from.g + (int)((float)color->to.g * progress)); + b = (color->from.b + (int)((float)color->to.b * progress)); + a = (color->from.a + (int)((float)color->to.a * progress)); + + EINA_LIST_FOREACH(transit->objs, elist, obj) + evas_object_color_set(obj, r, g, b, a); +} + +static void * +_transit_effect_color_context_new(unsigned int from_r, unsigned int from_g, unsigned int from_b, unsigned int from_a, unsigned int to_r, unsigned int to_g, unsigned int to_b, unsigned int to_a) +{ + Elm_Transit_Effect_Color *color; + + color = ELM_NEW(Elm_Transit_Effect_Color); + if (!color) return NULL; + + color->from.r = from_r; + color->from.g = from_g; + color->from.b = from_b; + color->from.a = from_a; + color->to.r = to_r - from_r; + color->to.g = to_g - from_g; + color->to.b = to_b - from_b; + color->to.a = to_a - from_a; + + return color; +} + +/** + * Add the Color Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates color effect context + * and add it's required APIs to elm_transit_effect_add. + * @note This effect will be applied to the objects that are in the transit, + * If you change the set of objects in the transit with elm_transit_object_add() + * or elm_transit_object_remove(), the set of objects affected by this effect + * will be changed too. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @param from_r RGB R when effect begins. + * @param from_g RGB G when effect begins. + * @param from_b RGB B when effect begins. + * @param from_a RGB A when effect begins. + * @param to_r RGB R when effect ends. + * @param to_g RGB G when effect ends. + * @param to_b RGB B when effect ends. + * @param to_a RGB A when effect ends. + * @return Color effect context data. + * + * @ingroup Transit + */ +EAPI void * +elm_transit_effect_color_add(Elm_Transit *transit, unsigned int from_r, unsigned int from_g, unsigned int from_b, unsigned int from_a, unsigned int to_r, unsigned int to_g, unsigned int to_b, unsigned int to_a) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_color_context_new(from_r, from_g, from_b, from_a, to_r, to_g, to_b, to_a); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_color_op, effect_context, + _transit_effect_color_context_free); + return effect_context; +} + +/////////////////////////////////////////////////////////////////////////////// +//Fade FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Fade Elm_Transit_Effect_Fade; +typedef struct _Elm_Transit_Effect_Fade_Node Elm_Transit_Effect_Fade_Node; + +struct _Elm_Transit_Effect_Fade_Node +{ + Evas_Object *before; + Evas_Object *after; + struct _signed_color before_color, after_color; + int before_alpha; + int after_alpha; + Eina_Bool inversed : 1; +}; + +struct _Elm_Transit_Effect_Fade +{ + Eina_List *nodes; +}; + +static void +_fade_object_del_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit_Effect_Fade *fade = data; + Eina_List *elist; + Elm_Transit_Effect_Fade_Node *fade_node; + + EINA_LIST_FOREACH(fade->nodes, elist, fade_node) + { + if (fade_node->before == obj) + evas_object_event_callback_del(fade_node->after, + EVAS_CALLBACK_DEL, _fade_object_del_cb); + else if (fade_node->after == obj) + evas_object_event_callback_del(fade_node->before, + EVAS_CALLBACK_DEL, _fade_object_del_cb); + else continue; + + fade->nodes = eina_list_remove_list(fade->nodes, elist); + free(fade_node); + break; + } +} + +static Eina_List * +_fade_nodes_build(Elm_Transit *transit, Elm_Transit_Effect_Fade *fade_data) +{ + Elm_Transit_Effect_Fade_Node *fade; + Eina_List *data_list = NULL; + int i, count; + + count = eina_list_count(transit->objs); + for (i = 0; i < (count - 1); i += 2) + { + fade = ELM_NEW(Elm_Transit_Effect_Fade_Node); + if (!fade) + { + eina_list_free(data_list); + return NULL; + } + + fade->before = eina_list_nth(transit->objs, i); + fade->after = eina_list_nth(transit->objs, i+1); + + evas_object_color_get(fade->before, + &fade->before_color.r, &fade->before_color.g, + &fade->before_color.b, &fade->before_color.a); + evas_object_color_get(fade->after, + &fade->after_color.r, &fade->after_color.g, + &fade->after_color.b, &fade->after_color.a); + + fade->before_alpha = (255 - fade->before_color.a); + fade->after_alpha = (255 - fade->after_color.a); + + data_list = eina_list_append(data_list, fade); + + evas_object_event_callback_add(fade->before, + EVAS_CALLBACK_DEL, _fade_object_del_cb, fade_data); + evas_object_event_callback_add(fade->after, + EVAS_CALLBACK_DEL, _fade_object_del_cb, fade_data); + } + return data_list; +} + +static void +_transit_effect_fade_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + Elm_Transit_Effect_Fade *fade = data; + Elm_Transit_Effect_Fade_Node *fade_node; + Eina_List *elist, *elist_next; + + EINA_LIST_FOREACH_SAFE(fade->nodes, elist, elist_next, fade_node) + { + evas_object_color_set(fade_node->before, fade_node->before_color.r, + fade_node->before_color.g, + fade_node->before_color.b, + fade_node->before_color.a); + evas_object_color_set(fade_node->after, fade_node->after_color.r, + fade_node->after_color.g, + fade_node->after_color.b, + fade_node->after_color.a); + + fade->nodes = eina_list_remove_list(fade->nodes, elist); + evas_object_event_callback_del(fade_node->before, + EVAS_CALLBACK_DEL, _fade_object_del_cb); + evas_object_event_callback_del(fade_node->after, + EVAS_CALLBACK_DEL, _fade_object_del_cb); + free(fade_node); + } + + free(fade); +} + +static void +_transit_effect_fade_op(void *data, Elm_Transit *transit __UNUSED__, double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + Elm_Transit_Effect_Fade *fade = data; + Eina_List *elist; + Elm_Transit_Effect_Fade_Node *fade_node; + float _progress; + + if (!fade->nodes) + fade->nodes = _fade_nodes_build(transit, fade); + + EINA_LIST_FOREACH(fade->nodes, elist, fade_node) + { + if (progress < 0.5) + { + if (!fade_node->inversed) + { + evas_object_hide(fade_node->after); + evas_object_show(fade_node->before); + fade_node->inversed = EINA_TRUE; + } + + _progress = (1 - (progress * 2)); + + evas_object_color_set(fade_node->before, + fade_node->before_color.r * _progress, + fade_node->before_color.g * _progress, + fade_node->before_color.b * _progress, + fade_node->before_color.a + + fade_node->before_alpha * (1 - _progress)); + } + else + { + if (fade_node->inversed) + { + evas_object_hide(fade_node->before); + evas_object_show(fade_node->after); + fade_node->inversed = EINA_FALSE; + } + + _progress = ((progress - 0.5) * 2); + + evas_object_color_set(fade_node->after, + fade_node->after_color.r * _progress, + fade_node->after_color.g * _progress, + fade_node->after_color.b * _progress, + fade_node->after_color.a + + fade_node->after_alpha * (1 - _progress)); + } + } +} + +static void * +_transit_effect_fade_context_new(void) +{ + Elm_Transit_Effect_Fade *fade; + fade = ELM_NEW(Elm_Transit_Effect_Fade); + if (!fade) return NULL; + return fade; +} + +/** + * Add the Fade Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates fade effect context + * and add it's required APIs to elm_transit_effect_add. + * @note This effect is applied to each pair of objects in the order they are listed + * in the transit list of objects. The first object in the pair will be the + * "before" object and the second will be the "after" object. + * @note When this function is called, it gets the current objects in + * the transit, that is, elm_transit_object_remove() and elm_transit_object_add() + * will not cause any changes in the set of objects that this effect is being + * applied. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @return Fade effect context data. + * + * @ingroup Transit + * @warning Is higher recommended just create a transit with this effect when + * the window that the objects of the transit belongs has already been created. + * This is because this effect needs the color information about the objects, + * and if the window was not created yet, it can get a wrong information. + * @warning Is not recommended remove or add an object after the transit begins + * to run, because the order of the objects will be affected. + */ +EAPI void * +elm_transit_effect_fade_add(Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + + void *effect_context = _transit_effect_fade_context_new(); + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_fade_op, effect_context, + _transit_effect_fade_context_free); + return effect_context; +} + + +/////////////////////////////////////////////////////////////////////////////// +//Blend FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Blend Elm_Transit_Effect_Blend; +typedef struct _Elm_Transit_Effect_Blend_Node Elm_Transit_Effect_Blend_Node; + +struct _Elm_Transit_Effect_Blend_Node +{ + Evas_Object *before; + Evas_Object *after; + struct _signed_color from, to; +}; + +struct _Elm_Transit_Effect_Blend +{ + Eina_List *nodes; +}; + +static void +_blend_object_del_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Transit_Effect_Blend *blend = data; + Eina_List *elist; + Elm_Transit_Effect_Blend_Node *blend_node; + + EINA_LIST_FOREACH(blend->nodes, elist, blend_node) + { + if (blend_node->after == obj) + evas_object_event_callback_del(blend_node->before, + EVAS_CALLBACK_DEL, _blend_object_del_cb); + else if (blend_node->before == obj) + evas_object_event_callback_del(blend_node->after, + EVAS_CALLBACK_DEL, _blend_object_del_cb); + else continue; + + blend->nodes = eina_list_remove_list(blend->nodes, elist); + free(blend_node); + break; + } +} + +static Eina_List * +_blend_nodes_build(Elm_Transit *transit, Elm_Transit_Effect_Blend *blend) +{ + Elm_Transit_Effect_Blend_Node *blend_node; + Eina_List *data_list = NULL; + int i, count; + + count = eina_list_count(transit->objs); + for (i = 0; i < (count - 1); i += 2) + { + blend_node = ELM_NEW(Elm_Transit_Effect_Blend_Node); + if (!blend_node) + { + eina_list_free(data_list); + return NULL; + } + + blend_node->before = eina_list_nth(transit->objs, i); + blend_node->after = eina_list_nth(transit->objs, i + 1); + evas_object_show(blend_node->before); + evas_object_show(blend_node->after); + + evas_object_color_get(blend_node->before, &blend_node->from.r, + &blend_node->from.g, &blend_node->from.b, + &blend_node->from.a); + evas_object_color_get(blend_node->after, &blend_node->to.r, + &blend_node->to.g, &blend_node->to.b, + &blend_node->to.a); + + data_list = eina_list_append(data_list, blend_node); + + evas_object_event_callback_add(blend_node->before, + EVAS_CALLBACK_DEL, _blend_object_del_cb, blend); + evas_object_event_callback_add(blend_node->after, + EVAS_CALLBACK_DEL, _blend_object_del_cb, blend); + } + return data_list; +} + +void +_transit_effect_blend_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + Elm_Transit_Effect_Blend *blend = data; + Elm_Transit_Effect_Blend_Node *blend_node; + Eina_List *elist, *elist_next; + + EINA_LIST_FOREACH_SAFE(blend->nodes, elist, elist_next, blend_node) + { + evas_object_color_set(blend_node->before, + blend_node->from.r, blend_node->from.g, + blend_node->from.b, blend_node->from.a); + evas_object_color_set(blend_node->after, blend_node->to.r, + blend_node->to.g, blend_node->to.b, + blend_node->to.a); + + if (elm_transit_auto_reverse_get(transit)) + evas_object_hide(blend_node->after); + else + evas_object_hide(blend_node->before); + + blend->nodes = eina_list_remove_list(blend->nodes, elist); + + evas_object_event_callback_del(blend_node->before, + EVAS_CALLBACK_DEL, _blend_object_del_cb); + evas_object_event_callback_del(blend_node->after, + EVAS_CALLBACK_DEL, _blend_object_del_cb); + free(blend_node); + } + free(data); +} + +void +_transit_effect_blend_op(void *data, Elm_Transit *transit, double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Elm_Transit_Effect_Blend *blend = data; + Elm_Transit_Effect_Blend_Node *blend_node; + Eina_List *elist; + + if (!blend->nodes) blend->nodes = _blend_nodes_build(transit, blend); + + EINA_LIST_FOREACH(blend->nodes, elist, blend_node) + { + evas_object_color_set(blend_node->before, + (int)(blend_node->from.r * (1 - progress)), + (int)(blend_node->from.g * (1 - progress)), + (int)(blend_node->from.b * (1 - progress)), + (int)(blend_node->from.a * (1 - progress))); + evas_object_color_set(blend_node->after, + (int)(blend_node->to.r * progress), + (int)(blend_node->to.g * progress), + (int)(blend_node->to.b * progress), + (int)(blend_node->to.a * progress)); + } +} + +static void * +_transit_effect_blend_context_new(void) +{ + Elm_Transit_Effect_Blend *blend; + + blend = ELM_NEW(Elm_Transit_Effect_Blend); + if (!blend) return NULL; + return blend; +} + +/** + * Add the Blend Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates blend effect context + * and add it's required APIs to elm_transit_effect_add. + * @note This effect is applied to each pair of objects in the order they are listed + * in the transit list of objects. The first object in the pair will be the + * "before" object and the second will be the "after" object. + * @note When this function be called, it gets the current objects in + * the transit, that is, elm_transit_object_remove() and elm_transit_object_add() + * will not cause any changes in the set of objects that this effect is being + * applied. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @return Blend effect context data. + * + * @ingroup Transit + * @warning Is higher recommended just create a transit with this effect when + * the window that the objects of the transit belongs has already been created. + * This is because this effect needs the color information about the objects, + * and if the window was not created yet, it can get a wrong information. + * @warning Is not recommended remove or add an object after the transit begins + * to run, because the order of the objects will be affected. + */ +EAPI void * +elm_transit_effect_blend_add(Elm_Transit *transit) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_blend_context_new(); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_blend_op, effect_context, + _transit_effect_blend_context_free); + return effect_context; +} + + +/////////////////////////////////////////////////////////////////////////////// +//Rotation FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Rotation Elm_Transit_Effect_Rotation; + +struct _Elm_Transit_Effect_Rotation +{ + float from, to; +}; + +static void +_transit_effect_rotation_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + free(data); +} + +static void +_transit_effect_rotation_op(void *data, Elm_Transit *transit, double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Elm_Transit_Effect_Rotation *rotation = data; + Evas_Map *map; + Evas_Coord x, y, w, h; + float degree; + float half_w, half_h; + Eina_List *elist; + Evas_Object *obj; + + map = evas_map_new(4); + if (!map) return; + + evas_map_smooth_set(map, EINA_TRUE); + + EINA_LIST_FOREACH(transit->objs, elist, obj) + { + evas_map_util_points_populate_from_object_full(map, obj, 0); + degree = rotation->from + (float)(progress * rotation->to); + + evas_object_geometry_get(obj, &x, &y, &w, &h); + + half_w = (float)w * 0.5; + half_h = (float)h * 0.5; + + evas_map_util_3d_rotate(map, 0, 0, degree, x + half_w, y + half_h, 0); + evas_map_util_3d_perspective(map, x + half_w, y + half_h, 0, FOCAL); + evas_object_map_enable_set(obj, EINA_TRUE); + evas_object_map_set(obj, map); + } + evas_map_free(map); +} + +static void * +_transit_effect_rotation_context_new(float from_degree, float to_degree) +{ + Elm_Transit_Effect_Rotation *rotation; + + rotation = ELM_NEW(Elm_Transit_Effect_Rotation); + if (!rotation) return NULL; + + rotation->from = from_degree; + rotation->to = to_degree - from_degree; + + return rotation; +} + +/** + * Add the Rotation Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates rotation effect context + * and add it's required APIs to elm_transit_effect_add. + * @note This effect will be applied to the objects that are in the transit, + * If you change the set of objects in the transit with elm_transit_object_add() + * or elm_transit_object_remove(), the set of objects affected by this effect + * will be changed too. + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @param from_degree Degree when effect begins. + * @param to_degree Degree when effect is ends. + * @return Rotation effect context data. + * + * @ingroup Transit + * @warning Is higher recommended just create a transit with this effect when + * the window that the objects of the transit belongs has already been created. + * This is because this effect needs the geometry information about the objects, + * and if the window was not created yet, it can get a wrong information. + * @warning Is not recommended remove or add an object after the transit begins + * to run, because the order of the objects will be affected. + */ +EAPI void * +elm_transit_effect_rotation_add(Elm_Transit *transit, float from_degree, float to_degree) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_rotation_context_new(from_degree, to_degree); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_rotation_op, effect_context, + _transit_effect_rotation_context_free); + return effect_context; +} + + +/////////////////////////////////////////////////////////////////////////////// +// ImageAnimation FX +/////////////////////////////////////////////////////////////////////////////// +typedef struct _Elm_Transit_Effect_Image_Animation Elm_Transit_Effect_Image_Animation; + +struct _Elm_Transit_Effect_Image_Animation +{ + Eina_List *images; +}; + +static void +_transit_effect_image_animation_context_free(void *data, Elm_Transit *transit __UNUSED__) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + Elm_Transit_Effect_Image_Animation *image_animation = data; + const char *image; + Eina_List *elist, *elist_next; + + EINA_LIST_FOREACH_SAFE(image_animation->images, elist, elist_next, image) + { + image_animation->images = + eina_list_remove_list(image_animation->images, elist); + eina_stringshare_del(image); + } + + free(data); +} + +static void +_transit_effect_image_animation_op(void *data, Elm_Transit *transit, double progress) +{ + EINA_SAFETY_ON_NULL_RETURN(data); + EINA_SAFETY_ON_NULL_RETURN(transit); + Eina_List *elist; + Evas_Object *obj; + const char *type; + Elm_Transit_Effect_Image_Animation *image_animation = data; + unsigned int count = 0; + int len; + + type = eina_stringshare_add("icon"); + len = eina_list_count(image_animation->images); + + if (!len) count = floor(progress * len); + else count = floor(progress * (len - 1)); + + EINA_LIST_FOREACH(transit->objs, elist, obj) + { + if (elm_widget_type_check(obj, type)) + elm_icon_file_set(obj, + eina_list_nth(image_animation->images, count), NULL); + } + + eina_stringshare_del(type); +} + +static void * +_transit_effect_image_animation_context_new(Eina_List *images) +{ + Elm_Transit_Effect_Image_Animation *image_animation; + image_animation = ELM_NEW(Elm_Transit_Effect_Image_Animation); + + if (!image_animation) return NULL; + image_animation->images = images; + return image_animation; +} + +/** + * Add the Rotation Effect to Elm_Transit. + * + * @note This API is one of the facades. It creates image animation effect context + * and add it's required APIs to elm_transit_effect_add. + * The @p images parameter is a list images paths. This list and + * its contents will be deleted at the end of the effect by + * elm_transit_effect_image_animation_context_free() function. + * @note This effect will be applied to the objects that are in the transit, + * If you change the set of objects in the transit with elm_transit_object_add() + * or elm_transit_object_remove(), the set of objects affected by this effect + * will be changed too. + * + * Example: + * @code + * char buf[PATH_MAX]; + * Eina_List *images = NULL; + * Elm_Transit *transi = elm_transit_add(); + * + * snprintf(buf, sizeof(buf), "%s/images/icon_11.png", PACKAGE_DATA_DIR); + * images = eina_list_append(images, eina_stringshare_add(buf)); + * + * snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + * images = eina_list_append(images, eina_stringshare_add(buf)); + * elm_transit_effect_image_animation_add(transi, images); + * + * @endcode + * + * @see elm_transit_effect_add() + * + * @param transit Transit object. + * @param images Eina_List of images file paths. This list and + * its contents will be deleted at the end of the effect by + * elm_transit_effect_image_animation_context_free() function. + * @return Image Animation effect context data. + * + * @ingroup Transit + */ +EAPI void * +elm_transit_effect_image_animation_add(Elm_Transit *transit, Eina_List *images) +{ + ELM_TRANSIT_CHECK_OR_RETURN(transit, NULL); + void *effect_context = _transit_effect_image_animation_context_new(images); + + if (!effect_context) return NULL; + elm_transit_effect_add(transit, + _transit_effect_image_animation_op, effect_context, + _transit_effect_image_animation_context_free); + return effect_context; +} diff --git a/src/lib/elm_util.c b/src/lib/elm_util.c new file mode 100644 index 0000000..f3d65d7 --- /dev/null +++ b/src/lib/elm_util.c @@ -0,0 +1,197 @@ +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif +#include +#include "elm_priv.h" + +static char * +_str_ncpy(char *dest, const char *src, size_t count) +{ + if ((!dest) || (!src)) return NULL; + return strncpy(dest, src, count); +} + +static char * +_str_append(char *str, const char *txt, int *len, int *alloc) +{ + int txt_len = strlen(txt); + + if (txt_len <= 0) return str; + if ((*len + txt_len) >= *alloc) + { + char *str2; + int alloc2; + + alloc2 = *alloc + txt_len + 128; + str2 = realloc(str, alloc2); + if (!str2) return str; + *alloc = alloc2; + str = str2; + } + strcpy(str + *len, txt); + *len += txt_len; + return str; +} + +char * +_elm_util_mkup_to_text(const char *mkup) +{ + char *str = NULL; + int str_len = 0, str_alloc = 0; + char *s, *p; + char *tag_start, *tag_end, *esc_start, *esc_end, *ts; + + if (!mkup) return NULL; + tag_start = tag_end = esc_start = esc_end = NULL; + p = (char *)mkup; + s = p; + for (;;) + { + if ((!*p) || + (tag_end) || (esc_end) || + (tag_start) || (esc_start)) + { + if (tag_end) + { + char *ttag; + + ttag = malloc(tag_end - tag_start); + if (ttag) + { + _str_ncpy(ttag, tag_start + 1, tag_end - tag_start - 1); + ttag[tag_end - tag_start - 1] = 0; + if (!strcmp(ttag, "br")) + str = _str_append(str, "\n", &str_len, &str_alloc); + else if (!strcmp(ttag, "\n")) + str = _str_append(str, "\n", &str_len, &str_alloc); + else if (!strcmp(ttag, "\\n")) + str = _str_append(str, "\n", &str_len, &str_alloc); + else if (!strcmp(ttag, "\t")) + str = _str_append(str, "\t", &str_len, &str_alloc); + else if (!strcmp(ttag, "\\t")) + str = _str_append(str, "\t", &str_len, &str_alloc); + else if (!strcmp(ttag, "ps")) /* Unicode paragraph separator */ + str = _str_append(str, "\xE2\x80\xA9", &str_len, &str_alloc); + free(ttag); + } + tag_start = tag_end = NULL; + } + else if (esc_end) + { + ts = malloc(esc_end - esc_start + 1); + if (ts) + { + const char *esc; + _str_ncpy(ts, esc_start, esc_end - esc_start); + ts[esc_end - esc_start] = 0; + esc = evas_textblock_escape_string_get(ts); + if (esc) + str = _str_append(str, esc, &str_len, &str_alloc); + free(ts); + } + esc_start = esc_end = NULL; + } + else if ((!*p) && (s)) + { + ts = malloc(p - s + 1); + if (ts) + { + _str_ncpy(ts, s, p - s); + ts[p - s] = 0; + str = _str_append(str, ts, &str_len, &str_alloc); + free(ts); + } + break; + } + } + if (*p == '<') + { + if ((s) && (!esc_start)) + { + tag_start = p; + tag_end = NULL; + ts = malloc(p - s + 1); + if (ts) + { + _str_ncpy(ts, s, p - s); + ts[p - s] = 0; + str = _str_append(str, ts, &str_len, &str_alloc); + free(ts); + } + s = NULL; + } + } + else if (*p == '>') + { + if (tag_start) + { + tag_end = p; + s = p + 1; + } + } + else if (*p == '&') + { + if ((s) && (!tag_start)) + { + esc_start = p; + esc_end = NULL; + ts = malloc(p - s + 1); + if (ts) + { + _str_ncpy(ts, s, p - s); + ts[p - s] = 0; + str = _str_append(str, ts, &str_len, &str_alloc); + free(ts); + } + s = NULL; + } + } + else if (*p == ';') + { + if (esc_start) + { + esc_end = p; + s = p + 1; + } + } + p++; + } + return str; +} + +char * +_elm_util_text_to_mkup(const char *text) +{ + char *str = NULL; + int str_len = 0, str_alloc = 0; + int ch, pos = 0, pos2 = 0; + + if (!text) return NULL; + for (;;) + { + pos = pos2; + pos2 = evas_string_char_next_get((char *)(text), pos2, &ch); + if ((ch <= 0) || (pos2 <= 0)) break; + if (ch == '\n') + str = _str_append(str, "
    ", &str_len, &str_alloc); + else if (ch == '\t') + str = _str_append(str, "<\t>", &str_len, &str_alloc); + else if (ch == '<') + str = _str_append(str, "<", &str_len, &str_alloc); + else if (ch == '>') + str = _str_append(str, ">", &str_len, &str_alloc); + else if (ch == '&') + str = _str_append(str, "&", &str_len, &str_alloc); + else if (ch == 0x2029) /* PS */ + str = _str_append(str, "", &str_len, &str_alloc); + else + { + char tstr[16]; + + _str_ncpy(tstr, text + pos, pos2 - pos); + tstr[pos2 - pos] = 0; + str = _str_append(str, tstr, &str_len, &str_alloc); + } + } + return str; +} diff --git a/src/lib/elm_widget.c b/src/lib/elm_widget.c new file mode 100644 index 0000000..e3e1e5a --- /dev/null +++ b/src/lib/elm_widget.c @@ -0,0 +1,2758 @@ +#include +#include "elm_priv.h" + +static const char SMART_NAME[] = "elm_widget"; + +#define API_ENTRY \ + Smart_Data *sd = evas_object_smart_data_get(obj); \ + if ((!obj) || (!sd) || (!_elm_widget_is(obj))) +#define INTERNAL_ENTRY \ + Smart_Data *sd = evas_object_smart_data_get(obj); \ + if (!sd) return; + +typedef struct _Smart_Data Smart_Data; +typedef struct _Edje_Signal_Data Edje_Signal_Data; +typedef struct _Elm_Event_Cb_Data Elm_Event_Cb_Data; + +struct _Smart_Data +{ + Evas_Object *obj; + const char *type; + Evas_Object *parent_obj; + Evas_Coord x, y, w, h; + Eina_List *subobjs; + Evas_Object *resize_obj; + Evas_Object *hover_obj; + Eina_List *tooltips, *cursors; + void (*del_func) (Evas_Object *obj); + void (*del_pre_func) (Evas_Object *obj); + void (*focus_func) (Evas_Object *obj); + void (*activate_func) (Evas_Object *obj); + void (*disable_func) (Evas_Object *obj); + void (*theme_func) (Evas_Object *obj); + Eina_Bool (*event_func) (Evas_Object *obj, Evas_Object *source, Evas_Callback_Type type, void *event_info); + void (*signal_func) (Evas_Object *obj, const char *emission, + const char *source); + void (*callback_add_func) (Evas_Object *obj, const char *emission, + const char *source, void (*func) (void *data, + Evas_Object *o, const char *emission, + const char *source), void *data); + void (*callback_del_func) (Evas_Object *obj, const char *emission, + const char *source, void (*func) (void *data, + Evas_Object *o, const char *emission, + const char *source), void *data); + void (*changed_func) (Evas_Object *obj); + Eina_Bool (*focus_next_func) (const Evas_Object *obj, Elm_Focus_Direction dir, + Evas_Object **next); + void (*on_focus_func) (void *data, Evas_Object *obj); + void *on_focus_data; + void (*on_change_func) (void *data, Evas_Object *obj); + void *on_change_data; + void (*on_show_region_func) (void *data, Evas_Object *obj); + void *on_show_region_data; + void (*focus_region_func) (Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h); + void (*on_focus_region_func) (const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h); + void *data; + Evas_Coord rx, ry, rw, rh; + int scroll_hold; + int scroll_freeze; + double scale; + Elm_Theme *theme; + const char *style; + unsigned int focus_order; + Eina_Bool focus_order_on_calc; + + int child_drag_x_locked; + int child_drag_y_locked; + + Eina_List *edje_signals; + + Eina_Bool drag_x_locked : 1; + Eina_Bool drag_y_locked : 1; + + Eina_Bool can_focus : 1; + Eina_Bool child_can_focus : 1; + Eina_Bool focused : 1; + Eina_Bool highlight_ignore : 1; + Eina_Bool highlight_in_theme : 1; + Eina_Bool disabled : 1; + + Eina_List *focus_chain; + Eina_List *event_cb; +}; + +struct _Edje_Signal_Data +{ + Evas_Object *obj; + Edje_Signal_Cb func; + const char *emission; + const char *source; + void *data; +}; + +struct _Elm_Event_Cb_Data { + Elm_Event_Cb func; + const void *data; +}; + +/* local subsystem functions */ +static void _smart_reconfigure(Smart_Data *sd); +static void _smart_add(Evas_Object *obj); +static void _smart_del(Evas_Object *obj); +static void _smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y); +static void _smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h); +static void _smart_show(Evas_Object *obj); +static void _smart_hide(Evas_Object *obj); +static void _smart_color_set(Evas_Object *obj, int r, int g, int b, int a); +static void _smart_clip_set(Evas_Object *obj, Evas_Object * clip); +static void _smart_clip_unset(Evas_Object *obj); +static void _smart_calculate(Evas_Object *obj); +static void _smart_init(void); + +static void _if_focused_revert(Evas_Object *obj, Eina_Bool can_focus_only); +static Evas_Object *_newest_focus_order_get(Evas_Object *obj, unsigned int *newest_focus_order, Eina_Bool can_focus_only); + +/* local subsystem globals */ +static Evas_Smart *_e_smart = NULL; +static Eina_List *widtypes = NULL; + +static unsigned int focus_order = 0; + +// internal funcs +static inline Eina_Bool +_elm_widget_is(const Evas_Object *obj) +{ + const char *type = evas_object_type_get(obj); + return type == SMART_NAME; +} + +static inline Eina_Bool +_is_focusable(Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->can_focus || (sd->child_can_focus); +} + +static void +_unfocus_parents(Evas_Object *obj) +{ + for (; obj; obj = elm_widget_parent_get(obj)) + { + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (!sd->focused) return; + sd->focused = 0; + } +} + +static void +_focus_parents(Evas_Object *obj) +{ + for (; obj; obj = elm_widget_parent_get(obj)) + { + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->focused) return; + sd->focused = 1; + } +} + +static void +_sub_obj_del(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Smart_Data *sd = data; + + if (_elm_widget_is(obj)) + { + if (elm_widget_focus_get(obj)) _unfocus_parents(sd->obj); + } + if (obj == sd->resize_obj) + sd->resize_obj = NULL; + else if (obj == sd->hover_obj) + sd->hover_obj = NULL; + else + sd->subobjs = eina_list_remove(sd->subobjs, obj); + evas_object_smart_callback_call(sd->obj, "sub-object-del", obj); +} + +static void +_sub_obj_mouse_down(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Evas_Object *o = obj; + do + { + if (_elm_widget_is(o)) break; + o = evas_object_smart_parent_get(o); + } + while (o); + if (!o) return; + if (!_is_focusable(o)) return; + elm_widget_focus_steal(o); +} + +static void +_propagate_x_drag_lock(Evas_Object *obj, int dir) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (sd->parent_obj) + { + Smart_Data *sd2 = evas_object_smart_data_get(sd->parent_obj); + if (sd2) + { + sd2->child_drag_x_locked += dir; + _propagate_x_drag_lock(sd->parent_obj, dir); + } + } +} + +static void +_propagate_y_drag_lock(Evas_Object *obj, int dir) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (sd->parent_obj) + { + Smart_Data *sd2 = evas_object_smart_data_get(sd->parent_obj); + if (sd2) + { + sd2->child_drag_y_locked += dir; + _propagate_y_drag_lock(sd->parent_obj, dir); + } + } +} + +static void +_propagate_event(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info) +{ + INTERNAL_ENTRY; + Evas_Callback_Type type = (Evas_Callback_Type)(long) data; + Evas_Event_Flags *event_flags = NULL; + + switch (type) + { + case EVAS_CALLBACK_KEY_DOWN: + { + Evas_Event_Key_Down *ev = event_info; + event_flags = &(ev->event_flags); + break; + } + case EVAS_CALLBACK_KEY_UP: + { + Evas_Event_Key_Up *ev = event_info; + event_flags = &(ev->event_flags); + break; + } + case EVAS_CALLBACK_MOUSE_WHEEL: + { + Evas_Event_Mouse_Wheel *ev = event_info; + event_flags = &(ev->event_flags); + break; + } + default: + break; + } + + elm_widget_event_propagate(obj, type, event_info, event_flags); +} + +static void +_parent_focus(Evas_Object *obj) +{ + API_ENTRY return; + + Evas_Object *o = elm_widget_parent_get(obj); + sd->focus_order_on_calc = EINA_TRUE; + + if (sd->focused) return; + if (o) + { + unsigned int i = 0; + Evas_Object *ret; + + ret = _newest_focus_order_get(o, &i, EINA_TRUE); + + /* we don't want to bump a common widget ancestor's + focus_order *twice* while parent focusing */ + if (!ret || (!i) || (i != focus_order)) + _parent_focus(o); + } + + if (!sd->focus_order_on_calc) + return; /* we don't want to override it if by means of any of the + callbacks below one gets to calculate our order + first. */ + + focus_order++; + sd->focus_order = focus_order; + sd->focused = EINA_TRUE; + if (sd->on_focus_func) sd->on_focus_func(sd->on_focus_data, obj); + if (sd->focus_func) sd->focus_func(obj); + + _elm_widget_focus_region_show(obj); + + sd->focus_order_on_calc = EINA_FALSE; +} + +static void +_elm_object_focus_chain_del_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Smart_Data *sd = data; + + sd->focus_chain = eina_list_remove(sd->focus_chain, obj); +} + +// exposed util funcs to elm +void +_elm_widget_type_clear(void) +{ + const char **ptr; + + EINA_LIST_FREE(widtypes, ptr) + { + eina_stringshare_del(*ptr); + *ptr = NULL; + } +} + +void +_elm_widget_focus_region_show(const Evas_Object *obj) +{ + Evas_Coord x, y, w, h, ox, oy; + Smart_Data *sd2; + Evas_Object *o; + + API_ENTRY return; + + o = elm_widget_parent_get(obj); + if (!o) return; + + elm_widget_focus_region_get(obj, &x, &y, &w, &h); + evas_object_geometry_get(obj, &ox, &oy, NULL, NULL); + while (o) + { + Evas_Coord px, py; + sd2 = evas_object_smart_data_get(o); + if (sd2->focus_region_func) + { + sd2->focus_region_func(o, x, y, w, h); + elm_widget_focus_region_get(o, &x, &y, &w, &h); + } + else + { + evas_object_geometry_get(o, &px, &py, NULL, NULL); + x += ox - px; + y += oy - py; + ox = px; + oy = py; + } + o = elm_widget_parent_get(o); + } +} + +/** + * @defgroup Widget Widget + * + * @internal + * Exposed api for making widgets + */ +EAPI void +elm_widget_type_register(const char **ptr) +{ + widtypes = eina_list_append(widtypes, (void *)ptr); +} + +EAPI Eina_Bool +elm_widget_api_check(int ver) +{ + if (ver != ELM_INTERNAL_API_VERSION) + { + CRITICAL("Elementary widget api versions do not match"); + return EINA_FALSE; + } + return EINA_TRUE; +} + +EAPI Evas_Object * +elm_widget_add(Evas *evas) +{ + _smart_init(); + return evas_object_smart_add(evas, _e_smart); +} + +EAPI void +elm_widget_del_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)) +{ + API_ENTRY return; + sd->del_func = func; +} + +EAPI void +elm_widget_del_pre_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)) +{ + API_ENTRY return; + sd->del_pre_func = func; +} + +EAPI void +elm_widget_focus_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)) +{ + API_ENTRY return; + sd->focus_func = func; +} + +EAPI void +elm_widget_activate_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)) +{ + API_ENTRY return; + sd->activate_func = func; +} + +EAPI void +elm_widget_disable_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)) +{ + API_ENTRY return; + sd->disable_func = func; +} + +EAPI void +elm_widget_theme_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)) +{ + API_ENTRY return; + sd->theme_func = func; +} + +EAPI void +elm_widget_event_hook_set(Evas_Object *obj, Eina_Bool (*func) (Evas_Object *obj, Evas_Object *source, Evas_Callback_Type type, void *event_info)) +{ + API_ENTRY return; + sd->event_func = func; +} + +EAPI void +elm_widget_changed_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)) +{ + API_ENTRY return; + sd->changed_func = func; +} + +EAPI void +elm_widget_signal_emit_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj, const char *emission, const char *source)) +{ + API_ENTRY return; + sd->signal_func = func; +} + +EAPI void +elm_widget_signal_callback_add_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data)) +{ + API_ENTRY return; + sd->callback_add_func = func; +} + +EAPI void +elm_widget_signal_callback_del_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data)) +{ + API_ENTRY return; + sd->callback_del_func = func; +} + +EAPI void +elm_widget_theme(Evas_Object *obj) +{ + const Eina_List *l; + Evas_Object *child; + Elm_Tooltip *tt; + Elm_Cursor *cur; + + API_ENTRY return; + EINA_LIST_FOREACH(sd->subobjs, l, child) elm_widget_theme(child); + if (sd->resize_obj) elm_widget_theme(sd->resize_obj); + if (sd->hover_obj) elm_widget_theme(sd->hover_obj); + EINA_LIST_FOREACH(sd->tooltips, l, tt) elm_tooltip_theme(tt); + EINA_LIST_FOREACH(sd->cursors, l, cur) elm_cursor_theme(cur); + if (sd->theme_func) sd->theme_func(obj); +} + +EAPI void +elm_widget_theme_specific(Evas_Object *obj, Elm_Theme *th, Eina_Bool force) +{ + const Eina_List *l; + Evas_Object *child; + Elm_Tooltip *tt; + Elm_Cursor *cur; + Elm_Theme *th2, *thdef; + + API_ENTRY return; + thdef = elm_theme_default_get(); + if (!th) th = thdef; + if (!force) + { + th2 = sd->theme; + if (!th2) th2 = thdef; + while (th2) + { + if (th2 == th) + { + force = EINA_TRUE; + break; + } + if (th2 == thdef) break; + th2 = th2->ref_theme; + if (!th2) th2 = thdef; + } + } + if (!force) return; + EINA_LIST_FOREACH(sd->subobjs, l, child) + elm_widget_theme_specific(child, th, force); + if (sd->resize_obj) elm_widget_theme(sd->resize_obj); + if (sd->hover_obj) elm_widget_theme(sd->hover_obj); + EINA_LIST_FOREACH(sd->tooltips, l, tt) elm_tooltip_theme(tt); + EINA_LIST_FOREACH(sd->cursors, l, cur) elm_cursor_theme(cur); + if (sd->theme_func) sd->theme_func(obj); +} + +/** + * @internal + * + * Set hook to get next object in object focus chain. + * + * @param obj The widget object. + * @param func The hook to be used with this widget. + * + * @ingroup Widget + */ +EAPI void +elm_widget_focus_next_hook_set(Evas_Object *obj, Eina_Bool (*func) (const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next)) +{ + API_ENTRY return; + sd->focus_next_func = func; +} + +EAPI void +elm_widget_on_focus_hook_set(Evas_Object *obj, void (*func) (void *data, Evas_Object *obj), void *data) +{ + API_ENTRY return; + sd->on_focus_func = func; + sd->on_focus_data = data; +} + +EAPI void +elm_widget_on_change_hook_set(Evas_Object *obj, void (*func) (void *data, Evas_Object *obj), void *data) +{ + API_ENTRY return; + sd->on_change_func = func; + sd->on_change_data = data; +} + +EAPI void +elm_widget_on_show_region_hook_set(Evas_Object *obj, void (*func) (void *data, Evas_Object *obj), void *data) +{ + API_ENTRY return; + sd->on_show_region_func = func; + sd->on_show_region_data = data; +} + +/** + * @internal + * + * Set the hook to use to show the focused region. + * + * Whenever a new widget gets focused or it's needed to show the focused + * area of the current one, this hook will be called on objects that may + * want to move their children into their visible area. + * The area given in the hook function is relative to the @p obj widget. + * + * @param obj The widget object + * @param func The function to call to show the specified area. + * + * @ingroup Widget + */ +EAPI void +elm_widget_focus_region_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h)) +{ + API_ENTRY return; + sd->focus_region_func = func; +} + +/** + * @internal + * + * Set the hook to retrieve the focused region of a widget. + * + * This hook will be called by elm_widget_focus_region_get() whenever + * it's needed to get the focused area of a widget. The area must be relative + * to the widget itself and if no hook is set, it will default to the entire + * object. + * + * @param obj The widget object + * @param func The function used to retrieve the focus region. + * + * @ingroup Widget + */ +EAPI void +elm_widget_on_focus_region_hook_set(Evas_Object *obj, void (*func) (const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h)) +{ + API_ENTRY return; + sd->on_focus_region_func = func; +} + +EAPI void +elm_widget_data_set(Evas_Object *obj, void *data) +{ + API_ENTRY return; + sd->data = data; +} + +EAPI void * +elm_widget_data_get(const Evas_Object *obj) +{ + API_ENTRY return NULL; + return sd->data; +} + +EAPI void +elm_widget_sub_object_add(Evas_Object *obj, Evas_Object *sobj) +{ + API_ENTRY return; + double scale, pscale = elm_widget_scale_get(sobj); + Elm_Theme *th, *pth = elm_widget_theme_get(sobj); + + if (_elm_widget_is(sobj)) + { + Smart_Data *sd2 = evas_object_smart_data_get(sobj); + if (sd2) + { + if (sd2->parent_obj == obj) + return; + elm_widget_sub_object_del(sd2->parent_obj, sobj); + sd2->parent_obj = obj; + if (!sd->child_can_focus && (_is_focusable(sobj))) + sd->child_can_focus = EINA_TRUE; + } + } + else + { + void *data = evas_object_data_get(sobj, "elm-parent"); + if (data) + { + if (data == obj) return; + evas_object_event_callback_del(sobj, EVAS_CALLBACK_DEL, + _sub_obj_del); + } + } + + sd->subobjs = eina_list_append(sd->subobjs, sobj); + evas_object_data_set(sobj, "elm-parent", obj); + evas_object_event_callback_add(sobj, EVAS_CALLBACK_DEL, _sub_obj_del, sd); + evas_object_smart_callback_call(obj, "sub-object-add", sobj); + scale = elm_widget_scale_get(sobj); + th = elm_widget_theme_get(sobj); + if ((scale != pscale) || (th != pth)) elm_widget_theme(sobj); + if (elm_widget_focus_get(sobj)) _focus_parents(obj); +} + +EAPI void +elm_widget_sub_object_del(Evas_Object *obj, Evas_Object *sobj) +{ + Evas_Object *sobj_parent; + API_ENTRY return; + if (!sobj) return; + + sobj_parent = evas_object_data_del(sobj, "elm-parent"); + if (sobj_parent != obj) + { + static int abort_on_warn = -1; + ERR("removing sub object %p from parent %p, " + "but elm-parent is different %p!", + sobj, obj, sobj_parent); + if (EINA_UNLIKELY(abort_on_warn == -1)) + { + if (getenv("ELM_ERROR_ABORT")) abort_on_warn = 1; + else abort_on_warn = 0; + } + if (abort_on_warn == 1) abort(); + } + if (!sd->child_can_focus) + { + if (_is_focusable(sobj)) sd->child_can_focus = 0; + } + if (_elm_widget_is(sobj)) + { + Smart_Data *sd2 = evas_object_smart_data_get(sobj); + if (sd2) + { + sd2->parent_obj = NULL; + if (sd2->resize_obj == sobj) + sd2->resize_obj = NULL; + else + sd->subobjs = eina_list_remove(sd->subobjs, sobj); + } + else + sd->subobjs = eina_list_remove(sd->subobjs, sobj); + if (elm_widget_focus_get(sobj)) _unfocus_parents(obj); + } + else + sd->subobjs = eina_list_remove(sd->subobjs, sobj); + evas_object_event_callback_del_full(sobj, EVAS_CALLBACK_DEL, + _sub_obj_del, sd); + evas_object_smart_callback_call(obj, "sub-object-del", sobj); +} + +EAPI void +elm_widget_resize_object_set(Evas_Object *obj, Evas_Object *sobj) +{ + API_ENTRY return; + // orphan previous resize obj + if (sd->resize_obj) + { + evas_object_clip_unset(sd->resize_obj); + evas_object_data_del(sd->resize_obj, "elm-parent"); + if (_elm_widget_is(sd->resize_obj)) + { + Smart_Data *sd2 = evas_object_smart_data_get(sd->resize_obj); + if (sd2) sd2->parent_obj = NULL; + } + evas_object_event_callback_del_full(sd->resize_obj, EVAS_CALLBACK_DEL, + _sub_obj_del, sd); + evas_object_event_callback_del_full(sd->resize_obj, EVAS_CALLBACK_MOUSE_DOWN, + _sub_obj_mouse_down, sd); + evas_object_smart_member_del(sd->resize_obj); + if (_elm_widget_is(sd->resize_obj)) + { + if (elm_widget_focus_get(sd->resize_obj)) _unfocus_parents(obj); + } + } + // orphan new resize obj + if (sobj) + { + evas_object_data_del(sobj, "elm-parent"); + if (_elm_widget_is(sobj)) + { + Smart_Data *sd2 = evas_object_smart_data_get(sobj); + if (sd2) sd2->parent_obj = NULL; + } + evas_object_event_callback_del_full(sobj, EVAS_CALLBACK_DEL, + _sub_obj_del, sd); + evas_object_event_callback_del_full(sobj, EVAS_CALLBACK_MOUSE_DOWN, + _sub_obj_mouse_down, sd); + evas_object_smart_member_del(sobj); + if (_elm_widget_is(sobj)) + { + if (elm_widget_focus_get(sobj)) _unfocus_parents(obj); + } + } + // set the resize obj up + sd->resize_obj = sobj; + if (sd->resize_obj) + { + if (_elm_widget_is(sd->resize_obj)) + { + Smart_Data *sd2 = evas_object_smart_data_get(sd->resize_obj); + if (sd2) sd2->parent_obj = obj; + } + evas_object_clip_set(sobj, evas_object_clip_get(obj)); + evas_object_smart_member_add(sobj, obj); + evas_object_event_callback_add(sobj, EVAS_CALLBACK_DEL, + _sub_obj_del, sd); + evas_object_event_callback_add(sobj, EVAS_CALLBACK_MOUSE_DOWN, + _sub_obj_mouse_down, sd); + _smart_reconfigure(sd); + evas_object_data_set(sobj, "elm-parent", obj); + evas_object_smart_callback_call(obj, "sub-object-add", sobj); + if (_elm_widget_is(sobj)) + { + if (elm_widget_focus_get(sobj)) _focus_parents(obj); + } + } +} + +EAPI void +elm_widget_hover_object_set(Evas_Object *obj, Evas_Object *sobj) +{ + API_ENTRY return; + if (sd->hover_obj) + { + evas_object_event_callback_del_full(sd->hover_obj, EVAS_CALLBACK_DEL, + _sub_obj_del, sd); + } + sd->hover_obj = sobj; + if (sd->hover_obj) + { + evas_object_event_callback_add(sobj, EVAS_CALLBACK_DEL, + _sub_obj_del, sd); + _smart_reconfigure(sd); + } +} + +EAPI void +elm_widget_can_focus_set(Evas_Object *obj, Eina_Bool can_focus) +{ + API_ENTRY return; + sd->can_focus = can_focus; + if (can_focus) + { + evas_object_event_callback_add(obj, EVAS_CALLBACK_KEY_DOWN, + _propagate_event, + (void *)(long) EVAS_CALLBACK_KEY_DOWN); + evas_object_event_callback_add(obj, EVAS_CALLBACK_KEY_UP, + _propagate_event, + (void *)(long) EVAS_CALLBACK_KEY_UP); + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOUSE_WHEEL, + _propagate_event, + (void *)(long)EVAS_CALLBACK_MOUSE_WHEEL); + } + else + { + evas_object_event_callback_del(obj, EVAS_CALLBACK_KEY_DOWN, + _propagate_event); + evas_object_event_callback_del(obj, EVAS_CALLBACK_KEY_UP, + _propagate_event); + evas_object_event_callback_del(obj, EVAS_CALLBACK_MOUSE_WHEEL, + _propagate_event); + } +} + +EAPI Eina_Bool +elm_widget_can_focus_get(const Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->can_focus; +} + +EAPI Eina_Bool +elm_widget_child_can_focus_get(const Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->child_can_focus; +} + +EAPI void +elm_widget_highlight_ignore_set(Evas_Object *obj, Eina_Bool ignore) +{ + API_ENTRY return; + sd->highlight_ignore = !!ignore; +} + +EAPI Eina_Bool +elm_widget_highlight_ignore_get(const Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->highlight_ignore; +} + +EAPI void +elm_widget_highlight_in_theme_set(Evas_Object *obj, Eina_Bool highlight) +{ + API_ENTRY return; + sd->highlight_in_theme = !!highlight; + /* FIXME: if focused, it should switch from one mode to the other */ +} + +EAPI Eina_Bool +elm_widget_highlight_in_theme_get(const Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->highlight_in_theme; +} + +EAPI Eina_Bool +elm_widget_focus_get(const Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->focused; +} + +EAPI Evas_Object * +elm_widget_focused_object_get(const Evas_Object *obj) +{ + const Evas_Object *subobj; + const Eina_List *l; + API_ENTRY return NULL; + + if (!sd->focused) return NULL; + EINA_LIST_FOREACH(sd->subobjs, l, subobj) + { + Evas_Object *fobj = elm_widget_focused_object_get(subobj); + if (fobj) return fobj; + } + return (Evas_Object *)obj; +} + +EAPI Evas_Object * +elm_widget_top_get(const Evas_Object *obj) +{ + API_ENTRY return NULL; + if (sd->parent_obj) return elm_widget_top_get(sd->parent_obj); + return (Evas_Object *)obj; +} + +EAPI Eina_Bool +elm_widget_is(const Evas_Object *obj) +{ + return _elm_widget_is(obj); +} + +EAPI Evas_Object * +elm_widget_parent_widget_get(const Evas_Object *obj) +{ + Evas_Object *parent; + + if (_elm_widget_is(obj)) + { + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return NULL; + parent = sd->parent_obj; + } + else + { + parent = evas_object_data_get(obj, "elm-parent"); + if (!parent) parent = evas_object_smart_parent_get(obj); + } + + while (parent) + { + Evas_Object *elm_parent; + if (_elm_widget_is(parent)) break; + elm_parent = evas_object_data_get(parent, "elm-parent"); + if (elm_parent) parent = elm_parent; + else parent = evas_object_smart_parent_get(parent); + } + return parent; +} + +EAPI void +elm_widget_event_callback_add(Evas_Object *obj, Elm_Event_Cb func, const void *data) +{ + API_ENTRY return; + EINA_SAFETY_ON_NULL_RETURN(func); + Elm_Event_Cb_Data *ecb = ELM_NEW(Elm_Event_Cb_Data); + ecb->func = func; + ecb->data = data; + sd->event_cb = eina_list_append(sd->event_cb, ecb); +} + +EAPI void * +elm_widget_event_callback_del(Evas_Object *obj, Elm_Event_Cb func, const void *data) +{ + API_ENTRY return NULL; + EINA_SAFETY_ON_NULL_RETURN_VAL(func, NULL); + Eina_List *l; + Elm_Event_Cb_Data *ecd; + EINA_LIST_FOREACH(sd->event_cb, l, ecd) + if ((ecd->func == func) && (ecd->data == data)) + { + free(ecd); + sd->event_cb = eina_list_remove_list(sd->event_cb, l); + return (void *)data; + } + return NULL; +} + +EAPI Eina_Bool +elm_widget_event_propagate(Evas_Object *obj, Evas_Callback_Type type, void *event_info, Evas_Event_Flags *event_flags) +{ + API_ENTRY return EINA_FALSE; //TODO reduce. + if (!_elm_widget_is(obj)) return EINA_FALSE; + Evas_Object *parent = obj; + Elm_Event_Cb_Data *ecd; + Eina_List *l, *l_prev; + + while (parent && + (!(event_flags && ((*event_flags) & EVAS_EVENT_FLAG_ON_HOLD)))) + { + sd = evas_object_smart_data_get(parent); + if ((!sd) || (!_elm_widget_is(obj))) + return EINA_FALSE; //Not Elm Widget + + if (sd->event_func && (sd->event_func(parent, obj, type, event_info))) + return EINA_TRUE; + + EINA_LIST_FOREACH_SAFE(sd->event_cb, l, l_prev, ecd) + { + if (ecd->func((void *)ecd->data, parent, obj, type, event_info) || + (event_flags && ((*event_flags) & EVAS_EVENT_FLAG_ON_HOLD))) + return EINA_TRUE; + } + parent = sd->parent_obj; + } + + return EINA_FALSE; +} + +/** + * @internal + * + * Set custom focus chain. + * + * This function i set one new and overwrite any previous custom focus chain + * with the list of objects. The previous list will be deleted and this list + * will be managed. After setted, don't modity it. + * + * @note On focus cycle, only will be evaluated children of this container. + * + * @param obj The container widget + * @param objs Chain of objects to pass focus + * @ingroup Widget + */ +EAPI void +elm_widget_focus_custom_chain_set(Evas_Object *obj, Eina_List *objs) +{ + API_ENTRY return; + if (!sd->focus_next_func) + return; + + elm_widget_focus_custom_chain_unset(obj); + + Eina_List *l; + Evas_Object *o; + + EINA_LIST_FOREACH(objs, l, o) + { + evas_object_event_callback_add(o, EVAS_CALLBACK_DEL, + _elm_object_focus_chain_del_cb, sd); + } + + sd->focus_chain = objs; +} + +/** + * @internal + * + * Get custom focus chain + * + * @param obj The container widget + * @ingroup Widget + */ +EAPI const Eina_List * +elm_widget_focus_custom_chain_get(const Evas_Object *obj) +{ + API_ENTRY return NULL; + return (const Eina_List *) sd->focus_chain; +} + +/** + * @internal + * + * Unset custom focus chain + * + * @param obj The container widget + * @ingroup Widget + */ +EAPI void +elm_widget_focus_custom_chain_unset(Evas_Object *obj) +{ + API_ENTRY return; + Eina_List *l, *l_next; + Evas_Object *o; + + EINA_LIST_FOREACH_SAFE(sd->focus_chain, l, l_next, o) + { + evas_object_event_callback_del_full(o, EVAS_CALLBACK_DEL, + _elm_object_focus_chain_del_cb, sd); + sd->focus_chain = eina_list_remove_list(sd->focus_chain, l); + } +} + +/** + * @internal + * + * Append object to custom focus chain. + * + * @note If relative_child equal to NULL or not in custom chain, the object + * will be added in end. + * + * @note On focus cycle, only will be evaluated children of this container. + * + * @param obj The container widget + * @param child The child to be added in custom chain + * @param relative_child The relative object to position the child + * @ingroup Widget + */ +EAPI void +elm_widget_focus_custom_chain_append(Evas_Object *obj, Evas_Object *child, Evas_Object *relative_child) +{ + API_ENTRY return; + EINA_SAFETY_ON_NULL_RETURN(child); + if (!sd->focus_next_func) + return; + + evas_object_event_callback_del_full(child, EVAS_CALLBACK_DEL, + _elm_object_focus_chain_del_cb, sd); + + if (!relative_child) + { + sd->focus_chain = eina_list_append(sd->focus_chain, child); + return; + } + + sd->focus_chain = eina_list_append_relative(sd->focus_chain, child, relative_child); + return; +} + +/** + * @internal + * + * Prepend object to custom focus chain. + * + * @note If relative_child equal to NULL or not in custom chain, the object + * will be added in begin. + * + * @note On focus cycle, only will be evaluated children of this container. + * + * @param obj The container widget + * @param child The child to be added in custom chain + * @param relative_child The relative object to position the child + * @ingroup Widget + */ +EAPI void +elm_widget_focus_custom_chain_prepend(Evas_Object *obj, Evas_Object *child, Evas_Object *relative_child) +{ + API_ENTRY return; + EINA_SAFETY_ON_NULL_RETURN(child); + if (!sd->focus_next_func) + return; + + evas_object_event_callback_del_full(child, EVAS_CALLBACK_DEL, + _elm_object_focus_chain_del_cb, sd); + + if (!relative_child) + { + sd->focus_chain = eina_list_prepend(sd->focus_chain, child); + return; + } + + sd->focus_chain = eina_list_prepend_relative(sd->focus_chain, child, relative_child); + return; +} + +/** + * @internal + * + * Give focus to next object in object tree. + * + * Give focus to next object in focus chain of one object sub-tree. + * If the last object of chain already have focus, the focus will go to the + * first object of chain. + * + * @param obj The widget root of sub-tree + * @param dir Direction to cycle the focus + * + * @ingroup Widget + */ +EAPI void +elm_widget_focus_cycle(Evas_Object *obj, Elm_Focus_Direction dir) +{ + Evas_Object *target = NULL; + if (!_elm_widget_is(obj)) + return; + elm_widget_focus_next_get(obj, dir, &target); + if (target) + elm_widget_focus_steal(target); +} + +/** + * @internal + * + * Give focus to near object in one direction. + * + * Give focus to near object in direction of one object. + * If none focusable object in given direction, the focus will not change. + * + * @param obj The reference widget + * @param x Horizontal component of direction to focus + * @param y Vertical component of direction to focus + * + * @ingroup Widget + */ +EAPI void +elm_widget_focus_direction_go(Evas_Object *obj __UNUSED__, int x __UNUSED__, int y __UNUSED__) +{ + return; /* TODO */ +} + +/** + * @internal + * + * Get next object in focus chain of object tree. + * + * Get next object in focus chain of one object sub-tree. + * Return the next object by reference. If don't have any candidate to receive + * focus before chain end, the first candidate will be returned. + * + * @param obj The widget root of sub-tree + * @param dir Direction os focus chain + * @param next The next object in focus chain + * @return EINA_TRUE if don't need focus chain restart/loop back + * to use 'next' obj. + * + * @ingroup Widget + */ +EAPI Eina_Bool +elm_widget_focus_next_get(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + if (!next) + return EINA_FALSE; + *next = NULL; + + API_ENTRY return EINA_FALSE; + + /* Ignore if disabled */ + if ((!evas_object_visible_get(obj)) || (elm_widget_disabled_get(obj))) + return EINA_FALSE; + + /* Try use hook */ + if (sd->focus_next_func) + return sd->focus_next_func(obj, dir, next); + + if (!elm_widget_can_focus_get(obj)) + return EINA_FALSE; + + /* Return */ + *next = (Evas_Object *)obj; + return !elm_widget_focus_get(obj); +} + + +/** + * @internal + * + * Get next object in focus chain of object tree in list. + * + * Get next object in focus chain of one object sub-tree ordered by one list. + * Return the next object by reference. If don't have any candidate to receive + * focus before list end, the first candidate will be returned. + * + * @param obj The widget root of sub-tree + * @param dir Direction os focus chain + * @param items list with ordered objects + * @param list_data_get function to get the object from one item of list + * @param next The next object in focus chain + * @return EINA_TRUE if don't need focus chain restart/loop back + * to use 'next' obj. + * + * @ingroup Widget + */ +EAPI Eina_Bool +elm_widget_focus_list_next_get(const Evas_Object *obj, const Eina_List *items, void *(*list_data_get) (const Eina_List *list), Elm_Focus_Direction dir, Evas_Object **next) +{ + Eina_List *(*list_next) (const Eina_List *list); + + if (!next) + return EINA_FALSE; + *next = NULL; + + if (!_elm_widget_is(obj)) + return EINA_FALSE; + + if (!items) + return EINA_FALSE; + + /* Direction */ + if (dir == ELM_FOCUS_PREVIOUS) + { + items = eina_list_last(items); + list_next = eina_list_prev; + } + else if (dir == ELM_FOCUS_NEXT) + list_next = eina_list_next; + else + return EINA_FALSE; + + const Eina_List *l = items; + + /* Recovery last focused sub item */ + if (elm_widget_focus_get(obj)) + for (; l; l = list_next(l)) + { + Evas_Object *cur = list_data_get(l); + if (elm_widget_focus_get(cur)) break; + } + + const Eina_List *start = l; + Evas_Object *to_focus = NULL; + + /* Interate sub items */ + /* Go to end of list */ + for (; l; l = list_next(l)) + { + Evas_Object *tmp = NULL; + Evas_Object *cur = list_data_get(l); + + if (elm_widget_parent_get(cur) != obj) + continue; + + /* Try Focus cycle in subitem */ + if (elm_widget_focus_next_get(cur, dir, &tmp)) + { + *next = tmp; + return EINA_TRUE; + } + else if ((tmp) && (!to_focus)) + to_focus = tmp; + } + + l = items; + + /* Get First possible */ + for (;l != start; l = list_next(l)) + { + Evas_Object *tmp = NULL; + Evas_Object *cur = list_data_get(l); + + if (elm_widget_parent_get(cur) != obj) + continue; + + /* Try Focus cycle in subitem */ + elm_widget_focus_next_get(cur, dir, &tmp); + if (tmp) + { + *next = tmp; + return EINA_FALSE; + } + } + + *next = to_focus; + return EINA_FALSE; +} + +EAPI void +elm_widget_signal_emit(Evas_Object *obj, const char *emission, const char *source) +{ + API_ENTRY return; + if (!sd->signal_func) return; + sd->signal_func(obj, emission, source); +} + +static void +_edje_signal_callback(void *data, Evas_Object *obj __UNUSED__, const char *emission, const char *source) +{ + Edje_Signal_Data *esd = data; + esd->func(esd->data, esd->obj, emission, source); +} + +EAPI void +elm_widget_signal_callback_add(Evas_Object *obj, const char *emission, const char *source, void (*func) (void *data, Evas_Object *o, const char *emission, const char *source), void *data) +{ + Edje_Signal_Data *esd; + API_ENTRY return; + if (!sd->callback_add_func) return; + EINA_SAFETY_ON_NULL_RETURN(func); + + esd = ELM_NEW(Edje_Signal_Data); + if (!esd) return; + + esd->obj = obj; + esd->func = func; + esd->emission = eina_stringshare_add(emission); + esd->source = eina_stringshare_add(source); + esd->data = data; + sd->edje_signals = eina_list_append(sd->edje_signals, esd); + sd->callback_add_func(obj, emission, source, _edje_signal_callback, esd); +} + +EAPI void * +elm_widget_signal_callback_del(Evas_Object *obj, const char *emission, const char *source, void (*func) (void *data, Evas_Object *o, const char *emission, const char *source)) +{ + Edje_Signal_Data *esd; + Eina_List *l; + void *data = NULL; + API_ENTRY return NULL; + if (!sd->callback_del_func) return NULL; + + EINA_LIST_FOREACH(sd->edje_signals, l, esd) + { + if ((esd->func == func) && (!strcmp(esd->emission, emission)) && + (!strcmp(esd->source, source))) + { + sd->edje_signals = eina_list_remove_list(sd->edje_signals, l); + eina_stringshare_del(esd->emission); + eina_stringshare_del(esd->source); + data = esd->data; + free(esd); + break; + } + } + sd->callback_del_func(obj, emission, source, _edje_signal_callback, esd); + return data; +} + +EAPI void +elm_widget_focus_set(Evas_Object *obj, int first) +{ + API_ENTRY return; + if (!sd->focused) + { + focus_order++; + sd->focus_order = focus_order; + sd->focused = EINA_TRUE; + if (sd->on_focus_func) sd->on_focus_func(sd->on_focus_data, obj); + } + if (sd->focus_func) + { + sd->focus_func(obj); + return; + } + else + { + if (first) + { + if ((_is_focusable(sd->resize_obj)) && + (!elm_widget_disabled_get(sd->resize_obj))) + { + elm_widget_focus_set(sd->resize_obj, first); + } + else + { + const Eina_List *l; + Evas_Object *child; + EINA_LIST_FOREACH(sd->subobjs, l, child) + { + if ((_is_focusable(child)) && + (!elm_widget_disabled_get(child))) + { + elm_widget_focus_set(child, first); + break; + } + } + } + } + else + { + const Eina_List *l; + Evas_Object *child; + EINA_LIST_REVERSE_FOREACH(sd->subobjs, l, child) + { + if ((_is_focusable(child)) && + (!elm_widget_disabled_get(child))) + { + elm_widget_focus_set(child, first); + break; + } + } + if (!l) + { + if ((_is_focusable(sd->resize_obj)) && + (!elm_widget_disabled_get(sd->resize_obj))) + { + elm_widget_focus_set(sd->resize_obj, first); + } + } + } + } +} + +EAPI Evas_Object * +elm_widget_parent_get(const Evas_Object *obj) +{ + API_ENTRY return NULL; + return sd->parent_obj; +} + +EAPI void +elm_widget_focused_object_clear(Evas_Object *obj) +{ + API_ENTRY return; + if (!sd->focused) return; + if (elm_widget_focus_get(sd->resize_obj)) + elm_widget_focused_object_clear(sd->resize_obj); + else + { + const Eina_List *l; + Evas_Object *child; + EINA_LIST_FOREACH(sd->subobjs, l, child) + { + if (elm_widget_focus_get(child)) + { + elm_widget_focused_object_clear(child); + break; + } + } + } + sd->focused = EINA_FALSE; + if (sd->on_focus_func) sd->on_focus_func(sd->on_focus_data, obj); + if (sd->focus_func) sd->focus_func(obj); +} + +EAPI void +elm_widget_focus_steal(Evas_Object *obj) +{ + Evas_Object *parent, *o; + API_ENTRY return; + + if (sd->focused) return; + if (sd->disabled) return; + parent = obj; + for (;;) + { + o = elm_widget_parent_get(parent); + if (!o) break; + sd = evas_object_smart_data_get(o); + if (sd->focused) break; + parent = o; + } + if (!elm_widget_parent_get(parent)) + elm_widget_focused_object_clear(parent); + else + { + parent = elm_widget_parent_get(parent); + sd = evas_object_smart_data_get(parent); + if (elm_widget_focus_get(sd->resize_obj)) + { + elm_widget_focused_object_clear(sd->resize_obj); + } + else + { + const Eina_List *l; + Evas_Object *child; + EINA_LIST_FOREACH(sd->subobjs, l, child) + { + if (elm_widget_focus_get(child)) + { + elm_widget_focused_object_clear(child); + break; + } + } + } + } + _parent_focus(obj); + return; +} + +EAPI void +elm_widget_activate(Evas_Object *obj) +{ + API_ENTRY return; + elm_widget_change(obj); + if (sd->activate_func) sd->activate_func(obj); +} + +EAPI void +elm_widget_change(Evas_Object *obj) +{ + API_ENTRY return; + elm_widget_change(elm_widget_parent_get(obj)); + if (sd->on_change_func) sd->on_change_func(sd->on_change_data, obj); +} + +EAPI void +elm_widget_disabled_set(Evas_Object *obj, int disabled) +{ + API_ENTRY return; + + if (sd->disabled == disabled) return; + sd->disabled = disabled; + if (sd->focused) + { + Evas_Object *o, *parent; + + parent = obj; + for (;;) + { + o = elm_widget_parent_get(parent); + if (!o) break; + parent = o; + } + if (elm_widget_focus_get(obj)) + elm_widget_focus_cycle(parent, ELM_FOCUS_NEXT); + } + if (sd->disable_func) sd->disable_func(obj); +} + +EAPI int +elm_widget_disabled_get(const Evas_Object *obj) +{ + API_ENTRY return 0; + return sd->disabled; +} + +EAPI void +elm_widget_show_region_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h) +{ + Evas_Object *parent_obj, *child_obj; + Evas_Coord px, py, cx, cy; + + API_ENTRY return; + if ((x == sd->rx) && (y == sd->ry) && (w == sd->rw) && (h == sd->rh)) return; + sd->rx = x; + sd->ry = y; + sd->rw = w; + sd->rh = h; + if (sd->on_show_region_func) + sd->on_show_region_func(sd->on_show_region_data, obj); + + do + { + parent_obj = sd->parent_obj; + child_obj = sd->obj; + sd = evas_object_smart_data_get(parent_obj); + + if ((!parent_obj) || (!sd) || (!_elm_widget_is(parent_obj))) break; + + evas_object_geometry_get(parent_obj, &px, &py, NULL, NULL); + evas_object_geometry_get(child_obj, &cx, &cy, NULL, NULL); + + x += (cx - px); + y += (cy - py); + sd->rx = x; + sd->ry = y; + sd->rw = w; + sd->rh = h; + + if (sd->on_show_region_func) + { + sd->on_show_region_func(sd->on_show_region_data, parent_obj); + } + } + while (parent_obj); +} + +EAPI void +elm_widget_show_region_get(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h) +{ + API_ENTRY return; + if (x) *x = sd->rx; + if (y) *y = sd->ry; + if (w) *w = sd->rw; + if (h) *h = sd->rh; +} + +/** + * @internal + * + * Get the focus region of the given widget. + * + * The focus region is the area of a widget that should brought into the + * visible area when the widget is focused. Mostly used to show the part of + * an entry where the cursor is, for example. The area returned is relative + * to the object @p obj. + * If the @p obj doesn't have the proper on_focus_region_hook set, this + * function will return the full size of the object. + * + * @param obj The widget object + * @param x Where to store the x coordinate of the area + * @param y Where to store the y coordinate of the area + * @param w Where to store the width of the area + * @param h Where to store the height of the area + * + * @ingroup Widget + */ +EAPI void +elm_widget_focus_region_get(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h) +{ + Smart_Data *sd; + + if (!obj) return; + + sd = evas_object_smart_data_get(obj); + if (!sd || !_elm_widget_is(obj) || !sd->on_focus_region_func) + { + evas_object_geometry_get(obj, NULL, NULL, w, h); + if (x) *x = 0; + if (y) *y = 0; + return; + } + sd->on_focus_region_func(obj, x, y, w, h); +} + +EAPI void +elm_widget_scroll_hold_push(Evas_Object *obj) +{ + API_ENTRY return; + sd->scroll_hold++; + if (sd->scroll_hold == 1) + evas_object_smart_callback_call(obj, "scroll-hold-on", obj); + if (sd->parent_obj) elm_widget_scroll_hold_push(sd->parent_obj); + // FIXME: on delete/reparent hold pop +} + +EAPI void +elm_widget_scroll_hold_pop(Evas_Object *obj) +{ + API_ENTRY return; + sd->scroll_hold--; + if (sd->scroll_hold < 0) sd->scroll_hold = 0; + if (!sd->scroll_hold) + evas_object_smart_callback_call(obj, "scroll-hold-off", obj); + if (sd->parent_obj) elm_widget_scroll_hold_pop(sd->parent_obj); +} + +EAPI int +elm_widget_scroll_hold_get(const Evas_Object *obj) +{ + API_ENTRY return 0; + return sd->scroll_hold; +} + +EAPI void +elm_widget_scroll_freeze_push(Evas_Object *obj) +{ + API_ENTRY return; + sd->scroll_freeze++; + if (sd->scroll_freeze == 1) + evas_object_smart_callback_call(obj, "scroll-freeze-on", obj); + if (sd->parent_obj) elm_widget_scroll_freeze_push(sd->parent_obj); + // FIXME: on delete/reparent freeze pop +} + +EAPI void +elm_widget_scroll_freeze_pop(Evas_Object *obj) +{ + API_ENTRY return; + sd->scroll_freeze--; + if (sd->scroll_freeze < 0) sd->scroll_freeze = 0; + if (!sd->scroll_freeze) + evas_object_smart_callback_call(obj, "scroll-freeze-off", obj); + if (sd->parent_obj) elm_widget_scroll_freeze_pop(sd->parent_obj); +} + +EAPI int +elm_widget_scroll_freeze_get(const Evas_Object *obj) +{ + API_ENTRY return 0; + return sd->scroll_freeze; +} + +EAPI void +elm_widget_scale_set(Evas_Object *obj, double scale) +{ + API_ENTRY return; + if (scale <= 0.0) scale = 0.0; + if (sd->scale != scale) + { + sd->scale = scale; + elm_widget_theme(obj); + } +} + +EAPI double +elm_widget_scale_get(const Evas_Object *obj) +{ + API_ENTRY return 1.0; + // FIXME: save walking up the tree by storing/caching parent scale + if (sd->scale == 0.0) + { + if (sd->parent_obj) + return elm_widget_scale_get(sd->parent_obj); + else + return 1.0; + } + return sd->scale; +} + +EAPI void +elm_widget_theme_set(Evas_Object *obj, Elm_Theme *th) +{ + API_ENTRY return; + if (sd->theme != th) + { + if (sd->theme) elm_theme_free(sd->theme); + sd->theme = th; + if (th) th->ref++; + elm_widget_theme(obj); + } +} + +EAPI Elm_Theme * +elm_widget_theme_get(const Evas_Object *obj) +{ + API_ENTRY return NULL; + if (!sd->theme) + { + if (sd->parent_obj) + return elm_widget_theme_get(sd->parent_obj); + else + return NULL; + } + return sd->theme; +} + +EAPI void +elm_widget_style_set(Evas_Object *obj, const char *style) +{ + API_ENTRY return; + + if (eina_stringshare_replace(&sd->style, style)) + elm_widget_theme(obj); +} + +EAPI const char * +elm_widget_style_get(const Evas_Object *obj) +{ + API_ENTRY return NULL; + if (sd->style) return sd->style; + return "default"; +} + +EAPI void +elm_widget_type_set(Evas_Object *obj, const char *type) +{ + API_ENTRY return; + eina_stringshare_replace(&sd->type, type); +} + +EAPI const char * +elm_widget_type_get(const Evas_Object *obj) +{ + API_ENTRY return NULL; + if (sd->type) return sd->type; + return ""; +} + +EAPI void +elm_widget_tooltip_add(Evas_Object *obj, Elm_Tooltip *tt) +{ + API_ENTRY return; + sd->tooltips = eina_list_append(sd->tooltips, tt); +} + +EAPI void +elm_widget_tooltip_del(Evas_Object *obj, Elm_Tooltip *tt) +{ + API_ENTRY return; + sd->tooltips = eina_list_remove(sd->tooltips, tt); +} + +EAPI void +elm_widget_cursor_add(Evas_Object *obj, Elm_Cursor *cur) +{ + API_ENTRY return; + sd->cursors = eina_list_append(sd->cursors, cur); +} + +EAPI void +elm_widget_cursor_del(Evas_Object *obj, Elm_Cursor *cur) +{ + API_ENTRY return; + sd->cursors = eina_list_remove(sd->cursors, cur); +} + +EAPI void +elm_widget_drag_lock_x_set(Evas_Object *obj, Eina_Bool lock) +{ + API_ENTRY return; + if (sd->drag_x_locked == lock) return; + sd->drag_x_locked = lock; + if (sd->drag_x_locked) _propagate_x_drag_lock(obj, 1); + else _propagate_x_drag_lock(obj, -1); +} + +EAPI void +elm_widget_drag_lock_y_set(Evas_Object *obj, Eina_Bool lock) +{ + API_ENTRY return; + if (sd->drag_y_locked == lock) return; + sd->drag_y_locked = lock; + if (sd->drag_y_locked) _propagate_y_drag_lock(obj, 1); + else _propagate_y_drag_lock(obj, -1); +} + +EAPI Eina_Bool +elm_widget_drag_lock_x_get(const Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->drag_x_locked; +} + +EAPI Eina_Bool +elm_widget_drag_lock_y_get(const Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->drag_y_locked; +} + +EAPI int +elm_widget_drag_child_locked_x_get(const Evas_Object *obj) +{ + API_ENTRY return 0; + return sd->child_drag_x_locked; +} + +EAPI int +elm_widget_drag_child_locked_y_get(const Evas_Object *obj) +{ + API_ENTRY return 0; + return sd->child_drag_y_locked; +} + +EAPI Eina_Bool +elm_widget_theme_object_set(Evas_Object *obj, Evas_Object *edj, const char *wname, const char *welement, const char *wstyle) +{ + API_ENTRY return EINA_FALSE; + return _elm_theme_object_set(obj, edj, wname, welement, wstyle); +} + +EAPI Eina_Bool +elm_widget_type_check(const Evas_Object *obj, const char *type) +{ + const char *provided, *expected = "(unknown)"; + static int abort_on_warn = -1; + provided = elm_widget_type_get(obj); + if (EINA_LIKELY(provided == type)) return EINA_TRUE; + if (type) expected = type; + if ((!provided) || (!provided[0])) + { + provided = evas_object_type_get(obj); + if ((!provided) || (!provided[0])) + provided = "(unknown)"; + } + ERR("Passing Object: %p, of type: '%s' when expecting type: '%s'", obj, provided, expected); + if (abort_on_warn == -1) + { + if (getenv("ELM_ERROR_ABORT")) abort_on_warn = 1; + else abort_on_warn = 0; + } + if (abort_on_warn == 1) abort(); + return EINA_FALSE; +} + +/** + * @internal + * + * Split string in words + * + * @param str Source string + * @return List of const words + * + * @see elm_widget_stringlist_free() + * @ingroup Widget + */ +EAPI Eina_List * +elm_widget_stringlist_get(const char *str) +{ + Eina_List *list = NULL; + const char *s, *b; + if (!str) return NULL; + for (b = s = str; 1; s++) + { + if ((*s == ' ') || (!*s)) + { + char *t = malloc(s - b + 1); + if (t) + { + strncpy(t, b, s - b); + t[s - b] = 0; + list = eina_list_append(list, eina_stringshare_add(t)); + free(t); + } + b = s + 1; + } + if (!*s) break; + } + return list; +} + +EAPI void +elm_widget_stringlist_free(Eina_List *list) +{ + const char *s; + EINA_LIST_FREE(list, s) eina_stringshare_del(s); +} + +/** + * @internal + * + * Allocate a new Elm_Widget_Item-derived structure. + * + * The goal of this structure is to provide common ground for actions + * that a widget item have, such as the owner widget, callback to + * notify deletion, data pointer and maybe more. + * + * @param widget the owner widget that holds this item, must be an elm_widget! + * @param alloc_size any number greater than sizeof(Elm_Widget_Item) that will + * be used to allocate memory. + * + * @return allocated memory that is already zeroed out, or NULL on errors. + * + * @see elm_widget_item_new() convenience macro. + * @see elm_widget_item_del() to release memory. + * @ingroup Widget + */ +EAPI Elm_Widget_Item * +_elm_widget_item_new(Evas_Object *widget, size_t alloc_size) +{ + if (!_elm_widget_is(widget)) + return NULL; + + Elm_Widget_Item *item; + + EINA_SAFETY_ON_TRUE_RETURN_VAL(alloc_size < sizeof(Elm_Widget_Item), NULL); + EINA_SAFETY_ON_TRUE_RETURN_VAL(!_elm_widget_is(widget), NULL); + + item = calloc(1, alloc_size); + EINA_SAFETY_ON_NULL_RETURN_VAL(item, NULL); + + EINA_MAGIC_SET(item, ELM_WIDGET_ITEM_MAGIC); + item->widget = widget; + return item; +} + +/** + * @internal + * + * Releases widget item memory, calling back del_cb() if it exists. + * + * If there is a Elm_Widget_Item::del_cb, then it will be called prior + * to memory release. Note that elm_widget_item_pre_notify_del() calls + * this function and then unset it, thus being useful for 2 step + * cleanup whenever the del_cb may use any of the data that must be + * deleted from item. + * + * The Elm_Widget_Item::view will be deleted (evas_object_del()) if it + * is presented! + * + * @param item a valid #Elm_Widget_Item to be deleted. + * @see elm_widget_item_del() convenience macro. + * @ingroup Widget + */ +EAPI void +_elm_widget_item_del(Elm_Widget_Item *item) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + + if (item->del_cb) + item->del_cb((void *)item->data, item->widget, item); + + if (item->view) + evas_object_del(item->view); + + EINA_MAGIC_SET(item, EINA_MAGIC_NONE); + free(item); +} + +/** + * @internal + * + * Notify object will be deleted without actually deleting it. + * + * This function will callback Elm_Widget_Item::del_cb if it is set + * and then unset it so it is not called twice (ie: from + * elm_widget_item_del()). + * + * @param item a valid #Elm_Widget_Item to be notified + * @see elm_widget_item_pre_notify_del() convenience macro. + * @ingroup Widget + */ +EAPI void +_elm_widget_item_pre_notify_del(Elm_Widget_Item *item) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + if (!item->del_cb) return; + item->del_cb((void *)item->data, item->widget, item); + item->del_cb = NULL; +} + +/** + * @internal + * + * Set the function to notify when item is being deleted. + * + * This function will complain if there was a callback set already, + * however it will set the new one. + * + * The callback will be called from elm_widget_item_pre_notify_del() + * or elm_widget_item_del() will be called with: + * - data: the Elm_Widget_Item::data value. + * - obj: the Elm_Widget_Item::widget evas object. + * - event_info: the item being deleted. + * + * @param item a valid #Elm_Widget_Item to be notified + * @see elm_widget_item_del_cb_set() convenience macro. + * @ingroup Widget + */ +EAPI void +_elm_widget_item_del_cb_set(Elm_Widget_Item *item, Evas_Smart_Cb del_cb) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + + if ((item->del_cb) && (item->del_cb != del_cb)) + WRN("You're replacing a previously set del_cb %p of item %p with %p", + item->del_cb, item, del_cb); + + item->del_cb = del_cb; +} + +/** + * @internal + * + * Set user-data in this item. + * + * User data may be used to identify this item or just store any + * application data. It is automatically given as the first parameter + * of the deletion notify callback. + * + * @param item a valid #Elm_Widget_Item to store data in. + * @param data user data to store. + * @see elm_widget_item_del_cb_set() convenience macro. + * @ingroup Widget + */ +EAPI void +_elm_widget_item_data_set(Elm_Widget_Item *item, const void *data) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + if ((item->data) && (item->data != data)) + DBG("Replacing item %p data %p with %p", item, item->data, data); + item->data = data; +} + +/** + * @internal + * + * Retrieves user-data of this item. + * + * @param item a valid #Elm_Widget_Item to get data from. + * @see elm_widget_item_data_set() + * @ingroup Widget + */ +EAPI void * +_elm_widget_item_data_get(const Elm_Widget_Item *item) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item, NULL); + return (void *)item->data; +} + +typedef struct _Elm_Widget_Item_Tooltip Elm_Widget_Item_Tooltip; + +struct _Elm_Widget_Item_Tooltip +{ + Elm_Widget_Item *item; + Elm_Tooltip_Item_Content_Cb func; + Evas_Smart_Cb del_cb; + const void *data; +}; + +static Evas_Object * +_elm_widget_item_tooltip_label_create(void *data, Evas_Object *obj, void *item __UNUSED__) +{ + Evas_Object *label = elm_label_add(obj); + if (!label) + return NULL; + elm_object_style_set(label, "tooltip"); + elm_label_label_set(label, data); + return label; +} + +static void +_elm_widget_item_tooltip_label_del_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + eina_stringshare_del(data); +} + +/** + * @internal + * + * Set the text to be shown in the widget item. + * + * @param item Target item + * @param text The text to set in the content + * + * Setup the text as tooltip to object. The item can have only one tooltip, + * so any previous tooltip data is removed. + * + * @ingroup Widget + */ +EAPI void +_elm_widget_item_tooltip_text_set(Elm_Widget_Item *item, const char *text) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + EINA_SAFETY_ON_NULL_RETURN(text); + + text = eina_stringshare_add(text); + _elm_widget_item_tooltip_content_cb_set + (item, _elm_widget_item_tooltip_label_create, text, + _elm_widget_item_tooltip_label_del_cb); +} + +static Evas_Object * +_elm_widget_item_tooltip_create(void *data, Evas_Object *obj) +{ + Elm_Widget_Item_Tooltip *wit = data; + return wit->func((void *)wit->data, obj, wit->item); +} + +static void +_elm_widget_item_tooltip_del_cb(void *data, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Widget_Item_Tooltip *wit = data; + if (wit->del_cb) wit->del_cb((void *)wit->data, obj, wit->item); + free(wit); +} + +/** + * @internal + * + * Set the content to be shown in the tooltip item + * + * Setup the tooltip to item. The item can have only one tooltip, + * so any previous tooltip data is removed. @p func(with @p data) will + * be called every time that need show the tooltip and it should + * return a valid Evas_Object. This object is then managed fully by + * tooltip system and is deleted when the tooltip is gone. + * + * @param item the widget item being attached a tooltip. + * @param func the function used to create the tooltip contents. + * @param data what to provide to @a func as callback data/context. + * @param del_cb called when data is not needed anymore, either when + * another callback replaces @func, the tooltip is unset with + * elm_widget_item_tooltip_unset() or the owner @a item + * dies. This callback receives as the first parameter the + * given @a data, and @c event_info is the item. + * + * @ingroup Widget + */ +EAPI void +_elm_widget_item_tooltip_content_cb_set(Elm_Widget_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) +{ + Elm_Widget_Item_Tooltip *wit; + + ELM_WIDGET_ITEM_CHECK_OR_GOTO(item, error_noitem); + + if (!func) + { + _elm_widget_item_tooltip_unset(item); + return; + } + + wit = ELM_NEW(Elm_Widget_Item_Tooltip); + if (!wit) goto error; + wit->item = item; + wit->func = func; + wit->data = data; + wit->del_cb = del_cb; + + elm_object_sub_tooltip_content_cb_set + (item->view, item->widget, _elm_widget_item_tooltip_create, wit, + _elm_widget_item_tooltip_del_cb); + + return; + + error_noitem: + if (del_cb) del_cb((void *)data, NULL, item); + return; + error: + if (del_cb) del_cb((void *)data, item->widget, item); +} + +/** + * @internal + * + * Unset tooltip from item + * + * @param item widget item to remove previously set tooltip. + * + * Remove tooltip from item. The callback provided as del_cb to + * elm_widget_item_tooltip_content_cb_set() will be called to notify + * it is not used anymore. + * + * @see elm_widget_item_tooltip_content_cb_set() + * + * @ingroup Widget + */ +EAPI void +_elm_widget_item_tooltip_unset(Elm_Widget_Item *item) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + elm_object_tooltip_unset(item->view); +} + +/** + * @internal + * + * Sets a different style for this item tooltip. + * + * @note before you set a style you should define a tooltip with + * elm_widget_item_tooltip_content_cb_set() or + * elm_widget_item_tooltip_text_set() + * + * @param item widget item with tooltip already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Widget + */ +EAPI void +_elm_widget_item_tooltip_style_set(Elm_Widget_Item *item, const char *style) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + elm_object_tooltip_style_set(item->view, style); +} + +/** + * @internal + * + * Get the style for this item tooltip. + * + * @param item widget item with tooltip already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a tooltip set, then NULL is returned. + * + * @ingroup Widget + */ +EAPI const char * +_elm_widget_item_tooltip_style_get(const Elm_Widget_Item *item) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item, NULL); + return elm_object_tooltip_style_get(item->view); +} + +EAPI void +_elm_widget_item_cursor_set(Elm_Widget_Item *item, const char *cursor) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + elm_object_sub_cursor_set(item->view, item->widget, cursor); +} + +EAPI const char * +_elm_widget_item_cursor_get(const Elm_Widget_Item *item) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item, NULL); + return elm_object_cursor_get(item->view); +} + +EAPI void +_elm_widget_item_cursor_unset(Elm_Widget_Item *item) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + elm_object_cursor_unset(item->view); +} + +/** + * @internal + * + * Sets a different style for this item cursor. + * + * @note before you set a style you should define a cursor with + * elm_widget_item_cursor_set() + * + * @param item widget item with cursor already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Widget + */ +EAPI void +_elm_widget_item_cursor_style_set(Elm_Widget_Item *item, const char *style) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + elm_object_cursor_style_set(item->view, style); +} + +/** + * @internal + * + * Get the style for this item cursor. + * + * @param item widget item with cursor already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a cursor set, then NULL is returned. + * + * @ingroup Widget + */ +EAPI const char * +_elm_widget_item_cursor_style_get(const Elm_Widget_Item *item) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item, NULL); + return elm_object_cursor_style_get(item->view); +} + +/** + * @internal + * + * Set if the cursor set should be searched on the theme or should use + * the provided by the engine, only. + * + * @note before you set if should look on theme you should define a cursor + * with elm_object_cursor_set(). By default it will only look for cursors + * provided by the engine. + * + * @param item widget item with cursor already set. + * @param engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. + * + * @ingroup Widget + */ +EAPI void +_elm_widget_item_cursor_engine_only_set(Elm_Widget_Item *item, Eina_Bool engine_only) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item); + elm_object_cursor_engine_only_set(item->view, engine_only); +} + +/** + * @internal + * + * Get the cursor engine only usage for this item cursor. + * + * @param item widget item with cursor already set. + * @return engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. If + * the object does not have a cursor set, then EINA_FALSE is returned. + * + * @ingroup Widget + */ +EAPI Eina_Bool +_elm_widget_item_cursor_engine_only_get(const Elm_Widget_Item *item) +{ + ELM_WIDGET_ITEM_CHECK_OR_RETURN(item, EINA_FALSE); + return elm_object_cursor_engine_only_get(item->view); +} + +// smart object funcs +static void +_smart_reconfigure(Smart_Data *sd) +{ + if (sd->resize_obj) + { + evas_object_move(sd->resize_obj, sd->x, sd->y); + evas_object_resize(sd->resize_obj, sd->w, sd->h); + } + if (sd->hover_obj) + { + evas_object_move(sd->hover_obj, sd->x, sd->y); + evas_object_resize(sd->hover_obj, sd->w, sd->h); + } +} + +static void +_smart_add(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = calloc(1, sizeof(Smart_Data)); + if (!sd) return; + sd->obj = obj; + sd->x = sd->y = sd->w = sd->h = 0; + sd->can_focus = 1; + evas_object_smart_data_set(obj, sd); +} + +static Evas_Object * +_newest_focus_order_get(Evas_Object *obj, unsigned int *newest_focus_order, Eina_Bool can_focus_only) +{ + const Eina_List *l; + Evas_Object *child, *ret, *best; + + API_ENTRY return NULL; + if (!evas_object_visible_get(obj)) return NULL; + best = NULL; + if (*newest_focus_order < sd->focus_order) + { + *newest_focus_order = sd->focus_order; + best = obj; + } + EINA_LIST_FOREACH(sd->subobjs, l, child) + { + ret = _newest_focus_order_get(child, newest_focus_order, can_focus_only); + if (!ret) continue; + best = ret; + } + if ((can_focus_only) && (!elm_widget_can_focus_get(best))) return NULL; + return best; +} + +static void +_if_focused_revert(Evas_Object *obj, Eina_Bool can_focus_only) +{ + Evas_Object *top; + Evas_Object *newest = NULL; + unsigned int newest_focus_order = 0; + + INTERNAL_ENTRY; + + if (!sd->focused) return; + if (!sd->parent_obj) return; + + top = elm_widget_top_get(sd->parent_obj); + if (top) + { + newest = _newest_focus_order_get(top, &newest_focus_order, can_focus_only); + if (newest) + { + elm_object_unfocus(newest); + elm_object_focus(newest); + } + } +} + +static void +_smart_del(Evas_Object *obj) +{ + Evas_Object *sobj; + Edje_Signal_Data *esd; + + INTERNAL_ENTRY; + + if (sd->del_pre_func) sd->del_pre_func(obj); + if (sd->resize_obj) + { + sobj = sd->resize_obj; + sd->resize_obj = NULL; + evas_object_event_callback_del_full(sobj, EVAS_CALLBACK_DEL, _sub_obj_del, sd); + evas_object_smart_callback_call(sd->obj, "sub-object-del", sobj); + evas_object_del(sobj); + } + if (sd->hover_obj) + { + sobj = sd->hover_obj; + sd->hover_obj = NULL; + evas_object_event_callback_del_full(sobj, EVAS_CALLBACK_DEL, _sub_obj_del, sd); + evas_object_smart_callback_call(sd->obj, "sub-object-del", sobj); + evas_object_del(sobj); + } + EINA_LIST_FREE(sd->subobjs, sobj) + { + evas_object_event_callback_del_full(sobj, EVAS_CALLBACK_DEL, _sub_obj_del, sd); + evas_object_smart_callback_call(sd->obj, "sub-object-del", sobj); + evas_object_del(sobj); + } + eina_list_free(sd->tooltips); /* should be empty anyway */ + eina_list_free(sd->cursors); /* should be empty anyway */ + EINA_LIST_FREE(sd->edje_signals, esd) + { + eina_stringshare_del(esd->emission); + eina_stringshare_del(esd->source); + free(esd); + } + eina_list_free(sd->event_cb); /* should be empty anyway */ + if (sd->del_func) sd->del_func(obj); + if (sd->style) eina_stringshare_del(sd->style); + if (sd->type) eina_stringshare_del(sd->type); + if (sd->theme) elm_theme_free(sd->theme); + _if_focused_revert(obj, EINA_TRUE); + free(sd); +} + +static void +_smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + INTERNAL_ENTRY; + sd->x = x; + sd->y = y; + _smart_reconfigure(sd); +} + +static void +_smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h) +{ + INTERNAL_ENTRY; + sd->w = w; + sd->h = h; + _smart_reconfigure(sd); +} + +static void +_smart_show(Evas_Object *obj) +{ + Eina_List *list; + Evas_Object *o; + INTERNAL_ENTRY; + if ((list = evas_object_smart_members_get(obj))) + { + EINA_LIST_FREE(list, o) + { + if (evas_object_data_get(o, "_elm_leaveme")) continue; + evas_object_show(o); + } + } +} + +static void +_smart_hide(Evas_Object *obj) +{ + Eina_List *list; + Evas_Object *o; + INTERNAL_ENTRY; + list = evas_object_smart_members_get(obj); + EINA_LIST_FREE(list, o) + { + if (evas_object_data_get(o, "_elm_leaveme")) continue; + evas_object_hide(o); + } + _if_focused_revert(obj, EINA_TRUE); +} + +static void +_smart_color_set(Evas_Object *obj, int r, int g, int b, int a) +{ + Eina_List *list; + Evas_Object *o; + INTERNAL_ENTRY; + if ((list = evas_object_smart_members_get(obj))) + { + EINA_LIST_FREE(list, o) + { + if (evas_object_data_get(o, "_elm_leaveme")) continue; + evas_object_color_set(o, r, g, b, a); + } + } +} + +static void +_smart_clip_set(Evas_Object *obj, Evas_Object *clip) +{ + Eina_List *list; + Evas_Object *o; + INTERNAL_ENTRY; + if ((list = evas_object_smart_members_get(obj))) + { + EINA_LIST_FREE(list, o) + { + if (evas_object_data_get(o, "_elm_leaveme")) continue; + evas_object_clip_set(o, clip); + } + } +} + +static void +_smart_clip_unset(Evas_Object *obj) +{ + Eina_List *list; + Evas_Object *o; + INTERNAL_ENTRY; + if ((list = evas_object_smart_members_get(obj))) + { + EINA_LIST_FREE(list, o) + { + if (evas_object_data_get(o, "_elm_leaveme")) continue; + evas_object_clip_unset(o); + } + } +} + +static void +_smart_calculate(Evas_Object *obj) +{ + INTERNAL_ENTRY; + if (sd->changed_func) sd->changed_func(obj); +} + +/* never need to touch this */ +static void +_smart_init(void) +{ + if (_e_smart) return; + { + static const Evas_Smart_Class sc = + { + SMART_NAME, + EVAS_SMART_CLASS_VERSION, + _smart_add, + _smart_del, + _smart_move, + _smart_resize, + _smart_show, + _smart_hide, + _smart_color_set, + _smart_clip_set, + _smart_clip_unset, + _smart_calculate, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL + }; + _e_smart = evas_smart_class_new(&sc); + } +} + +/* happy debug functions */ +#ifdef ELM_DEBUG +static void +_sub_obj_tree_dump(const Evas_Object *o, int lvl) +{ + int i; + + for (i = 0; i < lvl*3; i++) + putchar(' '); + + if (_elm_widget_is(o)) + { + Eina_List *l; + Smart_Data *sd = evas_object_smart_data_get(o); + printf("+ %s(%p)\n", sd->type, o); + if (sd->resize_obj) + _sub_obj_tree_dump(sd->resize_obj, lvl + 1); + EINA_LIST_FOREACH(sd->subobjs, l, o) + { + if (o != sd->resize_obj) + _sub_obj_tree_dump(o, lvl + 1); + } + } + else + printf("+ %s(%p)\n", evas_object_type_get(o), o); +} + +static void +_sub_obj_tree_dot_dump(const Evas_Object *obj, FILE *output) +{ + if (!_elm_widget_is(obj)) + return; + + Smart_Data *sd = evas_object_smart_data_get(obj); + + Eina_Bool visible = evas_object_visible_get(obj); + Eina_Bool disabled = elm_widget_disabled_get(obj); + Eina_Bool focused = elm_widget_focus_get(obj); + Eina_Bool can_focus = elm_widget_can_focus_get(obj); + + if (sd->parent_obj) + { + fprintf(output, "\"%p\" -- \"%p\" [ color=black", sd->parent_obj, obj); + + if (focused) + fprintf(output, ", style=bold"); + + if (!visible) + fprintf(output, ", color=gray28"); + + fprintf(output, " ];\n"); + } + + fprintf(output, "\"%p\" [ label = \"{%p|%s|%s|visible: %d|" + "disabled: %d|focused: %d/%d|focus order:%d}\"", obj, obj, sd->type, + evas_object_name_get(obj), visible, disabled, focused, can_focus, + sd->focus_order); + + if (focused) + fprintf(output, ", style=bold"); + + if (!visible) + fprintf(output, ", fontcolor=gray28"); + + if ((disabled) || (!visible)) + fprintf(output, ", color=gray"); + + + fprintf(output, " ];\n"); + + Eina_List *l; + Evas_Object *o; + EINA_LIST_FOREACH(sd->subobjs, l, o) + _sub_obj_tree_dot_dump(o, output); +} +#endif + +EAPI void +elm_widget_tree_dump(const Evas_Object *top) +{ +#ifdef ELM_DEBUG + _sub_obj_tree_dump(top, 0); +#else + return; + (void)top; +#endif +} + +EAPI void +elm_widget_tree_dot_dump(const Evas_Object *top, FILE *output) +{ +#ifdef ELM_DEBUG + if (!_elm_widget_is(top)) + return; + fprintf(output, "graph "" { node [shape=record];\n"); + _sub_obj_tree_dot_dump(top, output); + fprintf(output, "}\n"); +#else + return; + (void)top; + (void)output; +#endif +} diff --git a/src/lib/elm_widget.h b/src/lib/elm_widget.h new file mode 100644 index 0000000..bb25156 --- /dev/null +++ b/src/lib/elm_widget.h @@ -0,0 +1,545 @@ +#ifndef ELM_WIDGET_H +#define ELM_WIDGET_H + +/* DO NOT USE THIS HEADER UNLESS YOU ARE PREPARED FOR BREAKING OF YOUR + * CODE. THIS IS ELEMENTARY'S INTERNAL WIDGET API (for now) AND IS NOT + * FINAL. CALL elm_widget_api_check(ELM_INTERNAL_API_VERSION) TO CHECK IT + * AT RUNTIME + * + * How to make your own widget? like this: + * + * #include + * #include "elm_priv.h" + * + * typedef struct _Widget_Data Widget_Data; + * + * struct _Widget_Data + * { + * Evas_Object *sub; + * // add any other widget data here too + * }; + * + * static const char *widtype = NULL; + * static void _del_hook(Evas_Object *obj); + * static void _theme_hook(Evas_Object *obj); + * static void _disable_hook(Evas_Object *obj); + * static void _sizing_eval(Evas_Object *obj); + * static void _on_focus_hook(void *data, Evas_Object *obj); + * + * static const char SIG_CLICKED[] = "clicked"; + * static const Evas_Smart_Cb_Description _signals[] = { + * {SIG_CLICKED, ""}, + * {NULL, NULL} + * }; + * + * static void + * _del_hook(Evas_Object *obj) + * { + * Widget_Data *wd = elm_widget_data_get(obj); + * if (!wd) return; + * // delete hook - on delete of object delete object struct etc. + * free(wd); + * } + * + * static void + * _on_focus_hook(void *data __UNUSED__, Evas_Object *obj) + * { + * Widget_Data *wd = elm_widget_data_get(obj); + * if (!wd) return; + * // handle focus going in and out - optional, but if you want to, set + * // this hook and handle it (eg emit a signal to an edje obj) + * if (elm_widget_focus_get(obj)) + * { + * edje_object_signal_emit(wd->sub, "elm,action,focus", "elm"); + * evas_object_focus_set(wd->sub, EINA_TRUE); + * } + * else + * { + * edje_object_signal_emit(wd->sub, "elm,action,unfocus", "elm"); + * evas_object_focus_set(wd->sub, EINA_FALSE); + * } + * } + * + * static void + * _theme_hook(Evas_Object *obj) + * { + * Widget_Data *wd = elm_widget_data_get(obj); + * if (!wd) return; + * // handle change in theme/scale etc. + * elm_widget_theme_object_set(obj, wd->sub, "mywidget", "base", + * elm_widget_style_get(obj)); + * } + * + * static void + * _disable_hook(Evas_Object *obj) + * { + * Widget_Data *wd = elm_widget_data_get(obj); + * if (!wd) return; + * // optional, but handle if the widget gets disabled or not + * if (elm_widget_disabled_get(obj)) + * edje_object_signal_emit(wd->sub, "elm,state,disabled", "elm"); + * else + * edje_object_signal_emit(wd->sub, "elm,state,enabled", "elm"); + * } + * + * static void + * _sizing_eval(Evas_Object *obj) + * { + * Widget_Data *wd = elm_widget_data_get(obj); + * Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1; + * if (!wd) return; + * elm_coords_finger_size_adjust(1, &minw, 1, &minh); + * edje_object_size_min_restricted_calc(wd->sub, &minw, &minh, minw, minh); + * elm_coords_finger_size_adjust(1, &minw, 1, &minh); + * evas_object_size_hint_min_set(obj, minw, minh); + * evas_object_size_hint_max_set(obj, maxw, maxh); + * } + * + * // actual api to create your widget. add more to manipulate it as needed + * // mark your calls with EAPI to make them "external api" calls. + * EAPI Evas_Object * + * elm_mywidget_add(Evas_Object *parent) + * { + * Evas_Object *obj; + * Evas *e; + * Widget_Data *wd; + * + * // ALWAYS call this - this checks that your widget matches that of + * // elementary and that the api hasn't broken. if it has this returns + * // false and you need to handle this error gracefully + * if (!elm_widget_api_check(ELM_INTERNAL_API_VERSION)) return NULL; + * + * // basic - allocate data for widget and fill it + * wd = ELM_NEW(Widget_Data); + * e = evas_object_evas_get(parent); + * if (!e) return NULL; + * obj = elm_widget_add(e); + * // give it a type name and set up a mywidget type string if needed + * ELM_SET_WIDTYPE(widtype, "mywidget"); + * elm_widget_type_set(obj, "mywidget"); + * // tell the parent widget that we are a sub object + * elm_widget_sub_object_add(parent, obj); + * // setup hooks we need (some are optional) + * elm_widget_on_focus_hook_set(obj, _on_focus_hook, NULL); + * elm_widget_data_set(obj, wd); + * elm_widget_del_hook_set(obj, _del_hook); + * elm_widget_theme_hook_set(obj, _theme_hook); + * elm_widget_disable_hook_set(obj, _disable_hook); + * // this widget can focus (true means yes it can, false means it can't) + * elm_widget_can_focus_set(obj, EINA_TRUE); + * + * // for this widget we will add 1 sub object that is an edje object + * wd->sub = edje_object_add(e); + * // set the theme. this follows a scheme for group name like this: + * // "elm/WIDGETNAME/ELEMENT/STYLE" + * // so here it will be: + * // "elm/mywidget/base/default" + * // changing style changes style name from default (all widgets start + * // with the default style) and element is for your widget internal + * // structure as you see fit + * elm_widget_theme_object_set(obj, wd->sub, "mywidget", "base", "default"); + * // listen to a signal from the edje object to produce widget smart + * // callback (like click) + * edje_object_signal_callback_add(wd->sub, "elm,action,click", "", + * _signal_clicked, obj); + * // set this sub object as the "resize object". widgets get 1 resize + * // object that is resized along with the object wrapper. + * elm_widget_resize_object_set(obj, wd->sub); + * + * // evaluate sizing of the widget (minimum size calc etc.). optional but + * // not a bad idea to do here. it will get queued for later anyway + * _sizing_eval(obj); + * + * // register the smart callback descriptions so we can have some runtime + * // info as to what the smart callback strings mean + * evas_object_smart_callbacks_descriptions_set(obj, _signals); + * return obj; + * } + * + * // example - do "whatever" to the widget (here just emit a signal) + * EAPI void + * elm_mywidget_whatever(Evas_Object *obj) + * { + * // check if type is correct - check will return if it fails + * ELM_CHECK_WIDTYPE(obj, widtype); + * // get widget data - type is correct and sane by this point, so this + * // should never fail + * Widget_Data *wd = elm_widget_data_get(obj); + * // do whatever you like + * edje_object_signal_emit(wd->sub, "elm,state,action,whatever", "elm"); + * } + * + * // you can add more - you need to see elementary's code to know how to + * // handle all cases. remember this api is not stable and may change. it's + * // internal + * + */ + +#ifndef ELM_INTERAL_API_MDFGELQ +# warning "You are using an internal elementary API. This API is not stable" +# warning "and is subject to change. You use this at your own risk." +# warning "Remember to call elm_widget_api_check(ELM_INTERNAL_API_VERSION);" +# warning "in your widgets before you call any other elm_widget calls to do" +# warning "a correct runtime version check." +#endif +#define ELM_INTERNAL_API_VERSION 7000 + +typedef struct _Elm_Tooltip Elm_Tooltip; +typedef struct _Elm_Cursor Elm_Cursor; +typedef struct _Elm_Widget_Item Elm_Widget_Item; /**< base structure for all widget items that are not Elm_Widget themselves */ + +struct _Elm_Widget_Item +{ + /* ef1 ~~ efl, el3 ~~ elm */ +#define ELM_WIDGET_ITEM_MAGIC 0xef1e1301 + EINA_MAGIC; + + Evas_Object *widget; /**< the owner widget that owns this item */ + Evas_Object *view; /**< the base view object */ + const void *data; /**< item specific data */ + Evas_Smart_Cb del_cb; /**< used to notify the item is being deleted */ + /* widget variations should have data from here and on */ + /* @todo: TODO check if this is enough for 1.0 release, maybe add padding! */ +}; + +#define ELM_NEW(t) calloc(1, sizeof(t)) + +EAPI Eina_Bool elm_widget_api_check(int ver); +EAPI Evas_Object *elm_widget_add(Evas *evas); +EAPI void elm_widget_del_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)); +EAPI void elm_widget_del_pre_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)); +EAPI void elm_widget_focus_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)); +EAPI void elm_widget_activate_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)); +EAPI void elm_widget_disable_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)); +EAPI void elm_widget_theme_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)); +EAPI void elm_widget_event_hook_set(Evas_Object *obj, Eina_Bool (*func) (Evas_Object *obj, Evas_Object *source, Evas_Callback_Type type, void *event_info)); +EAPI void elm_widget_changed_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj)); +EAPI void elm_widget_signal_emit_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj, const char *emission, const char *source)); +EAPI void elm_widget_signal_callback_add_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data)); +EAPI void elm_widget_signal_callback_del_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj, const char *emission, const char *source, void (*func_cb) (void *data, Evas_Object *o, const char *emission, const char *source), void *data)); +EAPI void elm_widget_theme(Evas_Object *obj); +EAPI void elm_widget_theme_specific(Evas_Object *obj, Elm_Theme *th, Eina_Bool force); +EAPI void elm_widget_focus_next_hook_set(Evas_Object *obj, Eina_Bool (*func) (const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next)); +EAPI void elm_widget_on_focus_hook_set(Evas_Object *obj, void (*func) (void *data, Evas_Object *obj), void *data); +EAPI void elm_widget_on_change_hook_set(Evas_Object *obj, void (*func) (void *data, Evas_Object *obj), void *data); +EAPI void elm_widget_on_show_region_hook_set(Evas_Object *obj, void (*func) (void *data, Evas_Object *obj), void *data); +EAPI void elm_widget_focus_region_hook_set(Evas_Object *obj, void (*func) (Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h)); +EAPI void elm_widget_on_focus_region_hook_set(Evas_Object *obj, void (*func) (const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h)); +EAPI void elm_widget_data_set(Evas_Object *obj, void *data); +EAPI void *elm_widget_data_get(const Evas_Object *obj); +EAPI void elm_widget_sub_object_add(Evas_Object *obj, Evas_Object *sobj); +EAPI void elm_widget_sub_object_del(Evas_Object *obj, Evas_Object *sobj); +EAPI void elm_widget_resize_object_set(Evas_Object *obj, Evas_Object *sobj); +EAPI void elm_widget_hover_object_set(Evas_Object *obj, Evas_Object *sobj); +EAPI void elm_widget_signal_emit(Evas_Object *obj, const char *emission, const char *source); +EAPI void elm_widget_signal_callback_add(Evas_Object *obj, const char *emission, const char *source, void (*func) (void *data, Evas_Object *o, const char *emission, const char *source), void *data); +EAPI void *elm_widget_signal_callback_del(Evas_Object *obj, const char *emission, const char *source, void (*func) (void *data, Evas_Object *o, const char *emission, const char *source)); +EAPI void elm_widget_can_focus_set(Evas_Object *obj, Eina_Bool can_focus); +EAPI Eina_Bool elm_widget_can_focus_get(const Evas_Object *obj); +EAPI Eina_Bool elm_widget_child_can_focus_get(const Evas_Object *obj); +EAPI void elm_widget_highlight_ignore_set(Evas_Object *obj, Eina_Bool ignore); +EAPI Eina_Bool elm_widget_highlight_ignore_get(const Evas_Object *obj); +EAPI void elm_widget_highlight_in_theme_set(Evas_Object *obj, Eina_Bool highlight); +EAPI Eina_Bool elm_widget_highlight_in_theme_get(const Evas_Object *obj); +EAPI Eina_Bool elm_widget_focus_get(const Evas_Object *obj); +EAPI Evas_Object *elm_widget_focused_object_get(const Evas_Object *obj); +EAPI Evas_Object *elm_widget_top_get(const Evas_Object *obj); +EAPI Eina_Bool elm_widget_is(const Evas_Object *obj); +EAPI Evas_Object *elm_widget_parent_widget_get(const Evas_Object *obj); +EAPI void elm_widget_event_callback_add(Evas_Object *obj, Elm_Event_Cb func, const void *data); +EAPI void *elm_widget_event_callback_del(Evas_Object *obj, Elm_Event_Cb func, const void *data); +EAPI Eina_Bool elm_widget_event_propagate(Evas_Object *obj, Evas_Callback_Type type, void *event_info, Evas_Event_Flags *event_flags); +EAPI void elm_widget_focus_custom_chain_set(Evas_Object *obj, Eina_List *objs); +EAPI void elm_widget_focus_custom_chain_unset(Evas_Object *obj); +EAPI const Eina_List *elm_widget_focus_custom_chain_get(const Evas_Object *obj); +EAPI void elm_widget_focus_custom_chain_append(Evas_Object *obj, Evas_Object *child, Evas_Object *relative_child); +EAPI void elm_widget_focus_custom_chain_prepend(Evas_Object *obj, Evas_Object *child, Evas_Object *relative_child); +EAPI void elm_widget_focus_cycle(Evas_Object *obj, Elm_Focus_Direction dir); +EAPI void elm_widget_focus_direction_go(Evas_Object *obj, int x, int y); +EAPI Eina_Bool elm_widget_focus_next_get(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next); +EAPI Eina_Bool elm_widget_focus_list_next_get(const Evas_Object *obj, const Eina_List *items, void *(*list_data_get) (const Eina_List *list), Elm_Focus_Direction dir, Evas_Object **next); +EAPI void elm_widget_focus_set(Evas_Object *obj, int first); +EAPI void elm_widget_focused_object_clear(Evas_Object *obj); +EAPI Evas_Object *elm_widget_parent_get(const Evas_Object *obj); +EAPI void elm_widget_focus_steal(Evas_Object *obj); +EAPI void elm_widget_activate(Evas_Object *obj); +EAPI void elm_widget_change(Evas_Object *obj); +EAPI void elm_widget_disabled_set(Evas_Object *obj, int disabled); +EAPI int elm_widget_disabled_get(const Evas_Object *obj); +EAPI void elm_widget_show_region_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h); +EAPI void elm_widget_show_region_get(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h); +EAPI void elm_widget_focus_region_get(const Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h); +EAPI void elm_widget_scroll_hold_push(Evas_Object *obj); +EAPI void elm_widget_scroll_hold_pop(Evas_Object *obj); +EAPI int elm_widget_scroll_hold_get(const Evas_Object *obj); +EAPI void elm_widget_scroll_freeze_push(Evas_Object *obj); +EAPI void elm_widget_scroll_freeze_pop(Evas_Object *obj); +EAPI int elm_widget_scroll_freeze_get(const Evas_Object *obj); +EAPI void elm_widget_scale_set(Evas_Object *obj, double scale); +EAPI double elm_widget_scale_get(const Evas_Object *obj); +EAPI void elm_widget_theme_set(Evas_Object *obj, Elm_Theme *th); +EAPI Elm_Theme *elm_widget_theme_get(const Evas_Object *obj); +EAPI void elm_widget_style_set(Evas_Object *obj, const char *style); +EAPI const char *elm_widget_style_get(const Evas_Object *obj); +EAPI void elm_widget_type_set(Evas_Object *obj, const char *type); +EAPI const char *elm_widget_type_get(const Evas_Object *obj); +EAPI void elm_widget_tooltip_add(Evas_Object *obj, Elm_Tooltip *tt); +EAPI void elm_widget_tooltip_del(Evas_Object *obj, Elm_Tooltip *tt); +EAPI void elm_widget_cursor_add(Evas_Object *obj, Elm_Cursor *cur); +EAPI void elm_widget_cursor_del(Evas_Object *obj, Elm_Cursor *cur); +EAPI void elm_widget_drag_lock_x_set(Evas_Object *obj, Eina_Bool lock); +EAPI void elm_widget_drag_lock_y_set(Evas_Object *obj, Eina_Bool lock); +EAPI Eina_Bool elm_widget_drag_lock_x_get(const Evas_Object *obj); +EAPI Eina_Bool elm_widget_drag_lock_y_get(const Evas_Object *obj); +EAPI int elm_widget_drag_child_locked_x_get(const Evas_Object *obj); +EAPI int elm_widget_drag_child_locked_y_get(const Evas_Object *obj); +EAPI Eina_Bool elm_widget_theme_object_set(Evas_Object *obj, Evas_Object *edj, const char *wname, const char *welement, const char *wstyle); +EAPI void elm_widget_type_register(const char **ptr); +EAPI Eina_Bool elm_widget_type_check(const Evas_Object *obj, const char *type); +EAPI Eina_List *elm_widget_stringlist_get(const char *str); +EAPI void elm_widget_stringlist_free(Eina_List *list); + +EAPI Elm_Widget_Item *_elm_widget_item_new(Evas_Object *parent, size_t alloc_size); +EAPI void _elm_widget_item_del(Elm_Widget_Item *item); +EAPI void _elm_widget_item_pre_notify_del(Elm_Widget_Item *item); +EAPI void _elm_widget_item_del_cb_set(Elm_Widget_Item *item, Evas_Smart_Cb del_cb); +EAPI void _elm_widget_item_data_set(Elm_Widget_Item *item, const void *data); +EAPI void *_elm_widget_item_data_get(const Elm_Widget_Item *item); +EAPI void _elm_widget_item_tooltip_text_set(Elm_Widget_Item *item, const char *text); +EAPI void _elm_widget_item_tooltip_content_cb_set(Elm_Widget_Item *item, Elm_Tooltip_Item_Content_Cb func, const void *data, Evas_Smart_Cb del_cb); +EAPI void _elm_widget_item_tooltip_unset(Elm_Widget_Item *item); +EAPI void _elm_widget_item_tooltip_style_set(Elm_Widget_Item *item, const char *style); +EAPI const char *_elm_widget_item_tooltip_style_get(const Elm_Widget_Item *item); +EAPI void _elm_widget_item_cursor_set(Elm_Widget_Item *item, const char *cursor); +EAPI const char *_elm_widget_item_cursor_get(const Elm_Widget_Item *item); +EAPI void _elm_widget_item_cursor_unset(Elm_Widget_Item *item); +EAPI void _elm_widget_item_cursor_style_set(Elm_Widget_Item *item, const char *style); +EAPI const char *_elm_widget_item_cursor_style_get(const Elm_Widget_Item *item); +EAPI void _elm_widget_item_cursor_engine_only_set(Elm_Widget_Item *item, Eina_Bool engine_only); +EAPI Eina_Bool _elm_widget_item_cursor_engine_only_get(const Elm_Widget_Item *item); + +/* debug function. don't use it unless you are tracking parenting issues */ +EAPI void elm_widget_tree_dump(const Evas_Object *top); +EAPI void elm_widget_tree_dot_dump(const Evas_Object *top, FILE *output); + +/** + * Convenience macro to create new widget item, doing casts for you. + * @see _elm_widget_item_new() + * @param parent a valid elm_widget variant. + * @param type the C type that extends Elm_Widget_Item + */ +#define elm_widget_item_new(parent, type) \ + (type *)_elm_widget_item_new((parent), sizeof(type)) +/** + * Convenience macro to delete widget item, doing casts for you. + * @see _elm_widget_item_del() + * @param item a valid item. + */ +#define elm_widget_item_del(item) \ + _elm_widget_item_del((Elm_Widget_Item *)item) +/** + * Convenience macro to notify deletion of widget item, doing casts for you. + * @see _elm_widget_item_pre_notify_del() + */ +#define elm_widget_item_pre_notify_del(item) \ + _elm_widget_item_pre_notify_del((Elm_Widget_Item *)item) +/** + * Convenience macro to set deletion callback of widget item, doing casts for you. + * @see _elm_widget_item_del_cb_set() + */ +#define elm_widget_item_del_cb_set(item, del_cb) \ + _elm_widget_item_del_cb_set((Elm_Widget_Item *)item, del_cb) + +/** + * Set item's data + * @see _elm_widget_item_data_set() + */ +#define elm_widget_item_data_set(item, data) \ + _elm_widget_item_data_set((Elm_Widget_Item *)item, data) +/** + * Get item's data + * @see _elm_widget_item_data_get() + */ +#define elm_widget_item_data_get(item) \ + _elm_widget_item_data_get((const Elm_Widget_Item *)item) + +/** + * Convenience function to set widget item tooltip as a text string. + * @see _elm_widget_item_tooltip_text_set() + */ +#define elm_widget_item_tooltip_text_set(item, text) \ + _elm_widget_item_tooltip_text_set((Elm_Widget_Item *)item, text) +/** + * Convenience function to set widget item tooltip. + * @see _elm_widget_item_tooltip_content_cb_set() + */ +#define elm_widget_item_tooltip_content_cb_set(item, func, data, del_cb) \ + _elm_widget_item_tooltip_content_cb_set((Elm_Widget_Item *)item, \ + func, data, del_cb) +/** + * Convenience function to unset widget item tooltip. + * @see _elm_widget_item_tooltip_unset() + */ +#define elm_widget_item_tooltip_unset(item) \ + _elm_widget_item_tooltip_unset((Elm_Widget_Item *)item) +/** + * Convenience function to change item's tooltip style. + * @see _elm_widget_item_tooltip_style_set() + */ +#define elm_widget_item_tooltip_style_set(item, style) \ + _elm_widget_item_tooltip_style_set((Elm_Widget_Item *)item, style) +/** + * Convenience function to query item's tooltip style. + * @see _elm_widget_item_tooltip_style_get() + */ +#define elm_widget_item_tooltip_style_get(item) \ + _elm_widget_item_tooltip_style_get((const Elm_Widget_Item *)item) +/** + * Convenience function to set widget item cursor. + * @see _elm_widget_item_cursor_set() + */ +#define elm_widget_item_cursor_set(item, cursor) \ + _elm_widget_item_cursor_set((Elm_Widget_Item *)item, cursor) +/** + * Convenience function to get widget item cursor. + * @see _elm_widget_item_cursor_get() + */ +#define elm_widget_item_cursor_get(item) \ + _elm_widget_item_cursor_get((const Elm_Widget_Item *)item) +/** + * Convenience function to unset widget item cursor. + * @see _elm_widget_item_cursor_unset() + */ +#define elm_widget_item_cursor_unset(item) \ + _elm_widget_item_cursor_unset((Elm_Widget_Item *)item) +/** + * Convenience function to change item's cursor style. + * @see _elm_widget_item_cursor_style_set() + */ +#define elm_widget_item_cursor_style_set(item, style) \ + _elm_widget_item_cursor_style_set((Elm_Widget_Item *)item, style) +/** + * Convenience function to query item's cursor style. + * @see _elm_widget_item_cursor_style_get() + */ +#define elm_widget_item_cursor_style_get(item) \ + _elm_widget_item_cursor_style_get((const Elm_Widget_Item *)item) +/** + * Convenience function to change item's cursor engine_only. + * @see _elm_widget_item_cursor_engine_only_set() + */ +#define elm_widget_item_cursor_engine_only_set(item, engine_only) \ + _elm_widget_item_cursor_engine_only_set((Elm_Widget_Item *)item, engine_only) +/** + * Convenience function to query item's cursor engine_only. + * @see _elm_widget_item_cursor_engine_only_get() + */ +#define elm_widget_item_cursor_engine_only_get(item) \ + _elm_widget_item_cursor_engine_only_get((const Elm_Widget_Item *)item) + +/** + * Cast and ensure the given pointer is an Elm_Widget_Item or return NULL. + */ +#define ELM_WIDGET_ITEM(item) \ + (((item) && (EINA_MAGIC_CHECK(item, ELM_WIDGET_ITEM_MAGIC))) ? \ + ((Elm_Widget_Item *)(item)) : NULL) + +#define ELM_WIDGET_ITEM_CHECK_OR_RETURN(item, ...) \ + do { \ + if (!item) { \ + CRITICAL("Elm_Widget_Item " # item " is NULL!"); \ + return __VA_ARGS__; \ + } \ + if (!EINA_MAGIC_CHECK(item, ELM_WIDGET_ITEM_MAGIC)) { \ + EINA_MAGIC_FAIL(item, ELM_WIDGET_ITEM_MAGIC); \ + return __VA_ARGS__; \ + } \ + } while (0) + +#define ELM_WIDGET_ITEM_CHECK_OR_GOTO(item, label) \ + do { \ + if (!item) { \ + CRITICAL("Elm_Widget_Item " # item " is NULL!"); \ + goto label; \ + } \ + if (!EINA_MAGIC_CHECK(item, ELM_WIDGET_ITEM_MAGIC)) { \ + EINA_MAGIC_FAIL(item, ELM_WIDGET_ITEM_MAGIC); \ + goto label; \ + } \ + } while (0) + +#define ELM_SET_WIDTYPE(widtype, type) \ + do { \ + if (!widtype) { \ + widtype = eina_stringshare_add(type); \ + elm_widget_type_register(&widtype); \ + } \ + } while (0) + +#define ELM_CHECK_WIDTYPE(obj, widtype) \ + if (!elm_widget_type_check((obj), (widtype))) return + +#define ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_RETURN(it, ...) \ + ELM_WIDGET_ITEM_CHECK_OR_RETURN((Elm_Widget_Item *)it, __VA_ARGS__); \ + ELM_CHECK_WIDTYPE(it->base.widget, widtype) __VA_ARGS__; + +#define ELM_WIDGET_ITEM_WIDTYPE_CHECK_OR_GOTO(it, label) \ + ELM_WIDGET_ITEM_CHECK_OR_GOTO((Elm_Widget_Item *)it, label); \ + if (!elm_widget_type_check((it->base.widget), (widtype))) goto label; + + +/** + * The drag and drop API. + * Currently experimental, and will change when it does dynamic type + * addition RSN. + * + * Here so applications can start to use it, if they ask elm nicely. + * + * And yes, elm_widget, should probably be elm_experimental... + * Complaints about this code should go to /dev/null, or failing that nash. + */ +typedef struct _Elm_Selection_Data Elm_Selection_Data; + +typedef Eina_Bool (*Elm_Drop_Cb) (void *d, Evas_Object *o, Elm_Selection_Data *data); + +typedef enum _Elm_Sel_Type +{ + ELM_SEL_PRIMARY, + ELM_SEL_SECONDARY, + ELM_SEL_CLIPBOARD, + ELM_SEL_XDND, + + ELM_SEL_MAX, +} Elm_Sel_Type; + +typedef enum _Elm_Sel_Format +{ + /** Plain unformated text: Used for things that don't want rich markup */ + ELM_SEL_FORMAT_TEXT = 0x01, + /** Edje textblock markup, including inline images */ + ELM_SEL_FORMAT_MARKUP = 0x02, + /** Images */ + ELM_SEL_FORMAT_IMAGE = 0x04, + /** Vcards */ + ELM_SEL_FORMAT_VCARD = 0x08, + /** Raw HTMLish things for widgets that want that stuff (hello webkit!) */ + ELM_SEL_FORMAT_HTML = 0x10, +} Elm_Sel_Format; + +struct _Elm_Selection_Data +{ + int x, y; + Elm_Sel_Format format; + void *data; + int len; +}; + +Eina_Bool elm_selection_set(Elm_Sel_Type selection, Evas_Object *widget, Elm_Sel_Format format, const char *buf); +Eina_Bool elm_selection_clear(Elm_Sel_Type selection, Evas_Object *widget); +Eina_Bool elm_selection_get(Elm_Sel_Type selection, Elm_Sel_Format format, Evas_Object *widget, Elm_Drop_Cb datacb, void *udata); +Eina_Bool elm_drop_target_add(Evas_Object *widget, Elm_Sel_Type, Elm_Drop_Cb, void *); +Eina_Bool elm_drop_target_del(Evas_Object *widget); +Eina_Bool elm_drag_start(Evas_Object *, Elm_Sel_Format, const char *, void (*)(void *,Evas_Object*),void*); + + +#endif diff --git a/src/lib/elm_win.c b/src/lib/elm_win.c new file mode 100644 index 0000000..9241bce --- /dev/null +++ b/src/lib/elm_win.c @@ -0,0 +1,2505 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Win Win + * + * The window class of Elementary. Contains functions to manipulate + * windows. + */ + +typedef struct _Elm_Win Elm_Win; + +struct _Elm_Win +{ + Ecore_Evas *ee; + Evas *evas; + Evas_Object *parent, *win_obj; + Eina_List *subobjs; +#ifdef HAVE_ELEMENTARY_X + Ecore_X_Window xwin; + Ecore_Event_Handler *client_message_handler; +#endif + Ecore_Job *deferred_resize_job; + Ecore_Job *deferred_child_eval_job; + + Elm_Win_Type type; + Elm_Win_Keyboard_Mode kbdmode; + Eina_Bool autodel : 1; + int *autodel_clear, rot; + struct { + int x, y; + } screen; + + struct { + Evas_Object *top; + + struct { + Evas_Object *target; + Eina_Bool visible : 1; + Eina_Bool handled : 1; + } cur, prev; + + const char *style; + Ecore_Job *reconf_job; + + Eina_Bool enabled : 1; + Eina_Bool changed_theme : 1; + Eina_Bool top_animate : 1; + Eina_Bool geometry_changed : 1; + } focus_highlight; +}; + +static const char *widtype = NULL; +static void _elm_win_obj_callback_del(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _elm_win_obj_callback_parent_del(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _elm_win_obj_intercept_show(void *data, Evas_Object *obj); +static void _elm_win_move(Ecore_Evas *ee); +static void _elm_win_resize(Ecore_Evas *ee); +static void _elm_win_delete_request(Ecore_Evas *ee); +static void _elm_win_resize_job(void *data); +#ifdef HAVE_ELEMENTARY_X +static void _elm_win_xwin_update(Elm_Win *win); +#endif +static void _elm_win_eval_subobjs(Evas_Object *obj); +static void _elm_win_subobj_callback_del(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _elm_win_subobj_callback_changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _elm_win_focus_highlight_init(Elm_Win *win); +static void _elm_win_focus_highlight_shutdown(Elm_Win *win); +static void _elm_win_focus_highlight_visible_set(Elm_Win *win, Eina_Bool visible); +static void _elm_win_focus_highlight_reconfigure_job_start(Elm_Win *win); +static void _elm_win_focus_highlight_reconfigure_job_stop(Elm_Win *win); +static void _elm_win_focus_highlight_anim_end(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _elm_win_focus_highlight_reconfigure(Elm_Win *win); + +Eina_List *_elm_win_list = NULL; + +static void +_elm_win_move(Ecore_Evas *ee) +{ + Evas_Object *obj = ecore_evas_object_associate_get(ee); + Elm_Win *win; + int x, y; + + if (!obj) return; + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_geometry_get(ee, &x, &y, NULL, NULL); + win->screen.x = x; + win->screen.y = y; + evas_object_smart_callback_call(win->win_obj, "moved", NULL); +} + +static void +_elm_win_resize(Ecore_Evas *ee) +{ + Evas_Object *obj = ecore_evas_object_associate_get(ee); + Elm_Win *win; + + if (!obj) return; + win = elm_widget_data_get(obj); + if (!win) return; + if (win->deferred_resize_job) ecore_job_del(win->deferred_resize_job); + win->deferred_resize_job = ecore_job_add(_elm_win_resize_job, win); +} + +static void +_elm_win_focus_in(Ecore_Evas *ee) +{ + Evas_Object *obj = ecore_evas_object_associate_get(ee); + Elm_Win *win; + + if (!obj) return; + win = elm_widget_data_get(obj); + if (!win) return; + /*NB: Why two different "focus signals" here ??? */ + evas_object_smart_callback_call(win->win_obj, "focus-in", NULL); // FIXME: remove me + evas_object_smart_callback_call(win->win_obj, "focus,in", NULL); + win->focus_highlight.cur.visible = EINA_TRUE; + _elm_win_focus_highlight_reconfigure_job_start(win); +} + +static void +_elm_win_focus_out(Ecore_Evas *ee) +{ + Evas_Object *obj = ecore_evas_object_associate_get(ee); + Elm_Win *win; + + if (!obj) return; + win = elm_widget_data_get(obj); + if (!win) return; + evas_object_smart_callback_call(win->win_obj, "focus-out", NULL); // FIXME: remove me + evas_object_smart_callback_call(win->win_obj, "focus,out", NULL); + win->focus_highlight.cur.visible = EINA_FALSE; + _elm_win_focus_highlight_reconfigure_job_start(win); +} + +static Eina_Bool +_elm_win_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Elm_Win *wd = elm_widget_data_get(obj); + const Eina_List *items; + void *(*list_data_get) (const Eina_List *list); + + if (!wd) + return EINA_FALSE; + + /* Focus chain */ + if (wd->subobjs) + { + if (!(items = elm_widget_focus_custom_chain_get(obj))) + { + items = wd->subobjs; + if (!items) + return EINA_FALSE; + } + list_data_get = eina_list_data_get; + + elm_widget_focus_list_next_get(obj, items, list_data_get, dir, next); + + if (*next) + return EINA_TRUE; + } + + *next = (Evas_Object *)obj; + return EINA_FALSE; +} + +static void +_elm_win_on_focus_hook(void *data __UNUSED__, Evas_Object *obj) +{ + if (elm_widget_focus_get(obj)) + evas_object_focus_set(obj, EINA_TRUE); + else + evas_object_focus_set(obj, EINA_FALSE); +} + +static Eina_Bool +_elm_win_event_cb(Evas_Object *obj, Evas_Object *src __UNUSED__, Evas_Callback_Type type, void *event_info) +{ + if (type == EVAS_CALLBACK_KEY_DOWN) + { + Evas_Event_Key_Down *ev = event_info; + if (!strcmp(ev->keyname, "Tab")) + { + if(evas_key_modifier_is_set(ev->modifiers, "Shift")) + elm_widget_focus_cycle(obj, ELM_FOCUS_PREVIOUS); + else + elm_widget_focus_cycle(obj, ELM_FOCUS_NEXT); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + return EINA_TRUE; + } + } + + return EINA_FALSE; +} + +static void +_deferred_ecore_evas_free(void *data) +{ + ecore_evas_free(data); +} + +static void +_elm_win_obj_callback_show(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + elm_object_focus(obj); +} + +static void +_elm_win_obj_callback_del(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Win *win = data; + Evas_Object *child; + + if (win->parent) + { + evas_object_event_callback_del_full(win->parent, EVAS_CALLBACK_DEL, + _elm_win_obj_callback_parent_del, win); + win->parent = NULL; + } + if (win->autodel_clear) *(win->autodel_clear) = -1; + _elm_win_list = eina_list_remove(_elm_win_list, win->win_obj); + while (win->subobjs) elm_win_resize_object_del(obj, win->subobjs->data); + ecore_evas_callback_delete_request_set(win->ee, NULL); + ecore_evas_callback_resize_set(win->ee, NULL); + if (win->deferred_resize_job) ecore_job_del(win->deferred_resize_job); + if (win->deferred_child_eval_job) ecore_job_del(win->deferred_child_eval_job); + while (((child = evas_object_bottom_get(win->evas))) && + (child != obj)) + { + evas_object_del(child); + } + while (((child = evas_object_top_get(win->evas))) && + (child != obj)) + { + evas_object_del(child); + } +#ifdef HAVE_ELEMENTARY_X + if (win->client_message_handler) + ecore_event_handler_del(win->client_message_handler); +#endif +// FIXME: Why are we flushing edje on every window destroy ?? +// edje_file_cache_flush(); +// edje_collection_cache_flush(); +// evas_image_cache_flush(win->evas); +// evas_font_cache_flush(win->evas); +// FIXME: we are in the del handler for the object and delete the canvas +// that lives under it from the handler... nasty. deferring doesn't help either + ecore_job_add(_deferred_ecore_evas_free, win->ee); +// ecore_evas_free(win->ee); + + _elm_win_focus_highlight_shutdown(win); + eina_stringshare_del(win->focus_highlight.style); + + free(win); + + if ((!_elm_win_list) && + (elm_policy_get(ELM_POLICY_QUIT) == ELM_POLICY_QUIT_LAST_WINDOW_CLOSED)) + { + edje_file_cache_flush(); + edje_collection_cache_flush(); + evas_image_cache_flush(e); + evas_font_cache_flush(e); + elm_exit(); + } +} + +static void +_elm_win_obj_callback_parent_del(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Win *win = data; + if (obj == win->parent) win->parent = NULL; +} + +static void +_elm_win_obj_intercept_show(void *data __UNUSED__, Evas_Object *obj) +{ + // this is called to make sure all smart containers have calculated their + // sizes BEFORE we show the window to make sure it initially appears at + // our desired size (ie min size is known first) + evas_smart_objects_calculate(evas_object_evas_get(obj)); + evas_object_show(obj); +} + +static void +_elm_win_delete_request(Ecore_Evas *ee) +{ + Evas_Object *obj = ecore_evas_object_associate_get(ee); + Elm_Win *win; + if (strcmp(elm_widget_type_get(obj), "win")) return; + + win = elm_widget_data_get(obj); + if (!win) return; + int autodel = win->autodel; + win->autodel_clear = &autodel; + evas_object_smart_callback_call(win->win_obj, "delete-request", NULL); // FIXME: remove me + evas_object_smart_callback_call(win->win_obj, "delete,request", NULL); + // FIXME: if above callback deletes - then the below will be invalid + if (autodel) evas_object_del(win->win_obj); + else win->autodel_clear = NULL; +} + +static void +_elm_win_resize_job(void *data) +{ + Elm_Win *win = data; + const Eina_List *l; + Evas_Object *obj; + int w, h; + + win->deferred_resize_job = NULL; + ecore_evas_geometry_get(win->ee, NULL, NULL, &w, &h); + evas_object_resize(win->win_obj, w, h); + EINA_LIST_FOREACH(win->subobjs, l, obj) + { + evas_object_move(obj, 0, 0); + evas_object_resize(obj, w, h); + } +} + +#ifdef HAVE_ELEMENTARY_X +static void +_elm_win_xwindow_get(Elm_Win *win) +{ + win->xwin = 0; + +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_X11)) + { + if (win->ee) win->xwin = ecore_evas_software_x11_window_get(win->ee); + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_X11) || + ENGINE_COMPARE(ELM_SOFTWARE_FB) || + ENGINE_COMPARE(ELM_SOFTWARE_16_WINCE) || + ENGINE_COMPARE(ELM_SOFTWARE_SDL) || + ENGINE_COMPARE(ELM_SOFTWARE_16_SDL) || + ENGINE_COMPARE(ELM_OPENGL_SDL)) + { + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_16_X11)) + { + if (win->ee) win->xwin = ecore_evas_software_x11_16_window_get(win->ee); + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_8_X11)) + { + if (win->ee) win->xwin = ecore_evas_software_x11_8_window_get(win->ee); + } + else if (ENGINE_COMPARE(ELM_XRENDER_X11)) + { + if (win->ee) win->xwin = ecore_evas_xrender_x11_window_get(win->ee); + } + else if (ENGINE_COMPARE(ELM_OPENGL_X11)) + { + if (win->ee) win->xwin = ecore_evas_gl_x11_window_get(win->ee); + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_WIN32)) + { + if (win->ee) win->xwin = (long)ecore_evas_win32_window_get(win->ee); + } +#undef ENGINE_COMPARE +} +#endif + +#ifdef HAVE_ELEMENTARY_X +static void +_elm_win_xwin_update(Elm_Win *win) +{ + _elm_win_xwindow_get(win); + if (win->parent) + { + Elm_Win *win2; + + win2 = elm_widget_data_get(win->parent); + if (win2) + { + if (win->xwin) + ecore_x_icccm_transient_for_set(win->xwin, win2->xwin); + } + } + + if (!win->xwin) return; /* nothing more to do */ + + switch (win->type) + { + case ELM_WIN_BASIC: + ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_NORMAL); + break; + case ELM_WIN_DIALOG_BASIC: + ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_DIALOG); + break; + case ELM_WIN_DESKTOP: + ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_DESKTOP); + break; + case ELM_WIN_DOCK: + ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_DOCK); + break; + case ELM_WIN_TOOLBAR: + ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_TOOLBAR); + break; + case ELM_WIN_MENU: + ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_MENU); + break; + case ELM_WIN_UTILITY: + ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_UTILITY); + break; + case ELM_WIN_SPLASH: + ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_SPLASH); + break; + default: + break; + } + ecore_x_e_virtual_keyboard_state_set + (win->xwin, (Ecore_X_Virtual_Keyboard_State)win->kbdmode); +} +#endif + +static void +_elm_win_eval_subobjs(Evas_Object *obj) +{ + const Eina_List *l; + const Evas_Object *child; + + Elm_Win *win = elm_widget_data_get(obj); + Evas_Coord w, h, minw = -1, minh = -1, maxw = -1, maxh = -1; + int xx = 1, xy = 1; + double wx, wy; + + EINA_LIST_FOREACH(win->subobjs, l, child) + { + evas_object_size_hint_weight_get(child, &wx, &wy); + if (wx == 0.0) xx = 0; + if (wy == 0.0) xy = 0; + + evas_object_size_hint_min_get(child, &w, &h); + if (w < 1) w = -1; + if (h < 1) h = -1; + if (w > minw) minw = w; + if (h > minh) minh = h; + + evas_object_size_hint_max_get(child, &w, &h); + if (w < 1) w = -1; + if (h < 1) h = -1; + if (maxw == -1) maxw = w; + else if ((w > 0) && (w < maxw)) maxw = w; + if (maxh == -1) maxh = h; + else if ((h > 0) && (h < maxh)) maxh = h; + } + if (!xx) maxw = minw; + else maxw = 32767; + if (!xy) maxh = minh; + else maxh = 32767; + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, maxw, maxh); + evas_object_geometry_get(obj, NULL, NULL, &w, &h); + if (w < minw) w = minw; + if (h < minh) h = minh; + if ((maxw >= 0) && (w > maxw)) w = maxw; + if ((maxh >= 0) && (h > maxh)) h = maxh; + evas_object_resize(obj, w, h); +} + +static void +_elm_win_subobj_callback_del(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Win *win = elm_widget_data_get(data); + win->subobjs = eina_list_remove(win->subobjs, obj); + _elm_win_eval_subobjs(win->win_obj); +} + +static void +_elm_win_subobj_callback_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _elm_win_eval_subobjs(data); +} + +void +_elm_win_shutdown(void) +{ + while (_elm_win_list) + evas_object_del(_elm_win_list->data); +} + +void +_elm_win_rescale(Elm_Theme *th, Eina_Bool use_theme) +{ + const Eina_List *l; + Evas_Object *obj; + + if (!use_theme) + { + EINA_LIST_FOREACH(_elm_win_list, l, obj) + elm_widget_theme(obj); + } + else + { + EINA_LIST_FOREACH(_elm_win_list, l, obj) + elm_widget_theme_specific(obj, th, EINA_FALSE); + } +} + +#ifdef HAVE_ELEMENTARY_X +static Eina_Bool +_elm_win_client_message(void *data, int type __UNUSED__, void *event) +{ + Elm_Win *win = data; + Ecore_X_Event_Client_Message *e = event; + + if (e->format != 32) return ECORE_CALLBACK_PASS_ON; + if (e->message_type == ECORE_X_ATOM_E_COMP_FLUSH) + { + if ((unsigned)e->data.l[0] == win->xwin) + { + Evas *evas = evas_object_evas_get(win->win_obj); + if (evas) + { + edje_file_cache_flush(); + edje_collection_cache_flush(); + evas_image_cache_flush(evas); + evas_font_cache_flush(evas); + } + } + } + else if (e->message_type == ECORE_X_ATOM_E_COMP_DUMP) + { + if ((unsigned)e->data.l[0] == win->xwin) + { + Evas *evas = evas_object_evas_get(win->win_obj); + if (evas) + { + edje_file_cache_flush(); + edje_collection_cache_flush(); + evas_image_cache_flush(evas); + evas_font_cache_flush(evas); + evas_render_dump(evas); + } + } + } + return ECORE_CALLBACK_PASS_ON; +} +#endif + +static void +_elm_win_focus_target_move(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Win *win = data; + + win->focus_highlight.geometry_changed = EINA_TRUE; + _elm_win_focus_highlight_reconfigure_job_start(win); +} + +static void +_elm_win_focus_target_resize(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Win *win = data; + + win->focus_highlight.geometry_changed = EINA_TRUE; + _elm_win_focus_highlight_reconfigure_job_start(win); +} + +static void +_elm_win_focus_target_del(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Win *win = data; + + win->focus_highlight.cur.target = NULL; + + _elm_win_focus_highlight_reconfigure_job_start(win); +} + +static void +_elm_win_focus_target_callbacks_add(Elm_Win *win) +{ + Evas_Object *obj = win->focus_highlight.cur.target; + + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOVE, + _elm_win_focus_target_move, win); + evas_object_event_callback_add(obj, EVAS_CALLBACK_RESIZE, + _elm_win_focus_target_resize, win); + evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, + _elm_win_focus_target_del, win); +} + +static void +_elm_win_focus_target_callbacks_del(Elm_Win *win) +{ + Evas_Object *obj = win->focus_highlight.cur.target; + + evas_object_event_callback_del_full(obj, EVAS_CALLBACK_MOVE, + _elm_win_focus_target_move, win); + evas_object_event_callback_del_full(obj, EVAS_CALLBACK_RESIZE, + _elm_win_focus_target_resize, win); + evas_object_event_callback_del_full(obj, EVAS_CALLBACK_DEL, + _elm_win_focus_target_del, win); +} + +static Evas_Object * +_elm_win_focus_target_get(Evas_Object *obj) +{ + Evas_Object *o = obj; + + do + { + if (elm_widget_is(o)) + { + if (!elm_widget_highlight_ignore_get(o)) + break; + o = elm_widget_parent_get(o); + if (!o) + o = evas_object_smart_parent_get(o); + } + else + { + o = elm_widget_parent_widget_get(o); + if (!o) + o = evas_object_smart_parent_get(o); + } + } + while (o); + + return o; +} + +static void +_elm_win_object_focus_in(void *data, Evas *e __UNUSED__, void *event_info) +{ + Evas_Object *obj = event_info, *target; + Elm_Win *win = data; + + if (win->focus_highlight.cur.target == obj) + return; + + target = _elm_win_focus_target_get(obj); + win->focus_highlight.cur.target = target; + if (elm_widget_highlight_in_theme_get(target)) + win->focus_highlight.cur.handled = EINA_TRUE; + else + _elm_win_focus_target_callbacks_add(win); + + _elm_win_focus_highlight_reconfigure_job_start(win); +} + +static void +_elm_win_object_focus_out(void *data, Evas *e __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Win *win = data; + + if (!win->focus_highlight.cur.target) + return; + + if (!win->focus_highlight.cur.handled) + _elm_win_focus_target_callbacks_del(win); + win->focus_highlight.cur.target = NULL; + win->focus_highlight.cur.handled = EINA_FALSE; + + _elm_win_focus_highlight_reconfigure_job_start(win); +} + +static void +_elm_win_focus_highlight_hide(void *data __UNUSED__, Evas_Object *obj, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + evas_object_hide(obj); +} + +static void +_elm_win_focus_highlight_init(Elm_Win *win) +{ + evas_event_callback_add(win->evas, EVAS_CALLBACK_CANVAS_OBJECT_FOCUS_IN, + _elm_win_object_focus_in, win); + evas_event_callback_add(win->evas, + EVAS_CALLBACK_CANVAS_OBJECT_FOCUS_OUT, + _elm_win_object_focus_out, win); + + win->focus_highlight.cur.target = evas_focus_get(win->evas); + + win->focus_highlight.top = edje_object_add(win->evas); + win->focus_highlight.changed_theme = EINA_TRUE; + edje_object_signal_callback_add(win->focus_highlight.top, + "elm,action,focus,hide,end", "", + _elm_win_focus_highlight_hide, NULL); + edje_object_signal_callback_add(win->focus_highlight.top, + "elm,action,focus,anim,end", "", + _elm_win_focus_highlight_anim_end, win); + _elm_win_focus_highlight_reconfigure_job_start(win); +} + +static void +_elm_win_focus_highlight_shutdown(Elm_Win *win) +{ + _elm_win_focus_highlight_reconfigure_job_stop(win); + if (win->focus_highlight.cur.target) + { + _elm_win_focus_target_callbacks_del(win); + win->focus_highlight.cur.target = NULL; + } + if (win->focus_highlight.top) + { + evas_object_del(win->focus_highlight.top); + win->focus_highlight.top = NULL; + } + + evas_event_callback_del_full(win->evas, + EVAS_CALLBACK_CANVAS_OBJECT_FOCUS_IN, + _elm_win_object_focus_in, win); + evas_event_callback_del_full(win->evas, + EVAS_CALLBACK_CANVAS_OBJECT_FOCUS_OUT, + _elm_win_object_focus_out, win); +} + +static void +_elm_win_focus_highlight_visible_set(Elm_Win *win, Eina_Bool visible) +{ + Evas_Object *top; + + top = win->focus_highlight.top; + if (visible) + { + if (top) + { + evas_object_show(top); + edje_object_signal_emit(top, "elm,action,focus,show", "elm"); + } + } + else + { + if (top) + edje_object_signal_emit(top, "elm,action,focus,hide", "elm"); + } +} + +static void +_elm_win_focus_highlight_reconfigure_job(void *data) +{ + _elm_win_focus_highlight_reconfigure((Elm_Win *)data); +} + +static void +_elm_win_focus_highlight_reconfigure_job_start(Elm_Win *win) +{ + if (win->focus_highlight.reconf_job) + ecore_job_del(win->focus_highlight.reconf_job); + win->focus_highlight.reconf_job = ecore_job_add( + _elm_win_focus_highlight_reconfigure_job, win); +} + +static void +_elm_win_focus_highlight_reconfigure_job_stop(Elm_Win *win) +{ + if (win->focus_highlight.reconf_job) + ecore_job_del(win->focus_highlight.reconf_job); + win->focus_highlight.reconf_job = NULL; +} + +static void +_elm_win_focus_highlight_simple_setup(Elm_Win *win, Evas_Object *obj) +{ + Evas_Object *clip, *target = win->focus_highlight.cur.target; + Evas_Coord x, y, w, h; + + clip = evas_object_clip_get(target); + evas_object_geometry_get(target, &x, &y, &w, &h); + + evas_object_move(obj, x, y); + evas_object_resize(obj, w, h); + evas_object_clip_set(obj, clip); +} + +static void +_elm_win_focus_highlight_anim_setup(Elm_Win *win, Evas_Object *obj) +{ + Evas_Coord tx, ty, tw, th; + Evas_Coord w, h, px, py, pw, ph; + Edje_Message_Int_Set *m; + Evas_Object *previous = win->focus_highlight.prev.target; + Evas_Object *target = win->focus_highlight.cur.target; + + evas_object_geometry_get(win->win_obj, NULL, NULL, &w, &h); + evas_object_geometry_get(target, &tx, &ty, &tw, &th); + evas_object_geometry_get(previous, &px, &py, &pw, &ph); + evas_object_move(obj, 0, 0); + evas_object_resize(obj, tw, th); + evas_object_clip_unset(obj); + + m = alloca(sizeof(*m) + (sizeof(int) * 8)); + m->count = 8; + m->val[0] = px; + m->val[1] = py; + m->val[2] = pw; + m->val[3] = ph; + m->val[4] = tx; + m->val[5] = ty; + m->val[6] = tw; + m->val[7] = th; + edje_object_message_send(obj, EDJE_MESSAGE_INT_SET, 1, m); +} + +static void +_elm_win_focus_highlight_anim_end(void *data, Evas_Object *obj, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Elm_Win *win = data; + _elm_win_focus_highlight_simple_setup(win, obj); +} + +static void +_elm_win_focus_highlight_reconfigure(Elm_Win *win) +{ + Evas_Object *target = win->focus_highlight.cur.target; + Evas_Object *previous = win->focus_highlight.prev.target; + Evas_Object *top = win->focus_highlight.top; + Eina_Bool visible_changed; + Eina_Bool common_visible; + const char *sig = NULL; + + _elm_win_focus_highlight_reconfigure_job_stop(win); + + visible_changed = (win->focus_highlight.cur.visible != + win->focus_highlight.prev.visible); + + if ((target == previous) && (!visible_changed) && + (!win->focus_highlight.geometry_changed)) + return; + + if ((previous) && (win->focus_highlight.prev.handled)) + elm_widget_signal_emit(previous, "elm,action,focus_highlight,hide", "elm"); + + if (!target) + common_visible = EINA_FALSE; + else if (win->focus_highlight.cur.handled) + { + common_visible = EINA_FALSE; + if (win->focus_highlight.cur.visible) + sig = "elm,action,focus_highlight,show"; + else + sig = "elm,action,focus_highlight,hide"; + } + else + common_visible = win->focus_highlight.cur.visible; + + _elm_win_focus_highlight_visible_set(win, common_visible); + if (sig) + elm_widget_signal_emit(target, sig, "elm"); + + if ((!target) || (!common_visible) || (win->focus_highlight.cur.handled)) + goto the_end; + + if (win->focus_highlight.changed_theme) + { + const char *str; + if (win->focus_highlight.style) + str = win->focus_highlight.style; + else + str = "default"; + _elm_theme_object_set(win->win_obj, top, "focus_highlight", "top", + str); + win->focus_highlight.changed_theme = EINA_FALSE; + + if (_elm_config->focus_highlight_animate) + { + str = edje_object_data_get(win->focus_highlight.top, "animate"); + win->focus_highlight.top_animate = ((str) && (!strcmp(str, "on"))); + } + } + + if ((win->focus_highlight.top_animate) && (previous) && + (!win->focus_highlight.prev.handled)) + _elm_win_focus_highlight_anim_setup(win, top); + else + _elm_win_focus_highlight_simple_setup(win, top); + evas_object_raise(top); + +the_end: + win->focus_highlight.geometry_changed = EINA_FALSE; + win->focus_highlight.prev = win->focus_highlight.cur; +} + +#ifdef ELM_DEBUG +static void +_debug_key_down(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj, void *event_info) +{ + Evas_Event_Key_Down *ev = event_info; + + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) + return; + + + if ((strcmp(ev->keyname, "F12")) || + (!evas_key_modifier_is_set(ev->modifiers, "Control"))) + return; + + printf("Tree graph generated.\n"); + elm_object_tree_dot_dump(obj, "./dump.dot"); +} +#endif + +/** + * Adds a window object. If this is the first window created, pass NULL as + * @p parent. + * + * @param parent Parent object to add the window to, or NULL + * @param name The name of the window + * @param type The window type, one of the following: + * ELM_WIN_BASIC + * ELM_WIN_DIALOG_BASIC + * ELM_WIN_DESKTOP + * ELM_WIN_DOCK + * ELM_WIN_TOOLBAR + * ELM_WIN_MENU + * ELM_WIN_UTILITY + * ELM_WIN_SPLASH + * + * @return The created object, or NULL on failure + * + * @ingroup Win + */ +EAPI Evas_Object * +elm_win_add(Evas_Object *parent, const char *name, Elm_Win_Type type) +{ + Elm_Win *win; + const Eina_List *l; + const char *fontpath; + + win = ELM_NEW(Elm_Win); + +#define FALLBACK_TRY(engine) \ + if (!win->ee) \ + do { \ + CRITICAL(engine " engine creation failed. Trying software X11."); \ + win->ee = ecore_evas_software_x11_new(NULL, 0, 0, 0, 1, 1); \ + } while (0) + +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_X11)) + { + win->ee = ecore_evas_software_x11_new(NULL, 0, 0, 0, 1, 1); +#ifdef HAVE_ELEMENTARY_X + win->client_message_handler = ecore_event_handler_add + (ECORE_X_EVENT_CLIENT_MESSAGE, _elm_win_client_message, win); +#endif + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_FB)) + { + win->ee = ecore_evas_fb_new(NULL, 0, 1, 1); + FALLBACK_TRY("Sofware FB"); + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_DIRECTFB)) + { + win->ee = ecore_evas_directfb_new(NULL, 1, 0, 0, 1, 1); + FALLBACK_TRY("Sofware DirectFB"); + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_16_X11)) + { + win->ee = ecore_evas_software_x11_16_new(NULL, 0, 0, 0, 1, 1); + FALLBACK_TRY("Sofware-16"); +#ifdef HAVE_ELEMENTARY_X + win->client_message_handler = ecore_event_handler_add + (ECORE_X_EVENT_CLIENT_MESSAGE, _elm_win_client_message, win); +#endif + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_8_X11)) + { + win->ee = ecore_evas_software_x11_8_new(NULL, 0, 0, 0, 1, 1); + FALLBACK_TRY("Sofware-8"); +#ifdef HAVE_ELEMENTARY_X + win->client_message_handler = ecore_event_handler_add + (ECORE_X_EVENT_CLIENT_MESSAGE, _elm_win_client_message, win); +#endif + } + else if (ENGINE_COMPARE(ELM_XRENDER_X11)) + { + win->ee = ecore_evas_xrender_x11_new(NULL, 0, 0, 0, 1, 1); + FALLBACK_TRY("XRender"); +#ifdef HAVE_ELEMENTARY_X + win->client_message_handler = ecore_event_handler_add + (ECORE_X_EVENT_CLIENT_MESSAGE, _elm_win_client_message, win); +#endif + } + else if (ENGINE_COMPARE(ELM_OPENGL_X11)) + { + win->ee = ecore_evas_gl_x11_new(NULL, 0, 0, 0, 1, 1); + FALLBACK_TRY("OpenGL"); +#ifdef HAVE_ELEMENTARY_X + win->client_message_handler = ecore_event_handler_add + (ECORE_X_EVENT_CLIENT_MESSAGE, _elm_win_client_message, win); +#endif + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_WIN32)) + { + win->ee = ecore_evas_software_gdi_new(NULL, 0, 0, 1, 1); + FALLBACK_TRY("Sofware Win32"); + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_16_WINCE)) + { + win->ee = ecore_evas_software_wince_gdi_new(NULL, 0, 0, 1, 1); + FALLBACK_TRY("Sofware-16-WinCE"); + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_SDL)) + { + win->ee = ecore_evas_sdl_new(NULL, 0, 0, 0, 0, 0, 1); + FALLBACK_TRY("Sofware SDL"); + } + else if (ENGINE_COMPARE(ELM_SOFTWARE_16_SDL)) + { + win->ee = ecore_evas_sdl16_new(NULL, 0, 0, 0, 0, 0, 1); + FALLBACK_TRY("Sofware-16-SDL"); + } + else if (ENGINE_COMPARE(ELM_OPENGL_SDL)) + { + win->ee = ecore_evas_gl_sdl_new(NULL, 1, 1, 0, 0); + FALLBACK_TRY("OpenGL SDL"); + } +#undef FALLBACK_TRY + + if (!win->ee) + { + ERR("Cannot create window."); + free(win); + return NULL; + } +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); +#endif + if ((_elm_config->bgpixmap) && (!_elm_config->compositing)) + ecore_evas_avoid_damage_set(win->ee, ECORE_EVAS_AVOID_DAMAGE_EXPOSE); +// bg pixmap done by x - has other issues like can be redrawn by x before it +// is filled/ready by app +// ecore_evas_avoid_damage_set(win->ee, ECORE_EVAS_AVOID_DAMAGE_BUILT_IN); + + win->type = type; + win->parent = parent; + if (win->parent) + evas_object_event_callback_add(win->parent, EVAS_CALLBACK_DEL, + _elm_win_obj_callback_parent_del, win); + + win->evas = ecore_evas_get(win->ee); + win->win_obj = elm_widget_add(win->evas); + elm_widget_type_set(win->win_obj, "win"); + ELM_SET_WIDTYPE(widtype, "win"); + elm_widget_data_set(win->win_obj, win); + elm_widget_event_hook_set(win->win_obj, _elm_win_event_cb); + elm_widget_on_focus_hook_set(win->win_obj, _elm_win_on_focus_hook, NULL); + elm_widget_can_focus_set(win->win_obj, EINA_TRUE); + elm_widget_highlight_ignore_set(win->win_obj, EINA_TRUE); + elm_widget_focus_next_hook_set(win->win_obj, _elm_win_focus_next_hook); + evas_object_color_set(win->win_obj, 0, 0, 0, 0); + evas_object_move(win->win_obj, 0, 0); + evas_object_resize(win->win_obj, 1, 1); + evas_object_layer_set(win->win_obj, 50); + evas_object_pass_events_set(win->win_obj, EINA_TRUE); + + evas_object_intercept_show_callback_add(win->win_obj, + _elm_win_obj_intercept_show, win); + ecore_evas_object_associate(win->ee, win->win_obj, + ECORE_EVAS_OBJECT_ASSOCIATE_BASE | + ECORE_EVAS_OBJECT_ASSOCIATE_STACK | + ECORE_EVAS_OBJECT_ASSOCIATE_LAYER); + evas_object_event_callback_add(win->win_obj, EVAS_CALLBACK_SHOW, + _elm_win_obj_callback_show, win); + evas_object_event_callback_add(win->win_obj, EVAS_CALLBACK_DEL, + _elm_win_obj_callback_del, win); + + ecore_evas_name_class_set(win->ee, name, _elm_appname); + ecore_evas_callback_delete_request_set(win->ee, _elm_win_delete_request); + ecore_evas_callback_resize_set(win->ee, _elm_win_resize); + ecore_evas_callback_focus_in_set(win->ee, _elm_win_focus_in); + ecore_evas_callback_focus_out_set(win->ee, _elm_win_focus_out); + ecore_evas_callback_move_set(win->ee, _elm_win_move); + evas_image_cache_set(win->evas, (_elm_config->image_cache * 1024)); + evas_font_cache_set(win->evas, (_elm_config->font_cache * 1024)); + EINA_LIST_FOREACH(_elm_config->font_dirs, l, fontpath) + evas_font_path_append(win->evas, fontpath); + if (!_elm_config->font_hinting) + evas_font_hinting_set(win->evas, EVAS_FONT_HINTING_NONE); + else if (_elm_config->font_hinting == 1) + evas_font_hinting_set(win->evas, EVAS_FONT_HINTING_AUTO); + else if (_elm_config->font_hinting == 2) + evas_font_hinting_set(win->evas, EVAS_FONT_HINTING_BYTECODE); + +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif + + _elm_win_list = eina_list_append(_elm_win_list, win->win_obj); + + if (ENGINE_COMPARE(ELM_SOFTWARE_FB)) + { + ecore_evas_fullscreen_set(win->ee, 1); + } +#undef ENGINE_COMPARE + + if (_elm_config->focus_highlight_enable) + elm_win_focus_highlight_enabled_set(win->win_obj, EINA_TRUE); + +#ifdef ELM_DEBUG + Evas_Modifier_Mask mask = evas_key_modifier_mask_get(win->evas, "Control"); + evas_object_event_callback_add(win->win_obj, EVAS_CALLBACK_KEY_DOWN, + _debug_key_down, win); + Eina_Bool ret = evas_object_key_grab(win->win_obj, "F12", mask, 0, EINA_TRUE); + printf("Key F12 exclusive for dot tree generation. (%d)\n", ret); +#endif + return win->win_obj; +} + +/** + * Add @p subobj as a resize object of window @p obj. + * + * @param obj The window object + * @param subobj The resize object to add + * + * @ingroup Win + */ +EAPI void +elm_win_resize_object_add(Evas_Object *obj, Evas_Object *subobj) +{ + Evas_Coord w, h; + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + win->subobjs = eina_list_append(win->subobjs, subobj); + elm_widget_sub_object_add(obj, subobj); + evas_object_event_callback_add(subobj, EVAS_CALLBACK_DEL, + _elm_win_subobj_callback_del, obj); + evas_object_event_callback_add(subobj, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _elm_win_subobj_callback_changed_size_hints, + obj); + ecore_evas_geometry_get(win->ee, NULL, NULL, &w, &h); + evas_object_move(subobj, 0, 0); + evas_object_resize(subobj, w, h); + _elm_win_eval_subobjs(obj); +} + +/** + * Delete @p subobj as a resize object of window @p obj. + * + * @param obj The window object + * @param subobj The resize object to add + * + * @ingroup Win + */ +EAPI void +elm_win_resize_object_del(Evas_Object *obj, Evas_Object *subobj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + evas_object_event_callback_del_full(subobj, + EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _elm_win_subobj_callback_changed_size_hints, + obj); + evas_object_event_callback_del_full(subobj, EVAS_CALLBACK_DEL, + _elm_win_subobj_callback_del, obj); + win->subobjs = eina_list_remove(win->subobjs, subobj); + elm_widget_sub_object_del(obj, subobj); + _elm_win_eval_subobjs(obj); +} + +/** + * Set the title of the window + * + * @param obj The window object + * @param title The title to set + * + * @ingroup Win + */ +EAPI void +elm_win_title_set(Evas_Object *obj, const char *title) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_title_set(win->ee, title); +} + +/** + * Get the title of the window + * + * @param obj The window object + * @return The title + * + * @ingroup Win + */ +EAPI const char * +elm_win_title_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + win = elm_widget_data_get(obj); + if (!win) return NULL; + return ecore_evas_title_get(win->ee); +} + +/** + * Set the window's autodel state. + * + * @param obj The window object + * @param autodel If true, the window will automatically delete itself when closed + * + * @ingroup Win + */ +EAPI void +elm_win_autodel_set(Evas_Object *obj, Eina_Bool autodel) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + win->autodel = autodel; +} + +/** + * Get the window's autodel state. + * + * @param obj The window object + * @return If the window will automatically delete itself when closed + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_autodel_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + return win->autodel; +} + +/** + * Activate a window object. + * + * @param obj The window object + * + * @ingroup Win + */ +EAPI void +elm_win_activate(Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_activate(win->ee); +} + +/** + * Lower a window object. + * + * @param obj The window object + * + * @ingroup Win + */ +EAPI void +elm_win_lower(Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_lower(win->ee); +} + +/** + * Raise a window object. + * + * @param obj The window object + * + * @ingroup Win + */ +EAPI void +elm_win_raise(Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_raise(win->ee); +} + +/** + * Set the borderless state of a window. + * + * @param obj The window object + * @param borderless If true, the window is borderless + * + * @ingroup Win + */ +EAPI void +elm_win_borderless_set(Evas_Object *obj, Eina_Bool borderless) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_borderless_set(win->ee, borderless); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif +} + +/** + * Get the borderless state of a window. + * + * @param obj The window object + * @return If true, the window is borderless + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_borderless_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + return ecore_evas_borderless_get(win->ee); +} + +/** + * Set the shaped state of a window. + * + * @param obj The window object + * @param shaped If true, the window is shaped + * + * @ingroup Win + */ +EAPI void +elm_win_shaped_set(Evas_Object *obj, Eina_Bool shaped) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_shaped_set(win->ee, shaped); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif +} + +/** + * Get the shaped state of a window. + * + * @param obj The window object + * @return If true, the window is shaped + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_shaped_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + return ecore_evas_shaped_get(win->ee); +} + +/** + * Set the alpha channel state of a window. + * + * @param obj The window object + * @param alpha If true, the window has an alpha channel + * + * @ingroup Win + */ +EAPI void +elm_win_alpha_set(Evas_Object *obj, Eina_Bool alpha) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; +#ifdef HAVE_ELEMENTARY_X + if (win->xwin) + { + if (alpha) + { + if (!_elm_config->compositing) + elm_win_shaped_set(obj, alpha); + else + ecore_evas_alpha_set(win->ee, alpha); + } + else + ecore_evas_alpha_set(win->ee, alpha); + _elm_win_xwin_update(win); + } + else +#endif + ecore_evas_alpha_set(win->ee, alpha); +} + +/** + * Get the alpha channel state of a window. + * + * @param obj The window object + * @return If true, the window has an alpha channel + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_alpha_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + return ecore_evas_alpha_get(win->ee); +} + +/** + * Set the transparency state of a window. + * + * @param obj The window object + * @param transparent If true, the window is transparent + * + * @ingroup Win + */ +EAPI void +elm_win_transparent_set(Evas_Object *obj, Eina_Bool transparent) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + +#ifdef HAVE_ELEMENTARY_X + if (win->xwin) + { + ecore_evas_transparent_set(win->ee, transparent); + _elm_win_xwin_update(win); + } + else +#endif + ecore_evas_transparent_set(win->ee, transparent); +} + +/** + * Get the transparency state of a window. + * + * @param obj The window object + * @return If true, the window is transparent + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_transparent_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + + return ecore_evas_transparent_get(win->ee); +} + +/** + * Set the override state of a window. + * + * @param obj The window object + * @param override If true, the window is overridden + * + * @ingroup Win + */ +EAPI void +elm_win_override_set(Evas_Object *obj, Eina_Bool override) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_override_set(win->ee, override); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif +} + +/** + * Get the override state of a window. + * + * @param obj The window object + * @return If true, the window is overridden + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_override_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + return ecore_evas_override_get(win->ee); +} + +/** + * Set the fullscreen state of a window. + * + * @param obj The window object + * @param fullscreen If true, the window is fullscreen + * + * @ingroup Win + */ +EAPI void +elm_win_fullscreen_set(Evas_Object *obj, Eina_Bool fullscreen) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_FB) || + ENGINE_COMPARE(ELM_SOFTWARE_16_WINCE)) + { + // these engines... can ONLY be fullscreen + return; + } + else + { + ecore_evas_fullscreen_set(win->ee, fullscreen); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif + } +#undef ENGINE_COMPARE +} + +/** + * Get the fullscreen state of a window. + * + * @param obj The window object + * @return If true, the window is fullscreen + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_fullscreen_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + +#define ENGINE_COMPARE(name) (!strcmp(_elm_config->engine, name)) + if (ENGINE_COMPARE(ELM_SOFTWARE_FB) || + ENGINE_COMPARE(ELM_SOFTWARE_16_WINCE)) + { + // these engines... can ONLY be fullscreen + return EINA_TRUE; + } + else + { + return ecore_evas_fullscreen_get(win->ee); + } +#undef ENGINE_COMPARE +} + +/** + * Set the maximized state of a window. + * + * @param obj The window object + * @param maximized If true, the window is maximized + * + * @ingroup Win + */ +EAPI void +elm_win_maximized_set(Evas_Object *obj, Eina_Bool maximized) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_maximized_set(win->ee, maximized); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif +} + +/** + * Get the maximized state of a window. + * + * @param obj The window object + * @return If true, the window is maximized + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_maximized_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + return ecore_evas_maximized_get(win->ee); +} + +/** + * Set the iconified state of a window. + * + * @param obj The window object + * @param iconified If true, the window is iconified + * + * @ingroup Win + */ +EAPI void +elm_win_iconified_set(Evas_Object *obj, Eina_Bool iconified) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_iconified_set(win->ee, iconified); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif +} + +/** + * Get the iconified state of a window. + * + * @param obj The window object + * @return If true, the window is iconified + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_iconified_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + return ecore_evas_iconified_get(win->ee); +} + +/** + * Set the layer of the window. + * + * @param obj The window object + * @param layer The layer of the window + * + * @ingroup Win + */ +EAPI void +elm_win_layer_set(Evas_Object *obj, int layer) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_layer_set(win->ee, layer); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif +} + +/** + * Get the layer of the window. + * + * @param obj The window object + * @return The layer of the window + * + * @ingroup Win + */ +EAPI int +elm_win_layer_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) -1; + win = elm_widget_data_get(obj); + if (!win) return -1; + return ecore_evas_layer_get(win->ee); +} + +/** + * Set the rotation of the window. + * + * @param obj The window object + * @param rotation The rotation of the window, in degrees (0-360) + * + * @ingroup Win + */ +EAPI void +elm_win_rotation_set(Evas_Object *obj, int rotation) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + if (win->rot == rotation) return; + win->rot = rotation; + ecore_evas_rotation_set(win->ee, rotation); + evas_object_size_hint_min_set(obj, -1, -1); + evas_object_size_hint_max_set(obj, -1, -1); + _elm_win_eval_subobjs(obj); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif +} + +/** + * Rotates the window and resizes it + * + * @param obj The window object + * @param layer The rotation of the window in degrees (0-360) + * + * @ingroup Win + */ +EAPI void +elm_win_rotation_with_resize_set(Evas_Object *obj, int rotation) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + if (win->rot == rotation) return; + win->rot = rotation; + ecore_evas_rotation_with_resize_set(win->ee, rotation); + evas_object_size_hint_min_set(obj, -1, -1); + evas_object_size_hint_max_set(obj, -1, -1); + _elm_win_eval_subobjs(obj); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif +} + +/** + * Get the rotation of the window. + * + * @param obj The window object + * @return The rotation of the window in degrees (0-360) + * + * @ingroup Win + */ +EAPI int +elm_win_rotation_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) -1; + win = elm_widget_data_get(obj); + if (!win) return -1; + return win->rot; +} + +/** + * Set the sticky state of the window. + * + * @param obj The window object + * @param sticky If true, the window's sticky state is enabled + * + * @ingroup Win + */ +EAPI void +elm_win_sticky_set(Evas_Object *obj, Eina_Bool sticky) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + ecore_evas_sticky_set(win->ee, sticky); +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwin_update(win); +#endif +} + +/** + * Get the sticky state of the window. + * + * @param obj The window object + * @return If true, the window's sticky state is enabled + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_sticky_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; + return ecore_evas_sticky_get(win->ee); +} + +/** + * Sets the keyboard mode of the window. + * + * @param obj The window object + * @param mode The mode to set; one of: + * ELM_WIN_KEYBOARD_UNKNOWN + * ELM_WIN_KEYBOARD_OFF + * ELM_WIN_KEYBOARD_ON + * ELM_WIN_KEYBOARD_ALPHA + * ELM_WIN_KEYBOARD_NUMERIC + * ELM_WIN_KEYBOARD_PIN + * ELM_WIN_KEYBOARD_PHONE_NUMBER + * ELM_WIN_KEYBOARD_HEX + * ELM_WIN_KEYBOARD_TERMINAL + * ELM_WIN_KEYBOARD_PASSWORD + * ELM_WIN_KEYBOARD_IP + * ELM_WIN_KEYBOARD_HOST + * ELM_WIN_KEYBOARD_FILE + * ELM_WIN_KEYBOARD_URL + * ELM_WIN_KEYBOARD_KEYPAD + * ELM_WIN_KEYBOARD_J2ME + * + * @ingroup Win + */ +EAPI void +elm_win_keyboard_mode_set(Evas_Object *obj, Elm_Win_Keyboard_Mode mode) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + if (mode == win->kbdmode) return; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); +#endif + win->kbdmode = mode; +#ifdef HAVE_ELEMENTARY_X + if (win->xwin) + ecore_x_e_virtual_keyboard_state_set + (win->xwin, (Ecore_X_Virtual_Keyboard_State)win->kbdmode); +#endif +} + +/** + * Gets the keyboard mode of the window. + * + * @param obj The window object + * @return The mode; one of: + * ELM_WIN_KEYBOARD_UNKNOWN + * ELM_WIN_KEYBOARD_OFF + * ELM_WIN_KEYBOARD_ON + * ELM_WIN_KEYBOARD_ALPHA + * ELM_WIN_KEYBOARD_NUMERIC + * ELM_WIN_KEYBOARD_PIN + * ELM_WIN_KEYBOARD_PHONE_NUMBER + * ELM_WIN_KEYBOARD_HEX + * ELM_WIN_KEYBOARD_TERMINAL + * ELM_WIN_KEYBOARD_PASSWORD + * ELM_WIN_KEYBOARD_IP + * ELM_WIN_KEYBOARD_HOST + * ELM_WIN_KEYBOARD_FILE + * ELM_WIN_KEYBOARD_URL + * ELM_WIN_KEYBOARD_KEYPAD + * ELM_WIN_KEYBOARD_J2ME + * + * @ingroup Win + */ +EAPI Elm_Win_Keyboard_Mode +elm_win_keyboard_mode_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) ELM_WIN_KEYBOARD_UNKNOWN; + win = elm_widget_data_get(obj); + if (!win) return ELM_WIN_KEYBOARD_UNKNOWN; + return win->kbdmode; +} + +/** + * Sets whether the window is a keyboard. + * + * @param obj The window object + * @param is_keyboard If true, the window is a virtual keyboard + * + * @ingroup Win + */ +EAPI void +elm_win_keyboard_win_set(Evas_Object *obj, Eina_Bool is_keyboard) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + ecore_x_e_virtual_keyboard_set(win->xwin, is_keyboard); +#endif +} + +/** + * Gets whether the window is a keyboard. + * + * @param obj The window object + * @return If the window is a virtual keyboard + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_keyboard_win_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + return ecore_x_e_virtual_keyboard_get(win->xwin); +#endif + return EINA_FALSE; +} + +/** + * Get the screen position of a window. + * + * @param obj The window object + * @param x The int to store the x coordinate to + * @param y The int to store the y coordinate to + * + * @ingroup Win + */ +EAPI void +elm_win_screen_position_get(const Evas_Object *obj, int *x, int *y) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; + if (x) *x = win->screen.x; + if (y) *y = win->screen.y; +} + +/** + * Set if this window is an illume conformant window + * + * @param obj The window object + * @param conformant The conformant flag (1 = conformant, 0 = non-conformant) + * + * @ingroup Win + */ +EAPI void +elm_win_conformant_set(Evas_Object *obj, Eina_Bool conformant) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + ecore_x_e_illume_conformant_set(win->xwin, conformant); +#endif +} + +/** + * Get if this window is an illume conformant window + * + * @param obj The window object + * @return A boolean if this window is illume conformant or not + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_conformant_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + return ecore_x_e_illume_conformant_get(win->xwin); +#endif + return EINA_FALSE; +} + +/** + * Set a window to be an illume quickpanel window + * + * By default window objects are not quickpanel windows. + * + * @param obj The window object + * @param quickpanel The quickpanel flag (1 = quickpanel, 0 = normal window) + * + * @ingroup Win + */ +EAPI void +elm_win_quickpanel_set(Evas_Object *obj, Eina_Bool quickpanel) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + { + ecore_x_e_illume_quickpanel_set(win->xwin, quickpanel); + if (quickpanel) + { + Ecore_X_Window_State states[2]; + + states[0] = ECORE_X_WINDOW_STATE_SKIP_TASKBAR; + states[1] = ECORE_X_WINDOW_STATE_SKIP_PAGER; + ecore_x_netwm_window_state_set(win->xwin, states, 2); + ecore_x_icccm_hints_set(win->xwin, 0, 0, 0, 0, 0, 0, 0); + } + } +#endif +} + +/** + * Get if this window is a quickpanel or not + * + * @param obj The window object + * @return A boolean if this window is a quickpanel or not + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_quickpanel_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + win = elm_widget_data_get(obj); + if (!win) return EINA_FALSE; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + return ecore_x_e_illume_quickpanel_get(win->xwin); +#endif + return EINA_FALSE; +} + +/** + * Set the major priority of a quickpanel window + * + * @param obj The window object + * @param priority The major priority for this quickpanel + * + * @ingroup Win + */ +EAPI void +elm_win_quickpanel_priority_major_set(Evas_Object *obj, int priority) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + ecore_x_e_illume_quickpanel_priority_major_set(win->xwin, priority); +#endif +} + +/** + * Get the major priority of a quickpanel window + * + * @param obj The window object + * @return The major priority of this quickpanel + * + * @ingroup Win + */ +EAPI int +elm_win_quickpanel_priority_major_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) -1; + win = elm_widget_data_get(obj); + if (!win) return -1; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + return ecore_x_e_illume_quickpanel_priority_major_get(win->xwin); +#endif + return -1; +} + +/** + * Set the minor priority of a quickpanel window + * + * @param obj The window object + * @param priority The minor priority for this quickpanel + * + * @ingroup Win + */ +EAPI void +elm_win_quickpanel_priority_minor_set(Evas_Object *obj, int priority) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + ecore_x_e_illume_quickpanel_priority_minor_set(win->xwin, priority); +#endif +} + +/** + * Get the minor priority of a quickpanel window + * + * @param obj The window object + * @return The minor priority of this quickpanel + * + * @ingroup Win + */ +EAPI int +elm_win_quickpanel_priority_minor_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) -1; + win = elm_widget_data_get(obj); + if (!win) return -1; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + return ecore_x_e_illume_quickpanel_priority_minor_get(win->xwin); +#endif + return -1; +} + +/** + * Set which zone this quickpanel should appear in + * + * @param obj The window object + * @param zone The requested zone for this quickpanel + * + * @ingroup Win + */ +EAPI void +elm_win_quickpanel_zone_set(Evas_Object *obj, int zone) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype); + win = elm_widget_data_get(obj); + if (!win) return; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + ecore_x_e_illume_quickpanel_zone_set(win->xwin, zone); +#endif +} + +/** + * Get which zone this quickpanel should appear in + * + * @param obj The window object + * @return The requested zone for this quickpanel + * + * @ingroup Win + */ +EAPI int +elm_win_quickpanel_zone_get(const Evas_Object *obj) +{ + Elm_Win *win; + ELM_CHECK_WIDTYPE(obj, widtype) 0; + win = elm_widget_data_get(obj); + if (!win) return 0; +#ifdef HAVE_ELEMENTARY_X + _elm_win_xwindow_get(win); + if (win->xwin) + return ecore_x_e_illume_quickpanel_zone_get(win->xwin); +#endif + return 0; +} + +/** + * Set the enabled status for the focus highlight in a window + * + * This function will enable or disable the focus highlight only for the + * given window, regardless of the global setting for it + * + * @param obj The window where to enable the highlight + * @param enabled The enabled value for the highlight + * + * @ingroup Win + */ +EAPI void +elm_win_focus_highlight_enabled_set(Evas_Object *obj, Eina_Bool enabled) +{ + Elm_Win *win; + + ELM_CHECK_WIDTYPE(obj, widtype); + + win = elm_widget_data_get(obj); + enabled = !!enabled; + if (win->focus_highlight.enabled == enabled) + return; + + win->focus_highlight.enabled = enabled; + + if (win->focus_highlight.enabled) + _elm_win_focus_highlight_init(win); + else + _elm_win_focus_highlight_shutdown(win); +} + +/** + * Get the enabled value of the focus highlight for this window + * + * @param obj The window in which to check if the focus highlight is enabled + * + * @return EINA_TRUE if enabled, EINA_FALSE otherwise + * + * @ingroup Win + */ +EAPI Eina_Bool +elm_win_focus_highlight_enabled_get(const Evas_Object *obj) +{ + Elm_Win *win; + + ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE; + + win = elm_widget_data_get(obj); + return win->focus_highlight.enabled; +} + +/** + * Set the style for the focus highlight on this window + * + * Sets the style to use for theming the highlight of focused objects on + * the given window. If @p style is NULL, the default will be used. + * + * @param obj The window where to set the style + * @param style The style to set + * + * @ingroup Win + */ +EAPI void +elm_win_focus_highlight_style_set(Evas_Object *obj, const char *style) +{ + Elm_Win *win; + + ELM_CHECK_WIDTYPE(obj, widtype); + + win = elm_widget_data_get(obj); + eina_stringshare_replace(&win->focus_highlight.style, style); + win->focus_highlight.changed_theme = EINA_TRUE; + _elm_win_focus_highlight_reconfigure_job_start(win); +} + +/** + * Get the style set for the focus highlight object + * + * Gets the style set for this windows highilght object, or NULL if none + * is set. + * + * @param obj The window to retrieve the highlights style from + * + * @return The style set or NULL if none was. Default is used in that case. + * + * @ingroup Win + */ +EAPI const char * +elm_win_focus_highlight_style_get(const Evas_Object *obj) +{ + Elm_Win *win; + + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + + win = elm_widget_data_get(obj); + return win->focus_highlight.style; +} + +typedef struct _Widget_Data Widget_Data; + +struct _Widget_Data +{ + Evas_Object *frm; + Evas_Object *content; +}; + +static void _del_hook(Evas_Object *obj); +static void _theme_hook(Evas_Object *obj); +static void _sizing_eval(Evas_Object *obj); +static void _changed_size_hints(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _sub_del(void *data, Evas_Object *obj, void *event_info); + +static const char *widtype2 = NULL; + +static void +_del_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + free(wd); +} + +static void +_theme_hook(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + _elm_theme_object_set(obj, wd->frm, "win", "inwin", elm_widget_style_get(obj)); + if (wd->content) + edje_object_part_swallow(wd->frm, "elm.swallow.content", wd->content); + _sizing_eval(obj); +} + +static Eina_Bool +_elm_inwin_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next) +{ + Widget_Data *wd = elm_widget_data_get(obj); + + if (!wd) + return EINA_FALSE; + + /* Try Focus cycle in subitem */ + if (wd->content) + { + elm_widget_focus_next_get(wd->content, dir, next); + if (*next) + return EINA_TRUE; + } + + *next = (Evas_Object *)obj; + return EINA_FALSE; +} + +static void +_sizing_eval(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord minw = -1, minh = -1; + + evas_object_size_hint_min_get(wd->content, &minw, &minh); + edje_object_size_min_calc(wd->frm, &minw, &minh); + evas_object_size_hint_min_set(obj, minw, minh); + evas_object_size_hint_max_set(obj, -1, -1); +} + +static void +_changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _sizing_eval(data); +} + +static void +_sub_del(void *data __UNUSED__, Evas_Object *obj, void *event_info) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Object *sub = event_info; + if (sub == wd->content) + { + evas_object_event_callback_del_full + (sub, EVAS_CALLBACK_CHANGED_SIZE_HINTS, _changed_size_hints, obj); + wd->content = NULL; + _sizing_eval(obj); + } +} + +/** + * @defgroup Inwin Inwin + * + * An inwin is a window inside a window that is useful for a quick popup. It does not hover. + */ +EAPI Evas_Object * +elm_win_inwin_add(Evas_Object *obj) +{ + Evas_Object *obj2; + Widget_Data *wd; + Elm_Win *win; + + ELM_CHECK_WIDTYPE(obj, widtype) NULL; + win = elm_widget_data_get(obj); + if (!win) return NULL; + wd = ELM_NEW(Widget_Data); + obj2 = elm_widget_add(win->evas); + elm_widget_type_set(obj2, "inwin"); + ELM_SET_WIDTYPE(widtype2, "inwin"); + elm_widget_sub_object_add(obj, obj2); + evas_object_size_hint_weight_set(obj2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(obj2, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_win_resize_object_add(obj, obj2); + + elm_widget_data_set(obj2, wd); + elm_widget_del_hook_set(obj2, _del_hook); + elm_widget_theme_hook_set(obj2, _theme_hook); + elm_widget_focus_next_hook_set(obj2, _elm_inwin_focus_next_hook); + elm_widget_can_focus_set(obj2, EINA_TRUE); + elm_widget_highlight_ignore_set(obj2, EINA_TRUE); + + wd->frm = edje_object_add(win->evas); + _elm_theme_object_set(obj, wd->frm, "win", "inwin", "default"); + elm_widget_resize_object_set(obj2, wd->frm); + + evas_object_smart_callback_add(obj2, "sub-object-del", _sub_del, obj2); + + _sizing_eval(obj2); + return obj2; +} + +/** + * Activates an inwin object + * + * @param obj The inwin to activate + * + * @ingroup Inwin + */ +EAPI void +elm_win_inwin_activate(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype2); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + evas_object_raise(obj); + evas_object_show(obj); + edje_object_signal_emit(wd->frm, "elm,action,show", "elm"); + elm_object_focus(obj); +} + +/** + * Set the content of an inwin object. + * + * Once the content object is set, a previously set one will be deleted. + * If you want to keep that old content object, use the + * elm_win_inwin_content_unset() function. + * + * @param obj The inwin object + * @param content The object to set as content + * + * @ingroup Inwin + */ +EAPI void +elm_win_inwin_content_set(Evas_Object *obj, Evas_Object *content) +{ + ELM_CHECK_WIDTYPE(obj, widtype2); + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return; + if (wd->content == content) return; + if (wd->content) evas_object_del(wd->content); + wd->content = content; + if (content) + { + elm_widget_sub_object_add(obj, content); + evas_object_event_callback_add(content, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _changed_size_hints, obj); + edje_object_part_swallow(wd->frm, "elm.swallow.content", content); + } + _sizing_eval(obj); +} + +/** + * Get the content of an inwin object. + * + * Return the content object which is set for this widget. + * + * @param obj The inwin object + * @return The content that is being used + * + * @ingroup Inwin + */ +EAPI Evas_Object * +elm_win_inwin_content_get(const Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype2) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + return wd->content; +} + +/** + * Unset the content of an inwin object. + * + * Unparent and return the content object which was set for this widget. + * + * @param obj The inwin object + * @return The content that was being used + * + * @ingroup Inwin + */ +EAPI Evas_Object * +elm_win_inwin_content_unset(Evas_Object *obj) +{ + ELM_CHECK_WIDTYPE(obj, widtype2) NULL; + Widget_Data *wd = elm_widget_data_get(obj); + if (!wd) return NULL; + if (!wd->content) return NULL; + Evas_Object *content = wd->content; + elm_widget_sub_object_del(obj, wd->content); + edje_object_part_unswallow(wd->frm, wd->content); + wd->content = NULL; + return content; +} + +/* windowing spcific calls - shall we do this differently? */ +/** + * Get the Ecore_X_Window of an Evas_Object + * + * @param obj The object + * + * @return The Ecore_X_Window of @p obj + * + * @ingroup Win + */ +EAPI Ecore_X_Window +elm_win_xwindow_get(const Evas_Object *obj) +{ + Ecore_X_Window xwin = 0; + Ecore_Evas *ee = NULL; + if (!obj) return 0; +#ifdef HAVE_ELEMENTARY_X + ee = ecore_evas_ecore_evas_get(evas_object_evas_get(obj)); + if (ee) xwin = (Ecore_X_Window)ecore_evas_window_get(ee); + return xwin; +#else + return 0; +#endif +} diff --git a/src/lib/els_box.c b/src/lib/els_box.c new file mode 100644 index 0000000..46b47aa --- /dev/null +++ b/src/lib/els_box.c @@ -0,0 +1,220 @@ +#include +#include "elm_priv.h" + +static void +_smart_extents_calculate(Evas_Object *box, Evas_Object_Box_Data *priv, int horizontal, int homogeneous) +{ + Evas_Coord minw, minh, mnw, mnh; + const Eina_List *l; + Evas_Object_Box_Option *opt; + + /* FIXME: need to calc max */ + minw = 0; + minh = 0; + if (homogeneous) + { + EINA_LIST_FOREACH(priv->children, l, opt) + { + evas_object_size_hint_min_get(opt->obj, &mnw, &mnh); + if (minh < mnh) minh = mnh; + if (minw < mnw) minw = mnw; + } + if (horizontal) + minw *= eina_list_count(priv->children); + else + minh *= eina_list_count(priv->children); + } + else + { + EINA_LIST_FOREACH(priv->children, l, opt) + { + evas_object_size_hint_min_get(opt->obj, &mnw, &mnh); + if (horizontal) + { + if (minh < mnh) minh = mnh; + minw += mnw; + } + else + { + if (minw < mnw) minw = mnw; + minh += mnh; + } + } + } + evas_object_size_hint_min_set(box, minw, minh); +} + +void +_els_box_layout(Evas_Object *o, Evas_Object_Box_Data *priv, int horizontal, int homogeneous) +{ + Evas_Coord x, y, w, h, xx, yy; + const Eina_List *l; + Evas_Object *obj; + Evas_Coord minw, minh, wdif, hdif; + int count = 0, expand = 0; + double ax, ay; + Evas_Object_Box_Option *opt; + + _smart_extents_calculate(o, priv, horizontal, homogeneous); + + evas_object_geometry_get(o, &x, &y, &w, &h); + + evas_object_size_hint_min_get(o, &minw, &minh); + evas_object_size_hint_align_get(o, &ax, &ay); + count = eina_list_count(priv->children); + if (w < minw) + { + x = x + ((w - minw) * (1.0 - ax)); + w = minw; + } + if (h < minh) + { + y = y + ((h - minh) * (1.0 - ay)); + h = minh; + } + EINA_LIST_FOREACH(priv->children, l, opt) + { + double wx, wy; + + evas_object_size_hint_weight_get(opt->obj, &wx, &wy); + if (horizontal) + { + if (wx > 0.0) expand++; + } + else + { + if (wy > 0.0) expand++; + } + } + if (!expand) + { + evas_object_size_hint_align_get(o, &ax, &ay); + if (horizontal) + { + x += (double)(w - minw) * ax; + w = minw; + } + else + { + y += (double)(h - minh) * ay; + h = minh; + } + } + wdif = w - minw; + hdif = h - minh; + xx = x; + yy = y; + EINA_LIST_FOREACH(priv->children, l, opt) + { + Evas_Coord mnw, mnh, mxw, mxh; + double wx, wy; + int fw, fh, xw, xh; + + obj = opt->obj; + evas_object_size_hint_align_get(obj, &ax, &ay); + evas_object_size_hint_weight_get(obj, &wx, &wy); + evas_object_size_hint_min_get(obj, &mnw, &mnh); + evas_object_size_hint_max_get(obj, &mxw, &mxh); + fw = fh = 0; + xw = xh = 0; + if (ax == -1.0) {fw = 1; ax = 0.5;} + if (ay == -1.0) {fh = 1; ay = 0.5;} + if (wx > 0.0) xw = 1; + if (wy > 0.0) xh = 1; + if (horizontal) + { + if (homogeneous) + { + Evas_Coord ww, hh, ow, oh; + + ww = (w / (Evas_Coord)count); + hh = h; + ow = mnw; + if (fw) ow = ww; + if ((mxw >= 0) && (mxw < ow)) + ow = mxw; + oh = mnh; + if (fh) oh = hh; + if ((mxh >= 0) && (mxh < oh)) + oh = mxh; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * ax), + yy + (Evas_Coord)(((double)(hh - oh)) * ay)); + evas_object_resize(obj, ow, oh); + xx += ww; + } + else + { + Evas_Coord ww, hh, ow, oh; + + ww = mnw; + if ((expand > 0) && (xw)) + { + if (expand == 1) ow = wdif; + else ow = (w - minw) / expand; + wdif -= ow; + ww += ow; + } + hh = h; + ow = mnw; + if (fw) ow = ww; + if ((mxw >= 0) && (mxw < ow)) ow = mxw; + oh = mnh; + if (fh) oh = hh; + if ((mxh >= 0) && (mxh < oh)) oh = mxh; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * ax), + yy + (Evas_Coord)(((double)(hh - oh)) * ay)); + evas_object_resize(obj, ow, oh); + xx += ww; + } + } + else + { + if (homogeneous) + { + Evas_Coord ww, hh, ow, oh; + + ww = w; + hh = (h / (Evas_Coord)count); + ow = mnw; + if (fw) ow = ww; + if ((mxw >= 0) && (mxw < ow)) ow = mxw; + oh = mnh; + if (fh) oh = hh; + if ((mxh >= 0) && (mxh < oh)) oh = mxh; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * ax), + yy + (Evas_Coord)(((double)(hh - oh)) * ay)); + evas_object_resize(obj, ow, oh); + yy += hh; + } + else + { + Evas_Coord ww, hh, ow, oh; + + ww = w; + hh = mnh; + if ((expand > 0) && (xh)) + { + if (expand == 1) oh = hdif; + else oh = (h - minh) / expand; + hdif -= oh; + hh += oh; + } + ow = mnw; + if (fw) ow = ww; + if ((mxw >= 0) && (mxw < ow)) ow = mxw; + oh = mnh; + if (fh) oh = hh; + if ((mxh >= 0) && (mxh < oh)) oh = mxh; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * ax), + yy + (Evas_Coord)(((double)(hh - oh)) * ay)); + evas_object_resize(obj, ow, oh); + yy += hh; + } + } + } +} + diff --git a/src/lib/els_box.h b/src/lib/els_box.h new file mode 100644 index 0000000..e394884 --- /dev/null +++ b/src/lib/els_box.h @@ -0,0 +1 @@ +void _els_box_layout(Evas_Object *o, Evas_Object_Box_Data *priv, int horizontal, int homogeneous); diff --git a/src/lib/els_cursor.c b/src/lib/els_cursor.c new file mode 100644 index 0000000..45b0ed1 --- /dev/null +++ b/src/lib/els_cursor.c @@ -0,0 +1,617 @@ +#include +#include +#include "elm_priv.h" + +#ifdef HAVE_ELEMENTARY_X +#include +#include +#endif + +/** + * @defgroup Cursors Cursors + * + * The Cursor is an internal smart object used to customize the + * cursor displayed over objects (or widgets). + * It can use default X cursors (if using X), or cursors from a + * theme. + */ + +#define _cursor_key "_elm_cursor" + +struct _Cursor_Id +{ + const char *name; +#ifdef HAVE_ELEMENTARY_X + int id; +#endif +}; + +#ifdef HAVE_ELEMENTARY_X +#define CURSOR(_name, _xid) \ + {_name , _xid} +# else +#define CURSOR(_name, _xid) \ + {_name} +#endif + +/* Please keep order in sync with Ecore_X_Cursor.h values! */ +struct _Cursor_Id _cursors[] = +{ + CURSOR(ELM_CURSOR_X , ECORE_X_CURSOR_X ), + CURSOR(ELM_CURSOR_ARROW , ECORE_X_CURSOR_ARROW ), + CURSOR(ELM_CURSOR_BASED_ARROW_DOWN , ECORE_X_CURSOR_BASED_ARROW_DOWN ), + CURSOR(ELM_CURSOR_BASED_ARROW_UP , ECORE_X_CURSOR_UP ), + CURSOR(ELM_CURSOR_BOAT , ECORE_X_CURSOR_BOAT ), + CURSOR(ELM_CURSOR_BOGOSITY , ECORE_X_CURSOR_BOGOSITY ), + CURSOR(ELM_CURSOR_BOTTOM_LEFT_CORNER , ECORE_X_CURSOR_BOTTOM_LEFT_CORNER ), + CURSOR(ELM_CURSOR_BOTTOM_RIGHT_CORNER, ECORE_X_CURSOR_BOTTOM_RIGHT_CORNER), + CURSOR(ELM_CURSOR_BOTTOM_SIDE , ECORE_X_CURSOR_BOTTOM_SIDE ), + CURSOR(ELM_CURSOR_BOTTOM_TEE , ECORE_X_CURSOR_BOTTOM_TEE ), + CURSOR(ELM_CURSOR_BOX_SPIRAL , ECORE_X_CURSOR_BOX_SPIRAL ), + CURSOR(ELM_CURSOR_CENTER_PTR , ECORE_X_CURSOR_CENTER_PTR ), + CURSOR(ELM_CURSOR_CIRCLE , ECORE_X_CURSOR_CIRCLE ), + CURSOR(ELM_CURSOR_CLOCK , ECORE_X_CURSOR_CLOCK ), + CURSOR(ELM_CURSOR_COFFEE_MUG , ECORE_X_CURSOR_COFFEE_MUG ), + CURSOR(ELM_CURSOR_CROSS , ECORE_X_CURSOR_CROSS ), + CURSOR(ELM_CURSOR_CROSS_REVERSE , ECORE_X_CURSOR_CROSS_REVERSE ), + CURSOR(ELM_CURSOR_CROSSHAIR , ECORE_X_CURSOR_CROSSHAIR ), + CURSOR(ELM_CURSOR_DIAMOND_CROSS , ECORE_X_CURSOR_DIAMOND_CROSS ), + CURSOR(ELM_CURSOR_DOT , ECORE_X_CURSOR_DOT ), + CURSOR(ELM_CURSOR_DOT_BOX_MASK , ECORE_X_CURSOR_DOT_BOX_MASK ), + CURSOR(ELM_CURSOR_DOUBLE_ARROW , ECORE_X_CURSOR_DOUBLE_ARROW ), + CURSOR(ELM_CURSOR_DRAFT_LARGE , ECORE_X_CURSOR_DRAFT_LARGE ), + CURSOR(ELM_CURSOR_DRAFT_SMALL , ECORE_X_CURSOR_DRAFT_SMALL ), + CURSOR(ELM_CURSOR_DRAPED_BOX , ECORE_X_CURSOR_DRAPED_BOX ), + CURSOR(ELM_CURSOR_EXCHANGE , ECORE_X_CURSOR_EXCHANGE ), + CURSOR(ELM_CURSOR_FLEUR , ECORE_X_CURSOR_FLEUR ), + CURSOR(ELM_CURSOR_GOBBLER , ECORE_X_CURSOR_GOBBLER ), + CURSOR(ELM_CURSOR_GUMBY , ECORE_X_CURSOR_GUMBY ), + CURSOR(ELM_CURSOR_HAND1 , ECORE_X_CURSOR_HAND1 ), + CURSOR(ELM_CURSOR_HAND2 , ECORE_X_CURSOR_HAND2 ), + CURSOR(ELM_CURSOR_HEART , ECORE_X_CURSOR_HEART ), + CURSOR(ELM_CURSOR_ICON , ECORE_X_CURSOR_ICON ), + CURSOR(ELM_CURSOR_IRON_CROSS , ECORE_X_CURSOR_IRON_CROSS ), + CURSOR(ELM_CURSOR_LEFT_PTR , ECORE_X_CURSOR_LEFT_PTR ), + CURSOR(ELM_CURSOR_LEFT_SIDE , ECORE_X_CURSOR_LEFT_SIDE ), + CURSOR(ELM_CURSOR_LEFT_TEE , ECORE_X_CURSOR_LEFT_TEE ), + CURSOR(ELM_CURSOR_LEFTBUTTON , ECORE_X_CURSOR_LEFTBUTTON ), + CURSOR(ELM_CURSOR_LL_ANGLE , ECORE_X_CURSOR_LL_ANGLE ), + CURSOR(ELM_CURSOR_LR_ANGLE , ECORE_X_CURSOR_LR_ANGLE ), + CURSOR(ELM_CURSOR_MAN , ECORE_X_CURSOR_MAN ), + CURSOR(ELM_CURSOR_MIDDLEBUTTON , ECORE_X_CURSOR_MIDDLEBUTTON ), + CURSOR(ELM_CURSOR_MOUSE , ECORE_X_CURSOR_MOUSE ), + CURSOR(ELM_CURSOR_PENCIL , ECORE_X_CURSOR_PENCIL ), + CURSOR(ELM_CURSOR_PIRATE , ECORE_X_CURSOR_PIRATE ), + CURSOR(ELM_CURSOR_PLUS , ECORE_X_CURSOR_PLUS ), + CURSOR(ELM_CURSOR_QUESTION_ARROW , ECORE_X_CURSOR_QUESTION_ARROW ), + CURSOR(ELM_CURSOR_RIGHT_PTR , ECORE_X_CURSOR_RIGHT_PTR ), + CURSOR(ELM_CURSOR_RIGHT_SIDE , ECORE_X_CURSOR_RIGHT_SIDE ), + CURSOR(ELM_CURSOR_RIGHT_TEE , ECORE_X_CURSOR_RIGHT_TEE ), + CURSOR(ELM_CURSOR_RIGHTBUTTON , ECORE_X_CURSOR_RIGHTBUTTON ), + CURSOR(ELM_CURSOR_RTL_LOGO , ECORE_X_CURSOR_RTL_LOGO ), + CURSOR(ELM_CURSOR_SAILBOAT , ECORE_X_CURSOR_SAILBOAT ), + CURSOR(ELM_CURSOR_SB_DOWN_ARROW , ECORE_X_CURSOR_SB_DOWN_ARROW ), + CURSOR(ELM_CURSOR_SB_H_DOUBLE_ARROW , ECORE_X_CURSOR_SB_H_DOUBLE_ARROW ), + CURSOR(ELM_CURSOR_SB_LEFT_ARROW , ECORE_X_CURSOR_SB_LEFT_ARROW ), + CURSOR(ELM_CURSOR_SB_RIGHT_ARROW , ECORE_X_CURSOR_SB_RIGHT_ARROW ), + CURSOR(ELM_CURSOR_SB_UP_ARROW , ECORE_X_CURSOR_SB_UP_ARROW ), + CURSOR(ELM_CURSOR_SB_V_DOUBLE_ARROW , ECORE_X_CURSOR_SB_V_DOUBLE_ARROW ), + CURSOR(ELM_CURSOR_SHUTTLE , ECORE_X_CURSOR_SHUTTLE ), + CURSOR(ELM_CURSOR_SIZING , ECORE_X_CURSOR_SIZING ), + CURSOR(ELM_CURSOR_SPIDER , ECORE_X_CURSOR_SPIDER ), + CURSOR(ELM_CURSOR_SPRAYCAN , ECORE_X_CURSOR_SPRAYCAN ), + CURSOR(ELM_CURSOR_STAR , ECORE_X_CURSOR_STAR ), + CURSOR(ELM_CURSOR_TARGET , ECORE_X_CURSOR_TARGET ), + CURSOR(ELM_CURSOR_TCROSS , ECORE_X_CURSOR_TCROSS ), + CURSOR(ELM_CURSOR_TOP_LEFT_ARROW , ECORE_X_CURSOR_TOP_LEFT_ARROW ), + CURSOR(ELM_CURSOR_TOP_LEFT_CORNER , ECORE_X_CURSOR_TOP_LEFT_CORNER ), + CURSOR(ELM_CURSOR_TOP_RIGHT_CORNER , ECORE_X_CURSOR_TOP_RIGHT_CORNER ), + CURSOR(ELM_CURSOR_TOP_SIDE , ECORE_X_CURSOR_TOP_SIDE ), + CURSOR(ELM_CURSOR_TOP_TEE , ECORE_X_CURSOR_TOP_TEE ), + CURSOR(ELM_CURSOR_TREK , ECORE_X_CURSOR_TREK ), + CURSOR(ELM_CURSOR_UL_ANGLE , ECORE_X_CURSOR_UL_ANGLE ), + CURSOR(ELM_CURSOR_UMBRELLA , ECORE_X_CURSOR_UMBRELLA ), + CURSOR(ELM_CURSOR_UR_ANGLE , ECORE_X_CURSOR_UR_ANGLE ), + CURSOR(ELM_CURSOR_WATCH , ECORE_X_CURSOR_WATCH ), + CURSOR(ELM_CURSOR_XTERM , ECORE_X_CURSOR_XTERM ) +}; +static const int _cursors_count = sizeof(_cursors)/sizeof(struct _Cursor_Id); + +#define ELM_CURSOR_GET_OR_RETURN(cur, obj, ...) \ + Elm_Cursor *cur; \ + do \ + { \ + if (!(obj)) \ + { \ + CRITICAL("Null pointer: " #obj); \ + return __VA_ARGS__; \ + } \ + cur = evas_object_data_get((obj), _cursor_key); \ + if (!cur) \ + { \ + ERR("Object does not have cursor: " #obj); \ + return __VA_ARGS__; \ + } \ + } \ + while (0) + +struct _Elm_Cursor +{ + Evas_Object *obj; + Evas_Object *eventarea, *owner; + const char *style, *cursor_name; + int hot_x, hot_y; + Ecore_Evas *ee; + Evas *evas; +#ifdef HAVE_ELEMENTARY_X + Ecore_X_Cursor cursor; + Ecore_X_Window win; +#endif + Eina_Bool visible:1; + Eina_Bool use_engine:1; + Eina_Bool engine_only:1; +}; + +static void +_elm_cursor_obj_del(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Cursor *cur = data; + + if (cur) cur->obj = NULL; +} + +static Eina_Bool +_elm_cursor_obj_add(Evas_Object *obj, Elm_Cursor *cur) +{ + int x, y; + + cur->obj = edje_object_add(cur->evas); + + if (!cur->obj) + return EINA_FALSE; + + if (!_elm_theme_object_set(obj, cur->obj, "cursor", cur->cursor_name, + cur->style ? cur->style : "default")) + { + evas_object_del(cur->obj); + cur->obj = NULL; + return EINA_FALSE; + } + + evas_object_event_callback_add(cur->obj, EVAS_CALLBACK_DEL, + _elm_cursor_obj_del, cur); + + edje_object_size_min_get(cur->obj, &x, &y); + evas_object_resize(cur->obj, x, y); + return EINA_TRUE; +} + +static void +_elm_cursor_set_hot_spots(Elm_Cursor *cur) +{ + const char *str; + + str = edje_object_data_get(cur->obj, "hot_x"); + if (str) cur->hot_x = atoi(str); + else cur->hot_x = 0; + + str = edje_object_data_get(cur->obj, "hot_y"); + if (str) cur->hot_y = atoi(str); + else cur->hot_y = 0; +} + +static void +_elm_cursor_mouse_in(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Cursor *cur = data; + + if (cur->visible) return; + evas_event_freeze(cur->evas); + cur->visible = EINA_TRUE; + if ((!cur->engine_only) && (!cur->use_engine)) + { + if (!cur->obj) + _elm_cursor_obj_add(cur->eventarea, cur); + ecore_evas_object_cursor_set(cur->ee, cur->obj, + ELM_OBJECT_LAYER_CURSOR, cur->hot_x, + cur->hot_y); + } + else + { +#ifdef HAVE_ELEMENTARY_X + ecore_x_window_cursor_set(cur->win, cur->cursor); +#endif + } + evas_event_thaw(cur->evas); +} + +static void +_elm_cursor_mouse_out(void *data, Evas *evas __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Object *sobj_parent; + Elm_Cursor *pcur = NULL; + Elm_Cursor *cur = data; + + if (!cur->visible) return; + evas_event_freeze(cur->evas); + cur->visible = EINA_FALSE; + + sobj_parent = evas_object_data_get(cur->eventarea, "elm-parent"); + while (sobj_parent) + { + pcur = evas_object_data_get((sobj_parent), _cursor_key); + if ((pcur) && (pcur->visible)) break; + sobj_parent = evas_object_data_get(sobj_parent, "elm-parent"); + } + + if (pcur) + { + pcur->visible = EINA_FALSE; + evas_event_thaw(cur->evas); + _elm_cursor_mouse_in(pcur, NULL, NULL, NULL); + return; + } + + if ((!cur->engine_only) || (!cur->use_engine)) + { + ecore_evas_object_cursor_set(cur->ee, NULL, ELM_OBJECT_LAYER_CURSOR, + cur->hot_x, cur->hot_y); + } + else + { +#ifdef HAVE_ELEMENTARY_X + ecore_x_window_cursor_set(cur->win, ECORE_X_CURSOR_X); +#endif + } + evas_event_thaw(cur->evas); +} + +static void +_elm_cursor_del(void *data __UNUSED__, Evas *evas __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + elm_object_cursor_unset(obj); +} + +static int +_elm_cursor_strcmp(const void *data1, const void *data2) +{ + const struct _Cursor_Id *c1 = data1; + const struct _Cursor_Id *c2 = data2; + return strcmp (c1->name, c2->name); +} + +static void +_elm_cursor_cur_set(Elm_Cursor *cur) +{ + if (cur->engine_only) + { + INF("Using only engine cursors"); + cur->use_engine = EINA_TRUE; + } + else if (_elm_cursor_obj_add(cur->eventarea, cur)) + { + _elm_cursor_set_hot_spots(cur); + cur->use_engine = EINA_FALSE; + elm_widget_cursor_add(cur->owner, cur); + } + else + { + INF("Cursor couldn't be found on theme: %s", cur->cursor_name); + cur->use_engine = EINA_TRUE; + } + + if (cur->use_engine) + { +#ifdef HAVE_ELEMENTARY_X + struct _Cursor_Id cur_search, *cur_id; + + cur_search.name = cur->cursor_name; + cur_id = bsearch(&(cur->cursor_name), _cursors, _cursors_count, + sizeof(struct _Cursor_Id), _elm_cursor_strcmp); + + cur->win = elm_win_xwindow_get(cur->eventarea); + if (!cur_id) + { + INF("X cursor couldn't be found: %s. Using default.", + cur->cursor_name); + cur->cursor = ecore_x_cursor_shape_get(ECORE_X_CURSOR_X); + } + else + cur->cursor = ecore_x_cursor_shape_get(cur_id->id); +#endif + } +} + +/** + * Set the cursor to be shown when mouse is over the object + * + * Set the cursor that will be displayed when mouse is over the + * object. The object can have only one cursor set to it, so if + * this function is called twice for an object, the previous set + * will be unset. + * If using X cursors, a definition of all the valid cursor names + * is listed on Elementary_Cursors.h. If an invalid name is set + * the default cursor will be used. + * + * This is an internal function that is used by objects with sub-items + * that want to provide different cursors for each of them. The @a + * owner object should be an elm_widget and will be used to track + * theme changes and to feed @a func and @a del_cb. The @a eventarea + * may be any object and is the one that should be used later on with + * elm_object_cursor apis, such as elm_object_cursor_unset(). + * + * @param eventarea the object being attached a cursor. + * @param owner the elm_widget that owns this object, will be used to + * track theme changes and to be used in @a func or @a del_cb. + * @param cursor the cursor name to be used. + * + * @internal + * @ingroup Cursors + */ +void +elm_object_sub_cursor_set(Evas_Object *eventarea, Evas_Object *owner, const char *cursor) +{ + Elm_Cursor *cur = NULL; + + cur = evas_object_data_get(eventarea, _cursor_key); + if (cur) + elm_object_cursor_unset(eventarea); + + if (!cursor) return; + + cur = ELM_NEW(Elm_Cursor); + if (!cur) return; + + cur->owner = owner; + cur->eventarea = eventarea; + cur->engine_only = _elm_config->cursor_engine_only; + cur->visible = EINA_FALSE; + + cur->cursor_name = eina_stringshare_add(cursor); + if (!cur->cursor_name) + ERR("Could not store cursor name %s", cursor); + + cur->evas = evas_object_evas_get(eventarea); + cur->ee = ecore_evas_ecore_evas_get(cur->evas); + + _elm_cursor_cur_set(cur); + + evas_object_data_set(eventarea, _cursor_key, cur); + + evas_object_event_callback_add(eventarea, EVAS_CALLBACK_MOUSE_IN, + _elm_cursor_mouse_in, cur); + evas_object_event_callback_add(eventarea, EVAS_CALLBACK_MOUSE_OUT, + _elm_cursor_mouse_out, cur); + evas_object_event_callback_add(eventarea, EVAS_CALLBACK_DEL, + _elm_cursor_del, cur); +} + +/** + * Set the cursor to be shown when mouse is over the object + * + * Set the cursor that will be displayed when mouse is over the + * object. The object can have only one cursor set to it, so if + * this function is called twice for an object, the previous set + * will be unset. + * If using X cursors, a definition of all the valid cursor names + * is listed on Elementary_Cursors.h. If an invalid name is set + * the default cursor will be used. + * + * @param obj the object being set a cursor. + * @param cursor the cursor name to be used. + * + * @ingroup Cursors + */ +EAPI void +elm_object_cursor_set(Evas_Object *obj, const char *cursor) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + elm_object_sub_cursor_set(obj, obj, cursor); +} + +/** + * Get the cursor to be shown when mouse is over the object + * + * @param obj an object with cursor already set. + * @return the cursor name. + * + * @ingroup Cursors + */ +EAPI const char * +elm_object_cursor_get(const Evas_Object *obj) +{ + ELM_CURSOR_GET_OR_RETURN(cur, obj, NULL); + return cur->cursor_name; +} + +/** + * Unset cursor for object + * + * Unset cursor for object, and set the cursor to default if the mouse + * was over this object. + * + * @param obj Target object + * @see elm_object_cursor_set() + * + * @ingroup Cursors + */ +EAPI void +elm_object_cursor_unset(Evas_Object *obj) +{ + ELM_CURSOR_GET_OR_RETURN(cur, obj); + + eina_stringshare_del(cur->cursor_name); + eina_stringshare_del(cur->style); + + if (cur->owner) + elm_widget_cursor_del(cur->owner, cur); + + if (cur->obj) + evas_object_del(cur->obj); + + if (cur->visible) + { + if (!cur->use_engine) + ecore_evas_object_cursor_set(cur->ee, NULL, ELM_OBJECT_LAYER_CURSOR, + cur->hot_x, cur->hot_y); +#ifdef HAVE_ELEMENTARY_X + else + ecore_x_window_cursor_set(cur->win, ECORE_X_CURSOR_X); +#endif + } + + evas_object_event_callback_del(obj, EVAS_CALLBACK_MOUSE_IN, + _elm_cursor_mouse_in); + evas_object_event_callback_del(obj, EVAS_CALLBACK_MOUSE_OUT, + _elm_cursor_mouse_out); + evas_object_event_callback_del(obj, EVAS_CALLBACK_DEL, _elm_cursor_del); + + evas_object_data_del(obj, _cursor_key); + free(cur); +} + +/** + * Sets a different style for this object cursor. + * + * @note before you set a style you should define a cursor with + * elm_object_cursor_set() + * + * @param obj an object with cursor already set. + * @param style the theme style to use (default, transparent, ...) + * + * @ingroup Cursors + */ +EAPI void +elm_object_cursor_style_set(Evas_Object *obj, const char *style) +{ + ELM_CURSOR_GET_OR_RETURN(cur, obj); + + if (!eina_stringshare_replace(&cur->style, style)) + ERR("Could not set current style=%s", style); + + if (cur->use_engine) return; + + if (!cur->obj) + { + if (!_elm_cursor_obj_add(obj, cur)) + ERR("Could not create cursor object"); + else + _elm_cursor_set_hot_spots(cur); + } + else + { + if (!_elm_theme_object_set(obj, cur->obj, "cursor", cur->cursor_name, + style)) + ERR("Could not apply the theme to the cursor style=%s", style); + else + _elm_cursor_set_hot_spots(cur); + } +} + +/** + * Get the style for this object cursor. + * + * @param obj an object with cursor already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a cursor set, then NULL is returned. + * + * @ingroup Cursors + */ +EAPI const char * +elm_object_cursor_style_get(const Evas_Object *obj) +{ + ELM_CURSOR_GET_OR_RETURN(cur, obj, NULL); + return cur->style ? cur->style : "default"; +} + +/** + * Notify cursor should recalculate its theme. + * @internal + */ +void +elm_cursor_theme(Elm_Cursor *cur) +{ + if ((!cur) || (!cur->obj)) return; + if (!_elm_theme_object_set(cur->eventarea, cur->obj, "cursor", + cur->cursor_name, cur->style)) + ERR("Could not apply the theme to the cursor style=%s", cur->style); + else + _elm_cursor_set_hot_spots(cur); +} + +/** + * Set if the cursor set should be searched on the theme or should use + * the provided by the engine, only. + * + * @note before you set if should look on theme you should define a cursor + * with elm_object_cursor_set(). By default it will only look for cursors + * provided by the engine. + * + * @param obj an object with cursor already set. + * @param engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. + * + * @ingroup Cursors + */ +EAPI void +elm_object_cursor_engine_only_set(Evas_Object *obj, Eina_Bool engine_only) +{ + ELM_CURSOR_GET_OR_RETURN(cur, obj); + cur->engine_only = engine_only; + if (cur->obj) + { + evas_object_del(cur->obj); + cur->obj = NULL; + } + _elm_cursor_cur_set(cur); +} + +/** + * Get the cursor engine only usage for this object cursor. + * + * @param obj an object with cursor already set. + * @return engine_only boolean to define it cursors should be looked only + * between the provided by the engine or searched on widget's theme as well. If + * the object does not have a cursor set, then EINA_FALSE is returned. + * + * @ingroup Cursors + */ +EAPI Eina_Bool +elm_object_cursor_engine_only_get(const Evas_Object *obj) +{ + ELM_CURSOR_GET_OR_RETURN(cur, obj, EINA_FALSE); + return cur->engine_only; +} + +/** + * Get the configured cursor engine only usage + * + * This gets the globally configured exclusive usage of engine cursors. + * + * @return 1 if only engine cursors should be used + * @ingroup Cursors + */ +EAPI int +elm_cursor_engine_only_get(void) +{ + return _elm_config->cursor_engine_only; +} + +/** + * Set the configured cursor engine only usage + * + * This sets the globally configured exclusive usage of engine cursors. + * It won't affect cursors set before changing this value. + * + * @param engine_only If 1 only engine cursors will be enabled, if 0 will + * look for them on theme before. + * @return EINA_TRUE if value is valid and setted (0 or 1) + * @ingroup Cursors + */ +EAPI Eina_Bool +elm_cursor_engine_only_set(int engine_only) +{ + if ((engine_only < 0) || (engine_only > 1)) return EINA_FALSE; + _elm_config->cursor_engine_only = engine_only; + return EINA_TRUE; +} diff --git a/src/lib/els_icon.c b/src/lib/els_icon.c new file mode 100644 index 0000000..ac0b092 --- /dev/null +++ b/src/lib/els_icon.c @@ -0,0 +1,726 @@ +#include +#include "elm_priv.h" + +typedef struct _Smart_Data Smart_Data; + +struct _Smart_Data +{ + Evas_Coord x, y, w, h; + Evas_Object *obj; + int size; + double scale; + Eina_Bool fill_inside : 1; + Eina_Bool scale_up : 1; + Eina_Bool scale_down : 1; + Eina_Bool preloading : 1; + Eina_Bool show : 1; + Eina_Bool edit : 1; + Eina_Bool edje : 1; + Elm_Image_Orient orient; +}; + +/* local subsystem functions */ +static void _smart_reconfigure(Smart_Data *sd); +static void _smart_init(void); +static void _smart_add(Evas_Object *obj); +static void _smart_del(Evas_Object *obj); +static void _smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y); +static void _smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h); +static void _smart_show(Evas_Object *obj); +static void _smart_hide(Evas_Object *obj); +static void _smart_color_set(Evas_Object *obj, int r, int g, int b, int a); +static void _smart_clip_set(Evas_Object *obj, Evas_Object * clip); +static void _smart_clip_unset(Evas_Object *obj); + +static void _els_smart_icon_flip_horizontal(Smart_Data *sd); +static void _els_smart_icon_flip_vertical(Smart_Data *sd); +static void _els_smart_icon_rotate_180(Smart_Data *sd); +static Eina_Bool _els_smart_icon_dropcb(void *,Evas_Object *, Elm_Selection_Data *); + +/* local subsystem globals */ +static Evas_Smart *_e_smart = NULL; + +/* externally accessible functions */ +Evas_Object * +_els_smart_icon_add(Evas *evas) +{ + _smart_init(); + return evas_object_smart_add(evas, _e_smart); +} + +static void +_preloaded(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event __UNUSED__) +{ + Smart_Data *sd = data; + + sd->preloading = EINA_FALSE; + if (sd->show) + evas_object_show(sd->obj); +} + +Eina_Bool +_els_smart_icon_file_key_set(Evas_Object *obj, const char *file, const char *key) +{ + Smart_Data *sd; + Evas_Object *pclip; + + sd = evas_object_smart_data_get(obj); + if (!sd) return EINA_FALSE; + /* smart code here */ + if (sd->edje) + { + pclip = evas_object_clip_get(sd->obj); + if (sd->obj) evas_object_del(sd->obj); + sd->obj = evas_object_image_add(evas_object_evas_get(obj)); + evas_object_image_scale_hint_set(sd->obj, EVAS_IMAGE_SCALE_HINT_STATIC); + evas_object_smart_member_add(sd->obj, obj); + evas_object_event_callback_add(sd->obj, EVAS_CALLBACK_IMAGE_PRELOADED, + _preloaded, sd); + evas_object_clip_set(sd->obj, pclip); + sd->edje = EINA_FALSE; + } + if (!sd->size) + evas_object_image_load_size_set(sd->obj, sd->size, sd->size); + evas_object_image_file_set(sd->obj, file, key); + sd->preloading = EINA_TRUE; + sd->show = EINA_TRUE; + evas_object_hide(sd->obj); + evas_object_image_preload(sd->obj, EINA_FALSE); + if (evas_object_image_load_error_get(sd->obj) != EVAS_LOAD_ERROR_NONE) + return EINA_FALSE; + _smart_reconfigure(sd); + return EINA_TRUE; +} + +Eina_Bool +_els_smart_icon_file_edje_set(Evas_Object *obj, const char *file, const char *part) +{ + Smart_Data *sd; + Evas_Object *pclip; + + sd = evas_object_smart_data_get(obj); + if (!sd) return EINA_FALSE; + /* smart code here */ + if (!sd->edje) + { + pclip = evas_object_clip_get(sd->obj); + if (sd->obj) evas_object_del(sd->obj); + sd->obj = edje_object_add(evas_object_evas_get(obj)); + evas_object_smart_member_add(sd->obj, obj); + if (sd->show) evas_object_show(sd->obj); + evas_object_clip_set(sd->obj, pclip); + } + sd->edje = EINA_TRUE; + if (!edje_object_file_set(sd->obj, file, part)) + return EINA_FALSE; + _smart_reconfigure(sd); + return EINA_TRUE; +} + +void +_els_smart_icon_file_get(const Evas_Object *obj, const char **file, const char **key) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->edje) + edje_object_file_get(sd->obj, file, key); + else + evas_object_image_file_get(sd->obj, file, key); +} + +void +_els_smart_icon_smooth_scale_set(Evas_Object *obj, Eina_Bool smooth) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->edje) + return; + evas_object_image_smooth_scale_set(sd->obj, smooth); +} + +Eina_Bool +_els_smart_icon_smooth_scale_get(const Evas_Object *obj) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return EINA_FALSE; + if (sd->edje) + return EINA_FALSE; + return evas_object_image_smooth_scale_get(sd->obj); +} + +Evas_Object * +_els_smart_icon_object_get(const Evas_Object *obj) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return NULL; + return sd->obj; +} + +void +_els_smart_icon_size_get(const Evas_Object *obj, int *w, int *h) +{ + Smart_Data *sd; + int tw, th; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (!strcmp(evas_object_type_get(sd->obj), "edje")) + edje_object_size_min_get(sd->obj, &tw, &th); + else + evas_object_image_size_get(sd->obj, &tw, &th); + tw = ((double)tw) * sd->scale; + th = ((double)th) * sd->scale; + if (w) *w = tw; + if (h) *h = th; +} + +void +_els_smart_icon_fill_inside_set(Evas_Object *obj, Eina_Bool fill_inside) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (((sd->fill_inside) && (fill_inside)) || + ((!sd->fill_inside) && (!fill_inside))) return; + sd->fill_inside = fill_inside; + _smart_reconfigure(sd); +} + +Eina_Bool +_els_smart_icon_fill_inside_get(const Evas_Object *obj) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return EINA_FALSE; + return sd->fill_inside; +} + +void +_els_smart_icon_scale_up_set(Evas_Object *obj, Eina_Bool scale_up) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (((sd->scale_up) && (scale_up)) || + ((!sd->scale_up) && (!scale_up))) return; + sd->scale_up = scale_up; + _smart_reconfigure(sd); +} + +Eina_Bool +_els_smart_icon_scale_up_get(const Evas_Object *obj) +{ + Smart_Data *sd; sd = evas_object_smart_data_get(obj); + if (!sd) return EINA_FALSE; + return sd->scale_up; +} + +void +_els_smart_icon_scale_down_set(Evas_Object *obj, Eina_Bool scale_down) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (((sd->scale_down) && (scale_down)) || + ((!sd->scale_down) && (!scale_down))) return; + sd->scale_down = scale_down; + _smart_reconfigure(sd); +} + +Eina_Bool +_els_smart_icon_scale_down_get(const Evas_Object *obj) +{ + Smart_Data *sd; sd = evas_object_smart_data_get(obj); + if (!sd) return EINA_FALSE; + return sd->scale_up; +} + +void +_els_smart_icon_scale_size_set(Evas_Object *obj, int size) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + sd->size = size; + if (!sd->obj) return; + if (sd->edje) + return; + evas_object_image_load_size_set(sd->obj, sd->size, sd->size); +} + +int +_els_smart_icon_scale_size_get(const Evas_Object *obj) +{ + Smart_Data *sd; sd = evas_object_smart_data_get(obj); + if (!sd) return 0; + return sd->size; +} + +void +_els_smart_icon_scale_set(Evas_Object *obj, double scale) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return; + sd->scale = scale; + _smart_reconfigure(sd); +} + +double +_els_smart_icon_scale_get(const Evas_Object *obj) +{ + Smart_Data *sd; sd = evas_object_smart_data_get(obj); + if (!sd) return 0.0; + return sd->scale; +} + +void +_els_smart_icon_orient_set(Evas_Object *obj, Elm_Image_Orient orient) +{ + Smart_Data *sd; + Evas_Object *tmp; + unsigned int *data, *data2, *to, *from; + int x, y, w, hw, iw, ih; + const char *file, *key; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->edje) + return; + + switch (orient) + { + case ELM_IMAGE_FLIP_HORIZONTAL: + _els_smart_icon_flip_horizontal(sd); + return; + case ELM_IMAGE_FLIP_VERTICAL: + _els_smart_icon_flip_vertical(sd); + return; + case ELM_IMAGE_ROTATE_180_CW: + _els_smart_icon_rotate_180(sd); + return; + default: + break; + } + + evas_object_image_size_get(sd->obj, &iw, &ih); + evas_object_image_file_get(sd->obj, &file, &key); + tmp = evas_object_image_add(evas_object_evas_get(sd->obj)); + evas_object_image_file_set(tmp, file, key); + data2 = evas_object_image_data_get(tmp, EINA_FALSE); + + w = ih; + ih = iw; + iw = w; + hw = w * ih; + + evas_object_image_size_set(sd->obj, iw, ih); + data = evas_object_image_data_get(sd->obj, EINA_TRUE); + switch (orient) + { + case ELM_IMAGE_FLIP_TRANSPOSE: + to = data; + hw = -hw + 1; + break; + case ELM_IMAGE_FLIP_TRANSVERSE: + to = data + hw - 1; + w = -w; + hw = hw - 1; + break; + case ELM_IMAGE_ROTATE_90_CW: + to = data + w - 1; + hw = -hw - 1; + break; + case ELM_IMAGE_ROTATE_90_CCW: + to = data + hw - w; + w = -w; + hw = hw + 1; + break; + default: + ERR("unknown orient %d", orient); + evas_object_del(tmp); + evas_object_image_data_set(sd->obj, data); // give it back + return; + } + from = data2; + for (x = iw; --x >= 0;) + { + for (y = ih; --y >= 0;) + { + *to = *from; + from++; + to += w; + } + to += hw; + } + sd->orient = orient; + evas_object_del(tmp); + evas_object_image_data_set(sd->obj, data); + evas_object_image_data_update_add(sd->obj, 0, 0, iw, ih); + _smart_reconfigure(sd); +} + +Elm_Image_Orient +_els_smart_icon_orient_get(const Evas_Object *obj) +{ + Smart_Data *sd; sd = evas_object_smart_data_get(obj); + if (!sd) return 0; + return sd->orient; +} + +/** + * Turns on editing through drag and drop and copy and paste. + */ +void +_els_smart_icon_edit_set(Evas_Object *obj, Eina_Bool edit, Evas_Object *parent) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return; + + if (sd->edje) + { + printf("No editing edje objects yet (ever)\n"); + return; + } + + /* Unfortunately eina bool is not a bool, but a char */ + if (edit == sd->edit) return; + + sd->edit = edit; + + if (sd->edit) + elm_drop_target_add(obj, ELM_SEL_FORMAT_IMAGE, _els_smart_icon_dropcb, + parent); + else + elm_drop_target_del(obj); +} + +Eina_Bool +_els_smart_icon_edit_get(const Evas_Object *obj) +{ + Smart_Data *sd; sd = evas_object_smart_data_get(obj); + if (!sd) return EINA_FALSE; + return sd->edit; +} + +Evas_Object * +_els_smart_icon_edje_get(Evas_Object *obj) +{ + Smart_Data *sd = evas_object_smart_data_get(obj); + if (!sd) return NULL; + if (!sd->edje) return NULL; + return sd->obj; +} + +/* local subsystem globals */ +static void +_smart_reconfigure(Smart_Data *sd) +{ + Evas_Coord x, y, w, h; + + if (!sd->obj) return; + if (!strcmp(evas_object_type_get(sd->obj), "edje")) + { + w = sd->w; + h = sd->h; + x = sd->x; + y = sd->y; + evas_object_move(sd->obj, x, y); + evas_object_resize(sd->obj, w, h); + } + else + { + int iw = 0, ih = 0; + + evas_object_image_size_get(sd->obj, &iw, &ih); + + iw = ((double)iw) * sd->scale; + ih = ((double)ih) * sd->scale; + + if (iw < 1) iw = 1; + if (ih < 1) ih = 1; + + if (sd->fill_inside) + { + w = sd->w; + h = ((double)ih * w) / (double)iw; + if (h > sd->h) + { + h = sd->h; + w = ((double)iw * h) / (double)ih; + } + } + else + { + w = sd->w; + h = ((double)ih * w) / (double)iw; + if (h < sd->h) + { + h = sd->h; + w = ((double)iw * h) / (double)ih; + } + } + if (!sd->scale_up) + { + if ((w > iw) || (h > ih)) + { + w = iw; + h = ih; + } + } + if (!sd->scale_down) + { + if ((w < iw) || (h < ih)) + { + w = iw; + h = ih; + } + } + x = sd->x + ((sd->w - w) / 2); + y = sd->y + ((sd->h - h) / 2); + evas_object_move(sd->obj, x, y); + evas_object_image_fill_set(sd->obj, 0, 0, w, h); + evas_object_resize(sd->obj, w, h); + } +} + +static void +_smart_init(void) +{ + if (_e_smart) return; + { + static const Evas_Smart_Class sc = + { + "e_icon", + EVAS_SMART_CLASS_VERSION, + _smart_add, + _smart_del, + _smart_move, + _smart_resize, + _smart_show, + _smart_hide, + _smart_color_set, + _smart_clip_set, + _smart_clip_unset, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL + }; + _e_smart = evas_smart_class_new(&sc); + } +} + +static void +_smart_add(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = calloc(1, sizeof(Smart_Data)); + if (!sd) return; + sd->obj = evas_object_image_add(evas_object_evas_get(obj)); + evas_object_image_scale_hint_set(sd->obj, EVAS_IMAGE_SCALE_HINT_STATIC); + sd->x = 0; + sd->y = 0; + sd->w = 0; + sd->h = 0; + sd->fill_inside = EINA_TRUE; + sd->scale_up = EINA_TRUE; + sd->scale_down = EINA_TRUE; + sd->size = 64; + sd->scale = 1.0; + evas_object_smart_member_add(sd->obj, obj); + evas_object_smart_data_set(obj, sd); + evas_object_event_callback_add(sd->obj, EVAS_CALLBACK_IMAGE_PRELOADED, + _preloaded, sd); +} + +static void +_smart_del(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + evas_object_del(sd->obj); + free(sd); +} + +static void +_smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if ((sd->x == x) && (sd->y == y)) return; + sd->x = x; + sd->y = y; + _smart_reconfigure(sd); +} + +static void +_smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if ((sd->w == w) && (sd->h == h)) return; + sd->w = w; + sd->h = h; + _smart_reconfigure(sd); +} + +static void +_smart_show(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + sd->show = EINA_TRUE; + if (!sd->preloading) + evas_object_show(sd->obj); +} + +static void +_smart_hide(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + sd->show = EINA_FALSE; + evas_object_hide(sd->obj); +} + +static void +_smart_color_set(Evas_Object *obj, int r, int g, int b, int a) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + evas_object_color_set(sd->obj, r, g, b, a); +} + +static void +_smart_clip_set(Evas_Object *obj, Evas_Object * clip) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + evas_object_clip_set(sd->obj, clip); +} + +static void +_smart_clip_unset(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + evas_object_clip_unset(sd->obj); +} + +static void +_els_smart_icon_flip_horizontal(Smart_Data *sd) +{ + unsigned int *data; + unsigned int *p1, *p2, tmp; + int x, y, iw, ih; + + evas_object_image_size_get(sd->obj, &iw, &ih); + data = evas_object_image_data_get(sd->obj, EINA_TRUE); + + for (y = 0; y < ih; y++) + { + p1 = data + (y * iw); + p2 = data + ((y + 1) * iw) - 1; + for (x = 0; x < (iw >> 1); x++) + { + tmp = *p1; + *p1 = *p2; + *p2 = tmp; + p1++; + p2--; + } + } + + evas_object_image_data_set(sd->obj, data); + evas_object_image_data_update_add(sd->obj, 0, 0, iw, ih); + _smart_reconfigure(sd); +} + +static void +_els_smart_icon_flip_vertical(Smart_Data *sd) +{ + unsigned int *data; + unsigned int *p1, *p2, tmp; + int x, y, iw, ih; + + evas_object_image_size_get(sd->obj, &iw, &ih); + data = evas_object_image_data_get(sd->obj, EINA_TRUE); + + for (y = 0; y < (ih >> 1); y++) + { + p1 = data + (y * iw); + p2 = data + ((ih - 1 - y) * iw); + for (x = 0; x < iw; x++) + { + tmp = *p1; + *p1 = *p2; + *p2 = tmp; + p1++; + p2++; + } + } + + evas_object_image_data_set(sd->obj, data); + evas_object_image_data_update_add(sd->obj, 0, 0, iw, ih); + _smart_reconfigure(sd); +} + +static void +_els_smart_icon_rotate_180(Smart_Data *sd) +{ + unsigned int *data; + unsigned int *p1, *p2, tmp; + int x, hw, iw, ih; + + evas_object_image_size_get(sd->obj, &iw, &ih); + data = evas_object_image_data_get(sd->obj, 1); + + hw = iw * ih; + x = (hw / 2); + p1 = data; + p2 = data + hw - 1; + for (; --x > 0;) + { + tmp = *p1; + *p1 = *p2; + *p2 = tmp; + p1++; + p2--; + } + evas_object_image_data_set(sd->obj, data); + evas_object_image_data_update_add(sd->obj, 0, 0, iw, ih); + _smart_reconfigure(sd); +} + +static Eina_Bool +_els_smart_icon_dropcb(void *elmobj,Evas_Object *obj, Elm_Selection_Data *drop) +{ + _els_smart_icon_file_key_set(obj, drop->data, NULL); + evas_object_smart_callback_call(elmobj, "drop", drop->data); + + return EINA_TRUE; +} +/* vim:set ts=8 sw=3 sts=3 expandtab cino=>5n-2f0^-2{2(0W1st0 :*/ diff --git a/src/lib/els_icon.h b/src/lib/els_icon.h new file mode 100644 index 0000000..f4325c8 --- /dev/null +++ b/src/lib/els_icon.h @@ -0,0 +1,23 @@ +Evas_Object *_els_smart_icon_add (Evas *evas); +Eina_Bool _els_smart_icon_file_key_set (Evas_Object *obj, const char *file, const char *key); +Eina_Bool _els_smart_icon_file_edje_set (Evas_Object *obj, const char *file, const char *part); +void _els_smart_icon_file_get (const Evas_Object *obj, const char **file, const char **key); +void _els_smart_icon_smooth_scale_set (Evas_Object *obj, Eina_Bool smooth); +Eina_Bool _els_smart_icon_smooth_scale_get (const Evas_Object *obj); +Evas_Object *_els_smart_icon_object_get (const Evas_Object *obj); +void _els_smart_icon_size_get (const Evas_Object *obj, int *w, int *h); +void _els_smart_icon_fill_inside_set (Evas_Object *obj, Eina_Bool fill_inside); +Eina_Bool _els_smart_icon_fill_inside_get (const Evas_Object *obj); +void _els_smart_icon_scale_up_set (Evas_Object *obj, Eina_Bool scale_up); +Eina_Bool _els_smart_icon_scale_up_get (const Evas_Object *obj); +void _els_smart_icon_scale_down_set (Evas_Object *obj, Eina_Bool scale_down); +Eina_Bool _els_smart_icon_scale_down_get (const Evas_Object *obj); +void _els_smart_icon_scale_size_set (Evas_Object *obj, int size); +int _els_smart_icon_scale_size_get (const Evas_Object *obj); +void _els_smart_icon_scale_set (Evas_Object *obj, double scale); +double _els_smart_icon_scale_get (const Evas_Object *obj); +void _els_smart_icon_orient_set (Evas_Object *obj, Elm_Image_Orient orient); +Elm_Image_Orient _els_smart_icon_orient_get (const Evas_Object *obj); +void _els_smart_icon_edit_set (Evas_Object *obj, Eina_Bool, Evas_Object *parent); +Eina_Bool _els_smart_icon_edit_get (const Evas_Object *obj); +Evas_Object *_els_smart_icon_edje_get(Evas_Object *obj); diff --git a/src/lib/els_pan.c b/src/lib/els_pan.c new file mode 100644 index 0000000..436d287 --- /dev/null +++ b/src/lib/els_pan.c @@ -0,0 +1,285 @@ +#include +#include "elm_priv.h" + +#define SMART_NAME "elm_pan" +#define API_ENTRY Smart_Data *sd; sd = evas_object_smart_data_get(obj); if ((!obj) || (!sd) || (evas_object_type_get(obj) && strcmp(evas_object_type_get(obj), SMART_NAME))) +#define INTERNAL_ENTRY Smart_Data *sd; sd = evas_object_smart_data_get(obj); if (!sd) return; +typedef struct _Smart_Data Smart_Data; + +struct _Smart_Data +{ + Evas_Object *smart_obj; + Evas_Object *child_obj; + Evas_Coord x, y, w, h; + Evas_Coord child_w, child_h, px, py; +}; + +/* local subsystem functions */ +static void _smart_child_del_hook(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _smart_child_resize_hook(void *data, Evas *e, Evas_Object *obj, void *event_info); + +static void _smart_reconfigure(Smart_Data *sd); +static void _smart_add(Evas_Object *obj); +static void _smart_del(Evas_Object *obj); +static void _smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y); +static void _smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h); +static void _smart_show(Evas_Object *obj); +static void _smart_hide(Evas_Object *obj); +static void _smart_color_set(Evas_Object *obj, int r, int g, int b, int a); +static void _smart_clip_set(Evas_Object *obj, Evas_Object * clip); +static void _smart_clip_unset(Evas_Object *obj); +static void _smart_init(void); + +/* local subsystem globals */ +static Evas_Smart *_smart = NULL; + +/* externally accessible functions */ +Evas_Object * +_elm_smart_pan_add(Evas *evas) +{ + _smart_init(); + return evas_object_smart_add(evas, _smart); +} + +void +_elm_smart_pan_child_set(Evas_Object *obj, Evas_Object *child) +{ + API_ENTRY return; + if (child == sd->child_obj) return; + if (sd->child_obj) + { + evas_object_clip_unset(sd->child_obj); + evas_object_smart_member_del(sd->child_obj); + evas_object_event_callback_del_full(sd->child_obj, EVAS_CALLBACK_FREE, _smart_child_del_hook, sd); + evas_object_event_callback_del_full(sd->child_obj, EVAS_CALLBACK_RESIZE, _smart_child_resize_hook, sd); + sd->child_obj = NULL; + } + if (child) + { + Evas_Coord w, h; + int r, g, b, a; + + sd->child_obj = child; + evas_object_smart_member_add(sd->child_obj, sd->smart_obj); + evas_object_geometry_get(sd->child_obj, NULL, NULL, &w, &h); + sd->child_w = w; + sd->child_h = h; + evas_object_event_callback_add(child, EVAS_CALLBACK_FREE, _smart_child_del_hook, sd); + evas_object_event_callback_add(child, EVAS_CALLBACK_RESIZE, _smart_child_resize_hook, sd); + evas_object_color_get(sd->smart_obj, &r, &g, &b, &a); + evas_object_color_set(sd->child_obj, r, g, b, a); + evas_object_clip_set(sd->child_obj, evas_object_clip_get(sd->smart_obj)); + if (evas_object_visible_get(sd->smart_obj)) evas_object_show(sd->child_obj); + else evas_object_hide(sd->child_obj); + _smart_reconfigure(sd); + } + evas_object_smart_callback_call(sd->smart_obj, "changed", NULL); +} + +Evas_Object * +_elm_smart_pan_child_get(Evas_Object *obj) +{ + API_ENTRY return NULL; + return sd->child_obj; +} + +void +_elm_smart_pan_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + API_ENTRY return; +// if (x > (sd->child_w - sd->w)) x = sd->child_w - sd->w; +// if (y > (sd->child_h - sd->h)) y = sd->child_h - sd->h; +// if (x < 0) x = 0; +// if (y < 0) y = 0; + if ((x == sd->px) && (y == sd->py)) return; + sd->px = x; + sd->py = y; + _smart_reconfigure(sd); + evas_object_smart_callback_call(sd->smart_obj, "changed", NULL); +} + +void +_elm_smart_pan_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + API_ENTRY return; + if (x) *x = sd->px; + if (y) *y = sd->py; +} + +void +_elm_smart_pan_max_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + API_ENTRY return; + if (x) + { + if (sd->w < sd->child_w) *x = sd->child_w - sd->w; + else *x = 0; + } + if (y) + { + if (sd->h < sd->child_h) *y = sd->child_h - sd->h; + else *y = 0; + } +} + +void +_elm_smart_pan_min_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + API_ENTRY return; + if (x) + *x = 0; + if (y) + *y = 0; +} + +void +_elm_smart_pan_child_size_get(Evas_Object *obj, Evas_Coord *w, Evas_Coord *h) +{ + API_ENTRY return; + if (w) *w = sd->child_w; + if (h) *h = sd->child_h; +} + +/* local subsystem functions */ +static void +_smart_child_del_hook(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Smart_Data *sd; + + sd = data; + sd->child_obj = NULL; + evas_object_smart_callback_call(sd->smart_obj, "changed", NULL); +} + +static void +_smart_child_resize_hook(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Smart_Data *sd; + Evas_Coord w, h; + + sd = data; + evas_object_geometry_get(sd->child_obj, NULL, NULL, &w, &h); + if ((w != sd->child_w) || (h != sd->child_h)) + { + sd->child_w = w; + sd->child_h = h; + _smart_reconfigure(sd); + } + evas_object_smart_callback_call(sd->smart_obj, "changed", NULL); +} + +static void +_smart_reconfigure(Smart_Data *sd) +{ + evas_object_move(sd->child_obj, sd->x - sd->px, sd->y - sd->py); +} + +static void +_smart_add(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = calloc(1, sizeof(Smart_Data)); + if (!sd) return; + sd->smart_obj = obj; + sd->x = 0; + sd->y = 0; + sd->w = 0; + sd->h = 0; + evas_object_smart_data_set(obj, sd); +} + +static void +_smart_del(Evas_Object *obj) +{ + INTERNAL_ENTRY; + _elm_smart_pan_child_set(obj, NULL); + free(sd); +} + +static void +_smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + INTERNAL_ENTRY; + sd->x = x; + sd->y = y; + _smart_reconfigure(sd); +} + +static void +_smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h) +{ + INTERNAL_ENTRY; + sd->w = w; + sd->h = h; + _smart_reconfigure(sd); + evas_object_smart_callback_call(sd->smart_obj, "changed", NULL); +} + +static void +_smart_show(Evas_Object *obj) +{ + INTERNAL_ENTRY; + evas_object_show(sd->child_obj); +} + +static void +_smart_hide(Evas_Object *obj) +{ + INTERNAL_ENTRY; + evas_object_hide(sd->child_obj); +} + +static void +_smart_color_set(Evas_Object *obj, int r, int g, int b, int a) +{ + INTERNAL_ENTRY; + evas_object_color_set(sd->child_obj, r, g, b, a); +} + +static void +_smart_clip_set(Evas_Object *obj, Evas_Object *clip) +{ + INTERNAL_ENTRY; + evas_object_clip_set(sd->child_obj, clip); +} + +static void +_smart_clip_unset(Evas_Object *obj) +{ + INTERNAL_ENTRY; + evas_object_clip_unset(sd->child_obj); +} + +/* never need to touch this */ + +static void +_smart_init(void) +{ + if (_smart) return; + { + static const Evas_Smart_Class sc = + { + SMART_NAME, + EVAS_SMART_CLASS_VERSION, + _smart_add, + _smart_del, + _smart_move, + _smart_resize, + _smart_show, + _smart_hide, + _smart_color_set, + _smart_clip_set, + _smart_clip_unset, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL + }; + _smart = evas_smart_class_new(&sc); + } +} + diff --git a/src/lib/els_pan.h b/src/lib/els_pan.h new file mode 100644 index 0000000..cb64fa1 --- /dev/null +++ b/src/lib/els_pan.h @@ -0,0 +1,8 @@ +Evas_Object *_elm_smart_pan_add (Evas *evas); +void _elm_smart_pan_child_set (Evas_Object *obj, Evas_Object *child); +Evas_Object *_elm_smart_pan_child_get (Evas_Object *obj); +void _elm_smart_pan_set (Evas_Object *obj, Evas_Coord x, Evas_Coord y); +void _elm_smart_pan_get (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); +void _elm_smart_pan_max_get (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); +void _elm_smart_pan_min_get (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); +void _elm_smart_pan_child_size_get (Evas_Object *obj, Evas_Coord *w, Evas_Coord *h); diff --git a/src/lib/els_scroller.c b/src/lib/els_scroller.c new file mode 100644 index 0000000..85d002e --- /dev/null +++ b/src/lib/els_scroller.c @@ -0,0 +1,2606 @@ +#include +#include "elm_priv.h" + +#define SMART_NAME "els_scroller" +#define API_ENTRY Smart_Data *sd; sd = evas_object_smart_data_get(obj); if ((!obj) || (!sd) || (evas_object_type_get(obj) && strcmp(evas_object_type_get(obj), SMART_NAME))) +#define INTERNAL_ENTRY Smart_Data *sd; sd = evas_object_smart_data_get(obj); if (!sd) return; +typedef struct _Smart_Data Smart_Data; + +#define EVTIME 1 +//#define SCROLLDBG 1 + +struct _Smart_Data +{ + Evas_Coord x, y, w, h; + Evas_Coord wx, wy, ww, wh; /* Last "wanted" geometry */ + + Evas_Object *smart_obj; + Evas_Object *child_obj; + Evas_Object *pan_obj; + Evas_Object *edje_obj; + Evas_Object *event_obj; + + Evas_Object *widget; + + Elm_Smart_Scroller_Policy hbar_flags, vbar_flags; + + struct { + Evas_Coord x, y; + Evas_Coord sx, sy; + Evas_Coord dx, dy; + Evas_Coord pdx, pdy; + Evas_Coord bx, by; + Evas_Coord ax, ay; + Evas_Coord bx0, by0; + Evas_Coord b0x, b0y; + Evas_Coord b2x, b2y; + struct { + Evas_Coord x, y; + double timestamp; + } history[20]; + double anim_start; + double anim_start2; + double anim_start3; + double onhold_vx, onhold_vy, onhold_tlast, onhold_vxe, onhold_vye; + double extra_time; + Evas_Coord hold_x, hold_y; + Ecore_Animator *hold_animator; + Ecore_Animator *onhold_animator; + Ecore_Animator *momentum_animator; + Ecore_Animator *bounce_x_animator; + Ecore_Animator *bounce_y_animator; + Evas_Coord locked_x, locked_y; + int hdir, vdir; + unsigned char now : 1; + unsigned char cancelled : 1; + unsigned char hold : 1; + unsigned char hold_parent : 1; + unsigned char want_dragged : 1; + unsigned char dragged : 1; + unsigned char dragged_began : 1; + unsigned char dir_x : 1; + unsigned char dir_y : 1; + unsigned char locked : 1; + unsigned char bounce_x_hold : 1; + unsigned char bounce_y_hold : 1; + unsigned char scroll : 1; + } down; + + struct { + Evas_Coord w, h; + } child; + struct { + Evas_Coord x, y; + } step, page; + + struct { + void (*set) (Evas_Object *obj, Evas_Coord x, Evas_Coord y); + void (*get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); + void (*max_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); + void (*min_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); + void (*child_size_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); + } pan_func; + + struct { + struct { + Evas_Coord start, end; + double t_start, t_end; + Ecore_Animator *animator; + } x, y; + } scrollto; + + double pagerel_h, pagerel_v; + Evas_Coord pagesize_h, pagesize_v; + + unsigned char hbar_visible : 1; + unsigned char vbar_visible : 1; + unsigned char extern_pan : 1; + unsigned char one_dir_at_a_time : 1; + unsigned char hold : 1; + unsigned char freeze : 1; + unsigned char bouncemex : 1; + unsigned char bouncemey : 1; + unsigned char bounce_horiz : 1; + unsigned char bounce_vert : 1; + unsigned char momentum_animator_disabled :1; + unsigned char bounce_animator_disabled :1; +}; + +/* local subsystem functions */ +static void _smart_child_del_hook(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _smart_pan_changed_hook(void *data, Evas_Object *obj, void *event_info); +static void _smart_pan_pan_changed_hook(void *data, Evas_Object *obj, void *event_info); +static void _smart_event_wheel(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _smart_event_mouse_down(void *data, Evas *e, Evas_Object *obj, void *event_info); +static Eina_Bool _smart_hold_animator(void *data); +static Eina_Bool _smart_momentum_animator(void *data); +static void _smart_event_mouse_up(void *data, Evas *e, Evas_Object *obj, void *event_info); +static Eina_Bool _smart_onhold_animator(void *data); +static void _smart_event_mouse_move(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _smart_edje_drag_v_start(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _smart_edje_drag_v_stop(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _smart_edje_drag_v(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _smart_edje_drag_h_start(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _smart_edje_drag_h_stop(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _smart_edje_drag_h(void *data, Evas_Object *obj, const char *emission, const char *source); +static void _smart_scrollbar_read(Smart_Data *sd); +static void _smart_scrollbar_reset(Smart_Data *sd); +static int _smart_scrollbar_bar_h_visibility_adjust(Smart_Data *sd); +static int _smart_scrollbar_bar_v_visibility_adjust(Smart_Data *sd); +static void _smart_scrollbar_bar_visibility_adjust(Smart_Data *sd); +static void _smart_scrollbar_size_adjust(Smart_Data *sd); +static void _smart_reconfigure(Smart_Data *sd); +static void _smart_add(Evas_Object *obj); +static void _smart_del(Evas_Object *obj); +static void _smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y); +static void _smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h); +static void _smart_show(Evas_Object *obj); +static void _smart_hide(Evas_Object *obj); +static void _smart_color_set(Evas_Object *obj, int r, int g, int b, int a); +static void _smart_clip_set(Evas_Object *obj, Evas_Object *clip); +static void _smart_clip_unset(Evas_Object *obj); +static void _smart_init(void); + +/* local subsystem globals */ +static Evas_Smart *_smart = NULL; + +/* externally accessible functions */ +Evas_Object * +elm_smart_scroller_add(Evas *evas) +{ + _smart_init(); + return evas_object_smart_add(evas, _smart); +} + +void +elm_smart_scroller_child_set(Evas_Object *obj, Evas_Object *child) +{ + Evas_Coord w, h; + Evas_Object *o; + + API_ENTRY return; + if (sd->child_obj) + { + _elm_smart_pan_child_set(sd->pan_obj, NULL); + evas_object_event_callback_del_full(sd->child_obj, EVAS_CALLBACK_DEL, _smart_child_del_hook, sd); + } + + sd->child_obj = child; + sd->wx = sd->wy = sd->ww = sd->wh = 0; + if (!child) return; + + if (!sd->pan_obj) + { + o = _elm_smart_pan_add(evas_object_evas_get(obj)); + sd->pan_obj = o; + evas_object_smart_callback_add(o, "changed", _smart_pan_changed_hook, sd); + evas_object_smart_callback_add(o, "pan_changed", _smart_pan_pan_changed_hook, sd); + evas_object_show(o); + edje_object_part_swallow(sd->edje_obj, "elm.swallow.content", o); + } + + sd->pan_func.set = _elm_smart_pan_set; + sd->pan_func.get = _elm_smart_pan_get; + sd->pan_func.max_get = _elm_smart_pan_max_get; + sd->pan_func.min_get = _elm_smart_pan_min_get; + sd->pan_func.child_size_get = _elm_smart_pan_child_size_get; + + evas_object_event_callback_add(child, EVAS_CALLBACK_DEL, _smart_child_del_hook, sd); + _elm_smart_pan_child_set(sd->pan_obj, sd->child_obj); + sd->pan_func.child_size_get(sd->pan_obj, &w, &h); + sd->child.w = w; + sd->child.h = h; + _smart_scrollbar_size_adjust(sd); + _smart_scrollbar_reset(sd); +} + +void +elm_smart_scroller_extern_pan_set(Evas_Object *obj, Evas_Object *pan, + void (*pan_set) (Evas_Object *obj, Evas_Coord x, Evas_Coord y), + void (*pan_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y), + void (*pan_max_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y), + void (*pan_min_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y), + void (*pan_child_size_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y)) +{ + API_ENTRY return; + + elm_smart_scroller_child_set(obj, NULL); + + if (sd->pan_obj) + { + evas_object_smart_callback_del(sd->pan_obj, "changed", _smart_pan_changed_hook); + evas_object_smart_callback_del(sd->pan_obj, "pan_changed", _smart_pan_pan_changed_hook); + } + + if (sd->extern_pan) + { + if (sd->pan_obj) + { + edje_object_part_unswallow(sd->edje_obj, sd->pan_obj); + sd->pan_obj = NULL; + } + } + else + { + if (sd->pan_obj) + { + evas_object_del(sd->pan_obj); + sd->pan_obj = NULL; + } + } + if (!pan) + { + sd->extern_pan = 0; + return; + } + + sd->pan_obj = pan; + sd->pan_func.set = pan_set; + sd->pan_func.get = pan_get; + sd->pan_func.max_get = pan_max_get; + sd->pan_func.min_get = pan_min_get; + sd->pan_func.child_size_get = pan_child_size_get; + sd->extern_pan = 1; + evas_object_smart_callback_add(sd->pan_obj, "changed", _smart_pan_changed_hook, sd); + evas_object_smart_callback_add(sd->pan_obj, "pan_changed", _smart_pan_pan_changed_hook, sd); + edje_object_part_swallow(sd->edje_obj, "elm.swallow.content", sd->pan_obj); + evas_object_show(sd->pan_obj); +} + +void +elm_smart_scroller_custom_edje_file_set(Evas_Object *obj, char *file, char *group) +{ + API_ENTRY return; + + edje_object_file_set(sd->edje_obj, file, group); + if (sd->pan_obj) + edje_object_part_swallow(sd->edje_obj, "elm.swallow.content", sd->pan_obj); + sd->vbar_visible = !sd->vbar_visible; + sd->hbar_visible = !sd->hbar_visible; + _smart_scrollbar_bar_visibility_adjust(sd); + if (sd->hbar_flags == ELM_SMART_SCROLLER_POLICY_ON) + edje_object_signal_emit(sd->edje_obj, "elm,action,show_always,hbar", "elm"); + else if (sd->hbar_flags == ELM_SMART_SCROLLER_POLICY_OFF) + edje_object_signal_emit(sd->edje_obj, "elm,action,hide,hbar", "elm"); + else + edje_object_signal_emit(sd->edje_obj, "elm,action,show_notalways,hbar", "elm"); + if (sd->vbar_flags == ELM_SMART_SCROLLER_POLICY_ON) + edje_object_signal_emit(sd->edje_obj, "elm,action,show_always,vbar", "elm"); + else if (sd->vbar_flags == ELM_SMART_SCROLLER_POLICY_OFF) + edje_object_signal_emit(sd->edje_obj, "elm,action,hide,vbar", "elm"); + else + edje_object_signal_emit(sd->edje_obj, "elm,action,show_notalways,vbar", "elm"); +} + +Eina_Bool +elm_smart_scroller_momentum_animator_disabled_get(Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->momentum_animator_disabled; +} + +void +elm_smart_scroller_momentum_animator_disabled_set(Evas_Object *obj, Eina_Bool disabled) +{ + API_ENTRY return; + sd->momentum_animator_disabled = disabled; + if (sd->momentum_animator_disabled) + { + if (sd->down.momentum_animator) + { + ecore_animator_del(sd->down.momentum_animator); + sd->down.momentum_animator = NULL; + } + } +} + +Eina_Bool +elm_smart_scroller_bounce_animator_disabled_get(Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->bounce_animator_disabled; +} + +void +elm_smart_scroller_bounce_animator_disabled_set(Evas_Object *obj, Eina_Bool disabled) +{ + API_ENTRY return; + sd->bounce_animator_disabled = disabled; + if (sd->bounce_animator_disabled) + { + if (sd->scrollto.x.animator) + { + ecore_animator_del(sd->scrollto.x.animator); + sd->scrollto.x.animator = NULL; + } + + if (sd->scrollto.y.animator) + { + ecore_animator_del(sd->scrollto.y.animator); + sd->scrollto.y.animator = NULL; + } + } +} + +static void +_smart_anim_start(Evas_Object *obj) +{ + evas_object_smart_callback_call(obj, "animate,start", NULL); +} + +static void +_smart_anim_stop(Evas_Object *obj) +{ + evas_object_smart_callback_call(obj, "animate,stop", NULL); +} + +static void +_smart_drag_start(Evas_Object *obj) +{ + evas_object_smart_callback_call(obj, "drag,start", NULL); +} + +static void +_smart_drag_stop(Evas_Object *obj) +{ + evas_object_smart_callback_call(obj, "drag,stop", NULL); +} + +static Eina_Bool +_smart_scrollto_x_animator(void *data) +{ + Smart_Data *sd = data; + Evas_Coord px, py; + double t, tt; + + t = ecore_loop_time_get(); + tt = (t - sd->scrollto.x.t_start) / (sd->scrollto.x.t_end - sd->scrollto.x.t_start); + tt = 1.0 - tt; + tt = 1.0 - (tt * tt); + sd->pan_func.get(sd->pan_obj, &px, &py); + px = (sd->scrollto.x.start * (1.0 - tt)) + + (sd->scrollto.x.end * tt); + if (t >= sd->scrollto.x.t_end) + { + px = sd->scrollto.x.end; + elm_smart_scroller_child_pos_set(sd->smart_obj, px, py); + sd->scrollto.x.animator = NULL; + if ((!sd->scrollto.y.animator) && (!sd->down.bounce_y_animator)) + _smart_anim_stop(sd->smart_obj); + return ECORE_CALLBACK_CANCEL; + } + elm_smart_scroller_child_pos_set(sd->smart_obj, px, py); + return ECORE_CALLBACK_RENEW; +} + +static void +_smart_momentum_end(Smart_Data *sd) +{ + if ((sd->down.bounce_x_animator) || (sd->down.bounce_y_animator)) return; + if (sd->down.momentum_animator) + { + ecore_animator_del(sd->down.momentum_animator); + sd->down.momentum_animator = NULL; + sd->down.bounce_x_hold = 0; + sd->down.bounce_y_hold = 0; + sd->down.ax = 0; + sd->down.ay = 0; + sd->down.pdx = 0; + sd->down.pdy = 0; + } +} + +static void +_smart_scrollto_x(Smart_Data *sd, double t_in, Evas_Coord pos_x) +{ + Evas_Coord px, py, x, y, w, h; + double t; + + if (sd->freeze) return; + if (t_in <= 0.0) + { + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + elm_smart_scroller_child_viewport_size_get(sd->smart_obj, &w, &h); + x = pos_x; + elm_smart_scroller_child_region_set(sd->smart_obj, x, y, w, h); + return; + } + t = ecore_loop_time_get(); + sd->pan_func.get(sd->pan_obj, &px, &py); + sd->scrollto.x.start = px; + sd->scrollto.x.end = pos_x; + sd->scrollto.x.t_start = t; + sd->scrollto.x.t_end = t + t_in; + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + elm_smart_scroller_child_viewport_size_get(sd->smart_obj, &w, &h); + elm_smart_scroller_child_region_set(sd->smart_obj, x, y, w, h); + if (!sd->scrollto.x.animator) + { + if (!sd->scrollto.y.animator) + _smart_anim_start(sd->smart_obj); + sd->scrollto.x.animator = ecore_animator_add(_smart_scrollto_x_animator, sd); + } + if (sd->down.bounce_x_animator) + { + ecore_animator_del(sd->down.bounce_x_animator); + sd->down.bounce_x_animator = NULL; + _smart_momentum_end(sd); + } + sd->bouncemex = 0; +} + +static Eina_Bool +_smart_scrollto_y_animator(void *data) +{ + Smart_Data *sd = data; + Evas_Coord px, py; + double t, tt; + + t = ecore_loop_time_get(); + tt = (t - sd->scrollto.y.t_start) / (sd->scrollto.y.t_end - sd->scrollto.y.t_start); + tt = 1.0 - tt; + tt = 1.0 - (tt * tt); + sd->pan_func.get(sd->pan_obj, &px, &py); + py = (sd->scrollto.y.start * (1.0 - tt)) + + (sd->scrollto.y.end * tt); + if (t >= sd->scrollto.y.t_end) + { + py = sd->scrollto.y.end; + elm_smart_scroller_child_pos_set(sd->smart_obj, px, py); + sd->scrollto.y.animator = NULL; + if ((!sd->scrollto.x.animator) && (!sd->down.bounce_x_animator)) + _smart_anim_stop(sd->smart_obj); + return ECORE_CALLBACK_CANCEL; + } + elm_smart_scroller_child_pos_set(sd->smart_obj, px, py); + + return ECORE_CALLBACK_RENEW; +} + +static void +_smart_scrollto_y(Smart_Data *sd, double t_in, Evas_Coord pos_y) +{ + Evas_Coord px, py, x, y, w, h; + double t; + + if (sd->freeze) return; + if (t_in <= 0.0) + { + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + elm_smart_scroller_child_viewport_size_get(sd->smart_obj, &w, &h); + y = pos_y; + elm_smart_scroller_child_region_set(sd->smart_obj, x, y, w, h); + return; + } + t = ecore_loop_time_get(); + sd->pan_func.get(sd->pan_obj, &px, &py); + sd->scrollto.y.start = py; + sd->scrollto.y.end = pos_y; + sd->scrollto.y.t_start = t; + sd->scrollto.y.t_end = t + t_in; + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + elm_smart_scroller_child_viewport_size_get(sd->smart_obj, &w, &h); + elm_smart_scroller_child_region_set(sd->smart_obj, x, y, w, h); + if (!sd->scrollto.y.animator) + { + if (!sd->scrollto.x.animator) + _smart_anim_start(sd->smart_obj); + sd->scrollto.y.animator = ecore_animator_add(_smart_scrollto_y_animator, sd); + } + if (sd->down.bounce_y_animator) + { + ecore_animator_del(sd->down.bounce_y_animator); + sd->down.bounce_y_animator = NULL; + _smart_momentum_end(sd); + } + sd->bouncemey = 0; +} + +static Eina_Bool +_smart_do_page(Smart_Data *sd) +{ + if ((sd->pagerel_h == 0.0) && (!sd->pagesize_h) && + (sd->pagerel_v == 0.0) && (!sd->pagesize_v)) + return EINA_FALSE; + return EINA_TRUE; +} + +static Evas_Coord +_smart_page_x_get(Smart_Data *sd, int offset) +{ + Evas_Coord x, y, w, h, cw, ch, minx = 0; + + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + elm_smart_scroller_child_viewport_size_get(sd->smart_obj, &w, &h); + sd->pan_func.child_size_get(sd->pan_obj, &cw, &ch); + sd->pan_func.min_get(sd->pan_obj, &minx, NULL); + + x += offset; + + if (sd->pagerel_h > 0.0) + { + x = x + (w * sd->pagerel_h * 0.5); + x = x / (w * sd->pagerel_h); + x = x * (w * sd->pagerel_h); + } + else if (sd->pagesize_h > 0) + { + x = x + (sd->pagesize_h * 0.5); + x = x / (sd->pagesize_h); + x = x * (sd->pagesize_h); + } + if (x < minx) x = minx; + else if ((x + w) > cw) x = cw - w; + return x; +} + +static Evas_Coord +_smart_page_y_get(Smart_Data *sd, int offset) +{ + Evas_Coord x, y, w, h, cw, ch, miny = 0; + + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + elm_smart_scroller_child_viewport_size_get(sd->smart_obj, &w, &h); + sd->pan_func.child_size_get(sd->pan_obj, &cw, &ch); + sd->pan_func.min_get(sd->pan_obj, NULL, &miny); + + y += offset; + + if (sd->pagerel_v > 0.0) + { + y = y + (h * sd->pagerel_v * 0.5); + y = y / (h * sd->pagerel_v); + y = y * (h * sd->pagerel_v); + } + else if (sd->pagesize_v > 0) + { + y = y + (sd->pagesize_v * 0.5); + y = y / (sd->pagesize_v); + y = y * (sd->pagesize_v); + } + if (y < miny) y = miny; + else if ((y + h) > ch) y = ch - h; + return y; +} + +static void +_smart_page_adjust(Smart_Data *sd) +{ + Evas_Coord x, y, w, h; + + if (!_smart_do_page(sd)) return; + + elm_smart_scroller_child_viewport_size_get(sd->smart_obj, &w, &h); + + x = _smart_page_x_get(sd, 0); + y = _smart_page_y_get(sd, 0); + + elm_smart_scroller_child_region_set(sd->smart_obj, x, y, w, h); +} + +static Eina_Bool +_smart_bounce_x_animator(void *data) +{ + Smart_Data *sd; + Evas_Coord x, y, dx; + double t, p, dt; + + sd = data; + t = ecore_loop_time_get(); + dt = t - sd->down.anim_start2; + if (dt >= 0.0) + { + dt = dt / _elm_config->thumbscroll_bounce_friction; + if (dt > 1.0) dt = 1.0; + p = 1.0 - ((1.0 - dt) * (1.0 - dt)); + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + dx = sd->down.b2x - sd->down.bx; + dx = (dx * p); + x = sd->down.bx + dx; + if (!sd->down.cancelled) + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + if (dt >= 1.0) + { + if (sd->down.momentum_animator) + sd->down.bounce_x_hold = 1; + else if ((!sd->down.bounce_y_animator) && + (!sd->scrollto.y.animator)) + _smart_anim_stop(sd->smart_obj); + sd->down.bounce_x_animator = NULL; + sd->down.pdx = 0; + sd->bouncemex = 0; + _smart_momentum_end(sd); + return ECORE_CALLBACK_CANCEL; + } + } + return ECORE_CALLBACK_RENEW; +} + +static Eina_Bool +_smart_bounce_y_animator(void *data) +{ + Smart_Data *sd; + Evas_Coord x, y, dy; + double t, p, dt; + + sd = data; + t = ecore_loop_time_get(); + dt = t - sd->down.anim_start3; + if (dt >= 0.0) + { + dt = dt / _elm_config->thumbscroll_bounce_friction; + if (dt > 1.0) dt = 1.0; + p = 1.0 - ((1.0 - dt) * (1.0 - dt)); + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + dy = sd->down.b2y - sd->down.by; + dy = (dy * p); + y = sd->down.by + dy; + if (!sd->down.cancelled) + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + if (dt >= 1.0) + { + if (sd->down.momentum_animator) + sd->down.bounce_y_hold = 1; + else if ((!sd->down.bounce_x_animator) && + (!sd->scrollto.y.animator)) + _smart_anim_stop(sd->smart_obj); + sd->down.bounce_y_animator = NULL; + sd->down.pdy = 0; + sd->bouncemey = 0; + _smart_momentum_end(sd); + return ECORE_CALLBACK_CANCEL; + } + } + return ECORE_CALLBACK_RENEW; +} + +#define LEFT 0 +#define RIGHT 1 +#define UP 2 +#define DOWN 3 +static Eina_Bool +can_scroll(Smart_Data *sd, int dir) +{ + Evas_Coord mx = 0, my = 0, px = 0, py = 0, minx = 0, miny = 0; + + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + sd->pan_func.get(sd->pan_obj, &px, &py); + switch (dir) + { + case LEFT: + if (px > minx) return EINA_TRUE; + break; + case RIGHT: + if ((px - minx) < mx) return EINA_TRUE; + break; + case UP: + if (py > miny) return EINA_TRUE; + break; + case DOWN: + if ((py - miny) < my) return EINA_TRUE; + break; + default: + break; + } + return EINA_FALSE; +} + +static Eina_Bool +_smart_momentum_animator(void *data) +{ + Smart_Data *sd; + double t, dt, p; + Evas_Coord x, y, dx, dy, px, py, maxx, maxy, minx, miny; + + sd = data; + t = ecore_loop_time_get(); + dt = t - sd->down.anim_start; + if (dt >= 0.0) + { + /* + if (sd->down.hold_parent) + { + if ((sd->down.dir_x) && !can_scroll(sd, sd->down.hdir)) + { + sd->down.dir_x = 0; + } + if ((sd->down.dir_y) && !can_scroll(sd, sd->down.vdir)) + { + sd->down.dir_y = 0; + } + } + if ((!sd->down.dir_x) && (!sd->down.dir_y)) + { + sd->down.cancelled = 1; + } + */ + dt = dt / (_elm_config->thumbscroll_friction + sd->down.extra_time); + if (dt > 1.0) dt = 1.0; + p = 1.0 - ((1.0 - dt) * (1.0 - dt)); + dx = (sd->down.dx * (_elm_config->thumbscroll_friction + sd->down.extra_time) * p); + dy = (sd->down.dy * (_elm_config->thumbscroll_friction + sd->down.extra_time) * p); + sd->down.ax = dx; + sd->down.ay = dy; + x = sd->down.sx - dx; + y = sd->down.sy - dy; + elm_smart_scroller_child_pos_get(sd->smart_obj, &px, &py); + if ((sd->down.bounce_x_animator) || + (sd->down.bounce_x_hold)) + { + sd->down.bx = sd->down.bx0 - dx + sd->down.b0x; + x = px; + } + if ((sd->down.bounce_y_animator) || + (sd->down.bounce_y_hold)) + { + sd->down.by = sd->down.by0 - dy + sd->down.b0y; + y = py; + } + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + sd->pan_func.max_get(sd->pan_obj, &maxx, &maxy); + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + if ((dt >= 1.0) || + ((sd->down.bounce_x_hold) && (sd->down.bounce_y_hold))) + { + _smart_anim_stop(sd->smart_obj); + sd->down.momentum_animator = NULL; + sd->down.bounce_x_hold = 0; + sd->down.bounce_y_hold = 0; + sd->down.ax = 0; + sd->down.ay = 0; + sd->down.pdx = 0; + sd->down.pdy = 0; + return ECORE_CALLBACK_CANCEL; + } + } + return ECORE_CALLBACK_RENEW; +} + +static void +bounce_eval(Smart_Data *sd) +{ + Evas_Coord mx, my, px, py, bx, by, b2x, b2y, minx = 0, miny = 0; + + if (sd->freeze) return; + if ((!sd->bouncemex) && (!sd->bouncemey)) return; + if (sd->down.now) return; // down bounce while still held down + if (sd->down.onhold_animator) + { + ecore_animator_del(sd->down.onhold_animator); + sd->down.onhold_animator = NULL; + } + if (sd->down.hold_animator) + { + ecore_animator_del(sd->down.hold_animator); + sd->down.hold_animator = NULL; + } + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + sd->pan_func.get(sd->pan_obj, &px, &py); + bx = px; + by = py; + if (px < minx) px = minx; + if ((px - minx) > mx) px = mx + minx; + if (py < miny) py = miny; + if ((py - miny) > my) py = my + miny; + b2x = px; + b2y = py; + if ((!sd->widget) || + (!elm_widget_drag_child_locked_x_get(sd->widget))) + { + if (!sd->down.bounce_x_animator && !sd->bounce_animator_disabled) + { + if (sd->bouncemex) + { + if (sd->scrollto.x.animator) + { + ecore_animator_del(sd->scrollto.x.animator); + sd->scrollto.x.animator = NULL; + } + sd->down.bounce_x_animator = ecore_animator_add(_smart_bounce_x_animator, sd); + sd->down.anim_start2 = ecore_loop_time_get(); + sd->down.bx = bx; + sd->down.bx0 = bx; + sd->down.b2x = b2x; + if (sd->down.momentum_animator) sd->down.b0x = sd->down.ax; + else sd->down.b0x = 0; + } + } + } + if ((!sd->widget) || + (!elm_widget_drag_child_locked_y_get(sd->widget))) + { + if (!sd->down.bounce_y_animator && !sd->bounce_animator_disabled) + { + if (sd->bouncemey) + { + if (sd->scrollto.y.animator) + { + ecore_animator_del(sd->scrollto.y.animator); + sd->scrollto.y.animator = NULL; + } + sd->down.bounce_y_animator = ecore_animator_add(_smart_bounce_y_animator, sd); + sd->down.anim_start3 = ecore_loop_time_get(); + sd->down.by = by; + sd->down.by0 = by; + sd->down.b2y = b2y; + if (sd->down.momentum_animator) sd->down.b0y = sd->down.ay; + else sd->down.b0y = 0; + } + } + } +} + +void +elm_smart_scroller_child_pos_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + Evas_Coord mx = 0, my = 0, px, py, minx = 0, miny = 0; + double vx, vy; + + API_ENTRY return; + // FIXME: allow for bounce outside of range + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + if (mx > 0) vx = (double)(x - minx) / (double)mx; + else vx = 0.0; + if (vx < 0.0) vx = 0.0; + else if (vx > 1.0) vx = 1.0; + if (my > 0) vy = (double)(y - miny) / (double)my; + else vy = 0.0; + if (vy < 0.0) vy = 0.0; + else if (vy > 1.0) vy = 1.0; + edje_object_part_drag_value_set(sd->edje_obj, "elm.dragable.vbar", 0.0, vy); + edje_object_part_drag_value_set(sd->edje_obj, "elm.dragable.hbar", vx, 0.0); + sd->pan_func.get(sd->pan_obj, &px, &py); + if (!_elm_config->thumbscroll_bounce_enable) + { + if (x < minx) x = minx; + if ((x - minx) > mx) x = mx + minx; + if (y < miny) y = miny; + if ((y - miny) > my) y = my + miny; + } + + if (!sd->bounce_horiz) + { + if (x < minx) x = minx; + if ((x - minx) > mx) x = mx + minx; + } + if (!sd->bounce_vert) + { + if (y < miny) y = miny; + if (y - miny > my) y = my + miny; + } + + sd->pan_func.set(sd->pan_obj, x, y); + if ((px != x) || (py != y)) + edje_object_signal_emit(sd->edje_obj, "elm,action,scroll", "elm"); + if (!sd->down.bounce_x_animator) + { + if ((x < minx) || (x > (mx + minx))) + { + sd->bouncemex = 1; + bounce_eval(sd); + } + } + if (!sd->down.bounce_y_animator) + { + if ((y < miny) || (y > my + miny)) + { + sd->bouncemey = 1; + bounce_eval(sd); + } + } + if ((x != px) || (y != py)) + { + evas_object_smart_callback_call(obj, "scroll", NULL); + } + if ((x != px)/* && (!sd->bouncemex)*/) + { + if (x == minx) + evas_object_smart_callback_call(obj, "edge,left", NULL); + if (x == (mx + minx)) + evas_object_smart_callback_call(obj, "edge,right", NULL); + } + if ((y != py)/* && (!sd->bouncemey)*/) + { + if (y == miny) + evas_object_smart_callback_call(obj, "edge,top", NULL); + if (y == my + miny) + evas_object_smart_callback_call(obj, "edge,bottom", NULL); + } +} + +void +elm_smart_scroller_child_pos_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + API_ENTRY return; + sd->pan_func.get(sd->pan_obj, x, y); +} + +/* "internal_call" actually toggles whether we should save the coords and do + * extra "speedup" checks, or not. */ +static void +_elm_smart_scroller_child_region_show_internal(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h, Eina_Bool internal_call) +{ + Evas_Coord mx = 0, my = 0, cw = 0, ch = 0, px = 0, py = 0, nx, ny, minx = 0, miny = 0; + + API_ENTRY return; + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + sd->pan_func.child_size_get(sd->pan_obj, &cw, &ch); + sd->pan_func.get(sd->pan_obj, &px, &py); + + nx = px; + if (x < px) nx = x; + else if ((x + w) > (px + (cw - mx))) + { + nx = x + w - (cw - mx); + if (nx > x) nx = x; + } + ny = py; + if (y < py) ny = y; + else if ((y + h) > (py + (ch - my))) + { + ny = y + h - (ch - my); + if (ny > y) ny = y; + } + if (!internal_call) + { + sd->wx = x; + sd->wy = y; + sd->ww = w; + sd->wh = h; + if ((nx == px) && (ny == py)) return; + } + + if ((sd->down.bounce_x_animator) || (sd->down.bounce_y_animator) || + (sd->scrollto.x.animator) || (sd->scrollto.y.animator)) + { + _smart_anim_stop(sd->smart_obj); + } + if (sd->scrollto.x.animator) + { + ecore_animator_del(sd->scrollto.x.animator); + sd->scrollto.x.animator = NULL; + } + if (sd->scrollto.y.animator) + { + ecore_animator_del(sd->scrollto.y.animator); + sd->scrollto.y.animator = NULL; + } + if (sd->down.bounce_x_animator) + { + ecore_animator_del(sd->down.bounce_x_animator); + sd->down.bounce_x_animator = NULL; + sd->bouncemex = 0; + } + if (sd->down.bounce_y_animator) + { + ecore_animator_del(sd->down.bounce_y_animator); + sd->down.bounce_y_animator = NULL; + sd->bouncemey = 0; + } + if (sd->down.hold_animator) + { + ecore_animator_del(sd->down.hold_animator); + sd->down.hold_animator = NULL; + _smart_drag_stop(sd->smart_obj); + } + if (sd->down.momentum_animator) + { + ecore_animator_del(sd->down.momentum_animator); + sd->down.momentum_animator = NULL; + sd->down.bounce_x_hold = 0; + sd->down.bounce_y_hold = 0; + sd->down.ax = 0; + sd->down.ay = 0; + sd->down.pdx = 0; + sd->down.pdy = 0; + } + elm_smart_scroller_child_pos_set(obj, nx, ny); +} + +/* Set should be used for calculated positions, for example, when we move + * because of an animation or because this is the correct position after + * constraints. */ +void +elm_smart_scroller_child_region_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h) +{ + _elm_smart_scroller_child_region_show_internal(obj, x, y, w, h, EINA_TRUE); +} + +/* Set should be used for setting the wanted position, for example a user scroll + * or moving the cursor in an entry. */ +void +elm_smart_scroller_child_region_show(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h) +{ + _elm_smart_scroller_child_region_show_internal(obj, x, y, w, h, EINA_FALSE); +} + +void +elm_smart_scroller_child_viewport_size_get(Evas_Object *obj, Evas_Coord *w, Evas_Coord *h) +{ + API_ENTRY return; + edje_object_calc_force(sd->edje_obj); + evas_object_geometry_get(sd->pan_obj, NULL, NULL, w, h); +} + +void +elm_smart_scroller_step_size_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + API_ENTRY return; + if (x < 1) x = 1; + if (y < 1) y = 1; + sd->step.x = x; + sd->step.y = y; + _smart_scrollbar_size_adjust(sd); +} + +void +elm_smart_scroller_step_size_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + API_ENTRY return; + if (x) *x = sd->step.x; + if (y) *y = sd->step.y; +} + +void +elm_smart_scroller_page_size_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + API_ENTRY return; + sd->page.x = x; + sd->page.y = y; + _smart_scrollbar_size_adjust(sd); +} + +void +elm_smart_scroller_page_size_get(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y) +{ + API_ENTRY return; + if (x) *x = sd->page.x; + if (y) *y = sd->page.y; +} + +void +elm_smart_scroller_policy_set(Evas_Object *obj, Elm_Smart_Scroller_Policy hbar, Elm_Smart_Scroller_Policy vbar) +{ + API_ENTRY return; + if ((sd->hbar_flags == hbar) && (sd->vbar_flags == vbar)) return; + sd->hbar_flags = hbar; + sd->vbar_flags = vbar; + if (sd->hbar_flags == ELM_SMART_SCROLLER_POLICY_ON) + edje_object_signal_emit(sd->edje_obj, "elm,action,show_always,hbar", "elm"); + else if (sd->hbar_flags == ELM_SMART_SCROLLER_POLICY_OFF) + edje_object_signal_emit(sd->edje_obj, "elm,action,hide,hbar", "elm"); + else + edje_object_signal_emit(sd->edje_obj, "elm,action,show_notalways,hbar", "elm"); + if (sd->vbar_flags == ELM_SMART_SCROLLER_POLICY_ON) + edje_object_signal_emit(sd->edje_obj, "elm,action,show_always,vbar", "elm"); + else if (sd->vbar_flags == ELM_SMART_SCROLLER_POLICY_OFF) + edje_object_signal_emit(sd->edje_obj, "elm,action,hide,vbar", "elm"); + else + edje_object_signal_emit(sd->edje_obj, "elm,action,show_notalways,vbar", "elm"); + _smart_scrollbar_size_adjust(sd); +} + +void +elm_smart_scroller_policy_get(Evas_Object *obj, Elm_Smart_Scroller_Policy *hbar, Elm_Smart_Scroller_Policy *vbar) +{ + API_ENTRY return; + if (hbar) *hbar = sd->hbar_flags; + if (vbar) *vbar = sd->vbar_flags; +} + +Evas_Object * +elm_smart_scroller_edje_object_get(Evas_Object *obj) +{ + API_ENTRY return NULL; + return sd->edje_obj; +} + +void +elm_smart_scroller_single_dir_set(Evas_Object *obj, Eina_Bool single_dir) +{ + API_ENTRY return; + sd->one_dir_at_a_time = single_dir; +} + +Eina_Bool +elm_smart_scroller_single_dir_get(Evas_Object *obj) +{ + API_ENTRY return EINA_FALSE; + return sd->one_dir_at_a_time; +} + +void +elm_smart_scroller_object_theme_set(Evas_Object *parent, Evas_Object *obj, const char *clas, const char *group, const char *style) +{ + API_ENTRY return; + Evas_Coord mw, mh; + _elm_theme_object_set(parent, sd->edje_obj, clas, group, style); + edje_object_scale_set(sd->edje_obj, elm_widget_scale_get(parent) * _elm_config->scale); + if (sd->pan_obj) + edje_object_part_swallow(sd->edje_obj, "elm.swallow.content", sd->pan_obj); + mw = mh = -1; + elm_coords_finger_size_adjust(1, &mw, 1, &mh); + if (edje_object_part_exists(sd->edje_obj, "elm.scrollbar.base")) + { + Evas_Object *base; + base = edje_object_part_swallow_get(sd->edje_obj, "elm.scrollbar.base"); + if (!base) + { + base = evas_object_rectangle_add(evas_object_evas_get(sd->edje_obj)); + evas_object_color_set(base, 0, 0, 0, 0); + edje_object_part_swallow(sd->edje_obj, "elm.scrollbar.base", base); + } + if (!_elm_config->thumbscroll_enable) + evas_object_size_hint_min_set(base, mw, mh); + } + sd->vbar_visible = !sd->vbar_visible; + sd->hbar_visible = !sd->hbar_visible; + _smart_scrollbar_bar_visibility_adjust(sd); +} + +void +elm_smart_scroller_hold_set(Evas_Object *obj, Eina_Bool hold) +{ + API_ENTRY return; + sd->hold = hold; +} + +void +elm_smart_scroller_freeze_set(Evas_Object *obj, Eina_Bool freeze) +{ + API_ENTRY return; + sd->freeze = freeze; + if (sd->freeze) + { + if (sd->down.onhold_animator) + { + ecore_animator_del(sd->down.onhold_animator); + sd->down.onhold_animator = NULL; + } + } +} + +void +elm_smart_scroller_bounce_allow_set(Evas_Object *obj, Eina_Bool horiz, Eina_Bool vert) +{ + API_ENTRY return; + sd->bounce_horiz = horiz; + sd->bounce_vert = vert; +} + +void +elm_smart_scroller_bounce_allow_get(const Evas_Object *obj, Eina_Bool *horiz, Eina_Bool *vert) +{ + API_ENTRY return; + *horiz = sd->bounce_horiz; + *vert = sd->bounce_vert; +} + +void +elm_smart_scroller_paging_set(Evas_Object *obj, double pagerel_h, double pagerel_v, Evas_Coord pagesize_h, Evas_Coord pagesize_v) +{ + API_ENTRY return; + sd->pagerel_h = pagerel_h; + sd->pagerel_v = pagerel_v; + sd->pagesize_h = pagesize_h; + sd->pagesize_v = pagesize_v; + _smart_page_adjust(sd); +} + +void +elm_smart_scroller_paging_get(Evas_Object *obj, double *pagerel_h, double *pagerel_v, Evas_Coord *pagesize_h, Evas_Coord *pagesize_v) +{ + API_ENTRY return; + if(pagerel_h) *pagerel_h = sd->pagerel_h; + if(pagerel_v) *pagerel_v = sd->pagerel_v; + if(pagesize_h) *pagesize_h = sd->pagesize_h; + if(pagesize_v) *pagesize_v = sd->pagesize_v; +} + +void +elm_smart_scroller_region_bring_in(Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h) +{ + Evas_Coord mx = 0, my = 0, cw = 0, ch = 0, px = 0, py = 0, nx, ny, minx = 0, miny = 0; + + API_ENTRY return; + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + sd->pan_func.child_size_get(sd->pan_obj, &cw, &ch); + sd->pan_func.get(sd->pan_obj, &px, &py); + + nx = px; + if (x < px) nx = x; + else if ((x + w) > (px + (cw - mx))) + { + nx = x + w - (cw - mx); + if (nx > x) nx = x; + } + ny = py; + if (y < py) ny = y; + else if ((y + h) > (py + (ch - my))) + { + ny = y + h - (ch - my); + if (ny > y) ny = y; + } + if ((nx == px) && (ny == py)) return; + if ((sd->down.bounce_x_animator) || (sd->down.bounce_y_animator) || + (sd->scrollto.x.animator) || (sd->scrollto.y.animator)) + { + _smart_anim_stop(sd->smart_obj); + } + if (sd->scrollto.x.animator) + { + ecore_animator_del(sd->scrollto.x.animator); + sd->scrollto.x.animator = NULL; + } + if (sd->scrollto.y.animator) + { + ecore_animator_del(sd->scrollto.y.animator); + sd->scrollto.y.animator = NULL; + } + if (sd->down.bounce_x_animator) + { + ecore_animator_del(sd->down.bounce_x_animator); + sd->down.bounce_x_animator = NULL; + sd->bouncemex = 0; + } + if (sd->down.bounce_y_animator) + { + ecore_animator_del(sd->down.bounce_y_animator); + sd->down.bounce_y_animator = NULL; + sd->bouncemey = 0; + } + if (sd->down.hold_animator) + { + ecore_animator_del(sd->down.hold_animator); + sd->down.hold_animator = NULL; + _smart_drag_stop(sd->smart_obj); + } + if (sd->down.momentum_animator) + { + ecore_animator_del(sd->down.momentum_animator); + sd->down.momentum_animator = NULL; + sd->down.bounce_x_hold = 0; + sd->down.bounce_y_hold = 0; + sd->down.ax = 0; + sd->down.ay = 0; + sd->down.pdx = 0; + sd->down.pdy = 0; + } + x = nx; + if (x < minx) x = minx; + else if ((x + w) > cw) x = cw - w; + _smart_scrollto_x(sd, _elm_config->bring_in_scroll_friction, x); + y = ny; + if (y < miny) y = miny; + else if ((y + h) > ch) y = ch - h; + _smart_scrollto_y(sd, _elm_config->bring_in_scroll_friction, y); +} + +void +elm_smart_scroller_widget_set(Evas_Object *obj, Evas_Object *wid) +{ + API_ENTRY return; + sd->widget = wid; +} + +/* local subsystem functions */ +static void +_smart_edje_drag_v_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Smart_Data *sd; + + sd = data; + _smart_scrollbar_read(sd); + _smart_drag_start(sd->smart_obj); +} + +static void +_smart_edje_drag_v_stop(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Smart_Data *sd; + + sd = data; + _smart_scrollbar_read(sd); + _smart_drag_stop(sd->smart_obj); +} + +static void +_smart_edje_drag_v(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Smart_Data *sd; + + sd = data; + _smart_scrollbar_read(sd); +} + +static void +_smart_edje_drag_h_start(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Smart_Data *sd; + + sd = data; + _smart_scrollbar_read(sd); + _smart_drag_start(sd->smart_obj); +} + +static void +_smart_edje_drag_h_stop(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Smart_Data *sd; + + sd = data; + _smart_scrollbar_read(sd); + _smart_drag_stop(sd->smart_obj); +} + +static void +_smart_edje_drag_h(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__) +{ + Smart_Data *sd; + + sd = data; + _smart_scrollbar_read(sd); +} + +static void +_smart_child_del_hook(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Smart_Data *sd; + + sd = data; + sd->child_obj = NULL; + _smart_scrollbar_size_adjust(sd); + _smart_scrollbar_reset(sd); +} + +static void +_smart_pan_changed_hook(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Coord x, y; + Evas_Coord w, h; + Smart_Data *sd; + + sd = data; + sd->pan_func.get(sd->pan_obj, &x, &y); + sd->pan_func.child_size_get(sd->pan_obj, &w, &h); + if ((w != sd->child.w) || (h != sd->child.h)) + { + sd->child.w = w; + sd->child.h = h; + _smart_scrollbar_size_adjust(sd); + evas_object_size_hint_min_set(sd->smart_obj, sd->child.w, sd->child.h); + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + } +} + +static void +_smart_pan_pan_changed_hook(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Evas_Coord x, y; + Smart_Data *sd; + + sd = data; + sd->pan_func.get(sd->pan_obj, &x, &y); + if ((sd->down.bounce_x_animator) || (sd->down.bounce_y_animator) || + (sd->scrollto.x.animator) || (sd->scrollto.y.animator)) + { + _smart_anim_stop(sd->smart_obj); + } + if (sd->scrollto.x.animator) + { + ecore_animator_del(sd->scrollto.x.animator); + sd->scrollto.x.animator = NULL; + } + if (sd->scrollto.y.animator) + { + ecore_animator_del(sd->scrollto.y.animator); + sd->scrollto.y.animator = NULL; + } + if (sd->down.bounce_x_animator) + { + ecore_animator_del(sd->down.bounce_x_animator); + sd->down.bounce_x_animator = NULL; + sd->bouncemex = 0; + } + if (sd->down.bounce_y_animator) + { + ecore_animator_del(sd->down.bounce_y_animator); + sd->down.bounce_y_animator = NULL; + sd->bouncemey = 0; + } + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); +} + +static void +_smart_event_wheel(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Wheel *ev; + Smart_Data *sd; + Evas_Coord x = 0, y = 0; + + sd = data; + ev = event_info; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return ; + if ((evas_key_modifier_is_set(ev->modifiers, "Control")) || + (evas_key_modifier_is_set(ev->modifiers, "Alt")) || + (evas_key_modifier_is_set(ev->modifiers, "Shift")) || + (evas_key_modifier_is_set(ev->modifiers, "Meta")) || + (evas_key_modifier_is_set(ev->modifiers, "Hyper")) || + (evas_key_modifier_is_set(ev->modifiers, "Super"))) + return; + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + if ((sd->down.bounce_x_animator) || (sd->down.bounce_y_animator) || + (sd->scrollto.x.animator) || (sd->scrollto.y.animator)) + { + _smart_anim_stop(sd->smart_obj); + } + if (sd->scrollto.x.animator) + { + ecore_animator_del(sd->scrollto.x.animator); + sd->scrollto.x.animator = NULL; + } + if (sd->scrollto.y.animator) + { + ecore_animator_del(sd->scrollto.y.animator); + sd->scrollto.y.animator = NULL; + } + if (sd->down.bounce_x_animator) + { + ecore_animator_del(sd->down.bounce_x_animator); + sd->down.bounce_x_animator = NULL; + sd->bouncemex = 0; + } + if (sd->down.bounce_y_animator) + { + ecore_animator_del(sd->down.bounce_y_animator); + sd->down.bounce_y_animator = NULL; + sd->bouncemey = 0; + } + if (!ev->direction) + y += ev->z * sd->step.y; + else if (ev->direction == 1) + x += ev->z * sd->step.x; + + if ((!sd->hold) && (!sd->freeze)) + { + sd->wx = x; + sd->wy = y; + elm_smart_scroller_child_viewport_size_get(sd->smart_obj, &sd->ww, &sd->wh); + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + } +} + +static void +_smart_event_mouse_down(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Down *ev; + Smart_Data *sd; + Evas_Coord x = 0, y = 0; + + sd = data; + ev = event_info; +// if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return ; + if (_elm_config->thumbscroll_enable) + { + sd->down.hold = 0; + if ((sd->down.bounce_x_animator) || (sd->down.bounce_y_animator) || + (sd->down.momentum_animator) || (sd->scrollto.x.animator) || + (sd->scrollto.y.animator)) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_SCROLL | EVAS_EVENT_FLAG_ON_HOLD; + sd->down.scroll = 1; + sd->down.hold = 1; + _smart_anim_stop(sd->smart_obj); + } + if (sd->scrollto.x.animator) + { + ecore_animator_del(sd->scrollto.x.animator); + sd->scrollto.x.animator = NULL; + } + if (sd->scrollto.y.animator) + { + ecore_animator_del(sd->scrollto.y.animator); + sd->scrollto.y.animator = NULL; + } + if (sd->down.bounce_x_animator) + { + ecore_animator_del(sd->down.bounce_x_animator); + sd->down.bounce_x_animator = NULL; + sd->bouncemex = 0; + } + if (sd->down.bounce_y_animator) + { + ecore_animator_del(sd->down.bounce_y_animator); + sd->down.bounce_y_animator = NULL; + sd->bouncemey = 0; + } + if (sd->down.hold_animator) + { + ecore_animator_del(sd->down.hold_animator); + sd->down.hold_animator = NULL; + _smart_drag_stop(sd->smart_obj); + } + if (sd->down.momentum_animator) + { + ecore_animator_del(sd->down.momentum_animator); + sd->down.momentum_animator = NULL; + sd->down.bounce_x_hold = 0; + sd->down.bounce_y_hold = 0; + sd->down.ax = 0; + sd->down.ay = 0; + } + if (ev->button == 1) + { + sd->down.now = 1; + sd->down.dragged = 0; + sd->down.dir_x = 0; + sd->down.dir_y = 0; + sd->down.x = ev->canvas.x; + sd->down.y = ev->canvas.y; + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + sd->down.sx = x; + sd->down.sy = y; + sd->down.locked = 0; + memset(&(sd->down.history[0]), 0, sizeof(sd->down.history[0]) * 20); +#ifdef EVTIME + sd->down.history[0].timestamp = ev->timestamp / 1000.0; +#else + sd->down.history[0].timestamp = ecore_loop_time_get(); +#endif + sd->down.history[0].x = ev->canvas.x; + sd->down.history[0].y = ev->canvas.y; + } + sd->down.dragged_began = 0; + sd->down.hold_parent = 0; + sd->down.cancelled = 0; + } +} + +static Eina_Bool +_smart_hold_animator(void *data) +{ + Smart_Data *sd = data; + Evas_Coord ox, oy; + + elm_smart_scroller_child_pos_get(sd->smart_obj, &ox, &oy); + if (sd->down.dir_x) + { + if ((!sd->widget) || + (!elm_widget_drag_child_locked_x_get(sd->widget))) + { + ox = sd->down.hold_x; + } + } + if (sd->down.dir_y) + { + if ((!sd->widget) || + (!elm_widget_drag_child_locked_y_get(sd->widget))) + { + oy = sd->down.hold_y; + } + } + elm_smart_scroller_child_pos_set(sd->smart_obj, ox, oy); + return ECORE_CALLBACK_RENEW; +} + +static Eina_Bool +_smart_event_post_up(void *data, Evas *e __UNUSED__) +{ + Smart_Data *sd = data; + if (sd->widget) + { + if (sd->down.dragged) + { + elm_widget_drag_lock_x_set(sd->widget, 0); + elm_widget_drag_lock_y_set(sd->widget, 0); + } + } + return EINA_TRUE; +} + +static void +_smart_event_mouse_up(void *data, Evas *e, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Down *ev; + Smart_Data *sd; + Evas_Coord x = 0, y = 0, ox = 0, oy = 0; + + sd = data; + ev = event_info; + sd->down.hold_parent = 0; +// if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return ; + evas_post_event_callback_push(e, _smart_event_post_up, sd); + // FIXME: respect elm_widget_scroll_hold_get of parent container + if (_elm_config->thumbscroll_enable) + { + if (ev->button == 1) + { + if (sd->down.onhold_animator) + { + ecore_animator_del(sd->down.onhold_animator); + sd->down.onhold_animator = NULL; + } + x = ev->canvas.x - sd->down.x; + y = ev->canvas.y - sd->down.y; + if (sd->down.dragged) + { + _smart_drag_stop(sd->smart_obj); + if ((!sd->hold) && (!sd->freeze)) + { + double t, at, dt; + int i; + Evas_Coord ax, ay, dx, dy, vel; + +#ifdef EVTIME + t = ev->timestamp / 1000.0; +#else + t = ecore_loop_time_get(); +#endif + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + ax = ev->canvas.x; + ay = ev->canvas.y; + at = 0.0; +#ifdef SCROLLDBG + printf("------ %i %i\n", ev->canvas.x, ev->canvas.y); +#endif + for (i = 0; i < 20; i++) + { + dt = t - sd->down.history[i].timestamp; + if (dt > 0.2) break; +#ifdef SCROLLDBG + printf("H: %i %i @ %1.3f\n", + sd->down.history[i].x, + sd->down.history[i].y, dt); +#endif + at += dt; + ax += sd->down.history[i].x; + ay += sd->down.history[i].y; + } + ax /= (i + 1); + ay /= (i + 1); + at /= (i + 1); + at *= 4.0; + dx = ev->canvas.x - ax; + dy = ev->canvas.y - ay; + if (at > 0) + { + vel = sqrt((dx * dx) + (dy * dy)) / at; + if ((_elm_config->thumbscroll_friction > 0.0) && + (vel > _elm_config->thumbscroll_momentum_threshold) && + (!sd->freeze)) + { + sd->down.dx = ((double)dx / at); + sd->down.dy = ((double)dy / at); + if (((sd->down.dx > 0) && (sd->down.pdx > 0)) || + ((sd->down.dx < 0) && (sd->down.pdx < 0))) + sd->down.dx += (double)sd->down.pdx * 1.5; // FIXME: * 1.5 - probably should be config + if (((sd->down.dy > 0) && (sd->down.pdy > 0)) || + ((sd->down.dy < 0) && (sd->down.pdy < 0))) + sd->down.dy += (double)sd->down.pdy * 1.5; // FIXME: * 1.5 - probably should be config + if (((sd->down.dx > 0) && (sd->down.pdx > 0)) || + ((sd->down.dx < 0) && (sd->down.pdx < 0)) || + ((sd->down.dy > 0) && (sd->down.pdy > 0)) || + ((sd->down.dy < 0) && (sd->down.pdy < 0))) + { + double t = ecore_loop_time_get(); + double dt = t - sd->down.anim_start; + + if (dt < 0.0) dt = 0.0; + else if (dt > _elm_config->thumbscroll_friction) + dt = _elm_config->thumbscroll_friction; + sd->down.extra_time = _elm_config->thumbscroll_friction - dt; + } + else + sd->down.extra_time = 0.0; + sd->down.pdx = sd->down.dx; + sd->down.pdy = sd->down.dy; + ox = -sd->down.dx; + oy = -sd->down.dy; + if (!_smart_do_page(sd)) + { + if (!sd->down.momentum_animator && !sd->momentum_animator_disabled) + { + sd->down.momentum_animator = ecore_animator_add(_smart_momentum_animator, sd); + ev->event_flags |= EVAS_EVENT_FLAG_ON_SCROLL; + _smart_anim_start(sd->smart_obj); + } + sd->down.anim_start = ecore_loop_time_get(); + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + sd->down.sx = x; + sd->down.sy = y; + sd->down.b0x = 0; + sd->down.b0y = 0; + } + } + } + if (sd->down.hold_animator) + { + ecore_animator_del(sd->down.hold_animator); + sd->down.hold_animator = NULL; + } + } + else + { + sd->down.pdx = 0; + sd->down.pdy = 0; + } + evas_event_feed_hold(e, 0, ev->timestamp, ev->data); + if (_smart_do_page(sd)) + { + Evas_Coord pgx, pgy; + + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + if ((!sd->widget) || + (!elm_widget_drag_child_locked_x_get(sd->widget))) + { + pgx = _smart_page_x_get(sd, ox); + if (pgx != x) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_SCROLL; + _smart_scrollto_x(sd, _elm_config->page_scroll_friction, pgx); + } + } + if ((!sd->widget) || + (!elm_widget_drag_child_locked_y_get(sd->widget))) + { + pgy = _smart_page_y_get(sd, oy); + if (pgy != y) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_SCROLL; + _smart_scrollto_y(sd, _elm_config->page_scroll_friction, pgy); + } + } + } + } + else + { + sd->down.pdx = 0; + sd->down.pdy = 0; + if (_smart_do_page(sd)) + { + Evas_Coord pgx, pgy; + + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + if ((!sd->widget) || + (!elm_widget_drag_child_locked_x_get(sd->widget))) + { + pgx = _smart_page_x_get(sd, ox); + if (pgx != x) _smart_scrollto_x(sd, _elm_config->page_scroll_friction, pgx); + } + if ((!sd->widget) || + (!elm_widget_drag_child_locked_y_get(sd->widget))) + { + pgy = _smart_page_y_get(sd, oy); + if (pgy != y) _smart_scrollto_y(sd, _elm_config->page_scroll_friction, pgy); + } + } + if (sd->down.hold_animator) + { + ecore_animator_del(sd->down.hold_animator); + sd->down.hold_animator = NULL; + } + } + if (sd->down.scroll) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_SCROLL; + sd->down.scroll = 0; + } + if (sd->down.hold) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + sd->down.hold = 0; + } + sd->down.dragged_began = 0; + sd->down.dir_x = 0; + sd->down.dir_y = 0; + sd->down.want_dragged = 0; + sd->down.dragged = 0; + sd->down.now = 0; + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + sd->wx = x; + sd->wy = y; + elm_smart_scroller_child_viewport_size_get(sd->smart_obj, &sd->ww, &sd->wh); + if (!_smart_do_page(sd)) + bounce_eval(sd); + } + } +} + +static Eina_Bool +_smart_onhold_animator(void *data) +{ + Smart_Data *sd; + double t, td; + double vx, vy; + Evas_Coord x, y, ox, oy; + + sd = data; + t = ecore_loop_time_get(); + if (sd->down.onhold_tlast > 0.0) + { + td = t - sd->down.onhold_tlast; + vx = sd->down.onhold_vx * td * (double)_elm_config->thumbscroll_threshold * 2.0; + vy = sd->down.onhold_vy * td * (double)_elm_config->thumbscroll_threshold * 2.0; + elm_smart_scroller_child_pos_get(sd->smart_obj, &ox, &oy); + x = ox; + y = oy; + + if (sd->down.dir_x) + { + if ((!sd->widget) || + (!elm_widget_drag_child_locked_x_get(sd->widget))) + { + sd->down.onhold_vxe += vx; + x = ox + (int)sd->down.onhold_vxe; + sd->down.onhold_vxe -= (int)sd->down.onhold_vxe; + } + } + + if (sd->down.dir_y) + { + if ((!sd->widget) || + (!elm_widget_drag_child_locked_y_get(sd->widget))) + { + sd->down.onhold_vye += vy; + y = oy + (int)sd->down.onhold_vye; + sd->down.onhold_vye -= (int)sd->down.onhold_vye; + } + } + + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + } + sd->down.onhold_tlast = t; + return ECORE_CALLBACK_RENEW; +} + +static Eina_Bool +_smart_event_post_move(void *data, Evas *e __UNUSED__) +{ + Smart_Data *sd = data; + + if (sd->down.want_dragged) + { + int start = 0; + + if (sd->down.hold_parent) + { + if ((sd->down.dir_x) && !can_scroll(sd, sd->down.hdir)) + { + sd->down.dir_x = 0; + } + if ((sd->down.dir_y) && !can_scroll(sd, sd->down.vdir)) + { + sd->down.dir_y = 0; + } + } + if (sd->down.dir_x) + { + if ((!sd->widget) || + (!elm_widget_drag_child_locked_x_get(sd->widget))) + { + sd->down.want_dragged = 0; + sd->down.dragged = 1; + if (sd->widget) + { + elm_widget_drag_lock_x_set(sd->widget, 1); + } + start = 1; + } + else + sd->down.dir_x = 0; + } + if (sd->down.dir_y) + { + if ((!sd->widget) || + (!elm_widget_drag_child_locked_y_get(sd->widget))) + { + sd->down.want_dragged = 0; + sd->down.dragged = 1; + if (sd->widget) + { + elm_widget_drag_lock_y_set(sd->widget, 1); + } + start = 1; + } + else + sd->down.dir_y = 0; + } + if ((!sd->down.dir_x) && (!sd->down.dir_y)) + { + sd->down.cancelled = 1; + } + if (start) _smart_drag_start(sd->smart_obj); + } + return EINA_TRUE; +} + +static void +_smart_event_mouse_move(void *data, Evas *e, Evas_Object *obj __UNUSED__, void *event_info) +{ + Evas_Event_Mouse_Move *ev; + Smart_Data *sd; + Evas_Coord x = 0, y = 0; + + sd = data; + ev = event_info; +// if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return ; + if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) sd->down.hold_parent = 1; + evas_post_event_callback_push(e, _smart_event_post_move, sd); + // FIXME: respect elm_widget_scroll_hold_get of parent container + if (_elm_config->thumbscroll_enable) + { + if (sd->down.now) + { + int dodir = 0; + +#ifdef SCROLLDBG + printf("::: %i %i\n", ev->cur.canvas.x, ev->cur.canvas.y); +#endif + memmove(&(sd->down.history[1]), &(sd->down.history[0]), + sizeof(sd->down.history[0]) * 19); +#ifdef EVTIME + sd->down.history[0].timestamp = ev->timestamp / 1000.0; +#else + sd->down.history[0].timestamp = ecore_loop_time_get(); +#endif + sd->down.history[0].x = ev->cur.canvas.x; + sd->down.history[0].y = ev->cur.canvas.y; + + if (!sd->down.dragged_began) + { + x = ev->cur.canvas.x - sd->down.x; + y = ev->cur.canvas.y - sd->down.y; + + sd->down.hdir = -1; + sd->down.vdir = -1; + + if (x > 0) sd->down.hdir = LEFT; + else if (x < 0) sd->down.hdir = RIGHT; + if (y > 0) sd->down.vdir = UP; + else if (y < 0) sd->down.vdir = DOWN; + + if (x < 0) x = -x; + if (y < 0) y = -y; + + if ((sd->one_dir_at_a_time) && + (!((sd->down.dir_x) || (sd->down.dir_y)))) + { + if (x > _elm_config->thumbscroll_threshold) + { + if (x > (y * 2)) + { + sd->down.dir_x = 1; + sd->down.dir_y = 0; + dodir++; + } + } + if (y > _elm_config->thumbscroll_threshold) + { + if (y > (x * 2)) + { + sd->down.dir_x = 0; + sd->down.dir_y = 1; + dodir++; + } + } + if (!dodir) + { + sd->down.dir_x = 1; + sd->down.dir_y = 1; + } + } + else + { +// can_scroll(sd, LEFT); +// can_scroll(sd, RIGHT); +// can_scroll(sd, UP); +// can_scroll(sd, DOWN); + sd->down.dir_x = 1; + sd->down.dir_y = 1; + } + } + if ((!sd->hold) && (!sd->freeze)) + { + if ((sd->down.dragged) || + (((x * x) + (y * y)) > + (_elm_config->thumbscroll_threshold * + _elm_config->thumbscroll_threshold))) + { + sd->down.dragged_began = 1; + if (!sd->down.dragged) + { + sd->down.want_dragged = 1; + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; +// evas_event_feed_hold(e, 1, ev->timestamp, ev->data); +// _smart_drag_start(sd->smart_obj); + } + if (sd->down.dragged) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + } +// ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; +// sd->down.dragged = 1; + if (sd->down.dir_x) + x = sd->down.sx - (ev->cur.canvas.x - sd->down.x); + else + x = sd->down.sx; + if (sd->down.dir_y) + y = sd->down.sy - (ev->cur.canvas.y - sd->down.y); + else + y = sd->down.sy; + if ((sd->down.dir_x) || (sd->down.dir_y)) + { + if (!sd->down.locked) + { + sd->down.locked_x = x; + sd->down.locked_y = y; + sd->down.locked = 1; + } + if (!((sd->down.dir_x) && (sd->down.dir_y))) + { + if (sd->down.dir_x) y = sd->down.locked_y; + else x = sd->down.locked_x; + } + } + if (_elm_config->thumbscroll_border_friction > 0.0) + { + Evas_Coord minx, miny; + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + if (y < miny) + y += (miny - y) * + _elm_config->thumbscroll_border_friction; + else if (sd->child.h <= sd->h) + y += (sd->down.sy - y) * + _elm_config->thumbscroll_border_friction; + else if ((sd->child.h - sd->h + miny) < y) + y += (sd->child.h - sd->h + miny - y) * + _elm_config->thumbscroll_border_friction; + if (x < minx) + x += (minx - x) * + _elm_config->thumbscroll_border_friction; + else if (sd->child.w <= sd->w) + x += (sd->down.sx - x) * + _elm_config->thumbscroll_border_friction; + else if ((sd->child.w - sd->w + minx) < x) + x += (sd->child.w - sd->w + minx - x) * + _elm_config->thumbscroll_border_friction; + } + + sd->down.hold_x = x; + sd->down.hold_y = y; + if (!sd->down.hold_animator) + sd->down.hold_animator = + ecore_animator_add(_smart_hold_animator, sd); +// printf("a %i %i\n", sd->down.hold_x, sd->down.hold_y); +// _smart_onhold_animator(sd); +// elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + } + else + { + if (sd->down.dragged_began) + { + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + if (!sd->down.hold) + { + sd->down.hold = 1; + evas_event_feed_hold(e, 1, ev->timestamp, ev->data); + } + } + } + } + else if (!sd->freeze) + { + Evas_Coord ex, ey, ew, eh; + double vx = 0.0, vy = 0.0; + + evas_object_geometry_get(sd->event_obj, &ex, &ey, &ew, &eh); + x = ev->cur.canvas.x - ex; + y = ev->cur.canvas.y - ey; + if (x < _elm_config->thumbscroll_threshold) + { + if (_elm_config->thumbscroll_threshold > 0.0) + vx = -(double)(_elm_config->thumbscroll_threshold - x) / + _elm_config->thumbscroll_threshold; + else + vx = -1.0; + } + else if (x > (ew - _elm_config->thumbscroll_threshold)) + { + if (_elm_config->thumbscroll_threshold > 0.0) + vx = (double)(_elm_config->thumbscroll_threshold - (ew - x)) / + _elm_config->thumbscroll_threshold; + else + vx = 1.0; + } + if (y < _elm_config->thumbscroll_threshold) + { + if (_elm_config->thumbscroll_threshold > 0.0) + vy = -(double)(_elm_config->thumbscroll_threshold - y) / + _elm_config->thumbscroll_threshold; + else + vy = -1.0; + } + else if (y > (eh - _elm_config->thumbscroll_threshold)) + { + if (_elm_config->thumbscroll_threshold > 0.0) + vy = (double)(_elm_config->thumbscroll_threshold - (eh - y)) / + _elm_config->thumbscroll_threshold; + else + vy = 1.0; + } + if ((vx != 0.0) || (vy != 0.0)) + { + sd->down.onhold_vx = vx; + sd->down.onhold_vy = vy; + if (!sd->down.onhold_animator) + { + sd->down.onhold_vxe = 0.0; + sd->down.onhold_vye = 0.0; + sd->down.onhold_tlast = 0.0; + sd->down.onhold_animator = ecore_animator_add(_smart_onhold_animator, sd); + } +// printf("b %i %i\n", sd->down.hold_x, sd->down.hold_y); + } + else + { + if (sd->down.onhold_animator) + { + ecore_animator_del(sd->down.onhold_animator); + sd->down.onhold_animator = NULL; + } + } + } + } + } +} + +static void +_smart_scrollbar_read(Smart_Data *sd) +{ + Evas_Coord x, y, mx = 0, my = 0, px, py, minx = 0, miny = 0; + double vx, vy; + + edje_object_part_drag_value_get(sd->edje_obj, "elm.dragable.vbar", NULL, &vy); + edje_object_part_drag_value_get(sd->edje_obj, "elm.dragable.hbar", &vx, NULL); + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + x = vx * (double)mx + minx; + y = vy * (double)my + miny; + sd->pan_func.get(sd->pan_obj, &px, &py); + sd->pan_func.set(sd->pan_obj, x, y); + if ((px != x) || (py != y)) + edje_object_signal_emit(sd->edje_obj, "elm,action,scroll", "elm"); +} + +static void +_smart_scrollbar_reset(Smart_Data *sd) +{ + Evas_Coord px = 0, py = 0, minx = 0, miny = 0; + + edje_object_part_drag_value_set(sd->edje_obj, "elm.dragable.vbar", 0.0, 0.0); + edje_object_part_drag_value_set(sd->edje_obj, "elm.dragable.hbar", 0.0, 0.0); + if ((!sd->child_obj) && (!sd->extern_pan)) + { + edje_object_part_drag_size_set(sd->edje_obj, "elm.dragable.vbar", 1.0, 1.0); + edje_object_part_drag_size_set(sd->edje_obj, "elm.dragable.hbar", 1.0, 1.0); + } + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + sd->pan_func.get(sd->pan_obj, &px, &py); + sd->pan_func.set(sd->pan_obj, minx, miny); + if ((px != minx) || (py != miny)) + edje_object_signal_emit(sd->edje_obj, "elm,action,scroll", "elm"); +} + +static int +_smart_scrollbar_bar_v_visibility_adjust(Smart_Data *sd) +{ + int scroll_v_vis_change = 0; + Evas_Coord h, vw, vh; + + h = sd->child.h; + evas_object_geometry_get(sd->pan_obj, NULL, NULL, &vw, &vh); + if (sd->vbar_visible) + { + if (sd->vbar_flags == ELM_SMART_SCROLLER_POLICY_AUTO) + { + if ((sd->child_obj) || (sd->extern_pan)) + { + if (h <= vh) + { + scroll_v_vis_change = 1; + sd->vbar_visible = 0; + } + } + else + { + scroll_v_vis_change = 1; + sd->vbar_visible = 0; + } + } + else if (sd->vbar_flags == ELM_SMART_SCROLLER_POLICY_OFF) + { + scroll_v_vis_change = 1; + sd->vbar_visible = 0; + } + } + else + { + if (sd->vbar_flags == ELM_SMART_SCROLLER_POLICY_AUTO) + { + if ((sd->child_obj) || (sd->extern_pan)) + { + if (h > vh) + { + scroll_v_vis_change = 1; + sd->vbar_visible = 1; + } + } + } + else if (sd->vbar_flags == ELM_SMART_SCROLLER_POLICY_ON) + { + scroll_v_vis_change = 1; + sd->vbar_visible = 1; + } + } + if (scroll_v_vis_change) + { + if (sd->vbar_flags != ELM_SMART_SCROLLER_POLICY_OFF) + { + if (sd->vbar_visible) + edje_object_signal_emit(sd->edje_obj, "elm,action,show,vbar", "elm"); + else + edje_object_signal_emit(sd->edje_obj, "elm,action,hide,vbar", "elm"); + edje_object_message_signal_process(sd->edje_obj); + _smart_scrollbar_size_adjust(sd); + } + else + edje_object_signal_emit(sd->edje_obj, "elm,action,hide,vbar", "elm"); + } + return scroll_v_vis_change; +} + +static int +_smart_scrollbar_bar_h_visibility_adjust(Smart_Data *sd) +{ + int scroll_h_vis_change = 0; + Evas_Coord w, vw, vh; + + w = sd->child.w; + evas_object_geometry_get(sd->pan_obj, NULL, NULL, &vw, &vh); + if (sd->hbar_visible) + { + if (sd->hbar_flags == ELM_SMART_SCROLLER_POLICY_AUTO) + { + if ((sd->child_obj) || (sd->extern_pan)) + { + if (w <= vw) + { + scroll_h_vis_change = 1; + sd->hbar_visible = 0; + } + } + else + { + scroll_h_vis_change = 1; + sd->hbar_visible = 0; + } + } + else if (sd->hbar_flags == ELM_SMART_SCROLLER_POLICY_OFF) + { + scroll_h_vis_change = 1; + sd->hbar_visible = 0; + } + } + else + { + if (sd->hbar_flags == ELM_SMART_SCROLLER_POLICY_AUTO) + { + if ((sd->child_obj) || (sd->extern_pan)) + { + if (w > vw) + { + scroll_h_vis_change = 1; + sd->hbar_visible = 1; + } + } + } + else if (sd->hbar_flags == ELM_SMART_SCROLLER_POLICY_ON) + { + scroll_h_vis_change = 1; + sd->hbar_visible = 1; + } + } + if (scroll_h_vis_change) + { + if (sd->hbar_flags != ELM_SMART_SCROLLER_POLICY_OFF) + { + if (sd->hbar_visible) + edje_object_signal_emit(sd->edje_obj, "elm,action,show,hbar", "elm"); + else + edje_object_signal_emit(sd->edje_obj, "elm,action,hide,hbar", "elm"); + edje_object_message_signal_process(sd->edje_obj); + _smart_scrollbar_size_adjust(sd); + } + else + edje_object_signal_emit(sd->edje_obj, "elm,action,hide,hbar", "elm"); + _smart_scrollbar_size_adjust(sd); + } + return scroll_h_vis_change; +} + +static void +_smart_scrollbar_bar_visibility_adjust(Smart_Data *sd) +{ + int changed = 0; + + changed |= _smart_scrollbar_bar_h_visibility_adjust(sd); + changed |= _smart_scrollbar_bar_v_visibility_adjust(sd); + if (changed) + { + _smart_scrollbar_bar_h_visibility_adjust(sd); + _smart_scrollbar_bar_v_visibility_adjust(sd); + } +} + +static void +_smart_scrollbar_size_adjust(Smart_Data *sd) +{ + if ((sd->child_obj) || (sd->extern_pan)) + { + Evas_Coord x, y, w, h, mx = 0, my = 0, vw = 0, vh = 0, px, py, minx = 0, miny = 0; + double vx, vy, size; + + edje_object_part_geometry_get(sd->edje_obj, "elm.swallow.content", + NULL, NULL, &vw, &vh); + w = sd->child.w; + if (w < 1) w = 1; + size = (double)vw / (double)w; + if (size > 1.0) + { + size = 1.0; + edje_object_part_drag_value_set(sd->edje_obj, "elm.dragable.hbar", 0.0, 0.0); + } + edje_object_part_drag_size_set(sd->edje_obj, "elm.dragable.hbar", size, 1.0); + + h = sd->child.h; + if (h < 1) h = 1; + size = (double)vh / (double)h; + if (size > 1.0) + { + size = 1.0; + edje_object_part_drag_value_set(sd->edje_obj, "elm.dragable.vbar", 0.0, 0.0); + } + edje_object_part_drag_size_set(sd->edje_obj, "elm.dragable.vbar", 1.0, size); + + edje_object_part_drag_value_get(sd->edje_obj, "elm.dragable.hbar", &vx, NULL); + edje_object_part_drag_value_get(sd->edje_obj, "elm.dragable.vbar", NULL, &vy); + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + x = vx * mx + minx; + y = vy * my + miny; + + edje_object_part_drag_step_set(sd->edje_obj, "elm.dragable.hbar", (double)sd->step.x / (double)w, 0.0); + edje_object_part_drag_step_set(sd->edje_obj, "elm.dragable.vbar", 0.0, (double)sd->step.y / (double)h); + if (sd->page.x > 0) + edje_object_part_drag_page_set(sd->edje_obj, "elm.dragable.hbar", (double)sd->page.x / (double)w, 0.0); + else + edje_object_part_drag_page_set(sd->edje_obj, "elm.dragable.hbar", -((double)sd->page.x * ((double)vw / (double)w)) / 100.0, 0.0); + if (sd->page.y > 0) + edje_object_part_drag_page_set(sd->edje_obj, "elm.dragable.vbar", 0.0, (double)sd->page.y / (double)h); + else + edje_object_part_drag_page_set(sd->edje_obj, "elm.dragable.vbar", 0.0, -((double)sd->page.y * ((double)vh / (double)h)) / 100.0); + + sd->pan_func.get(sd->pan_obj, &px, &py); + if (vx != mx) x = px; + if (vy != my) y = py; + sd->pan_func.set(sd->pan_obj, x, y); +// if ((px != 0) || (py != 0)) +// edje_object_signal_emit(sd->edje_obj, "elm,action,scroll", "elm"); + } + else + { + Evas_Coord px = 0, py = 0, minx = 0, miny = 0; + + edje_object_part_drag_size_set(sd->edje_obj, "elm.dragable.vbar", 1.0, 1.0); + edje_object_part_drag_size_set(sd->edje_obj, "elm.dragable.hbar", 1.0, 1.0); + sd->pan_func.min_get(sd->pan_obj, &minx, &miny); + sd->pan_func.get(sd->pan_obj, &px, &py); + sd->pan_func.set(sd->pan_obj, minx, miny); + if ((px != minx) || (py != miny)) + edje_object_signal_emit(sd->edje_obj, "elm,action,scroll", "elm"); + } + _smart_scrollbar_bar_visibility_adjust(sd); +} + +static void +_smart_reconfigure(Smart_Data *sd) +{ + evas_object_move(sd->edje_obj, sd->x, sd->y); + evas_object_resize(sd->edje_obj, sd->w, sd->h); + evas_object_move(sd->event_obj, sd->x, sd->y); + evas_object_resize(sd->event_obj, sd->w, sd->h); + _smart_scrollbar_size_adjust(sd); +} + +static void +_smart_add(Evas_Object *obj) +{ + Smart_Data *sd; + Evas_Object *o; + + sd = calloc(1, sizeof(Smart_Data)); + if (!sd) return; + evas_object_smart_data_set(obj, sd); + + sd->smart_obj = obj; + sd->x = 0; + sd->y = 0; + sd->w = 0; + sd->h = 0; + sd->step.x = 32; + sd->step.y = 32; + sd->page.x = -50; + sd->page.y = -50; + sd->hbar_flags = ELM_SMART_SCROLLER_POLICY_AUTO; + sd->vbar_flags = ELM_SMART_SCROLLER_POLICY_AUTO; + sd->hbar_visible = 1; + sd->vbar_visible = 1; + + sd->bounce_horiz = 1; + sd->bounce_vert = 1; + + sd->one_dir_at_a_time = 1; + sd->momentum_animator_disabled = 0; + sd->bounce_animator_disabled = 0; + + o = edje_object_add(evas_object_evas_get(obj)); + evas_object_propagate_events_set(o, 0); + sd->edje_obj = o; + // FIXME: null parent obj ... :( + elm_smart_scroller_object_theme_set(NULL, obj, "scroller", "base", "default"); + edje_object_signal_callback_add(o, "drag", "elm.dragable.vbar", _smart_edje_drag_v, sd); + edje_object_signal_callback_add(o, "drag,start", "elm.dragable.vbar", _smart_edje_drag_v_start, sd); + edje_object_signal_callback_add(o, "drag,stop", "elm.dragable.vbar", _smart_edje_drag_v_stop, sd); + edje_object_signal_callback_add(o, "drag,step", "elm.dragable.vbar", _smart_edje_drag_v, sd); + edje_object_signal_callback_add(o, "drag,page", "elm.dragable.vbar", _smart_edje_drag_v, sd); + edje_object_signal_callback_add(o, "drag", "elm.dragable.hbar", _smart_edje_drag_h, sd); + edje_object_signal_callback_add(o, "drag,start", "elm.dragable.hbar", _smart_edje_drag_h_start, sd); + edje_object_signal_callback_add(o, "drag,stop", "elm.dragable.hbar", _smart_edje_drag_h_stop, sd); + edje_object_signal_callback_add(o, "drag,step", "elm.dragable.hbar", _smart_edje_drag_h, sd); + edje_object_signal_callback_add(o, "drag,page", "elm.dragable.hbar", _smart_edje_drag_h, sd); + evas_object_smart_member_add(o, obj); + + o = evas_object_rectangle_add(evas_object_evas_get(obj)); + sd->event_obj = o; + evas_object_color_set(o, 0, 0, 0, 0); + evas_object_event_callback_add(o, EVAS_CALLBACK_MOUSE_WHEEL, _smart_event_wheel, sd); + evas_object_event_callback_add(o, EVAS_CALLBACK_MOUSE_DOWN, _smart_event_mouse_down, sd); + evas_object_event_callback_add(o, EVAS_CALLBACK_MOUSE_UP, _smart_event_mouse_up, sd); + evas_object_event_callback_add(o, EVAS_CALLBACK_MOUSE_MOVE, _smart_event_mouse_move, sd); + evas_object_smart_member_add(o, obj); + evas_object_repeat_events_set(o, 1); + + sd->pan_func.set = _elm_smart_pan_set; + sd->pan_func.get = _elm_smart_pan_get; + sd->pan_func.max_get = _elm_smart_pan_max_get; + sd->pan_func.min_get = _elm_smart_pan_min_get; + sd->pan_func.child_size_get = _elm_smart_pan_child_size_get; + + _smart_scrollbar_reset(sd); +} + +static void +_smart_del(Evas_Object *obj) +{ + INTERNAL_ENTRY; + elm_smart_scroller_child_set(obj, NULL); + if (!sd->extern_pan) evas_object_del(sd->pan_obj); + evas_object_del(sd->edje_obj); + evas_object_del(sd->event_obj); + if (sd->down.hold_animator) ecore_animator_del(sd->down.hold_animator); + if (sd->down.onhold_animator) ecore_animator_del(sd->down.onhold_animator); + if (sd->down.momentum_animator) ecore_animator_del(sd->down.momentum_animator); + if (sd->down.bounce_x_animator) ecore_animator_del(sd->down.bounce_x_animator); + if (sd->down.bounce_y_animator) ecore_animator_del(sd->down.bounce_y_animator); + if (sd->scrollto.x.animator) ecore_animator_del(sd->scrollto.x.animator); + if (sd->scrollto.y.animator) ecore_animator_del(sd->scrollto.y.animator); + free(sd); + evas_object_smart_data_set(obj, NULL); +} + +static void +_smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + INTERNAL_ENTRY; + sd->x = x; + sd->y = y; + _smart_reconfigure(sd); +} + +static void +_smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h) +{ + INTERNAL_ENTRY; + sd->w = w; + sd->h = h; + _smart_reconfigure(sd); + elm_smart_scroller_child_region_set(obj, sd->wx, sd->wy, sd->ww, sd->h); +} + +static void +_smart_show(Evas_Object *obj) +{ + INTERNAL_ENTRY; + evas_object_show(sd->edje_obj); + evas_object_show(sd->event_obj); +} + +static void +_smart_hide(Evas_Object *obj) +{ + INTERNAL_ENTRY; + evas_object_hide(sd->edje_obj); + evas_object_hide(sd->event_obj); +} + +static void +_smart_color_set(Evas_Object *obj, int r, int g, int b, int a) +{ + INTERNAL_ENTRY; + evas_object_color_set(sd->edje_obj, r, g, b, a); +} + +static void +_smart_clip_set(Evas_Object *obj, Evas_Object *clip) +{ + INTERNAL_ENTRY; + evas_object_clip_set(sd->edje_obj, clip); + evas_object_clip_set(sd->event_obj, clip); +} + +static void +_smart_clip_unset(Evas_Object *obj) +{ + INTERNAL_ENTRY; + evas_object_clip_unset(sd->edje_obj); + evas_object_clip_unset(sd->event_obj); +} + +/* never need to touch this */ + +static void +_smart_init(void) +{ + if (_smart) return; + { + static const Evas_Smart_Class sc = + { + SMART_NAME, + EVAS_SMART_CLASS_VERSION, + _smart_add, + _smart_del, + _smart_move, + _smart_resize, + _smart_show, + _smart_hide, + _smart_color_set, + _smart_clip_set, + _smart_clip_unset, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL + }; + _smart = evas_smart_class_new(&sc); + } +} + diff --git a/src/lib/els_scroller.h b/src/lib/els_scroller.h new file mode 100644 index 0000000..4fe85fc --- /dev/null +++ b/src/lib/els_scroller.h @@ -0,0 +1,39 @@ +typedef enum _Elm_Smart_Scroller_Policy +{ + ELM_SMART_SCROLLER_POLICY_AUTO, + ELM_SMART_SCROLLER_POLICY_ON, + ELM_SMART_SCROLLER_POLICY_OFF +} +Elm_Smart_Scroller_Policy; + +Evas_Object *elm_smart_scroller_add (Evas *evas); +void elm_smart_scroller_child_set (Evas_Object *obj, Evas_Object *child); +void elm_smart_scroller_extern_pan_set (Evas_Object *obj, Evas_Object *pan, void (*pan_set) (Evas_Object *obj, Evas_Coord x, Evas_Coord y), void (*pan_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y), void (*pan_max_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y), void (*pan_min_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y), void (*pan_child_size_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y)); +void elm_smart_scroller_custom_edje_file_set (Evas_Object *obj, char *file, char *group); +void elm_smart_scroller_child_pos_set (Evas_Object *obj, Evas_Coord x, Evas_Coord y); +void elm_smart_scroller_child_pos_get (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); +void elm_smart_scroller_child_region_show (Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h); +void elm_smart_scroller_child_region_set (Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h); +void elm_smart_scroller_child_viewport_size_get (Evas_Object *obj, Evas_Coord *w, Evas_Coord *h); +void elm_smart_scroller_step_size_set (Evas_Object *obj, Evas_Coord x, Evas_Coord y); +void elm_smart_scroller_step_size_get (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); +void elm_smart_scroller_page_size_set (Evas_Object *obj, Evas_Coord x, Evas_Coord y); +void elm_smart_scroller_page_size_get (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); +void elm_smart_scroller_policy_set (Evas_Object *obj, Elm_Smart_Scroller_Policy hbar, Elm_Smart_Scroller_Policy vbar); +void elm_smart_scroller_policy_get (Evas_Object *obj, Elm_Smart_Scroller_Policy *hbar, Elm_Smart_Scroller_Policy *vbar); +Evas_Object *elm_smart_scroller_edje_object_get (Evas_Object *obj); +void elm_smart_scroller_single_dir_set (Evas_Object *obj, Eina_Bool single_dir); +Eina_Bool elm_smart_scroller_single_dir_get (Evas_Object *obj); +void elm_smart_scroller_object_theme_set (Evas_Object *parent, Evas_Object *obj, const char *clas, const char *group, const char *style); +void elm_smart_scroller_hold_set (Evas_Object *obj, Eina_Bool hold); +void elm_smart_scroller_freeze_set (Evas_Object *obj, Eina_Bool freeze); +void elm_smart_scroller_bounce_allow_set (Evas_Object *obj, Eina_Bool horiz, Eina_Bool vert); +void elm_smart_scroller_bounce_allow_get (const Evas_Object *obj, Eina_Bool *horiz, Eina_Bool *vert); +void elm_smart_scroller_paging_set (Evas_Object *obj, double pagerel_h, double pagerel_v, Evas_Coord pagesize_h, Evas_Coord pagesize_v); +void elm_smart_scroller_paging_get (Evas_Object *obj, double *pagerel_h, double *pagerel_v, Evas_Coord *pagesize_h, Evas_Coord *pagesize_v); +void elm_smart_scroller_region_bring_in (Evas_Object *obj, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h); +void elm_smart_scroller_widget_set (Evas_Object *obj, Evas_Object *wid); +Eina_Bool elm_smart_scroller_momentum_animator_disabled_get (Evas_Object *obj); +void elm_smart_scroller_momentum_animator_disabled_set (Evas_Object *obj, Eina_Bool disabled); +void elm_smart_scroller_bounce_animator_disabled_set (Evas_Object *obj, Eina_Bool disabled); +Eina_Bool elm_smart_scroller_bounce_animator_disabled_get (Evas_Object *obj); diff --git a/src/lib/els_tooltip.c b/src/lib/els_tooltip.c new file mode 100644 index 0000000..060f06f --- /dev/null +++ b/src/lib/els_tooltip.c @@ -0,0 +1,787 @@ +#include +#include "elm_priv.h" + +/** + * @defgroup Tooltips Tooltips + * + * The Tooltip is an (internal, for now) smart object used to show a + * content in a frame on mouse hover of objects(or widgets), with + * tips/information about them. + */ + +static const char _tooltip_key[] = "_elm_tooltip"; + +#define ELM_TOOLTIP_GET_OR_RETURN(tt, obj, ...) \ + Elm_Tooltip *tt; \ + do \ + { \ + if (!(obj)) \ + { \ + CRITICAL("Null pointer: " #obj); \ + return __VA_ARGS__; \ + } \ + tt = evas_object_data_get((obj), _tooltip_key); \ + if (!tt) \ + { \ + ERR("Object does not have tooltip: " #obj); \ + return __VA_ARGS__; \ + } \ + } \ + while (0) + +struct _Elm_Tooltip +{ + Elm_Tooltip_Content_Cb func; + Evas_Smart_Cb del_cb; + const void *data; + const char *style; + Evas *evas; + Evas_Object *eventarea, *owner; + Evas_Object *tooltip, *content; + Ecore_Timer *show_timer; + Ecore_Timer *hide_timer; + Ecore_Job *reconfigure_job; + struct { + Evas_Coord x, y, bx, by; + } pad; + struct { + double x, y; + } rel_pos; + double hide_timeout; /* from theme */ + Eina_Bool visible_lock:1; + Eina_Bool changed_style:1; +}; + +static void _elm_tooltip_reconfigure(Elm_Tooltip *tt); +static void _elm_tooltip_reconfigure_job_start(Elm_Tooltip *tt); +static void _elm_tooltip_reconfigure_job_stop(Elm_Tooltip *tt); +static void _elm_tooltip_hide_anim_start(Elm_Tooltip *tt); +static void _elm_tooltip_hide_anim_stop(Elm_Tooltip *tt); +static void _elm_tooltip_show_timer_stop(Elm_Tooltip *tt); +static void _elm_tooltip_hide(Elm_Tooltip *tt); +static void _elm_tooltip_data_clean(Elm_Tooltip *tt); + + +static void +_elm_tooltip_content_changed_hints_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + _elm_tooltip_reconfigure_job_start(data); +} + +static void +_elm_tooltip_content_del_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Tooltip *tt = data; + tt->content = NULL; + tt->visible_lock = EINA_FALSE; + _elm_tooltip_hide(tt); +} + +static void +_elm_tooltip_obj_move_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Tooltip *tt = data; + _elm_tooltip_reconfigure_job_start(tt); +} + +static void +_elm_tooltip_obj_resize_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Tooltip *tt = data; + _elm_tooltip_reconfigure_job_start(tt); +} + +static void +_elm_tooltip_obj_mouse_move_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Tooltip *tt = data; + _elm_tooltip_reconfigure_job_start(tt); +} + +static void +_elm_tooltip_show(Elm_Tooltip *tt) +{ + _elm_tooltip_show_timer_stop(tt); + _elm_tooltip_hide_anim_stop(tt); + + if (tt->tooltip) + { + _elm_tooltip_reconfigure_job_start(tt); + return; + } + tt->tooltip = edje_object_add(tt->evas); + if (!tt->tooltip) return; + + evas_object_layer_set(tt->tooltip, ELM_OBJECT_LAYER_TOOLTIP); + + evas_object_event_callback_add + (tt->eventarea, EVAS_CALLBACK_MOVE, _elm_tooltip_obj_move_cb, tt); + evas_object_event_callback_add + (tt->eventarea, EVAS_CALLBACK_RESIZE, _elm_tooltip_obj_resize_cb, tt); + evas_object_event_callback_add + (tt->eventarea, EVAS_CALLBACK_MOUSE_MOVE, _elm_tooltip_obj_mouse_move_cb, tt); + + evas_object_pass_events_set(tt->tooltip, EINA_TRUE); + tt->changed_style = EINA_TRUE; + _elm_tooltip_reconfigure_job_start(tt); +} + +static void +_elm_tooltip_content_del(Elm_Tooltip *tt) +{ + if (!tt->content) return; + + evas_object_event_callback_del_full + (tt->content, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _elm_tooltip_content_changed_hints_cb, tt); + evas_object_event_callback_del_full + (tt->content, EVAS_CALLBACK_DEL, + _elm_tooltip_content_del_cb, tt); + evas_object_del(tt->content); + tt->content = NULL; +} + + +static void +_elm_tooltip_hide(Elm_Tooltip *tt) +{ + _elm_tooltip_show_timer_stop(tt); + _elm_tooltip_hide_anim_stop(tt); + _elm_tooltip_reconfigure_job_stop(tt); + + if (!tt->tooltip) return; + if (tt->visible_lock) return; + + _elm_tooltip_content_del(tt); + + evas_object_event_callback_del_full + (tt->eventarea, EVAS_CALLBACK_MOVE, _elm_tooltip_obj_move_cb, tt); + evas_object_event_callback_del_full + (tt->eventarea, EVAS_CALLBACK_RESIZE, _elm_tooltip_obj_resize_cb, tt); + evas_object_event_callback_del_full + (tt->eventarea, EVAS_CALLBACK_MOUSE_MOVE, _elm_tooltip_obj_mouse_move_cb, tt); + + evas_object_del(tt->tooltip); + tt->tooltip = NULL; +} + +static void +_elm_tooltip_reconfigure_job(void *data) +{ + Elm_Tooltip *tt = data; + tt->reconfigure_job = NULL; + _elm_tooltip_reconfigure(data); +} + +static void +_elm_tooltip_reconfigure_job_stop(Elm_Tooltip *tt) +{ + if (!tt->reconfigure_job) return; + ecore_job_del(tt->reconfigure_job); + tt->reconfigure_job = NULL; +} + +static void +_elm_tooltip_reconfigure_job_start(Elm_Tooltip *tt) +{ + if (tt->reconfigure_job) ecore_job_del(tt->reconfigure_job); + tt->reconfigure_job = ecore_job_add + (_elm_tooltip_reconfigure_job, tt); +} + +static Eina_Bool +_elm_tooltip_hide_anim_cb(void *data) +{ + Elm_Tooltip *tt = data; + tt->hide_timer = NULL; + _elm_tooltip_hide(tt); + return EINA_FALSE; +} + +static void +_elm_tooltip_hide_anim_start(Elm_Tooltip *tt) +{ + if (tt->hide_timer) return; + edje_object_signal_emit(tt->tooltip, "elm,action,hide", "elm"); + tt->hide_timer = ecore_timer_add + (tt->hide_timeout, _elm_tooltip_hide_anim_cb, tt); +} + +static void +_elm_tooltip_hide_anim_stop(Elm_Tooltip *tt) +{ + if (!tt->hide_timer) return; + if (tt->tooltip) + edje_object_signal_emit(tt->tooltip, "elm,action,show", "elm"); + ecore_timer_del(tt->hide_timer); + tt->hide_timer = NULL; +} + +static void +_elm_tooltip_reconfigure(Elm_Tooltip *tt) +{ + Evas_Coord ox, oy, ow, oh, px, py, tx, ty, tw, th, cw, ch; + Evas_Coord eminw, eminh, ominw, ominh; + double rel_x, rel_y; + Eina_Bool inside_eventarea; + + _elm_tooltip_reconfigure_job_stop(tt); + + if (tt->hide_timer) return; + if (!tt->tooltip) return; + if (tt->changed_style) + { + const char *style = tt->style ? tt->style : "default"; + const char *str; + if (!_elm_theme_object_set + (tt->owner, tt->tooltip, "tooltip", "base", style)) + { + ERR("Could not apply the theme to the tooltip! style=%s", style); + evas_object_del(tt->tooltip); + tt->tooltip = NULL; + return; + } + + tt->rel_pos.x = 0; + tt->rel_pos.y = 0; + + tt->pad.x = 0; + tt->pad.y = 0; + tt->pad.bx = 0; + tt->pad.by = 0; + tt->hide_timeout = 0.0; + + str = edje_object_data_get(tt->tooltip, "pad_x"); + if (str) tt->pad.x = atoi(str); + str = edje_object_data_get(tt->tooltip, "pad_y"); + if (str) tt->pad.y = atoi(str); + + str = edje_object_data_get(tt->tooltip, "pad_border_x"); + if (str) tt->pad.bx = atoi(str); + str = edje_object_data_get(tt->tooltip, "pad_border_y"); + if (str) tt->pad.by = atoi(str); + + str = edje_object_data_get(tt->tooltip, "hide_timeout"); + if (str) + { + tt->hide_timeout = atof(str); + if (tt->hide_timeout < 0.0) tt->hide_timeout = 0.0; + } + + evas_object_pass_events_set(tt->tooltip, EINA_TRUE); + tt->changed_style = EINA_FALSE; + if (tt->tooltip) + edje_object_part_swallow + (tt->tooltip, "elm.swallow.content", tt->content); + + edje_object_signal_emit(tt->tooltip, "elm,action,show", "elm"); + } + + if (!tt->content) + { + tt->content = tt->func((void *)tt->data, tt->owner); + if (!tt->content) + { + WRN("could not create tooltip content!"); + evas_object_del(tt->tooltip); + tt->tooltip = NULL; + return; + } + evas_object_layer_set(tt->content, ELM_OBJECT_LAYER_TOOLTIP); + evas_object_pass_events_set(tt->content, EINA_TRUE); + edje_object_part_swallow + (tt->tooltip, "elm.swallow.content", tt->content); + evas_object_event_callback_add + (tt->content, EVAS_CALLBACK_CHANGED_SIZE_HINTS, + _elm_tooltip_content_changed_hints_cb, tt); + evas_object_event_callback_add + (tt->content, EVAS_CALLBACK_DEL, + _elm_tooltip_content_del_cb, tt); + + } + + evas_object_size_hint_min_get(tt->content, &ominw, &ominh); + edje_object_size_min_get(tt->tooltip, &eminw, &eminh); + + if (ominw < eminw) ominw = eminw; + if (ominh < eminh) ominh = eminh; + + if (ominw < 1) ominw = 10; /* at least it is noticeable */ + if (ominh < 1) ominh = 10; /* at least it is noticeable */ + + edje_object_size_min_restricted_calc + (tt->tooltip, &tw, &th, ominw, ominh); + + evas_output_size_get(tt->evas, &cw, &ch); + evas_pointer_canvas_xy_get(tt->evas, &px, &py); + + evas_object_geometry_get(tt->eventarea, &ox, &oy, &ow, &oh); + + inside_eventarea = ((px >= ox) && (py >= oy) && + (px <= ox + ow) && (py <= oy + oh)); + if (inside_eventarea) + { + tx = px; + ty = py; + + if (tx + tw + tt->pad.x < cw) tx += tt->pad.x; + if (ty + th + tt->pad.y < ch) ty += tt->pad.y; + } + else + { + tx = ox + (ow / 2) - (tw / 2); + if (ch < (th + oy + oh)) ty = oy - th; + else ty = oy + oh; + } + + if (tt->pad.bx * 2 + tw < cw) + { + if (tx < tt->pad.bx) tx = tt->pad.bx; + else if (tx + tw >= cw - tt->pad.bx) tx = cw - tw - tt->pad.bx; + } + + if (tt->pad.by * 2 + th < ch) + { + if (ty < tt->pad.by) ty = tt->pad.by; + else if (ty + th >= ch - tt->pad.by) ty = ch - th - tt->pad.by; + } + + evas_object_move(tt->tooltip, tx, ty); + evas_object_resize(tt->tooltip, tw, th); + evas_object_show(tt->tooltip); + + if (inside_eventarea) + { + rel_x = (px - tx) / (double)tw; + rel_y = (py - ty) / (double)th; + } + else + { + rel_x = (ox + (ow / 2) - tx) / (double)tw; + rel_y = (oy + (oh / 2) - ty) / (double)th; + } + +#define FDIF(a, b) (fabs((a) - (b)) > 0.0001) + if ((FDIF(rel_x, tt->rel_pos.x)) || (FDIF(rel_y, tt->rel_pos.y))) + { + Edje_Message_Float_Set *msg; + + msg = alloca(sizeof(Edje_Message_Float_Set) + sizeof(double)); + msg->count = 2; + msg->val[0] = rel_x; + msg->val[1] = rel_y; + tt->rel_pos.x = rel_x; + tt->rel_pos.y = rel_y; + + edje_object_message_send(tt->tooltip, EDJE_MESSAGE_FLOAT_SET, 1, msg); + } +#undef FDIF +} + +static void +_elm_tooltip_show_timer_stop(Elm_Tooltip *tt) +{ + if (!tt->show_timer) return; + ecore_timer_del(tt->show_timer); + tt->show_timer = NULL; +} + +static Eina_Bool +_elm_tooltip_timer_show_cb(void *data) +{ + Elm_Tooltip *tt = data; + tt->show_timer = NULL; + _elm_tooltip_show(tt); + return ECORE_CALLBACK_CANCEL; +} + +static void +_elm_tooltip_obj_mouse_in_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Tooltip *tt = data; + + _elm_tooltip_hide_anim_stop(tt); + + if ((tt->show_timer) || (tt->tooltip)) return; + + tt->show_timer = ecore_timer_add + (_elm_config->tooltip_delay, _elm_tooltip_timer_show_cb, tt); +} + +static void +_elm_tooltip_obj_mouse_out_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + Elm_Tooltip *tt = data; + + if (tt->visible_lock) return; + + if (!tt->tooltip) + { + _elm_tooltip_show_timer_stop(tt); + return; + } + + _elm_tooltip_hide_anim_start(tt); +} + +static void _elm_tooltip_obj_del_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__); + +static void +_elm_tooltip_unset(Elm_Tooltip *tt) +{ + tt->visible_lock = EINA_FALSE; + _elm_tooltip_hide(tt); + _elm_tooltip_data_clean(tt); + + if (tt->eventarea) + { + evas_object_event_callback_del_full + (tt->eventarea, EVAS_CALLBACK_MOUSE_IN, + _elm_tooltip_obj_mouse_in_cb, tt); + evas_object_event_callback_del_full + (tt->eventarea, EVAS_CALLBACK_MOUSE_OUT, + _elm_tooltip_obj_mouse_out_cb, tt); + evas_object_event_callback_del_full + (tt->eventarea, EVAS_CALLBACK_DEL, _elm_tooltip_obj_del_cb, tt); + + evas_object_data_del(tt->eventarea, _tooltip_key); + } + if (tt->owner) + { + evas_object_event_callback_del_full + (tt->owner, EVAS_CALLBACK_DEL, _elm_tooltip_obj_del_cb, tt); + elm_widget_tooltip_del(tt->owner, tt); + } + + eina_stringshare_del(tt->style); + free(tt); +} + +static void +_elm_tooltip_obj_del_cb(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event_info __UNUSED__) +{ + Elm_Tooltip *tt = data; + if (tt->eventarea == obj) tt->eventarea = NULL; + if (tt->owner == obj) tt->owner = NULL; + _elm_tooltip_unset(tt); +} + +static Evas_Object * +_elm_tooltip_label_create(void *data, Evas_Object *obj) +{ + Evas_Object *label = elm_label_add(obj); + if (!label) + return NULL; + elm_object_style_set(label, "tooltip"); + elm_label_label_set(label, data); + return label; +} + +static void +_elm_tooltip_label_del_cb(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) +{ + eina_stringshare_del(data); +} + +static void +_elm_tooltip_data_clean(Elm_Tooltip *tt) +{ + if (tt->del_cb) tt->del_cb((void *)tt->data, tt->owner, NULL); + + _elm_tooltip_content_del(tt); + + tt->data = NULL; + tt->del_cb = NULL; +} + +/** + * Notify tooltip should recalculate its theme. + * @internal + */ +void +elm_tooltip_theme(Elm_Tooltip *tt) +{ + if (!tt->tooltip) return; + tt->changed_style = EINA_TRUE; + _elm_tooltip_reconfigure_job_start(tt); +} + + +/** + * Set the content to be shown in the tooltip object for specific event area. + * + * Setup the tooltip to object. The object @a eventarea can have only + * one tooltip, so any previous tooltip data is removed. @p func(with + * @p data) will be called every time that need show the tooltip and + * it should return a valid Evas_Object. This object is then managed + * fully by tooltip system and is deleted when the tooltip is gone. + * + * This is an internal function that is used by objects with sub-items + * that want to provide different tooltips for each of them. The @a + * owner object should be an elm_widget and will be used to track + * theme changes and to feed @a func and @a del_cb. The @a eventarea + * may be any object and is the one that should be used later on with + * elm_object_tooltip apis, such as elm_object_tooltip_hide(), + * elm_object_tooltip_show() or elm_object_tooltip_unset(). + * + * @param eventarea the object being attached a tooltip. + * @param owner the elm_widget that owns this object, will be used to + * track theme changes and to be used in @a func or @a del_cb. + * @param func the function used to create the tooltip contents. The + * @a Evas_Object parameters will receive @a owner as value. + * @param data what to provide to @a func as callback data/context. + * @param del_cb called when data is not needed anymore, either when + * another callback replaces @func, the tooltip is unset with + * elm_object_tooltip_unset() or the owner object @a obj + * dies. This callback receives as the first parameter the + * given @a data, and @c event_info is NULL. + * + * @internal + * @ingroup Tooltips + */ +void +elm_object_sub_tooltip_content_cb_set(Evas_Object *eventarea, Evas_Object *owner, Elm_Tooltip_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) +{ + Elm_Tooltip *tt = NULL; + Eina_Bool just_created; + + EINA_SAFETY_ON_NULL_GOTO(owner, error); + EINA_SAFETY_ON_NULL_GOTO(eventarea, error); + + if (!func) + { + elm_object_tooltip_unset(eventarea); + return; + } + + tt = evas_object_data_get(eventarea, _tooltip_key); + if (tt) + { + if (tt->owner != owner) + { + if (tt->owner != eventarea) + evas_object_event_callback_del_full + (tt->owner, EVAS_CALLBACK_DEL, _elm_tooltip_obj_del_cb, tt); + + elm_widget_tooltip_del(tt->owner, tt); + + if (owner != eventarea) + evas_object_event_callback_add + (owner, EVAS_CALLBACK_DEL, _elm_tooltip_obj_del_cb, tt); + + elm_widget_tooltip_add(tt->owner, tt); + } + + if ((tt->func == func) && (tt->data == data) && + (tt->del_cb == del_cb)) + return; + _elm_tooltip_data_clean(tt); + just_created = EINA_FALSE; + } + else + { + tt = ELM_NEW(Elm_Tooltip); + if (!tt) goto error; + + tt->owner = owner; + tt->eventarea = eventarea; + tt->evas = evas_object_evas_get(eventarea); + evas_object_data_set(eventarea, _tooltip_key, tt); + + just_created = EINA_TRUE; + + evas_object_event_callback_add + (eventarea, EVAS_CALLBACK_MOUSE_IN, + _elm_tooltip_obj_mouse_in_cb, tt); + evas_object_event_callback_add + (eventarea, EVAS_CALLBACK_MOUSE_OUT, + _elm_tooltip_obj_mouse_out_cb, tt); + evas_object_event_callback_add + (eventarea, EVAS_CALLBACK_DEL, _elm_tooltip_obj_del_cb, tt); + + if (owner != eventarea) + evas_object_event_callback_add + (owner, EVAS_CALLBACK_DEL, _elm_tooltip_obj_del_cb, tt); + + elm_widget_tooltip_add(tt->owner, tt); + } + + tt->func = func; + tt->data = data; + tt->del_cb = del_cb; + + if (!just_created) _elm_tooltip_reconfigure_job_start(tt); + return; + + error: + if (del_cb) del_cb((void *)data, owner, NULL); +} + +/** + * Force show tooltip of object + * + * @param obj Target object + * + * Force show the tooltip and disable hide on mouse_out. + * If another content is set as tooltip, the visible tooltip will hididen and + * showed again with new content. + * This can force show more than one tooltip at a time. + * + * @ingroup Tooltips + */ +EAPI void +elm_object_tooltip_show(Evas_Object *obj) +{ + ELM_TOOLTIP_GET_OR_RETURN(tt, obj); + tt->visible_lock = EINA_TRUE; + _elm_tooltip_show(tt); +} + +/** + * Force hide tooltip of object + * + * @param obj Target object + * + * Force hide the tooltip and (re)enable future mouse interations. + * + * @ingroup Tooltips + */ +EAPI void +elm_object_tooltip_hide(Evas_Object *obj) +{ + ELM_TOOLTIP_GET_OR_RETURN(tt, obj); + tt->visible_lock = EINA_FALSE; + _elm_tooltip_hide_anim_start(tt); +} + +/** + * Set the text to be shown in the tooltip object + * + * @param obj Target object + * @param text The text to set in the content + * + * Setup the text as tooltip to object. The object can have only one tooltip, + * so any previous tooltip data is removed. + * This method call internaly the elm_tooltip_content_cb_set(). + * + * @ingroup Tooltips + */ +EAPI void +elm_object_tooltip_text_set(Evas_Object *obj, const char *text) +{ + EINA_SAFETY_ON_NULL_RETURN(obj); + EINA_SAFETY_ON_NULL_RETURN(text); + + text = eina_stringshare_add(text); + elm_object_tooltip_content_cb_set + (obj, _elm_tooltip_label_create, text, _elm_tooltip_label_del_cb); +} + +/** + * Set the content to be shown in the tooltip object + * + * Setup the tooltip to object. The object can have only one tooltip, + * so any previous tooltip data is removed. @p func(with @p data) will + * be called every time that need show the tooltip and it should + * return a valid Evas_Object. This object is then managed fully by + * tooltip system and is deleted when the tooltip is gone. + * + * @param obj the object being attached a tooltip. + * @param func the function used to create the tooltip contents. + * @param data what to provide to @a func as callback data/context. + * @param del_cb called when data is not needed anymore, either when + * another callback replaces @func, the tooltip is unset with + * elm_object_tooltip_unset() or the owner object @a obj + * dies. This callback receives as the first parameter the + * given @a data, and @c event_info is NULL. + * + * @ingroup Tooltips + */ +EAPI void +elm_object_tooltip_content_cb_set(Evas_Object *obj, Elm_Tooltip_Content_Cb func, const void *data, Evas_Smart_Cb del_cb) +{ + elm_object_sub_tooltip_content_cb_set(obj, obj, func, data, del_cb); +} + +/** + * Unset tooltip from object + * + * @param obj Target object + * + * Remove tooltip from object. The callback provided as del_cb to + * elm_object_tooltip_content_cb_set() will be called to notify it is + * not used anymore. + * + * @see elm_object_tooltip_content_cb_set() + * + * @ingroup Tooltips + */ +EAPI void +elm_object_tooltip_unset(Evas_Object *obj) +{ + ELM_TOOLTIP_GET_OR_RETURN(tt, obj); + _elm_tooltip_unset(tt); +} + +/** + * Sets a different style for this object tooltip. + * + * @note before you set a style you should define a tooltip with + * elm_object_tooltip_content_cb_set() or + * elm_object_tooltip_text_set(). + * + * @param obj an object with tooltip already set. + * @param style the theme style to use (default, transparent, ...) + */ +EAPI void +elm_object_tooltip_style_set(Evas_Object *obj, const char *style) +{ + ELM_TOOLTIP_GET_OR_RETURN(tt, obj); + if (!eina_stringshare_replace(&tt->style, style)) return; + elm_tooltip_theme(tt); +} + +/** + * Get the style for this object tooltip. + * + * @param obj an object with tooltip already set. + * @return style the theme style in use, defaults to "default". If the + * object does not have a tooltip set, then NULL is returned. + */ +EAPI const char * +elm_object_tooltip_style_get(const Evas_Object *obj) +{ + ELM_TOOLTIP_GET_OR_RETURN(tt, obj, NULL); + return tt->style ? tt->style : "default"; +} + +/** + * Get the configured tooltip delay + * + * This gets the globally configured tooltip delay in seconds + * + * @return The tooltip delay + * @ingroup Tooltips + */ +EAPI double +elm_tooltip_delay_get(void) +{ + return _elm_config->tooltip_delay; +} + +/** + * Set the configured tooltip delay + * + * This sets the globally configured delay to tooltip + * + * @param delay The delay to show the tooltip + * @return EINA_TRUE if value is valid and setted + * @ingroup Tooltips + */ +EAPI Eina_Bool +elm_tooltip_delay_set(double delay) +{ + if (delay < 0.0) return EINA_FALSE; + _elm_config->tooltip_delay = delay; + return EINA_TRUE; +} diff --git a/src/modules/Makefile.am b/src/modules/Makefile.am new file mode 100644 index 0000000..b00ad7e --- /dev/null +++ b/src/modules/Makefile.am @@ -0,0 +1,6 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +SUBDIRS = \ +test_entry \ +test_map diff --git a/src/modules/test_entry/Makefile.am b/src/modules/test_entry/Makefile.am new file mode 100644 index 0000000..7f7e05b --- /dev/null +++ b/src/modules/test_entry/Makefile.am @@ -0,0 +1,32 @@ + +MAINTAINERCLEANFILES = Makefile.in + +AM_CPPFLAGS = \ +-I. \ +-I$(top_builddir) \ +-I$(top_srcdir) \ +-I$(top_srcdir)/src/lib \ +-I$(top_builddir)/src/lib \ +-DPACKAGE_DATA_DIR=\"$(datadir)/$(PACKAGE)\" \ +-DPACKAGE_LIB_DIR=\"$(libdir)\" \ +@ELEMENTARY_CFLAGS@ \ +@ELEMENTARY_X_CFLAGS@ \ +@ELEMENTARY_FB_CFLAGS@ \ +@ELEMENTARY_WIN32_CFLAGS@ \ +@ELEMENTARY_WINCE_CFLAGS@ \ +@ELEMENTARY_EDBUS_CFLAGS@ \ +@ELEMENTARY_EFREET_CFLAGS@ \ +@ELEMENTARY_ETHUMB_CFLAGS@ + +if ELEMENTARY_WINDOWS_BUILD +AM_CPPFLAGS += -DELEMENTARY_BUILD +endif + +pkgdir = $(libdir)/elementary/modules/test_entry/$(MODULE_ARCH) +pkg_LTLIBRARIES = module.la + +module_la_SOURCES = mod.c + +module_la_LIBADD = $(top_builddir)/src/lib/libelementary.la +module_la_LDFLAGS = -no-undefined @lt_enable_auto_import@ -module -avoid-version +module_la_LIBTOOLFLAGS = --tag=disable-static diff --git a/src/modules/test_entry/mod.c b/src/modules/test_entry/mod.c new file mode 100644 index 0000000..0b978e6 --- /dev/null +++ b/src/modules/test_entry/mod.c @@ -0,0 +1,36 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif + +// module api funcs needed +EAPI int +elm_modapi_init(void *m __UNUSED__) +{ + return 1; // succeed always +} + +EAPI int +elm_modapi_shutdown(void *m __UNUSED__) +{ + return 1; // succeed always +} + +// module fucns for the specific module type +EAPI void +obj_hook(Evas_Object *obj) +{ + printf("hook: %p\n", obj); +} + +EAPI void +obj_unhook(Evas_Object *obj) +{ + printf("unhook: %p\n", obj); +} + +EAPI void +obj_longpress(Evas_Object *obj) +{ + printf("longpress: %p\n", obj); +} diff --git a/src/modules/test_map/Makefile.am b/src/modules/test_map/Makefile.am new file mode 100644 index 0000000..d789ce9 --- /dev/null +++ b/src/modules/test_map/Makefile.am @@ -0,0 +1,32 @@ + +MAINTAINERCLEANFILES = Makefile.in + +AM_CPPFLAGS = \ +-I. \ +-I$(top_builddir) \ +-I$(top_srcdir) \ +-I$(top_srcdir)/src/lib \ +-I$(top_builddir)/src/lib \ +-DPACKAGE_DATA_DIR=\"$(datadir)/$(PACKAGE)\" \ +-DPACKAGE_LIB_DIR=\"$(libdir)\" \ +@ELEMENTARY_CFLAGS@ \ +@ELEMENTARY_X_CFLAGS@ \ +@ELEMENTARY_FB_CFLAGS@ \ +@ELEMENTARY_WIN32_CFLAGS@ \ +@ELEMENTARY_WINCE_CFLAGS@ \ +@ELEMENTARY_EDBUS_CFLAGS@ \ +@ELEMENTARY_EFREET_CFLAGS@ \ +@ELEMENTARY_ETHUMB_CFLAGS@ + +if ELEMENTARY_WINDOWS_BUILD +AM_CPPFLAGS += -DELEMENTARY_BUILD +endif + +pkgdir = $(libdir)/elementary/modules/test_map/$(MODULE_ARCH) +pkg_LTLIBRARIES = module.la + +module_la_SOURCES = mod.c + +module_la_LIBADD = $(top_builddir)/src/lib/libelementary.la +module_la_LDFLAGS = -no-undefined @lt_enable_auto_import@ -module -avoid-version +module_la_LIBTOOLFLAGS = --tag=disable-static diff --git a/src/modules/test_map/mod.c b/src/modules/test_map/mod.c new file mode 100644 index 0000000..8b45ede --- /dev/null +++ b/src/modules/test_map/mod.c @@ -0,0 +1,50 @@ +#include +#ifdef HAVE_CONFIG_H +# include "elementary_config.h" +#endif + +EAPI int +elm_modapi_init(void *m __UNUSED__) +{ + return 1; // succeed always +} + +EAPI int +elm_modapi_shutdown(void *m __UNUSED__) +{ + return 1; // succeed always +} + +EAPI Eina_Bool +obj_hook(Evas_Object *obj __UNUSED__) +{ + return EINA_TRUE; +} + +EAPI Eina_Bool +obj_unhook(Evas_Object *obj __UNUSED__) +{ + return EINA_TRUE; +} + +EAPI Eina_Bool +obj_convert_geo_into_coord(const Evas_Object *obj __UNUSED__, int zoom __UNUSED__, double lon __UNUSED__, double lat __UNUSED__, int size __UNUSED__, int *x __UNUSED__, int *y __UNUSED__) +{ + return EINA_FALSE; +} + +EAPI Eina_Bool +obj_convert_coord_into_geo(const Evas_Object *obj __UNUSED__, int zoom __UNUSED__, int x __UNUSED__, int y __UNUSED__, int size __UNUSED__, double *lon __UNUSED__, double *lat __UNUSED__) +{ + return EINA_FALSE; +} + +EAPI char* +obj_url_request(Evas_Object *obj __UNUSED__, int x, int y, int zoom) +{ + char buf[PATH_MAX]; + snprintf(buf, sizeof(buf), "http://tile.openstreetmap.org/%d/%d/%d.png", + zoom, x, y); + return strdup(buf); +} + diff --git a/tests/test_decl.sh b/tests/test_decl.sh new file mode 100755 index 0000000..ca86eba --- /dev/null +++ b/tests/test_decl.sh @@ -0,0 +1,102 @@ +#!/bin/bash +ret=0 + +check(){ + i=$1 + shift + grep -h -B1 -10 -e "^$i(" $@ >eapi.decl + if [ $? != 0 ]; then + echo -e "\e[31;1mNOT IMPLEMENTED\e[m\t $i" + ret=1 + return + fi + grep -qe "^--$" eapi.decl + if [ $? == 0 ]; then + echo -e "\e[31;1mMULTI IMPLEMENT\e[m\t $i" + ret=1 + return + fi + + head -1 eapi.decl | grep -qe '^EAPI' + if [ $? != 0 ];then + echo -e "\e[31;1mMISSING EAPI\e[m\t $i" + ret=1 + fi + + func=$(echo $i | grep -oe 'elm_\w\+') + ass=$(sed '2q;d' eapi.decl) + + echo $i | grep -qe "^elm_object" + if [ $? == 0 ];then + rm eapi.decl + return + fi + + echo $i | grep -qe "^elm_widget" + if [ $? == 0 ];then + + echo $ass | grep -qe "elm_widget\w\+(\(const \)\?Evas_Object \*" + if [ $? == 0 ];then + tail -n9 eapi.decl | grep -q "\(API_ENTRY\|_elm_widget_is\)" + if [ $? != 0 ];then + echo -e "\e[31;1mMISSING CHECKER\e[m\t $i" + ret=1 + fi + return + fi + + echo $ass | grep -qe "elm_widget\w\+(\(const \)\?Elm_ \*" + if [ $? == 0 ];then + tail -n9 eapi.decl | grep -qe "ELM_WIDGET_ITEM_CHECK" + if [ $? != 0 ];then + echo -e "\e[31;1mMISSING CHECKER\e[m\t $i" + ret=1 + fi + return + fi + fi + + echo $ass | grep -qe "elm_\w\+_add" + if [ $? == 0 ];then + echo -e "\e[32;1m???\e[m\t $i" + return + fi + + echo $ass | grep -qe "elm_\w\+(\(const \)\?Evas_Object \*" + if [ $? == 0 ];then + tail -n9 eapi.decl | grep -q "ELM_CHECK_WIDTYPE" + if [ $? != 0 ];then + echo -e "\e[31;1mMISSING CHECKER\e[m\t $i" + ret=1 + fi + return + fi + + echo $ass | grep -qe "elm_\w\+(\(const \)\?Elm_\w\+_Item \*" + if [ $? == 0 ];then + tail -n9 eapi.decl | grep -qe "ELM_\w\+_ITEM_.*CHECK" + if [ $? != 0 ];then + echo -e "\e[31;1mMISSING CHECKER\e[m\t $i" + ret=1 + fi + return + fi + + rm eapi.decl +} + +grep -e "^ *EAPI.*(.*)" src/lib/Elementary.h.in | grep -oe 'elm_\w\+' >eapi.list + +for i in $(cat eapi.list); do + check $i $(ls -1 src/lib/*.c | grep -v elm_widget) +done + +grep -e "^ *EAPI.*(.*)" src/lib/elm_widget.h | grep -oe '_\?elm_\w\+' >eapi.list + +for i in $(cat eapi.list); do + check $i src/lib/elm_widget.c +done + +rm -f eapi.decl +rm eapi.list +exit $ret diff --git a/tests/test_eapi.sh b/tests/test_eapi.sh new file mode 100755 index 0000000..4a190e5 --- /dev/null +++ b/tests/test_eapi.sh @@ -0,0 +1,40 @@ +#!/bin/bash +ret=0 + +sed -n '/^EAPI /{n;p;}' src/lib/*.c >eapi.list + +for i in $(cat eapi.list|grep -o "^\w\+"); do + grep -q "\<$i\>" src/lib/elm_priv.h + if [ $? == 0 ]; then + echo -e "\e[31;1mEAPI in priv.h\e[m\t $i" + ret=1 + fi + + echo $i | grep -qe '^_\?elm_widget' + if [ $? == 0 ]; then + grep -qe "EAPI.*\<$i\>" src/lib/elm_widget.h + if [ $? != 0 ]; then + echo -e "\e[31;1m WIDGET missing in widget.h\e[m\t $i" + ret=1 + fi + grep -qe "EAPI.*\<$i\>" src/lib/Elementary.h.in + if [ $? == 0 ]; then + echo -e "\e[31;1m WIDGET in Elm.h\e[m\t $i" + ret=1 + fi + else + grep -qe "EAPI.*\<$i\>" src/lib/Elementary.h.in + if [ $? != 0 ]; then + echo -e "\e[31;1m ELM missing in Elm.h\e[m\t $i" + ret=1 + fi + grep -qe "EAPI.*\<$i\>" src/lib/elm_widget.h + if [ $? == 0 ]; then + echo -e "\e[31;1m ELM in widget.h\e[m\t $i" + ret=1 + fi + fi +done + +rm eapi.list +exit $ret diff --git a/tests/test_getter.sh b/tests/test_getter.sh new file mode 100755 index 0000000..749d488 --- /dev/null +++ b/tests/test_getter.sh @@ -0,0 +1,27 @@ +#!/bin/bash +ret=0 +check(){ + func=$(echo $1 | grep -oe 'elm_\w\+') + echo $1 | grep -qe "_get([^\(const \)]\([^,\*)]\)\+\*" + if [ $? == 0 ];then + echo -e "\e[31;1mNOT CONST\e[m\t $func" + ret=1 + fi + +} + +HEADERS="src/lib/Elementary.h.in +src/lib/Elementary_Cursor.h +src/lib/elm_widget.h" + +IFS=$'\n' + +for header in $HEADERS; do + grep -e "^ *EAPI.*(.*)" $header | grep -e 'elm_\w\+_get' >eapi.list + + for i in $(cat eapi.list); do + check $i $header + done + rm eapi.list +done +exit $ret diff --git a/tests/test_setter.sh b/tests/test_setter.sh new file mode 100755 index 0000000..eef7200 --- /dev/null +++ b/tests/test_setter.sh @@ -0,0 +1,55 @@ +#!/bin/bash +ret=0 + +BLACKLIST="tests/test_setter_blacklist.txt" + +check(){ + func=$(echo $1 | grep -oe '_\?elm_\w\+') + base=${func%_set} + cat $BLACKLIST | grep -q $func + if [ $? == 0 ];then + return + fi + echo $1 | grep -qe "_set(const \+[^\(char \+\*\)]" + if [ $? == 0 ];then + echo -e "\e[31;1mCONST\e[m\t $func" + ret=1 + fi + echo $1 | grep -qe "EAPI \+\(void\|Eina_Bool\)" + if [ $? != 0 ];then + echo -e "\e[31;1mUNKNOWN RETURN\e[m\t $func" + ret=1 + fi + echo $1 | grep -qe "\(cb_set\|all_set\)(" + if [ $? != 0 ];then + grep -qe "EAPI.*\<${base}_get\>" $2 + if [ $? != 0 ];then + echo -e "\e[31;1mMISSING GETTER\e[m\t $func" + ret=1 + fi + echo $1 | grep -qe "\(content\|icon\|end\)_set(\w\+ \+\*obj, \w\+ \+\*\w\+);" + if [ $? == 0 ];then + grep -qe "EAPI.*\<${base}_unset\>" $2 + if [ $? != 0 ];then + echo -e "\e[31;1mMISSING UNSETTER\e[m\t $func" + ret=1 + fi + fi + fi +} + +HEADERS="src/lib/Elementary.h.in +src/lib/Elementary_Cursor.h +src/lib/elm_widget.h" + +IFS=$'\n' + +for header in $HEADERS; do + grep -e "^ *EAPI.*(.*)" $header | grep -e 'elm_\w\+_set' >eapi.list + + for i in $(cat eapi.list); do + check $i $header + done + rm eapi.list +done +exit $ret diff --git a/tests/test_setter_blacklist.txt b/tests/test_setter_blacklist.txt new file mode 100644 index 0000000..61e4501 --- /dev/null +++ b/tests/test_setter_blacklist.txt @@ -0,0 +1,18 @@ +elm_widget_del_hook_set +elm_widget_del_pre_hook_set +elm_widget_focus_hook_set +elm_widget_activate_hook_set +elm_widget_disable_hook_set +elm_widget_theme_hook_set +elm_widget_event_hook_set +elm_widget_changed_hook_set +elm_widget_signal_emit_hook_set +elm_widget_signal_callback_add_hook_set +elm_widget_signal_callback_del_hook_set +elm_widget_focus_next_hook_set +elm_widget_on_focus_hook_set +elm_widget_on_change_hook_set +elm_widget_on_show_region_hook_set +elm_widget_focus_region_hook_set +elm_widget_on_focus_region_hook_set +elm_radio_value_pointer_set -- 2.7.4

  2. Q1C7IYam~%1Y%Liik0S?^5Z|Oo}@7+$f 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 literal 0 HcmV?d00001 diff --git a/data/images/rock_01.jpg b/data/images/rock_01.jpg new file mode 100644 index 0000000000000000000000000000000000000000..c50ccb31975d7ebe60268f6154fbb08b7798cc03 GIT binary patch literal 330094 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 kJM%@ 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𝔡rE*dU!kRr07vg3fI2hXrgv1++XP_Uts0sxoTJs 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