Animate transitions for zoom focus point change.

Handle the transition when focus changes from text cursor to
mouse pointer or vice versa.
This commit is contained in:
Scott Moreau
2012-06-17 18:10:58 -06:00
committed by Kristian Høgsberg
parent 5b72a4d21d
commit 8dacaaba1b
3 changed files with 176 additions and 60 deletions
+164 -52
View File
@@ -1633,7 +1633,7 @@ notify_motion(struct wl_seat *seat, uint32_t time, wl_fixed_t x, wl_fixed_t y)
if (output->zoom.active && if (output->zoom.active &&
pixman_region32_contains_point(&output->region, pixman_region32_contains_point(&output->region,
ix, iy, NULL)) ix, iy, NULL))
weston_output_update_zoom(output, x, y, ZOOM_FOCUS_POINTER); weston_output_update_zoom(output, ZOOM_FOCUS_POINTER);
weston_device_repick(seat); weston_device_repick(seat);
interface = seat->pointer->grab->interface; interface = seat->pointer->grab->interface;
@@ -2783,9 +2783,11 @@ weston_text_cursor_position_notify(struct weston_surface *surface,
pixman_region32_contains_point(&output->region, pixman_region32_contains_point(&output->region,
wl_fixed_to_int(global_x), wl_fixed_to_int(global_x),
wl_fixed_to_int(global_y), wl_fixed_to_int(global_y),
NULL)) NULL)) {
weston_output_update_zoom(output, global_x, global_y, output->zoom.text_cursor.x = global_x;
ZOOM_FOCUS_TEXT); output->zoom.text_cursor.y = global_y;
weston_output_update_zoom(output, ZOOM_FOCUS_TEXT);
}
} }
static void static void
@@ -2815,8 +2817,133 @@ weston_zoom_frame_z(struct weston_animation *animation,
} }
static void static void
weston_zoom_transition(struct weston_output *output) weston_zoom_frame_xy(struct weston_animation *animation,
struct weston_output *output, uint32_t msecs)
{ {
wl_fixed_t x, y;
if (animation->frame_counter <= 1)
output->zoom.spring_xy.timestamp = msecs;
weston_spring_update(&output->zoom.spring_xy, msecs);
x = output->zoom.from.x - ((output->zoom.from.x - output->zoom.to.x) *
output->zoom.spring_xy.current);
y = output->zoom.from.y - ((output->zoom.from.y - output->zoom.to.y) *
output->zoom.spring_xy.current);
output->zoom.current.x = x;
output->zoom.current.y = y;
if (weston_spring_done(&output->zoom.spring_xy)) {
output->zoom.spring_xy.current = output->zoom.spring_xy.target;
output->zoom.current.x =
(output->zoom.type == ZOOM_FOCUS_POINTER) ?
output->compositor->seat->pointer.x :
output->zoom.text_cursor.x;
output->zoom.current.y =
(output->zoom.type == ZOOM_FOCUS_POINTER) ?
output->compositor->seat->pointer.y :
output->zoom.text_cursor.y;
wl_list_remove(&animation->link);
wl_list_init(&animation->link);
}
output->dirty = 1;
weston_output_damage(output);
}
static void
zoom_area_center_from_pointer(struct weston_output *output,
wl_fixed_t *x, wl_fixed_t *y)
{
float level = output->zoom.spring_z.current;
wl_fixed_t offset_x = wl_fixed_from_int(output->x);
wl_fixed_t offset_y = wl_fixed_from_int(output->y);
wl_fixed_t w = wl_fixed_from_int(output->current->width);
wl_fixed_t h = wl_fixed_from_int(output->current->height);
*x -= ((((*x - offset_x) / (float) w) - 0.5) * (w * (1.0 - level)));
*y -= ((((*y - offset_y) / (float) h) - 0.5) * (h * (1.0 - level)));
}
static void
weston_output_update_zoom_transform(struct weston_output *output)
{
uint32_t type = output->zoom.type;
float global_x, global_y;
wl_fixed_t x = output->zoom.current.x;
wl_fixed_t y = output->zoom.current.y;
float trans_min, trans_max;
float ratio, level;
level = output->zoom.spring_z.current;
ratio = 1 / level;
if (!output->zoom.active || level > output->zoom.max_level)
return;
if (type == ZOOM_FOCUS_POINTER &&
wl_list_empty(&output->zoom.animation_xy.link))
zoom_area_center_from_pointer(output, &x, &y);
global_x = wl_fixed_to_double(x);
global_y = wl_fixed_to_double(y);
output->zoom.trans_x =
((((global_x - output->x) / output->current->width) *
(level * 2)) - level) * ratio;
output->zoom.trans_y =
((((global_y - output->y) / output->current->height) *
(level * 2)) - level) * ratio;
trans_max = level * 2 - level;
trans_min = -trans_max;
/* Clip zoom area to output */
if (output->zoom.trans_x > trans_max)
output->zoom.trans_x = trans_max;
else if (output->zoom.trans_x < trans_min)
output->zoom.trans_x = trans_min;
if (output->zoom.trans_y > trans_max)
output->zoom.trans_y = trans_max;
else if (output->zoom.trans_y < trans_min)
output->zoom.trans_y = trans_min;
}
static void
weston_zoom_transition(struct weston_output *output, uint32_t type,
wl_fixed_t x, wl_fixed_t y)
{
if (output->zoom.type != type) {
/* Set from/to points and start animation */
output->zoom.spring_xy.current = 0.0;
output->zoom.spring_xy.previous = 0.0;
output->zoom.spring_xy.target = 1.0;
if (wl_list_empty(&output->zoom.animation_xy.link)) {
output->zoom.animation_xy.frame_counter = 0;
wl_list_insert(output->animation_list.prev,
&output->zoom.animation_xy.link);
output->zoom.from.x = (type == ZOOM_FOCUS_TEXT) ?
x : output->zoom.text_cursor.x;
output->zoom.from.y = (type == ZOOM_FOCUS_TEXT) ?
y : output->zoom.text_cursor.y;
} else {
output->zoom.from.x = output->zoom.current.x;
output->zoom.from.y = output->zoom.current.y;
}
output->zoom.to.x = (type == ZOOM_FOCUS_POINTER) ?
x : output->zoom.text_cursor.x;
output->zoom.to.y = (type == ZOOM_FOCUS_POINTER) ?
y : output->zoom.text_cursor.y;
output->zoom.current.x = output->zoom.from.x;
output->zoom.current.y = output->zoom.from.y;
output->zoom.type = type;
}
if (output->zoom.level != output->zoom.spring_z.current) { if (output->zoom.level != output->zoom.spring_z.current) {
output->zoom.spring_z.target = output->zoom.level; output->zoom.spring_z.target = output->zoom.level;
if (wl_list_empty(&output->zoom.animation_z.link)) { if (wl_list_empty(&output->zoom.animation_z.link)) {
@@ -2831,55 +2958,37 @@ weston_zoom_transition(struct weston_output *output)
} }
WL_EXPORT void WL_EXPORT void
weston_output_update_zoom(struct weston_output *output, weston_output_update_zoom(struct weston_output *output, uint32_t type)
wl_fixed_t x,
wl_fixed_t y,
uint32_t type)
{ {
float global_x, global_y; wl_fixed_t x = output->compositor->seat->pointer.x;
float trans_min, trans_max; wl_fixed_t y = output->compositor->seat->pointer.y;
float ratio, level;
level = output->zoom.spring_z.current; zoom_area_center_from_pointer(output, &x, &y);
if (!output->zoom.active || level > output->zoom.max_level) if (type == ZOOM_FOCUS_POINTER) {
return; if (wl_list_empty(&output->zoom.animation_xy.link)) {
output->zoom.current.x =
output->zoom.type = type; output->compositor->seat->pointer.x;
output->zoom.current.y =
output->zoom.fx = x; output->compositor->seat->pointer.y;
output->zoom.fy = y; } else {
output->zoom.to.x = x;
global_x = wl_fixed_to_double(x); output->zoom.to.y = y;
global_y = wl_fixed_to_double(y); }
output->zoom.trans_x =
(((global_x - output->x) / output->current->width) *
(level * 2)) - level;
output->zoom.trans_y =
(((global_y - output->y) / output->current->height) *
(level * 2)) - level;
if (type == ZOOM_FOCUS_TEXT) {
ratio = 1 / level;
output->zoom.trans_x *= ratio;
output->zoom.trans_y *= ratio;
trans_max = level * 2 - level;
trans_min = -trans_max;
if (output->zoom.trans_x > trans_max)
output->zoom.trans_x = trans_max;
else if (output->zoom.trans_x < trans_min)
output->zoom.trans_x = trans_min;
if (output->zoom.trans_y > trans_max)
output->zoom.trans_y = trans_max;
else if (output->zoom.trans_y < trans_min)
output->zoom.trans_y = trans_min;
} }
weston_zoom_transition(output); if (type == ZOOM_FOCUS_TEXT) {
if (wl_list_empty(&output->zoom.animation_xy.link)) {
output->zoom.current.x = output->zoom.text_cursor.x;
output->zoom.current.y = output->zoom.text_cursor.y;
} else {
output->zoom.to.x = output->zoom.text_cursor.x;
output->zoom.to.y = output->zoom.text_cursor.y;
}
}
weston_zoom_transition(output, type, x, y);
weston_output_update_zoom_transform(output);
} }
WL_EXPORT void WL_EXPORT void
@@ -2904,9 +3013,7 @@ weston_output_update_matrix(struct weston_output *output)
magnification = 1 / (1 - output->zoom.spring_z.current); magnification = 1 / (1 - output->zoom.spring_z.current);
weston_matrix_init(&camera); weston_matrix_init(&camera);
weston_matrix_init(&modelview); weston_matrix_init(&modelview);
weston_output_update_zoom(output, output->zoom.fx, weston_output_update_zoom(output, output->zoom.type);
output->zoom.fy,
output->zoom.type);
weston_matrix_translate(&camera, output->zoom.trans_x, weston_matrix_translate(&camera, output->zoom.trans_x,
flip * output->zoom.trans_y, 0); flip * output->zoom.trans_y, 0);
weston_matrix_invert(&modelview, &camera); weston_matrix_invert(&modelview, &camera);
@@ -2951,10 +3058,15 @@ weston_output_init(struct weston_output *output, struct weston_compositor *c,
output->zoom.level = 0.0; output->zoom.level = 0.0;
output->zoom.trans_x = 0.0; output->zoom.trans_x = 0.0;
output->zoom.trans_y = 0.0; output->zoom.trans_y = 0.0;
output->zoom.type = ZOOM_FOCUS_POINTER;
weston_spring_init(&output->zoom.spring_z, 250.0, 0.0, 0.0); weston_spring_init(&output->zoom.spring_z, 250.0, 0.0, 0.0);
output->zoom.spring_z.friction = 1000; output->zoom.spring_z.friction = 1000;
output->zoom.animation_z.frame = weston_zoom_frame_z; output->zoom.animation_z.frame = weston_zoom_frame_z;
wl_list_init(&output->zoom.animation_z.link); wl_list_init(&output->zoom.animation_z.link);
weston_spring_init(&output->zoom.spring_xy, 250.0, 0.0, 0.0);
output->zoom.spring_xy.friction = 1000;
output->zoom.animation_xy.frame = weston_zoom_frame_xy;
wl_list_init(&output->zoom.animation_xy.link);
output->flags = flags; output->flags = flags;
weston_output_move(output, x, y); weston_output_move(output, x, y);
+11 -4
View File
@@ -115,16 +115,25 @@ enum {
ZOOM_FOCUS_TEXT ZOOM_FOCUS_TEXT
}; };
struct weston_fixed_point {
wl_fixed_t x, y;
};
struct weston_output_zoom { struct weston_output_zoom {
int active; int active;
uint32_t type; uint32_t type;
float increment; float increment;
float level; float level;
float max_level; float max_level;
wl_fixed_t fx, fy;
float trans_x, trans_y; float trans_x, trans_y;
struct weston_animation animation_z; struct weston_animation animation_z;
struct weston_spring spring_z; struct weston_spring spring_z;
struct weston_animation animation_xy;
struct weston_spring spring_xy;
struct weston_fixed_point from;
struct weston_fixed_point to;
struct weston_fixed_point current;
struct weston_fixed_point text_cursor;
}; };
/* bit compatible with drm definitions. */ /* bit compatible with drm definitions. */
@@ -633,9 +642,7 @@ void
weston_text_cursor_position_notify(struct weston_surface *surface, weston_text_cursor_position_notify(struct weston_surface *surface,
wl_fixed_t x, wl_fixed_t y); wl_fixed_t x, wl_fixed_t y);
void void
weston_output_update_zoom(struct weston_output *output, weston_output_update_zoom(struct weston_output *output, uint32_t type);
wl_fixed_t x, wl_fixed_t y,
uint32_t type);
void void
weston_output_update_matrix(struct weston_output *output); weston_output_update_matrix(struct weston_output *output);
void void
+1 -4
View File
@@ -2185,10 +2185,7 @@ do_zoom(struct wl_seat *seat, uint32_t time, uint32_t key, uint32_t axis,
output->zoom.spring_z.target = output->zoom.level; output->zoom.spring_z.target = output->zoom.level;
weston_output_update_zoom(output, weston_output_update_zoom(output, output->zoom.type);
seat->pointer->x,
seat->pointer->y,
ZOOM_FOCUS_POINTER);
} }
} }
} }