123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148 |
- #pragma once
- #include <Mathematics/Matrix2x2.h>
- #include <Mathematics/ParametricSurface.h>
- #include <Mathematics/Vector3.h>
- #include <memory>
- namespace WwiseGTE
- {
- template <typename Real>
- class DarbouxFrame3
- {
- public:
-
-
- DarbouxFrame3(std::shared_ptr<ParametricSurface<3, Real>> const& surface)
- :
- mSurface(surface)
- {
- }
-
-
-
-
-
-
-
- void operator()(Real u, Real v, Vector3<Real>& position, Vector3<Real>& tangent0,
- Vector3<Real>& tangent1, Vector3<Real>& normal) const
- {
- std::array<Vector3<Real>, 3> jet;
- mSurface->Evaluate(u, v, 1, jet.data());
- position = jet[0];
- tangent0 = jet[1];
- Normalize(tangent0);
- tangent1 = jet[2];
- Normalize(tangent1);
- normal = UnitCross(tangent0, tangent1);
- tangent1 = Cross(normal, tangent0);
- }
-
- void GetPrincipalInformation(Real u, Real v, Real& curvature0, Real& curvature1,
- Vector3<Real>& direction0, Vector3<Real>& direction1) const
- {
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- std::array<Vector3<Real>, 6> jet;
- mSurface->Evaluate(u, v, 2, jet.data());
- Vector3<Real> derU = jet[1];
- Vector3<Real> derV = jet[2];
- Vector3<Real> derUU = jet[3];
- Vector3<Real> derUV = jet[4];
- Vector3<Real> derVV = jet[5];
-
- Matrix2x2<Real> metricTensor;
- metricTensor(0, 0) = Dot(jet[1], jet[1]);
- metricTensor(0, 1) = Dot(jet[1], jet[2]);
- metricTensor(1, 0) = metricTensor(0, 1);
- metricTensor(1, 1) = Dot(jet[2], jet[2]);
-
- Vector3<Real> normal = UnitCross(jet[1], jet[2]);
- Matrix2x2<Real> curvatureTensor;
- curvatureTensor(0, 0) = -Dot(normal, derUU);
- curvatureTensor(0, 1) = -Dot(normal, derUV);
- curvatureTensor(1, 0) = curvatureTensor(0, 1);
- curvatureTensor(1, 1) = -Dot(normal, derVV);
-
- Real c0 = Determinant(curvatureTensor);
- Real c1 = (Real)2 * curvatureTensor(0, 1) * metricTensor(0, 1) -
- curvatureTensor(0, 0) * metricTensor(1, 1) -
- curvatureTensor(1, 1) * metricTensor(0, 0);
- Real c2 = Determinant(metricTensor);
-
- Real temp = std::sqrt(std::max(c1 * c1 - (Real)4 * c0 * c2, (Real)0));
- Real mult = (Real)0.5 / c2;
- curvature0 = -mult * (c1 + temp);
- curvature1 = -mult * (c1 - temp);
-
-
- Real a0 = curvatureTensor(0, 1) - curvature0 * metricTensor(0, 1);
- Real a1 = curvature0 * metricTensor(0, 0) - curvatureTensor(0, 0);
- Real length = std::sqrt(a0 * a0 + a1 * a1);
- if (length > (Real)0)
- {
- direction0 = a0 * derU + a1 * derV;
- }
- else
- {
- a0 = curvatureTensor(1, 1) - curvature0 * metricTensor(1, 1);
- a1 = curvature0 * metricTensor(0, 1) - curvatureTensor(0, 1);
- length = std::sqrt(a0 * a0 + a1 * a1);
- if (length > (Real)0)
- {
- direction0 = a0 * derU + a1 * derV;
- }
- else
- {
-
-
- direction0 = derU;
- }
- }
- Normalize(direction0);
-
- direction1 = Cross(direction0, normal);
- }
- private:
- std::shared_ptr<ParametricSurface<3, Real>> mSurface;
- };
- }
|