summaryrefslogtreecommitdiff
path: root/src/lib/ecore
diff options
context:
space:
mode:
authorOtavio Pontes <otavio@profusion.mobi>2013-12-02 14:59:43 +0900
committerCarsten Haitzler (Rasterman) <raster@rasterman.com>2013-12-02 15:02:40 +0900
commitafd8a238d199a90e95a826c31a091e9adb11cc1e (patch)
tree5a91790c9133be4139f31d57515b3a8f4a806828 /src/lib/ecore
parent0b605c5daad9dd4934f9f0a4ae3ce2c00aadf63c (diff)
Adding the cubic-bezier curve to edje transitions
Summary: Adding an option to use a cubic-bezier curve in edje transitions. Reviewers: Sachiel, cedric, raster Reviewed By: raster CC: raster Differential Revision: https://phab.enlightenment.org/D319
Diffstat (limited to 'src/lib/ecore')
-rw-r--r--src/lib/ecore/Ecore_Common.h68
-rw-r--r--src/lib/ecore/ecore_anim.c120
2 files changed, 176 insertions, 12 deletions
diff --git a/src/lib/ecore/Ecore_Common.h b/src/lib/ecore/Ecore_Common.h
index bf6d1de8ed..39feead947 100644
--- a/src/lib/ecore/Ecore_Common.h
+++ b/src/lib/ecore/Ecore_Common.h
@@ -1899,7 +1899,8 @@ enum _Ecore_Pos_Map /* Position mappings */
1899 ECORE_POS_MAP_SINUSOIDAL_FACTOR, /**< Start slow, speed up then slow down at end, v1 being a power factor, 0.0 being linear, 1.0 being normal sinusoidal, 2.0 being much more pronounced sinusoidal (squared), 3.0 being cubed, etc. */ 1899 ECORE_POS_MAP_SINUSOIDAL_FACTOR, /**< Start slow, speed up then slow down at end, v1 being a power factor, 0.0 being linear, 1.0 being normal sinusoidal, 2.0 being much more pronounced sinusoidal (squared), 3.0 being cubed, etc. */
1900 ECORE_POS_MAP_DIVISOR_INTERP, /**< Start at gradient * v1, interpolated via power of v2 curve */ 1900 ECORE_POS_MAP_DIVISOR_INTERP, /**< Start at gradient * v1, interpolated via power of v2 curve */
1901 ECORE_POS_MAP_BOUNCE, /**< Start at 0.0 then "drop" like a ball bouncing to the ground at 1.0, and bounce v2 times, with decay factor of v1 */ 1901 ECORE_POS_MAP_BOUNCE, /**< Start at 0.0 then "drop" like a ball bouncing to the ground at 1.0, and bounce v2 times, with decay factor of v1 */
1902 ECORE_POS_MAP_SPRING /**< Start at 0.0 then "wobble" like a spring rest position 1.0, and wobble v2 times, with decay factor of v1 */ 1902 ECORE_POS_MAP_SPRING, /**< Start at 0.0 then "wobble" like a spring rest position 1.0, and wobble v2 times, with decay factor of v1 */
1903 ECORE_POS_MAP_CUBIC_BEZIER /**< Follow the cubic-bezier curve calculated with the points (x1, y1), (x2, y2) */
1903}; 1904};
1904typedef enum _Ecore_Pos_Map Ecore_Pos_Map; 1905typedef enum _Ecore_Pos_Map Ecore_Pos_Map;
1905 1906
@@ -2010,6 +2011,71 @@ EAPI double ecore_animator_frametime_get(void);
2010 * @since 1.1.0 2011 * @since 1.1.0
2011 */ 2012 */
2012EAPI double ecore_animator_pos_map(double pos, Ecore_Pos_Map map, double v1, double v2); 2013EAPI double ecore_animator_pos_map(double pos, Ecore_Pos_Map map, double v1, double v2);
2014
2015/**
2016 * @brief Maps an input position from 0.0 to 1.0 along a timeline to a
2017 * position in a different curve.
2018 *
2019 * @param pos The input position to map
2020 * @param map The mapping to use
2021 * @param v_size The size of the v array.
2022 * @param v An array with the double parameters to be used by the mapping.
2023 * NULL if not used.
2024 * @return The mapped value
2025 *
2026 * Takes an input position (0.0 to 1.0) and maps to a new position (normally
2027 * between 0.0 and 1.0, but it may go above/below 0.0 or 1.0 to show that it
2028 * has "overshot" the mark) using some interpolation (mapping) algorithm.
2029 *
2030 * This function useful to create non-linear animations. It offers a variety
2031 * of possible animation curves to be used:
2032 * @li ECORE_POS_MAP_LINEAR - Linear, returns @p pos
2033 * @li ECORE_POS_MAP_ACCELERATE - Start slow then speed up
2034 * @li ECORE_POS_MAP_DECELERATE - Start fast then slow down
2035 * @li ECORE_POS_MAP_SINUSOIDAL - Start slow, speed up then slow down at end
2036 * @li ECORE_POS_MAP_ACCELERATE_FACTOR - Start slow then speed up, v[0] being a
2037 * power factor, 0.0 being linear, 1.0 being ECORE_POS_MAP_ACCELERATE, 2.0
2038 * being much more pronounced accelerate (squared), 3.0 being cubed, etc.
2039 * @li ECORE_POS_MAP_DECELERATE_FACTOR - Start fast then slow down, v[0] being a
2040 * power factor, 0.0 being linear, 1.0 being ECORE_POS_MAP_DECELERATE, 2.0
2041 * being much more pronounced decelerate (squared), 3.0 being cubed, etc.
2042 * @li ECORE_POS_MAP_SINUSOIDAL_FACTOR - Start slow, speed up then slow down
2043 * at end, v[0] being a power factor, 0.0 being linear, 1.0 being
2044 * ECORE_POS_MAP_SINUSOIDAL, 2.0 being much more pronounced sinusoidal
2045 * (squared), 3.0 being cubed, etc.
2046 * @li ECORE_POS_MAP_DIVISOR_INTERP - Start at gradient * v[0], interpolated via
2047 * power of v2 curve
2048 * @li ECORE_POS_MAP_BOUNCE - Start at 0.0 then "drop" like a ball bouncing to
2049 * the ground at 1.0, and bounce v2 times, with decay factor of v[0]
2050 * @li ECORE_POS_MAP_SPRING - Start at 0.0 then "wobble" like a spring rest
2051 * position 1.0, and wobble v2 times, with decay factor of v[0]
2052 * @li ECORE_POS_MAP_CUBIC_BEZIER - Use an interpolated cubic-bezier curve
2053 * ajusted with parameters from v[0] to v[3].
2054 * @note When not listed v has no effect.
2055 *
2056 * @image html ecore-pos-map.png
2057 * @image latex ecore-pos-map.eps width=\textwidth
2058 *
2059 * One way to use this would be:
2060 * @code
2061 * double pos; // input position in a timeline from 0.0 to 1.0
2062 * double out; // output position after mapping
2063 * int x1, y1, x2, y2; // x1 & y1 are start position, x2 & y2 are end position
2064 * int x, y; // x & y are the calculated position
2065 * double v[2] = {1.8, 7};
2066 *
2067 * out = ecore_animator_pos_map(pos, ECORE_POS_MAP_BOUNCE, 2, v);
2068 * x = (x1 * out) + (x2 * (1.0 - out));
2069 * y = (y1 * out) + (y2 * (1.0 - out));
2070 * move_my_object_to(myobject, x, y);
2071 * @endcode
2072 * This will make an animation that bounces 7 each times diminishing by a
2073 * factor of 1.8.
2074 *
2075 * @see _Ecore_Pos_Map
2076 */
2077EAPI double ecore_animator_pos_map_n(double pos, Ecore_Pos_Map map, int v_size, double v[]);
2078
2013/** 2079/**
2014 * @brief Set the source of animator ticks for the mainloop 2080 * @brief Set the source of animator ticks for the mainloop
2015 * 2081 *
diff --git a/src/lib/ecore/ecore_anim.c b/src/lib/ecore/ecore_anim.c
index 7b33f71385..dd76dafcbf 100644
--- a/src/lib/ecore/ecore_anim.c
+++ b/src/lib/ecore/ecore_anim.c
@@ -313,6 +313,72 @@ _pos_map_spring(double pos,
313 return _pos_map_sin((M_PI / 2.0) + (p2 * len)) * decay; 313 return _pos_map_sin((M_PI / 2.0) + (p2 * len)) * decay;
314} 314}
315 315
316static double
317_cubic_bezier_a (double a1, double a2)
318{
319 return 1.0 - 3.0 * a2 + 3.0 * a1;
320}
321
322static double
323_cubic_bezier_b (double a1, double a2)
324{
325 return 3.0 * a2 - 6.0 * a1;
326}
327
328static double
329_cubic_bezier_c(double a1)
330{
331 return 3.0 * a1;
332}
333
334static double
335_cubic_bezier_calc(double t,
336 double a1,
337 double a2)
338{
339 return ((_cubic_bezier_a(a1, a2) * t +
340 _cubic_bezier_b(a1, a2)) * t +
341 _cubic_bezier_c(a1)) * t;
342}
343
344static double
345_cubic_bezier_slope_get(double t,
346 double a1,
347 double a2)
348{
349 return 3.0 * _cubic_bezier_a(a1, a2) * t * t +
350 2.0 * _cubic_bezier_b(a1, a2) * t +
351 _cubic_bezier_c(a1);
352}
353
354static double
355_cubic_bezier_t_get(double a,
356 double x1,
357 double x2)
358{
359 double guess_t = a;
360 for (int i = 0; i < 4; ++i)
361 {
362 double current_slope = _cubic_bezier_slope_get(a, x1, x2);
363 if (current_slope == 0.0)
364 return guess_t;
365 double current_x = _cubic_bezier_calc(guess_t, x1, x2) - a;
366 guess_t -= current_x / current_slope;
367 }
368 return guess_t;
369}
370
371static double
372_pos_map_cubic_bezier(double pos,
373 double x1,
374 double y1,
375 double x2,
376 double y2)
377{
378 if (x1 == y1 && x2 == y2) return pos;
379 return _cubic_bezier_calc(_cubic_bezier_t_get(pos, x1, x2), y1, y2);
380}
381
316#define DBL_TO(Fp) eina_f32p32_double_to(Fp) 382#define DBL_TO(Fp) eina_f32p32_double_to(Fp)
317#define DBL_FROM(D) eina_f32p32_double_from(D) 383#define DBL_FROM(D) eina_f32p32_double_from(D)
318#define INT_FROM(I) eina_f32p32_int_from(I) 384#define INT_FROM(I) eina_f32p32_int_from(I)
@@ -323,11 +389,13 @@ _pos_map_spring(double pos,
323#define MUL(A, B) eina_f32p32_mul(A, B) 389#define MUL(A, B) eina_f32p32_mul(A, B)
324 390
325EAPI double 391EAPI double
326ecore_animator_pos_map(double pos, 392ecore_animator_pos_map_n(double pos,
327 Ecore_Pos_Map map, 393 Ecore_Pos_Map map,
328 double v1, 394 int v_size,
329 double v2) 395 double v[])
330{ 396{
397 double v0 = 0, v1 = 0, v2 = 0, v3 = 0;
398
331 /* purely functional - locking not required */ 399 /* purely functional - locking not required */
332 if (pos >= 1.0) return 1.0; 400 if (pos >= 1.0) return 1.0;
333 else if (pos <= 0.0) 401 else if (pos <= 0.0)
@@ -353,30 +421,47 @@ ecore_animator_pos_map(double pos,
353 return pos; 421 return pos;
354 422
355 case ECORE_POS_MAP_ACCELERATE_FACTOR: 423 case ECORE_POS_MAP_ACCELERATE_FACTOR:
356 pos = _pos_map_accel_factor(pos, v1); 424 if (v_size > 0) v0 = v[0];
425 pos = _pos_map_accel_factor(pos, v0);
357 return pos; 426 return pos;
358 427
359 case ECORE_POS_MAP_DECELERATE_FACTOR: 428 case ECORE_POS_MAP_DECELERATE_FACTOR:
360 pos = 1.0 - _pos_map_accel_factor(1.0 - pos, v1); 429 if (v_size > 0) v0 = v[0];
430 pos = 1.0 - _pos_map_accel_factor(1.0 - pos, v0);
361 return pos; 431 return pos;
362 432
363 case ECORE_POS_MAP_SINUSOIDAL_FACTOR: 433 case ECORE_POS_MAP_SINUSOIDAL_FACTOR:
364 if (pos < 0.5) pos = _pos_map_accel_factor(pos * 2.0, v1) / 2.0; 434 if (v_size > 0) v0 = v[0];
365 else pos = 1.0 - (_pos_map_accel_factor((1.0 - pos) * 2.0, v1) / 2.0); 435 if (pos < 0.5) pos = _pos_map_accel_factor(pos * 2.0, v0) / 2.0;
436 else pos = 1.0 - (_pos_map_accel_factor((1.0 - pos) * 2.0, v0) / 2.0);
366 return pos; 437 return pos;
367 438
368 case ECORE_POS_MAP_DIVISOR_INTERP: 439 case ECORE_POS_MAP_DIVISOR_INTERP:
369 pos = _pos_map_pow(pos, v1, (int)v2); 440 if (v_size > 0) v0 = v[0];
441 if (v_size > 1) v1 = v[1];
442 pos = _pos_map_pow(pos, v0, (int)v1);
370 return pos; 443 return pos;
371 444
372 case ECORE_POS_MAP_BOUNCE: 445 case ECORE_POS_MAP_BOUNCE:
373 pos = _pos_map_spring(pos, (int)v2, v1); 446 if (v_size > 0) v0 = v[0];
447 if (v_size > 1) v1 = v[1];
448 pos = _pos_map_spring(pos, (int)v1, v0);
374 if (pos < 0.0) pos = -pos; 449 if (pos < 0.0) pos = -pos;
375 pos = 1.0 - pos; 450 pos = 1.0 - pos;
376 return pos; 451 return pos;
377 452
378 case ECORE_POS_MAP_SPRING: 453 case ECORE_POS_MAP_SPRING:
379 pos = 1.0 - _pos_map_spring(pos, (int)v2, v1); 454 if (v_size > 0) v0 = v[0];
455 if (v_size > 1) v1 = v[1];
456 pos = 1.0 - _pos_map_spring(pos, (int)v1, v0);
457 return pos;
458
459 case ECORE_POS_MAP_CUBIC_BEZIER:
460 if (v_size > 0) v0 = v[0];
461 if (v_size > 1) v1 = v[1];
462 if (v_size > 2) v2 = v[2];
463 if (v_size > 3) v3 = v[3];
464 pos = _pos_map_cubic_bezier(pos, v0, v1, v2, v3);
380 return pos; 465 return pos;
381 466
382 default: 467 default:
@@ -386,6 +471,19 @@ ecore_animator_pos_map(double pos,
386 return pos; 471 return pos;
387} 472}
388 473
474EAPI double
475ecore_animator_pos_map(double pos,
476 Ecore_Pos_Map map,
477 double v1,
478 double v2)
479{
480 double v[2];
481
482 v[0] = v1;
483 v[1] = v2;
484 return ecore_animator_pos_map_n(pos, map, 2, v);
485}
486
389EAPI void * 487EAPI void *
390ecore_animator_del(Ecore_Animator *obj) 488ecore_animator_del(Ecore_Animator *obj)
391{ 489{