// // Return the position of the second link compared to this link // Result = IS_ON | IS_LEFT | IS_RIGHT // Here Left and Right is defined as being left or right from // the this link towards the center (common) node // LinkStatus KBoolLink::OutProduct(KBoolLink* const two,double accur) { Node* center; double distance; if (two->GetBeginNode()->Equal(two->GetEndNode(), 1)) assert(!two); if (GetBeginNode()->Equal(GetEndNode(), 1)) assert(!this); KBoolLine* temp_line = new KBoolLine(this, _GC); //the this link should connect to the other two link at at least one node if (m_endnode == two->m_endnode || m_endnode == two->m_beginnode) center = m_endnode; else { center = m_beginnode; // assert(center==two->endnode || center==two->beginnode); } //here something tricky // the factor 10000.0 is needed to asure that the pointonline // is more accurate in this case compared to the intersection for graphs int uitp = temp_line->PointOnLine(two->GetOther(center), distance, accur); delete temp_line; /*double uitp= (_x - first._x) * (third._y - _y) - (_y - first._y) * (third._x - _x); if (uitp>0) return IS_LEFT; if (uitp<0) return IS_RIGHT; return IS_ON;*/ //depending on direction of this link (going to or coming from centre) if (center == m_endnode) { if (uitp==LEFT_SIDE) return IS_LEFT; if (uitp==RIGHT_SIDE) return IS_RIGHT; } else //center=beginnode { if (uitp==LEFT_SIDE) return IS_RIGHT; if (uitp==RIGHT_SIDE) return IS_LEFT; } return IS_ON; }
kbNode* kbLine::OffsetContour( kbLine* const nextline, kbNode* _last_ins, double factor, kbGraph *shape ) { kbLink * offs_currentlink; kbLine offs_currentline( m_GC ); kbLink* offs_nextlink; kbLine offs_nextline( m_GC ); kbNode* offs_end; kbNode* offs_bgn_next; kbNode* offs_end_next; // make a node from this point offs_end = new kbNode( GetEndNode(), m_GC ); Virtual_Point( offs_end, factor ); offs_currentlink = new kbLink( 0, _last_ins, offs_end, m_GC ); offs_currentline.Set( offs_currentlink ); offs_bgn_next = new kbNode( nextline->m_link->GetBeginNode(), m_GC ); nextline->Virtual_Point( offs_bgn_next, factor ); offs_end_next = new kbNode( nextline->m_link->GetEndNode(), m_GC ); nextline->Virtual_Point( offs_end_next, factor ); offs_nextlink = new kbLink( 0, offs_bgn_next, offs_end_next, m_GC ); offs_nextline.Set( offs_nextlink ); offs_currentline.CalculateLineParameters(); offs_nextline.CalculateLineParameters(); offs_currentline.Intersect2( offs_end, &offs_nextline ); // make a link between the current and the previous and add this to kbGraph shape->AddLink( offs_currentlink ); delete offs_nextlink; return( offs_end ); }
kbNode* kbLine::OffsetContour_rounded( kbLine* const nextline, kbNode* _last_ins, double factor, kbGraph *shape ) { kbLink * offs_currentlink; kbLine offs_currentline( m_GC ); kbLink* offs_nextlink; kbLine offs_nextline( m_GC ); kbNode* offs_end; kbNode* medial_axes_point = new kbNode( m_GC ); kbNode* bu_last_ins = new kbNode( _last_ins, m_GC ); kbNode* offs_bgn_next; kbNode* offs_end_next; // make a node from this point offs_end = new kbNode( GetEndNode(), m_GC ); *_last_ins = *GetBeginNode(); Virtual_Point( _last_ins, factor ); Virtual_Point( offs_end, factor ); offs_currentlink = new kbLink( 0, _last_ins, offs_end, m_GC ); offs_currentline.Set( offs_currentlink ); offs_bgn_next = new kbNode( nextline->m_link->GetBeginNode(), m_GC ); nextline->Virtual_Point( offs_bgn_next, factor ); offs_end_next = new kbNode( nextline->m_link->GetEndNode(), m_GC ); nextline->Virtual_Point( offs_end_next, factor ); offs_nextlink = new kbLink( 0, offs_bgn_next, offs_end_next, m_GC ); offs_nextline.Set( offs_nextlink ); offs_currentline.CalculateLineParameters(); offs_nextline.CalculateLineParameters(); offs_currentline.Intersect2( medial_axes_point, &offs_nextline ); double result_offs = sqrt( pow( ( double )GetEndNode()->GetY() - medial_axes_point->GetY(), 2 ) + pow( ( double )GetEndNode()->GetX() - medial_axes_point->GetX(), 2 ) ); if ( result_offs < fabs( m_GC->GetRoundfactor() * factor ) ) { *_last_ins = *bu_last_ins; *offs_end = *medial_axes_point; delete medial_axes_point; delete bu_last_ins; // make a link between the current and the previous and add this to kbGraph delete offs_nextlink; shape->AddLink( offs_currentlink ); return( offs_end ); } else { //let us create a circle *_last_ins = *bu_last_ins; delete medial_axes_point; delete bu_last_ins; kbNode* endarc = new kbNode( offs_bgn_next, m_GC ); shape->AddLink( offs_currentlink ); delete offs_nextlink; shape->CreateArc( GetEndNode(), &offs_currentline, endarc, fabs( factor ), m_GC->GetInternalCorrectionAber() ); return( endarc ); } }
//~~ glVector verticalForce() [glOrtogonalEdge] ~~ glVector diff = (GetEndNode().absGetPosition() - GetStartNode().absGetPosition()).Dir(); double a = fabs(diff.m_x) * fabs(diff.m_y); const double f = 0.05; double force; if (a <= f) force = a / f; else force = f / a; if (fabs(diff.m_x) > fabs(diff.m_y)) { return glVector(0,14*force * diff.m_y); } else { return glVector(14*force * diff.m_x,0); }
glVector startCenter = GetStartNode().absGetPosition(); glVector endCenter = GetEndNode().absGetPosition(); glVector diff = endCenter - startCenter; glVector centerdir = diff.Dir().Rotate90Degree(); glVector halfdiff(diff); halfdiff *= 0.5; double d; if (width<0) d = -width - radius(); else d = radius() - width; centerdir *= d; return startCenter + halfdiff + centerdir;