public void GetCubicSegment(float time, out BezierPoint3D startPoint, out BezierPoint3D endPoint, out float timeRelativeToSegment) { startPoint = null; endPoint = null; timeRelativeToSegment = 0f; float subCurvePercent = 0f; float totalPercent = 0f; float approximateLength = this.GetApproximateLength(); int subCurveSampling = (this.Sampling / (this.KeyPointsCount - 1)) + 1; for (int i = 0; i < this.KeyPointsCount - 1; i++) { subCurvePercent = BezierCurve3D.GetApproximateLengthOfCubicCurve(this.KeyPoints[i], this.KeyPoints[i + 1], subCurveSampling) / approximateLength; if (subCurvePercent + totalPercent > time) { startPoint = this.KeyPoints[i]; endPoint = this.KeyPoints[i + 1]; break; } totalPercent += subCurvePercent; } if (endPoint == null) { // If the evaluated point is very near to the end of the curve we are in the last segment startPoint = this.KeyPoints[this.KeyPointsCount - 2]; endPoint = this.KeyPoints[this.KeyPointsCount - 1]; // We remove the percentage of the last sub-curve totalPercent -= subCurvePercent; } timeRelativeToSegment = (time - totalPercent) / subCurvePercent; }
public static float GetApproximateLengthOfCubicCurve(BezierPoint3D startPoint, BezierPoint3D endPoint, int sampling) { return(GetApproximateLengthOfCubicCurve(startPoint.Position, endPoint.Position, startPoint.RightHandlePosition, endPoint.LeftHandlePosition, sampling)); }
public static Vector3 GetNormalOnCubicCurve(float time, Vector3 up, BezierPoint3D startPoint, BezierPoint3D endPoint) { return(GetNormalOnCubicCurve(time, up, startPoint.Position, endPoint.Position, startPoint.RightHandlePosition, endPoint.LeftHandlePosition)); }