diff options
Diffstat (limited to 'src/livarot/PathOutline.cpp')
| -rw-r--r-- | src/livarot/PathOutline.cpp | 75 |
1 files changed, 46 insertions, 29 deletions
diff --git a/src/livarot/PathOutline.cpp b/src/livarot/PathOutline.cpp index d170e5d3a..211ee31e2 100644 --- a/src/livarot/PathOutline.cpp +++ b/src/livarot/PathOutline.cpp @@ -387,7 +387,7 @@ void Path::SubContractOutline(int off, int num_pd, if (closeIfNeeded) { if ( Geom::LInfty (curX- firstP) < 0.0001 ) { OutlineJoin (dest, firstP, curT, firstT, width, join, - miter); + miter, nType); dest->Close (); } else { PathDescrLineTo temp(firstP); @@ -404,7 +404,7 @@ void Path::SubContractOutline(int off, int num_pd, Geom::Point pos; pos = curX; OutlineJoin (dest, pos, curT, stNor, width, join, - miter); + miter, nType); } dest->LineTo (enPos+width*enNor); @@ -413,7 +413,7 @@ void Path::SubContractOutline(int off, int num_pd, Geom::Point pos; pos = firstP; OutlineJoin (dest, enPos, enNor, firstT, width, join, - miter); + miter, nType); dest->Close (); } } @@ -429,7 +429,7 @@ void Path::SubContractOutline(int off, int num_pd, if (Geom::LInfty (curX - firstP) < 0.0001) { OutlineJoin (dest, firstP, curT, firstT, width, join, - miter); + miter, nType); dest->Close (); } else @@ -445,7 +445,7 @@ void Path::SubContractOutline(int off, int num_pd, // jointure { OutlineJoin (dest, stPos, curT, stNor, width, join, - miter); + miter, nType); } dest->LineTo (enPos+width*enNor); @@ -453,7 +453,7 @@ void Path::SubContractOutline(int off, int num_pd, // jointure { OutlineJoin (dest, enPos, enNor, firstT, width, join, - miter); + miter, nType); dest->Close (); } } @@ -465,15 +465,15 @@ void Path::SubContractOutline(int off, int num_pd, { PathDescrLineTo* nData = dynamic_cast<PathDescrLineTo*>(descr_cmd[curD]); nextX = nData->p; + // et on avance + TangentOnSegAt (0.0, curX, *nData, stPos, stTgt, stTle); + TangentOnSegAt (1.0, curX, *nData, enPos, enTgt, enTle); // test de nullité du segment if (IsNulCurve (descr_cmd, curD, curX)) { - curP++; - continue; + stTgt = dest->descr_cmd.size() ? Geom::Point(1, 0) : Geom::Point(-1, 0); // reverse direction + enTgt = stTgt; } - // et on avance - TangentOnSegAt (0.0, curX, *nData, stPos, stTgt, stTle); - TangentOnSegAt (1.0, curX, *nData, enPos, enTgt, enTle); stNor=stTgt.cw(); enNor=enTgt.cw(); @@ -497,7 +497,7 @@ void Path::SubContractOutline(int off, int num_pd, // jointure Geom::Point pos; pos = curX; - OutlineJoin (dest, pos, curT, stNor, width, join, miter); + OutlineJoin (dest, pos, curT, stNor, width, join, miter, nType); } int n_d = dest->LineTo (nextX+width*enNor); @@ -547,7 +547,7 @@ void Path::SubContractOutline(int off, int num_pd, // jointure Geom::Point pos; pos = curX; - OutlineJoin (dest, pos, curT, stNor, width, join, miter); + OutlineJoin (dest, pos, curT, stNor, width, join, miter, nType); } callsData.piece = curP; @@ -603,7 +603,7 @@ void Path::SubContractOutline(int off, int num_pd, // jointure Geom::Point pos; pos = curX; - OutlineJoin (dest, pos, curT, stNor, width, join, miter); + OutlineJoin (dest, pos, curT, stNor, width, join, miter, nType); } callsData.piece = curP; @@ -661,7 +661,7 @@ void Path::SubContractOutline(int off, int num_pd, // jointure Geom::Point pos; pos = curX; - if (stTle > 0) OutlineJoin (dest, pos, curT, stNor, width, join, miter); + if (stTle > 0) OutlineJoin (dest, pos, curT, stNor, width, join, miter, nType); } int n_d = dest->LineTo (nextX+width*enNor); if (n_d >= 0) { @@ -692,7 +692,7 @@ void Path::SubContractOutline(int off, int num_pd, // jointure Geom::Point pos; pos = curX; - OutlineJoin (dest, pos, curT, stNor, width, join, miter); + OutlineJoin (dest, pos, curT, stNor, width, join, miter, nType); } callsData.piece = curP; @@ -709,9 +709,8 @@ void Path::SubContractOutline(int off, int num_pd, } else if (nbInterm > 1) { Geom::Point bx=curX; Geom::Point cx=curX; - Geom::Point dx=curX; + Geom::Point dx=nData->p; - dx = nData->p; TangentOnBezAt (0.0, curX, *nData, *nBData, false, stPos, stTgt, stTle, stRad); stNor=stTgt.cw(); @@ -729,7 +728,7 @@ void Path::SubContractOutline(int off, int num_pd, } else { // jointure Geom::Point pos=curX; - OutlineJoin (dest, pos, stTgt, stNor, width, join, miter); + OutlineJoin (dest, pos, stTgt, stNor, width, join, miter, nType); // dest->LineTo(curX+width*stNor.x,curY+width*stNor.y); } } @@ -931,7 +930,7 @@ void Path::TangentOnArcAt(double at, const Geom::Point &iS, PathDescrArcTo const Geom::Point const iE = fin.p; double const rx = fin.rx; double const ry = fin.ry; - double const angle = fin.angle; + double const angle = fin.angle*M_PI/180.0; bool const large = fin.large; bool const wise = fin.clockwise; @@ -1048,7 +1047,7 @@ void Path::TangentOnArcAt(double at, const Geom::Point &iS, PathDescrArcTo const dtgt[0] = -ca * rx * cb + sa * ry * sb; dtgt[1] = -sa * rx * cb - ca * ry * sb; len = L2(tgt); - rad = len * dot(tgt, tgt) / (tgt[0] * dtgt[1] - tgt[1] * dtgt[0]); + rad = -len * dot(tgt, tgt) / (tgt[0] * dtgt[1] - tgt[1] * dtgt[0]); tgt /= len; } else @@ -1164,7 +1163,7 @@ Path::TangentOnBezAt (double at, Geom::Point const &iS, void Path::OutlineJoin (Path * dest, Geom::Point pos, Geom::Point stNor, Geom::Point enNor, double width, - JoinType join, double miter) + JoinType join, double miter, int nType) { /* Arbitrarily decide if we're on the inside or outside of a half turn. @@ -1184,12 +1183,24 @@ Path::OutlineJoin (Path * dest, Geom::Point pos, Geom::Point stNor, Geom::Point const double angSi = cross (enNor,stNor); const double angCo = dot (stNor, enNor); - if (angSi == 0 && angCo > 0) { // The join is straight -> nothing to do. + if ((fabs(angSi) < .0000001) && angCo > 0) { // The join is straight -> nothing to do. } else { if ((angSi > 0 && width >= 0) || (angSi < 0 && width < 0)) { // This is an inside join -> join is independent of chosen JoinType. - dest->LineTo (pos); - dest->LineTo (pos + width*enNor); + if ((dest->descr_cmd[dest->descr_cmd.size() - 1]->getType() == descr_lineto) && (nType == descr_lineto)) { + Geom::Point const biss = unit_vector(Geom::rot90( stNor - enNor )); + double c2 = Geom::dot (biss, enNor); + if (fabs(c2) > 0.707107) { // apply only to obtuse angles + double l = width / c2; + PathDescrLineTo* nLine = dynamic_cast<PathDescrLineTo*>(dest->descr_cmd[dest->descr_cmd.size() - 1]); + nLine->p = pos + l*biss; // relocate to bisector + } else { + dest->LineTo (pos + width*enNor); + } + } else { +// dest->LineTo (pos); // redundant + dest->LineTo (pos + width*enNor); + } } else if (angSi == 0 && TurnInside) { // Half turn (180 degrees) ... inside (see above). dest->LineTo (pos + width*enNor); } else { // This is an outside join -> chosen JoinType should be applied. @@ -1241,8 +1252,14 @@ Path::OutlineJoin (Path * dest, Geom::Point pos, Geom::Point stNor, Geom::Point if ( fabs(l) > miter) { dest->LineTo (pos + width*enNor); } else { - dest->LineTo (pos+l*biss); - dest->LineTo (pos+width*enNor); + if (dest->descr_cmd[dest->descr_cmd.size() - 1]->getType() == descr_lineto) { + PathDescrLineTo* nLine = dynamic_cast<PathDescrLineTo*>(dest->descr_cmd[dest->descr_cmd.size() - 1]); + nLine->p = pos+l*biss; // relocate to bisector + } else { + dest->LineTo (pos+l*biss); + } + if (nType != descr_lineto) + dest->LineTo (pos+width*enNor); } } else { // Bevel join dest->LineTo (pos + width*enNor); @@ -1425,7 +1442,7 @@ Path::RecStdArcTo (outline_callback_data * data, double tol, double width, { Geom::Point tms(data->x1,data->y1),tme(data->x2,data->y2); ArcAngles (tms,tme, data->d.a.rx, - data->d.a.ry, data->d.a.angle, data->d.a.large, !data->d.a.clock, + data->d.a.ry, data->d.a.angle*M_PI/180.0, data->d.a.large, !data->d.a.clock, sang, eang); } double scal = eang - sang; @@ -1459,7 +1476,7 @@ Path::RecStdArcTo (outline_callback_data * data, double tol, double width, } const Geom::Point diff = req - chk; const double err = (dot(diff,diff)); - if (err <= tol * tol) + if (err <= tol) // tolerance is given as a quadratic value, no need to use tol*tol here { int n_d = data->dest->CubicTo (enPos + width*enNor, stGue*scal*stTgt, |
