e_hwc_windows: fix the problem that window located under 24 depth window is visible 62/298862/1 accepted/tizen/7.0/unified/20230918.160929
authorChangyeon Lee <cyeon.lee@samsung.com>
Wed, 13 Sep 2023 12:56:48 +0000 (21:56 +0900)
committerChangyeon Lee <cyeon.lee@samsung.com>
Thu, 14 Sep 2023 09:49:15 +0000 (18:49 +0900)
if tdm backend set target buffer to upper hw layer that used device type window,
window located under 24 depth window can be visible when evas object is visible.

so to fix the problem, hwc set transparent object when bottom ui window is device type
and target window is enabled.

Change-Id: I321b4fc84f3cb0f172d21eca92e9f317e454e77f

src/bin/e_hwc.h
src/bin/e_hwc_window.c
src/bin/e_hwc_window.h
src/bin/e_hwc_windows.c

index d60f9b439af9b9078bd16ba206db7c235068df54..f595d19ef6ef732d55073413992ec2fa51d4c887 100644 (file)
@@ -201,6 +201,8 @@ struct _E_Hwc
    Eina_List           *wins_commit_data_list;
 
    Eina_List           *sync_callback_list;
+
+   E_Hwc_Window        *below_transparent_window;
 };
 
 E_API extern int E_EVENT_HWC_ACTIVE;
index 5e19a26b15097ab85d702345dbd6038bb512e8f0..8fa4e36ae83e7003930afb0ef26eb79b63c15a10 100644 (file)
@@ -681,6 +681,7 @@ _e_hwc_window_del(E_Hwc_Window *hwc_window)
         hwc_window->queue = NULL;
      }
 
+   e_hwc_window_below_transparent_obj_set(hwc_window, EINA_FALSE);
    e_hwc_window_state_set(hwc_window, E_HWC_WINDOW_STATE_NONE, EINA_TRUE);
 
    e_object_del(E_OBJECT(hwc_window));
@@ -3189,3 +3190,96 @@ e_hwc_window_presentation_callback_call(E_Hwc_Window *hwc_window)
 
    return EINA_TRUE;
 }
+
+static void
+_e_hwc_window_below_transparent_obj_map_apply(E_Hwc_Window *hwc_window)
+{
+   E_Map *map;
+   int w, h;
+
+   EINA_SAFETY_ON_NULL_RETURN(hwc_window->below_transparent_obj);
+
+   map = e_map_new();
+   EINA_SAFETY_ON_NULL_RETURN(map);
+
+   e_map_util_points_populate_from_object_full(map, hwc_window->ec->frame, 0);
+   e_map_util_points_color_set(map, 255, 255, 255, 255);
+   evas_object_geometry_get(hwc_window->below_transparent_obj, NULL, NULL, &w, &h);
+   e_map_point_image_uv_set(map, 0, 0, 0);
+   e_map_point_image_uv_set(map, 1, w, 0);
+   e_map_point_image_uv_set(map, 2, w, h);
+   e_map_point_image_uv_set(map, 3, 0, h);
+
+   e_comp_object_map_set(hwc_window->below_transparent_obj, map);
+   e_comp_object_map_enable_set(hwc_window->below_transparent_obj, EINA_TRUE);
+
+   e_map_free(map);
+}
+
+static void
+_e_hwc_window_below_transparent_obj_cb_resize(void *data, Evas *evas EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
+{
+   E_Hwc_Window *hwc_window;
+
+   if (!(hwc_window = data)) return;
+
+   EINA_SAFETY_ON_NULL_RETURN(hwc_window->ec);
+
+   _e_hwc_window_below_transparent_obj_map_apply(hwc_window);
+}
+
+EINTERN void
+e_hwc_window_below_transparent_obj_set(E_Hwc_Window *hwc_window, Eina_Bool set)
+{
+   Evas_Object *below_transparent_obj;
+
+   EINA_SAFETY_ON_NULL_RETURN(hwc_window);
+
+   if (set)
+     {
+        EINA_SAFETY_ON_NULL_RETURN(hwc_window->ec);
+
+        if (hwc_window->below_transparent_obj) return;
+
+        below_transparent_obj = evas_object_rectangle_add(e_comp->evas);
+        EINA_SAFETY_ON_NULL_RETURN(below_transparent_obj);
+
+        evas_object_pass_events_set(below_transparent_obj, EINA_TRUE);
+
+        evas_object_layer_set(below_transparent_obj, evas_object_layer_get(hwc_window->ec->frame));
+        evas_object_render_op_set(below_transparent_obj, EVAS_RENDER_COPY);
+
+        evas_object_color_set(below_transparent_obj, 0, 0, 0, 0);
+        evas_object_move(below_transparent_obj, hwc_window->ec->x, hwc_window->ec->y);
+        evas_object_resize(below_transparent_obj, 1, 1);
+        evas_object_name_set(below_transparent_obj, "hwc_below_transparent_obj");
+
+        hwc_window->below_transparent_obj = below_transparent_obj;
+
+        _e_hwc_window_below_transparent_obj_map_apply(hwc_window);
+
+        evas_object_smart_member_add(hwc_window->below_transparent_obj, hwc_window->ec->frame);
+        evas_object_lower(hwc_window->below_transparent_obj);
+        evas_object_show(hwc_window->below_transparent_obj);
+
+        evas_object_event_callback_add(hwc_window->ec->frame, EVAS_CALLBACK_RESIZE,
+                                       _e_hwc_window_below_transparent_obj_cb_resize,
+                                       hwc_window);
+
+        EHWINF("Set below_transparent_obj", hwc_window->ec, hwc_window->hwc, hwc_window);
+     }
+   else
+     {
+        if (!hwc_window->below_transparent_obj) return;
+
+        evas_object_smart_member_del(hwc_window->below_transparent_obj);
+        E_FREE_FUNC(hwc_window->below_transparent_obj, evas_object_del);
+
+        if (hwc_window->ec)
+          evas_object_event_callback_del_full(hwc_window->ec->frame, EVAS_CALLBACK_RESIZE,
+                                              _e_hwc_window_below_transparent_obj_cb_resize,
+                                              hwc_window);
+
+        EHWINF("Unset below_transparent_obj", hwc_window->ec, hwc_window->hwc, hwc_window);
+     }
+}
index eb7bb64999dbf9fd7c4a04f5b94944763782a9bb..5a3657b947794c9a554e0c678d108685a0ec9d64 100644 (file)
@@ -161,6 +161,8 @@ struct _E_Hwc_Window
    E_Hwc_Presentation_Callback_List presentation_callbacks;
 
    struct wayland_tbm_client_queue *cqueue;
+
+   Evas_Object                   *below_transparent_obj;
 };
 
 struct _E_Hwc_Window_Target
@@ -271,5 +273,7 @@ EINTERN Eina_Bool                 e_hwc_window_presentation_callback_call(E_Hwc_
 
 struct wayland_tbm_client_queue  *e_hwc_window_wayland_tbm_client_queue_get(E_Hwc_Window *hwc_window);
 
+EINTERN void                      e_hwc_window_below_transparent_obj_set(E_Hwc_Window *hwc_window, Eina_Bool set);
+
 #endif // E_HWC_WINDOW_H
 #endif
index afbd54c5cade9a222a58132982da7e9ea8e53d83..474dfd6b1dbf41ec5d967efa65004fdb8f22e237 100644 (file)
@@ -2950,6 +2950,73 @@ _e_hwc_windows_buffer_clear(E_Hwc *hwc, tbm_surface_h tsurface)
    tbm_surface_unmap(tsurface);
 }
 
+static E_Hwc_Window *
+_e_hwc_windows_visible_ui_window_bottom_get(E_Hwc *hwc)
+{
+   E_Hwc_Window *hwc_window;
+   Eina_List *l;
+
+   EINA_LIST_REVERSE_FOREACH(hwc->visible_windows, l, hwc_window)
+     {
+        if (hwc_window->state == E_HWC_WINDOW_STATE_VIDEO)
+          continue;
+
+        return hwc_window;
+     }
+
+   return NULL;
+}
+
+static E_Hwc_Window *
+_e_hwc_windows_below_transparent_window_find(E_Hwc *hwc)
+{
+   E_Hwc_Window *hwc_window;
+
+   if (hwc->hwc_mode != E_HWC_MODE_HYBRID) return NULL;
+
+   hwc_window = _e_hwc_windows_visible_ui_window_bottom_get(hwc);
+   if (!hwc_window) return NULL;
+
+   if (hwc_window->state != E_HWC_WINDOW_STATE_DEVICE) return NULL;
+   if (!hwc_window->ec) return NULL;
+   if (hwc_window->ec->argb) return NULL;
+
+   return hwc_window;
+}
+
+static void
+_e_hwc_windows_below_transparent_window_update(E_Hwc *hwc)
+{
+   E_Hwc_Window *hwc_window;
+
+   hwc_window = _e_hwc_windows_below_transparent_window_find(hwc);
+   if (hwc_window)
+     {
+        if (hwc->below_transparent_window == hwc_window)
+          return;
+
+        if (hwc->below_transparent_window)
+          {
+             e_hwc_window_below_transparent_obj_set(hwc->below_transparent_window, EINA_FALSE);
+             e_hwc_window_unref(hwc->below_transparent_window);
+             hwc->below_transparent_window = NULL;
+          }
+
+        e_hwc_window_below_transparent_obj_set(hwc_window, EINA_TRUE);
+        e_hwc_window_ref(hwc_window);
+        hwc->below_transparent_window = hwc_window;
+     }
+   else
+     {
+        if (!hwc->below_transparent_window)
+          return;
+
+        e_hwc_window_below_transparent_obj_set(hwc->below_transparent_window, EINA_FALSE);
+        e_hwc_window_unref(hwc->below_transparent_window);
+        hwc->below_transparent_window = NULL;
+     }
+}
+
 /* evaluate the hwc_windows */
 static Eina_Bool
 _e_hwc_windows_evaluate(E_Hwc *hwc, E_Output_Display_Mode display_mode)
@@ -3011,6 +3078,8 @@ _e_hwc_windows_evaluate(E_Hwc *hwc, E_Output_Display_Mode display_mode)
         _e_hwc_windows_target_state_set(hwc->target_hwc_window, E_HWC_WINDOW_STATE_NONE);
      }
 
+   _e_hwc_windows_below_transparent_window_update(hwc);
+
    /* skip the target_buffer when the window is on trainsition of the composition */
    if ((hwc_mode != E_HWC_MODE_FULL) &&
        (!hwc->pp_set) && (display_mode != E_OUTPUT_DISPLAY_MODE_MIRROR) &&