add progressbar including slider and info of progress time 27/43027/2
authorMinkyu Kang <mk7.kang@samsung.com>
Tue, 7 Jul 2015 06:31:41 +0000 (15:31 +0900)
committerMinkyu Kang <mk7.kang@samsung.com>
Tue, 7 Jul 2015 06:59:35 +0000 (15:59 +0900)
the progressbar is including slider widget and progress time texts.
timer and progress info codes are moved to progressbar.

Change-Id: Id557c4996a8cfdde2ed6a457b209bcd0511fb135
Signed-off-by: Minkyu Kang <mk7.kang@samsung.com>
12 files changed:
CMakeLists.txt
include/define.h
include/util/progressbar.h [new file with mode: 0644]
include/util/util.h
include/view/viewer.h
res/edc/mediahub-theme.edc
res/edc/view/viewer.edc
res/edc/widgets/button.edc
res/edc/widgets/slider.edc [new file with mode: 0644]
src/util/progressbar.c [new file with mode: 0644]
src/util/util.c
src/view/viewer.c

index cba373b..08e5efd 100644 (file)
@@ -59,6 +59,7 @@ src/util/listmgr.c
 src/util/timeout_handler.c
 src/util/util.c
 src/util/playermgr.c
+src/util/progressbar.c
 src/data/mediadata.c
 )
 
index 6ecf61b..1b4651b 100644 (file)
 #define COLOR_TEXT_FOCUS 255 255 255 255
 #define COLOR_TEXT_SELECTED 64 136 211 255
 #define COLOR_TEXT_DISABLED 87 87 87 128
-#define COLOR_BTN_FOCUS 0 119 246 255
-#define COLOR_BTN_SELECTED 64 136 211 255
 #define COLOR_ITEM_BG 56 55 59 255
 #define COLOR_ITEM_FOCUS 0 119 246 255
 #define COLOR_ITEM_FOCUS_0 0 119 246 0
+#define COLOR_ITEM_SELECTED 64 136 211 255
 
 /* part */
 #define PART_ELM_TEXT_TITLE "elm.text.title"
diff --git a/include/util/progressbar.h b/include/util/progressbar.h
new file mode 100644 (file)
index 0000000..c93a87e
--- /dev/null
@@ -0,0 +1,44 @@
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the License);
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an AS IS BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef __AIR_MEDIAHUB_PROGRESSBAR_H__
+#define __AIR_MEDIAHUB_PROGRESSBAR_H__
+
+struct progressbar;
+
+struct progressbar_ops {
+       int (*get_value)(void *data);
+       int (*set_value)(void *data);
+};
+
+struct progressbar *progressbar_create(Evas_Object *base);
+void progressbar_destroy(struct progressbar *m);
+
+void progressbar_set_parts(struct progressbar *m, const char *slider,
+               const char *total, const char *progress, const char *separator);
+void progressbar_set_ops(struct progressbar *m,
+               struct progressbar_ops *ops, void *data);
+void progressbar_reset(struct progressbar *m, int position, int duration);
+
+void progressbar_show(struct progressbar *m);
+void progressbar_hide(struct progressbar *m);
+
+void progressbar_start(struct progressbar *m);
+void progressbar_stop(struct progressbar *m);
+void progressbar_pause(struct progressbar *m);
+void progressbar_resume(struct progressbar *m);
+
+#endif
index 59aefce..0d624af 100644 (file)
@@ -22,4 +22,7 @@ Evas_Object *util_add_gengrid(Evas_Object *base,
                        int item_size_x, int item_size_y);
 Evas_Object *util_add_scroller(Evas_Object *base);
 
+void util_time_string(char *str, int size, unsigned int ms);
+void util_up_string(char *str);
+
 #endif /* __AIR_MEDIAHUB_UTIL_H__ */
index b7622f2..580e287 100644 (file)
@@ -23,6 +23,9 @@
 /* group */
 #define GRP_VIEWER_VIEW "group.viewer_view"
 
+/* style */
+#define STYLE_VIEWER_PROGRESS "viewer_progress"
+
 /* part */
 #define PART_VIEWER_BG "part.viewer_bg"
 #define PART_VIEWER_CONTENT "part.viewer_content"
@@ -32,6 +35,7 @@
 #define PART_VIEWER_PROGRESS "part.viewer_progress"
 #define PART_VIEWER_TOTAL "part.viewer_total"
 #define PART_VIEWER_FAVORITE "part.viewer_favorite"
+#define PART_VIEWER_SLIDER "part.viewer_slider"
 
 /* signal */
 #define SIG_SET_PLAY "set,play,icon"
index 4187a48..4eb7b88 100644 (file)
@@ -19,4 +19,5 @@
 collections {
        #include "widgets/button.edc"
        #include "widgets/gengrid.edc"
+       #include "widgets/slider.edc"
 }
index e698125..bf7bb02 100644 (file)
@@ -442,6 +442,31 @@ group {
                                align: 0.0 0.5;
                        }
                }
+               part {
+                       name: PART_VIEWER_SLIDER;
+                       type: SWALLOW;
+                       scale: 1;
+                       description {
+                               state: "default" 0.0;
+                               min: 0 4;
+                               rel1 {
+                                       to: "bottomarea";
+                                       relative: 0.0 0.0;
+                               }
+                               rel2 {
+                                       to: "bottomarea";
+                                       relative: 1.0 0.0;
+                               }
+                               fixed: 0 1;
+                               align: 0.0 1.0;
+                       }
+                       description {
+                               state: "hide" 0.0;
+                               inherit: "default" 0.0;
+                               align: 0.0 0.0;
+                               visible: 0;
+                       }
+               }
        }
 
        programs {
@@ -452,6 +477,7 @@ group {
                        action: STATE_SET "hide" 0.0;
                        target: "toparea";
                        target: "bottomarea";
+                       target: PART_VIEWER_SLIDER;
                        transition: LINEAR TRANSITION_TIME;
                }
                program {
@@ -461,6 +487,7 @@ group {
                        action: STATE_SET "default" 0.0;
                        target: "toparea";
                        target: "bottomarea";
+                       target: PART_VIEWER_SLIDER;
                        transition: LINEAR TRANSITION_TIME;
                        after: SIG_SHOWED_BAR;
                }
index 98bff76..27bbf34 100644 (file)
@@ -33,7 +33,7 @@ group {
                        description {
                                state: "focused" 0.0;
                                inherit: "default" 0.0;
-                               color: COLOR_BTN_FOCUS;
+                               color: COLOR_ITEM_FOCUS;
                        }
                        description {
                                state: "selected" 0.0;
@@ -97,7 +97,7 @@ group {
                        description {
                                state: "selected" 0.0;
                                inherit: "default" 0.0;
-                               color: COLOR_BTN_SELECTED;
+                               color: COLOR_ITEM_SELECTED;
                        }
                }
        }
@@ -142,7 +142,7 @@ group {
                        description {
                                state: "focused" 0.0;
                                inherit: "default" 0.0;
-                               color: COLOR_BTN_FOCUS;
+                               color: COLOR_ITEM_FOCUS;
                        }
                }
                part {
@@ -191,7 +191,7 @@ group {
                        }
                        description {
                                state: "selected" 0.0;
-                               color: COLOR_BTN_FOCUS;
+                               color: COLOR_ITEM_FOCUS;
                        }
                }
                part {
@@ -441,7 +441,7 @@ group {
                        }
                        description {
                                state: "selected_pause" 0.0;
-                               color: COLOR_BTN_FOCUS;
+                               color: COLOR_ITEM_FOCUS;
                        }
                }
                part {
diff --git a/res/edc/widgets/slider.edc b/res/edc/widgets/slider.edc
new file mode 100644 (file)
index 0000000..2e0e34c
--- /dev/null
@@ -0,0 +1,225 @@
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the License);
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an AS IS BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+group {
+       name: "elm/slider/horizontal/viewer_progress";
+       data.item: "focus_highlight" "on";
+       parts {
+               part {
+                       name: "bg";
+                       type: RECT;
+                       description {
+                               state: "default" 0.0;
+                               min: 0 4;
+                               fixed: 0 1;
+                               color: 0 0 0 0;
+                       }
+               }
+               part {
+                       name: "base";
+                       scale: 1;
+                       type: RECT;
+                       description {
+                               state: "default" 0.0;
+                               rel1 {
+                                       to: "bg";
+                                       relative: 0.0 1.0;
+                               }
+                               rel2 {
+                                       to: "bg";
+                                       relative: 1.0 1.0;
+                               }
+                               min: 0 4;
+                               fixed: 0 1;
+                               align: 0.0 1.0;
+                               color: 255 255 255 255;
+                       }
+               }
+               part {
+                       name: "glow";
+                       mouse_events: 0;
+                       scale: 1;
+                       type: RECT;
+                       description {
+                               state: "default" 0.0;
+                               rel1.to: "base";
+                               rel2 {
+                                       relative: 0.5 1.0;
+                                       to_x: "button";
+                                       to_y: "base";
+                               }
+                               min: 0 4;
+                               max: 99999 4;
+                               fixed: 0 1;
+                               align: 0.0 1.0;
+                               color: COLOR_ITEM_SELECTED;
+                       }
+                       description {
+                               state: "focused" 0.0;
+                               inherit: "default" 0.0;
+                               color: COLOR_ITEM_FOCUS;
+                       }
+                       description {
+                               state: "disabled" 0.0;
+                               inherit: "default" 0.0;
+                               color: COLOR_ITEM_FOCUS_0;
+                       }
+               }
+               part {
+                       name: "pad.align";
+                       type: SPACER;
+                       mouse_events: 0;
+                       description {
+                               state: "default" 0.0;
+                               fixed: 1 1;
+                               rel1.to: "elm.dragable.slider";
+                               rel2.to: "elm.dragable.slider";
+                               align: 0.0 1.0;
+                               min: 0 0;
+                               max: 0 0;
+                       }
+               }
+               part {
+                       name: "clip";
+                       type: RECT;
+                       scale: 1;
+                       description {
+                               state: "default" 0.0;
+                               color: 255 255 255 0;
+                               min: 0 0;
+                               max: 0 0;
+                               fixed: 1 1;
+                               rel1 {
+                                       to: "elm.dragable.slider";
+                                       to_y: "bg";
+                               }
+                               rel2 {
+                                       to: "elm.dragable.slider";
+                                       to_y: "bg";
+                               }
+                               visible: 0;
+                       }
+               }
+               part {
+                       name: "button";
+                       type: GROUP;
+                       mouse_events: 1;
+                       source: "elm/slider/horizontal/progress_indicator/default";
+                       description {
+                               state: "default" 0.0;
+                               fixed: 1 1;
+                               rel1 {
+                                       to: "elm.dragable.slider";
+                                       to_y: "bg";
+                               }
+                               rel2 {
+                                       to: "elm.dragable.slider";
+                                       to_y: "bg";
+                               }
+                               align: 0.0 0.5;
+                       }
+                       description {
+                               state: "hidden" 0.0;
+                               inherit: "default" 0.0;
+                               visible: 0;
+                       }
+               }
+               part {
+                       name: "elm.swallow.bar";
+                       type: SWALLOW;
+                       repeat_events: 1;
+                       description {
+                               state: "default" 0.0;
+                               rel1.to_y: "bg";
+                               rel2.to_y: "bg";
+                               fixed: 1 1;
+                               min: 0 0;
+                       }
+               }
+               part {
+                       name: "elm.dragable.slider";
+                       type: RECT;
+                       mouse_events: 0;
+                       scale: 1;
+                       dragable.x: 1 1 0;
+                       dragable.y: 0 0 0;
+                       dragable.confine: "bg";
+                       description {
+                               state: "default" 0.0;
+                               min: 1 4;
+                               max: 1 4;
+                               rel1 {
+                                       to_x: "bg";
+                                       relative: 0 0.5;
+                               }
+                               rel2 {
+                                       to_x: "bg";
+                                       relative: 1 0.5;
+                               }
+                               color: 0 0 0 0;
+                               fixed: 1 1;
+                               align: 0.0 1.0;
+                       }
+               }
+               part {
+                       name: "slideevent";
+                       type: RECT;
+                       mouse_events: 0;
+                       scale: 1;
+                       dragable.events: "elm.dragable.slider";
+                       description {
+                               state: "default" 0.0;
+                               fixed: 1 1;
+                               min: 1 4;
+                               max: 1 4;
+                               rel1.to: "elm.dragable.slider";
+                               rel2.to: "elm.dragable.slider";
+                               color: 0 0 0 0;
+                       }
+               }
+       }
+}
+
+group {
+       name: "elm/slider/horizontal/progress_indicator/default";
+       alias: "elm/slider/horizontal/popup/default";
+       parts {
+               part {
+                       name: "knob_fill";
+                       repeat_events: 1;
+                       scale: 1;
+                       description {
+                               state: "default" 0.0;
+                               min: 1 4;
+                               align: 0.5 0.5;
+                               fixed: 1 1;
+                               visible: 0;
+                       }
+               }
+               part {
+                       name: "knob";
+                       repeat_events: 1;
+                       scale: 1;
+                       description {
+                               state: "default" 0.0;
+                               min: 1 4;
+                               fixed: 1 1;
+                               align: 0.0 1.0;
+                               visible: 0;
+                       }
+               }
+       }
+}
diff --git a/src/util/progressbar.c b/src/util/progressbar.c
new file mode 100644 (file)
index 0000000..853b507
--- /dev/null
@@ -0,0 +1,258 @@
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the License);
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an AS IS BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdbool.h>
+#include <Elementary.h>
+#include <app_debug.h>
+
+#include "define.h"
+#include "util/progressbar.h"
+#include "util/util.h"
+
+#define SLIDER_DEFAULT 0.05
+#define SLIDER_STEP 0.03
+
+#define PROGRESSBAR_INTERVAL 0.1
+
+struct progressbar {
+       Evas_Object *base;
+       Evas_Object *slider;
+       Ecore_Timer *timer;
+
+       struct progressbar_ops *ops;
+       void *ops_data;
+
+       char *part_slider;
+       char *part_total;
+       char *part_progress;
+       char *str_separator;
+};
+
+static void _update_progress_info(struct progressbar *m, int position)
+{
+       char progress[32] = {0,};
+
+       util_time_string(progress, sizeof(progress), position);
+       elm_object_part_text_set(m->base, m->part_progress, progress);
+}
+
+static void _update_time_info(struct progressbar *m, int position, int duration)
+{
+       char str[32] = {0,};
+       char total[32] = {0,};
+
+       util_time_string(str, sizeof(str), duration);
+       snprintf(total, sizeof(total), "%s%s", m->str_separator, str);
+
+       elm_object_part_text_set(m->base, m->part_total, total);
+
+       _update_progress_info(m, position);
+}
+
+static Eina_Bool _timer_cb(void *data)
+{
+       struct progressbar *m;
+       int position;
+
+       if (!data)
+               return ECORE_CALLBACK_CANCEL;
+
+       m = data;
+
+       position = m->ops->get_value(m->ops_data);
+
+       elm_slider_value_set(m->slider, position);
+       _update_progress_info(m, position);
+
+       return ECORE_CALLBACK_RENEW;
+}
+
+void progressbar_start(struct progressbar *m)
+{
+       if (!m) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       if (m->timer)
+               ecore_timer_reset(m->timer);
+       else
+               m->timer = ecore_timer_add(PROGRESSBAR_INTERVAL, _timer_cb, m);
+}
+
+void progressbar_stop(struct progressbar *m)
+{
+       if (!m) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       ecore_timer_del(m->timer);
+       m->timer = NULL;
+}
+
+void progressbar_pause(struct progressbar *m)
+{
+       if (!m) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       if (m->timer)
+               ecore_timer_freeze(m->timer);
+}
+
+void progressbar_resume(struct progressbar *m)
+{
+       if (!m) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       if (m->timer)
+               ecore_timer_thaw(m->timer);
+}
+
+void progressbar_show(struct progressbar *m)
+{
+       if (!m) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       if (!m->part_slider || !m->slider) {
+               _ERR("slider did not initialize");
+               return;
+       }
+
+       evas_object_show(m->slider);
+       elm_object_part_content_set(m->base, m->part_slider, m->slider);
+}
+
+void progressbar_hide(struct progressbar *m)
+{
+       if (!m) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       if (!m->part_slider) {
+               _ERR("slider did not initialize");
+               return;
+       }
+
+       evas_object_hide(m->slider);
+       elm_object_part_content_unset(m->base, m->part_slider);
+}
+
+void progressbar_reset(struct progressbar *m, int position, int duration)
+{
+       if (!m) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       progressbar_stop(m);
+
+       elm_slider_value_set(m->slider, position);
+       elm_slider_min_max_set(m->slider, 0, duration);
+       elm_slider_step_set(m->slider, SLIDER_STEP);
+
+       _update_time_info(m, position, duration);
+}
+
+void progressbar_set_ops(struct progressbar *m,
+               struct progressbar_ops *ops, void *data)
+{
+       if (!m || !ops) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       m->ops = ops;
+       m->ops_data = data;
+}
+
+void progressbar_set_parts(struct progressbar *m, const char *slider,
+               const char *total, const char *progress, const char *separator)
+{
+       if (!m) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       if (slider)
+               m->part_slider = strdup(slider);
+
+       if (total)
+               m->part_total = strdup(total);
+
+       if (progress)
+               m->part_progress = strdup(progress);
+
+       if (separator)
+               m->str_separator = strdup(separator);
+}
+
+struct progressbar *progressbar_create(Evas_Object *base)
+{
+       struct progressbar *m;
+       Evas_Object *obj;
+
+       m = calloc(1, sizeof(*m));
+       if (!m) {
+               _ERR("failed to allocate");
+               return NULL;
+       }
+
+       obj = elm_slider_add(base);
+       if (!obj) {
+               _ERR("failed to adding slider");
+               free(m);
+               return NULL;
+       }
+
+       elm_slider_indicator_show_set(obj, EINA_FALSE);
+       elm_slider_indicator_show_on_focus_set(obj, EINA_FALSE);
+       elm_object_style_set(obj, STYLE_VIEWER_PROGRESS);
+       elm_slider_horizontal_set(obj, EINA_TRUE);
+       elm_slider_step_set(obj, SLIDER_DEFAULT);
+
+       /* FIXME: focus disabled */
+       elm_object_focus_allow_set(obj, EINA_FALSE);
+
+       m->base = base;
+       m->slider = obj;
+
+       return m;
+}
+
+void progressbar_destroy(struct progressbar *m)
+{
+       if (!m) {
+               _ERR("invalid parameter");
+               return;
+       }
+
+       progressbar_stop(m);
+
+       free(m->part_slider);
+       free(m->part_total);
+       free(m->part_progress);
+       free(m->str_separator);
+
+       free(m);
+}
index df8abad..5289fe4 100644 (file)
@@ -87,3 +87,21 @@ Evas_Object *util_add_scroller(Evas_Object *base)
 
        return scr;
 }
+
+void util_time_string(char *str, int size, unsigned int ms)
+{
+       int sec;
+
+       sec = ms / 1000;
+
+       snprintf(str, size, "%02d:%02d:%02d",
+                       sec / 3600, (sec % 3600) / 60, sec % 60);
+}
+
+void util_up_string(char *str)
+{
+       while (*str) {
+               *str = toupper(*str);
+               str++;
+       }
+}
index 898aa07..8ee87bb 100644 (file)
@@ -27,6 +27,7 @@
 #include "util/controller.h"
 #include "util/timeout_handler.h"
 #include "util/playermgr.h"
+#include "util/progressbar.h"
 #include "util/util.h"
 
 #define STYLE_VIEWER_BTN "viewer_btn"
@@ -34,8 +35,7 @@
 #define PLAY_BTN_LOC 2
 
 #define VIEWER_TIMEOUT 3.0
-#define VIEWER_INTERVAL 0.1
-
+#define VIEWER_SEPARATOR "/ "
 #define VIDEO_COPYRIGHT "Unknown"
 
 enum {
@@ -67,12 +67,12 @@ struct _priv {
        Evas_Object *photo;
        Evas_Object *photo_pre;
        Evas_Object *favorite;
-       Evas_Object *timer;
 
        struct _viewer viewer;
        struct _playlist playlist;
        struct timeout_handler *timeout;
        struct playermgr *player;
+       struct progressbar *progress;
 
        bool bar_show;
 };
@@ -238,24 +238,6 @@ static inline bool _check_movie_type(app_media_info *mi)
        return strcmp(mi->video->copyright, VIDEO_COPYRIGHT);
 }
 
-static void _time_string(char *str, int size, unsigned int ms)
-{
-       int sec;
-
-       sec = ms / 1000;
-
-       snprintf(str, size, "%02d:%02d:%02d",
-                       sec / 3600, (sec % 3600) / 60, sec % 60);
-}
-
-static void _up_string(char *str)
-{
-       while (*str) {
-               *str = toupper(*str);
-               str++;
-       }
-}
-
 static void _set_bg_color(struct _priv *priv, int r, int g, int b, int a)
 {
        Evas_Object *bg;
@@ -408,7 +390,7 @@ static void _draw_title_bar(struct _priv *priv, int id, app_media_info *mi)
 
                strftime(date, sizeof(date), "%d %b", &tm);
                strftime(day, sizeof(day), "%a", &tm);
-               _up_string(day);
+               util_up_string(day);
 
                snprintf(buf, sizeof(buf), "%s, %s", day, date);
 
@@ -420,28 +402,19 @@ static void _draw_title_bar(struct _priv *priv, int id, app_media_info *mi)
        }
 }
 
-static void _draw_time_info(struct _priv *priv, int id, app_media_info *mi)
+static void _draw_progressbar(struct _priv *priv, int id, app_media_info *mi)
 {
-       char progress[32] = {0,};
-       char duration[32] = {0,};
-       char total[32] = {0,};
+       if (id == VIEWER_PHOTO) {
+               elm_object_part_text_set(priv->base, PART_VIEWER_PROGRESS, "");
+               elm_object_part_text_set(priv->base, PART_VIEWER_TOTAL, "");
+               progressbar_hide(priv->progress);
 
-       if (id != VIEWER_PHOTO) {
-               _time_string(progress, sizeof(progress), mi->video->position);
-               _time_string(duration, sizeof(duration), mi->video->duration);
-               snprintf(total, sizeof(total), "/ %s", duration);
+               return;
        }
 
-       elm_object_part_text_set(priv->base, PART_VIEWER_PROGRESS, progress);
-       elm_object_part_text_set(priv->base, PART_VIEWER_TOTAL, total);
-}
-
-static void _draw_progress_info(struct _priv *priv, int ms)
-{
-       char progress[32] = {0,};
-
-       _time_string(progress, sizeof(progress), ms);
-       elm_object_part_text_set(priv->base, PART_VIEWER_PROGRESS, progress);
+       progressbar_reset(priv->progress,
+                       mi->video->position, mi->video->duration);
+       progressbar_show(priv->progress);
 }
 
 static void _draw_favorite_icon(struct _priv *priv, int id, app_media_info *mi)
@@ -528,7 +501,7 @@ static bool _viewer_show(struct _priv *priv, int foc)
        _draw_contents(priv, id, mi);
 
        _draw_title_bar(priv, id, mi);
-       _draw_time_info(priv, id, mi);
+       _draw_progressbar(priv, id, mi);
        _draw_favorite_icon(priv, id, mi);
 
        return true;
@@ -577,6 +550,8 @@ static void _viewer_delete(struct _priv *priv)
 
        for (i = 0; i < VIEWER_MAX; i++)
                controller_destroy(priv->viewer.ctl[i]);
+
+       progressbar_destroy(priv->progress);
 }
 
 static bool _viewer_prev(struct _priv *priv)
@@ -655,64 +630,21 @@ static void _event_cb(void *data, int type, void *ei)
        _show_bar(data);
 }
 
-static bool _ui_init(struct _priv *priv)
-{
-       Evas_Object *obj;
-       bool r;
-       int i;
-
-       for (i = 0; i < VIEWER_MAX; i++) {
-               r = _viewer_add(priv, i);
-               if (!r)
-                       goto err;
-       }
-
-       obj = elm_image_add(priv->base);
-       if (!obj) {
-               _ERR("failed to adding image");
-               goto err;
-       }
-
-       elm_image_file_set(obj, IMAGE_VIEWER_FAVORITE, NULL);
-       priv->favorite = obj;
-
-       priv->timeout = timeout_handler_init(VIEWER_TIMEOUT,
-                       _timeout_cb, priv,
-                       _event_cb, priv);
-
-       priv->bar_show = true;
-
-       return true;
-
-err:
-       _viewer_delete(priv);
-       return false;
-}
-
-static Eina_Bool _timer_cb(void *data)
+static int _player_get_position(void *data)
 {
        struct _priv *priv;
-       int ms;
 
        if (!data)
-               return ECORE_CALLBACK_CANCEL;
+               return 0;
 
        priv = data;
 
-       ms = playermgr_get_position(priv->player);
-
-       _draw_progress_info(priv, ms);
-
-       return ECORE_CALLBACK_RENEW;
+       return playermgr_get_position(priv->player);
 }
 
-static void _timer_reset(struct _priv *priv)
-{
-       if (priv->timer)
-               ecore_timer_reset(priv->timer);
-       else
-               priv->timer = ecore_timer_add(VIEWER_INTERVAL, _timer_cb, priv);
-}
+struct progressbar_ops _progressbar_ops = {
+       .get_value = _player_get_position,
+};
 
 static void _player_play(struct _priv *priv)
 {
@@ -723,15 +655,11 @@ static void _player_play(struct _priv *priv)
 
        switch (state) {
        case PLAYER_STATE_PAUSED:
-               if (priv->timer)
-                       ecore_timer_thaw(priv->timer);
-
+               progressbar_resume(priv->progress);
                playermgr_resume(priv->player);
                break;
        case PLAYER_STATE_PLAYING:
-               if (priv->timer)
-                       ecore_timer_freeze(priv->timer);
-
+               progressbar_pause(priv->progress);
                playermgr_pause(priv->player);
                break;
        case PLAYER_STATE_IDLE:
@@ -743,8 +671,8 @@ static void _player_play(struct _priv *priv)
                }
 
                _remove_thumbnail(priv);
-               _timer_reset(priv);
 
+               progressbar_start(priv->progress);
                playermgr_play(priv->player, mi->file_path);
 
                break;
@@ -758,9 +686,7 @@ static void _player_stop(struct _priv *priv)
 {
        struct controller *ctl;
 
-       ecore_timer_del(priv->timer);
-       priv->timer = NULL;
-
+       progressbar_stop(priv->progress);
        playermgr_stop(priv->player);
 
        ctl = priv->viewer.ctl[priv->viewer.cur];
@@ -776,30 +702,23 @@ static void _player_complete_cb(void *data)
 
        priv = data;
 
-       ecore_timer_del(priv->timer);
-       priv->timer = NULL;
+       progressbar_stop(priv->progress);
 }
 
 static void _player_set_position_cb(void *data)
 {
        struct _priv *priv;
        struct controller *ctl;
-       int ms;
 
        if (!data)
                return;
 
        priv = data;
 
-       ms = playermgr_get_position(priv->player);
-       _draw_progress_info(priv, ms);
-
        /* FIXME: what will you do here? */
+       progressbar_pause(priv->progress);
        playermgr_pause(priv->player);
 
-       if (priv->timer)
-               ecore_timer_freeze(priv->timer);
-
        ctl = priv->viewer.ctl[priv->viewer.cur];
        ctl->ops->signal(ctl->handle, PLAY_BTN_LOC, SIG_SET_PLAY);
 }
@@ -861,6 +780,53 @@ static void _callback_video(void *data, const char *ev)
        }
 }
 
+static bool _ui_init(struct _priv *priv)
+{
+       Evas_Object *obj;
+       struct progressbar *prog;
+       bool r;
+       int i;
+
+       for (i = 0; i < VIEWER_MAX; i++) {
+               r = _viewer_add(priv, i);
+               if (!r)
+                       goto err;
+       }
+
+       prog = progressbar_create(priv->base);
+       if (!prog) {
+               _ERR("failed to adding progressbar");
+               goto err;
+       }
+
+       progressbar_set_parts(prog, PART_VIEWER_SLIDER, PART_VIEWER_TOTAL,
+                       PART_VIEWER_PROGRESS, VIEWER_SEPARATOR);
+       progressbar_set_ops(prog, &_progressbar_ops, priv);
+
+       priv->progress = prog;
+
+       obj = elm_image_add(priv->base);
+       if (!obj) {
+               _ERR("failed to adding image");
+               goto err;
+       }
+
+       elm_image_file_set(obj, IMAGE_VIEWER_FAVORITE, NULL);
+       priv->favorite = obj;
+
+       priv->timeout = timeout_handler_init(VIEWER_TIMEOUT,
+                       _timeout_cb, priv,
+                       _event_cb, priv);
+
+       priv->bar_show = true;
+
+       return true;
+
+err:
+       _viewer_delete(priv);
+       return false;
+}
+
 static Evas_Object *_create(Evas_Object *win, void *data)
 {
        struct _priv *priv;
@@ -982,9 +948,6 @@ static void _destroy(void *view_data)
 
        timeout_handler_fini(priv->timeout);
 
-       ecore_timer_del(priv->timer);
-       priv->timer = NULL;
-
        playermgr_destroy(priv->player);
 
        evas_object_del(priv->base);