// return how many lines are removed guint Printlines::makeIntoArc(guint fromind, guint toind) { if (toind < fromind || toind+1 > lines.size()) return 0; Vector2d P = lines[fromind].from; Vector2d Q = lines[toind].to; // center perp of start -- endpoint: Vector2d connp1,connp2; center_perpendicular(P, Q, connp1, connp2); // center perp of midpoint -- endpoint: guint midind = (toind+fromind)/2; Vector2d midp1,midp2; center_perpendicular(lines[midind].from, lines[toind].to, midp1, midp2); // intersection = center Vector2d center, ip; double t0, t1; int is = intersect2D_Segments(connp1, connp2, midp1, midp2, center, ip, t0,t1); if (is > 0) { double angle = angleBetween(P-center, Q-center); bool ccw = isleftof(center, lines[fromind].from, lines[fromind].to); if (!ccw) angle = -angle; if (angle<=0) angle+=2*M_PI; short arctype = ccw ? -1 : 1; PLine newline(P, Q, lines[fromind].speed, lines[fromind].feedrate, arctype, center, angle); lines[fromind] = newline; lines.erase(lines.begin()+fromind+1, lines.begin()+toind+1); return toind-fromind; } else cerr << "no Intersection of arc perpendiculars!" << endl; return 0; }
/* * Iterate the vertices, and calculate whether this * shape is a hole or enclosed, based on whether the * segment normals point outward (a hole) or inward * (enclosing) */ void Poly::calcHole() const // hole is mutable { if(vertices.size() < 3) return; // hole is undefined Vector2d p(-INFTY, -INFTY); int v=0; center = Vector2d(0,0); Vector2d q; for(size_t vert=0;vert<vertices.size();vert++) { q = vertices[vert]; center += q; if(q.x() > p.x()) { p = q; v=vert; } else if(q.x() == p.x() && q.y() > p.y()) { p.y() = q.y(); v=vert; } } center /= vertices.size(); // we have the x-most vertex (with the highest y if there was a contest), v Vector2d V1 = getVertexCircular(v-1); Vector2d V2 = getVertexCircular(v); Vector2d V3 = getVertexCircular(v+1); // Vector2d Va=V2-V1; // Vector2d Vb=V3-V2; hole = isleftof(V2, V3, V1); //cross(Vb,Va) > 0; holecalculated = true; }
long double angleBetween(const Vector2d &V1, const Vector2d &V2) { long double dotproduct = V1.dot(V2); long double length = V1.length() * V2.length(); if (length==0) return 0; long double quot = dotproduct / length; if (quot > 1 && quot < 1.0001) quot = 1; if (quot < -1 && quot > -1.0001) quot = -1; long double result = acosl( quot ); // 0 .. pi if (isleftof(Vector2d(0,0), V2, V1)) result = -result; return result; }