diff options
author | Carsten Haitzler <raster@rasterman.com> | 2008-09-30 06:58:56 +0000 |
---|---|---|
committer | Carsten Haitzler <raster@rasterman.com> | 2008-09-30 06:58:56 +0000 |
commit | 707657b49ca52860fde30c6b59c4453af7809d9d (patch) | |
tree | 9e7dba5578d2ea0ba1c933a496029c17c90e2866 | |
download | elementary-707657b49ca52860fde30c6b59c4453af7809d9d.tar.gz |
elementary becomes its own tree/lib/test binary
SVN revision: 36343
101 files changed, 9832 insertions, 0 deletions
diff --git a/AUTHORS b/AUTHORS new file mode 100644 index 000000000..73ebbe2df --- /dev/null +++ b/AUTHORS @@ -0,0 +1 @@ +The Rasterman (Carsten Haitzler) <raster@rasterman.com> diff --git a/COPYING b/COPYING new file mode 100644 index 000000000..a0990367e --- /dev/null +++ b/COPYING @@ -0,0 +1 @@ +TBD diff --git a/ChangeLog b/ChangeLog new file mode 100644 index 000000000..e69de29bb --- /dev/null +++ b/ChangeLog diff --git a/INSTALL b/INSTALL new file mode 100644 index 000000000..9cdec5bf2 --- /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 Rage for it to run properly. diff --git a/Makefile.am b/Makefile.am new file mode 100644 index 000000000..6f49e6a18 --- /dev/null +++ b/Makefile.am @@ -0,0 +1,14 @@ +SUBDIRS = src data + +MAINTAINERCLEANFILES = Makefile.in aclocal.m4 config.guess \ + config.h.in config.sub configure install-sh \ + ltconfig ltmain.sh missing mkinstalldirs \ + stamp-h.in acconfig.h depcomp + +EXTRA_DIST = README AUTHORS COPYING autogen.sh eet.pc.in + +pkgconfigdir = $(libdir)/pkgconfig +pkgconfig_DATA = elementary.pc + +installed_headersdir = $(prefix)/include/elementary +installed_headers_DATA = elementary_config.h @@ -0,0 +1 @@ +Alarm Clock diff --git a/autogen.sh b/autogen.sh new file mode 100755 index 000000000..2d15d5bea --- /dev/null +++ b/autogen.sh @@ -0,0 +1,19 @@ +#!/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 diff --git a/configure.in b/configure.in new file mode 100644 index 000000000..35b097d78 --- /dev/null +++ b/configure.in @@ -0,0 +1,57 @@ +# get rid of that stupid cache mechanism +rm -f config.cache + +AC_INIT(elementary, 0.1.0.0, enlightenment-devel@lists.sourceforge.net) +AC_PREREQ(2.52) +AC_CONFIG_SRCDIR(configure.in) + +AM_INIT_AUTOMAKE(1.6 dist-bzip2) +AM_CONFIG_HEADER(elementary_config.h) + +AC_CANONICAL_BUILD +AC_CANONICAL_HOST +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 + +VMAJ=`echo $PACKAGE_VERSION | awk -F. '{printf("%s", $1);}'` +VMIN=`echo $PACKAGE_VERSION | awk -F. '{printf("%s", $2);}'` +VMIC=`echo $PACKAGE_VERSION | awk -F. '{printf("%s", $3);}'` +SNAP=`echo $PACKAGE_VERSION | awk -F. '{printf("%s", $4);}'` +version_info=`expr $VMAJ + $VMIN`":$VMIC:$VMIN" +AC_SUBST(version_info) +PKG_PROG_PKG_CONFIG + +PKG_CHECK_MODULES([ELEMENTARY], [ + eet + evas + ecore + ecore-x + ecore-evas + ecore-job + ecore-txt + ecore-file + edje + edbus + ]) + +my_libs="-lm" +AC_SUBST(my_libs) + +AC_OUTPUT([ +Makefile +elementary.pc +src/Makefile +src/lib/Makefile +src/bin/Makefile +data/Makefile +data/themes/Makefile +]) diff --git a/data/.cvsignore b/data/.cvsignore new file mode 100644 index 000000000..d88045013 --- /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 000000000..b18097413 --- /dev/null +++ b/data/Makefile.am @@ -0,0 +1,3 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in +SUBDIRS = themes diff --git a/data/themes/Makefile.am b/data/themes/Makefile.am new file mode 100644 index 000000000..0e20a4150 --- /dev/null +++ b/data/themes/Makefile.am @@ -0,0 +1,68 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +EDJE_CC = edje_cc +EDJE_FLAGS = -v -id $(top_srcdir)/data/themes -fd $(top_srcdir)/data/themes + +filesdir = $(datadir)/elementary/themes +files_DATA = default.edj + +EXTRA_DIST = \ +default.edc \ +arrow_down.png \ +arrow_up.png \ +bt_base1.png \ +bt_base2.png \ +bt_bases.png \ +bt_basew.png \ +bt_hilight.png \ +bt_hilightw.png \ +bt_shine.png \ +bt_sm_base1.png \ +bt_sm_base2.png \ +bt_sm_hilight.png \ +bt_sm_shine.png \ +dia_botshad.png \ +dia_grad.png \ +dia_topshad.png \ +frame_1.png \ +frame_2.png \ +flip_0b.png \ +flip_0t.png \ +flip_1b.png \ +flip_1t.png \ +flip_2b.png \ +flip_2t.png \ +flip_3b.png \ +flip_3t.png \ +flip_4b.png \ +flip_4t.png \ +flip_5b.png \ +flip_5t.png \ +flip_6b.png \ +flip_6t.png \ +flip_7b.png \ +flip_7t.png \ +flip_8b.png \ +flip_8t.png \ +flip_9b.png \ +flip_9t.png \ +flip_amb.png \ +flip_amt.png \ +flip_base.png \ +flip_base_shad.png \ +flip_pmb.png \ +flip_pmt.png \ +flip_shad.png \ +sb_runnerh.png \ +sb_runnerv.png \ +shelf_inset.png \ +tog_base.png + +default.edj: Makefile $(EXTRA_DIST) + $(EDJE_CC) $(EDJE_FLAGS) \ + $(top_srcdir)/data/themes/default.edc \ + $(top_builddir)/data/themes/default.edj + +clean-local: + rm -f *.edj diff --git a/data/themes/arrow_down.png b/data/themes/arrow_down.png Binary files differnew file mode 100644 index 000000000..db81aac43 --- /dev/null +++ b/data/themes/arrow_down.png diff --git a/data/themes/arrow_down.xcf.gz b/data/themes/arrow_down.xcf.gz Binary files differnew file mode 100644 index 000000000..3d4e89c54 --- /dev/null +++ b/data/themes/arrow_down.xcf.gz diff --git a/data/themes/arrow_up.png b/data/themes/arrow_up.png Binary files differnew file mode 100644 index 000000000..a90fe9352 --- /dev/null +++ b/data/themes/arrow_up.png diff --git a/data/themes/arrow_up.xcf.gz b/data/themes/arrow_up.xcf.gz Binary files differnew file mode 100644 index 000000000..977e24cbf --- /dev/null +++ b/data/themes/arrow_up.xcf.gz diff --git a/data/themes/bt_base1.png b/data/themes/bt_base1.png Binary files differnew file mode 100644 index 000000000..2d1f17909 --- /dev/null +++ b/data/themes/bt_base1.png diff --git a/data/themes/bt_base2.png b/data/themes/bt_base2.png Binary files differnew file mode 100644 index 000000000..dd3e3ce06 --- /dev/null +++ b/data/themes/bt_base2.png diff --git a/data/themes/bt_bases.png b/data/themes/bt_bases.png Binary files differnew file mode 100644 index 000000000..1b867fd7a --- /dev/null +++ b/data/themes/bt_bases.png diff --git a/data/themes/bt_basew.png b/data/themes/bt_basew.png Binary files differnew file mode 100644 index 000000000..8d787dd2b --- /dev/null +++ b/data/themes/bt_basew.png diff --git a/data/themes/bt_hilight.png b/data/themes/bt_hilight.png Binary files differnew file mode 100644 index 000000000..3b7fe5b0c --- /dev/null +++ b/data/themes/bt_hilight.png diff --git a/data/themes/bt_hilightw.png b/data/themes/bt_hilightw.png Binary files differnew file mode 100644 index 000000000..b97a4f81b --- /dev/null +++ b/data/themes/bt_hilightw.png diff --git a/data/themes/bt_shine.png b/data/themes/bt_shine.png Binary files differnew file mode 100644 index 000000000..a58bdeed4 --- /dev/null +++ b/data/themes/bt_shine.png diff --git a/data/themes/bt_sm_base1.png b/data/themes/bt_sm_base1.png Binary files differnew file mode 100644 index 000000000..c37e182ed --- /dev/null +++ b/data/themes/bt_sm_base1.png diff --git a/data/themes/bt_sm_base2.png b/data/themes/bt_sm_base2.png Binary files differnew file mode 100644 index 000000000..f159648ec --- /dev/null +++ b/data/themes/bt_sm_base2.png diff --git a/data/themes/bt_sm_hilight.png b/data/themes/bt_sm_hilight.png Binary files differnew file mode 100644 index 000000000..63899caac --- /dev/null +++ b/data/themes/bt_sm_hilight.png diff --git a/data/themes/bt_sm_shine.png b/data/themes/bt_sm_shine.png Binary files differnew file mode 100644 index 000000000..23bf3110e --- /dev/null +++ b/data/themes/bt_sm_shine.png diff --git a/data/themes/default.edc b/data/themes/default.edc new file mode 100644 index 000000000..ed2004b9d --- /dev/null +++ b/data/themes/default.edc @@ -0,0 +1,2121 @@ +collections { + +/////////////////////////////////////////////////////////////////////////////// + group { name: "bg"; + 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.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 -4; + image.normal: "dia_botshad.png"; + fill { + smooth: 0; + size { + relative: 0.0 1.0; + offset: 64 0; + } + } + } + } + part { name: "elm.swallow.contents"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.offset: 4 4; + rel2.offset: -5 -5; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "scroller"; + 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: "sb_runnerh.png" COMP; + image: "sb_runnerv.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: "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"; + 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; + visible: 0; + min: 17 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: "sb_vbar_runner"; + clip_to: "sb_vbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + min: 3 3; + max: 3 99999; + rel1.to: "sb_vbar"; + rel2.to: "sb_vbar"; + image { + normal: "sb_runnerv.png"; + border: 0 0 4 4; + } + fill.smooth: 0; + } + } + 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; + min: 17 17; + 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; + } + } + } + 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"; + 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; + visible: 0; + min: 17 17; + 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: "sb_hbar_runner"; + clip_to: "sb_hbar_clip"; + mouse_events: 0; + description { state: "default" 0.0; + min: 3 3; + max: 99999 3; + rel1.to: "sb_hbar"; + rel2.to: "sb_hbar"; + image { + normal: "sb_runnerh.png"; + border: 4 4 0 0; + } + fill.smooth: 0; + } + } + 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; + min: 17 17; + 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: 6 6 6 6; + } + } + } + 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: "sb_vbar_show"; + signal: "elm,action,show,vbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: LINEAR 1.0; + target: "sb_vbar_clip"; + after: "sb_vbar_hide"; + } + program { name: "sb_vbar_hide"; + signal: "elm,action,hide,vbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 1.0; + target: "sb_vbar_clip"; + } + program { name: "sb_hbar_show"; + signal: "elm,action,show,hbar"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: LINEAR 1.0; + target: "sb_hbar_clip"; + after: "sb_hbar_hide"; + } + program { name: "sb_hbar_hide"; + signal: "elm,action,hide,hbar"; + source: "elm"; + action: STATE_SET "hidden" 0.0; + transition: LINEAR 1.0; + target: "sb_hbar_clip"; + } + // FIXME: check if visible and only if not - do this + program { name: "scroll"; + signal: "elm,action,scroll"; + source: "elm"; + action: STATE_SET "default" 0.0; + transition: LINEAR 1.0; + target: "sb_vbar_clip"; + target: "sb_hbar_clip"; + after: "sb_vbar_hide"; + after: "sb_hbar_hide"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "label"; + styles + { + style { name: "textblock_style"; + base: "font=Sans font_size=10 align=left color=#000 wrap=word"; + + tag: "br" "\n"; + tag: "hilight" "+ font=Sans:style=Bold"; + tag: "b" "+ font=Sans:style=Bold"; + } + } + parts { + part { name: "elm.text"; + type: TEXTBLOCK; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + text { + style: "textblock_style"; + min: 1 1; + } + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "button"; + images { + image: "bt_base1.png" COMP; + image: "bt_base2.png" COMP; + image: "bt_hilight.png" COMP; + image: "bt_shine.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; + } + } + description { state: "clicked" 0.0; + inherit: "default" 0.0; + image.normal: "bt_base1.png"; + } + } + part { name: "elm.swallow.contents"; + 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; + } + } + 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.contents"; + 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; + } + } + description { state: "visible" 0.0; + inherit: "default" 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; + } + } + } + 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; + } + } + } + } + programs { + program { + name: "button_click"; + signal: "mouse,down,1"; + source: "button_image"; + action: STATE_SET "clicked" 0.0; + target: "button_image"; + } + program { + name: "button_unclick"; + signal: "mouse,up,1"; + source: "button_image"; + action: STATE_SET "default" 0.0; + target: "button_image"; + } + program { + name: "button_unclick2"; + signal: "mouse,clicked,1"; + source: "over2"; + action: SIGNAL_EMIT "elm,action,click" ""; + } + 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.contents"; + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.contents"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "toggle"; + 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; + } + parts { + part { name: "bg"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + rel1.relative: 1.0 0.0; + rel1.offset: -16 3; + rel2.offset: -16 -4; + align: 1.0 0.5; + min: 96 24; + max: 96 24; + 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: 24 24; + max: 24 24; + aspect: 1.0 1.0; + aspect_preference: VERTICAL; + color: 0 0 0 0; + } + } + part { name: "onrect"; + type: RECT; + scale: 1; + clip_to: "clipper"; + mouse_events: 1; + description { state: "default" 0.0; + rel1.to: "button"; + rel1.relative: -3.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: 1; + description { state: "default" 0.0; + rel1.to: "button"; + rel1.relative: 1.0 0.0; + rel2.to: "button"; + rel2.relative: 4.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"; + } + } + part { name: "elm.offtext"; + type: TEXT; + mouse_events: 0; + scale: 1; + clip_to: "clipper"; + description { state: "default" 0.0; + rel1.to: "offrect"; + rel2.to: "offrect"; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 1; + align: 0.5 0.5; + text: "OFF"; + } + } + } + part { name: "elm.ontext"; + type: TEXT; + mouse_events: 0; + scale: 1; + clip_to: "clipper"; + description { state: "default" 0.0; + rel1.to: "onrect"; + rel2.to: "onrect"; + color: 0 0 0 255; + text { + font: "Sans,Edje-Vera"; + size: 10; + min: 0 1; + align: 0.5 0.5; + text: "ON"; + } + } + } + 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; + } + 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; + } + } + } + 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.contents"; + 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; + } + } + part { + name: "elm.text"; + type: TEXT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + rel1.to_x: "elm.swallow.contents"; + 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; + } + } + } + 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", 100.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.contents"; + } + program { name: "icon_hide"; + signal: "elm,state,icon,hidden"; + source: "elm"; + action: STATE_SET "default" 0.0; + target: "elm.swallow.contents"; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "flipdigit"; + 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; + 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_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"; + } + 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" ""; + } + program { name: "down"; + signal: "mouse,down,1"; + source: "b"; + action: SIGNAL_EMIT "elm,action,down" ""; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "flipampm"; + 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 + 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" ""; + } + program { name: "down"; + signal: "mouse,down,1"; + source: "b"; + action: SIGNAL_EMIT "elm,action,down" ""; + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "clock/all"; + 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: 20; + 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: 20; + 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: "clock/seconds"; + 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: 20; + 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: 20; + 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: "clock/am_pm"; + 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: 20; + 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: "clock"; + 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: 20; + 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: "pad"; + parts { + part { name: "t"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + align: 0.0 0.0; + min: 4 4; + max: 4 4; + rel1.relative: 0.0 0.0; + rel2.relative: 0.0 0.0; + rel2.offset: 0 0; + } + } + part { name: "b"; + type: RECT; + mouse_events: 0; + scale: 1; + description { state: "default" 0.0; + visible: 0; + align: 1.0 1.0; + min: 4 4; + max: 4 4; + rel1.relative: 1.0 1.0; + rel1.offset: -1 -1; + rel2.relative: 1.0 1.0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1.to: "t"; + rel1.relative: 1.0 1.0; + rel2.to: "b"; + rel2.relative: 0.0 0.0; + } + } + } + } + +/////////////////////////////////////////////////////////////////////////////// + group { name: "frame"; + 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; + image { + normal: "frame_2.png"; + border: 5 5 32 26; + middle: 0; + } + fill.smooth : 0; + } + } + part { name: "elm.swallow.content"; + type: SWALLOW; + description { state: "default" 0.0; + rel1 { + to_y: "elm.text"; + relative: 0.0 1.0; + offset: 8 2; + } + rel2.offset: -9 -9; + } + } + 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.offset: -5 -5; + image { + normal: "frame_1.png"; + border: 2 2 28 22; + middle: 0; + } + fill.smooth : 0; + } + } + } + } +} diff --git a/data/themes/dia_botshad.png b/data/themes/dia_botshad.png Binary files differnew file mode 100644 index 000000000..89a598e0f --- /dev/null +++ b/data/themes/dia_botshad.png diff --git a/data/themes/dia_grad.png b/data/themes/dia_grad.png Binary files differnew file mode 100644 index 000000000..bfd7d0e1d --- /dev/null +++ b/data/themes/dia_grad.png diff --git a/data/themes/dia_topshad.png b/data/themes/dia_topshad.png Binary files differnew file mode 100644 index 000000000..1a772130a --- /dev/null +++ b/data/themes/dia_topshad.png diff --git a/data/themes/flip.xcf.gz b/data/themes/flip.xcf.gz Binary files differnew file mode 100644 index 000000000..36aca4d2b --- /dev/null +++ b/data/themes/flip.xcf.gz diff --git a/data/themes/flip_0b.png b/data/themes/flip_0b.png Binary files differnew file mode 100644 index 000000000..8a6ae9e1c --- /dev/null +++ b/data/themes/flip_0b.png diff --git a/data/themes/flip_0t.png b/data/themes/flip_0t.png Binary files differnew file mode 100644 index 000000000..72506aa1b --- /dev/null +++ b/data/themes/flip_0t.png diff --git a/data/themes/flip_1b.png b/data/themes/flip_1b.png Binary files differnew file mode 100644 index 000000000..ed80e8b2f --- /dev/null +++ b/data/themes/flip_1b.png diff --git a/data/themes/flip_1t.png b/data/themes/flip_1t.png Binary files differnew file mode 100644 index 000000000..6c1fba8f0 --- /dev/null +++ b/data/themes/flip_1t.png diff --git a/data/themes/flip_2b.png b/data/themes/flip_2b.png Binary files differnew file mode 100644 index 000000000..3183b5900 --- /dev/null +++ b/data/themes/flip_2b.png diff --git a/data/themes/flip_2t.png b/data/themes/flip_2t.png Binary files differnew file mode 100644 index 000000000..3453e3d59 --- /dev/null +++ b/data/themes/flip_2t.png diff --git a/data/themes/flip_3b.png b/data/themes/flip_3b.png Binary files differnew file mode 100644 index 000000000..2eca7d4f2 --- /dev/null +++ b/data/themes/flip_3b.png diff --git a/data/themes/flip_3t.png b/data/themes/flip_3t.png Binary files differnew file mode 100644 index 000000000..4de980462 --- /dev/null +++ b/data/themes/flip_3t.png diff --git a/data/themes/flip_4b.png b/data/themes/flip_4b.png Binary files differnew file mode 100644 index 000000000..23484c982 --- /dev/null +++ b/data/themes/flip_4b.png diff --git a/data/themes/flip_4t.png b/data/themes/flip_4t.png Binary files differnew file mode 100644 index 000000000..20291610e --- /dev/null +++ b/data/themes/flip_4t.png diff --git a/data/themes/flip_5b.png b/data/themes/flip_5b.png Binary files differnew file mode 100644 index 000000000..8d9312a12 --- /dev/null +++ b/data/themes/flip_5b.png diff --git a/data/themes/flip_5t.png b/data/themes/flip_5t.png Binary files differnew file mode 100644 index 000000000..df439296c --- /dev/null +++ b/data/themes/flip_5t.png diff --git a/data/themes/flip_6b.png b/data/themes/flip_6b.png Binary files differnew file mode 100644 index 000000000..09393e648 --- /dev/null +++ b/data/themes/flip_6b.png diff --git a/data/themes/flip_6t.png b/data/themes/flip_6t.png Binary files differnew file mode 100644 index 000000000..3cc4061fc --- /dev/null +++ b/data/themes/flip_6t.png diff --git a/data/themes/flip_7b.png b/data/themes/flip_7b.png Binary files differnew file mode 100644 index 000000000..9afc41982 --- /dev/null +++ b/data/themes/flip_7b.png diff --git a/data/themes/flip_7t.png b/data/themes/flip_7t.png Binary files differnew file mode 100644 index 000000000..abe1bc94d --- /dev/null +++ b/data/themes/flip_7t.png diff --git a/data/themes/flip_8b.png b/data/themes/flip_8b.png Binary files differnew file mode 100644 index 000000000..2185ee984 --- /dev/null +++ b/data/themes/flip_8b.png diff --git a/data/themes/flip_8t.png b/data/themes/flip_8t.png Binary files differnew file mode 100644 index 000000000..718e484ec --- /dev/null +++ b/data/themes/flip_8t.png diff --git a/data/themes/flip_9b.png b/data/themes/flip_9b.png Binary files differnew file mode 100644 index 000000000..f867aea3c --- /dev/null +++ b/data/themes/flip_9b.png diff --git a/data/themes/flip_9t.png b/data/themes/flip_9t.png Binary files differnew file mode 100644 index 000000000..5800a4c74 --- /dev/null +++ b/data/themes/flip_9t.png diff --git a/data/themes/flip_amb.png b/data/themes/flip_amb.png Binary files differnew file mode 100644 index 000000000..e7b3b170d --- /dev/null +++ b/data/themes/flip_amb.png diff --git a/data/themes/flip_amt.png b/data/themes/flip_amt.png Binary files differnew file mode 100644 index 000000000..bc6a7154c --- /dev/null +++ b/data/themes/flip_amt.png diff --git a/data/themes/flip_base.png b/data/themes/flip_base.png Binary files differnew file mode 100644 index 000000000..607fba927 --- /dev/null +++ b/data/themes/flip_base.png diff --git a/data/themes/flip_base_shad.png b/data/themes/flip_base_shad.png Binary files differnew file mode 100644 index 000000000..056997776 --- /dev/null +++ b/data/themes/flip_base_shad.png diff --git a/data/themes/flip_pmb.png b/data/themes/flip_pmb.png Binary files differnew file mode 100644 index 000000000..de14fa5ee --- /dev/null +++ b/data/themes/flip_pmb.png diff --git a/data/themes/flip_pmt.png b/data/themes/flip_pmt.png Binary files differnew file mode 100644 index 000000000..8a72655ba --- /dev/null +++ b/data/themes/flip_pmt.png diff --git a/data/themes/flip_shad.png b/data/themes/flip_shad.png Binary files differnew file mode 100644 index 000000000..3d74ceae2 --- /dev/null +++ b/data/themes/flip_shad.png diff --git a/data/themes/frame_1.png b/data/themes/frame_1.png Binary files differnew file mode 100644 index 000000000..fd5645e5b --- /dev/null +++ b/data/themes/frame_1.png diff --git a/data/themes/frame_2.png b/data/themes/frame_2.png Binary files differnew file mode 100644 index 000000000..0fef1e9a9 --- /dev/null +++ b/data/themes/frame_2.png diff --git a/data/themes/sb_runnerh.png b/data/themes/sb_runnerh.png Binary files differnew file mode 100644 index 000000000..a483ce8b1 --- /dev/null +++ b/data/themes/sb_runnerh.png diff --git a/data/themes/sb_runnerv.png b/data/themes/sb_runnerv.png Binary files differnew file mode 100644 index 000000000..cb2da6fc3 --- /dev/null +++ b/data/themes/sb_runnerv.png diff --git a/data/themes/shelf_inset.png b/data/themes/shelf_inset.png Binary files differnew file mode 100644 index 000000000..bb1989dd7 --- /dev/null +++ b/data/themes/shelf_inset.png diff --git a/data/themes/tog_base.png b/data/themes/tog_base.png Binary files differnew file mode 100644 index 000000000..42cc65cfa --- /dev/null +++ b/data/themes/tog_base.png diff --git a/elementary.pc.in b/elementary.pc.in new file mode 100644 index 000000000..3d2dfa4b9 --- /dev/null +++ b/elementary.pc.in @@ -0,0 +1,11 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: eet +Description: Library for speedy data storage, retrieval, and compression +Version: @VERSION@ +Libs: -L${libdir} -lelementary +Libs.private: @my_libs@ @ELEMENTARY_LIBS@ +Cflags: -I${includedir} -I${includedir}/elementary diff --git a/src/.cvsignore b/src/.cvsignore new file mode 100644 index 000000000..282522db0 --- /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 000000000..62f6d80e5 --- /dev/null +++ b/src/Makefile.am @@ -0,0 +1,4 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +SUBDIRS = lib bin diff --git a/src/bin/.cvsignore b/src/bin/.cvsignore new file mode 100644 index 000000000..a25cf7742 --- /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 000000000..db3e761d6 --- /dev/null +++ b/src/bin/Makefile.am @@ -0,0 +1,17 @@ +AUTOMAKE_OPTIONS = 1.4 foreign + +MAINTAINERCLEANFILES = Makefile.in + +AM_CPPFLAGS = \ +-I$(top_srcdir) \ +-I$(top_srcdir)/src/lib \ +-I$(top_srcdir)/src/bin \ +-DPACKAGE_DATA_DIR=\"$(datadir)/$(PACKAGE)\" \ +@ELEMENTARY_CFLAGS@ + +bin_PROGRAMS = elementary_test + +elementary_test_SOURCES = test.c +elementary_test_LDADD = $(top_builddir)/src/lib/libelementary.la +elementary_test_LDFLAGS = +elementary_test_DEPENDENCIES = $(top_builddir)/src/lib/libelementary.la diff --git a/src/bin/test.c b/src/bin/test.c new file mode 100644 index 000000000..3d85be552 --- /dev/null +++ b/src/bin/test.c @@ -0,0 +1,999 @@ +#include <Elementary.h> + +/* This is a test app (that is also functional) to test the api and serve + * as an example + */ + +static void +on_win_resize(void *data, Elm_Win *win, Elm_Cb_Type type, void *info) +{ + /* window is resized */ + printf("resize to: %ix%i\n", win->w, win->h); +} + +static void +on_win_del_req(void *data, Elm_Win *win, Elm_Cb_Type type, void *info) +{ + /* because autodel is on - after this callback the window will be deleted */ + /* but to be explicit - exit the app when window is closed */ + elm_exit(); +} + +static void +win_bg_simple(void) +{ + Elm_Win *win; + Elm_Bg *bg; + + win = elm_win_new(); /* create a window */ + win->name_set(win, "win_simple"); /* set the window name - used by window + * manager. make it uniqie for windows + * with in this application */ + win->title_set(win, "Simple Window with default Bg"); /* set the title */ + win->autodel = 0; /* dont auto delete the window if someone closes it. + * this means the del+req handler has to delete it. by + * default it is on */ + /* add a callback that is called when the user tries to close the window */ + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + /* add a callback that gets called when the window is resized */ + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + /* our window needs a baground, so ask for one - it will be set with a + * default bg */ + bg = elm_bg_new(win); + bg->show(bg); /* show the bg */ + + win->size_req(win, NULL, 240, 320); /* request that the window is 240x240 + * no min/max size enforced */ + win->show(win); /* show the window */ +} + +static void +win_bg_image(void) +{ + Elm_Win *win; + Elm_Bg *bg; + char buf[PATH_MAX]; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with and image Bg"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + /* this is a test - shows how to have your own custom wallpaper in + * your app - don't use this unless you have a very good reason! there + * is a default and all apps look nicer sharing the default, but if + * you insist... */ + snprintf(buf, sizeof(buf), "%s/images/plant_01.jpg", PACKAGE_DATA_DIR); + bg->file_set(bg, buf, NULL); /* set the bg - the NULL is for special + * files that contain multiple images + * inside 1 file. not normally used but + * might be if you have archive files with + * multiple images in them */ + bg->show(bg); + + win->size_req(win, NULL, 240, 240); + win->show(win); +} + +static void +win_scrollable_label(void) +{ + Elm_Win *win; + Elm_Bg *bg; + Elm_Scroller *scroller; + Elm_Label *label; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with scroller and label inside"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + bg->show(bg); + + scroller = elm_scroller_new(win); + + label = elm_label_new(win); + label->text_set(label, + "Hello world<br>" + "<br>" + "I am a label. I come here to temonstrate how to put<br>" + "text into a label, with newlines, even markup to test<br>" + "things like <b>bold text</b> where markup can be custom<br>" + "and extensible, defined by the theme's textbloxk style<br>" + "for the label.<br>" + "<br>" + "Note that the markup is html-like and things like newline<br>" + "chars and tab chars like stdout text are not valid text<br>" + "markup mechanisms. Use markup tags instead.<br>" + "<br>" + "Now we shall borrow some text from another test program<br>" + "(Expedite) to put some more tests in here<br>" + "<br>" + "<style=outline color=#fff outline_color=#000>Styled</> " + "<style=shadow shadow_color=#fff8>text</> " + "<style=soft_shadow shadow_color=#0002>should</> " + "<style=glow color=#fff glow2_color=#fe87 glow_color=#f214 >go here</> " + "<style=far_shadow shadow_color=#0005>as it is</> " + "<style=outline_shadow color=#fff outline_color=#8228 shadow_color=#005>within</> " + "<style=outline_soft_shadow color=#fff outline_color=#8228 shadow_color=#0002>right tags</> " + "<style=far_soft_shadow color=#fff shadow_color=#0002>to make it align to the</> " + "<underline=on underline_color=#00f>right hand</> " + "<backing=on backing_color=#fff8>side </><backing_color=#ff08>of</><backing_color=#0f08> </>" + "<strikethrough=on strikethrough_color=#f0f8>the textblock</>." + "<br>" + "<underline=double underline_color=#f00 underline2_color=#00f>now we need</> " + "to test some <color=#f00 font_size=8>C</><color=#0f0 font_size=10>O</>" + "<color=#00f font_size=12>L</><color=#fff font_size=14>O</>" + "<color=#ff0 font_size=16>R</><color=#0ff font_size=18> Bla Rai</>" + "<color=#f0f font_size=20> Stuff</>." + "<br>" + "<style=outline color=#fff outline_color=#000>Round about the cauldron go;</> " + "In the poison'd entrails throw.<br>" + "<style=shadow shadow_color=#fff8>Toad, that under cold stone</> " + "Days and nights has thirty-one<br>" + "<style=soft_shadow shadow_color=#0002>Swelter'd venom sleeping got,</> " + "<style=glow color=#fff glow2_color=#fe87 glow_color=#f214 >Boil thou first i' the charmed pot.</><br>" + "Double, double toil and trouble; " + "Fire burn, and cauldron bubble.<br>" + "<style=far_shadow shadow_color=#0005>Fillet of a fenny snake,</> " + "In the cauldron boil and bake;<br>" + "<style=outline_shadow color=#fff outline_color=#8228 shadow_color=#005>Eye of newt and toe of frog,</> " + "<underline=on underline_color=#00f>Wool of bat and tongue of dog,</><br>" + "<backing=on backing_color=#fff8>Adder's fork and blind-worm's sting,</> " + "<underline=double underline_color=#f00 underline2_color=#00f>Lizard's leg and owlet's wing,</><br>" + "<color=#808 font_size=20>For a charm of powerful trouble, " + "Like a hell-broth boil and bubble.<br>" + "Double, double toil and trouble;</> " + "Fire burn and cauldron bubble.<br>" + "Scale of dragon, tooth of wolf, " + "Witches' mummy, maw and gulf<br>" + "Of the ravin'd salt-sea shark, " + "Root of hemlock digg'd i' the dark,<br>" + "Liver of blaspheming Jew, " + "Gall of goat, and slips of yew<br>" + "Silver'd in the moon's eclipse, " + "Nose of Turk and Tartar's lips,<br>" + "Finger of birth-strangled babe " + "Ditch-deliver'd by a drab,<br>" + "Make the gruel thick and slab: " + "Add thereto a tiger's chaudron,<br>" + "For the ingredients of our cauldron. " + "Double, double toil and trouble;<br>" + "Fire burn and cauldron bubble. " + "Cool it with a baboon's blood,<br>" + "Then the charm is firm and good.<br>" + "<br>" + "Heizölrückstoßabdämpfung fløde pingüino kilómetros cœur déçu l'âme<br>" + "plutôt naïve Louÿs rêva crapaüter Íosa Úrmhac Óighe pór Éava Ádhaim<br>" + ); + scroller->child_add(scroller, label); + label->show(label); + scroller->show(scroller); + + win->size_req(win, NULL, 240, 480); + win->show(win); +} + +static void +win_label_determines_min_size(void) +{ + Elm_Win *win; + Elm_Bg *bg; + Elm_Label *label; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with label setting minimum size"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + bg->expand_x = 0; /* allows the window to grow in the y axis because */ + bg->expand_y = 1; /* its only child can expand in y */ + bg->show(bg); + + label = elm_label_new(win); + label->text_set(label, + "Hello world<br>" + "<br>" + "I am a label. I come here to temonstrate how to put<br>" + "text into a label, with newlines, even markup to test<br>" + "things like <b>bold text</b> where markup can be custom<br>" + "and extensible, defined by the theme's textbloxk style<br>" + "for the label.<br>" + "<br>" + "Note that the markup is html-like and things like newline<br>" + "chars and tab chars like stdout text are not valid text<br>" + "markup mechanisms. Use markup tags instead.<br>" + ); + label->show(label); + label->expand_x = 0; /* allows the window to grow in the y axis because */ + label->expand_y = 1; /* its only child can expand in y */ + /* why do i change expand on both bg and label? both are children of the + * window widget and thus both affect the window sizing. if any expands + * in an axis then window expanding is allowed always */ + elm_widget_sizing_update(label); /* make sure that the lable knows about its + * sizing changes like expand above */ + win->show(win); +} + +static void +win_box_vert_of_labels(void) +{ + Elm_Win *win; + Elm_Bg *bg; + Elm_Box *box; + Elm_Label *label; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with box + labels setting minimum size"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + bg->expand_x = 1; + bg->expand_y = 1; + bg->show(bg); + + box = elm_box_new(win); + box->expand_x = 1; + box->expand_y = 1; + + label = elm_label_new(win); + label->text_set(label, "Expand X/Y 0/0, Fill X/Y 0/0, Align: 0.5 0.5"); + box->pack_end(box, label); + label->show(label); + label->align_x = 0.5; + label->align_y = 0.5; + label->expand_x = 0; + label->expand_y = 0; + label->fill_x = 0; + label->fill_y = 0; + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "Expand X/Y 1/1, Fill X/Y 0/0, Align: 0.5 0.5"); + box->pack_end(box, label); + label->show(label); + label->align_x = 0.5; + label->align_y = 0.5; + label->expand_x = 1; + label->expand_y = 1; + label->fill_x = 0; + label->fill_y = 0; + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "Expand X/Y 1/1, Fill X/Y 1/1, Align: 0.5 0.5"); + box->pack_end(box, label); + label->show(label); + label->align_x = 0.5; + label->align_y = 0.5; + label->expand_x = 1; + label->expand_y = 1; + label->fill_x = 1; + label->fill_y = 1; + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "Expand X/Y 0/0, Fill X/Y 1/1, Align: 0.5 0.5"); + box->pack_end(box, label); + label->show(label); + label->align_x = 0.5; + label->align_y = 0.5; + label->expand_x = 0; + label->expand_y = 0; + label->fill_x = 1; + label->fill_y = 1; + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "Expand X/Y 0/0, Fill X/Y 1/1, Align: 0.0 0.5"); + box->pack_end(box, label); + label->show(label); + label->align_x = 0.0; + label->align_y = 0.5; + label->expand_x = 0; + label->expand_y = 0; + label->fill_x = 1; + label->fill_y = 1; + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "Expand X/Y 0/0, Fill X/Y 1/1, Align: 1.0 0.5"); + box->pack_end(box, label); + label->show(label); + label->align_x = 1.0; + label->align_y = 0.5; + label->expand_x = 0; + label->expand_y = 0; + label->fill_x = 1; + label->fill_y = 1; + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "Expand X/Y 0/0, Fill X/Y 1/1, Align: 0.5 0.0"); + box->pack_end(box, label); + label->show(label); + label->align_x = 0.5; + label->align_y = 0.0; + label->expand_x = 0; + label->expand_y = 0; + label->fill_x = 1; + label->fill_y = 1; + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "Expand X/Y 0/0, Fill X/Y 1/1, Align: 0.5 1.0"); + box->pack_end(box, label); + label->show(label); + label->align_x = 0.5; + label->align_y = 1.0; + label->expand_x = 0; + label->expand_y = 0; + label->fill_x = 1; + label->fill_y = 1; + elm_widget_sizing_update(label); + + elm_widget_sizing_update(box); + box->show(box); + + win->show(win); +} + +static void +win_scrollable_box_vert_of_labels(void) +{ + Elm_Win *win; + Elm_Bg *bg; + Elm_Scroller *scroller; + Elm_Box *box; + Elm_Label *label; + int i; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with scroller and box + labels inside"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + bg->expand_x = 1; + bg->expand_y = 1; + bg->show(bg); + + scroller = elm_scroller_new(win); + + box = elm_box_new(win); + box->expand_x = 1; + box->expand_y = 1; + + for (i = 0; i < 40; i++) + { + char buf[200]; + + snprintf(buf, sizeof(buf), "This is a Label in a box, #%i", i); + label = elm_label_new(win); + label->text_set(label, buf); + box->pack_end(box, label); + label->show(label); + label->expand_x = 0; + label->expand_y = 0; + elm_widget_sizing_update(label); + label->show(label); + } + + scroller->child_add(scroller, box); + + elm_widget_sizing_update(box); + box->show(box); + + scroller->show(scroller); + + win->size_req(win, NULL, 240, 240); + win->show(win); +} + +static void +win_table_of_labels(void) +{ + Elm_Win *win; + Elm_Bg *bg; + Elm_Table *table; + Elm_Label *label; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with table + labels setting minimum size"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + bg->expand_x = 1; + bg->expand_y = 1; + bg->show(bg); + + table = elm_table_new(win); + table->expand_x = 1; + table->expand_y = 1; + + label = elm_label_new(win); + label->text_set(label, "X"); + table->pack(table, label, 0, 0, 1, 1); + label->fill_x = 0; + label->fill_y = 0; + label->show(label); + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "Y"); + table->pack(table, label, 1, 0, 1, 1); + label->fill_x = 0; + label->fill_y = 0; + label->show(label); + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "Z"); + table->pack(table, label, 2, 0, 1, 1); + label->fill_x = 0; + label->fill_y = 0; + label->show(label); + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "A"); + table->pack(table, label, 0, 1, 1, 1); + label->fill_x = 0; + label->fill_y = 0; + label->show(label); + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "BB"); + table->pack(table, label, 1, 1, 2, 1); + label->fill_x = 0; + label->fill_y = 0; + label->show(label); + elm_widget_sizing_update(label); + + label = elm_label_new(win); + label->text_set(label, "CCC"); + table->pack(table, label, 0, 2, 3, 1); + label->fill_x = 0; + label->fill_y = 0; + label->show(label); + elm_widget_sizing_update(label); + + elm_widget_sizing_update(table); + table->show(table); + + win->show(win); +} + +static void +on_button_activate(void *data, Elm_Button *bt, Elm_Cb_Type type, void *info) +{ + printf("Button %p activate\n", bt); +} + +static void +win_table_of_buttons(void) +{ + Elm_Win *win; + Elm_Bg *bg; + Elm_Icon *icon; + Elm_Table *table; + Elm_Button *button; + char buf[PATH_MAX]; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with table + buttons setting minimum size"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + bg->expand_x = 1; + bg->expand_y = 1; + bg->show(bg); + + table = elm_table_new(win); + table->expand_x = 1; + table->expand_y = 1; + + button = elm_button_new(win); + button->text_set(button, "Button 1"); + table->pack(table, button, 0, 0, 1, 1); + button->fill_x = 0; + button->fill_y = 0; + button->show(button); + elm_widget_sizing_update(button); + button->cb_add(button, ELM_CB_ACTIVATED, on_button_activate, NULL); + + button = elm_button_new(win); + button->text_set(button, "Button 2"); + table->pack(table, button, 1, 0, 1, 1); + button->fill_x = 0; + button->fill_y = 0; + button->show(button); + elm_widget_sizing_update(button); + button->cb_add(button, ELM_CB_ACTIVATED, on_button_activate, NULL); + + button = elm_button_new(win); + button->text_set(button, "Button 3"); + table->pack(table, button, 2, 0, 1, 1); + button->fill_x = 0; + button->fill_y = 0; + button->show(button); + elm_widget_sizing_update(button); + button->cb_add(button, ELM_CB_ACTIVATED, on_button_activate, NULL); + + button = elm_button_new(win); + button->text_set(button, "Button 4"); + table->pack(table, button, 0, 1, 1, 1); + button->fill_x = 1; + button->fill_y = 0; + button->show(button); + elm_widget_sizing_update(button); + button->cb_add(button, ELM_CB_ACTIVATED, on_button_activate, NULL); + + button = elm_button_new(win); + icon = elm_icon_new(win); + snprintf(buf, sizeof(buf), "%s/images/logo_small.png", PACKAGE_DATA_DIR); + icon->file_set(icon, buf, NULL); + icon->scale_up = 0; + icon->layout_update(icon); + button->child_add(button, icon); + table->pack(table, button, 1, 1, 2, 1); + button->fill_x = 1; + button->fill_y = 1; + button->show(button); + elm_widget_sizing_update(button); + button->cb_add(button, ELM_CB_ACTIVATED, on_button_activate, NULL); + + button = elm_button_new(win); + button->text_set(button, "Button 6"); + icon = elm_icon_new(win); + snprintf(buf, sizeof(buf), "%s/images/logo.png", PACKAGE_DATA_DIR); + icon->file_set(icon, buf, NULL); + button->child_add(button, icon); + table->pack(table, button, 0, 2, 3, 1); + button->fill_x = 1; + button->fill_y = 1; + button->show(button); + elm_widget_sizing_update(button); + button->cb_add(button, ELM_CB_ACTIVATED, on_button_activate, NULL); + + elm_widget_sizing_update(table); + table->show(table); + + win->show(win); +} + +static void +on_toggle_changed(void *data, Elm_Toggle *tg, Elm_Cb_Type type, void *info) +{ + printf("toggle: %i\n", tg->state); +} + +static void +win_box_vert_of_toggles(void) +{ + Elm_Win *win; + Elm_Bg *bg; + Elm_Box *box; + Elm_Toggle *toggle; + Elm_Icon *icon; + char buf[PATH_MAX]; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with box + toggles setting min size"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + bg->expand_x = 0; + bg->expand_y = 0; + bg->show(bg); + + box = elm_box_new(win); + box->expand_x = 0; + box->expand_y = 0; + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Label ON/OFF"); + toggle->state = 1; + toggle->layout_update(toggle); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Icon + Label ON/OFF"); + icon = elm_icon_new(win); + snprintf(buf, sizeof(buf), "%s/images/logo.png", PACKAGE_DATA_DIR); + icon->file_set(icon, buf, NULL); + toggle->child_add(toggle, icon); + toggle->state = 1; + toggle->layout_update(toggle); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, NULL); + icon = elm_icon_new(win); + snprintf(buf, sizeof(buf), "%s/images/logo.png", PACKAGE_DATA_DIR); + icon->file_set(icon, buf, NULL); + toggle->child_add(toggle, icon); + toggle->state = 1; + toggle->layout_update(toggle); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Label Yes/No"); + toggle->states_text_set(toggle, "Yes", "No"); + toggle->state = 1; + toggle->layout_update(toggle); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + elm_widget_sizing_update(box); + box->show(box); + + win->show(win); +} + +static void +win_scrollable_box_vert_of_toggles_and_buttons(void) +{ + Elm_Win *win; + Elm_Bg *bg; + Elm_Box *box; + Elm_Scroller *scroller; + Elm_Toggle *toggle; + Elm_Icon *icon; + Elm_Button *button; + Elm_Label *label; + char buf[PATH_MAX]; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with scroller + box + toggles + buttons"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + bg->expand_x = 1; + bg->expand_y = 1; + bg->show(bg); + + scroller = elm_scroller_new(win); + + box = elm_box_new(win); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Label ON/OFF"); + toggle->state = 1; + toggle->layout_update(toggle); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Icon + Label ON/OFF"); + icon = elm_icon_new(win); + snprintf(buf, sizeof(buf), "%s/images/logo.png", PACKAGE_DATA_DIR); + icon->file_set(icon, buf, NULL); + toggle->child_add(toggle, icon); + toggle->state = 1; + toggle->layout_update(toggle); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, NULL); + icon = elm_icon_new(win); + snprintf(buf, sizeof(buf), "%s/images/logo.png", PACKAGE_DATA_DIR); + icon->file_set(icon, buf, NULL); + toggle->child_add(toggle, icon); + toggle->state = 1; + toggle->layout_update(toggle); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Label Yes/No"); + toggle->states_text_set(toggle, "Yes", "No"); + toggle->state = 1; + toggle->layout_update(toggle); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Toggle "); + toggle->states_text_set(toggle, "Up", "Down"); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Toggle "); + toggle->states_text_set(toggle, "In", "Out"); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Toggle "); + toggle->states_text_set(toggle, "Up", "Down"); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + label = elm_label_new(win); + label->text_set(label, + "Hello world<br>" + "<br>" + "I am a label. I come here to temonstrate how to put<br>" + "text into a label, with newlines, even markup to test<br>" + "things like <b>bold text</b> where markup can be custom<br>" + "and extensible, defined by the theme's textbloxk style<br>" + "for the label.<br>" + "<br>" + "Note that the markup is html-like and things like newline<br>" + "chars and tab chars like stdout text are not valid text<br>" + "markup mechanisms. Use markup tags instead.<br>" + ); + box->pack_end(box, label); + label->expand_y = 0; + label->fill_y = 0; + elm_widget_sizing_update(label); + label->show(label); + + button = elm_button_new(win); + button->text_set(button, "Button 1"); + box->pack_end(box, button); + button->expand_y = 0; + button->fill_y = 0; + button->show(button); + elm_widget_sizing_update(button); + button->cb_add(button, ELM_CB_ACTIVATED, on_button_activate, NULL); + + button = elm_button_new(win); + button->text_set(button, "Button 2"); + box->pack_end(box, button); + button->expand_y = 0; + button->fill_y = 0; + button->show(button); + elm_widget_sizing_update(button); + button->cb_add(button, ELM_CB_ACTIVATED, on_button_activate, NULL); + + button = elm_button_new(win); + button->text_set(button, "Button 3"); + box->pack_end(box, button); + button->expand_y = 0; + button->fill_y = 0; + button->show(button); + elm_widget_sizing_update(button); + button->cb_add(button, ELM_CB_ACTIVATED, on_button_activate, NULL); + + scroller->child_add(scroller, box); + + elm_widget_sizing_update(box); + box->show(box); + + scroller->show(scroller); + + win->size_req(win, NULL, 400, 320); + + win->show(win); +} + +static void +on_clock_changed(void *data, Elm_Clock *cloc, Elm_Cb_Type type, void *info) +{ + printf("clock: %i:%i:%i\n", cloc->hrs, cloc->min, cloc->sec); +} + +static void +win_box_vert_of_clock_and_toggles(void) +{ + Elm_Win *win; + Elm_Bg *bg; + Elm_Box *box; + Elm_Toggle *toggle; + Elm_Clock *cloc; + Elm_Pad *pad; + Elm_Frame *frame; + char buf[PATH_MAX]; + + win = elm_win_new(); + win->name_set(win, "win_bg"); + win->title_set(win, "Simple Window with box + toggles setting min size"); + win->autodel = 0; + win->cb_add(win, ELM_CB_DEL_REQ, on_win_del_req, NULL); + win->cb_add(win, ELM_CB_RESIZE, on_win_resize, NULL); + + bg = elm_bg_new(win); + snprintf(buf, sizeof(buf), "%s/images/sky_04.jpg", PACKAGE_DATA_DIR); + bg->file_set(bg, buf, NULL); + bg->expand_x = 0; + bg->expand_y = 0; + bg->show(bg); + + pad = elm_pad_new(win); + pad->expand_x = 0; + pad->expand_y = 0; + pad->show(pad); + + frame = elm_frame_new(win); + pad->child_add(pad, frame); + frame->text_set(frame, "Time"); + frame->expand_x = 0; + frame->expand_y = 0; + frame->show(frame); +/* + pad = elm_pad_new(win); + frame->child_add(frame, pad); + pad->expand_x = 0; + pad->expand_y = 0; + pad->show(pad); +*/ + box = elm_box_new(win); +// pad->child_add(pad, box); + frame->child_add(frame, box); + box->expand_x = 0; + box->expand_y = 0; + + toggle = elm_toggle_new(win); + toggle->text_set(toggle, "Alarm"); + toggle->states_text_set(toggle, "ON", "OFF"); + toggle->state = 0; + toggle->layout_update(toggle); + toggle->cb_add(toggle, ELM_CB_CHANGED, on_toggle_changed, NULL); + box->pack_end(box, toggle); + toggle->show(toggle); + toggle->expand_y = 0; + toggle->fill_y = 0; + elm_widget_sizing_update(toggle); + + cloc = elm_clock_new(win); + cloc->expand_x = 0; + cloc->fill_x = 0; + cloc->edit = 1; + cloc->hrs = 6; + cloc->min = 54; + cloc->sec = 32; + cloc->time_update(cloc); + cloc->cb_add(cloc, ELM_CB_CHANGED, on_clock_changed, NULL); + box->pack_end(box, cloc); + elm_widget_sizing_update(cloc); + cloc->show(cloc); + + cloc = elm_clock_new(win); + cloc->expand_x = 0; + cloc->fill_x = 0; + box->pack_end(box, cloc); + elm_widget_sizing_update(cloc); + cloc->show(cloc); + + cloc = elm_clock_new(win); + cloc->am_pm = 0; + cloc->seconds = 1; + cloc->time_update(cloc); + cloc->expand_x = 0; + cloc->fill_x = 0; + box->pack_end(box, cloc); + elm_widget_sizing_update(cloc); + cloc->show(cloc); + + cloc = elm_clock_new(win); + cloc->am_pm = 0; + cloc->seconds = 0; + cloc->time_update(cloc); + cloc->expand_x = 0; + cloc->fill_x = 0; + box->pack_end(box, cloc); + elm_widget_sizing_update(cloc); + cloc->show(cloc); + +/* + cloc = elm_clock_new(win); + cloc->am_pm = 1; + cloc->seconds = 0; + cloc->time_update(cloc); + cloc->expand_x = 0; + cloc->fill_x = 0; + box->pack_end(box, cloc); + elm_widget_sizing_update(cloc); + cloc->show(cloc); + */ + + elm_widget_sizing_update(box); + box->show(box); + + win->show(win); +} + +int +main(int argc, char **argv) +{ + /* init Elementary (all Elementary calls begin with elm_ and all data + * types, enums and macros will be Elm_ and ELM_ etc.) */ + elm_init(argc, argv); + + /* setup some windows with test widgets in them */ + win_bg_simple(); + win_bg_image(); + win_scrollable_label(); + win_label_determines_min_size(); + win_box_vert_of_labels(); + win_scrollable_box_vert_of_labels(); + win_table_of_labels(); + win_table_of_buttons(); + win_box_vert_of_toggles(); + win_scrollable_box_vert_of_toggles_and_buttons(); + win_box_vert_of_clock_and_toggles(); + + elm_run(); /* and run the program now and handle all events etc. */ + + elm_shutdown(); /* clean up and shut down */ + return 0; +} diff --git a/src/lib/Elementary.h b/src/lib/Elementary.h new file mode 100644 index 000000000..ae11da749 --- /dev/null +++ b/src/lib/Elementary.h @@ -0,0 +1,553 @@ +/* + * vim:ts=8:sw=3:sts=8:noexpandtab:cino=>5n-3f0^-2{2 + */ +#ifndef ELEMENTARY_H +#define ELEMENTARY_H + +/* What is this? + * + * This is a VERY SIMPLE toolkit - VERY SIMPLE. It is not meant for writing + * extensive applications. Small simple ones with simple needs. It is meant + * to make the programmers work almost brainless. + * + * I'm toying with backing this with etk or ewl - or not. right now I am + * unsure as some of the widgets will be faily complex edje creations. Do + * not consider any choices permanent - but the API should stay unbroken. + * + */ + +#include "elementary_config.h" + +/* Standard headers for standard system calls etc. */ +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> +#include <string.h> +#include <sys/types.h> +#include <sys/stat.h> +#include <sys/time.h> +#include <sys/param.h> +#include <dlfcn.h> +#include <math.h> +#include <fnmatch.h> +#include <limits.h> +#include <ctype.h> +#include <time.h> +#include <dirent.h> +#include <pwd.h> +#include <grp.h> +#include <glob.h> +#include <locale.h> +#include <libintl.h> +#include <errno.h> +#include <signal.h> +#ifdef HAVE_ALLOCA_H +#include <alloca.h> +#endif + +/* EFL headers */ +#include <Evas.h> +#include <Ecore.h> +#include <Ecore_X.h> +#include <Ecore_Evas.h> +#include <Ecore_Job.h> +#include <Ecore_Txt.h> +#include <Ecore_File.h> +#include <Eet.h> +#include <Edje.h> + +/* allow usage from c++ */ +#ifdef __cplusplus +extern "C" { +#endif + +// FIXME: need to be able to enable/disable widgets +// FIXME: need to determine scale from dpi + /* Types here */ + typedef enum _Elm_Obj_Type + { + ELM_OBJ_OBJ, + ELM_OBJ_CB, + ELM_OBJ_WIDGET, + ELM_OBJ_WIN, + ELM_OBJ_BG, + ELM_OBJ_SCROLLER, + ELM_OBJ_LABEL, + ELM_OBJ_BOX, + ELM_OBJ_TABLE, + ELM_OBJ_BUTTON, + ELM_OBJ_ICON, + ELM_OBJ_TOGGLE, + ELM_OBJ_CLOCK, + ELM_OBJ_FRAME, + ELM_OBJ_PAD +// ELM_OBJ_CHECK, // FIXME: do +// ELM_OBJ_RADIO, // FIXME: do +// ELM_OBJ_SEP, // FIXME: do (separator horiz or vert) +// ELM_OBJ_EXPANDER // FIXME: do (like a paned but slides open/closed) +// ELM_OBJ_SPIN, // FIXME: do +// ELM_OBJ_SLIDER, // FIXME: do +// ELM_OBJ_ENTRY, // FIXME: do +// ELM_OBJ_EDITOR, // FIXME: do +// ELM_OBJ_LISTITEM, // FIXME: do +// ELM_OBJ_BUSY, // FIXME: do +// // FIXME: list more widgets to do here like: +// // CONTACT, SELECTOR, FILES, PREVIEW, SIGNALINFO, CALLINFO, +// // CELLEDIT (csv - maybe later xls or some other cell format), +// // COLORSEL, TACHO ... +// +// wrap other basic ecore things: +// ELM_OBJ_TIMER, +// ELM_OBJ_ANIMATOR, +// ELM_OBJ_JOB, + } Elm_Obj_Type; + + typedef enum _Elm_Cb_Type + { + ELM_CB_DEL, + ELM_CB_CHILD_ADD, + ELM_CB_CHILD_DEL, + ELM_CB_UNPARENT, + ELM_CB_PARENT, + ELM_CB_DEL_REQ, + ELM_CB_RESIZE, + ELM_CB_CHANGED, + ELM_CB_ACTIVATED + } Elm_Cb_Type; + + typedef enum _Elm_Win_Type + { + ELM_WIN_BASIC, + ELM_WIN_DIALOG_BASIC + } Elm_Win_Type; + + typedef struct _Elm_Obj_Class Elm_Obj_Class; + typedef struct _Elm_Obj Elm_Obj; + typedef struct _Elm_Cb_Class Elm_Cb_Class; + typedef struct _Elm_Cb Elm_Cb; + typedef struct _Elm_Win_Class Elm_Win_Class; + typedef struct _Elm_Win Elm_Win; + typedef struct _Elm_Widget_Class Elm_Widget_Class; + typedef struct _Elm_Widget Elm_Widget; + typedef struct _Elm_Bg_Class Elm_Bg_Class; + typedef struct _Elm_Bg Elm_Bg; + typedef struct _Elm_Scroller_Class Elm_Scroller_Class; + typedef struct _Elm_Scroller Elm_Scroller; + typedef struct _Elm_Label_Class Elm_Label_Class; + typedef struct _Elm_Label Elm_Label; + typedef struct _Elm_Box_Class Elm_Box_Class; + typedef struct _Elm_Box Elm_Box; + typedef struct _Elm_Table_Class Elm_Table_Class; + typedef struct _Elm_Table Elm_Table; + typedef struct _Elm_Button_Class Elm_Button_Class; + typedef struct _Elm_Button Elm_Button; + typedef struct _Elm_Icon_Class Elm_Icon_Class; + typedef struct _Elm_Icon Elm_Icon; + typedef struct _Elm_Toggle_Class Elm_Toggle_Class; + typedef struct _Elm_Toggle Elm_Toggle; + typedef struct _Elm_Clock_Class Elm_Clock_Class; + typedef struct _Elm_Clock Elm_Clock; + typedef struct _Elm_Frame_Class Elm_Frame_Class; + typedef struct _Elm_Frame Elm_Frame; + typedef struct _Elm_Pad_Class Elm_Pad_Class; + typedef struct _Elm_Pad Elm_Pad; + + typedef void (*Elm_Cb_Func) (void *data, Elm_Obj *obj, Elm_Cb_Type type, void *info); + + /* API calls here */ + +/**************************************************************************/ + /* General calls */ + EAPI void elm_init(int argc, char **argv); + EAPI void elm_shutdown(void); + EAPI void elm_run(void); + EAPI void elm_exit(void); + +/**************************************************************************/ + /* Generic Elm Object */ +#define Elm_Obj_Class_Methods \ + void (*del) (Elm_Obj *obj); \ + void (*ref) (Elm_Obj *obj); \ + void (*unref) (Elm_Obj *obj); \ + Elm_Cb *(*cb_add) (Elm_Obj *obj, Elm_Cb_Type type, Elm_Cb_Func func, void *data); \ + void (*child_add) (Elm_Obj *obj, Elm_Obj *child); \ + void (*unparent) (Elm_Obj *obj); \ + int (*hastype) (Elm_Obj *obj, Elm_Obj_Type type) +#define Elm_Obj_Class_All Elm_Obj_Class_Methods; \ + Elm_Obj_Type type; \ + void *clas; /* the obj class and parent classes */ \ + Elm_Obj *parent; \ + Evas_List *children; \ + Evas_List *cbs; \ + int refs; \ + unsigned char delete_me : 1; \ + unsigned char delete_deferred : 1 + + struct _Elm_Obj_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Obj_Class_Methods; + }; + struct _Elm_Obj + { + Elm_Obj_Class_All; + }; +#define ELM_OBJ(o) ((Elm_Obj *)o) + +/**************************************************************************/ + /* Callback Object */ +#define Elm_Cb_Class_Methods +#define Elm_Cb_Class_All Elm_Obj_Class_All; Elm_Cb_Class_Methods; \ + Elm_Cb_Class_Methods; \ + Elm_Cb_Type cb_type; \ + Elm_Cb_Func func; \ + void *data; + struct _Elm_Cb_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Cb_Class_Methods; + }; + struct _Elm_Cb + { + Elm_Cb_Class_All; + }; + +/**************************************************************************/ + /* Widget Object */ +#define Elm_Widget_Class_Methods \ + void (*geom_set) (Elm_Widget *wid, int x, int y, int w, int h); \ + void (*show) (Elm_Widget *wid); \ + void (*hide) (Elm_Widget *wid); \ + void (*size_alloc) (Elm_Widget *wid, int w, int h); \ + void (*size_req) (Elm_Widget *wid, Elm_Widget *child, int w, int h); \ + void (*above) (Elm_Widget *wid, Elm_Widget *above); \ + void (*below) (Elm_Widget *wid, Elm_Widget *below) + +#define Elm_Widget_Class_All Elm_Obj_Class_All; Elm_Widget_Class_Methods; \ + int x, y, w, h; \ + struct { int w, h; } req; \ + Evas_Object *base; \ + double align_x, align_y; \ + unsigned char expand_x : 1; \ + unsigned char expand_y : 1; \ + unsigned char fill_x : 1; \ + unsigned char fill_y : 1 + + /* Object specific ones */ + // FIXME: should this be a function or widget method call? + EAPI void elm_widget_sizing_update(Elm_Widget *wid); + struct _Elm_Widget_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Widget_Class_Methods; + }; + struct _Elm_Widget + { + Elm_Widget_Class_All; + }; + +#ifdef __cplusplus +} +#endif + +/**************************************************************************/ + /* Window Object */ +#define Elm_Win_Class_Methods \ + void (*name_set) (Elm_Win *win, const char *name); \ + void (*title_set) (Elm_Win *win, const char *title) +// FIXME: +// cover methods & state for: +// type, fullscreen, icon, activate, shaped, alpha, borderless, iconified, +// setting parent window (for dialogs) +#define Elm_Win_Class_All Elm_Widget_Class_All; Elm_Win_Class_Methods; \ + Elm_Win_Type win_type; \ + const char *name; \ + const char *title; \ + unsigned char autodel : 1 + + /* Object specific ones */ + EAPI Elm_Win *elm_win_new(void); + struct _Elm_Win_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Win_Class_Methods; + }; + struct _Elm_Win + { + Elm_Win_Class_All; + + Ecore_Evas *ee; /* private */ + Evas *evas; /* private */ + Ecore_X_Window xwin; /* private */ + Ecore_Job *deferred_resize_job; /* private */ + Ecore_Job *deferred_child_eval_job; /* private */ + unsigned char showme : 1; /* private */ + }; + +/**************************************************************************/ + /* Background Object */ +#define Elm_Bg_Class_Methods \ + void (*file_set) (Elm_Bg *bg, const char *file, const char *group); +#define Elm_Bg_Class_All Elm_Widget_Class_All; Elm_Bg_Class_Methods; \ + const char *file; \ + const char *group + + /* Object specific ones */ + EAPI Elm_Bg *elm_bg_new(Elm_Win *win); + struct _Elm_Bg_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Bg_Class_Methods; + }; + struct _Elm_Bg + { + Elm_Bg_Class_All; + + Evas_Object *custom_bg; + }; + +/**************************************************************************/ + /* Scroller (scrollframe/scrolledview) Object */ +#define Elm_Scroller_Class_Methods \ + void (*file_set) (Elm_Scroller *scroller, const char *file, const char *group); +#define Elm_Scroller_Class_All Elm_Widget_Class_All; Elm_Scroller_Class_Methods; \ + const char *file; \ + const char *group + + /* Object specific ones */ + EAPI Elm_Scroller *elm_scroller_new(Elm_Win *win); + struct _Elm_Scroller_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Scroller_Class_Methods; + }; + struct _Elm_Scroller + { + Elm_Scroller_Class_All; + + Evas_Object *scroller_pan; + }; + +/**************************************************************************/ + /* Label Object */ +#define Elm_Label_Class_Methods \ + void (*text_set) (Elm_Label *lb, const char *text) +#define Elm_Label_Class_All Elm_Widget_Class_All; Elm_Label_Class_Methods; \ + const char *text; \ + int minw, minh + + /* Object specific ones */ + EAPI Elm_Label *elm_label_new(Elm_Win *win); + struct _Elm_Label_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Label_Class_Methods; + }; + struct _Elm_Label + { + Elm_Label_Class_All; + }; + +/**************************************************************************/ + /* Box Object */ +#define Elm_Box_Class_Methods \ + void (*layout_update) (Elm_Box *bx); \ + void (*pack_start) (Elm_Box *bx, Elm_Widget *wid); \ + void (*pack_end) (Elm_Box *bx, Elm_Widget *wid); \ + void (*pack_before) (Elm_Box *bx, Elm_Widget *wid, Elm_Widget *wid_before); \ + void (*pack_after) (Elm_Box *bx, Elm_Widget *wid, Elm_Widget *wid_after); + +#define Elm_Box_Class_All Elm_Widget_Class_All; Elm_Box_Class_Methods; \ + unsigned char horizontal : 1; \ + unsigned char homogenous : 1 + + /* Object specific ones */ + EAPI Elm_Box *elm_box_new(Elm_Win *win); + struct _Elm_Box_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Box_Class_Methods; + }; + struct _Elm_Box + { + Elm_Box_Class_All; + }; + +/**************************************************************************/ + /* Table Object */ +#define Elm_Table_Class_Methods \ + void (*layout_update) (Elm_Table *tb); \ + void (*pack) (Elm_Table *tb, Elm_Widget *wid, int x, int y, int w, int h) +#define Elm_Table_Class_All Elm_Widget_Class_All; Elm_Table_Class_Methods; \ + unsigned char homogenous : 1 + + /* Object specific ones */ + EAPI Elm_Table *elm_table_new(Elm_Win *win); + struct _Elm_Table_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Table_Class_Methods; + }; + struct _Elm_Table + { + Elm_Table_Class_All; + }; + +/**************************************************************************/ + /* Button Object */ +#define Elm_Button_Class_Methods \ + void (*text_set) (Elm_Button *bt, const char *text) +#define Elm_Button_Class_All Elm_Widget_Class_All; Elm_Button_Class_Methods; \ + const char *text; \ + int minw, minh + + /* Object specific ones */ + EAPI Elm_Button *elm_button_new(Elm_Win *win); + struct _Elm_Button_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Button_Class_Methods; + }; + struct _Elm_Button + { + Elm_Button_Class_All; + }; + +/**************************************************************************/ + /* Icon Object */ +#define Elm_Icon_Class_Methods \ + void (*file_set) (Elm_Icon *icon, const char *file, const char *group); \ + void (*layout_update) (Elm_Icon *icon) +#define Elm_Icon_Class_All Elm_Widget_Class_All; Elm_Icon_Class_Methods; \ + unsigned char scale_up : 1; \ + unsigned char scale_down : 1; \ + unsigned char fill_outside : 1; \ + unsigned char smooth : 1; \ + unsigned char no_scale : 1; \ + const char *file; \ + const char *group + + /* Object specific ones */ + EAPI Elm_Icon *elm_icon_new(Elm_Win *win); + struct _Elm_Icon_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Icon_Class_Methods; + }; + struct _Elm_Icon + { + Elm_Icon_Class_All; + }; + +/**************************************************************************/ + /* Toggle Object */ +#define Elm_Toggle_Class_Methods \ + void (*text_set) (Elm_Toggle *tg, const char *text); \ + void (*layout_update) (Elm_Toggle *tg); \ + void (*states_text_set) (Elm_Toggle *tg, const char *ontext, const char *offtext) +#define Elm_Toggle_Class_All Elm_Widget_Class_All; Elm_Toggle_Class_Methods; \ + const char *text; \ + int minw, minh; \ + int state; \ + int *state_ptr + + /* Object specific ones */ + EAPI Elm_Toggle *elm_toggle_new(Elm_Win *win); + struct _Elm_Toggle_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Toggle_Class_Methods; + }; + struct _Elm_Toggle + { + Elm_Toggle_Class_All; + }; + +/**************************************************************************/ + /* Clock Object */ +#define Elm_Clock_Class_Methods \ + void (*time_update) (Elm_Clock *ck) +#define Elm_Clock_Class_All Elm_Widget_Class_All; Elm_Clock_Class_Methods; \ + int hrs, min, sec; \ + int minw, minh; \ + unsigned char seconds : 1; \ + unsigned char am_pm : 1; \ + unsigned char edit : 1 + + /* Object specific ones */ + EAPI Elm_Clock *elm_clock_new(Elm_Win *win); + struct _Elm_Clock_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Clock_Class_Methods; + }; + struct _Elm_Clock + { + Elm_Clock_Class_All; + + Evas_Object *digit[6]; + Evas_Object *ampm; + Ecore_Timer *ticker; + struct { + int hrs, min, sec; + char ampm; + char seconds; + char am_pm; + char edit; + } cur; + }; + +/**************************************************************************/ + /* Frame Object */ +#define Elm_Frame_Class_Methods \ + void (*text_set) (Elm_Frame *fr, const char *text) +#define Elm_Frame_Class_All Elm_Widget_Class_All; Elm_Frame_Class_Methods; \ + const char *text; \ + int minw, minh + + /* Object specific ones */ + EAPI Elm_Frame *elm_frame_new(Elm_Win *win); + struct _Elm_Frame_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Frame_Class_Methods; + }; + struct _Elm_Frame + { + Elm_Frame_Class_All; + }; + +/**************************************************************************/ + /* Pad Object */ +#define Elm_Pad_Class_Methods +#define Elm_Pad_Class_All Elm_Widget_Class_All; Elm_Pad_Class_Methods; \ + int minw, minh + + /* Object specific ones */ + EAPI Elm_Pad *elm_pad_new(Elm_Win *win); + struct _Elm_Pad_Class + { + void *parent; + Elm_Obj_Type type; + Elm_Pad_Class_Methods; + }; + struct _Elm_Pad + { + Elm_Pad_Class_All; + }; + +#endif diff --git a/src/lib/Makefile.am b/src/lib/Makefile.am new file mode 100644 index 000000000..a420573ae --- /dev/null +++ b/src/lib/Makefile.am @@ -0,0 +1,54 @@ +AUTOMAKE_OPTIONS = 1.4 foreign +MAINTAINERCLEANFILES = Makefile.in + +AM_CPPFLAGS = \ +-I. \ +-I$(top_builddir) \ +-I$(top_srcdir) \ +-I$(top_srcdir)/src/lib \ +-DPACKAGE_DATA_DIR=\"$(datadir)/$(PACKAGE)\" \ +@ELEMENTARY_CFLAGS@ + +lib_LTLIBRARIES = libelementary.la + +include_HEADERS = Elementary.h + +libelementary_la_SOURCES = \ +elm_priv.h \ +elm_main.c \ +elm_obj.c \ +elm_callback.c \ +elm_win.c \ +elm_theme.c \ +elm_widget.c \ +elm_bg.c \ +elm_scroller.c \ +elm_label.c \ +elm_box.c \ +elm_table.c \ +elm_button.c \ +elm_icon.c \ +elm_toggle.c \ +elm_clock.c \ +elm_frame.c \ +elm_pad.c \ +\ +els_pan.c \ +els_pan.h \ +els_scroller.c \ +els_scroller.h \ +els_box.c \ +els_box.h \ +els_table.c \ +els_table.h \ +els_icon.c \ +els_icon.h + +libelementary_la_CFLAGS = +libelementary_la_LIBADD = @my_libs@ @ELEMENTARY_LIBS@ +libelementary_la_LDFLAGS = -version-info @version_info@ +libelementary_la_DEPENDENCIES = $(top_builddir)/elementary_config.h + +clean-local: + @rm -rf *.gcno + diff --git a/src/lib/elm_bg.c b/src/lib/elm_bg.c new file mode 100644 index 000000000..0fef5fdd6 --- /dev/null +++ b/src/lib/elm_bg.c @@ -0,0 +1,99 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_bg_file_set(Elm_Bg *bg, const char *file, const char *group); +static void _elm_bg_del(Elm_Bg *bg); + +Elm_Bg_Class _elm_bg_class = +{ + &_elm_widget_class, + ELM_OBJ_BG, + _elm_bg_file_set +}; + +static void +_elm_bg_custom_resize(void *data, Evas *a, Evas_Object *obj, void *event_info) +{ + Elm_Bg *bg = data; + int iw = 0, ih = 0; + Evas_Coord x, y, w, h, ow = 0, oh = 0; + + evas_object_geometry_get(obj, NULL, NULL, &ow, &oh); + evas_object_image_size_get(obj, &iw, &ih); + + if ((iw < 1) || (ih < 1)) return; + w = ow; + h = (ih * w) / iw; + if (h < oh) + { + h = oh; + w = (iw * h) / ih; + } + x = (ow - w) / 2; + y = (oh - h) / 2; + evas_object_image_fill_set(obj, x, y, w, h); +} + +static void +_elm_bg_file_set(Elm_Bg *bg, const char *file, const char *group) +{ + const char *p; + + if (bg->custom_bg) + { + evas_object_del(bg->custom_bg); + bg->custom_bg = NULL; + } + if (!file) return; + if (bg->file) evas_stringshare_del(bg->file); + if (file) bg->file = evas_stringshare_add(file); + else bg->file = NULL; + if (bg->group) evas_stringshare_del(bg->group); + if (group) bg->group = evas_stringshare_add(group); + else bg->group = NULL; + if (((p = strrchr(file, '.'))) && (!strcasecmp(p, ".edj"))) + { + bg->custom_bg = edje_object_add(evas_object_evas_get(bg->base)); + edje_object_file_set(bg->custom_bg, file, group); + } + else + { + bg->custom_bg = evas_object_image_add(evas_object_evas_get(bg->base)); + evas_object_event_callback_add(bg->custom_bg, EVAS_CALLBACK_RESIZE, _elm_bg_custom_resize, bg); + evas_object_image_file_set(bg->custom_bg, file, group); + } + evas_object_repeat_events_set(bg->custom_bg, 1); + edje_object_part_swallow(bg->base, "elm.swallow.background", bg->custom_bg); + evas_object_show(bg->custom_bg); +} + +static void +_elm_bg_del(Elm_Bg *bg) +{ + if (bg->custom_bg) evas_object_del(bg->custom_bg); + if (bg->group) evas_stringshare_del(bg->group); + if (bg->file) evas_stringshare_del(bg->file); + ((Elm_Obj_Class *)(((Elm_Bg_Class *)(bg->clas))->parent))->del(ELM_OBJ(bg)); +} + +EAPI Elm_Bg * +elm_bg_new(Elm_Win *win) +{ + Elm_Bg *bg; + + bg = ELM_NEW(Elm_Bg); + + _elm_widget_init(bg); + bg->clas = &_elm_bg_class; + bg->type = ELM_OBJ_BG; + + bg->del = _elm_bg_del; + + bg->file_set = _elm_bg_file_set; + + bg->base = edje_object_add(win->evas); + _elm_theme_set(bg->base, "bg", "bg"); + _elm_widget_post_init(bg); + win->child_add(win, bg); + return bg; +} diff --git a/src/lib/elm_box.c b/src/lib/elm_box.c new file mode 100644 index 000000000..0a3264880 --- /dev/null +++ b/src/lib/elm_box.c @@ -0,0 +1,131 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_box_layout_update(Elm_Box *bx); +static void _elm_box_pack_start(Elm_Box *bx, Elm_Widget *wid); +static void _elm_box_pack_end(Elm_Box *bx, Elm_Widget *wid); +static void _elm_box_pack_before(Elm_Box *bx, Elm_Widget *wid, Elm_Widget *wid_before); +static void _elm_box_pack_after(Elm_Box *bx, Elm_Widget *wid, Elm_Widget *wid_after); + +Elm_Box_Class _elm_box_class = +{ + &_elm_widget_class, + ELM_OBJ_SCROLLER, + _elm_box_layout_update, + _elm_box_pack_start, + _elm_box_pack_end, + _elm_box_pack_before, + _elm_box_pack_after +}; + +static void +_elm_box_layout_update(Elm_Box *bx) +{ + _els_smart_box_orientation_set(bx->base, bx->horizontal); + _els_smart_box_homogenous_set(bx->base, bx->homogenous); +} + +static void +_elm_box_pack_start(Elm_Box *bx, Elm_Widget *wid) +{ + bx->child_add(bx, wid); + _els_smart_box_pack_start(bx->base, wid->base); +} + +static void +_elm_box_pack_end(Elm_Box *bx, Elm_Widget *wid) +{ + bx->child_add(bx, wid); + _els_smart_box_pack_end(bx->base, wid->base); +} + +static void +_elm_box_pack_before(Elm_Box *bx, Elm_Widget *wid, Elm_Widget *wid_before) +{ + bx->child_add(bx, wid); + _els_smart_box_pack_before(bx->base, wid->base, wid_before->base); +} + +static void +_elm_box_pack_after(Elm_Box *bx, Elm_Widget *wid, Elm_Widget *wid_after) +{ + bx->child_add(bx, wid); + _els_smart_box_pack_after(bx->base, wid->base, wid_after->base); +} + +static void +_elm_box_size_alloc(Elm_Box *bx, int w, int h) +{ + Evas_Coord mw, mh; + + _els_smart_box_min_size_get(bx->base, &mw, &mh); + if (w < mw) w = mw; + if (h < mh) h = mh; + bx->req.w = w; + bx->req.h = h; +} + +static void +_elm_box_size_req(Elm_Box *bx, Elm_Widget *child, int w, int h) +{ + Evas_Coord mw, mh; + + if (child) + { + Evas_Coord maxx, maxy; + + child->size_alloc(child, 0, 0); + maxx = child->req.w; + maxy = child->req.h; + if (child->expand_x) maxx = 32767; + if (child->expand_y) maxy = 32767; + _els_smart_box_pack_options_set(child->base, + child->fill_x, child->fill_y, + child->expand_x, child->expand_y, + child->align_x, child->align_y, + child->req.w, child->req.h, + maxx, maxy); + } + else + { + // FIXME: handle. + } + _els_smart_box_min_size_get(bx->base, &mw, &mh); + ((Elm_Widget *)(bx->parent))->size_req(bx->parent, bx, mw, mh); + bx->geom_set(bx, bx->x, bx->y, mw, mh); +} + +static void +_elm_on_child_del(void *data, Elm_Box *bx, Elm_Cb_Type type, Elm_Obj *obj) +{ + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + _els_smart_box_unpack(((Elm_Widget *)(obj))->base); +} + +EAPI Elm_Box * +elm_box_new(Elm_Win *win) +{ + Elm_Box *bx; + + bx = ELM_NEW(Elm_Box); + _elm_widget_init(bx); + + bx->clas = &_elm_box_class; + bx->type = ELM_OBJ_BOX; + + bx->layout_update = _elm_box_layout_update; + bx->pack_start = _elm_box_pack_start; + bx->pack_end = _elm_box_pack_end; + bx->pack_before = _elm_box_pack_before; + bx->pack_after = _elm_box_pack_after; + + bx->size_alloc = _elm_box_size_alloc; + bx->size_req = _elm_box_size_req; + + bx->base = _els_smart_box_add(win->evas); + + bx->cb_add(bx, ELM_CB_CHILD_DEL, _elm_on_child_del, NULL); + _elm_widget_post_init(bx); + win->child_add(win, bx); + return bx; +} diff --git a/src/lib/elm_button.c b/src/lib/elm_button.c new file mode 100644 index 000000000..a63f5649f --- /dev/null +++ b/src/lib/elm_button.c @@ -0,0 +1,170 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_button_text_set(Elm_Button *bt, const char *text); + +Elm_Button_Class _elm_button_class = +{ + &_elm_widget_class, + ELM_OBJ_BUTTON, + _elm_button_text_set +}; + +static void +_elm_button_text_set(Elm_Button *bt, const char *text) +{ + Evas_Coord mw, mh; + + if (text) + { + edje_object_signal_emit(bt->base, "elm,state,text,visible", "elm"); + edje_object_message_signal_process(bt->base); + } + else + { + edje_object_signal_emit(bt->base, "elm,state,text,hidden", "elm"); + edje_object_message_signal_process(bt->base); + } + edje_object_part_text_set(bt->base, "elm.text", text); + edje_object_size_min_calc(bt->base, &mw, &mh); + if ((bt->minw != mw) || (bt->minh != mh)) + { + bt->minw = mw; + bt->minh = mh; + ((Elm_Widget *)(bt->parent))->size_req(bt->parent, bt, bt->minw, bt->minh); + bt->geom_set(bt, bt->x, bt->y, bt->minw, bt->minh); + } +} + +static void +_elm_button_size_alloc(Elm_Button *bt, int w, int h) +{ + if (w < bt->minw) w = bt->minw; + if (h < bt->minh) h = bt->minh; + bt->req.w = w; + bt->req.h = h; +} + +static void +_elm_button_size_req(Elm_Button *bt, Elm_Widget *child, int w, int h) +{ + Evas_Coord mw, mh; + + if (child) + { + Evas_Coord maxx, maxy; + + child->size_alloc(child, 0, 0); + maxx = child->req.w; + maxy = child->req.h; + if (child->expand_x) maxx = 32767; + if (child->expand_y) maxy = 32767; + edje_extern_object_min_size_set(child->base, + child->req.w, + child->req.h); + edje_object_part_swallow(bt->base , "elm.swallow.contents", + child->base); + edje_object_size_min_calc(bt->base, &mw, &mh); + if ((bt->minw != mw) || (bt->minh != mh)) + { + bt->minw = mw; + bt->minh = mh; + ((Elm_Widget *)(bt->parent))->size_req(bt->parent, bt, mw, mh); + bt->geom_set(bt, bt->x, bt->y, mw, mh); + } + } + else + { + // FIXME: handle + } +} + +static void +_elm_on_child_add(void *data, Elm_Button *bt, Elm_Cb_Type type, Elm_Obj *obj) +{ + Evas_Coord mw, mh; + + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + edje_object_signal_emit(bt->base, "elm,state,icon,visible", "elm"); + edje_object_message_signal_process(bt->base); + ((Elm_Widget *)(obj))->size_alloc(obj, 0, 0); + ((Elm_Widget *)(obj))->geom_set(obj, + ((Elm_Widget *)(obj))->x, + ((Elm_Widget *)(obj))->y, + ((Elm_Widget *)(obj))->req.w, + ((Elm_Widget *)(obj))->req.h); + edje_extern_object_min_size_set(((Elm_Widget *)(obj))->base, + ((Elm_Widget *)(obj))->req.w, + ((Elm_Widget *)(obj))->req.h); + edje_object_part_swallow(bt->base , "elm.swallow.contents", + ((Elm_Widget *)(obj))->base); + edje_object_size_min_calc(bt->base, &mw, &mh); + if ((bt->minw != mw) || (bt->minh != mh)) + { + bt->minw = mw; + bt->minh = mh; + ((Elm_Widget *)(bt->parent))->size_req(bt->parent, bt, mw, mh); + bt->geom_set(bt, bt->x, bt->y, mw, mh); + } +} + +static void +_elm_on_child_del(void *data, Elm_Button *bt, Elm_Cb_Type type, Elm_Obj *obj) +{ + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + // FIXME: allow for removal of child - size down + edje_object_signal_emit(bt->base, "elm,state,icon,hidden", "elm"); + edje_object_message_signal_process(bt->base); +} + +static void +_elm_button_activate(Elm_Button *bt) +{ + _elm_obj_nest_push(); + _elm_cb_call(ELM_OBJ(bt), ELM_CB_ACTIVATED, NULL); + _elm_obj_nest_pop(); +} + +static void +_elm_signal_clicked(void *data, Evas_Object *obj, const char *emission, const char *source) +{ + Elm_Button *bt = data; + + _elm_button_activate(bt); +} + +static void +_elm_button_del(Elm_Button *bt) +{ + if (bt->text) evas_stringshare_del(bt->text); + ((Elm_Obj_Class *)(((Elm_Button_Class *)(bt->clas))->parent))->del(ELM_OBJ(bt)); +} + +EAPI Elm_Button * +elm_button_new(Elm_Win *win) +{ + Elm_Button *bt; + + bt = ELM_NEW(Elm_Button); + + _elm_widget_init(bt); + bt->clas = &_elm_button_class; + bt->type = ELM_OBJ_BUTTON; + + bt->del = _elm_button_del; + + bt->size_alloc = _elm_button_size_alloc; + bt->size_req = _elm_button_size_req; + + bt->text_set = _elm_button_text_set; + + bt->base = edje_object_add(win->evas); + _elm_theme_set(bt->base, "button", "button"); + edje_object_signal_callback_add(bt->base, "elm,action,click", "", + _elm_signal_clicked, bt); + bt->cb_add(bt, ELM_CB_CHILD_ADD, _elm_on_child_add, NULL); + bt->cb_add(bt, ELM_CB_CHILD_DEL, _elm_on_child_del, NULL); + _elm_widget_post_init(bt); + win->child_add(win, bt); + return bt; +} diff --git a/src/lib/elm_callback.c b/src/lib/elm_callback.c new file mode 100644 index 000000000..fb0137f12 --- /dev/null +++ b/src/lib/elm_callback.c @@ -0,0 +1,58 @@ +#include <Elementary.h> +#include "elm_priv.h" + +Elm_Cb_Class _elm_cb_class = +{ + &_elm_obj_class, + ELM_OBJ_CB +}; + + + +static void +_elm_cb_del(Elm_Cb *cb) +{ + if (_elm_obj_del_defer(ELM_OBJ(cb))) return; + if (cb->parent) /* callbacks are special children */ + { + cb->parent->cbs = evas_list_remove(cb->parent->cbs, cb); + cb->parent = NULL; + } + ((Elm_Obj_Class *)(((Elm_Cb_Class *)(cb->clas))->parent))->del(ELM_OBJ(cb)); +} + +Elm_Cb * +_elm_cb_new(void) +{ + Elm_Cb *cb; + + cb = ELM_NEW(Elm_Cb); + _elm_obj_init(ELM_OBJ(cb)); + cb->clas = &_elm_cb_class; + cb->type = ELM_OBJ_CB; + + cb->del = _elm_cb_del; + + return cb; +} + +void +_elm_cb_call(Elm_Obj *obj, Elm_Cb_Type type, void *info) +{ + Evas_List *l; + + _elm_obj_nest_push(); + for (l = obj->cbs; l; l = l->next) + { + Elm_Cb *cb; + + cb = l->data; + if (cb->delete_me) continue; + if (cb->cb_type == type) + { + if (cb->func) cb->func(cb->data, obj, type, info); + if (cb->cbs) _elm_cb_call(cb, type, info); + } + } + _elm_obj_nest_pop(); +} diff --git a/src/lib/elm_clock.c b/src/lib/elm_clock.c new file mode 100644 index 000000000..af968316b --- /dev/null +++ b/src/lib/elm_clock.c @@ -0,0 +1,393 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_clock_time_update(Elm_Clock *ck); + +Elm_Clock_Class _elm_clock_class = +{ + &_elm_widget_class, + ELM_OBJ_CLOCK, + _elm_clock_time_update +}; + + +static void +_elm_clock_val_up(void *data, Evas_Object *obj, const char *emission, const char *source) +{ + Elm_Clock *ck = data; + + if (!ck->edit) return; + if (obj == ck->digit[0]) + { + ck->hrs = ck->hrs + 10; + if (ck->hrs >= 24) ck->hrs -= 24; + } + if (obj == ck->digit[1]) + { + ck->hrs = ck->hrs + 1; + if (ck->hrs >= 24) ck->hrs -= 24; + } + if (obj == ck->digit[2]) + { + ck->min = ck->min + 10; + if (ck->min >= 60) ck->min -= 60; + } + if (obj == ck->digit[3]) + { + ck->min = ck->min + 1; + if (ck->min >= 60) ck->min -= 60; + } + if (obj == ck->digit[4]) + { + ck->sec = ck->sec + 10; + if (ck->sec >= 60) ck->sec -= 60; + } + if (obj == ck->digit[5]) + { + ck->sec = ck->sec + 1; + if (ck->sec >= 60) ck->sec -= 60; + } + if (obj == ck->ampm) + { + ck->hrs = ck->hrs + 12; + if (ck->hrs > 23) ck->hrs -= 24; + } + ck->time_update(ck); + _elm_obj_nest_push(); + _elm_cb_call(ELM_OBJ(ck), ELM_CB_CHANGED, NULL); + _elm_obj_nest_pop(); +} + +static void +_elm_clock_val_down(void *data, Evas_Object *obj, const char *emission, const char *source) +{ + Elm_Clock *ck = data; + if (!ck->edit) return; + if (obj == ck->digit[0]) + { + ck->hrs = ck->hrs - 10; + if (ck->hrs < 0) ck->hrs += 24; + } + if (obj == ck->digit[1]) + { + ck->hrs = ck->hrs - 1; + if (ck->hrs < 0) ck->hrs += 24; + } + if (obj == ck->digit[2]) + { + ck->min = ck->min - 10; + if (ck->min < 0) ck->min += 60; + } + if (obj == ck->digit[3]) + { + ck->min = ck->min - 1; + if (ck->min < 0) ck->min += 60; + } + if (obj == ck->digit[4]) + { + ck->sec = ck->sec - 10; + if (ck->sec < 0) ck->sec += 60; + } + if (obj == ck->digit[5]) + { + ck->sec = ck->sec - 1; + if (ck->sec < 0) ck->sec += 60; + } + if (obj == ck->ampm) + { + ck->hrs = ck->hrs - 12; + if (ck->hrs < 0) ck->hrs += 24; + } + ck->time_update(ck); + _elm_obj_nest_push(); + _elm_cb_call(ELM_OBJ(ck), ELM_CB_CHANGED, NULL); + _elm_obj_nest_pop(); +} + +static void +_elm_clock_time_update(Elm_Clock *ck) +{ + Edje_Message_Int msg; + int ampm = 0; + + if ((ck->cur.seconds != ck->seconds) || (ck->cur.am_pm != ck->am_pm) || + (ck->cur.edit != ck->edit)) + { + int i; + Evas_Coord mw, mh; + + for (i = 0; i < 6; i++) + { + if (ck->digit[i]) + { + evas_object_del(ck->digit[i]); + ck->digit[i] = NULL; + } + } + if (ck->ampm) + { + evas_object_del(ck->ampm); + ck->ampm = NULL; + } + + if ((ck->seconds) && (ck->am_pm)) + _elm_theme_set(ck->base, "clock", "clock/all"); + else if (ck->seconds) + _elm_theme_set(ck->base, "clock", "clock/seconds"); + else if (ck->am_pm) + _elm_theme_set(ck->base, "clock", "clock/am_pm"); + else + _elm_theme_set(ck->base, "clock", "clock"); + + for (i = 0; i < 6; i++) + { + char buf[16]; + + if ((!ck->seconds) && (i >= 4)) break; + ck->digit[i] = edje_object_add(evas_object_evas_get(ck->base)); + _elm_theme_set(ck->digit[i], "clock", "flipdigit"); + if (ck->edit) + edje_object_signal_emit(ck->digit[i], "elm,state,edit,on", "elm"); + edje_object_signal_callback_add(ck->digit[i], "elm,action,up", "", + _elm_clock_val_up, ck); + edje_object_signal_callback_add(ck->digit[i], "elm,action,down", "", + _elm_clock_val_down, ck); + edje_object_size_min_calc(ck->digit[i], &mw, &mh); + edje_extern_object_min_size_set(ck->digit[i], mw, mh); + snprintf(buf, sizeof(buf), "d%i", i); + edje_object_part_swallow(ck->base , buf, ck->digit[i]); + evas_object_show(ck->digit[i]); + } + if (ck->am_pm) + { + ck->ampm = edje_object_add(evas_object_evas_get(ck->base)); + _elm_theme_set(ck->ampm, "clock", "flipampm"); + if (ck->edit) + edje_object_signal_emit(ck->ampm, "elm,state,edit,on", "elm"); + edje_object_signal_callback_add(ck->ampm, "elm,action,up", "", + _elm_clock_val_up, ck); + edje_object_signal_callback_add(ck->ampm, "elm,action,down", "", + _elm_clock_val_down, ck); + edje_object_size_min_calc(ck->ampm, &mw, &mh); + edje_extern_object_min_size_set(ck->ampm, mw, mh); + edje_object_part_swallow(ck->base , "ampm", ck->ampm); + evas_object_show(ck->ampm); + } + + edje_object_size_min_calc(ck->base, &mw, &mh); + ck->minw = mw; + ck->minh = mh; + + ck->cur.hrs = 0; + ck->cur.min = 0; + ck->cur.sec = 0; + ck->cur.ampm = -1; + ck->cur.seconds = ck->seconds; + ck->cur.am_pm = ck->am_pm; + ck->cur.edit = ck->edit; + } + if (ck->hrs != ck->cur.hrs) + { + int hrs; + int d1, d2, dc1, dc2; + + hrs = ck->hrs; + if (ck->am_pm) + { + if (hrs >= 12) + { + if (hrs > 12) hrs -= 12; + ampm = 1; + } + else if (hrs == 0) hrs = 12; + } + d1 = hrs / 10; + d2 = hrs % 10; + dc1 = ck->cur.hrs / 10; + dc2 = ck->cur.hrs % 10; + if (d1 != dc1) + { + msg.val = d1; + edje_object_message_send(ck->digit[0], EDJE_MESSAGE_INT, 1, &msg); + } + if (d2 != dc2) + { + msg.val = d2; + edje_object_message_send(ck->digit[1], EDJE_MESSAGE_INT, 1, &msg); + } + ck->cur.hrs = hrs; + } + if (ck->min != ck->cur.min) + { + int d1, d2, dc1, dc2; + + d1 = ck->min / 10; + d2 = ck->min % 10; + dc1 = ck->cur.min / 10; + dc2 = ck->cur.min % 10; + if (d1 != dc1) + { + msg.val = d1; + edje_object_message_send(ck->digit[2], EDJE_MESSAGE_INT, 1, &msg); + } + if (d2 != dc2) + { + msg.val = d2; + edje_object_message_send(ck->digit[3], EDJE_MESSAGE_INT, 1, &msg); + } + ck->cur.min = ck->min; + } + if (ck->seconds) + { + if (ck->sec != ck->cur.sec) + { + int d1, d2, dc1, dc2; + + d1 = ck->sec / 10; + d2 = ck->sec % 10; + dc1 = ck->cur.sec / 10; + dc2 = ck->cur.sec % 10; + if (d1 != dc1) + { + msg.val = d1; + edje_object_message_send(ck->digit[4], EDJE_MESSAGE_INT, 1, &msg); + } + if (d2 != dc2) + { + msg.val = d2; + edje_object_message_send(ck->digit[5], EDJE_MESSAGE_INT, 1, &msg); + } + ck->cur.sec = ck->sec; + } + } + else + ck->cur.sec = -1; + + if (ck->am_pm) + { + if (ck->hrs >= 12) ampm = 1; + if (ampm != ck->cur.ampm) + { + int d1, d2, dc1, dc2; + + if (ck->cur.ampm != ampm) + { + msg.val = ampm; + edje_object_message_send(ck->ampm, EDJE_MESSAGE_INT, 1, &msg); + } + ck->cur.ampm = ampm; + } + } + else + ck->cur.ampm = -1; +} + +static void +_elm_clock_size_alloc(Elm_Clock *ck, int w, int h) +{ + Evas_Coord mw, mh; + + if (w < ck->minw) w = ck->minw; + if (h < ck->minh) h = ck->minh; + ck->req.w = w; + ck->req.h = h; +} + +static void +_elm_clock_size_req(Elm_Clock *ck, Elm_Widget *child, int w, int h) +{ + if (child) + { + } + else + { + // FIXME: handle + } +} + +static void +_elm_clock_activate(Elm_Clock *ck) +{ + _elm_obj_nest_push(); + _elm_cb_call(ELM_OBJ(ck), ELM_CB_ACTIVATED, NULL); + _elm_obj_nest_pop(); +} + +static void +_elm_clock_del(Elm_Clock *ck) +{ + int i; + + for (i = 0; i < 6; i++) + { + if (ck->digit[i]) evas_object_del(ck->digit[i]); + } + if (ck->ampm) evas_object_del(ck->ampm); + if (ck->ticker) ecore_timer_del(ck->ticker); + ((Elm_Obj_Class *)(((Elm_Clock_Class *)(ck->clas))->parent))->del(ELM_OBJ(ck)); +} + +static int +_elm_clock_ticker(Elm_Clock *ck) +{ + double t; + struct timeval timev; + struct tm *tm; + time_t tt; + + gettimeofday(&timev, NULL); + t = ((double)(1000000 - timev.tv_usec)) / 1000000.0; + ck->ticker = ecore_timer_add(t, _elm_clock_ticker, ck); + if (!ck->edit) + { + tt = (time_t)(timev.tv_sec); + tzset(); + tm = localtime(&tt); + if (tm) + { + ck->hrs = tm->tm_hour; + ck->min = tm->tm_min; + ck->sec = tm->tm_sec; + ck->time_update(ck); + } + } + return 0; +} + +EAPI Elm_Clock * +elm_clock_new(Elm_Win *win) +{ + Elm_Clock *ck; + + ck = ELM_NEW(Elm_Clock); + + _elm_widget_init(ck); + ck->clas = &_elm_clock_class; + ck->type = ELM_OBJ_CLOCK; + + ck->del = _elm_clock_del; + + ck->size_alloc = _elm_clock_size_alloc; + ck->size_req = _elm_clock_size_req; + + ck->time_update = _elm_clock_time_update; + + ck->seconds = 1; + ck->am_pm = 1; + + ck->cur.hrs = 0; + ck->cur.min = 0; + ck->cur.sec = 0; + ck->cur.ampm = -1; + ck->cur.seconds = -1; + ck->cur.am_pm = -1; + ck->cur.edit = -1; + + ck->base = edje_object_add(win->evas); + + _elm_clock_ticker(ck); + + _elm_widget_post_init(ck); + win->child_add(win, ck); + return ck; +} diff --git a/src/lib/elm_frame.c b/src/lib/elm_frame.c new file mode 100644 index 000000000..458573d36 --- /dev/null +++ b/src/lib/elm_frame.c @@ -0,0 +1,138 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_frame_text_set(Elm_Frame *fr, const char *text); + +Elm_Frame_Class _elm_frame_class = +{ + &_elm_widget_class, + ELM_OBJ_FRAME, + _elm_frame_text_set +}; + +static void +_elm_frame_text_set(Elm_Frame *fr, const char *text) +{ + Evas_Coord mw, mh; + + edje_object_part_text_set(fr->base, "elm.text", text); + edje_object_size_min_calc(fr->base, &mw, &mh); + if ((fr->minw != mw) || (fr->minh != mh)) + { + fr->minw = mw; + fr->minh = mh; + ((Elm_Widget *)(fr->parent))->size_req(fr->parent, fr, fr->minw, fr->minh); + fr->geom_set(fr, fr->x, fr->y, fr->minw, fr->minh); + } +} + +static void +_elm_frame_size_alloc(Elm_Frame *fr, int w, int h) +{ + if (w < fr->minw) w = fr->minw; + if (h < fr->minh) h = fr->minh; + fr->req.w = w; + fr->req.h = h; +} + +static void +_elm_frame_size_req(Elm_Frame *fr, Elm_Widget *child, int w, int h) +{ + Evas_Coord mw, mh; + + if (child) + { + Evas_Coord maxx, maxy; + + child->size_alloc(child, 0, 0); + maxx = child->req.w; + maxy = child->req.h; + if (child->expand_x) maxx = 32767; + if (child->expand_y) maxy = 32767; + edje_extern_object_min_size_set(child->base, + child->req.w, + child->req.h); + edje_object_part_swallow(fr->base , "elm.swallow.content", + child->base); + edje_object_size_min_calc(fr->base, &mw, &mh); + if ((fr->minw != mw) || (fr->minh != mh)) + { + fr->minw = mw; + fr->minh = mh; + ((Elm_Widget *)(fr->parent))->size_req(fr->parent, fr, mw, mh); + fr->geom_set(fr, fr->x, fr->y, mw, mh); + } + } + else + { + // FIXME: handle + } +} + +static void +_elm_on_child_add(void *data, Elm_Frame *fr, Elm_Cb_Type type, Elm_Obj *obj) +{ + Evas_Coord mw, mh; + + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + ((Elm_Widget *)(obj))->size_alloc(obj, 0, 0); + ((Elm_Widget *)(obj))->geom_set(obj, + ((Elm_Widget *)(obj))->x, + ((Elm_Widget *)(obj))->y, + ((Elm_Widget *)(obj))->req.w, + ((Elm_Widget *)(obj))->req.h); + edje_extern_object_min_size_set(((Elm_Widget *)(obj))->base, + ((Elm_Widget *)(obj))->req.w, + ((Elm_Widget *)(obj))->req.h); + edje_object_part_swallow(fr->base , "elm.swallow.content", + ((Elm_Widget *)(obj))->base); + edje_object_size_min_calc(fr->base, &mw, &mh); + if ((fr->minw != mw) || (fr->minh != mh)) + { + fr->minw = mw; + fr->minh = mh; + ((Elm_Widget *)(fr->parent))->size_req(fr->parent, fr, mw, mh); + fr->geom_set(fr, fr->x, fr->y, mw, mh); + } +} + +static void +_elm_on_child_del(void *data, Elm_Frame *fr, Elm_Cb_Type type, Elm_Obj *obj) +{ + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + // FIXME: allow for removal of child - size down +} + +static void +_elm_frame_del(Elm_Frame *fr) +{ + if (fr->text) evas_stringshare_del(fr->text); + ((Elm_Obj_Class *)(((Elm_Frame_Class *)(fr->clas))->parent))->del(ELM_OBJ(fr)); +} + +EAPI Elm_Frame * +elm_frame_new(Elm_Win *win) +{ + Elm_Frame *fr; + + fr = ELM_NEW(Elm_Frame); + + _elm_widget_init(fr); + fr->clas = &_elm_frame_class; + fr->type = ELM_OBJ_FRAME; + + fr->del = _elm_frame_del; + + fr->size_alloc = _elm_frame_size_alloc; + fr->size_req = _elm_frame_size_req; + + fr->text_set = _elm_frame_text_set; + + fr->base = edje_object_add(win->evas); + _elm_theme_set(fr->base, "frame", "frame"); + fr->cb_add(fr, ELM_CB_CHILD_ADD, _elm_on_child_add, NULL); + fr->cb_add(fr, ELM_CB_CHILD_DEL, _elm_on_child_del, NULL); + _elm_widget_post_init(fr); + win->child_add(win, fr); + return fr; +} diff --git a/src/lib/elm_icon.c b/src/lib/elm_icon.c new file mode 100644 index 000000000..37c5ea11e --- /dev/null +++ b/src/lib/elm_icon.c @@ -0,0 +1,103 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_icon_file_set(Elm_Icon *icon, const char *file, const char *group); +static void _elm_icon_layout_update(Elm_Icon *icon); + +Elm_Icon_Class _elm_icon_class = +{ + &_elm_widget_class, + ELM_OBJ_ICON, + _elm_icon_file_set, + _elm_icon_layout_update +}; + +static void +_elm_icon_file_set(Elm_Icon *icon, const char *file, const char *group) +{ + const char *p; + + if (!file) return; + if (icon->file) evas_stringshare_del(icon->file); + if (file) icon->file = evas_stringshare_add(file); + else icon->file = NULL; + if (icon->group) evas_stringshare_del(icon->group); + if (group) icon->group = evas_stringshare_add(group); + else icon->group = NULL; + if (((p = strrchr(file, '.'))) && (!strcasecmp(p, ".edj"))) + _els_smart_icon_file_edje_set(icon->base, file, group); + else + _els_smart_icon_file_key_set(icon->base, file, group); + icon->layout_update(icon); +} + +static void +_elm_icon_layout_update(Elm_Icon *icon) +{ + _els_smart_icon_scale_up_set(icon->base, icon->scale_up); + _els_smart_icon_scale_down_set(icon->base, icon->scale_down); + _els_smart_icon_smooth_scale_set(icon->base, icon->smooth); + _els_smart_icon_fill_inside_set(icon->base, !(icon->fill_outside)); + if (icon->no_scale) _els_smart_icon_scale_set(icon->base, 1.0); + else _els_smart_icon_scale_set(icon->base, _elm_config->scale); + if ((!icon->scale_down) || (!icon->scale_up)) + ((Elm_Widget *)(icon->parent))->size_req(icon->parent, icon, 0, 0); +} + +static void +_elm_icon_size_alloc(Elm_Icon *icon, int w, int h) +{ + int tw, th; + + _els_smart_icon_size_get(icon->base, &tw, &th); + if (!icon->scale_down) + { + if (w < tw) w = tw; + if (h < th) h = th; + } + if (!icon->scale_up) + { + if (w > tw) w = tw; + if (h > th) h = th; + } + icon->req.w = w; + icon->req.h = h; +} + +static void +_elm_icon_del(Elm_Icon *icon) +{ + if (icon->group) evas_stringshare_del(icon->group); + if (icon->file) evas_stringshare_del(icon->file); + ((Elm_Obj_Class *)(((Elm_Icon_Class *)(icon->clas))->parent))->del(ELM_OBJ(icon)); +} + +EAPI Elm_Icon * +elm_icon_new(Elm_Win *win) +{ + Elm_Icon *icon; + + icon = ELM_NEW(Elm_Icon); + + _elm_widget_init(icon); + icon->clas = &_elm_icon_class; + icon->type = ELM_OBJ_ICON; + + icon->del = _elm_icon_del; + + icon->size_alloc = _elm_icon_size_alloc; + + icon->file_set = _elm_icon_file_set; + icon->layout_update = _elm_icon_layout_update; + + icon->smooth = 1; + icon->scale_up = 1; + icon->scale_down = 1; + + icon->base = _els_smart_icon_add(win->evas); + evas_object_repeat_events_set(icon->base, 1); + + _elm_widget_post_init(icon); + win->child_add(win, icon); + return icon; +} diff --git a/src/lib/elm_label.c b/src/lib/elm_label.c new file mode 100644 index 000000000..67bd64134 --- /dev/null +++ b/src/lib/elm_label.c @@ -0,0 +1,68 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_label_text_set(Elm_Label *lb, const char *text); + +Elm_Label_Class _elm_label_class = +{ + &_elm_widget_class, + ELM_OBJ_LABEL, + _elm_label_text_set +}; + +static void +_elm_label_text_set(Elm_Label *lb, const char *text) +{ + Evas_Coord mw, mh; + + if (lb->text) evas_stringshare_del(lb->text); + if (text) lb->text = evas_stringshare_add(text); + else lb->text = NULL; + edje_object_part_text_set(lb->base, "elm.text", text); + edje_object_size_min_calc(lb->base, &mw, &mh); + if ((lb->minw != mw) || (lb->minh != mh)) + { + lb->minw = mw; + lb->minh = mh; + ((Elm_Widget *)(lb->parent))->size_req(lb->parent, lb, lb->minw, lb->minh); + lb->geom_set(lb, lb->x, lb->y, lb->minw, lb->minh); + } +} + +static void +_elm_label_size_alloc(Elm_Label *lb, int w, int h) +{ + lb->req.w = lb->minw; + lb->req.h = lb->minh; +} + +static void +_elm_label_del(Elm_Label *lb) +{ + if (lb->text) evas_stringshare_del(lb->text); + ((Elm_Obj_Class *)(((Elm_Label_Class *)(lb->clas))->parent))->del(ELM_OBJ(lb)); +} + +EAPI Elm_Label * +elm_label_new(Elm_Win *win) +{ + Elm_Label *lb; + + lb = ELM_NEW(Elm_Label); + + _elm_widget_init(lb); + lb->clas = &_elm_label_class; + lb->type = ELM_OBJ_LABEL; + + lb->del = _elm_label_del; + + lb->size_alloc = _elm_label_size_alloc; + + lb->text_set = _elm_label_text_set; + + lb->base = edje_object_add(win->evas); + _elm_theme_set(lb->base, "label", "label"); + _elm_widget_post_init(lb); + win->child_add(win, lb); + return lb; +} diff --git a/src/lib/elm_main.c b/src/lib/elm_main.c new file mode 100644 index 000000000..f919f2ad4 --- /dev/null +++ b/src/lib/elm_main.c @@ -0,0 +1,79 @@ +#include <Elementary.h> +#include "elm_priv.h" + +char *_elm_appname = NULL; +Elm_Config *_elm_config = NULL; + +static int +_elm_signal_exit(void *data, int ev_type, void *ev) +{ + elm_exit(); + return 1; +} + +EAPI void +elm_init(int argc, char **argv) +{ + int i; + + eet_init(); + ecore_init(); + ecore_app_args_set(argc, (const char **)argv); + ecore_file_init(); + evas_init(); + edje_init(); + ecore_evas_init(); // FIXME: check errors + + ecore_event_handler_add(ECORE_EVENT_SIGNAL_EXIT, _elm_signal_exit, NULL); + + _elm_appname = strdup(ecore_file_file_get(argv[0])); + + // FIXME: actually load config + _elm_config = ELM_NEW(Elm_Config); + _elm_config->engine = ELM_SOFTWARE_X11; + _elm_config->thumbscroll_enable = 1; + _elm_config->thumbscroll_threshhold = 24; + _elm_config->thumbscroll_momentum_threshhold = 100.0; + _elm_config->thumbscroll_friction = 1.0; + _elm_config->scale = 1.0; + + if ((_elm_config->engine == ELM_SOFTWARE_X11) || + (_elm_config->engine == ELM_SOFTWARE_16_X11) || + (_elm_config->engine == ELM_XRENDER_X11) || + (_elm_config->engine == ELM_OPENGL_X11)) + { + int val; + + ecore_x_init(NULL); + if (ecore_x_window_prop_card32_get(ecore_x_window_root_first_get(), + ecore_x_atom_get("ENLIGHTENMENT_SCALE"), + &val, 1)) + _elm_config->scale = (double)val / 1000.0; + } + +} + +EAPI void +elm_shutdown(void) +{ + free(_elm_config); + free(_elm_appname); + ecore_evas_shutdown(); + edje_shutdown(); + evas_shutdown(); + ecore_file_shutdown(); + ecore_shutdown(); + eet_shutdown(); +} + +EAPI void +elm_run(void) +{ + ecore_main_loop_begin(); +} + +EAPI void +elm_exit(void) +{ + ecore_main_loop_quit(); +} diff --git a/src/lib/elm_obj.c b/src/lib/elm_obj.c new file mode 100644 index 000000000..37639a2ae --- /dev/null +++ b/src/lib/elm_obj.c @@ -0,0 +1,177 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_obj_del(Elm_Obj *obj); +static void _elm_obj_ref(Elm_Obj *obj); +static void _elm_obj_unref(Elm_Obj *obj); +static Elm_Cb *_elm_obj_cb_add(Elm_Obj *obj, Elm_Cb_Type type, Elm_Cb_Func func, void *data); +static void _elm_obj_child_add(Elm_Obj *obj, Elm_Obj *child); +static int _elm_obj_hastype(Elm_Obj *obj, Elm_Obj_Type type); + +Elm_Obj_Class _elm_obj_class = +{ + NULL, /* parent */ + ELM_OBJ_OBJ, + _elm_obj_del, + _elm_obj_ref, + _elm_obj_unref, + _elm_obj_cb_add, + _elm_obj_child_add, + +}; + +static int deferred_nest = 0; +static Evas_List *deferred_deletions = NULL; + +static void +_elm_obj_del(Elm_Obj *obj) +{ + if (_elm_obj_del_defer(obj)) return; + _elm_obj_unref(obj); +} + +static void +_elm_obj_ref(Elm_Obj *obj) +{ + obj->ref++; +} + +static void +_elm_obj_unref(Elm_Obj *obj) +{ + obj->ref--; + if (obj->ref > 0) return; + if (!obj->delete_me) + { + obj->del(obj); + return; + } + if (obj->parent) + obj->parent->children = evas_list_remove(obj->parent->children, obj); + while (obj->cbs) + { + ((Elm_Obj *)obj->cbs->data)->parent = NULL; + ((Elm_Obj *)obj->cbs->data)->del(obj->cbs->data); + obj->cbs = evas_list_remove_list(obj->cbs, obj->cbs); + } + while (obj->children) + { + _elm_cb_call(obj, ELM_CB_CHILD_DEL, obj->children->data); + ((Elm_Obj *)obj->children->data)->parent = NULL; + ((Elm_Obj *)obj->children->data)->del(obj->children->data); + obj->children = evas_list_remove_list(obj->children, obj->children); + } + free(obj); +} + +static Elm_Cb * +_elm_obj_cb_add(Elm_Obj *obj, Elm_Cb_Type type, Elm_Cb_Func func, void *data) +{ + Elm_Cb *cb; + + cb = _elm_cb_new(); + cb->cb_type = type; + cb->func = func; + cb->data = data; + cb->parent = obj; + obj->cbs = evas_list_append(obj->cbs, cb); +} + +static void +_elm_obj_child_add(Elm_Obj *obj, Elm_Obj *child) +{ + if (child->parent) child->unparent(child); + obj->children = evas_list_prepend(obj->children, child); + child->parent = obj; + _elm_obj_nest_push(); + _elm_cb_call(obj, ELM_CB_CHILD_ADD, child); + _elm_cb_call(child, ELM_CB_PARENT, NULL); + _elm_obj_nest_pop(); +} + +static void +_elm_obj_unparent(Elm_Obj *obj) +{ + Elm_Obj *parent; + + parent = obj->parent; + obj->parent = NULL; + // FIXME: what if we are walking the children when we unparent? + parent->children = evas_list_remove(parent->children, obj); + _elm_obj_nest_push(); + _elm_cb_call(parent, ELM_CB_CHILD_DEL, obj); + _elm_cb_call(obj, ELM_CB_UNPARENT, NULL); + _elm_obj_nest_pop(); +} + +static int +_elm_obj_class_hastype(Elm_Obj_Class *clas, Elm_Obj_Type type) +{ + if (clas->type == type) return 1; + if (!clas->parent) return 0; + return _elm_obj_class_hastype(clas->parent, type); +} + +static int +_elm_obj_hastype(Elm_Obj *obj, Elm_Obj_Type type) +{ + if (obj->type == type) return 1; + if (obj->clas) return _elm_obj_class_hastype(obj->clas, type); + return 0; +} + +void +_elm_obj_init(Elm_Obj *obj) +{ + obj->del = _elm_obj_del; + obj->ref = _elm_obj_ref; + obj->unref = _elm_obj_unref; + obj->cb_add = _elm_obj_cb_add; + obj->child_add = _elm_obj_child_add; + obj->unparent = _elm_obj_unparent; + obj->hastype = _elm_obj_hastype; + obj->type = ELM_OBJ_OBJ; + obj->clas = &_elm_obj_class; + obj->refs = 1; +} + +void +_elm_obj_nest_push(void) +{ + deferred_nest++; +} + +void +_elm_obj_nest_pop(void) +{ + deferred_nest--; + if (deferred_nest > 0) return; + while (deferred_deletions) + { + ((Elm_Obj *)(deferred_deletions->data))->delete_deferred = 0; + ((Elm_Obj *)(deferred_deletions->data))->del(ELM_OBJ(deferred_deletions->data)); + deferred_deletions = evas_list_remove_list(deferred_deletions, deferred_deletions); + } +} + +int +_elm_obj_del_defer(Elm_Obj *obj) +{ + if (obj->delete_deferred) return 1; + if (!obj->delete_me) + { + /* will never be called during a deferred delete */ + obj->delete_me = 1; + _elm_obj_nest_push(); + _elm_cb_call(obj, ELM_CB_DEL, NULL); + _elm_obj_nest_pop(); + } + if (deferred_nest > 0) + { + /* mark to be deleted later */ + obj->delete_deferred = 1; + deferred_deletions = evas_list_append(deferred_deletions, obj); + return 1; + } + return 0; +} diff --git a/src/lib/elm_pad.c b/src/lib/elm_pad.c new file mode 100644 index 000000000..0513f4df5 --- /dev/null +++ b/src/lib/elm_pad.c @@ -0,0 +1,116 @@ +#include <Elementary.h> +#include "elm_priv.h" + +Elm_Pad_Class _elm_pad_class = +{ + &_elm_widget_class, + ELM_OBJ_PAD +}; + +static void +_elm_pad_size_alloc(Elm_Pad *pd, int w, int h) +{ + if (w < pd->minw) w = pd->minw; + if (h < pd->minh) h = pd->minh; + pd->req.w = w; + pd->req.h = h; +} + +static void +_elm_pad_size_req(Elm_Pad *pd, Elm_Widget *child, int w, int h) +{ + Evas_Coord mw, mh; + + if (child) + { + Evas_Coord maxx, maxy; + + child->size_alloc(child, 0, 0); + maxx = child->req.w; + maxy = child->req.h; + if (child->expand_x) maxx = 32767; + if (child->expand_y) maxy = 32767; + edje_extern_object_min_size_set(child->base, + child->req.w, + child->req.h); + edje_object_part_swallow(pd->base , "elm.swallow.contents", + child->base); + edje_object_size_min_calc(pd->base, &mw, &mh); + if ((pd->minw != mw) || (pd->minh != mh)) + { + pd->minw = mw; + pd->minh = mh; + ((Elm_Widget *)(pd->parent))->size_req(pd->parent, pd, mw, mh); + pd->geom_set(pd, pd->x, pd->y, mw, mh); + } + } + else + { + // FIXME: handle + } +} + +static void +_elm_on_child_add(void *data, Elm_Pad *pd, Elm_Cb_Type type, Elm_Obj *obj) +{ + Evas_Coord mw, mh; + + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + ((Elm_Widget *)(obj))->size_alloc(obj, 0, 0); + ((Elm_Widget *)(obj))->geom_set(obj, + ((Elm_Widget *)(obj))->x, + ((Elm_Widget *)(obj))->y, + ((Elm_Widget *)(obj))->req.w, + ((Elm_Widget *)(obj))->req.h); + edje_extern_object_min_size_set(((Elm_Widget *)(obj))->base, + ((Elm_Widget *)(obj))->req.w, + ((Elm_Widget *)(obj))->req.h); + edje_object_part_swallow(pd->base , "elm.swallow.content", + ((Elm_Widget *)(obj))->base); + edje_object_size_min_calc(pd->base, &mw, &mh); + if ((pd->minw != mw) || (pd->minh != mh)) + { + pd->minw = mw; + pd->minh = mh; + ((Elm_Widget *)(pd->parent))->size_req(pd->parent, pd, mw, mh); + pd->geom_set(pd, pd->x, pd->y, mw, mh); + } +} + +static void +_elm_on_child_del(void *data, Elm_Pad *pd, Elm_Cb_Type type, Elm_Obj *obj) +{ + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + // FIXME: allow for removal of child - size down +} + +static void +_elm_pad_del(Elm_Pad *pd) +{ + ((Elm_Obj_Class *)(((Elm_Pad_Class *)(pd->clas))->parent))->del(ELM_OBJ(pd)); +} + +EAPI Elm_Pad * +elm_pad_new(Elm_Win *win) +{ + Elm_Pad *pd; + + pd = ELM_NEW(Elm_Pad); + + _elm_widget_init(pd); + pd->clas = &_elm_pad_class; + pd->type = ELM_OBJ_PAD; + + pd->del = _elm_pad_del; + + pd->size_alloc = _elm_pad_size_alloc; + pd->size_req = _elm_pad_size_req; + + pd->base = edje_object_add(win->evas); + _elm_theme_set(pd->base, "pad", "pad"); + pd->cb_add(pd, ELM_CB_CHILD_ADD, _elm_on_child_add, NULL); + pd->cb_add(pd, ELM_CB_CHILD_DEL, _elm_on_child_del, NULL); + _elm_widget_post_init(pd); + win->child_add(win, pd); + return pd; +} diff --git a/src/lib/elm_priv.h b/src/lib/elm_priv.h new file mode 100644 index 000000000..377847d16 --- /dev/null +++ b/src/lib/elm_priv.h @@ -0,0 +1,64 @@ +#ifndef ELM_PRIV_H +#define ELM_PRIV_H + +#include "els_pan.h" +#include "els_scroller.h" +#include "els_box.h" +#include "els_table.h" +#include "els_icon.h" + +// FIXME: totally disorganised. clean this up! + +typedef enum _Elm_Engine +{ + ELM_SOFTWARE_X11, + ELM_SOFTWARE_FB, + ELM_SOFTWARE_16_X11, + ELM_XRENDER_X11, + ELM_OPENGL_X11 +} Elm_Engine; + +typedef struct _Elm_Config Elm_Config; + +struct _Elm_Config +{ + int engine; + int thumbscroll_enable; + int thumbscroll_threshhold; + double thumbscroll_momentum_threshhold; + double thumbscroll_friction; + double scale; +}; + +#define ELM_NEW(t) calloc(1, sizeof(t)) + +void _elm_obj_init(Elm_Obj *obj); +void _elm_obj_nest_push(void); +void _elm_obj_nest_pop(void); +int _elm_obj_del_defer(Elm_Obj *obj); +Elm_Cb *_elm_cb_new(void); +void _elm_cb_call(Elm_Obj *obj, Elm_Cb_Type, void *info); +int _elm_theme_set(Evas_Object *o, const char *clas, const char *group); +void _elm_widget_init(Elm_Widget *wid); +void _elm_widget_post_init(Elm_Widget *wid); + +extern char *_elm_appname; + +extern Elm_Config *_elm_config; + +extern Elm_Obj_Class _elm_obj_class; +extern Elm_Win_Class _elm_win_class; +extern Elm_Widget_Class _elm_widget_class; +extern Elm_Bg_Class _elm_bg_class; +extern Elm_Scroller_Class _elm_scroller_class; +extern Elm_Label_Class _elm_label_class; +extern Elm_Box_Class _elm_box_class; +extern Elm_Table_Class _elm_table_class; +extern Elm_Button_Class _elm_button_class; +extern Elm_Icon_Class _elm_icon_class; +extern Elm_Toggle_Class _elm_toggle_class; +extern Elm_Clock_Class _elm_clock_class; +extern Elm_Frame_Class _elm_frame_class; +extern Elm_Pad_Class _elm_pad_class; + +#endif diff --git a/src/lib/elm_scroller.c b/src/lib/elm_scroller.c new file mode 100644 index 000000000..ce1c567ab --- /dev/null +++ b/src/lib/elm_scroller.c @@ -0,0 +1,99 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_scroller_del(Elm_Scroller *sc); + +Elm_Scroller_Class _elm_scroller_class = +{ + &_elm_widget_class, + ELM_OBJ_SCROLLER +}; + +static void +_elm_scroller_del(Elm_Scroller *sc) +{ + evas_object_del(sc->scroller_pan); + ((Elm_Obj_Class *)(((Elm_Scroller_Class *)(sc->clas))->parent))->del(ELM_OBJ(sc)); +} + +static void +_elm_scroller_geom_set(Elm_Scroller *sc, int x, int y, int w, int h) +{ + Evas_Coord vw, vh; + + if ((sc->w != w) || (sc->h != h) || (sc->x != x) || (sc->y != y)) + { + Evas_List *l; + int tries = 0; + + ((Elm_Widget_Class *)(((Elm_Scroller_Class *)(sc->clas))->parent))->geom_set(sc, x, y, w, h); + again: + tries++; + elm_smart_scroller_child_viewport_size_get(sc->base, &vw, &vh); + for (l = sc->children; l; l = l->next) + { + if (((Elm_Obj *)(l->data))->hastype(l->data, ELM_OBJ_WIDGET)) + { + ((Elm_Widget *)(l->data))->size_alloc(l->data, vw, vh); + ((Elm_Widget *)(l->data))->geom_set(l->data, + ((Elm_Widget *)(l->data))->x, + ((Elm_Widget *)(l->data))->y, + ((Elm_Widget *)(l->data))->req.w, + ((Elm_Widget *)(l->data))->req.h); +// FIXME: if scrollbars affect viewport size then we get an on/off effect of +// resizing child up and down. we need to find a way to avoid this. this tries +// this is a hack - but works. + if ((tries == 1) && + (((vw == ((Elm_Widget *)(l->data))->req.w) || + (vh == ((Elm_Widget *)(l->data))->req.h)))) goto again; + } + } + } +} + +static void +_elm_on_child_add(void *data, Elm_Scroller *sc, Elm_Cb_Type type, Elm_Obj *obj) +{ + Evas_Coord vw, vh; + + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + elm_smart_scroller_child_set(sc->base, ((Elm_Widget *)(obj))->base); + elm_smart_scroller_child_viewport_size_get(sc->base, &vw, &vh); + ((Elm_Widget *)(obj))->size_alloc(obj, vw, vh); + ((Elm_Widget *)(obj))->geom_set(obj, + ((Elm_Widget *)(obj))->x, + ((Elm_Widget *)(obj))->y, + ((Elm_Widget *)(obj))->req.w, + ((Elm_Widget *)(obj))->req.h); +} + +static void +_elm_on_child_del(void *data, Elm_Scroller *sc, Elm_Cb_Type type, Elm_Obj *obj) +{ + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + elm_smart_scroller_child_set(sc->base, NULL); +} + +EAPI Elm_Scroller * +elm_scroller_new(Elm_Win *win) +{ + Elm_Scroller *sc; + + sc = ELM_NEW(Elm_Scroller); + _elm_widget_init(sc); + + sc->clas = &_elm_scroller_class; + sc->type = ELM_OBJ_SCROLLER; + + sc->del = _elm_scroller_del; + + sc->geom_set = _elm_scroller_geom_set; + + sc->base = elm_smart_scroller_add(win->evas); + + sc->cb_add(sc, ELM_CB_CHILD_ADD, _elm_on_child_add, NULL); + sc->cb_add(sc, ELM_CB_CHILD_DEL, _elm_on_child_del, NULL); + _elm_widget_post_init(sc); + win->child_add(win, sc); + return sc; +} diff --git a/src/lib/elm_table.c b/src/lib/elm_table.c new file mode 100644 index 000000000..5478b5bb6 --- /dev/null +++ b/src/lib/elm_table.c @@ -0,0 +1,104 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_table_layout_update(Elm_Table *tb); +static void _elm_table_pack(Elm_Table *tb, Elm_Widget *wid, int x, int y, int w, int h); + +Elm_Table_Class _elm_table_class = +{ + &_elm_widget_class, + ELM_OBJ_TABLE, + _elm_table_layout_update, + _elm_table_pack, +}; + +static void +_elm_table_layout_update(Elm_Table *tb) +{ + _els_smart_table_homogenous_set(tb->base, tb->homogenous); +} + +static void +_elm_table_pack(Elm_Table *tb, Elm_Widget *wid, int x, int y, int w, int h) +{ + tb->child_add(tb, wid); + _els_smart_table_pack(tb->base, wid->base, x, y, w, h); +} + +static void +_elm_table_size_alloc(Elm_Table *tb, int w, int h) +{ + Evas_Coord mw, mh; + + _els_smart_table_min_size_get(tb->base, &mw, &mh); + if (w < mw) w = mw; + if (h < mh) h = mh; + tb->req.w = w; + tb->req.h = h; +} + +static void +_elm_table_size_req(Elm_Table *tb, Elm_Widget *child, int w, int h) +{ + Evas_Coord mw, mh; + + if (child) + { + Evas_Coord maxx, maxy; + + child->size_alloc(child, 0, 0); + maxx = child->req.w; + maxy = child->req.h; + if (child->expand_x) maxx = 32767; + if (child->expand_y) maxy = 32767; + _els_smart_table_pack_options_set(child->base, + child->fill_x, child->fill_y, + child->expand_x, child->expand_y, + child->align_x, child->align_y, + child->req.w, child->req.h, + maxx, maxy); + } + else + { + // FIXME: handle. + } + _els_smart_table_min_size_get(tb->base, &mw, &mh); + ((Elm_Widget *)(tb->parent))->size_req(tb->parent, tb, mw, mh); + tb->geom_set(tb, tb->x, tb->y, mw, mh); +} + +static void +_elm_on_child_del(void *data, Elm_Table *tb, Elm_Cb_Type type, Elm_Obj *obj) +{ + Evas_Coord mw, mh; + + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + _els_smart_table_unpack(((Elm_Widget *)(obj))->base); + ((Elm_Widget *)(tb->parent))->size_req(tb->parent, tb, mw, mh); + tb->geom_set(tb, tb->x, tb->y, mw, mh); +} + +EAPI Elm_Table * +elm_table_new(Elm_Win *win) +{ + Elm_Table *tb; + + tb = ELM_NEW(Elm_Table); + + _elm_widget_init(tb); + tb->clas = &_elm_table_class; + tb->type = ELM_OBJ_TABLE; + + tb->layout_update = _elm_table_layout_update; + tb->pack = _elm_table_pack; + + tb->size_alloc = _elm_table_size_alloc; + tb->size_req = _elm_table_size_req; + + tb->base = _els_smart_table_add(win->evas); + + tb->cb_add(tb, ELM_CB_CHILD_DEL, _elm_on_child_del, NULL); + _elm_widget_post_init(tb); + win->child_add(win, tb); + return tb; +} diff --git a/src/lib/elm_theme.c b/src/lib/elm_theme.c new file mode 100644 index 000000000..c9b77a5ca --- /dev/null +++ b/src/lib/elm_theme.c @@ -0,0 +1,13 @@ +#include <Elementary.h> +#include "elm_priv.h" + +int +_elm_theme_set(Evas_Object *o, const char *clas, const char *group) +{ + char buf[PATH_MAX]; + + // FIXME: actually handle themes for real + snprintf(buf, sizeof(buf), "%s/themes/%s.edj", PACKAGE_DATA_DIR, + "default"); + return edje_object_file_set(o, buf, group); +} diff --git a/src/lib/elm_toggle.c b/src/lib/elm_toggle.c new file mode 100644 index 000000000..1e73d20c0 --- /dev/null +++ b/src/lib/elm_toggle.c @@ -0,0 +1,210 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_toggle_text_set(Elm_Toggle *tg, const char *text); +static void _elm_toggle_layout_update(Elm_Toggle *tg); +static void _elm_toggle_states_text_set(Elm_Toggle *tg, const char *ontext, const char *offtext); + +Elm_Toggle_Class _elm_toggle_class = +{ + &_elm_widget_class, + ELM_OBJ_TOGGLE, + _elm_toggle_text_set, + _elm_toggle_layout_update, + _elm_toggle_states_text_set +}; + +static void +_elm_toggle_text_set(Elm_Toggle *tg, const char *text) +{ + Evas_Coord mw, mh; + + if (text) + { + edje_object_signal_emit(tg->base, "elm,state,text,visible", "elm"); + edje_object_message_signal_process(tg->base); + } + else + { + edje_object_signal_emit(tg->base, "elm,state,text,hidden", "elm"); + edje_object_message_signal_process(tg->base); + } + edje_object_part_text_set(tg->base, "elm.text", text); + edje_object_size_min_calc(tg->base, &mw, &mh); + if ((tg->minw != mw) || (tg->minh != mh)) + { + tg->minw = mw; + tg->minh = mh; + ((Elm_Widget *)(tg->parent))->size_req(tg->parent, tg, tg->minw, tg->minh); + tg->geom_set(tg, tg->x, tg->y, tg->minw, tg->minh); + } +} + +static void +_elm_toggle_states_text_set(Elm_Toggle *tg, const char *ontext, const char *offtext) +{ + edje_object_part_text_set(tg->base, "elm.ontext", ontext); + edje_object_part_text_set(tg->base, "elm.offtext", offtext); +} + +static void +_elm_toggle_layout_update(Elm_Toggle *tg) +{ + if (tg->state_ptr) tg->state = *(tg->state_ptr); + if (tg->state) + edje_object_signal_emit(tg->base, "elm,state,toggle,on", "elm"); + else + edje_object_signal_emit(tg->base, "elm,state,toggle,off", "elm"); +} + +static void +_elm_toggle_size_alloc(Elm_Toggle *tg, int w, int h) +{ + if (w < tg->minw) w = tg->minw; + if (h < tg->minh) h = tg->minh; + tg->req.w = w; + tg->req.h = h; +} + +static void +_elm_toggle_size_req(Elm_Toggle *tg, Elm_Widget *child, int w, int h) +{ + Evas_Coord mw, mh; + + if (child) + { + Evas_Coord maxx, maxy; + + child->size_alloc(child, 0, 0); + maxx = child->req.w; + maxy = child->req.h; + if (child->expand_x) maxx = 32767; + if (child->expand_y) maxy = 32767; + edje_extern_object_min_size_set(child->base, + child->req.w, + child->req.h); + edje_object_part_swallow(tg->base , "elm.swallow.contents", + child->base); + edje_object_size_min_calc(tg->base, &mw, &mh); + if ((tg->minw != mw) || (tg->minh != mh)) + { + tg->minw = mw; + tg->minh = mh; + ((Elm_Widget *)(tg->parent))->size_req(tg->parent, tg, mw, mh); + tg->geom_set(tg, tg->x, tg->y, mw, mh); + } + } + else + { + // FIXME: handle + } +} + +static void +_elm_on_child_add(void *data, Elm_Toggle *tg, Elm_Cb_Type type, Elm_Obj *obj) +{ + Evas_Coord mw, mh; + + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + edje_object_signal_emit(tg->base, "elm,state,icon,visible", "elm"); + edje_object_message_signal_process(tg->base); + ((Elm_Widget *)(obj))->size_alloc(obj, 0, 0); + ((Elm_Widget *)(obj))->geom_set(obj, + ((Elm_Widget *)(obj))->x, + ((Elm_Widget *)(obj))->y, + ((Elm_Widget *)(obj))->req.w, + ((Elm_Widget *)(obj))->req.h); + edje_extern_object_min_size_set(((Elm_Widget *)(obj))->base, + ((Elm_Widget *)(obj))->req.w, + ((Elm_Widget *)(obj))->req.h); + edje_object_part_swallow(tg->base , "elm.swallow.contents", + ((Elm_Widget *)(obj))->base); + edje_object_size_min_calc(tg->base, &mw, &mh); + if ((tg->minw != mw) || (tg->minh != mh)) + { + tg->minw = mw; + tg->minh = mh; + ((Elm_Widget *)(tg->parent))->size_req(tg->parent, tg, mw, mh); + tg->geom_set(tg, tg->x, tg->y, mw, mh); + } +} + +static void +_elm_on_child_del(void *data, Elm_Toggle *tg, Elm_Cb_Type type, Elm_Obj *obj) +{ + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + // FIXME: allow for removal of child - size down + edje_object_signal_emit(tg->base, "elm,state,icon,hidden", "elm"); + edje_object_message_signal_process(tg->base); +} + +static void +_elm_toggle_activate(Elm_Toggle *tg) +{ + if (tg->state_ptr) *(tg->state_ptr) = tg->state; + _elm_obj_nest_push(); + _elm_cb_call(ELM_OBJ(tg), ELM_CB_CHANGED, NULL); + _elm_obj_nest_pop(); +} + +static void +_elm_signal_toggle_on(void *data, Evas_Object *obj, const char *emission, const char *source) +{ + Elm_Toggle *tg = data; + + if (tg->state) return; + tg->state = 1; + _elm_toggle_activate(tg); +} + +static void +_elm_signal_toggle_off(void *data, Evas_Object *obj, const char *emission, const char *source) +{ + Elm_Toggle *tg = data; + + if (!tg->state) return; + tg->state = 0; + _elm_toggle_activate(tg); +} + +static void +_elm_toggle_del(Elm_Toggle *tg) +{ + if (tg->text) evas_stringshare_del(tg->text); + ((Elm_Obj_Class *)(((Elm_Toggle_Class *)(tg->clas))->parent))->del(ELM_OBJ(tg)); +} + +EAPI Elm_Toggle * +elm_toggle_new(Elm_Win *win) +{ + Elm_Toggle *tg; + + tg = ELM_NEW(Elm_Toggle); + + _elm_widget_init(tg); + tg->clas = &_elm_toggle_class; + tg->type = ELM_OBJ_TOGGLE; + + tg->del = _elm_toggle_del; + + tg->size_alloc = _elm_toggle_size_alloc; + tg->size_req = _elm_toggle_size_req; + + tg->text_set = _elm_toggle_text_set; + tg->layout_update = _elm_toggle_layout_update; + tg->states_text_set = _elm_toggle_states_text_set; + + tg->base = edje_object_add(win->evas); + _elm_theme_set(tg->base, "toggle", "toggle"); + edje_object_part_text_set(tg->base, "elm.ontext", "ON"); + edje_object_part_text_set(tg->base, "elm.offtext", "OFF"); + edje_object_signal_callback_add(tg->base, "elm,action,toggle,on", "", + _elm_signal_toggle_on, tg); + edje_object_signal_callback_add(tg->base, "elm,action,toggle,off", "", + _elm_signal_toggle_off, tg); + tg->cb_add(tg, ELM_CB_CHILD_ADD, _elm_on_child_add, NULL); + tg->cb_add(tg, ELM_CB_CHILD_DEL, _elm_on_child_del, NULL); + _elm_widget_post_init(tg); + win->child_add(win, tg); + return tg; +} diff --git a/src/lib/elm_widget.c b/src/lib/elm_widget.c new file mode 100644 index 000000000..2fddfa8b0 --- /dev/null +++ b/src/lib/elm_widget.c @@ -0,0 +1,137 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_widget_geom_set(Elm_Widget *wid, int x, int y, int w, int h); +static void _elm_widget_show(Elm_Widget *wid); +static void _elm_widget_hide(Elm_Widget *wid); +static void _elm_widget_size_alloc(Elm_Widget *wid, int w, int h); +static void _elm_widget_size_req(Elm_Widget *wid, Elm_Widget *child, int w, int h); +static void _elm_widget_del(Elm_Widget *wid); +static void _elm_widget_above(Elm_Widget *wid, Elm_Widget *above); +static void _elm_widget_below(Elm_Widget *wid, Elm_Widget *below); + +Elm_Widget_Class _elm_widget_class = +{ + &_elm_obj_class, /* parent */ + ELM_OBJ_WIDGET, + _elm_widget_geom_set, + _elm_widget_show, + _elm_widget_hide, + _elm_widget_size_alloc, + _elm_widget_size_req, + _elm_widget_above, + _elm_widget_below +}; + +static void +_elm_widget_geom_set(Elm_Widget *wid, int x, int y, int w, int h) +{ + if ((wid->x != x) || (wid->y != y)) + { + wid->x = x; + wid->y = y; + evas_object_move(wid->base, wid->x, wid->y); + } + if ((wid->w != w) || (wid->h != h)) + { + wid->w = w; + wid->h = h; + evas_object_resize(wid->base, wid->w, wid->h); + _elm_obj_nest_push(); + _elm_cb_call(ELM_OBJ(wid), ELM_CB_RESIZE, NULL); + _elm_obj_nest_pop(); + } +} + +static void +_elm_widget_show(Elm_Widget *wid) +{ + evas_object_show(wid->base); +} + +static void +_elm_widget_hide(Elm_Widget *wid) +{ + evas_object_hide(wid->base); +} + +static void +_elm_widget_size_alloc(Elm_Widget *wid, int w, int h) +{ + // FIXME: widget gets to implement min/max etc. size here (indicating + // given the input w, h - what size it is willing to accept, then the + // parent checks and geometry_set()'s the child + wid->req.w = w; + wid->req.h = h; +} + +static void +_elm_widget_size_req(Elm_Widget *wid, Elm_Widget *child, int w, int h) +{ + // FIXME: a child will ask its parent for a requested size if something + // with its sizing setup. this is the call in the parent that will be + // called +} + +static void +_elm_widget_above(Elm_Widget *wid, Elm_Widget *above) +{ + if (above) evas_object_stack_above(wid->base, above->base); + else evas_object_raise(wid->base); +} + +static void +_elm_widget_below(Elm_Widget *wid, Elm_Widget *below) +{ + if (below) evas_object_stack_below(wid->base, below->base); + else evas_object_lower(wid->base); +} + +static void +_elm_widget_del(Elm_Widget *wid) +{ + if (_elm_obj_del_defer(ELM_OBJ(wid))) return; + + evas_object_del(wid->base); + + ((Elm_Obj_Class *)(((Elm_Widget_Class *)(wid->clas))->parent))->del(ELM_OBJ(wid)); +} + +void +_elm_widget_init(Elm_Widget *wid) +{ + _elm_obj_init(ELM_OBJ(wid)); + wid->clas = &_elm_widget_class; + wid->type = ELM_OBJ_WIDGET; + + wid->del = _elm_widget_del; + + wid->geom_set = _elm_widget_geom_set; + wid->show = _elm_widget_show; + wid->hide = _elm_widget_hide; + wid->size_alloc = _elm_widget_size_alloc; + wid->size_req = _elm_widget_size_req; + wid->above = _elm_widget_above; + wid->below = _elm_widget_below; + + wid->align_x = 0.5; + wid->align_y = 0.5; + wid->expand_x = 1; + wid->expand_y = 1; + wid->fill_x = 1; + wid->fill_y = 1; +} + +void +_elm_widget_post_init(Elm_Widget *wid) +{ + if (wid->base) evas_object_data_set(wid->base, "__Elm", wid); +} + +EAPI void +elm_widget_sizing_update(Elm_Widget *wid) +{ + wid->size_alloc(wid, 0, 0); + if (!wid->parent) return; + ((Elm_Widget *)(wid->parent))->size_req(wid->parent, wid, wid->w, wid->h); +} diff --git a/src/lib/elm_win.c b/src/lib/elm_win.c new file mode 100644 index 000000000..a0c7d185e --- /dev/null +++ b/src/lib/elm_win.c @@ -0,0 +1,307 @@ +#include <Elementary.h> +#include "elm_priv.h" + +static void _elm_win_name_set(Elm_Win *win, const char *name); +static void _elm_win_title_set(Elm_Win *win, const char *title); +static void _elm_win_show(Elm_Win *win); +static void _elm_win_hide(Elm_Win *win); +static void _elm_win_del(Elm_Win *win); + +Elm_Win_Class _elm_win_class = +{ + &_elm_obj_class, /* parent */ + ELM_OBJ_WIN, + _elm_win_name_set, + _elm_win_title_set +}; + +static void +_elm_child_eval_job(Elm_Win *win) +{ + Evas_List *l; + int w, h; + int expand_x, expand_y; + + win->deferred_child_eval_job = NULL; + _elm_obj_nest_push(); + w = h = 0; + expand_x = expand_y = 0; + for (l = win->children; l; l = l->next) + { + if (((Elm_Obj *)(l->data))->hastype(l->data, ELM_OBJ_WIDGET)) + { + if (((Elm_Widget *)(l->data))->w > w) w = ((Elm_Widget *)(l->data))->w; + if (((Elm_Widget *)(l->data))->h > h) h = ((Elm_Widget *)(l->data))->h; + if (((Elm_Widget *)(l->data))->expand_x) expand_x = 1; + if (((Elm_Widget *)(l->data))->expand_y) expand_y = 1; + } + } + ecore_evas_size_min_set(win->ee, w, h); + if ((!expand_x) && (!expand_y)) ecore_evas_size_max_set(win->ee, w, h); + else if (!expand_x) ecore_evas_size_max_set(win->ee, w, 32727); + else if (!expand_y) ecore_evas_size_max_set(win->ee, 32767, h); + else ecore_evas_size_max_set(win->ee, 0, 0); + if (w < win->w) w = win->w; + if (h < win->h) h = win->h; + if ((w > win->w) || (h > win->h)) ecore_evas_resize(win->ee, w, h); + if (win->showme) + { + win->showme = 0; + ecore_evas_show(win->ee); + } + _elm_obj_nest_pop(); +} + +static void +_elm_on_child_add(void *data, Elm_Win *win, Elm_Cb_Type type, Elm_Obj *obj) +{ + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + if (win->deferred_child_eval_job) ecore_job_del(win->deferred_child_eval_job); + win->deferred_child_eval_job = ecore_job_add(_elm_child_eval_job, win); +} + +static void +_elm_on_child_del(void *data, Elm_Win *win, Elm_Cb_Type type, Elm_Obj *obj) +{ + if (!(obj->hastype(obj, ELM_OBJ_WIDGET))) return; + if (win->deferred_child_eval_job) ecore_job_del(win->deferred_child_eval_job); + win->deferred_child_eval_job = ecore_job_add(_elm_child_eval_job, win); +} + +static void +_elm_win_name_set(Elm_Win *win, const char *name) +{ + if (win->name) evas_stringshare_del(win->name); + win->name = evas_stringshare_add(name); + if (win->ee) ecore_evas_name_class_set(win->ee, win->name, _elm_appname); +} + +static void +_elm_win_title_set(Elm_Win *win, const char *title) +{ + if (win->title) evas_stringshare_del(win->title); + win->title = evas_stringshare_add(title); + if (win->ee) ecore_evas_title_set(win->ee, win->title); +} + +static void +_elm_win_show(Elm_Win *win) +{ + if (win->deferred_child_eval_job) + win->showme = 1; + else + ecore_evas_show(win->ee); +} + +static void +_elm_win_hide(Elm_Win *win) +{ + win->showme = 0; + ecore_evas_hide(win->ee); +} + +static void +_elm_win_type_set(Elm_Win *win, Elm_Win_Type type) +{ + if (win->win_type == type) return; + win->win_type = type; + switch (win->win_type) + { + case ELM_WIN_BASIC: + if (win->xwin) ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_NORMAL); + // FIXME: if child object is a scroll region, then put its child back + break; + case ELM_WIN_DIALOG_BASIC: + if (win->xwin) ecore_x_netwm_window_type_set(win->xwin, ECORE_X_WINDOW_TYPE_DIALOG); + // FIXME: if child object is a scroll region, then put its child back + break; + default: + break; + } +} + +static void +_elm_win_geom_set(Elm_Win *win, int x, int y, int w, int h) +{ + if ((win->w != w) || (win->h != h) || (win->x != x) || (win->y != y)) + { + win->x = x; + win->y = y; + win->w = w; + win->h = h; + ecore_evas_move_resize(win->ee, win->x, win->y, win->w, win->h); + } +} + +static void +_elm_win_size_alloc(Elm_Win *win, int w, int h) +{ + /* this should never be called */ +} + +static void +_elm_win_size_req(Elm_Win *win, Elm_Widget *child, int w, int h) +{ + if (child) + { + if (win->deferred_child_eval_job) ecore_job_del(win->deferred_child_eval_job); + win->deferred_child_eval_job = ecore_job_add(_elm_child_eval_job, win); + } + else + { + if ((w == win->w) && (h == win->h)) return; + ecore_evas_resize(win->ee, w, h); + } +} + +static void +_elm_win_above(Elm_Win *win, Elm_Widget *above) +{ +} + +static void +_elm_win_below(Elm_Win *win, Elm_Widget *below) +{ +} + +static void +_elm_win_del(Elm_Win *win) +{ + if (_elm_obj_del_defer(ELM_OBJ(win))) return; + if (win->ee) + { + ecore_evas_free(win->ee); + evas_stringshare_del(win->title); + evas_stringshare_del(win->name); + } + 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); + ((Elm_Obj_Class *)(((Elm_Win_Class *)(win->clas))->parent))->del(ELM_OBJ(win)); +} + + + +static void +_elm_win_delete_request(Ecore_Evas *ee) +{ + Elm_Win *win = ecore_evas_data_get(ee, "__Elm"); + if (!win) return; + _elm_obj_nest_push(); + _elm_cb_call(ELM_OBJ(win), ELM_CB_DEL_REQ, NULL); + if (win->autodel) win->del(ELM_OBJ(win)); + _elm_obj_nest_pop(); +} + +static void +_elm_win_resize_job(Elm_Win *win) +{ + Evas_List *l; + int w, h; + + win->deferred_resize_job = NULL; + ecore_evas_geometry_get(win->ee, NULL, NULL, &w, &h); + if ((win->w == w) && (win->h == h)) return; + win->w = w; + win->h = h; + /* resize all immediate children if they are widgets or sub-classes */ + _elm_obj_nest_push(); + for (l = win->children; l; l = l->next) + { + if (((Elm_Obj *)(l->data))->hastype(l->data, ELM_OBJ_WIDGET)) + ((Elm_Widget *)(l->data))->geom_set(l->data, 0, 0, win->w, win->h); + } + _elm_cb_call(ELM_OBJ(win), ELM_CB_RESIZE, NULL); + _elm_obj_nest_pop(); +} + +static void +_elm_win_resize(Ecore_Evas *ee) +{ + Elm_Win *win = ecore_evas_data_get(ee, "__Elm"); + 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); +} + +EAPI Elm_Win * +elm_win_new(void) +{ + Elm_Win *win; + + win = ELM_NEW(Elm_Win); + + _elm_obj_init(ELM_OBJ(win)); + win->clas = &_elm_win_class; + win->type = ELM_OBJ_WIN; + + win->del = _elm_win_del; + + win->geom_set = _elm_win_geom_set; + win->show = _elm_win_show; + win->hide = _elm_win_hide; + win->size_alloc = _elm_win_size_alloc; + win->size_req = _elm_win_size_req; + win->above = _elm_win_above; + win->below = _elm_win_below; + + win->name_set = _elm_win_name_set; + win->title_set = _elm_win_title_set; + + switch (_elm_config->engine) + { + case ELM_SOFTWARE_X11: + win->ee = ecore_evas_software_x11_new(NULL, 0, 0, 0, 1, 1); + if (win->ee) win->xwin = ecore_evas_software_x11_window_get(win->ee); + break; + case ELM_SOFTWARE_FB: + win->ee = ecore_evas_fb_new(NULL, 0, 1, 1); + ecore_evas_fullscreen_set(win->ee, 1); + break; + case ELM_SOFTWARE_16_X11: + win->ee = ecore_evas_software_x11_16_new(NULL, 0, 0, 0, 1, 1); + if (win->ee) win->xwin = ecore_evas_software_x11_16_window_get(win->ee); + break; + case ELM_XRENDER_X11: + win->ee = ecore_evas_xrender_x11_new(NULL, 0, 0, 0, 1, 1); + if (win->ee) win->xwin = ecore_evas_xrender_x11_window_get(win->ee); + break; + case ELM_OPENGL_X11: + win->ee = ecore_evas_gl_x11_new(NULL, 0, 0, 0, 1, 1); + if (win->ee) win->xwin = ecore_evas_gl_x11_window_get(win->ee); + break; + default: + break; + } + if (!win->ee) + { + printf("ELEMENTARY: Error. Cannot create window.\n"); + win->del(ELM_OBJ(win)); + return NULL; + } + win->type = ELM_WIN_BASIC; + win->name = evas_stringshare_add("default"); + win->title = evas_stringshare_add("Elementary Window"); + + win->evas = ecore_evas_get(win->ee); + ecore_evas_title_set(win->ee, win->title); + ecore_evas_name_class_set(win->ee, win->name, _elm_appname); + ecore_evas_data_set(win->ee, "__Elm", win); + ecore_evas_callback_delete_request_set(win->ee, _elm_win_delete_request); + ecore_evas_callback_resize_set(win->ee, _elm_win_resize); + // FIXME: use elm config for this + evas_image_cache_set(win->evas, 4096 * 1024); + evas_font_cache_set(win->evas, 512 * 1024); + evas_font_path_append(win->evas, "fonts"); +// evas_font_hinting_set(win->evas, EVAS_FONT_HINTING_NONE); +// evas_font_hinting_set(win->evas, EVAS_FONT_HINTING_AUTO); +// evas_font_hinting_set(win->evas, EVAS_FONT_HINTING_BYTECODE); + edje_frametime_set(1.0 / 30.0); + edje_scale_set(_elm_config->scale); + + win->cb_add(win, ELM_CB_CHILD_ADD, _elm_on_child_add, NULL); + win->cb_add(win, ELM_CB_CHILD_DEL, _elm_on_child_del, NULL); + + return win; +} diff --git a/src/lib/els_box.c b/src/lib/els_box.c new file mode 100644 index 000000000..516a7714f --- /dev/null +++ b/src/lib/els_box.c @@ -0,0 +1,712 @@ +#include <Elementary.h> +#include "elm_priv.h" + +typedef struct _Smart_Data Smart_Data; +typedef struct _Box_Item Box_Item; + +struct _Smart_Data +{ + Evas_Coord x, y, w, h; + Evas_Object *obj; + Evas_Object *clip; + int frozen; + unsigned char changed : 1; + unsigned char horizontal : 1; + unsigned char homogenous : 1; + Evas_List *items; + struct { + Evas_Coord w, h; + } min, max; + struct { + double x, y; + } align; +}; + +struct _Box_Item +{ + Smart_Data *sd; + unsigned char fill_w : 1; + unsigned char fill_h : 1; + unsigned char expand_w : 1; + unsigned char expand_h : 1; + struct { + Evas_Coord w, h; + } min, max; + struct { + double x, y; + } align; + Evas_Object *obj; +}; + +/* local subsystem functions */ +static Box_Item *_smart_adopt(Smart_Data *sd, Evas_Object *obj); +static void _smart_disown(Evas_Object *obj); +static void _smart_item_del_hook(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _smart_reconfigure(Smart_Data *sd); +static void _smart_extents_calculate(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); + +/* local subsystem globals */ +static Evas_Smart *_e_smart = NULL; + +/* externally accessible functions */ +Evas_Object * +_els_smart_box_add(Evas *evas) +{ + _smart_init(); + return evas_object_smart_add(evas, _e_smart); +} + +int +_els_smart_box_freeze(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return 0; + sd->frozen++; + return sd->frozen; +} + +int +_els_smart_box_thaw(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return 0; + sd->frozen--; + if (sd->frozen <= 0) _smart_reconfigure(sd); + return sd->frozen; +} + +void +_els_smart_box_orientation_set(Evas_Object *obj, int horizontal) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->horizontal == horizontal) return; + sd->horizontal = horizontal; + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); +} + +int +_els_smart_box_orientation_get(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return 0; + return sd->horizontal; +} + +void +_els_smart_box_homogenous_set(Evas_Object *obj, int homogenous) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->homogenous == homogenous) return; + sd->homogenous = homogenous; + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); +} + +int +_els_smart_box_pack_start(Evas_Object *obj, Evas_Object *child) +{ + Smart_Data *sd; + + if (!child) return 0; + sd = evas_object_smart_data_get(obj); + if (!sd) return 0; + _smart_adopt(sd, child); + sd->items = evas_list_prepend(sd->items, child); + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); + return 0; +} + +int +_els_smart_box_pack_end(Evas_Object *obj, Evas_Object *child) +{ + Smart_Data *sd; + + if (!child) return 0; + sd = evas_object_smart_data_get(obj); + if (!sd) return 0; + _smart_adopt(sd, child); + sd->items = evas_list_append(sd->items, child); + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); + return evas_list_count(sd->items) - 1; +} + +int +_els_smart_box_pack_before(Evas_Object *obj, Evas_Object *child, Evas_Object *before) +{ + Smart_Data *sd; + int i = 0; + Evas_List *l; + + if (!child) return 0; + sd = evas_object_smart_data_get(obj); + if (!sd) return 0; + _smart_adopt(sd, child); + sd->items = evas_list_prepend_relative(sd->items, child, before); + for (i = 0, l = sd->items; l; l = l->next, i++) + { + if (l->data == child) break; + } + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); + return i; +} + +int +_els_smart_box_pack_after(Evas_Object *obj, Evas_Object *child, Evas_Object *after) +{ + Smart_Data *sd; + int i = 0; + Evas_List *l; + + if (!child) return 0; + sd = evas_object_smart_data_get(obj); + if (!sd) return 0; + _smart_adopt(sd, child); + sd->items = evas_list_append_relative(sd->items, child, after); + for (i = 0, l = sd->items; l; l = l->next, i++) + { + if (l->data == child) break; + } + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); + return i; +} + + +void +_els_smart_box_pack_options_set(Evas_Object *obj, int fill_w, int fill_h, int expand_w, int expand_h, double align_x, double align_y, Evas_Coord min_w, Evas_Coord min_h, Evas_Coord max_w, Evas_Coord max_h) +{ + Box_Item *bi; + + bi = evas_object_data_get(obj, "e_box_data"); + if (!bi) return; + bi->fill_w = fill_w; + bi->fill_h = fill_h; + bi->expand_w = expand_w; + bi->expand_h = expand_h; + bi->align.x = align_x; + bi->align.y = align_y; + bi->min.w = min_w; + bi->min.h = min_h; + bi->max.w = max_w; + bi->max.h = max_h; + bi->sd->changed = 1; + if (bi->sd->frozen <= 0) _smart_reconfigure(bi->sd); +} + +void +_els_smart_box_unpack(Evas_Object *obj) +{ + Box_Item *bi; + Smart_Data *sd; + + if (!obj) return; + bi = evas_object_data_get(obj, "e_box_data"); + if (!bi) return; + sd = bi->sd; + if (!sd) return; + sd->items = evas_list_remove(sd->items, obj); + _smart_disown(obj); + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); +} + +void +_els_smart_box_min_size_get(Evas_Object *obj, Evas_Coord *minw, Evas_Coord *minh) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->changed) _smart_extents_calculate(sd); + if (minw) *minw = sd->min.w; + if (minh) *minh = sd->min.h; +} + +void +_els_smart_box_max_size_get(Evas_Object *obj, Evas_Coord *maxw, Evas_Coord *maxh) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->changed) _smart_extents_calculate(sd); + if (maxw) *maxw = sd->max.w; + if (maxh) *maxh = sd->max.h; +} + +/* local subsystem functions */ +static Box_Item * +_smart_adopt(Smart_Data *sd, Evas_Object *obj) +{ + Box_Item *bi; + + bi = calloc(1, sizeof(Box_Item)); + if (!bi) return NULL; + bi->sd = sd; + bi->obj = obj; + /* defaults */ + bi->fill_w = 0; + bi->fill_h = 0; + bi->expand_w = 0; + bi->expand_h = 0; + bi->align.x = 0.5; + bi->align.y = 0.5; + bi->min.w = 0; + bi->min.h = 0; + bi->max.w = 0; + bi->max.h = 0; + evas_object_clip_set(obj, sd->clip); + evas_object_smart_member_add(obj, bi->sd->obj); + evas_object_data_set(obj, "e_box_data", bi); + evas_object_event_callback_add(obj, EVAS_CALLBACK_FREE, + _smart_item_del_hook, NULL); + if ((!evas_object_visible_get(sd->clip)) && + (evas_object_visible_get(sd->obj))) + evas_object_show(sd->clip); + return bi; +} + +static void +_smart_disown(Evas_Object *obj) +{ + Box_Item *bi; + + bi = evas_object_data_get(obj, "e_box_data"); + if (!bi) return; + if (!bi->sd->items) + { + if (evas_object_visible_get(bi->sd->clip)) + evas_object_hide(bi->sd->clip); + } + evas_object_event_callback_del(obj, + EVAS_CALLBACK_FREE, + _smart_item_del_hook); + evas_object_smart_member_del(obj); + evas_object_clip_unset(obj); + evas_object_data_del(obj, "e_box_data"); + free(bi); +} + +static void +_smart_item_del_hook(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + _els_smart_box_unpack(obj); +} + +static void +_smart_reconfigure(Smart_Data *sd) +{ + Evas_Coord x, y, w, h, xx, yy; + Evas_List *l; + int minw, minh, wdif, hdif; + int count, expand; + + if (!sd->changed) return; + + x = sd->x; + y = sd->y; + w = sd->w; + h = sd->h; + + _smart_extents_calculate(sd); + minw = sd->min.w; + minh = sd->min.h; + count = evas_list_count(sd->items); + expand = 0; + if (w < minw) + { + x = x + ((w - minw) * (1.0 - sd->align.x)); + w = minw; + } + if (h < minh) + { + y = y + ((h - minh) * (1.0 - sd->align.y)); + h = minh; + } + for (l = sd->items; l; l = l->next) + { + Box_Item *bi; + Evas_Object *obj; + + obj = l->data; + bi = evas_object_data_get(obj, "e_box_data"); + if (bi) + { + if (sd->horizontal) + { + if (bi->expand_w) expand++; + } + else + { + if (bi->expand_h) expand++; + } + } + } + if (expand == 0) + { + if (sd->horizontal) + { + x += (double)(w - minw) * sd->align.x; + w = minw; + } + else + { + y += (double)(h - minh) * sd->align.y; + h = minh; + } + } + wdif = w - minw; + hdif = h - minh; + xx = x; + yy = y; + for (l = sd->items; l; l = l->next) + { + Box_Item *bi; + Evas_Object *obj; + + obj = l->data; + bi = evas_object_data_get(obj, "e_box_data"); + if (bi) + { + if (sd->horizontal) + { + if (sd->homogenous) + { + Evas_Coord ww, hh, ow, oh; + + ww = (w / (Evas_Coord)count); + hh = h; + ow = bi->min.w; + if (bi->fill_w) ow = ww; + if ((bi->max.w >= 0) && (bi->max.w < ow)) + ow = bi->max.w; + oh = bi->min.h; + if (bi->fill_h) oh = hh; + if ((bi->max.h >= 0) && (bi->max.h < oh)) + oh = bi->max.h; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * bi->align.x), + yy + (Evas_Coord)(((double)(hh - oh)) * bi->align.y)); + evas_object_resize(obj, ow, oh); + xx += ww; + } + else + { + Evas_Coord ww, hh, ow, oh; + + ww = bi->min.w; + if ((expand > 0) && (bi->expand_w)) + { + if (expand == 1) ow = wdif; + else ow = (w - minw) / expand; + wdif -= ow; + ww += ow; + } + hh = h; + ow = bi->min.w; + if (bi->fill_w) ow = ww; + if ((bi->max.w >= 0) && (bi->max.w < ow)) ow = bi->max.w; + oh = bi->min.h; + if (bi->fill_h) oh = hh; + if ((bi->max.h >= 0) && (bi->max.h < oh)) oh = bi->max.h; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * bi->align.x), + yy + (Evas_Coord)(((double)(hh - oh)) * bi->align.y)); + evas_object_resize(obj, ow, oh); + xx += ww; + } + } + else + { + if (sd->homogenous) + { + Evas_Coord ww, hh, ow, oh; + + ww = w; + hh = (h / (Evas_Coord)count); + ow = bi->min.w; + if (bi->fill_w) ow = ww; + if ((bi->max.w >= 0) && (bi->max.w < ow)) ow = bi->max.w; + oh = bi->min.h; + if (bi->fill_h) oh = hh; + if ((bi->max.h >= 0) && (bi->max.h < oh)) oh = bi->max.h; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * bi->align.x), + yy + (Evas_Coord)(((double)(hh - oh)) * bi->align.y)); + evas_object_resize(obj, ow, oh); + yy += hh; + } + else + { + Evas_Coord ww, hh, ow, oh; + + ww = w; + hh = bi->min.h; + if ((expand > 0) && (bi->expand_h)) + { + if (expand == 1) oh = hdif; + else oh = (h - minh) / expand; + hdif -= oh; + hh += oh; + } + ow = bi->min.w; + if (bi->fill_w) ow = ww; + if ((bi->max.w >= 0) && (bi->max.w < ow)) ow = bi->max.w; + oh = bi->min.h; + if (bi->fill_h) oh = hh; + if ((bi->max.h >= 0) && (bi->max.h < oh)) oh = bi->max.h; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * bi->align.x), + yy + (Evas_Coord)(((double)(hh - oh)) * bi->align.y)); + evas_object_resize(obj, ow, oh); + yy += hh; + } + } + } + } + sd->changed = 0; +} + +static void +_smart_extents_calculate(Smart_Data *sd) +{ + Evas_List *l; + int minw, minh; + + /* FIXME: need to calc max */ + sd->max.w = -1; /* max < 0 == unlimited */ + sd->max.h = -1; + + minw = 0; + minh = 0; + if (sd->homogenous) + { + for (l = sd->items; l; l = l->next) + { + Box_Item *bi; + Evas_Object *obj; + + obj = l->data; + bi = evas_object_data_get(obj, "e_box_data"); + if (bi) + { + if (minh < bi->min.h) minh = bi->min.h; + if (minw < bi->min.w) minw = bi->min.w; + } + } + if (sd->horizontal) + minw *= evas_list_count(sd->items); + else + minh *= evas_list_count(sd->items); + } + else + { + for (l = sd->items; l; l = l->next) + { + Box_Item *bi; + Evas_Object *obj; + + obj = l->data; + bi = evas_object_data_get(obj, "e_box_data"); + if (bi) + { + if (sd->horizontal) + { + if (minh < bi->min.h) minh = bi->min.h; + minw += bi->min.w; + } + else + { + if (minw < bi->min.w) minw = bi->min.w; + minh += bi->min.h; + } + } + } + } + sd->min.w = minw; + sd->min.h = minh; +} + +static void +_smart_init(void) +{ + if (_e_smart) return; + { + static const Evas_Smart_Class sc = + { + "e_box", + 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 + }; + _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 = obj; + sd->x = 0; + sd->y = 0; + sd->w = 0; + sd->h = 0; + sd->align.x = 0.5; + sd->align.y = 0.5; + sd->clip = evas_object_rectangle_add(evas_object_evas_get(obj)); + evas_object_smart_member_add(sd->clip, obj); + evas_object_move(sd->clip, -100004, -100004); + evas_object_resize(sd->clip, 200008, 200008); + evas_object_color_set(sd->clip, 255, 255, 255, 255); + evas_object_smart_data_set(obj, sd); +} + +static void +_smart_del(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + _els_smart_box_freeze(obj); + while (sd->items) + { + Evas_Object *child; + + child = sd->items->data; + _els_smart_box_unpack(child); + } + _els_smart_box_thaw(obj); + evas_object_del(sd->clip); + 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 ((x == sd->x) && (y == sd->y)) return; + { + Evas_List *l; + Evas_Coord dx, dy; + + dx = x - sd->x; + dy = y - sd->y; + for (l = sd->items; l; l = l->next) + { + Evas_Coord ox, oy; + + evas_object_geometry_get(l->data, &ox, &oy, NULL, NULL); + evas_object_move(l->data, ox + dx, oy + dy); + } + } + sd->x = x; + sd->y = y; +} + +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 ((w == sd->w) && (h == sd->h)) return; + sd->w = w; + sd->h = h; + sd->changed = 1; + _smart_reconfigure(sd); +} + +static void +_smart_show(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->items) evas_object_show(sd->clip); +} + +static void +_smart_hide(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + evas_object_hide(sd->clip); +} + +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->clip, 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->clip, 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->clip); +} diff --git a/src/lib/els_box.h b/src/lib/els_box.h new file mode 100644 index 000000000..cb185ab59 --- /dev/null +++ b/src/lib/els_box.h @@ -0,0 +1,14 @@ +Evas_Object *_els_smart_box_add (Evas *evas); +int _els_smart_box_freeze (Evas_Object *obj); +int _els_smart_box_thaw (Evas_Object *obj); +void _els_smart_box_orientation_set (Evas_Object *obj, int horizontal); +int _els_smart_box_orientation_get (Evas_Object *obj); +void _els_smart_box_homogenous_set (Evas_Object *obj, int homogenous); +int _els_smart_box_pack_start (Evas_Object *obj, Evas_Object *child); +int _els_smart_box_pack_end (Evas_Object *obj, Evas_Object *child); +int _els_smart_box_pack_before (Evas_Object *obj, Evas_Object *child, Evas_Object *before); +int _els_smart_box_pack_after (Evas_Object *obj, Evas_Object *child, Evas_Object *after); +void _els_smart_box_pack_options_set (Evas_Object *obj, int fill_w, int fill_h, int expand_w, int expand_h, double align_x, double align_y, Evas_Coord min_w, Evas_Coord min_h, Evas_Coord max_w, Evas_Coord max_h); +void _els_smart_box_unpack (Evas_Object *obj); +void _els_smart_box_min_size_get (Evas_Object *obj, Evas_Coord *minw, Evas_Coord *minh); +void _els_smart_box_max_size_get (Evas_Object *obj, Evas_Coord *maxw, Evas_Coord *maxh); diff --git a/src/lib/els_icon.c b/src/lib/els_icon.c new file mode 100644 index 000000000..49151b7df --- /dev/null +++ b/src/lib/els_icon.c @@ -0,0 +1,364 @@ +#include <Elementary.h> +#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; + unsigned char fill_inside : 1; + unsigned char scale_up : 1; + unsigned char scale_down : 1; +}; + +/* 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); + +/* 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); +} + +void +_els_smart_icon_file_key_set(Evas_Object *obj, const char *file, const char *key) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + /* smart code here */ + if (sd->size != 0) + evas_object_image_load_size_set(sd->obj, sd->size, sd->size); + evas_object_image_file_set(sd->obj, file, key); + _smart_reconfigure(sd); +} + +void +_els_smart_icon_file_edje_set(Evas_Object *obj, const char *file, const char *part) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + /* smart code here */ + if (sd->obj) evas_object_del(sd->obj); + sd->obj = edje_object_add(evas_object_evas_get(obj)); + edje_object_file_set(sd->obj, file, part); + evas_object_smart_member_add(sd->obj, obj); + _smart_reconfigure(sd); +} + +void +_els_smart_icon_smooth_scale_set(Evas_Object *obj, int smooth) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (!strcmp(evas_object_type_get(sd->obj), "edje")) + return; + evas_object_image_smooth_scale_set(sd->obj, smooth); +} + +void +_els_smart_icon_size_get(Evas_Object *obj, int *w, int *h) +{ + Smart_Data *sd; + int tw, th; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + 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, int 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); +} + +void +_els_smart_icon_scale_up_set(Evas_Object *obj, int 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); +} + +void +_els_smart_icon_scale_down_set(Evas_Object *obj, int 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); +} + +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 (!strcmp(evas_object_type_get(sd->obj), "edje")) + return; + evas_object_image_load_size_set(sd->obj, sd->size, sd->size); +} + +void +_els_smart_icon_scale_set(Evas_Object *obj, double scale) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + sd->scale = scale; + _smart_reconfigure(sd); +} + +/* local subsystem globals */ +static void +_smart_reconfigure(Smart_Data *sd) +{ + int iw, ih; + 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 + { + ih = 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 + }; + _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)); + sd->x = 0; + sd->y = 0; + sd->w = 0; + sd->h = 0; + sd->fill_inside = 1; + sd->scale_up = 1; + sd->scale_down = 1; + sd->size = 64; + sd->scale = 1.0; + evas_object_smart_member_add(sd->obj, obj); + evas_object_smart_data_set(obj, 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; + 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; + 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); +} diff --git a/src/lib/els_icon.h b/src/lib/els_icon.h new file mode 100644 index 000000000..74cdb12fe --- /dev/null +++ b/src/lib/els_icon.h @@ -0,0 +1,10 @@ +Evas_Object *_els_smart_icon_add (Evas *evas); +void _els_smart_icon_file_key_set (Evas_Object *obj, const char *file, const char *key); +void _els_smart_icon_file_edje_set (Evas_Object *obj, const char *file, const char *part); +void _els_smart_icon_smooth_scale_set (Evas_Object *obj, int smooth); +void _els_smart_icon_size_get (Evas_Object *obj, int *w, int *h); +void _els_smart_icon_fill_inside_set (Evas_Object *obj, int fill_inside); +void _els_smart_icon_scale_up_set (Evas_Object *obj, int scale_up); +void _els_smart_icon_scale_down_set (Evas_Object *obj, int scale_down); +void _els_smart_icon_scale_size_set (Evas_Object *obj, int size); +void _els_smart_icon_scale_set (Evas_Object *obj, double scale); diff --git a/src/lib/els_pan.c b/src/lib/els_pan.c new file mode 100644 index 000000000..38d46de42 --- /dev/null +++ b/src/lib/els_pan.c @@ -0,0 +1,270 @@ +#include <Elementary.h> +#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(sd->child_obj, EVAS_CALLBACK_FREE, _smart_child_del_hook); + evas_object_event_callback_del(sd->child_obj, EVAS_CALLBACK_RESIZE, _smart_child_resize_hook); + 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_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, Evas_Object *obj, void *event_info) +{ + 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, Evas_Object *obj, void *event_info) +{ + 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 + }; + _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 000000000..a2ce00c92 --- /dev/null +++ b/src/lib/els_pan.h @@ -0,0 +1,7 @@ +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_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 000000000..7450d8be0 --- /dev/null +++ b/src/lib/els_scroller.c @@ -0,0 +1,1052 @@ +#include <Elementary.h> +#include "elm_priv.h" + +#define SMART_NAME "elm_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; + +struct _Smart_Data +{ + Evas_Coord x, y, w, h; + + Evas_Object *smart_obj; + Evas_Object *child_obj; + Evas_Object *pan_obj; + Evas_Object *edje_obj; + Evas_Object *event_obj; + + Elm_Smart_Scroller_Policy hbar_flags, vbar_flags; + + struct { + Evas_Coord x, y; + Evas_Coord sx, sy; + Evas_Coord dx, dy; + struct { + Evas_Coord x, y; + double timestamp; + } history[20]; + double anim_start; + Ecore_Animator *momentum_animator; + Evas_Coord locked_x, locked_y; + unsigned char now : 1; + unsigned char dragged : 1; + unsigned char dir_x : 1; + unsigned char dir_y : 1; + unsigned char locked : 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 (*child_size_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y); + } pan_func; + + + unsigned char hbar_visible : 1; + unsigned char vbar_visible : 1; + unsigned char extern_pan : 1; + unsigned char one_dir_at_a_time : 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 int _smart_momentum_animator(void *data); +static void _smart_event_mouse_up(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _smart_event_mouse_move(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _smart_event_key_down(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _smart_edje_drag_v(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(sd->child_obj, EVAS_CALLBACK_FREE, _smart_child_del_hook); + } + + sd->child_obj = child; + 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.child_size_get = _elm_smart_pan_child_size_get; + + evas_object_event_callback_add(child, EVAS_CALLBACK_FREE, _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_child_size_get) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y)) +{ + API_ENTRY return; + + elm_smart_scroller_child_set(obj, NULL); + 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.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); +} + +void +elm_smart_scroller_child_pos_set(Evas_Object *obj, Evas_Coord x, Evas_Coord y) +{ + Evas_Coord mx = 0, my = 0, px, py; + double vx, vy; + + API_ENTRY return; + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + if (mx > 0) vx = (double)x / (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 / (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); + 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"); +} + +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); +} + +void +elm_smart_scroller_child_region_show(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; + + API_ENTRY return; + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + 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; + elm_smart_scroller_child_pos_set(obj, nx, ny); +} + +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; + _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, Evas_Bool single_dir) +{ + API_ENTRY return; + sd->one_dir_at_a_time = single_dir; +} + +Evas_Bool +elm_smart_scroller_single_dir_get(Evas_Object *obj) +{ + API_ENTRY return 0; + return sd->one_dir_at_a_time; +} + +/* local subsystem functions */ +static void +_smart_edje_drag_v(void *data, Evas_Object *obj, const char *emission, const char *source) +{ + Smart_Data *sd; + + sd = data; + _smart_scrollbar_read(sd); +} + +static void +_smart_edje_drag_h(void *data, Evas_Object *obj, const char *emission, const char *source) +{ + Smart_Data *sd; + + sd = data; + _smart_scrollbar_read(sd); +} + +static void +_smart_child_del_hook(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + 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, void *event_info) +{ + Evas_Coord w, h; + Smart_Data *sd; + + sd = data; + 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); + } +} + +static void +_smart_pan_pan_changed_hook(void *data, Evas_Object *obj, void *event_info) +{ + Evas_Coord x, y; + Smart_Data *sd; + + sd = data; + sd->pan_func.get(sd->pan_obj, &x, &y); + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); +} + +static void +_smart_event_wheel(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Wheel *ev; + Smart_Data *sd; + Evas_Coord x = 0, y = 0; + + sd = data; + ev = event_info; + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + y += ev->z * sd->step.y; + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); +} + +static void +_smart_event_mouse_down(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Down *ev; + Smart_Data *sd; + Evas_Coord x = 0, y = 0; + + sd = data; + ev = event_info; + if (_elm_config->thumbscroll_enable) + { + if (sd->down.momentum_animator) + { + ecore_animator_del(sd->down.momentum_animator); + sd->down.momentum_animator = NULL; + } + 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); + sd->down.history[0].timestamp = ecore_time_get(); + sd->down.history[0].x = ev->canvas.x; + sd->down.history[0].y = ev->canvas.y; + } + } +} + +static int +_smart_momentum_animator(void *data) +{ + Smart_Data *sd; + double t, dt, p; + Evas_Coord x, y, dx, dy; + + sd = data; + t = ecore_time_get(); + dt = t - sd->down.anim_start; + if (dt >= 0.0) + { + dt = dt / _elm_config->thumbscroll_friction; + if (dt > 1.0) dt = 1.0; + p = 1.0 - ((1.0 - dt) * (1.0 - dt) * (1.0 - dt)); + dx = (sd->down.dx * _elm_config->thumbscroll_friction * p); + dy = (sd->down.dy * _elm_config->thumbscroll_friction * p); + x = sd->down.sx - dx; + y = sd->down.sy - dy; + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + if (dt >= 1.0) + { + sd->down.momentum_animator = NULL; + return 0; + } + } + return 1; +} + +static void +_smart_event_mouse_up(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Down *ev; + Smart_Data *sd; + Evas_Coord x = 0, y = 0; + + sd = data; + ev = event_info; + if (_elm_config->thumbscroll_enable) + { + if (ev->button == 1) + { + x = ev->canvas.x - sd->down.x; + y = ev->canvas.y - sd->down.y; + if (sd->down.dragged) + { + double t, at, dt; + int i; + Evas_Coord ax, ay, dx, dy, vel; + + t = ecore_time_get(); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + ax = ev->canvas.x; + ay = ev->canvas.y; + at = 0.0; + for (i = 0; i < 20; i++) + { + dt = t - sd->down.history[i].timestamp; + if (dt > 0.2) break; + 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_threshhold)) + { + if (!sd->down.momentum_animator) + sd->down.momentum_animator = ecore_animator_add(_smart_momentum_animator, sd); + sd->down.dx = ((double)dx / at); + sd->down.dy = ((double)dy / at); + sd->down.anim_start = t; + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + sd->down.sx = x; + sd->down.sy = y; + } + } + evas_event_feed_hold(e, 0, ev->timestamp, ev->data); + } + sd->down.dragged = 0; + sd->down.now = 0; + } + } +} + +static void +_smart_event_mouse_move(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + Evas_Event_Mouse_Move *ev; + Smart_Data *sd; + Evas_Coord x = 0, y = 0; + + sd = data; + ev = event_info; + if (_elm_config->thumbscroll_enable) + { + if (sd->down.now) + { + memmove(&(sd->down.history[1]), &(sd->down.history[0]), + sizeof(sd->down.history[0]) * 19); + sd->down.history[0].timestamp = ecore_time_get(); + sd->down.history[0].x = ev->cur.canvas.x; + sd->down.history[0].y = ev->cur.canvas.y; + + x = ev->cur.canvas.x - sd->down.x; + if (x < 0) x = -x; + y = ev->cur.canvas.y - sd->down.y; + if (y < 0) y = -y; + if ((sd->one_dir_at_a_time) && + (!sd->down.dir_x) && (!sd->down.dir_y)) + { + if (x > y) + { + if (x > _elm_config->thumbscroll_threshhold) + { + sd->down.dir_x = 1; + sd->down.dir_y = 0; + } + } + else + { + if (y > _elm_config->thumbscroll_threshhold) + { + sd->down.dir_x = 0; + sd->down.dir_y = 1; + } + } + } + if ((sd->down.dragged) || + (((x * x) + (y * y)) > + (_elm_config->thumbscroll_threshhold * + _elm_config->thumbscroll_threshhold))) + { + if (!sd->down.dragged) + evas_event_feed_hold(e, 1, ev->timestamp, ev->data); + ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD; + sd->down.dragged = 1; + x = sd->down.sx - (ev->cur.canvas.x - sd->down.x); + y = sd->down.sy - (ev->cur.canvas.y - sd->down.y); + 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) y = sd->down.locked_y; + else x = sd->down.locked_x; + } + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); + } + } + } +} + +static void +_smart_event_key_down(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + Evas_Event_Key_Down *ev; + Smart_Data *sd; + Evas_Coord x = 0, y = 0, vw = 0, vh = 0, mx = 0, my = 0; + + sd = data; + ev = event_info; + elm_smart_scroller_child_pos_get(sd->smart_obj, &x, &y); + sd->pan_func.max_get(sd->pan_obj, &mx, &my); + evas_object_geometry_get(sd->pan_obj, NULL, NULL, &vw, &vh); + if (!strcmp(ev->keyname, "Left")) + x -= sd->step.x; + else if (!strcmp(ev->keyname, "Right")) + x += sd->step.x; + else if (!strcmp(ev->keyname, "Up")) + y -= sd->step.y; + else if (!strcmp(ev->keyname, "Home")) + y = 0; + else if (!strcmp(ev->keyname, "End")) + y = my; + else if (!strcmp(ev->keyname, "Down")) + y += sd->step.y; + else if (!strcmp(ev->keyname, "Prior")) + { + if (sd->page.y < 0) + y -= -(sd->page.y * vh) / 100; + else + y -= sd->page.y; + } + else if (!strcmp(ev->keyname, "Next")) + { + if (sd->page.y < 0) + y += -(sd->page.y * vh) / 100; + else + y += sd->page.y; + } + elm_smart_scroller_child_pos_set(sd->smart_obj, x, y); +} + +static void +_smart_scrollbar_read(Smart_Data *sd) +{ + Evas_Coord x, y, mx = 0, my = 0, px, py; + 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); + x = vx * (double)mx; + y = vy * (double)my; + 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, py; + + 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.get(sd->pan_obj, &px, &py); + sd->pan_func.set(sd->pan_obj, 0, 0); + if ((px != 0) || (py != 0)) + 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 w, h, vw, vh; + + w = sd->child.w; + 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_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); + } + 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, h, vw, vh; + + w = sd->child.w; + h = sd->child.h; + 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_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); + } + 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; + 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); + x = vx * mx; + y = vy * my; + + 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); + 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, py; + + 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.get(sd->pan_obj, &px, &py); + sd->pan_func.set(sd->pan_obj, 0, 0); + if ((px != 0) || (py != 0)) + 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; + + evas_object_event_callback_add(obj, EVAS_CALLBACK_KEY_DOWN, _smart_event_key_down, sd); + evas_object_propagate_events_set(obj, 0); + + o = edje_object_add(evas_object_evas_get(obj)); + sd->edje_obj = o; + _elm_theme_set(o, "scroller", "scroller"); + edje_object_signal_callback_add(o, "drag*", "elm.dragable.vbar", _smart_edje_drag_v, sd); + edje_object_signal_callback_add(o, "drag*", "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.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.momentum_animator) ecore_animator_del(sd->down.momentum_animator); + 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) +{ + 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 + }; + _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 000000000..155c5dc92 --- /dev/null +++ b/src/lib/els_scroller.h @@ -0,0 +1,25 @@ +typedef enum _Elm_Smart_Scroller_Policy +{ + ELM_SMART_SCROLLER_POLICY_OFF, + ELM_SMART_SCROLLER_POLICY_ON, + ELM_SMART_SCROLLER_POLICY_AUTO +} +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_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_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, Evas_Bool single_dir); +Evas_Bool elm_smart_scroller_single_dir_get (Evas_Object *obj); diff --git a/src/lib/els_table.c b/src/lib/els_table.c new file mode 100644 index 000000000..17921bb4d --- /dev/null +++ b/src/lib/els_table.c @@ -0,0 +1,953 @@ +#include <Elementary.h> +#include "elm_priv.h" + +typedef struct _Smart_Data Smart_Data; +typedef struct _Table_Item Table_Item; + +struct _Smart_Data +{ + Evas_Coord x, y, w, h; + Evas_Object *obj; + Evas_Object *clip; + int frozen; + unsigned char changed : 1; + unsigned char homogenous : 1; + Evas_List *items; + struct { + Evas_Coord w, h; + } min, max; + struct { + double x, y; + } align; + struct { + int cols, rows; + } size; +}; + +struct _Table_Item +{ + Smart_Data *sd; + int col, row, colspan, rowspan; + unsigned char fill_w : 1; + unsigned char fill_h : 1; + unsigned char expand_w : 1; + unsigned char expand_h : 1; + struct { + Evas_Coord w, h; + } min, max; + struct { + double x, y; + } align; + Evas_Object *obj; +}; + +/* local subsystem functions */ +static Table_Item *_smart_adopt(Smart_Data *sd, Evas_Object *obj); +static void _smart_disown(Evas_Object *obj); +static void _smart_item_del_hook(void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _smart_reconfigure(Smart_Data *sd); +static void _smart_extents_calcuate(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); + +/* local subsystem globals */ +static Evas_Smart *_e_smart = NULL; + +/* externally accessible functions */ +Evas_Object * +_els_smart_table_add(Evas *evas) +{ + _smart_init(); + return evas_object_smart_add(evas, _e_smart); +} + +int +_els_smart_table_freeze(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + sd->frozen++; + return sd->frozen; +} + +int +_els_smart_table_thaw(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + sd->frozen--; + if (sd->frozen <= 0) _smart_reconfigure(sd); + return sd->frozen; +} + +void +_els_smart_table_homogenous_set(Evas_Object *obj, int homogenous) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (sd->homogenous == homogenous) return; + sd->homogenous = homogenous; + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); +} + +void +_els_smart_table_pack(Evas_Object *obj, Evas_Object *child, int col, int row, int colspan, int rowspan) +{ + Smart_Data *sd; + Table_Item *ti; + + sd = evas_object_smart_data_get(obj); + _smart_adopt(sd, child); + sd->items = evas_list_append(sd->items, child); + ti = evas_object_data_get(child, "e_table_data"); + if (ti) + { + ti->col = col; + ti->row = row; + ti->colspan = colspan; + ti->rowspan = rowspan; + if (sd->size.cols < (col + colspan)) sd->size.cols = col + colspan; + if (sd->size.rows < (row + rowspan)) sd->size.rows = row + rowspan; + } + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); +} + +void +_els_smart_table_pack_options_set(Evas_Object *obj, int fill_w, int fill_h, int expand_w, int expand_h, double align_x, double align_y, Evas_Coord min_w, Evas_Coord min_h, Evas_Coord max_w, Evas_Coord max_h) +{ + Table_Item *ti; + + ti = evas_object_data_get(obj, "e_table_data"); + if (!ti) return; + ti->fill_w = fill_w; + ti->fill_h = fill_h; + ti->expand_w = expand_w; + ti->expand_h = expand_h; + ti->align.x = align_x; + ti->align.y = align_y; + ti->min.w = min_w; + ti->min.h = min_h; + ti->max.w = max_w; + ti->max.h = max_h; + ti->sd->changed = 1; + if (ti->sd->frozen <= 0) _smart_reconfigure(ti->sd); +} + +void +_els_smart_table_unpack(Evas_Object *obj) +{ + Table_Item *ti; + Smart_Data *sd; + + ti = evas_object_data_get(obj, "e_table_data"); + if (!ti) return; + sd = ti->sd; + sd->items = evas_list_remove(sd->items, obj); + _smart_disown(obj); + sd->changed = 1; + if (sd->frozen <= 0) _smart_reconfigure(sd); +} + +void +_els_smart_table_col_row_size_get(Evas_Object *obj, int *cols, int *rows) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (sd->changed) _smart_extents_calcuate(sd); + if (cols) *cols = sd->size.cols; + if (rows) *rows = sd->size.rows; +} + +void +_els_smart_table_min_size_get(Evas_Object *obj, Evas_Coord *minw, Evas_Coord *minh) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (sd->changed) _smart_extents_calcuate(sd); + if (minw) *minw = sd->min.w; + if (minh) *minh = sd->min.h; +} + +void +_els_smart_table_max_size_get(Evas_Object *obj, Evas_Coord *maxw, Evas_Coord *maxh) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (sd->changed) _smart_extents_calcuate(sd); + if (maxw) *maxw = sd->max.w; + if (maxh) *maxh = sd->max.h; +} + +/* local subsystem functions */ +static Table_Item * +_smart_adopt(Smart_Data *sd, Evas_Object *obj) +{ + Table_Item *ti; + + ti = calloc(1, sizeof(Table_Item)); + if (!ti) return NULL; + ti->sd = sd; + ti->obj = obj; + /* defaults */ + ti->col = 0; + ti->row = 0; + ti->colspan = 1; + ti->rowspan = 1; + ti->fill_w = 0; + ti->fill_h = 0; + ti->expand_w = 0; + ti->expand_h = 0; + ti->align.x = 0.5; + ti->align.y = 0.5; + ti->min.w = 0; + ti->min.h = 0; + ti->max.w = 0; + ti->max.h = 0; + evas_object_clip_set(obj, sd->clip); + evas_object_stack_above(obj, sd->obj); + evas_object_smart_member_add(obj, ti->sd->obj); + evas_object_data_set(obj, "e_table_data", ti); + evas_object_event_callback_add(obj, EVAS_CALLBACK_FREE, + _smart_item_del_hook, NULL); + evas_object_stack_below(obj, sd->obj); + if ((!evas_object_visible_get(sd->clip)) && + (evas_object_visible_get(sd->obj))) + evas_object_show(sd->clip); + return ti; +} + +static void +_smart_disown(Evas_Object *obj) +{ + Table_Item *ti; + + ti = evas_object_data_get(obj, "e_table_data"); + if (!ti) return; + if (!ti->sd->items) + { + if (evas_object_visible_get(ti->sd->clip)) + evas_object_hide(ti->sd->clip); + } + evas_object_event_callback_del(obj, + EVAS_CALLBACK_FREE, + _smart_item_del_hook); + evas_object_smart_member_del(obj); + evas_object_data_del(obj, "e_table_data"); + free(ti); +} + +static void +_smart_item_del_hook(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + _els_smart_table_unpack(obj); +} + +static void +_smart_reconfigure(Smart_Data *sd) +{ + Evas_Coord x, y, w, h, xx, yy; + Evas_List *l; + int minw, minh, expandw, expandh; + + if (!sd->changed) return; + + x = sd->x; + y = sd->y; + w = sd->w; + h = sd->h; + + _smart_extents_calcuate(sd); + + minw = sd->min.w; + minh = sd->min.h; + expandw = 0; + expandh = 0; + if (w < minw) + { + x = x + ((w - minw) * (1.0 - sd->align.x)); + w = minw; + } + if (h < minh) + { + y = y + ((h - minh) * (1.0 - sd->align.y)); + h = minh; + } + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + if (ti->expand_w) expandw++; + if (ti->expand_h) expandh++; + } + if (expandw == 0) + { + x += (w - minw) / 2; + w = minw; + } + if (expandh == 0) + { + y += (h - minh) / 2; + h = minh; + } + x = sd->x; + y = sd->y; + if (sd->homogenous) + { + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + Evas_Coord ww, hh, ow, oh; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + + xx = x + ((ti->col) * (w / (Evas_Coord)sd->size.cols)); + yy = y + ((ti->row) * (h / (Evas_Coord)sd->size.rows)); + ww = ((w / (Evas_Coord)sd->size.cols) * (ti->colspan)); + hh = ((h / (Evas_Coord)sd->size.rows) * (ti->rowspan)); + ow = ti->min.w; + if (ti->expand_w) ow = ww; + if ((ti->max.w >= 0) && (ti->max.w < ow)) ow = ti->max.w; + oh = ti->min.h; + if (ti->expand_h) oh = hh; + if ((ti->max.h >= 0) && (ti->max.h < oh)) oh = ti->max.h; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * ti->align.x), + yy + (Evas_Coord)(((double)(hh - oh)) * ti->align.y)); + evas_object_resize(obj, ow, oh); + } + } + else + { + int i, ex, tot, need, num, dif, left, nx; + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + if (sd->size.cols < (ti->col + ti->colspan)) + sd->size.cols = ti->col + ti->colspan; + if (sd->size.rows < (ti->row + ti->rowspan)) + sd->size.rows = ti->row + ti->rowspan; + } + if ((sd->size.cols > 0) && (sd->size.rows > 0)) + { + int *cols, *rows, *colsx, *rowsx; + + cols = calloc(sd->size.cols, sizeof(int)); + rows = calloc(sd->size.rows, sizeof(int)); + colsx = calloc(sd->size.cols, sizeof(int)); + rowsx = calloc(sd->size.rows, sizeof(int)); + + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + for (i = ti->col; i < (ti->col + ti->colspan); i++) + colsx[i] |= ti->expand_w; + for (i = ti->row; i < (ti->row + ti->rowspan); i++) + rowsx[i] |= ti->expand_h; + } + + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + + /* handle horizontal */ + ex = 0; + tot = 0; + num = ti->colspan; + for (i = ti->col; i < (ti->col + num); i++) + { + if (colsx[i]) ex++; + tot += cols[i]; + } + need = ti->min.w; + if (tot < need) + { + dif = need - tot; + left = dif; + if (ex == 0) + { + nx = num; + for (i = ti->col; i < (ti->col + num); i++) + { + if (nx > 1) + { + cols[i] += dif / num; + left -= dif / num; + } + else + { + cols[i] += left; + left = 0; + } + nx--; + } + } + else + { + nx = ex; + for (i = ti->col; i < (ti->col + num); i++) + { + if (colsx[i]) + { + if (nx > 1) + { + cols[i] += dif / ex; + left -= dif / ex; + } + else + { + cols[i] += left; + left = 0; + } + nx--; + } + } + } + } + + /* handle vertical */ + ex = 0; + tot = 0; + num = ti->rowspan; + for (i = ti->row; i < (ti->row + num); i++) + { + if (rowsx[i]) ex++; + tot += rows[i]; + } + need = ti->min.h; + if (tot < need) + { + dif = need - tot; + left = dif; + if (ex == 0) + { + nx = num; + for (i = ti->row; i < (ti->row + num); i++) + { + if (nx > 1) + { + rows[i] += dif / num; + left -= dif / num; + } + else + { + rows[i] += left; + left = 0; + } + nx--; + } + } + else + { + nx = ex; + for (i = ti->row; i < (ti->row + num); i++) + { + if (rowsx[i]) + { + if (nx > 1) + { + rows[i] += dif / ex; + left -= dif / ex; + } + else + { + rows[i] += left; + left = 0; + } + nx--; + } + } + } + } + } + + ex = 0; + for (i = 0; i < sd->size.cols; i++) { if (colsx[i]) ex++; } + tot = 0; + for (i = 0; i < sd->size.cols; i++) tot += cols[i]; + dif = w - tot; + if ((ex > 0) && (dif > 0)) + { + int exl; + + left = dif; + exl = ex; + for (i = 0; i < sd->size.cols; i++) + { + if (colsx[i]) + { + if (exl == 1) + { + cols[i] += left; + exl--; + left = 0; + } + else + { + cols[i] += dif / ex; + exl--; + left -= dif / ex; + } + } + } + } + + ex = 0; + for (i = 0; i < sd->size.rows; i++) { if (rowsx[i]) ex++; } + tot = 0; + for (i = 0; i < sd->size.rows; i++) tot += rows[i]; + dif = h - tot; + if ((ex > 0) && (dif > 0)) + { + int exl; + + left = dif; + exl = ex; + for (i = 0; i < sd->size.rows; i++) + { + if (rowsx[i]) + { + if (exl == 1) + { + rows[i] += left; + exl--; + left = 0; + } + else + { + rows[i] += dif / ex; + exl--; + left -= dif / ex; + } + } + } + } + + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + Evas_Coord ww, hh, ow, oh, i; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + + xx = x; + for (i = 0; i < ti->col; i++) xx += cols[i]; + ww = 0; + for (i = ti->col; i < (ti->col + ti->colspan); i++) ww += cols[i]; + yy = y; + for (i = 0; i < ti->row; i++) yy += rows[i]; + hh = 0; + for (i = ti->row; i < (ti->row + ti->rowspan); i++) hh += rows[i]; + + ow = ti->min.w; + if (ti->fill_w) ow = ww; + if ((ti->max.w >= 0) && (ti->max.w < ow)) ow = ti->max.w; + oh = ti->min.h; + if (ti->fill_h) oh = hh; + if ((ti->max.h >= 0) && (ti->max.h < oh)) oh = ti->max.h; + evas_object_move(obj, + xx + (Evas_Coord)(((double)(ww - ow)) * ti->align.x), + yy + (Evas_Coord)(((double)(hh - oh)) * ti->align.y)); + evas_object_resize(obj, ow, oh); + } + free(rows); + free(cols); + free(rowsx); + free(colsx); + } + } + sd->changed = 0; +} + +static void +_smart_extents_calcuate(Smart_Data *sd) +{ + Evas_List *l; + int minw, minh; + + sd->max.w = -1; /* max < 0 == unlimited */ + sd->max.h = -1; + sd->size.cols = 0; + sd->size.rows = 0; + + minw = 0; + minh = 0; + if (sd->homogenous) + { + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + int mw, mh; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + if (sd->size.cols < (ti->col + ti->colspan)) + sd->size.cols = ti->col + ti->colspan; + if (sd->size.rows < (ti->row + ti->rowspan)) + sd->size.rows = ti->row + ti->rowspan; + mw = (ti->min.w + (ti->colspan - 1)) / ti->colspan; + mh = (ti->min.h + (ti->rowspan - 1)) / ti->rowspan; + if (minw < mw) minw = mw; + if (minh < mh) minh = mh; + } + minw *= sd->size.cols; + minh *= sd->size.rows; + } + else + { + int i, ex, tot, need, num, dif, left, nx; + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + if (sd->size.cols < (ti->col + ti->colspan)) + sd->size.cols = ti->col + ti->colspan; + if (sd->size.rows < (ti->row + ti->rowspan)) + sd->size.rows = ti->row + ti->rowspan; + } + if ((sd->size.cols > 0) && (sd->size.rows > 0)) + { + int *cols, *rows, *colsx, *rowsx; + + cols = calloc(sd->size.cols, sizeof(int)); + rows = calloc(sd->size.rows, sizeof(int)); + colsx = calloc(sd->size.cols, sizeof(int)); + rowsx = calloc(sd->size.rows, sizeof(int)); + + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + for (i = ti->col; i < (ti->col + ti->colspan); i++) + colsx[i] |= ti->expand_w; + for (i = ti->row; i < (ti->row + ti->rowspan); i++) + rowsx[i] |= ti->expand_h; + } + + for (l = sd->items; l; l = l->next) + { + Table_Item *ti; + Evas_Object *obj; + + obj = l->data; + ti = evas_object_data_get(obj, "e_table_data"); + + /* handle horizontal */ + ex = 0; + tot = 0; + num = ti->colspan; + for (i = ti->col; i < (ti->col + num); i++) + { + if (colsx[i]) ex++; + tot += cols[i]; + } + need = ti->min.w; + if (tot < need) + { + dif = need - tot; + left = dif; + if (ex == 0) + { + nx = num; + for (i = ti->col; i < (ti->col + num); i++) + { + if (nx > 1) + { + cols[i] += dif / num; + left -= dif / num; + } + else + { + cols[i] += left; + left = 0; + } + nx--; + } + } + else + { + nx = ex; + for (i = ti->col; i < (ti->col + num); i++) + { + if (colsx[i]) + { + if (nx > 1) + { + cols[i] += dif / ex; + left -= dif / ex; + } + else + { + cols[i] += left; + left = 0; + } + nx--; + } + } + } + } + + /* handle vertical */ + ex = 0; + tot = 0; + num = ti->rowspan; + for (i = ti->row; i < (ti->row + num); i++) + { + if (rowsx[i]) ex++; + tot += rows[i]; + } + need = ti->min.h; + if (tot < need) + { + dif = need - tot; + left = dif; + if (ex == 0) + { + nx = num; + for (i = ti->row; i < (ti->row + num); i++) + { + if (nx > 1) + { + rows[i] += dif / num; + left -= dif / num; + } + else + { + rows[i] += left; + left = 0; + } + nx--; + } + } + else + { + nx = ex; + for (i = ti->row; i < (ti->row + num); i++) + { + if (rowsx[i]) + { + if (nx > 1) + { + rows[i] += dif / ex; + left -= dif / ex; + } + else + { + rows[i] += left; + left = 0; + } + nx--; + } + } + } + } + } + for (i = 0; i < sd->size.cols; i++) minw += cols[i]; + for (i = 0; i < sd->size.rows; i++) minh += rows[i]; + free(rows); + free(cols); + free(rowsx); + free(colsx); + } + } + sd->min.w = minw; + sd->min.h = minh; +} + +static void +_smart_init(void) +{ + if (_e_smart) return; + { + static const Evas_Smart_Class sc = + { + "e_table", + 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 + }; + _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 = obj; + sd->x = 0; + sd->y = 0; + sd->w = 0; + sd->h = 0; + sd->clip = evas_object_rectangle_add(evas_object_evas_get(obj)); + evas_object_smart_member_add(sd->clip, obj); + evas_object_move(sd->clip, -100002, -100002); + evas_object_resize(sd->clip, 200004, 200004); + evas_object_color_set(sd->clip, 255, 255, 255, 255); + evas_object_smart_data_set(obj, sd); +} + +static void +_smart_del(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + _els_smart_table_freeze(obj); + while (sd->items) + { + Evas_Object *child; + + child = sd->items->data; + _els_smart_table_unpack(child); + } + _els_smart_table_thaw(obj); + evas_object_del(sd->clip); + 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 ((x == sd->x) && (y == sd->y)) return; + if ((x == sd->x) && (y == sd->y)) return; + { + Evas_List *l; + Evas_Coord dx, dy; + + dx = x - sd->x; + dy = y - sd->y; + for (l = sd->items; l; l = l->next) + { + Evas_Coord ox, oy; + + evas_object_geometry_get(l->data, &ox, &oy, NULL, NULL); + evas_object_move(l->data, ox + dx, oy + dy); + } + } + sd->x = x; + sd->y = y; +} + +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 ((w == sd->w) && (h == sd->h)) return; + sd->w = w; + sd->h = h; + sd->changed = 1; + _smart_reconfigure(sd); +} + +static void +_smart_show(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + if (sd->items) evas_object_show(sd->clip); +} + +static void +_smart_hide(Evas_Object *obj) +{ + Smart_Data *sd; + + sd = evas_object_smart_data_get(obj); + if (!sd) return; + evas_object_hide(sd->clip); +} + +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->clip, 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->clip, 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->clip); +} diff --git a/src/lib/els_table.h b/src/lib/els_table.h new file mode 100644 index 000000000..c760b36fe --- /dev/null +++ b/src/lib/els_table.h @@ -0,0 +1,10 @@ +Evas_Object *_els_smart_table_add (Evas *evas); +int _els_smart_table_freeze (Evas_Object *obj); +int _els_smart_table_thaw (Evas_Object *obj); +void _els_smart_table_homogenous_set (Evas_Object *obj, int homogenous); +void _els_smart_table_pack (Evas_Object *obj, Evas_Object *child, int col, int row, int colspan, int rowspan); +void _els_smart_table_pack_options_set (Evas_Object *obj, int fill_w, int fill_h, int expand_w, int expand_h, double align_x, double align_y, Evas_Coord min_w, Evas_Coord min_h, Evas_Coord max_w, Evas_Coord max_h); +void _els_smart_table_unpack (Evas_Object *obj); +void _els_smart_table_col_row_size_get (Evas_Object *obj, int *cols, int *rows); +void _els_smart_table_min_size_get (Evas_Object *obj, Evas_Coord *minw, Evas_Coord *minh); +void _els_smart_table_max_size_get (Evas_Object *obj, Evas_Coord *maxw, Evas_Coord *maxh); |