Tweeny 3.2.0
A Tweening library for modern C++
Loading...
Searching...
No Matches
easing.h
1/*
2 This file is part of the Tweeny library.
3
4 Copyright (c) 2016-2021 Leonardo Guilherme Lucena de Freitas
5 Copyright (c) 2016 Guilherme R. Costa
6
7 Permission is hereby granted, free of charge, to any person obtaining a copy of
8 this software and associated documentation files (the "Software"), to deal in
9 the Software without restriction, including without limitation the rights to
10 use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
11 the Software, and to permit persons to whom the Software is furnished to do so,
12 subject to the following conditions:
13
14 The above copyright notice and this permission notice shall be included in all
15 copies or substantial portions of the Software.
16
17 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
19 FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
20 COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
21 IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
22 CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23*/
24
31#ifndef TWEENY_EASING_H
32#define TWEENY_EASING_H
33
34#include <cmath>
35#include <type_traits>
36
37#ifndef M_PI
38#define M_PI 3.14159265358979323846
39#endif
40
117namespace tweeny {
130 class easing {
131 public:
138 enum class enumerated {
139 def,
140 linear,
141 stepped,
142 quadraticIn,
143 quadraticOut,
144 quadraticInOut,
145 cubicIn,
146 cubicOut,
147 cubicInOut,
148 quarticIn,
149 quarticOut,
150 quarticInOut,
151 quinticIn,
152 quinticOut,
153 quinticInOut,
154 sinusoidalIn,
155 sinusoidalOut,
156 sinusoidalInOut,
157 exponentialIn,
158 exponentialOut,
159 exponentialInOut,
160 circularIn,
161 circularOut,
162 circularInOut,
163 bounceIn,
164 bounceOut,
165 bounceInOut,
166 elasticIn,
167 elasticOut,
168 elasticInOut,
169 backIn,
170 backOut,
171 backInOut
172 };
173
178 static constexpr struct steppedEasing {
179 template<typename T>
180 static T run(float position, T start, T end) {
181 return start;
182 }
183 } stepped = steppedEasing{};
184
189 static constexpr struct defaultEasing {
190 template<class...> struct voidify { using type = void; };
191 template<class... Ts> using void_t = typename voidify<Ts...>::type;
192
193 template<class T, class = void>
194 struct supports_arithmetic_operations : std::false_type {};
195
196 template<class T>
197 struct supports_arithmetic_operations<T, void_t<
198 decltype(std::declval<T>() + std::declval<T>()),
199 decltype(std::declval<T>() - std::declval<T>()),
200 decltype(std::declval<T>() * std::declval<T>()),
201 decltype(std::declval<T>() * std::declval<float>()),
202 decltype(std::declval<float>() * std::declval<T>())
203 >> : std::true_type{};
204
205
206 template<typename T>
207 static typename std::enable_if<std::is_integral<T>::value, T>::type run(float position, T start, T end) {
208 return static_cast<T>(roundf((end - start) * position + start));
209 }
210
211 template<typename T>
212 static typename std::enable_if<supports_arithmetic_operations<T>::value && !std::is_integral<T>::value, T>::type run(float position, T start, T end) {
213 return static_cast<T>((end - start) * position + start);
214 }
215
216 template<typename T>
217 static typename std::enable_if<!supports_arithmetic_operations<T>::value, T>::type run(float position, T start, T end) {
218 return start;
219 }
220 } def = defaultEasing{};
221
226 static constexpr struct linearEasing {
227 template<typename T>
228 static typename std::enable_if<std::is_integral<T>::value, T>::type run(float position, T start, T end) {
229 return static_cast<T>(roundf((end - start) * position + start));
230 }
231
232 template<typename T>
233 static typename std::enable_if<!std::is_integral<T>::value, T>::type run(float position, T start, T end) {
234 return static_cast<T>((end - start) * position + start);
235 }
236 } linear = linearEasing{};
237
242 static constexpr struct quadraticInEasing {
243 template<typename T>
244 static T run(float position, T start, T end) {
245 return static_cast<T>((end - start) * position * position + start);
246 }
247 } quadraticIn = quadraticInEasing{};
248
253 static constexpr struct quadraticOutEasing {
254 template<typename T>
255 static T run(float position, T start, T end) {
256 return static_cast<T>((-(end - start)) * position * (position - 2) + start);
257 }
258 } quadraticOut = quadraticOutEasing{};
259
264 static constexpr struct quadraticInOutEasing {
265 template<typename T>
266 static T run(float position, T start, T end) {
267 position *= 2;
268 if (position < 1) {
269 return static_cast<T>(((end - start) / 2) * position * position + start);
270 }
271
272 --position;
273 return static_cast<T>((-(end - start) / 2) * (position * (position - 2) - 1) + start);
274 }
275 } quadraticInOut = quadraticInOutEasing{};
276
281 static constexpr struct cubicInEasing {
282 template<typename T>
283 static T run(float position, T start, T end) {
284 return static_cast<T>((end - start) * position * position * position + start);
285 }
286 } cubicIn = cubicInEasing{};
287
292 static constexpr struct cubicOutEasing {
293 template<typename T>
294 static T run(float position, T start, T end) {
295 --position;
296 return static_cast<T>((end - start) * (position * position * position + 1) + start);
297 }
298 } cubicOut = cubicOutEasing{};
299
304 static constexpr struct cubicInOutEasing {
305 template<typename T>
306 static T run(float position, T start, T end) {
307 position *= 2;
308 if (position < 1) {
309 return static_cast<T>(((end - start) / 2) * position * position * position + start);
310 }
311 position -= 2;
312 return static_cast<T>(((end - start) / 2) * (position * position * position + 2) + start);
313 }
314 } cubicInOut = cubicInOutEasing{};
315
320 static constexpr struct quarticInEasing {
321 template<typename T>
322 static T run(float position, T start, T end) {
323 return static_cast<T>((end - start) * position * position * position * position + start);
324 }
325 } quarticIn = quarticInEasing{};
326
331 static constexpr struct quarticOutEasing {
332 template<typename T>
333 static T run(float position, T start, T end) {
334 --position;
335 return static_cast<T>( -(end - start) * (position * position * position * position - 1) + start);
336 }
337 } quarticOut = quarticOutEasing{};
338
343 static constexpr struct quarticInOutEasing {
344 template<typename T>
345 static T run(float position, T start, T end) {
346 position *= 2;
347 if (position < 1) {
348 return static_cast<T>(((end - start) / 2) * (position * position * position * position) +
349 start);
350 }
351 position -= 2;
352 return static_cast<T>((-(end - start) / 2) * (position * position * position * position - 2) +
353 start);
354 }
355 } quarticInOut = quarticInOutEasing{};
356
361 static constexpr struct quinticInEasing {
362 template<typename T>
363 static T run(float position, T start, T end) {
364 return static_cast<T>((end - start) * position * position * position * position * position + start);
365 }
366 } quinticIn = quinticInEasing{};
367
372 static constexpr struct quinticOutEasing {
373 template<typename T>
374 static T run(float position, T start, T end) {
375 position--;
376 return static_cast<T>((end - start) * (position * position * position * position * position + 1) +
377 start);
378 }
379 } quinticOut = quinticOutEasing{};
380
385 static constexpr struct quinticInOutEasing {
386 template<typename T>
387 static T run(float position, T start, T end) {
388 position *= 2;
389 if (position < 1) {
390 return static_cast<T>(
391 ((end - start) / 2) * (position * position * position * position * position) +
392 start);
393 }
394 position -= 2;
395 return static_cast<T>(
396 ((end - start) / 2) * (position * position * position * position * position + 2) +
397 start);
398 }
399 } quinticInOut = quinticInOutEasing{};
400
405 static constexpr struct sinusoidalInEasing {
406 template<typename T>
407 static T run(float position, T start, T end) {
408 return static_cast<T>(-(end - start) * cosf(position * static_cast<float>(M_PI) / 2) + (end - start) + start);
409 }
410 } sinusoidalIn = sinusoidalInEasing{};
411
416 static constexpr struct sinusoidalOutEasing {
417 template<typename T>
418 static T run(float position, T start, T end) {
419 return static_cast<T>((end - start) * sinf(position * static_cast<float>(M_PI) / 2) + start);
420 }
421 } sinusoidalOut = sinusoidalOutEasing{};
422
427 static constexpr struct sinusoidalInOutEasing {
428 template<typename T>
429 static T run(float position, T start, T end) {
430 return static_cast<T>((-(end - start) / 2) * (cosf(position * static_cast<float>(M_PI)) - 1) + start);
431 }
432 } sinusoidalInOut = sinusoidalInOutEasing{};
433
438 static constexpr struct exponentialInEasing {
439 template<typename T>
440 static T run(float position, T start, T end) {
441 return static_cast<T>((end - start) * powf(2, 10 * (position - 1)) + start);
442 }
443 } exponentialIn = exponentialInEasing{};
444
449 static constexpr struct exponentialOutEasing {
450 template<typename T>
451 static T run(float position, T start, T end) {
452 return static_cast<T>((end - start) * (-powf(2, -10 * position) + 1) + start);
453 }
454 } exponentialOut = exponentialOutEasing{};
455
460 static constexpr struct exponentialInOutEasing {
461 template<typename T>
462 static T run(float position, T start, T end) {
463 position *= 2;
464 if (position < 1) {
465 return static_cast<T>(((end - start) / 2) * powf(2, 10 * (position - 1)) + start);
466 }
467 --position;
468 return static_cast<T>(((end - start) / 2) * (-powf(2, -10 * position) + 2) + start);
469 }
470 } exponentialInOut = exponentialInOutEasing{};
471
476 static constexpr struct circularInEasing {
477 template<typename T>
478 static T run(float position, T start, T end) {
479 return static_cast<T>( -(end - start) * (sqrtf(1 - position * position) - 1) + start );
480 }
481 } circularIn = circularInEasing{};
482
487 static constexpr struct circularOutEasing {
488 template<typename T>
489 static T run(float position, T start, T end) {
490 --position;
491 return static_cast<T>((end - start) * (sqrtf(1 - position * position)) + start);
492 }
493 } circularOut = circularOutEasing{};
494
499 static constexpr struct circularInOutEasing {
500 template<typename T>
501 static T run(float position, T start, T end) {
502 position *= 2;
503 if (position < 1) {
504 return static_cast<T>((-(end - start) / 2) * (sqrtf(1 - position * position) - 1) + start);
505 }
506
507 position -= 2;
508 return static_cast<T>(((end - start) / 2) * (sqrtf(1 - position * position) + 1) + start);
509 }
510 } circularInOut = circularInOutEasing{};
511
516 static constexpr struct bounceInEasing {
517 template<typename T>
518 static T run(float position, T start, T end) {
519 return (end - start) - bounceOut.run((1 - position), T(), end) + start;
520 }
521 } bounceIn = bounceInEasing{};
522
527 static constexpr struct bounceOutEasing {
528 template<typename T>
529 static T run(float position, T start, T end) {
530 T c = end - start;
531 if (position < (1 / 2.75f)) {
532 return static_cast<T>(c * (7.5625f * position * position) + start);
533 } else if (position < (2.0f / 2.75f)) {
534 float postFix = position -= (1.5f / 2.75f);
535 return static_cast<T>(c * (7.5625f * (postFix) * position + .75f) + start);
536 } else if (position < (2.5f / 2.75f)) {
537 float postFix = position -= (2.25f / 2.75f);
538 return static_cast<T>(c * (7.5625f * (postFix) * position + .9375f) + start);
539 } else {
540 float postFix = position -= (2.625f / 2.75f);
541 return static_cast<T>(c * (7.5625f * (postFix) * position + .984375f) + start);
542 }
543 }
544 } bounceOut = bounceOutEasing{};
545
550 static constexpr struct bounceInOutEasing {
551 template<typename T>
552 static T run(float position, T start, T end) {
553 if (position < 0.5f) return static_cast<T>(bounceIn.run(position * 2, T(), end) * .5f + start);
554 else return static_cast<T>(bounceOut.run((position * 2 - 1), T(), end) * .5f + (end - start) * .5f + start);
555 }
556 } bounceInOut = bounceInOutEasing{};
557
562 static constexpr struct elasticInEasing {
563 template<typename T>
564 static T run(float position, T start, T end) {
565 if (position <= 0.00001f) return start;
566 if (position >= 0.999f) return end;
567 float p = .3f;
568 auto a = end - start;
569 float s = p / 4;
570 float postFix =
571 a * powf(2, 10 * (position -= 1)); // this is a fix, again, with post-increment operators
572 return static_cast<T>(-(postFix * sinf((position - s) * (2 * static_cast<float>(M_PI)) / p)) + start);
573 }
574 } elasticIn = elasticInEasing{};
575
580 static constexpr struct elasticOutEasing {
581 template<typename T>
582 static T run(float position, T start, T end) {
583 if (position <= 0.00001f) return start;
584 if (position >= 0.999f) return end;
585 float p = .3f;
586 auto a = end - start;
587 float s = p / 4;
588 return static_cast<T>(a * powf(2, -10 * position) * sinf((position - s) * (2 * static_cast<float>(M_PI)) / p) + end);
589 }
590 } elasticOut = elasticOutEasing{};
591
596 static constexpr struct elasticInOutEasing {
597 template<typename T>
598 static T run(float position, T start, T end) {
599 if (position <= 0.00001f) return start;
600 if (position >= 0.999f) return end;
601 position *= 2;
602 float p = (.3f * 1.5f);
603 auto a = end - start;
604 float s = p / 4;
605 float postFix;
606
607 if (position < 1) {
608 postFix = a * powf(2, 10 * (position -= 1)); // postIncrement is evil
609 return static_cast<T>(-0.5f * (postFix * sinf((position - s) * (2 * static_cast<float>(M_PI)) / p)) + start);
610 }
611 postFix = a * powf(2, -10 * (position -= 1)); // postIncrement is evil
612 return static_cast<T>(postFix * sinf((position - s) * (2 * static_cast<float>(M_PI)) / p) * .5f + end);
613 }
614 } elasticInOut = elasticInOutEasing{};
615
620 static constexpr struct backInEasing {
621 template<typename T>
622 static T run(float position, T start, T end) {
623 float s = 1.70158f;
624 float postFix = position;
625 return static_cast<T>((end - start) * (postFix) * position * ((s + 1) * position - s) + start);
626 }
627 } backIn = backInEasing{};
628
633 static constexpr struct backOutEasing {
634 template<typename T>
635 static T run(float position, T start, T end) {
636 float s = 1.70158f;
637 position -= 1;
638 return static_cast<T>((end - start) * ((position) * position * ((s + 1) * position + s) + 1) + start);
639 }
640 } backOut = backOutEasing{};
641
646 static constexpr struct backInOutEasing {
647 template<typename T>
648 static T run(float position, T start, T end) {
649 float s = 1.70158f;
650 float t = position;
651 auto b = start;
652 auto c = end - start;
653 float d = 1;
654 s *= (1.525f);
655 if ((t /= d / 2) < 1) return static_cast<T>(c / 2 * (t * t * (((s) + 1) * t - s)) + b);
656 float postFix = t -= 2;
657 return static_cast<T>(c / 2 * ((postFix) * t * (((s) + 1) * t + s) + 2) + b);
658 }
659 } backInOut = backInOutEasing{};
660 };
661}
662#endif //TWEENY_EASING_H
enumerated
Enumerates all easings to aid in runtime when adding easins to a tween using tween::via.
Definition easing.h:138
The easing class holds all the bundled easings.
Definition easing.h:130
The tweeny namespace contains all symbols and names for the Tweeny library.
Definition MANUAL.dox:1
Acceelerate initial values with a "back" equation.
Definition easing.h:620
Acceelerate initial and deaccelerate ending values with a "back" equation.
Definition easing.h:646
Deaccelerate ending values with a "back" equation.
Definition easing.h:633
Acceelerate initial values with a "bounce" equation.
Definition easing.h:516
Acceelerate initial and deaccelerate ending values with a "bounce" equation.
Definition easing.h:550
Deaccelerate ending values with a "bounce" equation.
Definition easing.h:527
Acceelerate initial values with a circular equation.
Definition easing.h:476
Acceelerate initial and deaccelerate ending values with a circular equation.
Definition easing.h:499
Deaccelerate ending values with a circular equation.
Definition easing.h:487
Aaccelerate initial values with a cubic equation.
Definition easing.h:281
Acceelerate initial and deaccelerate ending values with a cubic equation.
Definition easing.h:304
Deaccelerate ending values with a cubic equation.
Definition easing.h:292
Values change with constant speed for arithmetic type only. The non-arithmetic it will be constant.
Definition easing.h:189
Acceelerate initial values with an "elastic" equation.
Definition easing.h:562
Acceelerate initial and deaccelerate ending values with an "elastic" equation.
Definition easing.h:596
Deaccelerate ending values with an "elastic" equation.
Definition easing.h:580
Acceelerate initial values with an exponential equation.
Definition easing.h:438
Acceelerate initial and deaccelerate ending values with an exponential equation.
Definition easing.h:460
Deaccelerate ending values with an exponential equation.
Definition easing.h:449
Values change with constant speed.
Definition easing.h:226
Accelerate initial values with a quadratic equation.
Definition easing.h:242
Acceelerate initial and deaccelerate ending values with a quadratic equation.
Definition easing.h:264
Deaccelerate ending values with a quadratic equation.
Definition easing.h:253
Acceelerate initial values with a quartic equation.
Definition easing.h:320
Acceelerate initial and deaccelerate ending values with a quartic equation.
Definition easing.h:343
Deaccelerate ending values with a quartic equation.
Definition easing.h:331
Acceelerate initial values with a quintic equation.
Definition easing.h:361
Acceelerate initial and deaccelerate ending values with a quintic equation.
Definition easing.h:385
Deaccelerate ending values with a quintic equation.
Definition easing.h:372
Acceelerate initial values with a sinusoidal equation.
Definition easing.h:405
Acceelerate initial and deaccelerate ending values with a sinusoidal equation.
Definition easing.h:427
Deaccelerate ending values with a sinusoidal equation.
Definition easing.h:416
Value is constant.
Definition easing.h:178