Eina_Bool wait_update;
Eina_Bool hint_fetch;
uint32_t serial;
+
+ /* WORKAROUND for the client used manual rotation */
+ struct
+ {
+ Eina_Bool use;
+ int count;
+ Ecore_Timer *timer;
+ } wait_update_pending;
};
struct _E_Client_Rotation
static Eina_Bool _rot_cb_idle_enterer(void *data EINA_UNUSED);
static Eina_Bool
+_browser_check(E_Client *ec)
+{
+ const char *name = e_client_util_name_get(ec);
+ if (!name) return EINA_FALSE;
+ if (!strncmp(name, "browser", 7)) return EINA_TRUE;
+ return EINA_FALSE;
+}
+
+static Eina_Bool
_camera_check(E_Client *ec)
{
const char *name = e_client_util_name_get(ec);
EINA_SAFETY_ON_NULL_RETURN(rot);
ec = rot->ec;
- if (!ec)
- return;
+ if (!ec) return;
EDBG(ec, "Rotation Done: prev %d cur %d serial %u",
ec->e.state.rot.ang.curr,
ec->e.state.rot.ang.prev = ec->e.state.rot.ang.curr;
ec->e.state.rot.ang.curr = TIZEN_ROTATION_ANGLE_TO_INT(rot->cur_angle);
- EDBG(ec, "Rotation Done: prev %d cur %d",
- ec->e.state.rot.ang.prev, ec->e.state.rot.ang.curr);
-
if (TIZEN_ROTATION_ANGLE_TO_INT(rot->cur_angle) == ec->e.state.rot.ang.next)
{
ec->e.state.rot.ang.next = -1;
}
else
{
+ /* it means that we need the next buffer commit after rotation ack event.
+ * once we get next buffer commit, policy module attempts to remove
+ * this ec from rotation_list_remove. and then, rotation process is finished.
+ */
rot->wait_update = EINA_TRUE;
+
+ /* WORKAROUND
+ *
+ * Until now, we have assumed that the buffer commit event after the rotation
+ * ack event informs us of completion of rotation. However this assumption could
+ * be wrong because the rotation ack event is dispatched by main thread of client,
+ * whereas the buffer commit event could be dispatched by other thread.
+ *
+ * The ideal solution for resolving this issue is introduction of same protocol
+ * serial number between the rotation ack event and buffer commit event. But this
+ * approach needs much of changes for EFL, E20 and DDK. Thus I have added workaround
+ * code for quick resolving this.
+ *
+ * We have to extend EFL, E20 and DDK to support this later.
+ */
+ if (_browser_check(ec))
+ {
+ if (rot->wait_update_pending.timer)
+ ecore_timer_del(rot->wait_update_pending.timer);
+
+ rot->wait_update_pending.timer = NULL;
+ rot->wait_update_pending.use = EINA_TRUE;
+ rot->wait_update_pending.count = 2;
+ }
}
}
}
Eina_List *list, *l;
E_Client *child;
int curr_rot;
+ Policy_Ext_Rotation *ext_rot;
if (!ec) return EINA_FALSE;
TRACE_DS_END();
return EINA_FALSE;
}
- else
- ;
}
else
{
}
TRACE_DS_END();
+ ext_rot = eina_hash_find(rot_hash, &ec);
+ if (ext_rot)
+ {
+ if (ext_rot->wait_update_pending.timer)
+ ecore_timer_del(ext_rot->wait_update_pending.timer);
+ ext_rot->wait_update_pending.timer = NULL;
+ }
+
// in case same with next angle.
curr_rot = e_client_rotation_next_angle_get(ec);
if (curr_rot == rotation)
ELOGF("ROTATION", "Do rotation of child win %s(%p)",
NULL, NULL, child->icccm.name, child);
- if (e_client_rotation_set(child, rotation))
- {
- ;
- }
- else
- {
- ;
- }
+ e_client_rotation_set(child, rotation);
}
eina_list_free(list);
}
static void
+_e_client_rotation_wait_update_clear(E_Client *ec)
+{
+ Policy_Ext_Rotation *rot;
+
+ rot = eina_hash_find(rot_hash, &ec);
+ if (!rot) return;
+
+ rot->wait_update_pending.timer = NULL;
+
+ _e_client_rotation_list_remove(ec);
+ if (ec->e.state.rot.pending_show)
+ {
+ ec->e.state.rot.pending_show = 0;
+ evas_object_show(ec->frame);
+ e_comp_object_damage(ec->frame, 0, 0, ec->w, ec->h);
+ }
+
+ if (rot->show_grab)
+ E_FREE_FUNC(rot->show_grab, e_policy_visibility_client_grab_release);
+
+ rot->wait_update = EINA_FALSE;
+}
+
+static Eina_Bool
+_e_client_rotation_wait_update_pending_timeout(void *data)
+{
+ E_Client *ec = (E_Client *)data;
+
+ if ((ec) && (!e_object_is_del(E_OBJECT(ec))))
+ WRN("Timeout Wait Update Pending %s(%p)",
+ ec->icccm.name ? ec->icccm.name : "", ec);
+ else
+ WRN("Timeout Wait Update Pending (%p)", ec);
+
+ _e_client_rotation_wait_update_clear(ec);
+
+ return ECORE_CALLBACK_CANCEL;
+}
+
+static void
_rot_cb_wl_buffer_change(void *d EINA_UNUSED, E_Client *ec)
{
Policy_Ext_Rotation *rot;
}
else if (rot->wait_update)
{
- DBG("Update Buffer After Rotation Done ec '%s'(%p) b %p",
- ev->ec->icccm.name ? ev->ec->icccm.name : "", ev->ec, e_pixmap_resource_get(ev->ec->pixmap));
- _e_client_rotation_list_remove(ev->ec);
- if (ev->ec->e.state.rot.pending_show)
+ DBG("Update Buffer After Rotation Done ec '%s'(%p) b %p pending:%d count:%d",
+ ev->ec->icccm.name ? ev->ec->icccm.name : "",
+ ev->ec,
+ e_pixmap_resource_get(ev->ec->pixmap),
+ rot->wait_update_pending.use,
+ rot->wait_update_pending.count);
+
+ if (rot->wait_update_pending.use)
{
- ev->ec->e.state.rot.pending_show = 0;
- evas_object_show(ev->ec->frame);
- e_comp_object_damage(ev->ec->frame, 0, 0, ev->ec->w, ev->ec->h);
- }
+ if (rot->wait_update_pending.count > 0)
+ {
+ if (rot->wait_update_pending.count == 2)
+ {
+ if (rot->wait_update_pending.timer)
+ ecore_timer_del(rot->wait_update_pending.timer);
- if (rot->show_grab)
- E_FREE_FUNC(rot->show_grab, e_policy_visibility_client_grab_release);
+ rot->wait_update_pending.timer = ecore_timer_add(0.1f,
+ _e_client_rotation_wait_update_pending_timeout,
+ ev->ec);
+ }
- rot->wait_update = EINA_FALSE;
+ rot->wait_update_pending.count--;
+ return ECORE_CALLBACK_RENEW;
+ }
+ else
+ {
+ if (rot->wait_update_pending.timer)
+ ecore_timer_del(rot->wait_update_pending.timer);
+ rot->wait_update_pending.timer = NULL;
+ }
+ }
+
+ _e_client_rotation_wait_update_clear(ev->ec);
}
if (ev->ec->e.state.rot.pending_show)
ext_rot = eina_hash_find(rot_hash, &ec);
if (ext_rot)
{
+ if (ext_rot->wait_update_pending.timer)
+ ecore_timer_del(ext_rot->wait_update_pending.timer);
+ ext_rot->wait_update_pending.timer = NULL;
+
EINA_LIST_FREE(ext_rot->rotation_list, res)
wl_resource_set_user_data(res, NULL);