#include "curve.h"
int Hermite::inflection(Real *l, const Real &p0, const Real &p1, const Real &t0, const Real &t1) {
Real root;
if (solve_equation(
&root,
-3*p0 + 3*p1 - 2*t0 - t1,
6*p0 - 6*p1 + 3*t0 + 3*t1 ))
{
if (less(0, root) && less(root, 1)) {
if (l) *l = root;
return 1;
}
}
return 0;
}
int Hermite::bends(Real *l, const Real &p0, const Real &p1, const Real &t0, const Real &t1) {
Real roots[2];
int count = solve_equation(
roots,
t0 ,
-6*p0 + 6*p1 - 4*t0 - 2*t1,
6*p0 - 6*p1 + 3*t0 + 3*t1 );
int valid_count = 0;
for(Real *i = roots, *end = i + count; i != end; ++i)
if (less(0, *i) && less(*i, 1)) {
if (l) l[valid_count] = *i;
++valid_count;
}
return valid_count;
}
Range Hermite::bounds_accurate(const Real &p0, const Real &p1, const Real &t0, const Real &t1) {
Range range(p0);
range.expand(p1);
Real roots[2];
int count = bends(roots, p0, p1, t0, t1);
for(Real *i = roots, *end = i + count; i != end; ++i)
range.expand( p(*i, p0, p1, t0, t1) );
return range;
}
int Hermite::intersections(Real *l, const Real &p, const Real &p0, const Real &p1, const Real &t0, const Real &t1) {
Real roots[3];
int count = solve_equation(
roots,
p0 - p ,
t0 ,
-3*p0 + 3*p1 - 2*t0 - t1,
2*p0 - 2*p1 + t0 + t1 );
int valid_count = 0;
for(Real *i = roots, *end = i + count; i != end; ++i)
if (less(0, *i) && less(*i, 1)) {
if (l) l[valid_count] = *i;
++valid_count;
}
return valid_count;
}
int Bezier::inflection(Real *l, const Real &p0, const Real &p1, const Real &pp0, const Real &pp1) {
Real root;
if (solve_equation(
&root,
p0 - 2*pp0 + pp1 ,
-p0 + 3*pp0 - 3*pp1 + p1 ))
{
if (less(0, root) && less(root, 1)) {
if (l) *l = root;
return 1;
}
}
return 0;
}
int Bezier::bends(Real *l, const Real &p0, const Real &p1, const Real &pp0, const Real &pp1) {
Real roots[2];
int count = solve_equation(
roots,
-p0 + pp0 ,
2*p0 - 4*pp0 + 2*pp1 ,
-p0 + 3*pp0 - 3*pp1 + p1 );
int valid_count = 0;
for(Real *i = roots, *end = i + count; i != end; ++i)
if (less(0, *i) && less(*i, 1)) {
if (l) l[valid_count] = *i;
++valid_count;
}
return valid_count;
}
Range Bezier::bounds_accurate(const Real &p0, const Real &p1, const Real &pp0, const Real &pp1) {
Range range(p0);
range.expand(p1);
Real roots[2];
int count = bends(roots, p0, p1, pp0, pp1);
for(Real *i = roots, *end = i + count; i != end; ++i)
range.expand( p(*i, p0, p1, pp0, pp1) );
return range;
}
int Bezier::intersections(Real *l, const Real &p, const Real &p0, const Real &p1, const Real &pp0, const Real &pp1) {
Real roots[3];
int count = solve_equation(
roots,
p0 - p ,
-3*p0 + 3*pp0 ,
3*p0 - 6*pp0 + 3*pp1 ,
-p0 + 3*pp0 - 3*pp1 + p1 );
int valid_count = 0;
for(Real *i = roots, *end = i + count; i != end; ++i)
if (less(0, *i) && less(*i, 1)) {
if (l) l[valid_count] = *i;
++valid_count;
}
return valid_count;
}