Added some transitions.

This commit is contained in:
2021-09-26 16:45:27 -07:00
parent 7740bd9930
commit f3a16b9c8c
17 changed files with 406 additions and 87 deletions

View File

@ -0,0 +1,60 @@
/**
* Copyright (c) 2021 Dominic Masters
*
* This software is released under the MIT License.
* https://opensource.org/licenses/MIT
*/
#include "easing.h"
float easeLinear(float t) {
return t;
}
float easeInQuad(float t) {
return t * t;
}
float easeOutQuad(float t) {
return t * (2 - t);
}
float easeInOutQuad(float t) {
return t < .5 ? 2 * t * t : -1 + (4 - 2 * t) * t;
}
float easeInCubic(float t) {
return t * t * t;
}
float easeOutCubic(float t) {
return (t - 1) * (t - 1) * (t - 1) + 1;
}
float easeInOutCubic(float t) {
return t < .5 ? 4 * t * t * t : (t - 1) * (2 * t - 2) * (2 * t - 2) + 1;
}
float easeInQuart(float t) {
return t * t * t * t;
}
float easeOutQuart(float t) {
return 1 - (t-1)*(t-1)*(t-1)*(t-1);
}
float easeInOutQuart(float t) {
return t < .5 ? 8*t*t*t*t : 1-8*(t-1)*(t-1)*(t-1)*(t-1);
}
float easeInQuint(float t) {
return t*t*t*t*t;
}
float easeOutQuint(float t) {
return 1 + (t-1)*(t-1)*(t-1)*(t-1)*(t-1);
}
float easeInOutQuint(float t) {
return t<.5 ? 16*t*t*t*t*t : 1+16*(t-1)*(t-1)*(t-1)*(t-1)*(t-1);
}

View File

@ -6,6 +6,8 @@
*/
#pragma once
typedef float easefunction_t(float t);
/**
* Returns the ease time for a given real time duration span.
* @param start At what point in time the animation started
@ -15,22 +17,16 @@
*/
#define easeTimeToEase(start, current, duration) ((current-start)/duration)
// Easing Functions, most were sourced from https://gist.github.com/gre/1650294
#define easeLinear(t) t
#define easeInQuad(t) (t*t)
#define easeOutQuad(t) (t*(2-t))
#define easeInOutQuad(t) (t < .5 ? 2*t*t : -1+(4-2*t)*t)
#define easeInCubic(t) (t*t*t)
#define easeOutCubic(t) ((t-1)*(t-1)*(t-1)+1)
#define easeInOutCubic(t) (t < .5 ? 4*t*t*t : (t-1)*(2*t-2)*(2*t-2)+1)
#define easeInQuart(t) (t*t*t*t)
#define easeOutQuart(t) (1 - (t-1)*(t-1)*(t-1)*(t-1))
#define easeInOutQuart(t) (t < .5 ? 8*t*t*t*t : 1-8*(t-1)*(t-1)*(t-1)*(t-1))
#define easeInQuint(t) (t*t*t*t*t)
#define easeOutQuint(t) (1 + (t-1)*(t-1)*(t-1)*(t-1)*(t-1))
#define easeInOutQuint(t) (t<.5 ? 16*t*t*t*t*t : 1+16*(t-1)*(t-1)*(t-1)*(t-1)*(t-1))
float easeLinear(float t);
float easeInQuad(float t);
float easeOutQuad(float t);
float easeInOutQuad(float t);
float easeInCubic(float t);
float easeOutCubic(float t);
float easeInOutCubic(float t);
float easeInQuart(float t);
float easeOutQuart(float t);
float easeInOutQuart(float t);
float easeInQuint(float t);
float easeOutQuint(float t);
float easeInOutQuint(float t);

View File

@ -7,6 +7,32 @@
#include "timeline.h"
void _timelineActionDeltaUpdateStart(
timeline_t *timeline, timelineaction_t *action, uint8_t i
) {
if(action->data == NULL) return;
*((float *)action->data) = timeline->initials[i];
}
void _timelineActionDeltaUpdateDuration(
timeline_t *timeline, timelineaction_t *action, uint8_t i
) {
float n;
if(action->data == NULL) return;
n = timeline->easings[i](
timelineActionGetTimeRaw(timeline, action)
);
*((float *)action->data) = timeline->initials[i] + (timeline->deltas[i] * n);
}
void _timelineActionDeltaUpdateEnd(
timeline_t *timeline, timelineaction_t *action, uint8_t i
) {
if(action->data == NULL) return;
*((float *)action->data) = timeline->initials[i] + timeline->deltas[i];
}
void timelineInit(timeline_t *timeline) {
timeline->current = 0;
timeline->diff = 0;
@ -68,10 +94,48 @@ bool timelineIsFinished(timeline_t *timeline) {
timelineaction_t * timelineAddAction(timeline_t *timeline, float start,
float duration
) {
if(timeline->actionCount == TIMELINE_ACTION_COUNT_MAX) return NULL;
timelineaction_t *action = timeline->actions + (timeline->actionCount++);
action->loop = false;
action->start = start, action->duration = duration;
action->onStart = action->onEnd = action->onDuration = NULL;
return action;
}
timelineaction_t * timelineAddDeltaAction(timeline_t *timeline,
float start, float duration, float initial, float delta,
easefunction_t *easing, float *destination
) {
timelineaction_t *action;
timeline->initials[timeline->actionCount] = initial;
timeline->deltas[timeline->actionCount] = delta;
timeline->easings[timeline->actionCount] = (
easing == NULL ? &easeLinear : easing
);
action = timelineAddAction(timeline, start, duration);
action->data = destination;
action->onStart = &_timelineActionDeltaUpdateStart;
action->onDuration = &_timelineActionDeltaUpdateDuration;
action->onEnd = &_timelineActionDeltaUpdateEnd;
return action;
}
timelineaction_t * timelineAddDeltaActionTo(timeline_t *timeline,
float start, float duration, float initial, float end,
easefunction_t *easing, float *destination
) {
return timelineAddDeltaAction(
timeline, start, duration, initial, end-initial, easing, destination
);
}
float timelineActionGetTimeRaw(timeline_t *timeline, timelineaction_t *action) {
return (timeline->current - action->start) / action->duration;
}
float timelineActionGetTime(timeline_t *tl, timelineaction_t *at) {
return mathClamp(timelineActionGetTimeRaw(tl, at), 0, 1);
}
void timelineClear(timeline_t *timeline) {
timeline->actionCount = 0;
}

View File

@ -5,6 +5,8 @@
#pragma once
#include "../../libs.h"
#include "../../util/math.h"
#include "easing.h"
/** Maximum number of actions a timeline can support, smaller than 0xFF */
#define TIMELINE_ACTION_COUNT_MAX 128
@ -72,6 +74,14 @@ typedef struct _timeline_t {
/** Actions within the timeline */
timelineaction_t actions[TIMELINE_ACTION_COUNT_MAX];
/** For delta actions, storage of the initial values */
float initials[TIMELINE_ACTION_COUNT_MAX];
/** For delta actions, storage of their deltas. */
float deltas[TIMELINE_ACTION_COUNT_MAX];
/** Easing functions to use for delta functions */
easefunction_t *easings[TIMELINE_ACTION_COUNT_MAX];
uint8_t actionCount;
} timeline_t;
@ -110,4 +120,68 @@ bool timelineIsFinished(timeline_t *timeline);
*/
timelineaction_t * timelineAddAction(timeline_t *timeline, float start,
float duration
);
);
/**
* Add a special action kind that can treat delta style animations. These are
* animations that have a start, and an end value, that will be tracked for you
* and keep you up to date.
*
* @param timeline Timeline to add to.
* @param start Starting time.
* @param duration Animation duration.
* @param initial Initial value for the animation.
* @param delta Delta value for the animation.
* @param easing Pointer to an easing function to use, set to NULL for linear.
* @param destination A constant floating point to update.
* @return The queued timeline action.
*/
timelineaction_t * timelineAddDeltaAction(timeline_t *timeline,
float start, float duration, float initial, float delta,
easefunction_t *easing, float *destination
);
/**
* Shorthand for timelineAddDeltaAction that will calculate the delta based on
* and end position.
*
* @param timeline Timeline to add to.
* @param start Starting time.
* @param duration Animation duration.
* @param initial Initial value for the animation.
* @param end End value for the animation.
* @param easing Pointer to an easing function to use, set to NULL for linear.
* @param destination A constant floating point to update.
* @return The queued timeline action.
*/
timelineaction_t * timelineAddDeltaActionTo(timeline_t *timeline,
float start, float duration, float initial, float end,
easefunction_t *easing, float *destination
);
/**
* Gets the timeline action's animation time. This is a representation of
* 0 - 1 where 0 means the animation is at the start, and 1 meaning the
* animation is at full completion. This is not clamped and may exceed 1.
*
* @param timeline Timeline the action belongs to.
* @param action Action itself.
* @return 0 - 1+, where 0 = start, 1 = duration, >1 is time since duration.
*/
float timelineActionGetTimeRaw(timeline_t *timeline, timelineaction_t *action);
/**
* Gets the timeline action's animation time between 0 - 1, clamped.
*
* @param tl Timeline to get delta from.
* @param at Timeline action.
* @return 0 - 1, where 0 = start, 1 = duration.
*/
float timelineActionGetTime(timeline_t *tl, timelineaction_t *at);
/**
* Removes all actions from the timeline.
*
* @param timeline Timeline to clear.
*/
void timelineClear(timeline_t *timeline);

View File

@ -15,6 +15,12 @@ void cameraLookAt(camera_t *camera,
matrixLookAt(&camera->view, x, y, z, targetX, targetY, targetZ, 0, 1, 0);
}
void cameraLookAtStruct(camera_t *camera, cameralookat_t look) {
cameraLookAt(camera,
look.x, look.y, look.z, look.lookX, look.lookY, look.lookZ
);
}
void cameraLook(camera_t *camera,
float x, float y, float z,
float pitch, float yaw, float roll

View File

@ -17,6 +17,10 @@ typedef struct {
matrix_t projection;
} camera_t;
typedef struct {
float x, y, z, lookX, lookY, lookZ;
} cameralookat_t;
/**
* Make a camera look at a position in world space while itself being positioned
* within world space.
@ -34,6 +38,14 @@ void cameraLookAt(camera_t *camera,
float targetX, float targetY, float targetZ
);
/**
* Shorthand for look at that uses the look struct.
*
* @param camera Camera to position.
* @param look Look vectors.
*/
void cameraLookAtStruct(camera_t *camera, cameralookat_t look);
/**
* Make a camera look in a direction based on a rotation direction.
*