Motive Animation System
An open source project by FPL.
 All Classes Functions Variables Typedefs Friends Pages
motive::RangeT< T > Class Template Reference

Represent an interval on a number line. More...

#include <range.h>

Detailed Description

template<class T>
class motive::RangeT< T >

Represent an interval on a number line.

Classes

struct  RangeArray
 
struct  TArray
 

Public Member Functions

 RangeT (const T point)
 
 RangeT (const T start, const T end)
 
bool Valid () const
 A range is valid if it contains at least one number.
 
Middle () const
 
Length () const
 
Clamp (const T x) const
 
ClampAfterStart (const T x) const
 
ClampBeforeEnd (const T x) const
 
DistanceFrom (const T x) const
 
Lerp (const float percent) const
 
float Percent (const T x) const
 
PercentClamped (const T x) const
 
Normalize (T x) const
 
NormalizeCloseValue (T x) const
 
NormalizeWildValue (T x) const
 
ModularAdjustment (T x) const
 
float ModDiffClose (T a, T b) const
 
float ModDiffFar (T a, T b) const
 Return the farthest difference from 'a' to 'b' under modular arithmetic.
 
float ModDiffPositive (T a, T b) const
 
float ModDiffNegative (T a, T b) const
 
float ModDiff (T a, T b, ModularDirection direction) const
 
bool Contains (const T x) const
 Return true if x is in [start_, end_], i.e. the inclusive range.
 
bool ContainsExcludingStart (const T x) const
 
bool ContainsExcludingEnd (const T x) const
 
bool StrictlyContains (const T x) const
 Return true if x is in (start_, end_), i.e. the exclusive range.
 
bool ContainsWithTolerance (const T x, const T percent) const
 
RangeT Invert () const
 
RangeT Lengthen (const float percent) const
 
RangeT Include (const T x) const
 
bool operator== (const RangeT &rhs) const
 Equality is strict. No epsilon checking here.
 
bool operator!= (const RangeT &rhs) const
 
RangeT operator* (const float s) const
 Scale by multiplying by a scalar.
 
start () const
 Accessors.
 
end () const
 
void set_start (const T start)
 
void set_end (const T end)
 

Static Public Member Functions

static RangeT Intersect (const RangeT &a, const RangeT &b)
 
static RangeT Union (const RangeT &a, const RangeT &b)
 Return the smallest range that covers all of 'a' and 'b'.
 
static size_t ValuesInRange (const RangeT &range, T epsilon, size_t num_values, T *values)
 
template<size_t kMaxLen>
static void ValuesInRange (const RangeT &range, T epsilon, TArray< kMaxLen > *values)
 
static size_t IntersectRanges (const RangeT *a, size_t len_a, const RangeT *b, size_t len_b, RangeT *intersections, RangeT *gaps=nullptr, size_t *len_gaps=nullptr)
 
template<size_t kMaxLen>
static void IntersectRanges (const RangeArray< kMaxLen > &a, const RangeArray< kMaxLen > &b, RangeArray< kMaxLen *kMaxLen > *intersections, RangeArray< kMaxLen *kMaxLen > *gaps=nullptr)
 
static size_t IndexOfLongest (const RangeT *ranges, size_t len)
 Return the index of the longest range in ranges.
 
template<size_t kMaxLen>
static size_t IndexOfLongest (const RangeArray< kMaxLen > &ranges)
 
static size_t IndexOfShortest (const RangeT *ranges, size_t len)
 Return the index of the shortest range in ranges.
 
template<size_t kMaxLen>
static size_t IndexOfShortest (const RangeArray< kMaxLen > &ranges)
 
static T ClampToClosest (T x, const RangeT *ranges, size_t len)
 Return the index of the shortest range in ranges.
 
template<size_t kMaxLen>
static T ClampToClosest (T x, const RangeArray< kMaxLen > &ranges)
 
template<typename S , typename F >
static RangeT< T > CoversLambda (const S *array, size_t len, const F &f)
 
static RangeT< T > Covers (const T *array, size_t len)
 Return the range that covers all values in array.
 
static RangeT< T > Full ()
 Returns the complete range. Every T is contained in this range.
 
static RangeT< T > Empty ()
 
static RangeT< T > Positive ()
 Returns the range of positive numbers: [0, +infinity].
 
static RangeT< T > Negative ()
 Returns the range of negative numbers.: [-infinity, 0].
 

Member Function Documentation

template<class T>
T motive::RangeT< T >::Clamp ( const T  x) const
inline

Returns x if it is within the range. Otherwise, returns start_ or end_, whichever is closer to x. Behavior is undefined for invalid regions.

template<class T>
T motive::RangeT< T >::ClampAfterStart ( const T  x) const
inline

Clamp x so it is inside the start bound. Can save cycles if you already know that x is inside the end bound.

template<class T>
T motive::RangeT< T >::ClampBeforeEnd ( const T  x) const
inline

Clamp x so it is inside the end bound. Can save cycles if you already know that x is inside the start bound.

template<class T>
bool motive::RangeT< T >::ContainsExcludingEnd ( const T  x) const
inline

Return true if x is in [start_, end_), i.e. the range that includes the start bound but not the end bound.

template<class T>
bool motive::RangeT< T >::ContainsExcludingStart ( const T  x) const
inline

Return true if x is in (start_, end_], i.e. the range that includes the end bound but not the start bound.

template<class T>
bool motive::RangeT< T >::ContainsWithTolerance ( const T  x,
const T  percent 
) const
inline

Return true if x is in [start_ - tolerance, end_ + tolerance], where tolerance = Length() * percent.

template<class T>
template<typename S , typename F >
static RangeT<T> motive::RangeT< T >::CoversLambda ( const S *  array,
size_t  len,
const F &  f 
)
inlinestatic

Returns the range that covers all values in f(array). f is a lambda to calculate T from S. See Covers() for a simple example. In general, if your S has a function T GetValue(), then your lambda can look something like, const RangeT<T> range = RangeT<T>::CoversLambda( s_array, len, [](const S& s) { return s.GetValue(); });

template<class T>
T motive::RangeT< T >::DistanceFrom ( const T  x) const
inline

Returns distance outside of the range. If inside the range, returns 0. Behavior is undefined for invalid regions.

template<class T>
static RangeT<T> motive::RangeT< T >::Empty ( )
inlinestatic

Returns the most empty range possible. The lower bound is greater than everything, and the upper bound is less than everything. Useful when finding the min/max values of an array of numbers.

template<class T>
RangeT motive::RangeT< T >::Include ( const T  x) const
inline

Returns the smallest range that contains both x and the range in this.

template<class T>
static RangeT motive::RangeT< T >::Intersect ( const RangeT< T > &  a,
const RangeT< T > &  b 
)
inlinestatic

Return the overlap of 'a' and 'b', or an invalid range if they do not overlap at all. When 'a' and 'b' don't overlap at all, calling Invert on the returned range will give the gap between 'a' and 'b'.

template<class T>
static size_t motive::RangeT< T >::IntersectRanges ( const RangeT< T > *  a,
size_t  len_a,
const RangeT< T > *  b,
size_t  len_b,
RangeT< T > *  intersections,
RangeT< T > *  gaps = nullptr,
size_t *  len_gaps = nullptr 
)
inlinestatic

Intersect every element of 'a' with every element of 'b'. Append intersections to 'intersections'. Note that 'intersections' is not reset at the start of the call.

template<class T>
RangeT motive::RangeT< T >::Invert ( ) const
inline

Swap start and end. When 'a' and 'b' don't overlap, if you invert the return value of Range::Intersect(a, b), you'll get the gap between 'a' and 'b'.

template<class T>
T motive::RangeT< T >::Length ( ) const
inline

Returns the span of the range. Returns 0 when only one number in range. Behavior is undefined for invalid regions.

template<class T>
RangeT motive::RangeT< T >::Lengthen ( const float  percent) const
inline

Returns a range that is 'percent' longer. If 'percent' is < 1.0, then returned range will actually be shorter.

template<class T>
T motive::RangeT< T >::Lerp ( const float  percent) const
inline

Lerps between the start and the end. 'percent' of 0 returns start. 'percent' of 1 returns end. Behavior is undefined for invalid regions.

template<class T>
T motive::RangeT< T >::Middle ( ) const
inline

Returns the mid-point of the range, rounded down for integers. Behavior is undefined for invalid regions.

template<class T>
float motive::RangeT< T >::ModDiff ( a,
b,
ModularDirection  direction 
) const
inline

Return the difference from 'a' to 'b' that satisfies the 'direction' criteria.

template<class T>
float motive::RangeT< T >::ModDiffClose ( a,
b 
) const
inline

In modular arithmetic, you can get from 'a' to 'b' by going directly, or by wrapping around. Return the closest difference from 'a' to 'b' under modular arithmetic.

template<class T>
float motive::RangeT< T >::ModDiffNegative ( a,
b 
) const
inline

Return the difference from 'a' to 'b' under modular arithmetic that is negative.

template<class T>
float motive::RangeT< T >::ModDiffPositive ( a,
b 
) const
inline

Return the difference from 'a' to 'b' under modular arithmetic that is positive.

template<class T>
T motive::RangeT< T >::ModularAdjustment ( x) const
inline

Returns: Length() if x is below the valid range -Length() if x is above the valid range 0 if x is within the valid range.

template<class T>
T motive::RangeT< T >::Normalize ( x) const
inline

Ensure x is within the valid constraint range, by subtracting or adding Length() to it. x must be within +-Length() of the range bounds. This is a reasonable restriction in most cases (such as after an arithmetic operation). For cases where x may be wildly outside the range, use NormalizeCloseValue() or NormalizeWildValue() instead.

template<class T>
T motive::RangeT< T >::NormalizeCloseValue ( x) const
inline

Ensure x is within the valid constraint range, by subtracting or adding Length() to it repeatedly. x must be within +-kMaxAdjustments * Length() of the range bounds for this function to be effective. If its greater, we end up calling NormalizeWildValue(), so you'd be better off calling NormalizeWildValue() from the beginning. This function is intended to be called in situations where x is almost always within one or two lengths of being normalized, so we don't want to incur the division cost of NormalizeWildValue(). It's still guaranteed to return a normalized value, however.

template<class T>
T motive::RangeT< T >::NormalizeWildValue ( x) const
inline

Ensure x is within the valid constraint range, by subtracting multiples of Length() from it until it is. x can be any value.

template<class T>
float motive::RangeT< T >::Percent ( const T  x) const
inline

Returns percent 0~1, from start to end. Not clamped to 0~1. 0 ==> start; 1 ==> end; 0.5 ==> Middle(); -1 ==> start - Length()

template<class T>
T motive::RangeT< T >::PercentClamped ( const T  x) const
inline

Returns percent 0~1, from start to end. Clamped to 0~1. 0 ==> start or earlier; 1 ==> end or later; 0.5 ==> Middle()

template<class T>
static size_t motive::RangeT< T >::ValuesInRange ( const RangeT< T > &  range,
epsilon,
size_t  num_values,
T *  values 
)
inlinestatic

Only keep entries in 'values' if they are in (range.start - epsition, range.end + epsilon). Any values that are kept are clamped to 'range'.

This function is useful when floating point precision error might put a value slightly outside 'range' even though mathematically it should be inside 'range'. This often happens with values right on the border of the valid range.


The documentation for this class was generated from the following file: