FBX2glTF/sdk/Linux/2019.2/include/fbxsdk/scene/geometry/fbxnurbscurve.h

234 lines
8.9 KiB
C++

/****************************************************************************************
Copyright (C) 2015 Autodesk, Inc.
All rights reserved.
Use of this software is subject to the terms of the Autodesk license agreement
provided at the time of installation or download, or which otherwise accompanies
this software in either electronic or hard copy form.
****************************************************************************************/
//! \file fbxnurbscurve.h
#ifndef _FBXSDK_SCENE_GEOMETRY_NURBS_CURVE_H_
#define _FBXSDK_SCENE_GEOMETRY_NURBS_CURVE_H_
#include <fbxsdk/fbxsdk_def.h>
#include <fbxsdk/scene/geometry/fbxgeometry.h>
#include <fbxsdk/scene/geometry/fbxline.h>
#include <fbxsdk/fbxsdk_nsbegin.h>
/**
A Non-Uniform Rational B-Spline (NURBS) curve is a type of parametric geometry. A NURBS
curve is defined by the order, form, knot vector and control points.
Let M be the order of the curve.
Let N be the number of control points of the curve.
The form of the curve can be open, closed or periodic. A curve with end points
that do not meet is defined as an open curve. The number of knots in an open curve
is defined as N+(M+1).
A closed curve simply has its last control point equal to its first control point.
Note that this does not imply tangent continuity at the end point. The curve may
have a kink at this point. In FBX the last control point is not specified by the user
in the InitControlPoints() method. For example, if there are to be 10 control points in
total, and the curve is to be closed, than only 9 control points need to be passed
into the InitControlPoints() method. The last control point is implied to be equal
to the first control point. Thus N represents the number of unique CVs.
A periodic curve has its last M control points equal to its first M control points.
A periodic curve is tangent continuous at the ends. Similar to a closed curve,
when creating a periodic curve, only the unique control points need to be set. For
example a periodic curve of order 3 with 10 control points requires only 7 CVs to
be specified in the InitControlPoints() method. The last 3 CVs, which are the same as
the first 3, are not included.
The calculation of the number of knots in closed and periodic curves is more complex.
Since we have excluded one CV in N in a closed curve, the number of knots is N+(M+1)+1.
Similarly, we excluded M CVs in periodic curves so the number of knots is N+(M+1)+M.
Note that FBX stores one extra knot at the beginning and and end of the knot vector,
compared to some other graphics applications such as Maya. The two knots are not
used in calculation, but they are included so that no data is lost when converting
from file formats that do store the extra knots.
* \nosubgrouping
*/
class FBXSDK_DLL FbxNurbsCurve : public FbxGeometry
{
FBXSDK_OBJECT_DECLARE(FbxNurbsCurve,FbxGeometry);
public:
//! Returns the EType::eNurbsCurve node attribute type.
FbxNodeAttribute::EType GetAttributeType() const override;
/** \enum EDimension The dimension of the CVs.
* - \e e2D The CVs are two dimensional points.
* - \e e3D The CVs are three dimensional points.
*/
enum EDimension
{
e2D = 2,
e3D
};
/** \enum EType The curve's form.
* - \e eOpen
* - \e eClosed
* - \e ePeriodic
*/
enum EType
{
eOpen,
eClosed,
ePeriodic
};
/** Allocates memory space for the control points array as well as for the knot
* vector.
* \param pCount Number of control points.
* \param pVType NURBS type.
* \remarks This function should always be called after FbxNurbsCurve::SetOrder().
*/
void InitControlPoints( int pCount, EType pVType );
/** Returns the knot vector.
* \return Pointer to the knots array.
*/
inline double* GetKnotVector() const { return mKnotVector; }
/** Returns the number of elements in the knot vector.
* \return The number of knots.
*/
int GetKnotCount() const;
/** Sets the order of the curve.
* \param pOrder The curve order.
* \remarks The curve order must be set before InitControlPoints() is called.
*/
inline void SetOrder( int pOrder ) { mOrder = pOrder; }
/** Returns the NURBS curve order.
* \return The NURBS curve order.
*/
inline int GetOrder() const { return mOrder; }
/** Sets the step of the curve.
* \param pStep The curve step.
* \remarks To tessellate curve, it denotes the evaluation frequency between two neighbor knots.
*/
inline void SetStep( int pStep ) { mStep = pStep; }
/** Returns the NURBS curve step.
* \return The NURBS curve step.
* \remarks To tessellate curve, it denotes the evaluation frequency between two neighbor knots.
*/
inline int GetStep() const { return mStep; }
/** Sets the dimension of the CVs.
* For 3D curves: control point = ( x, y, z, w ), where w is the weight.
* For 2D curves: control point = ( x, y, 0, w ), where the z component is unused, and w is the weight.
* \param pDimension The control points dimension(3D or 2D).
*/
inline void SetDimension( EDimension pDimension ) { mDimension = pDimension; }
/** Returns the control points dimension.
* \return The curve dimension.
*/
inline EDimension GetDimension() const { return mDimension; }
/** Determines if the curve is rational or not.
* \return \c True if the curve is rational, return \c false if not.
*/
bool IsRational();
/** Calculates the number of curve spans with the following:
* Where
* S = Number of spans
* N = Number of CVs
* M = Order of the curve
*
* S = N - M + 1;
*
* In this calculation N includes the duplicate CVs for closed and periodic curves.
*
* \return The number of curve spans if the curve has been initialized, returns -1 if the curve has not been initialized.
*/
int GetSpanCount() const;
/** Returns NURBS type.
* \return NURBS type identifier.
*/
inline EType GetType() const { return mNurbsType; }
/** Checks if the curve is a poly line. (A poly line is a
* linear NURBS curve )
*
* \return \c True if curve is a poly line, return \c false if it is not a poly line.
*/
inline bool IsPolyline() const { return ( GetOrder() == 2 ); }
/** This function determines if this NURBS curve is a Bezier curve.
* Bezier curves are a special case of NURBS curve.
* \return \c True if curve is a Bezier curve. If it is not a Bezier curve return \c false.
*/
bool IsBezier() const;
/** Evaluate the point on the curve. Save the result as a point array. Meanwhile, return the length of the point array.
* \param pPointArray Save the evaluate result as a point array.
* \param pStep The evaluation frequency between two neighbor knots. Its default value is 16, which is same as Maya.
* \return The length of the point array.
*/
int TessellateCurve(FbxArray<FbxVector4>& pPointArray, int pStep = 16);
/** Evaluate the point on the curve. Per the evaluation result, create a FbxLine and return the pointer to the line.
* \param pStep The evaluation frequency between two neighbor knots. Its default value is 16, which is same as Maya.
* \return A line to hold the tessellate points.
*/
FbxLine* TessellateCurve(int pStep = 16);
/*****************************************************************************************************************************
** WARNING! Anything beyond these lines is for internal use, may not be documented and is subject to change without notice! **
*****************************************************************************************************************************/
#ifndef DOXYGEN_SHOULD_SKIP_THIS
FbxObject& Copy(const FbxObject& pObject) override;
bool FullMultiplicity() const;
// Error identifiers, these are only used internally.
enum EErrorCode
{
eNurbsCurveTypeUnknown,
eWeightTooSmall,
eKnotVectorError,
eWrongNumberOfControlPoint,
eErrorCount
};
bool mIsRational;
void SetControlPointAt(const FbxVector4 &pCtrlPoint , int pIndex) override { ParentClass::SetControlPointAt(pCtrlPoint, pIndex); }
void InitControlPoints(int pCount) override { ParentClass::InitControlPoints(pCount); }
protected:
void Construct(const FbxObject* pFrom) override;
void Destruct(bool pRecursive) override;
void Reset();
private:
double* mKnotVector;
EType mNurbsType;
int mOrder;
EDimension mDimension;
int mStep;
#endif /* !DOXYGEN_SHOULD_SKIP_THIS *****************************************************************************************/
};
#include <fbxsdk/fbxsdk_nsend.h>
#endif /* _FBXSDK_SCENE_GEOMETRY_NURBS_CURVE_H_ */