focus: add the focus region show mode 36/48236/3
authorJaehwan Kim <jae.hwan.kim@samsung.com>
Wed, 12 Aug 2015 08:25:15 +0000 (17:25 +0900)
committerJaehwan Kim <jae.hwan.kim@samsung.com>
Wed, 16 Sep 2015 13:55:07 +0000 (06:55 -0700)
When the focus is move to the object in scroller, it is scrolled
to show the focus region as a widget.
If the focus region want to be shown as an item,
set the mode ELM_FOCUS_REGION_SHOW_ITEM.
If then, it will be scrolled as an item.
TODO: Widgets have items are added on_focus_region function.

@feature

Conflicts:
src/bin/test_gengrid.c
src/lib/elm_focus.h
src/lib/elm_gengrid.eo
src/lib/elm_widget.eo

Change-Id: Ibc66f2d10e720d90e7da328d1a3230813c72846b
origin: upstream

src/bin/test_gengrid.c
src/lib/elm_focus.h
src/lib/elm_gengrid.c
src/lib/elm_gengrid.eo
src/lib/elm_main.c
src/lib/elm_widget.c
src/lib/elm_widget.eo
src/lib/elm_widget.h

index 5cd87a5aaa08b189775177689a81148633c773e2..83c0e91b5c5d7f9da5a29edf75543ab95cb6b341 100644 (file)
@@ -29,6 +29,7 @@ struct _api_data
    unsigned int state;  /* What state we are testing       */
    Evas_Object *box;           /* Use this to get box content     */
    Evas_Object *grid;
+   Evas_Object *grid2;
 };
 typedef struct _api_data api_data;
 
@@ -1626,6 +1627,19 @@ _gg_focus_focus_animate_changed_cb(void *data,
                                        elm_check_state_get(obj));
 }
 
+static void
+_gg_focus_region_show_item_cb(void *data,
+                                   Evas_Object *obj,
+                                   void *event_info EINA_UNUSED)
+{
+   if (elm_check_state_get(obj))
+     elm_object_focus_region_show_mode_set((Evas_Object *)data,
+                                           ELM_FOCUS_REGION_SHOW_ITEM);
+   else
+     elm_object_focus_region_show_mode_set((Evas_Object *)data,
+                                           ELM_FOCUS_REGION_SHOW_WIDGET);
+}
+
 static void
 _grid_reorder_mode(void *data, Evas_Object *obj,
                    void *event_info EINA_UNUSED)
@@ -1658,7 +1672,7 @@ test_gengrid_focus(void *data EINA_UNUSED,
                    Evas_Object *obj EINA_UNUSED,
                    void *event_info EINA_UNUSED)
 {
-   Evas_Object *win, *bx, *bx_horiz, *gengrid, *btn, *fr, *bx_mv, *bx_opt, *ck, *rdg, *rd;
+   Evas_Object *win, *bx, *bx_horiz, *in_bx, *scr, *gengrid, *gengrid2, *btn, *fr, *bx_mv, *bx_opt, *ck, *rdg, *rd;
    Elm_Gengrid_Item_Class *ic;
    Item_Data *id;
    char buf[PATH_MAX];
@@ -1692,13 +1706,26 @@ test_gengrid_focus(void *data EINA_UNUSED,
    evas_object_show(btn);
    elm_object_focus_set(btn, EINA_TRUE);
 
-   gengrid = elm_gengrid_add(bx);
+   scr = elm_scroller_add(bx);
+   evas_object_size_hint_weight_set(scr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
+   evas_object_size_hint_align_set(scr, EVAS_HINT_FILL, EVAS_HINT_FILL);
+   elm_box_pack_end(bx, scr);
+   evas_object_show(scr);
+
+   in_bx = elm_box_add(scr);
+   evas_object_size_hint_weight_set(in_bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
+   evas_object_size_hint_align_set(in_bx, EVAS_HINT_FILL, EVAS_HINT_FILL);
+   elm_object_content_set(scr, in_bx);
+   evas_object_show(in_bx);
+
+   gengrid = elm_gengrid_add(in_bx);
    elm_gengrid_item_size_set(gengrid,
                              ELM_SCALE_SIZE(150),
                              ELM_SCALE_SIZE(150));
    evas_object_size_hint_weight_set(gengrid, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
    evas_object_size_hint_align_set(gengrid, EVAS_HINT_FILL, EVAS_HINT_FILL);
-   elm_box_pack_end(bx, gengrid);
+   evas_object_size_hint_min_set(gengrid, 0, ELM_SCALE_SIZE(600));
+   elm_box_pack_end(in_bx, gengrid);
    evas_object_show(gengrid);
    evas_object_smart_callback_add(gengrid, "item,focused", _gengrid_focus_item_cb, "item,focused");
    evas_object_smart_callback_add(gengrid, "item,unfocused", _gengrid_focus_item_cb, "item,unfocused");
@@ -1709,6 +1736,24 @@ test_gengrid_focus(void *data EINA_UNUSED,
    evas_object_smart_callback_add(gengrid, "unhighlighted", _gengrid_focus_item_cb, "unhighlighted");
    evas_object_event_callback_add(gengrid, EVAS_CALLBACK_KEY_DOWN, _gengrid_focus_key_down_cb, NULL);
 
+   gengrid2 = elm_gengrid_add(in_bx);
+   elm_gengrid_item_size_set(gengrid2,
+                             ELM_SCALE_SIZE(150),
+                             ELM_SCALE_SIZE(150));
+   evas_object_size_hint_weight_set(gengrid2, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
+   evas_object_size_hint_align_set(gengrid2, EVAS_HINT_FILL, EVAS_HINT_FILL);
+   evas_object_size_hint_min_set(gengrid2, 0, ELM_SCALE_SIZE(600));
+   elm_box_pack_end(in_bx, gengrid2);
+   evas_object_show(gengrid2);
+   evas_object_smart_callback_add(gengrid2, "item,focused", _gengrid_focus_item_cb, "item,focused");
+   evas_object_smart_callback_add(gengrid2, "item,unfocused", _gengrid_focus_item_cb, "item,unfocused");
+   evas_object_smart_callback_add(gengrid2, "selected", _gengrid_focus_item_cb, "selected");
+   evas_object_smart_callback_add(gengrid2, "unselected", _gengrid_focus_item_cb, "unselected");
+   evas_object_smart_callback_add(gengrid2, "activated", _gengrid_focus_item_cb, "activated");
+   evas_object_smart_callback_add(gengrid2, "highlighted", _gengrid_focus_item_cb, "highlighted");
+   evas_object_smart_callback_add(gengrid2, "unhighlighted", _gengrid_focus_item_cb, "unhighlighted");
+   evas_object_event_callback_add(gengrid2, EVAS_CALLBACK_KEY_DOWN, _gengrid_focus_key_down_cb, NULL);
+
    btn = elm_button_add(bx);
    elm_object_text_set(btn, "Down");
    elm_box_pack_end(bx, btn);
@@ -1752,10 +1797,24 @@ test_gengrid_focus(void *data EINA_UNUSED,
    elm_box_pack_end(bx_opt, ck);
    evas_object_show(ck);
 
+   ck = elm_check_add(bx_opt);
+   elm_object_text_set(ck, "Focus Region Show as Item");
+   elm_check_state_set(ck, EINA_FALSE);
+   evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, 0.0);
+   evas_object_smart_callback_add(ck, "changed",
+                                  _gg_focus_region_show_item_cb,
+                                  gengrid);
+   evas_object_smart_callback_add(ck, "changed",
+                                  _gg_focus_region_show_item_cb,
+                                  gengrid2);
+   elm_box_pack_end(bx_opt, ck);
+   evas_object_show(ck);
+
    ck = elm_check_add(bx_opt);
    elm_object_text_set(ck, "Horizontal Mode");
    evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, 0.0);
    evas_object_smart_callback_add(ck, "changed", _horizontal_grid, gengrid);
+   evas_object_smart_callback_add(ck, "changed", _horizontal_grid, gengrid2);
    elm_box_pack_end(bx_opt, ck);
    evas_object_show(ck);
 
@@ -1763,6 +1822,7 @@ test_gengrid_focus(void *data EINA_UNUSED,
    elm_object_text_set(ck, "Rorder mode enable");
    evas_object_size_hint_weight_set(ck, EVAS_HINT_EXPAND, 0.0);
    evas_object_smart_callback_add(ck, "changed", _grid_reorder_mode, gengrid);
+   evas_object_smart_callback_add(ck, "changed", _grid_reorder_mode, gengrid2);
    elm_box_pack_end(bx_opt, ck);
    evas_object_show(ck);
 
@@ -1843,6 +1903,19 @@ test_gengrid_focus(void *data EINA_UNUSED,
         if (i == 4)
           elm_object_item_disabled_set(id->item, EINA_TRUE);
      }
+
+   n = 0;
+   for (i = 0; i < 24; i++)
+     {
+        id = calloc(1, sizeof(Item_Data));
+        snprintf(buf, sizeof(buf), "%s/images/%s", elm_app_data_dir_get(), img[n]);
+        n = (n + 1) % 9;
+        id->mode = i;
+        id->path = eina_stringshare_add(buf);
+        id->item = elm_gengrid_item_append(gengrid2, ic, id, NULL, NULL);
+        if (i == 4)
+          elm_object_item_disabled_set(id->item, EINA_TRUE);
+     }
    elm_gengrid_item_class_free(ic);
 
    evas_object_resize(win, 600, 600);
index 29883f784f518fb753b6e14c6be8602c3b3f9ba0..aa03636300274946c2557bacb453329d72449750 100644 (file)
@@ -48,6 +48,17 @@ typedef enum
    ELM_FOCUS_LEFT      /**< left direction */
 } Elm_Focus_Direction;
 
+/**
+ * Focus region show mode.
+ *
+ * @ingroup Focus
+ */
+typedef enum
+{
+   ELM_FOCUS_REGION_SHOW_WIDGET, /**< as a widget */
+   ELM_FOCUS_REGION_SHOW_ITEM, /**< as an item */
+} Elm_Focus_Region_Show_Mode;
+
 /**
  * Get the whether an Elementary object has the focus or not.
  *
@@ -371,3 +382,36 @@ EAPI void                 elm_object_focus_move_policy_set(Evas_Object *obj, Elm
  * @ingroup Focus
  */
 EAPI Elm_Focus_Move_Policy  elm_object_focus_move_policy_get(Evas_Object *obj);
+
+/**
+ * Set the focus region show mode to a given Elementary object.
+ *
+ * @param obj The Elementary object to operate on
+ * @param mode A mode to show the focus region
+ *
+ * @see elm_object_focus_region_show_mode_get
+ *
+ * When the focus is move to the object in scroller, it is scrolled
+ * to show the focus region as a widget. If the focus region want to be shown
+ * as an item, set the mode ELM_FOCUS_REGION_SHOW_ITEM.
+ * If then, it will be scrolled as an item.
+ *
+ * @since 1.16
+ *
+ * @ingroup Focus
+ */
+EAPI void                       elm_object_focus_region_show_mode_set(Evas_Object *obj, Elm_Focus_Region_Show_Mode mode);
+
+/**
+ * Get the focus region show mode to a given Elementary object.
+ *
+ * @param obj The Elementary object to get the information from
+ * @return The focus region shown mode
+ *
+ * @see elm_object_focus_region_show_mode_set
+ *
+ * @since 1.16
+ *
+ * @ingroup Focus
+ */
+EAPI Elm_Focus_Region_Show_Mode elm_object_focus_region_show_mode_get(const Evas_Object *obj);
index 16fe3d52b75f102c9696c16a766b7738f81007c4..c6035b57f5710635b83f3e9c61257656ce170774 100644 (file)
@@ -3195,6 +3195,25 @@ _elm_gengrid_elm_widget_on_focus(Eo *obj, Elm_Gengrid_Data *sd)
    return EINA_TRUE;
 }
 
+EOLIAN static Eina_Bool
+_elm_gengrid_elm_widget_on_focus_region(Eo *obj, Elm_Gengrid_Data *sd, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h)
+{
+   if (!sd->focused_item) return EINA_FALSE;
+   if (elm_object_focus_region_show_mode_get(obj) == ELM_FOCUS_REGION_SHOW_ITEM)
+     {
+        Evas_Coord vx, vy;
+        ELM_GENGRID_ITEM_DATA_GET(sd->focused_item, focus_it);
+        evas_object_geometry_get(VIEW(focus_it), x, y, w, h);
+        evas_object_geometry_get(obj, &vx, &vy, NULL, NULL);
+
+        *x -= vx;
+        *y -= vy;
+
+        return EINA_TRUE;
+     }
+   return EINA_FALSE;
+}
+
 static Eina_Bool _elm_gengrid_smart_focus_next_enable = EINA_FALSE;
 
 EOLIAN static Eina_Bool
@@ -3518,6 +3537,7 @@ _elm_gengrid_item_elm_widget_item_focus_set(Eo *eo_it, Elm_Gen_Item *it, Eina_Bo
           return;
         _elm_gengrid_item_unfocused(eo_it);
      }
+   elm_widget_focus_region_show(obj);
 }
 
 EOLIAN static Eina_Bool
index d808ef6a3e41c2ddbf913255f72ae3d882dc7120..97fd46af19792cb2c089f014a6e3929ce37fea23 100644 (file)
@@ -696,6 +696,7 @@ class Elm_Gengrid (Elm_Layout, Elm_Interface_Scrollable,
       Elm_Widget.access;
       Elm_Widget.focus_next;
       Elm_Widget.on_focus;
+      Elm_Widget.on_focus_region;
       Elm_Widget.event;
       Elm_Widget.focus_highlight_geometry_get;
       Elm_Widget.focused_item.get;
index 30e0286f8b8f56d86c87dbe4a308c93bc716956c..2d8a7793483fadda62e6a5424392e61620cec1be 100644 (file)
@@ -1741,3 +1741,15 @@ elm_object_focused_item_get(const Evas_Object *obj)
    return elm_widget_focused_item_get(obj);
 }
 
+EAPI void
+elm_object_focus_region_show_mode_set(Evas_Object *obj, Elm_Focus_Region_Show_Mode mode)
+{
+   elm_widget_focus_region_show_mode_set(obj, mode);
+}
+
+EAPI Elm_Focus_Region_Show_Mode
+elm_object_focus_region_show_mode_get(const Evas_Object *obj)
+{
+   return elm_widget_focus_region_show_mode_get(obj);
+}
+
index 9dd9390b6c07e621e53fd87b6032531a4766812d..2aba765cd9e332d700785a9ae53af12a5d8e5dfe 100644 (file)
@@ -376,6 +376,7 @@ _elm_widget_evas_object_smart_add(Eo *obj, Elm_Widget_Smart_Data *priv)
    priv->obj = obj;
    priv->mirrored_auto_mode = EINA_TRUE; /* will follow system locale
                                           * settings */
+   priv->focus_region_show_mode = ELM_FOCUS_REGION_SHOW_WIDGET;
    elm_widget_can_focus_set(obj, EINA_TRUE);
    priv->is_mirrored = elm_config_mirrored_get();
    priv->focus_move_policy = _elm_config->focus_move_policy;
@@ -4005,6 +4006,18 @@ _elm_widget_focused_item_get(Eo *obj EINA_UNUSED, Elm_Widget_Smart_Data *_pd EIN
    return NULL;
 }
 
+EOLIAN static void
+_elm_widget_focus_region_show_mode_set(Eo *obj EINA_UNUSED, Elm_Widget_Smart_Data *_pd, Elm_Focus_Region_Show_Mode mode)
+{
+   _pd->focus_region_show_mode = mode;
+}
+
+EOLIAN static Elm_Focus_Region_Show_Mode
+_elm_widget_focus_region_show_mode_get(Eo *obj EINA_UNUSED, Elm_Widget_Smart_Data *_pd)
+{
+   return _pd->focus_region_show_mode;
+}
+
 EAPI void
 elm_widget_activate(Evas_Object *obj, Elm_Activate act)
 {
index cf40e1b31287639589b5c5a89ffab29c3cef46cf..429fdb323282316e8837c8aa0f4ee5d19d2847b1 100644 (file)
@@ -214,6 +214,16 @@ abstract Elm_Widget (Evas.Object_Smart, Elm_Interface_Atspi_Accessible, Elm_Inte
             bool highlight; /*@ highlight */
          }
       }
+      focus_region_show_mode {
+         /*Control the focus_region_show mode.*/
+         set {
+         }
+         get {
+         }
+         values {
+            Elm_Focus_Region_Show_Mode mode;
+         }
+      }
       parent_highlight {
          set {
             /*@ No description supplied by the EAPI. */
index e118af4a1431324a4fead8c168941c887fc3a2e0..351ff9050fee32dbc7b694d97fb9152a8ea8d9d5 100644 (file)
@@ -420,6 +420,7 @@ typedef struct _Elm_Widget_Smart_Data
 
    int                           orient_mode; /* -1 is disabled */
    Elm_Focus_Move_Policy         focus_move_policy;
+   Elm_Focus_Region_Show_Mode    focus_region_show_mode;
 
    Eina_Bool                     drag_x_locked : 1;
    Eina_Bool                     drag_y_locked : 1;
@@ -777,6 +778,8 @@ EAPI void             elm_widget_focus_highlight_geometry_get(const Evas_Object
 void                  _elm_widget_item_highlight_in_theme(Evas_Object *obj, Elm_Object_Item *it);
 EAPI void             elm_widget_focus_move_policy_set(Evas_Object *obj, Elm_Focus_Move_Policy policy);
 EAPI Elm_Focus_Move_Policy elm_widget_focus_move_policy_get(const Evas_Object *obj);
+EAPI void             elm_widget_focus_region_show_mode_set(Evas_Object *obj, Elm_Focus_Region_Show_Mode mode);
+EAPI Elm_Focus_Region_Show_Mode elm_widget_focus_region_show_mode_get(const Evas_Object *obj);
 
 /**
  * Function to operate on a given widget's scrollabe children when necessary.