Пример #1
0
        /// <summary>
        /// Evaluates the value at a position of this <see cref="Curve"/>.
        /// </summary>
        /// <param name="keys">Curve keys</param>
        /// <param name="position">Position to test</param>
        /// <returns>Returns the value at the position on this <see cref="Curve"/>.</returns>
        private static float EvaluateOscillate(CurveKeyCollection keys, float position)
        {
            var first = keys[0];
            var last  = keys[keys.Count - 1];

            if (position != first.Position)
            {
                //go back on curve from end and target start
                // start-> end / end -> start
                int   cycle = GetNumberOfCycle(first, last, position);
                float virtualPos;
                if (0 == cycle % 2f)
                {
                    //if pair
                    virtualPos = position - (cycle * (last.Position - first.Position));
                }
                else
                {
                    virtualPos = last.Position - position + first.Position + (cycle * (last.Position - first.Position));
                }
                return(GetCurvePosition(keys, virtualPos));
            }

            //in curve
            return(GetCurvePosition(keys, position));
        }
Пример #2
0
        /// <summary>
        /// Gets the curve position
        /// </summary>
        /// <param name="keys">Key collection</param>
        /// <param name="position">Position to test</param>
        /// <returns>Returns the curve position</returns>
        private static float GetCurvePosition(CurveKeyCollection keys, float position)
        {
            //only for position in curve
            CurveKey prev = keys[0];
            CurveKey next;

            for (int i = 1; i < keys.Count; ++i)
            {
                next = keys[i];
                if (next.Position >= position)
                {
                    if (prev.Continuity == CurveContinuity.Step)
                    {
                        if (position >= 1f)
                        {
                            return(next.Value);
                        }

                        return(prev.Value);
                    }

                    //http://en.wikipedia.org/wiki/Cubic_Hermite_spline
                    //P(t) = (2*t^3 - 3t^2 + 1)*P0 + (t^3 - 2t^2 + t)m0 + (-2t^3 + 3t^2)P1 + (t^3-t^2)m1
                    //with P0.value = prev.value , m0 = prev.tangentOut, P1= next.value, m1 = next.TangentIn
                    float t   = (position - prev.Position) / (next.Position - prev.Position);//to have t in [0,1]
                    float ts  = t * t;
                    float tss = ts * t;
                    return((2 * tss - 3 * ts + 1f) * prev.Value + (tss - 2 * ts + t) * prev.TangentOut + (3 * ts - 2 * tss) * next.Value + (tss - ts) * next.TangentIn);
                }
                prev = next;
            }

            return(0f);
        }
Пример #3
0
        /// <summary>
        /// Evaluates the value at a position of this <see cref="Curve"/>.
        /// </summary>
        /// <param name="keys">Curve keys</param>
        /// <param name="position">Position to test</param>
        /// <returns>Returns the value at the position on this <see cref="Curve"/>.</returns>
        private static float EvaluateCycleOffset(CurveKeyCollection keys, float position)
        {
            var first = keys[0];
            var last  = keys[keys.Count - 1];

            if (position != first.Position)
            {
                //make the curve continue (with no step) so must up the curve each cycle of delta(value)
                int   cycle      = GetNumberOfCycle(first, last, position);
                float virtualPos = position - (cycle * (last.Position - first.Position));
                return(GetCurvePosition(keys, virtualPos) + cycle * (last.Value - first.Value));
            }

            //in curve
            return(GetCurvePosition(keys, position));
        }
Пример #4
0
        /// <summary>
        /// Evaluates the value at a position of this <see cref="Curve"/>.
        /// </summary>
        /// <param name="keys">Curve keys</param>
        /// <param name="position">Position to test</param>
        /// <returns>Returns the value at the position on this <see cref="Curve"/>.</returns>
        private static float EvaluateCycle(CurveKeyCollection keys, float position)
        {
            var first = keys[0];
            var last  = keys[keys.Count - 1];

            if (position != first.Position)
            {
                //start -> end / start -> end
                int   cycle      = GetNumberOfCycle(first, last, position);
                float virtualPos = position - (cycle * (last.Position - first.Position));
                return(GetCurvePosition(keys, virtualPos));
            }

            //in curve
            return(GetCurvePosition(keys, position));
        }
Пример #5
0
        /// <summary>
        /// Evaluates the value at a position of this <see cref="Curve"/>.
        /// </summary>
        /// <param name="keys">Curve keys</param>
        /// <param name="position">Position to test</param>
        /// <returns>Returns the value at the position on this <see cref="Curve"/>.</returns>
        private static float EvaluateLinear(CurveKeyCollection keys, float position)
        {
            var first = keys[0];
            var last  = keys[keys.Count - 1];

            if (position < first.Position)
            {
                // linear y = a*x +b with a tangeant of last point
                return(first.Value - first.TangentIn * (first.Position - position));
            }
            else if (position > last.Position)
            {
                // linear y = a*x +b with a tangeant of last point
                return(last.Value + first.TangentOut * (position - last.Position));
            }

            return(GetCurvePosition(keys, position));
        }
Пример #6
0
        /// <summary>
        /// Evaluates the value at a position of this <see cref="Curve"/>.
        /// </summary>
        /// <param name="keys">Curve keys</param>
        /// <param name="position">Position to test</param>
        /// <returns>Returns the value at the position on this <see cref="Curve"/>.</returns>
        private static float EvaluateConstant(CurveKeyCollection keys, float position)
        {
            var first = keys[0];
            var last  = keys[keys.Count - 1];

            if (position < first.Position)
            {
                //constant
                return(first.Value);
            }
            else if (position > last.Position)
            {
                //constant
                return(last.Value);
            }

            return(GetCurvePosition(keys, position));
        }