KiCad PCB EDA Suite
PNS::NODE Class Reference

Keep the router "world" - i.e. More...

#include <pns_node.h>

Classes

struct  DEFAULT_OBSTACLE_VISITOR
 

Public Types

enum  COLLISION_QUERY_SCOPE { CQS_ALL_RULES = 1 , CQS_IGNORE_HOLE_CLEARANCE = 2 }
 < Supported item types More...
 
typedef OPT< OBSTACLEOPT_OBSTACLE
 
typedef std::vector< ITEM * > ITEM_VECTOR
 
typedef std::vector< OBSTACLEOBSTACLES
 

Public Member Functions

 NODE ()
 
 ~NODE ()
 Return the expected clearance between items a and b. More...
 
int GetClearance (const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true) const
 
int GetHoleClearance (const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true) const
 
int GetHoleToHoleClearance (const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true) const
 Return the pre-set worst case clearance between any pair of items. More...
 
int GetMaxClearance () const
 Set the worst-case clearance between any pair of items. More...
 
void SetMaxClearance (int aClearance)
 Assign a clearance resolution function object. More...
 
void SetRuleResolver (RULE_RESOLVER *aFunc)
 
RULE_RESOLVERGetRuleResolver () const
 Return the number of joints. More...
 
int JointCount () const
 Return the number of nodes in the inheritance chain (wrs to the root node). More...
 
int Depth () const
 
int QueryColliding (const ITEM *aItem, OBSTACLES &aObstacles, int aKindMask=ITEM::ANY_T, int aLimitCount=-1, bool aDifferentNetsOnly=true, int aOverrideClearance=-1)
 Find items colliding (closer than clearance) with the item aItem. More...
 
int QueryJoints (const BOX2I &aBox, std::vector< JOINT * > &aJoints, LAYER_RANGE aLayerMask=LAYER_RANGE::All(), int aKindMask=ITEM::ANY_T)
 
OPT_OBSTACLE NearestObstacle (const LINE *aLine, int aKindMask=ITEM::ANY_T, const std::set< ITEM * > *aRestrictedSet=nullptr, bool aUseClearanceEpsilon=true)
 Follow the line in search of an obstacle that is nearest to the starting to the line's starting point. More...
 
OPT_OBSTACLE CheckColliding (const ITEM *aItem, int aKindMask=ITEM::ANY_T)
 Check if the item collides with anything else in the world, and if found, returns the obstacle. More...
 
OPT_OBSTACLE CheckColliding (const ITEM_SET &aSet, int aKindMask=ITEM::ANY_T)
 Check if any item in the set collides with anything else in the world, and if found, returns the obstacle. More...
 
const ITEM_SET HitTest (const VECTOR2I &aPoint) const
 Find all items that contain the point aPoint. More...
 
bool Add (std::unique_ptr< SEGMENT > aSegment, bool aAllowRedundant=false)
 Add an item to the current node. More...
 
void Add (std::unique_ptr< SOLID > aSolid)
 
void Add (std::unique_ptr< VIA > aVia)
 
bool Add (std::unique_ptr< ARC > aArc, bool aAllowRedundant=false)
 
void Add (LINE &aLine, bool aAllowRedundant=false)
 
void AddEdgeExclusion (std::unique_ptr< SHAPE > aShape)
 
bool QueryEdgeExclusions (const VECTOR2I &aPos) const
 
void Remove (ARC *aArc)
 Remove an item from this branch. More...
 
void Remove (SOLID *aSolid)
 
void Remove (VIA *aVia)
 
void Remove (SEGMENT *aSegment)
 
void Remove (ITEM *aItem)
 
void Remove (LINE &aLine)
 Removes a line from this branch. More...
 
void Replace (ITEM *aOldItem, std::unique_ptr< ITEM > aNewItem)
 Replace an item with another one. More...
 
void Replace (LINE &aOldLine, LINE &aNewLine)
 
NODEBranch ()
 Create a lightweight copy (called branch) of self that tracks the changes (added/removed items) wrs to the root. More...
 
const LINE AssembleLine (LINKED_ITEM *aSeg, int *aOriginSegmentIndex=nullptr, bool aStopAtLockedJoints=false, bool aFollowLockedSegments=false)
 Follow the joint map to assemble a line connecting two non-trivial joints starting from segment aSeg. More...
 
void Dump (bool aLong=false)
 
void GetUpdatedItems (ITEM_VECTOR &aRemoved, ITEM_VECTOR &aAdded)
 Return the list of items removed and added in this branch with respect to the root branch. More...
 
void Commit (NODE *aNode)
 Apply the changes from a given branch (aNode) to the root branch. More...
 
JOINTFindJoint (const VECTOR2I &aPos, int aLayer, int aNet)
 Search for a joint at a given position, layer and belonging to given net. More...
 
void LockJoint (const VECTOR2I &aPos, const ITEM *aItem, bool aLock)
 
JOINTFindJoint (const VECTOR2I &aPos, const ITEM *aItem)
 Search for a joint at a given position, linked to given item. More...
 
int FindLinesBetweenJoints (const JOINT &aA, const JOINT &aB, std::vector< LINE > &aLines)
 Find the joints corresponding to the ends of line aLine. More...
 
void FindLineEnds (const LINE &aLine, JOINT &aA, JOINT &aB)
 Destroy all child nodes. Applicable only to the root node. More...
 
void KillChildren ()
 
void AllItemsInNet (int aNet, std::set< ITEM * > &aItems, int aKindMask=-1)
 
void ClearRanks (int aMarkerMask=MK_HEAD|MK_VIOLATION|MK_HOLE)
 
void RemoveByMarker (int aMarker)
 
ITEMFindItemByParent (const BOARD_ITEM *aParent)
 
bool HasChildren () const
 
NODEGetParent () const
 Check if this branch contains an updated version of the m_item from the root branch. More...
 
bool Overrides (ITEM *aItem) const
 
void FixupVirtualVias ()
 
void SetCollisionQueryScope (COLLISION_QUERY_SCOPE aScope)
 
COLLISION_QUERY_SCOPE GetCollisionQueryScope () const
 

Private Types

typedef std::unordered_multimap< JOINT::HASH_TAG, JOINT, JOINT::JOINT_TAG_HASHJOINT_MAP
 
typedef JOINT_MAP::value_type TagJointPair
 

Private Member Functions

void Add (std::unique_ptr< ITEM > aItem, bool aAllowRedundant=false)
 
 NODE (const NODE &aB)
 nodes are not copyable More...
 
NODEoperator= (const NODE &aB)
 Try to find matching joint and creates a new one if not found. More...
 
JOINTtouchJoint (const VECTOR2I &aPos, const LAYER_RANGE &aLayers, int aNet)
 Touch a joint and links it to an m_item. More...
 
void linkJoint (const VECTOR2I &aPos, const LAYER_RANGE &aLayers, int aNet, ITEM *aWhere)
 Unlink an item from a joint. More...
 
void unlinkJoint (const VECTOR2I &aPos, const LAYER_RANGE &aLayers, int aNet, ITEM *aWhere)
 Helpers for adding/removing items. More...
 
void addSolid (SOLID *aSeg)
 
void addSegment (SEGMENT *aSeg)
 
void addVia (VIA *aVia)
 
void addArc (ARC *aVia)
 
void removeSolidIndex (SOLID *aSeg)
 
void removeSegmentIndex (SEGMENT *aSeg)
 
void removeViaIndex (VIA *aVia)
 
void removeArcIndex (ARC *aVia)
 
void doRemove (ITEM *aItem)
 
void unlinkParent ()
 
void releaseChildren ()
 
void releaseGarbage ()
 
void rebuildJoint (JOINT *aJoint, ITEM *aItem)
 
bool isRoot () const
 
SEGMENTfindRedundantSegment (const VECTOR2I &A, const VECTOR2I &B, const LAYER_RANGE &lr, int aNet)
 
SEGMENTfindRedundantSegment (SEGMENT *aSeg)
 
ARCfindRedundantArc (const VECTOR2I &A, const VECTOR2I &B, const LAYER_RANGE &lr, int aNet)
 
ARCfindRedundantArc (ARC *aSeg)
 Scan the joint map, forming a line starting from segment (current). More...
 
void followLine (LINKED_ITEM *aCurrent, bool aScanDirection, int &aPos, int aLimit, VECTOR2I *aCorners, LINKED_ITEM **aSegments, bool *aArcReversed, bool &aGuardHit, bool aStopAtLockedJoints, bool aFollowLockedSegments)
 

Private Attributes

JOINT_MAP m_joints
 hash table with the joints, linking the items. More...
 
NODEm_parent
 node this node was branched from More...
 
NODEm_root
 root node of the whole hierarchy More...
 
std::set< NODE * > m_children
 list of nodes branched from this one More...
 
std::unordered_set< ITEM * > m_override
 hash of root's items that have been changed in this node More...
 
int m_maxClearance
 worst case item-item clearance More...
 
RULE_RESOLVERm_ruleResolver
 Design rules resolver. More...
 
INDEXm_index
 Geometric/Net index of the items. More...
 
int m_depth
 depth of the node (number of parent nodes in the inheritance chain) More...
 
std::vector< std::unique_ptr< SHAPE > > m_edgeExclusions
 
std::unordered_set< ITEM * > m_garbageItems
 
COLLISION_QUERY_SCOPE m_collisionQueryScope
 

Detailed Description

Keep the router "world" - i.e.

all the tracks, vias, solids in a hierarchical and indexed way.

Features:

  • spatial-indexed container for PCB item shapes.
  • collision search & clearance checking.
  • assembly of lines connecting joints, finding loops and unique paths.
  • lightweight cloning/branching (for recursive optimization and shove springback).

Definition at line 149 of file pns_node.h.

Member Typedef Documentation

◆ ITEM_VECTOR

typedef std::vector<ITEM*> PNS::NODE::ITEM_VECTOR

Definition at line 161 of file pns_node.h.

◆ JOINT_MAP

typedef std::unordered_multimap<JOINT::HASH_TAG, JOINT, JOINT::JOINT_TAG_HASH> PNS::NODE::JOINT_MAP
private

Definition at line 472 of file pns_node.h.

◆ OBSTACLES

typedef std::vector<OBSTACLE> PNS::NODE::OBSTACLES

Definition at line 162 of file pns_node.h.

◆ OPT_OBSTACLE

Definition at line 160 of file pns_node.h.

◆ TagJointPair

typedef JOINT_MAP::value_type PNS::NODE::TagJointPair
private

Definition at line 473 of file pns_node.h.

Member Enumeration Documentation

◆ COLLISION_QUERY_SCOPE

< Supported item types

Enumerator
CQS_ALL_RULES 

check all rules

CQS_IGNORE_HOLE_CLEARANCE 

check everything except hole2hole / hole2copper

Definition at line 154 of file pns_node.h.

155 {
156 CQS_ALL_RULES = 1,
158 };
@ CQS_IGNORE_HOLE_CLEARANCE
check everything except hole2hole / hole2copper
Definition: pns_node.h:157
@ CQS_ALL_RULES
check all rules
Definition: pns_node.h:156

Constructor & Destructor Documentation

◆ NODE() [1/2]

PNS::NODE::NODE ( )

Definition at line 54 of file pns_node.cpp.

55{
56 m_depth = 0;
57 m_root = this;
58 m_parent = nullptr;
59 m_maxClearance = 800000; // fixme: depends on how thick traces are.
60 m_ruleResolver = nullptr;
61 m_index = new INDEX;
63
64#ifdef DEBUG
65 allocNodes.insert( this );
66#endif
67}
NODE * m_root
root node of the whole hierarchy
Definition: pns_node.h:479
COLLISION_QUERY_SCOPE m_collisionQueryScope
Definition: pns_node.h:495
INDEX * m_index
Geometric/Net index of the items.
Definition: pns_node.h:487
int m_maxClearance
worst case item-item clearance
Definition: pns_node.h:485
int m_depth
depth of the node (number of parent nodes in the inheritance chain)
Definition: pns_node.h:488
NODE * m_parent
node this node was branched from
Definition: pns_node.h:478
RULE_RESOLVER * m_ruleResolver
Design rules resolver.
Definition: pns_node.h:486

References CQS_ALL_RULES, m_collisionQueryScope, m_depth, m_index, m_maxClearance, m_parent, m_root, and m_ruleResolver.

Referenced by Branch().

◆ ~NODE()

PNS::NODE::~NODE ( )

Return the expected clearance between items a and b.

Definition at line 70 of file pns_node.cpp.

71{
72 if( !m_children.empty() )
73 {
74 wxLogTrace( wxT( "PNS" ), wxT( "attempting to free a node that has kids." ) );
75 assert( false );
76 }
77
78#ifdef DEBUG
79 if( allocNodes.find( this ) == allocNodes.end() )
80 {
81 wxLogTrace( wxT( "PNS" ), wxT( "attempting to free an already-free'd node." ) );
82 assert( false );
83 }
84
85 allocNodes.erase( this );
86#endif
87
88 m_joints.clear();
89
90 for( ITEM* item : *m_index )
91 {
92 if( item->BelongsTo( this ) )
93 delete item;
94 }
95
98
99 delete m_index;
100}
void releaseGarbage()
Definition: pns_node.cpp:1416
std::set< NODE * > m_children
list of nodes branched from this one
Definition: pns_node.h:480
JOINT_MAP m_joints
hash table with the joints, linking the items.
Definition: pns_node.h:475
void unlinkParent()
Definition: pns_node.cpp:176

References m_children, m_index, m_joints, releaseGarbage(), and unlinkParent().

◆ NODE() [2/2]

PNS::NODE::NODE ( const NODE aB)
private

nodes are not copyable

Member Function Documentation

◆ Add() [1/6]

void PNS::NODE::Add ( LINE aLine,
bool  aAllowRedundant = false 
)

Definition at line 595 of file pns_node.cpp.

596{
597 assert( !aLine.IsLinked() );
598
599 SHAPE_LINE_CHAIN& l = aLine.Line();
600
601 for( size_t i = 0; i < l.ArcCount(); i++ )
602 {
603 auto s = l.Arc( i );
604 ARC* rarc;
605
606 if( !aAllowRedundant && ( rarc = findRedundantArc( s.GetP0(), s.GetP1(), aLine.Layers(),
607 aLine.Net() ) ) )
608 {
609 aLine.Link( rarc );
610 }
611 else
612 {
613 auto newarc = std::make_unique< ARC >( aLine, s );
614 aLine.Link( newarc.get() );
615 Add( std::move( newarc ), true );
616 }
617 }
618
619 for( int i = 0; i < l.SegmentCount(); i++ )
620 {
621 if( l.IsArcSegment( i ) )
622 continue;
623
624 SEG s = l.CSegment( i );
625
626 if( s.A != s.B )
627 {
628 SEGMENT* rseg;
629
630 if( !aAllowRedundant && ( rseg = findRedundantSegment( s.A, s.B, aLine.Layers(),
631 aLine.Net() ) ) )
632 {
633 // another line could be referencing this segment too :(
634 aLine.Link( rseg );
635 }
636 else
637 {
638 std::unique_ptr<SEGMENT> newseg = std::make_unique<SEGMENT>( aLine, s );
639 aLine.Link( newseg.get() );
640 Add( std::move( newseg ), true );
641 }
642 }
643 }
644}
bool Add(std::unique_ptr< SEGMENT > aSegment, bool aAllowRedundant=false)
Add an item to the current node.
Definition: pns_node.cpp:656
ARC * findRedundantArc(const VECTOR2I &A, const VECTOR2I &B, const LAYER_RANGE &lr, int aNet)
Definition: pns_node.cpp:1546
SEGMENT * findRedundantSegment(const VECTOR2I &A, const VECTOR2I &B, const LAYER_RANGE &lr, int aNet)
Definition: pns_node.cpp:1511
Definition: seg.h:42
VECTOR2I A
Definition: seg.h:49
VECTOR2I B
Definition: seg.h:50
Represent a polyline containing arcs as well as line segments: A chain of connected line and/or arc s...
const SHAPE_ARC & Arc(size_t aArc) const
int SegmentCount() const
Return the number of segments in this line chain.
size_t ArcCount() const
const SEG CSegment(int aIndex) const
Return a constant copy of the aIndex segment in the line chain.
bool IsArcSegment(size_t aSegment) const

References SEG::A, Add(), SHAPE_LINE_CHAIN::Arc(), SHAPE_LINE_CHAIN::ArcCount(), SEG::B, SHAPE_LINE_CHAIN::CSegment(), findRedundantArc(), findRedundantSegment(), SHAPE_LINE_CHAIN::IsArcSegment(), PNS::LINK_HOLDER::IsLinked(), PNS::ITEM::Layers(), PNS::LINE::Line(), PNS::LINK_HOLDER::Link(), PNS::ITEM::Net(), and SHAPE_LINE_CHAIN::SegmentCount().

◆ Add() [2/6]

bool PNS::NODE::Add ( std::unique_ptr< ARC aArc,
bool  aAllowRedundant = false 
)

Definition at line 684 of file pns_node.cpp.

685{
686 const SHAPE_ARC& arc = aArc->CArc();
687
688 if( !aAllowRedundant && findRedundantArc( arc.GetP0(), arc.GetP1(), aArc->Layers(),
689 aArc->Net() ) )
690 {
691 return false;
692 }
693
694 aArc->SetOwner( this );
695 addArc( aArc.release() );
696 return true;
697}
void addArc(ARC *aVia)
Definition: pns_node.cpp:675
const VECTOR2I & GetP1() const
Definition: shape_arc.h:113
const VECTOR2I & GetP0() const
Definition: shape_arc.h:112

References addArc(), findRedundantArc(), SHAPE_ARC::GetP0(), and SHAPE_ARC::GetP1().

◆ Add() [3/6]

void PNS::NODE::Add ( std::unique_ptr< ITEM aItem,
bool  aAllowRedundant = false 
)
private

Definition at line 700 of file pns_node.cpp.

701{
702 switch( aItem->Kind() )
703 {
704 case ITEM::SOLID_T: Add( ItemCast<SOLID>( std::move( aItem ) ) ); break;
705 case ITEM::SEGMENT_T: Add( ItemCast<SEGMENT>( std::move( aItem ) ), aAllowRedundant ); break;
706 case ITEM::VIA_T: Add( ItemCast<VIA>( std::move( aItem ) ) ); break;
707
708 case ITEM::ARC_T:
709 //todo(snh): Add redundant search
710 Add( ItemCast<ARC>( std::move( aItem ) ) );
711 break;
712
713 case ITEM::LINE_T:
714 default:
715 assert( false );
716 }
717}
@ SOLID_T
Definition: pns_item.h:63
@ LINE_T
Definition: pns_item.h:64
@ SEGMENT_T
Definition: pns_item.h:66

References Add(), PNS::ITEM::ARC_T, PNS::ITEM::LINE_T, PNS::ITEM::SEGMENT_T, PNS::ITEM::SOLID_T, and PNS::ITEM::VIA_T.

◆ Add() [4/6]

bool PNS::NODE::Add ( std::unique_ptr< SEGMENT aSegment,
bool  aAllowRedundant = false 
)

Add an item to the current node.

Parameters
aSegmentitem to add.
aAllowRedundantif true, duplicate items are allowed (e.g. a segment or via at the same coordinates as an existing one).
Returns
true if added

Definition at line 656 of file pns_node.cpp.

657{
658 if( aSegment->Seg().A == aSegment->Seg().B )
659 {
660 wxLogTrace( wxT( "PNS" ),
661 wxT( "attempting to add a segment with same end coordinates, ignoring." ) );
662 return false;
663 }
664
665 if( !aAllowRedundant && findRedundantSegment( aSegment.get() ) )
666 return false;
667
668 aSegment->SetOwner( this );
669 addSegment( aSegment.release() );
670
671 return true;
672}
void addSegment(SEGMENT *aSeg)
Definition: pns_node.cpp:647

References addSegment(), and findRedundantSegment().

Referenced by Add(), Commit(), PNS::COMPONENT_DRAGGER::Drag(), PNS::DRAGGER::dragMarkObstacles(), PNS::DRAGGER::dragShove(), PNS::DRAGGER::dragViaMarkObstacles(), PNS::DRAGGER::dragViaWalkaround(), PNS::DIFF_PAIR_PLACER::FixRoute(), PNS::LINE_PLACER::FixRoute(), PNS::DP_MEANDER_PLACER::FixRoute(), PNS::MEANDER_PLACER::FixRoute(), FixupVirtualVias(), PNS::DRAGGER::optimizeAndUpdateDraggedLine(), PNS::LINE_PLACER::removeLoops(), Replace(), PNS::SHOVE::ShoveLines(), PNS::SHOVE::ShoveMultiLines(), PNS::TOPOLOGY::SimplifyLine(), PNS::LINE_PLACER::simplifyNewLine(), PNS::LINE_PLACER::SplitAdjacentSegments(), PNS_KICAD_IFACE_BASE::syncGraphicalItem(), PNS_KICAD_IFACE_BASE::syncTextItem(), PNS_KICAD_IFACE_BASE::SyncWorld(), and PNS_KICAD_IFACE_BASE::syncZone().

◆ Add() [5/6]

void PNS::NODE::Add ( std::unique_ptr< SOLID aSolid)

Definition at line 573 of file pns_node.cpp.

574{
575 aSolid->SetOwner( this );
576 addSolid( aSolid.release() );
577}
void addSolid(SOLID *aSeg)
Definition: pns_node.cpp:564

References addSolid().

◆ Add() [6/6]

void PNS::NODE::Add ( std::unique_ptr< VIA aVia)

Definition at line 588 of file pns_node.cpp.

589{
590 aVia->SetOwner( this );
591 addVia( aVia.release() );
592}
void addVia(VIA *aVia)
Definition: pns_node.cpp:580

References addVia().

◆ addArc()

void PNS::NODE::addArc ( ARC aVia)
private

Definition at line 675 of file pns_node.cpp.

676{
677 linkJoint( aArc->Anchor( 0 ), aArc->Layers(), aArc->Net(), aArc );
678 linkJoint( aArc->Anchor( 1 ), aArc->Layers(), aArc->Net(), aArc );
679
680 m_index->Add( aArc );
681}
void Add(ITEM *aItem)
Adds item to the spatial index.
Definition: pns_index.cpp:28
void linkJoint(const VECTOR2I &aPos, const LAYER_RANGE &aLayers, int aNet, ITEM *aWhere)
Unlink an item from a joint.
Definition: pns_node.cpp:1280

References PNS::INDEX::Add(), PNS::ARC::Anchor(), PNS::ITEM::Layers(), linkJoint(), m_index, and PNS::ITEM::Net().

Referenced by Add().

◆ AddEdgeExclusion()

void PNS::NODE::AddEdgeExclusion ( std::unique_ptr< SHAPE aShape)

Definition at line 720 of file pns_node.cpp.

721{
722 m_edgeExclusions.push_back( std::move( aShape ) );
723}
std::vector< std::unique_ptr< SHAPE > > m_edgeExclusions
Definition: pns_node.h:491

References m_edgeExclusions.

Referenced by PNS_KICAD_IFACE_BASE::SyncWorld().

◆ addSegment()

void PNS::NODE::addSegment ( SEGMENT aSeg)
private

Definition at line 647 of file pns_node.cpp.

648{
649 linkJoint( aSeg->Seg().A, aSeg->Layers(), aSeg->Net(), aSeg );
650 linkJoint( aSeg->Seg().B, aSeg->Layers(), aSeg->Net(), aSeg );
651
652 m_index->Add( aSeg );
653}

References SEG::A, PNS::INDEX::Add(), SEG::B, PNS::ITEM::Layers(), linkJoint(), m_index, PNS::ITEM::Net(), and PNS::SEGMENT::Seg().

Referenced by Add().

◆ addSolid()

void PNS::NODE::addSolid ( SOLID aSeg)
private

Definition at line 564 of file pns_node.cpp.

565{
566 if( aSolid->IsRoutable() )
567 linkJoint( aSolid->Pos(), aSolid->Layers(), aSolid->Net(), aSolid );
568
569 m_index->Add( aSolid );
570}

References PNS::INDEX::Add(), PNS::ITEM::IsRoutable(), PNS::ITEM::Layers(), linkJoint(), m_index, PNS::ITEM::Net(), and PNS::SOLID::Pos().

Referenced by Add().

◆ addVia()

void PNS::NODE::addVia ( VIA aVia)
private

Definition at line 580 of file pns_node.cpp.

581{
582 linkJoint( aVia->Pos(), aVia->Layers(), aVia->Net(), aVia );
583
584 m_index->Add( aVia );
585}

References PNS::INDEX::Add(), PNS::ITEM::Layers(), linkJoint(), m_index, PNS::ITEM::Net(), and PNS::VIA::Pos().

Referenced by Add().

◆ AllItemsInNet()

void PNS::NODE::AllItemsInNet ( int  aNet,
std::set< ITEM * > &  aItems,
int  aKindMask = -1 
)

Definition at line 1457 of file pns_node.cpp.

1458{
1460
1461 if( l_cur )
1462 {
1463 for( ITEM* item : *l_cur )
1464 {
1465 if( item->OfKind( aKindMask ) && item->IsRoutable() )
1466 aItems.insert( item );
1467 }
1468 }
1469
1470 if( !isRoot() )
1471 {
1473
1474 if( l_root )
1475 {
1476 for( ITEM* item : *l_root )
1477 {
1478 if( !Overrides( item ) && item->OfKind( aKindMask ) && item->IsRoutable() )
1479 aItems.insert( item );
1480 }
1481 }
1482 }
1483}
std::list< ITEM * > NET_ITEMS_LIST
Definition: pns_index.h:48
NET_ITEMS_LIST * GetItemsForNet(int aNet)
Returns list of all items in a given net.
Definition: pns_index.cpp:71
bool Overrides(ITEM *aItem) const
Definition: pns_node.h:403
bool isRoot() const
Definition: pns_node.h:453

References PNS::INDEX::GetItemsForNet(), isRoot(), m_index, m_root, and Overrides().

Referenced by PNS::TOPOLOGY::AssembleDiffPair(), PNS::DIFF_PAIR_PLACER::FindDpPrimitivePair(), and PNS::TOPOLOGY::NearestUnconnectedItem().

◆ AssembleLine()

const LINE PNS::NODE::AssembleLine ( LINKED_ITEM aSeg,
int *  aOriginSegmentIndex = nullptr,
bool  aStopAtLockedJoints = false,
bool  aFollowLockedSegments = false 
)

Follow the joint map to assemble a line connecting two non-trivial joints starting from segment aSeg.

Parameters
aSegthe initial segment.
aOriginSegmentIndexindex of aSeg in the resulting line.
aStopAtLockedJointswill terminate the line at the first locked joint encountered
aFollowLockedSegmentswill consider a joint between a locked segment and an unlocked segment of the same width as a trivial joint.
Returns
the line Print the contents and joints structure.

Definition at line 983 of file pns_node.cpp.

985{
986 const int MaxVerts = 1024 * 16;
987
988 std::array<VECTOR2I, MaxVerts + 1> corners;
989 std::array<LINKED_ITEM*, MaxVerts + 1> segs;
990 std::array<bool, MaxVerts + 1> arcReversed;
991
992 LINE pl;
993 bool guardHit = false;
994
995 int i_start = MaxVerts / 2;
996 int i_end = i_start + 1;
997
998 pl.SetWidth( aSeg->Width() );
999 pl.SetLayers( aSeg->Layers() );
1000 pl.SetNet( aSeg->Net() );
1001 pl.SetOwner( this );
1002
1003 followLine( aSeg, false, i_start, MaxVerts, corners.data(), segs.data(), arcReversed.data(),
1004 guardHit, aStopAtLockedJoints, aFollowLockedSegments );
1005
1006 if( !guardHit )
1007 {
1008 followLine( aSeg, true, i_end, MaxVerts, corners.data(), segs.data(), arcReversed.data(),
1009 guardHit, aStopAtLockedJoints, aFollowLockedSegments );
1010 }
1011
1012 int n = 0;
1013
1014 LINKED_ITEM* prev_seg = nullptr;
1015 bool originSet = false;
1016
1017 SHAPE_LINE_CHAIN& line = pl.Line();
1018
1019 for( int i = i_start + 1; i < i_end; i++ )
1020 {
1021 const VECTOR2I& p = corners[i];
1022 LINKED_ITEM* li = segs[i];
1023
1024 if( !li || li->Kind() != ITEM::ARC_T )
1025 line.Append( p );
1026
1027 if( li && prev_seg != li )
1028 {
1029 if( li->Kind() == ITEM::ARC_T )
1030 {
1031 const ARC* arc = static_cast<const ARC*>( li );
1032 const SHAPE_ARC* sa = static_cast<const SHAPE_ARC*>( arc->Shape() );
1033
1034 int nSegs = line.PointCount();
1035 VECTOR2I last = nSegs ? line.CPoint( -1 ) : VECTOR2I();
1036 ssize_t lastShape = nSegs ? line.ArcIndex( static_cast<ssize_t>( nSegs ) - 1 ) : -1;
1037
1038 line.Append( arcReversed[i] ? sa->Reversed() : *sa );
1039 }
1040
1041 pl.Link( li );
1042
1043 // latter condition to avoid loops
1044 if( li == aSeg && aOriginSegmentIndex && !originSet )
1045 {
1046 wxASSERT( n < line.SegmentCount() ||
1047 ( n == line.SegmentCount() && li->Kind() == ITEM::SEGMENT_T ) );
1048 *aOriginSegmentIndex = line.PointCount() - 1;
1049 originSet = true;
1050 }
1051 }
1052
1053 prev_seg = li;
1054 }
1055
1056 // Remove duplicate verts, but do NOT remove colinear segments here!
1057 pl.Line().Simplify( false );
1058
1059 // TODO: maintain actual segment index under simplifcation system
1060 if( aOriginSegmentIndex && *aOriginSegmentIndex >= pl.SegmentCount() )
1061 *aOriginSegmentIndex = pl.SegmentCount() - 1;
1062
1063 assert( pl.SegmentCount() != 0 );
1064
1065 return pl;
1066}
void followLine(LINKED_ITEM *aCurrent, bool aScanDirection, int &aPos, int aLimit, VECTOR2I *aCorners, LINKED_ITEM **aSegments, bool *aArcReversed, bool &aGuardHit, bool aStopAtLockedJoints, bool aFollowLockedSegments)
Definition: pns_node.cpp:934
SHAPE_ARC Reversed() const
Definition: shape_arc.cpp:578
int PointCount() const
Return the number of points (vertices) in this line chain.
ssize_t ArcIndex(size_t aSegment) const
Return the arc index for the given segment index.
void Append(int aX, int aY, bool aAllowDuplication=false)
Append a new point at the end of the line chain.
const VECTOR2I & CPoint(int aIndex) const
Return a reference to a given point in the line chain.
VECTOR2< int > VECTOR2I
Definition: vector2d.h:607

References SHAPE_LINE_CHAIN::Append(), PNS::ITEM::ARC_T, SHAPE_LINE_CHAIN::ArcIndex(), SHAPE_LINE_CHAIN::CPoint(), followLine(), PNS::ITEM::Kind(), PNS::ITEM::Layers(), PNS::LINE::Line(), PNS::LINK_HOLDER::Link(), PNS::ITEM::Net(), SHAPE_LINE_CHAIN::PointCount(), SHAPE_ARC::Reversed(), PNS::ITEM::SEGMENT_T, SHAPE_LINE_CHAIN::SegmentCount(), PNS::LINE::SegmentCount(), PNS::ITEM::SetLayers(), PNS::ITEM::SetNet(), PNS::ITEM::SetOwner(), PNS::LINE::SetWidth(), PNS::ARC::Shape(), SHAPE_LINE_CHAIN::Simplify(), and PNS::LINKED_ITEM::Width().

Referenced by PNS::TOPOLOGY::AssembleDiffPair(), PNS::SHOVE::assembleLine(), PNS::TOPOLOGY::AssembleTrivialPath(), Dump(), FindLinesBetweenJoints(), PNS::DRAGGER::findViaFanoutByHandle(), PNS::TOPOLOGY::followTrivialPath(), PNS::LINE_PLACER::removeLoops(), PNS::TOPOLOGY::SimplifyLine(), PNS::LINE_PLACER::simplifyNewLine(), PNS::MEANDER_PLACER::Start(), PNS::MEANDER_SKEW_PLACER::Start(), PNS::COMPONENT_DRAGGER::Start(), PNS::DRAGGER::startDragArc(), and PNS::DRAGGER::startDragSegment().

◆ Branch()

NODE * PNS::NODE::Branch ( )

Create a lightweight copy (called branch) of self that tracks the changes (added/removed items) wrs to the root.

Note
If there are any branches in use, their parents must not be deleted.
Returns
the new branch.

Definition at line 139 of file pns_node.cpp.

140{
141 NODE* child = new NODE;
142
143 m_children.insert( child );
144
145 child->m_depth = m_depth + 1;
146 child->m_parent = this;
147 child->m_ruleResolver = m_ruleResolver;
148 child->m_root = isRoot() ? this : m_root;
150 child->m_collisionQueryScope = m_collisionQueryScope;
151
152 // Immediate offspring of the root branch needs not copy anything. For the rest, deep-copy
153 // joints, overridden item maps and pointers to stored items.
154 if( !isRoot() )
155 {
156 JOINT_MAP::iterator j;
157
158 for( ITEM* item : *m_index )
159 child->m_index->Add( item );
160
161 child->m_joints = m_joints;
162 child->m_override = m_override;
163 }
164
165#if 0
166 wxLogTrace( wxT( "PNS" ), wxT( "%d items, %d joints, %d overrides" ),
167 child->m_index->Size(),
168 (int) child->m_joints.size(),
169 (int) child->m_override.size() );
170#endif
171
172 return child;
173}
std::unordered_set< ITEM * > m_override
hash of root's items that have been changed in this node
Definition: pns_node.h:482

References PNS::INDEX::Add(), isRoot(), m_children, m_collisionQueryScope, m_depth, m_index, m_joints, m_maxClearance, m_override, m_parent, m_root, m_ruleResolver, NODE(), and PNS::INDEX::Size().

Referenced by PNS::MEANDER_PLACER::doMove(), PNS::COMPONENT_DRAGGER::Drag(), PNS::DRAGGER::dragMarkObstacles(), PNS::DRAGGER::dragWalkaround(), PNS::LINE_PLACER::FixRoute(), PNS::DIFF_PAIR_PLACER::initPlacement(), PNS::LINE_PLACER::initPlacement(), PNS::TOPOLOGY::LeadingRatLine(), PNS::DIFF_PAIR_PLACER::Move(), PNS::DP_MEANDER_PLACER::Move(), PNS::LINE_PLACER::Move(), PNS::SHOVE::SetInitialLine(), PNS::SHOVE::ShoveDraggingVia(), PNS::SHOVE::ShoveLines(), PNS::SHOVE::ShoveMultiLines(), PNS::DP_MEANDER_PLACER::Start(), PNS::MEANDER_PLACER::Start(), PNS::MEANDER_SKEW_PLACER::Start(), PNS::DIFF_PAIR_PLACER::tryWalkDp(), and PNS::LINE_PLACER::UnfixRoute().

◆ CheckColliding() [1/2]

NODE::OPT_OBSTACLE PNS::NODE::CheckColliding ( const ITEM aItem,
int  aKindMask = ITEM::ANY_T 
)

Check if the item collides with anything else in the world, and if found, returns the obstacle.

Parameters
aItemthe item to find collisions with
aKindMaskmask of obstacle types to take into account
Returns
the obstacle, if found, otherwise empty.

Definition at line 468 of file pns_node.cpp.

469{
470 OBSTACLES obs;
471
472 obs.reserve( 100 );
473
474 if( aItemA->Kind() == ITEM::LINE_T )
475 {
476 int n = 0;
477 const LINE* line = static_cast<const LINE*>( aItemA );
478 const SHAPE_LINE_CHAIN& l = line->CLine();
479
480 for( int i = 0; i < l.SegmentCount(); i++ )
481 {
482 const SEGMENT s( *line, l.CSegment( i ) );
483 n += QueryColliding( &s, obs, aKindMask, 1 );
484
485 if( n )
486 return OPT_OBSTACLE( obs[0] );
487 }
488
489 if( line->EndsWithVia() )
490 {
491 n += QueryColliding( &line->Via(), obs, aKindMask, 1 );
492
493 if( n )
494 return OPT_OBSTACLE( obs[0] );
495 }
496 }
497 else if( QueryColliding( aItemA, obs, aKindMask, 1 ) > 0 )
498 {
499 return OPT_OBSTACLE( obs[0] );
500 }
501
502 return OPT_OBSTACLE();
503}
int QueryColliding(const ITEM *aItem, OBSTACLES &aObstacles, int aKindMask=ITEM::ANY_T, int aLimitCount=-1, bool aDifferentNetsOnly=true, int aOverrideClearance=-1)
Find items colliding (closer than clearance) with the item aItem.
Definition: pns_node.cpp:271
std::vector< OBSTACLE > OBSTACLES
Definition: pns_node.h:162
OPT< OBSTACLE > OPT_OBSTACLE
Definition: pns_node.h:160

References PNS::LINE::CLine(), SHAPE_LINE_CHAIN::CSegment(), PNS::LINE::EndsWithVia(), PNS::ITEM::Kind(), PNS::ITEM::LINE_T, QueryColliding(), SHAPE_LINE_CHAIN::SegmentCount(), and PNS::LINE::Via().

Referenced by PNS::DIFF_PAIR_PLACER::attemptWalk(), CheckColliding(), PNS::OPTIMIZER::checkColliding(), PNS::checkDpColliding(), PNS::DP_MEANDER_PLACER::CheckFit(), PNS::MEANDER_PLACER::CheckFit(), PNS::DRAGGER::dragMarkObstacles(), PNS::DRAGGER::dragViaWalkaround(), PNS::DRAGGER::dragWalkaround(), PNS::OPTIMIZER::fanoutCleanup(), PNS::COMPONENT_DRAGGER::FixRoute(), PNS::LINE_PLACER::FixRoute(), PNS::DIFF_PAIR_PLACER::propagateDpHeadForces(), PNS::VIA::PushoutForce(), PNS::SHOVE::reduceSpringback(), PNS::LINE_PLACER::reduceTail(), PNS::DIFF_PAIR_PLACER::rhMarkObstacles(), PNS::DIFF_PAIR_PLACER::rhShoveOnly(), PNS::LINE_PLACER::rhWalkOnly(), PNS::WALKAROUND::Route(), PNS::SHOVE::ShoveLines(), PNS::tightenSegment(), and PNS::verifyDpBypass().

◆ CheckColliding() [2/2]

NODE::OPT_OBSTACLE PNS::NODE::CheckColliding ( const ITEM_SET aSet,
int  aKindMask = ITEM::ANY_T 
)

Check if any item in the set collides with anything else in the world, and if found, returns the obstacle.

Parameters
aSetset of items to find collisions with.
aKindMaskmask of obstacle types to take into account.
Returns
the obstacle, if found, otherwise empty.

Definition at line 454 of file pns_node.cpp.

455{
456 for( const ITEM* item : aSet.CItems() )
457 {
458 OPT_OBSTACLE obs = CheckColliding( item, aKindMask );
459
460 if( obs )
461 return obs;
462 }
463
464 return OPT_OBSTACLE();
465}
OPT_OBSTACLE CheckColliding(const ITEM *aItem, int aKindMask=ITEM::ANY_T)
Check if the item collides with anything else in the world, and if found, returns the obstacle.
Definition: pns_node.cpp:468

References CheckColliding(), and PNS::ITEM_SET::CItems().

◆ ClearRanks()

void PNS::NODE::ClearRanks ( int  aMarkerMask = MK_HEAD | MK_VIOLATION | MK_HOLE)

Definition at line 1486 of file pns_node.cpp.

1487{
1488 for( ITEM* item : *m_index )
1489 {
1490 item->SetRank( -1 );
1491 item->Mark( item->Marker() & ~aMarkerMask );
1492 }
1493}

References m_index.

Referenced by PNS::SHOVE::ShoveDraggingVia(), PNS::SHOVE::ShoveLines(), and PNS::SHOVE::ShoveMultiLines().

◆ Commit()

void PNS::NODE::Commit ( NODE aNode)

Apply the changes from a given branch (aNode) to the root branch.

Calling on a non-root branch will fail. Calling commit also kills all children nodes of the root branch.

Parameters
aNodenode to commit changes from.

Definition at line 1431 of file pns_node.cpp.

1432{
1433 if( aNode->isRoot() )
1434 return;
1435
1436 for( ITEM* item : aNode->m_override )
1437 Remove( item );
1438
1439 for( ITEM* item : *aNode->m_index )
1440 {
1441 item->SetRank( -1 );
1442 item->Unmark();
1443 Add( std::unique_ptr<ITEM>( item ) );
1444 }
1445
1448}
void releaseChildren()
Definition: pns_node.cpp:1403
void Remove(ARC *aArc)
Remove an item from this branch.
Definition: pns_node.cpp:873

References Add(), isRoot(), m_index, m_override, releaseChildren(), releaseGarbage(), Remove(), PNS::ITEM::SetRank(), and PNS::ITEM::Unmark().

◆ Depth()

int PNS::NODE::Depth ( ) const
inline

Definition at line 203 of file pns_node.h.

204 {
205 return m_depth;
206 }

References m_depth.

Referenced by PNS::LINE_PLACER::Move().

◆ doRemove()

void PNS::NODE::doRemove ( ITEM aItem)
private

Definition at line 738 of file pns_node.cpp.

739{
740 // case 1: removing an item that is stored in the root node from any branch:
741 // mark it as overridden, but do not remove
742 if( aItem->BelongsTo( m_root ) && !isRoot() )
743 m_override.insert( aItem );
744
745 // case 2: the item belongs to this branch or a parent, non-root branch,
746 // or the root itself and we are the root: remove from the index
747 else if( !aItem->BelongsTo( m_root ) || isRoot() )
748 m_index->Remove( aItem );
749
750 // the item belongs to this particular branch: un-reference it
751 if( aItem->BelongsTo( this ) )
752 {
753 aItem->SetOwner( nullptr );
754 m_root->m_garbageItems.insert( aItem );
755 }
756}
void Remove(ITEM *aItem)
Removes an item from the spatial index.
Definition: pns_index.cpp:46
std::unordered_set< ITEM * > m_garbageItems
Definition: pns_node.h:493

References PNS::ITEM::BelongsTo(), isRoot(), m_garbageItems, m_index, m_override, m_root, PNS::INDEX::Remove(), and PNS::ITEM::SetOwner().

Referenced by Remove().

◆ Dump()

void PNS::NODE::Dump ( bool  aLong = false)

Definition at line 1297 of file pns_node.cpp.

1298{
1299#if 0
1300 std::unordered_set<SEGMENT*> all_segs;
1302
1303 for( i = m_items.begin(); i != m_items.end(); i++ )
1304 {
1305 if( (*i)->GetKind() == ITEM::SEGMENT_T )
1306 all_segs.insert( static_cast<SEGMENT*>( *i ) );
1307 }
1308
1309 if( !isRoot() )
1310 {
1311 for( i = m_root->m_items.begin(); i != m_root->m_items.end(); i++ )
1312 {
1313 if( (*i)->GetKind() == ITEM::SEGMENT_T && !overrides( *i ) )
1314 all_segs.insert( static_cast<SEGMENT*>(*i) );
1315 }
1316 }
1317
1318 JOINT_MAP::iterator j;
1319
1320 if( aLong )
1321 {
1322 for( j = m_joints.begin(); j != m_joints.end(); ++j )
1323 {
1324 wxLogTrace( wxT( "PNS" ), wxT( "joint : %s, links : %d\n" ),
1325 j->second.GetPos().Format().c_str(), j->second.LinkCount() );
1326 JOINT::LINKED_ITEMS::const_iterator k;
1327
1328 for( k = j->second.GetLinkList().begin(); k != j->second.GetLinkList().end(); ++k )
1329 {
1330 const ITEM* m_item = *k;
1331
1332 switch( m_item->GetKind() )
1333 {
1334 case ITEM::SEGMENT_T:
1335 {
1336 const SEGMENT* seg = static_cast<const SEGMENT*>( m_item );
1337 wxLogTrace( wxT( "PNS" ), wxT( " -> seg %s %s\n" ),
1338 seg->GetSeg().A.Format().c_str(),
1339 seg->GetSeg().B.Format().c_str() );
1340 break;
1341 }
1342
1343 default:
1344 break;
1345 }
1346 }
1347 }
1348 }
1349
1350 int lines_count = 0;
1351
1352 while( !all_segs.empty() )
1353 {
1354 SEGMENT* s = *all_segs.begin();
1355 LINE* l = AssembleLine( s );
1356
1357 LINE::LinkedSegments* seg_refs = l->GetLinkedSegments();
1358
1359 if( aLong )
1360 {
1361 wxLogTrace( wxT( "PNS" ), wxT( "Line: %s, net %d " ),
1362 l->GetLine().Format().c_str(), l->GetNet() );
1363 }
1364
1365 for( std::vector<SEGMENT*>::iterator j = seg_refs->begin(); j != seg_refs->end(); ++j )
1366 {
1367 wxLogTrace( wxT( "PNS" ), wxT( "%s " ), (*j)->GetSeg().A.Format().c_str() );
1368
1369 if( j + 1 == seg_refs->end() )
1370 wxLogTrace( wxT( "PNS" ), wxT( "%s\n" ), (*j)->GetSeg().B.Format().c_str() );
1371
1372 all_segs.erase( *j );
1373 }
1374
1375 lines_count++;
1376 }
1377
1378 wxLogTrace( wxT( "PNS" ), wxT( "Local joints: %d, lines : %d \n" ),
1379 m_joints.size(), lines_count );
1380#endif
1381}
const LINE AssembleLine(LINKED_ITEM *aSeg, int *aOriginSegmentIndex=nullptr, bool aStopAtLockedJoints=false, bool aFollowLockedSegments=false)
Follow the joint map to assemble a line connecting two non-trivial joints starting from segment aSeg.
Definition: pns_node.cpp:983

References AssembleLine(), isRoot(), m_joints, m_root, and PNS::ITEM::SEGMENT_T.

◆ FindItemByParent()

ITEM * PNS::NODE::FindItemByParent ( const BOARD_ITEM aParent)

Definition at line 1619 of file pns_node.cpp.

1620{
1621 if( aParent->IsConnected() )
1622 {
1623 const BOARD_CONNECTED_ITEM* cItem = static_cast<const BOARD_CONNECTED_ITEM*>( aParent );
1624
1626
1627 if( l_cur )
1628 {
1629 for( ITEM* item : *l_cur )
1630 {
1631 if( item->Parent() == aParent )
1632 return item;
1633 }
1634 }
1635 }
1636
1637 return nullptr;
1638}
A base class derived from BOARD_ITEM for items that can be connected and have a net,...
virtual bool IsConnected() const
Returns information if the object is derived from BOARD_CONNECTED_ITEM.
Definition: board_item.h:108

References PNS::INDEX::GetItemsForNet(), BOARD_CONNECTED_ITEM::GetNetCode(), BOARD_ITEM::IsConnected(), and m_index.

Referenced by ROUTER_TOOL::InlineBreakTrack(), and ROUTER_TOOL::InlineDrag().

◆ FindJoint() [1/2]

JOINT * PNS::NODE::FindJoint ( const VECTOR2I aPos,
const ITEM aItem 
)
inline

Search for a joint at a given position, linked to given item.

Returns
the joint, if found, otherwise empty. Find all lines between a pair of joints. Used by the loop removal procedure.

Definition at line 370 of file pns_node.h.

References FindJoint(), PNS::ITEM::Layers(), PNS::ITEM::Net(), and LAYER_RANGE::Start().

◆ FindJoint() [2/2]

JOINT * PNS::NODE::FindJoint ( const VECTOR2I aPos,
int  aLayer,
int  aNet 
)

Search for a joint at a given position, layer and belonging to given net.

Returns
the joint, if found, otherwise empty.

Definition at line 1181 of file pns_node.cpp.

1182{
1183 JOINT::HASH_TAG tag;
1184
1185 tag.net = aNet;
1186 tag.pos = aPos;
1187
1188 JOINT_MAP::iterator f = m_joints.find( tag ), end = m_joints.end();
1189
1190 if( f == end && !isRoot() )
1191 {
1192 end = m_root->m_joints.end();
1193 f = m_root->m_joints.find( tag ); // m_root->FindJoint(aPos, aLayer, aNet);
1194 }
1195
1196 if( f == end )
1197 return nullptr;
1198
1199 while( f != end )
1200 {
1201 if( f->second.Layers().Overlaps( aLayer ) )
1202 return &f->second;
1203
1204 ++f;
1205 }
1206
1207 return nullptr;
1208}

References isRoot(), m_joints, m_root, PNS::JOINT::HASH_TAG::net, and PNS::JOINT::HASH_TAG::pos.

Referenced by PNS::TOPOLOGY::AssembleTrivialPath(), PNS::DRAGGER::checkVirtualVia(), PNS::TOPOLOGY::ConnectedJoints(), FindJoint(), FindLineEnds(), PNS::OPTIMIZER::findPadOrVia(), findRedundantArc(), findRedundantSegment(), PNS::findViaByHandle(), PNS::DRAGGER::findViaFanoutByHandle(), PNS::SHOVE::fixupViaCollisions(), followLine(), PNS::TOPOLOGY::followTrivialPath(), PNS::getDanglingAnchor(), PNS::SHOVE::onCollidingSolid(), PNS::SHOVE::onReverseCollidingVia(), PNS::SHOVE::pushOrShoveVia(), removeSolidIndex(), removeViaIndex(), PNS::SHOVE::shoveLineToHullSet(), PNS::LINE_PLACER::simplifyNewLine(), PNS::LINE_PLACER::SplitAdjacentSegments(), and PNS::COMPONENT_DRAGGER::Start().

◆ FindLineEnds()

void PNS::NODE::FindLineEnds ( const LINE aLine,
JOINT aA,
JOINT aB 
)

Destroy all child nodes. Applicable only to the root node.

Definition at line 1069 of file pns_node.cpp.

1070{
1071 aA = *FindJoint( aLine.CPoint( 0 ), &aLine );
1072 aB = *FindJoint( aLine.CPoint( -1 ), &aLine );
1073}
JOINT * FindJoint(const VECTOR2I &aPos, int aLayer, int aNet)
Search for a joint at a given position, layer and belonging to given net.
Definition: pns_node.cpp:1181

References PNS::LINE::CPoint(), and FindJoint().

Referenced by FindLinesBetweenJoints(), PNS::MEANDER_PLACER_BASE::GetTotalPadToDieLength(), and PNS::LINE_PLACER::removeLoops().

◆ FindLinesBetweenJoints()

int PNS::NODE::FindLinesBetweenJoints ( const JOINT aA,
const JOINT aB,
std::vector< LINE > &  aLines 
)

Find the joints corresponding to the ends of line aLine.

Definition at line 1076 of file pns_node.cpp.

1077{
1078 for( ITEM* item : aA.LinkList() )
1079 {
1080 if( item->Kind() == ITEM::SEGMENT_T || item->Kind() == ITEM::ARC_T )
1081 {
1082 LINKED_ITEM* li = static_cast<LINKED_ITEM*>( item );
1083 LINE line = AssembleLine( li );
1084
1085 if( !line.Layers().Overlaps( aB.Layers() ) )
1086 continue;
1087
1088 JOINT j_start, j_end;
1089
1090 FindLineEnds( line, j_start, j_end );
1091
1092 int id_start = line.CLine().Find( aA.Pos() );
1093 int id_end = line.CLine().Find( aB.Pos() );
1094
1095 if( id_end < id_start )
1096 std::swap( id_end, id_start );
1097
1098 if( id_start >= 0 && id_end >= 0 )
1099 {
1100 line.ClipVertexRange( id_start, id_end );
1101 aLines.push_back( line );
1102 }
1103 }
1104 }
1105
1106 return 0;
1107}
void FindLineEnds(const LINE &aLine, JOINT &aA, JOINT &aB)
Destroy all child nodes. Applicable only to the root node.
Definition: pns_node.cpp:1069

References PNS::ITEM::ARC_T, AssembleLine(), PNS::LINE::CLine(), PNS::LINE::ClipVertexRange(), SHAPE_LINE_CHAIN::Find(), FindLineEnds(), PNS::ITEM::Layers(), PNS::JOINT::LinkList(), LAYER_RANGE::Overlaps(), PNS::JOINT::Pos(), and PNS::ITEM::SEGMENT_T.

Referenced by PNS::LINE_PLACER::removeLoops().

◆ findRedundantArc() [1/2]

ARC * PNS::NODE::findRedundantArc ( ARC aSeg)
private

Scan the joint map, forming a line starting from segment (current).

Definition at line 1575 of file pns_node.cpp.

1576{
1577 return findRedundantArc( aArc->Anchor( 0 ), aArc->Anchor( 1 ), aArc->Layers(), aArc->Net() );
1578}

References PNS::ARC::Anchor(), findRedundantArc(), PNS::ITEM::Layers(), and PNS::ITEM::Net().

◆ findRedundantArc() [2/2]

ARC * PNS::NODE::findRedundantArc ( const VECTOR2I A,
const VECTOR2I B,
const LAYER_RANGE lr,
int  aNet 
)
private

Definition at line 1546 of file pns_node.cpp.

1548{
1549 JOINT* jtStart = FindJoint( A, lr.Start(), aNet );
1550
1551 if( !jtStart )
1552 return nullptr;
1553
1554 for( ITEM* item : jtStart->LinkList() )
1555 {
1556 if( item->OfKind( ITEM::ARC_T ) )
1557 {
1558 ARC* seg2 = static_cast<ARC*>( item );
1559
1560 const VECTOR2I a2( seg2->Anchor( 0 ) );
1561 const VECTOR2I b2( seg2->Anchor( 1 ) );
1562
1563 if( seg2->Layers().Start() == lr.Start()
1564 && ( ( A == a2 && B == b2 ) || ( A == b2 && B == a2 ) ) )
1565 {
1566 return seg2;
1567 }
1568 }
1569 }
1570
1571 return nullptr;
1572}
int Start() const
Definition: pns_layerset.h:82

References PNS::ARC::Anchor(), PNS::ITEM::ARC_T, FindJoint(), PNS::ITEM::Layers(), PNS::JOINT::LinkList(), and LAYER_RANGE::Start().

Referenced by Add(), and findRedundantArc().

◆ findRedundantSegment() [1/2]

SEGMENT * PNS::NODE::findRedundantSegment ( const VECTOR2I A,
const VECTOR2I B,
const LAYER_RANGE lr,
int  aNet 
)
private

Definition at line 1511 of file pns_node.cpp.

1513{
1514 JOINT* jtStart = FindJoint( A, lr.Start(), aNet );
1515
1516 if( !jtStart )
1517 return nullptr;
1518
1519 for( ITEM* item : jtStart->LinkList() )
1520 {
1521 if( item->OfKind( ITEM::SEGMENT_T ) )
1522 {
1523 SEGMENT* seg2 = (SEGMENT*)item;
1524
1525 const VECTOR2I a2( seg2->Seg().A );
1526 const VECTOR2I b2( seg2->Seg().B );
1527
1528 if( seg2->Layers().Start() == lr.Start()
1529 && ( ( A == a2 && B == b2 ) || ( A == b2 && B == a2 ) ) )
1530 {
1531 return seg2;
1532 }
1533 }
1534 }
1535
1536 return nullptr;
1537}

References SEG::A, SEG::B, FindJoint(), PNS::ITEM::Layers(), PNS::JOINT::LinkList(), PNS::SEGMENT::Seg(), PNS::ITEM::SEGMENT_T, and LAYER_RANGE::Start().

Referenced by Add(), and findRedundantSegment().

◆ findRedundantSegment() [2/2]

SEGMENT * PNS::NODE::findRedundantSegment ( SEGMENT aSeg)
private

Definition at line 1540 of file pns_node.cpp.

1541{
1542 return findRedundantSegment( aSeg->Seg().A, aSeg->Seg().B, aSeg->Layers(), aSeg->Net() );
1543}

References SEG::A, SEG::B, findRedundantSegment(), PNS::ITEM::Layers(), PNS::ITEM::Net(), and PNS::SEGMENT::Seg().

◆ FixupVirtualVias()

void PNS::NODE::FixupVirtualVias ( )

Definition at line 1110 of file pns_node.cpp.

1111{
1112 SEGMENT* locked_seg = nullptr;
1113 std::vector<VVIA*> vvias;
1114
1115 for( auto& jointPair : m_joints )
1116 {
1117 JOINT joint = jointPair.second;
1118
1119 if( joint.Layers().IsMultilayer() )
1120 continue;
1121
1122 int n_seg = 0, n_solid = 0, n_vias = 0;
1123 int prev_w = -1;
1124 int max_w = -1;
1125 bool is_width_change = false;
1126 bool is_locked = false;
1127
1128 for( const auto& lnk : joint.LinkList() )
1129 {
1130 if( lnk.item->OfKind( ITEM::VIA_T ) )
1131 {
1132 n_vias++;
1133 }
1134 else if( lnk.item->OfKind( ITEM::SOLID_T ) )
1135 {
1136 n_solid++;
1137 }
1138 else if( const auto t = dyn_cast<PNS::SEGMENT*>( lnk.item ) )
1139 {
1140 int w = t->Width();
1141
1142 if( prev_w >= 0 && w != prev_w )
1143 {
1144 is_width_change = true;
1145 }
1146
1147 max_w = std::max( w, max_w );
1148 prev_w = w;
1149
1150 is_locked = t->IsLocked();
1151 locked_seg = t;
1152 }
1153 }
1154
1155 if( ( is_width_change || n_seg >= 3 || is_locked ) && n_solid == 0 && n_vias == 0 )
1156 {
1157 // fixme: the hull margin here is an ugly temporary workaround. The real fix
1158 // is to use octagons for via force propagation.
1159 vvias.push_back( new VVIA( joint.Pos(), joint.Layers().Start(),
1160 max_w + 2 * PNS_HULL_MARGIN, joint.Net() ) );
1161 }
1162
1163 if( is_locked )
1164 {
1165 const VECTOR2I& secondPos = ( locked_seg->Seg().A == joint.Pos() ) ?
1166 locked_seg->Seg().B :
1167 locked_seg->Seg().A;
1168
1169 vvias.push_back( new VVIA( secondPos, joint.Layers().Start(),
1170 max_w + 2 * PNS_HULL_MARGIN, joint.Net() ) );
1171 }
1172 }
1173
1174 for( auto vvia : vvias )
1175 {
1176 Add( ItemCast<VIA>( std::move( std::unique_ptr<VVIA>( vvia ) ) ) );
1177 }
1178}
#define PNS_HULL_MARGIN
Definition: pns_line.h:44

References SEG::A, Add(), SEG::B, LAYER_RANGE::IsMultilayer(), PNS::ITEM::Layers(), PNS::JOINT::LinkList(), m_joints, PNS::JOINT::Net(), PNS_HULL_MARGIN, PNS::JOINT::Pos(), PNS::SEGMENT::Seg(), PNS::ITEM::SOLID_T, LAYER_RANGE::Start(), and PNS::ITEM::VIA_T.

◆ followLine()

void PNS::NODE::followLine ( LINKED_ITEM aCurrent,
bool  aScanDirection,
int &  aPos,
int  aLimit,
VECTOR2I aCorners,
LINKED_ITEM **  aSegments,
bool *  aArcReversed,
bool &  aGuardHit,
bool  aStopAtLockedJoints,
bool  aFollowLockedSegments 
)
private

Definition at line 934 of file pns_node.cpp.

937{
938 bool prevReversed = false;
939
940 const VECTOR2I guard = aCurrent->Anchor( aScanDirection );
941
942 for( int count = 0 ; ; ++count )
943 {
944 const VECTOR2I p = aCurrent->Anchor( aScanDirection ^ prevReversed );
945 const JOINT* jt = FindJoint( p, aCurrent );
946
947 assert( jt );
948
949 aCorners[aPos] = jt->Pos();
950 aSegments[aPos] = aCurrent;
951 aArcReversed[aPos] = false;
952
953 if( aCurrent->Kind() == ITEM::ARC_T )
954 {
955 if( ( aScanDirection && jt->Pos() == aCurrent->Anchor( 0 ) )
956 || ( !aScanDirection && jt->Pos() == aCurrent->Anchor( 1 ) ) )
957 aArcReversed[aPos] = true;
958 }
959
960 aPos += ( aScanDirection ? 1 : -1 );
961
962 if( count && guard == p )
963 {
964 if( aPos >= 0 && aPos < aLimit )
965 aSegments[aPos] = nullptr;
966
967 aGuardHit = true;
968 break;
969 }
970
971 bool locked = aStopAtLockedJoints ? jt->IsLocked() : false;
972
973 if( locked || !jt->IsLineCorner( aFollowLockedSegments ) || aPos < 0 || aPos == aLimit )
974 break;
975
976 aCurrent = jt->NextSegment( aCurrent, aFollowLockedSegments );
977
978 prevReversed = ( aCurrent && jt->Pos() == aCurrent->Anchor( aScanDirection ) );
979 }
980}

References PNS::ITEM::Anchor(), PNS::ITEM::ARC_T, FindJoint(), PNS::JOINT::IsLineCorner(), PNS::JOINT::IsLocked(), PNS::ITEM::Kind(), locked, PNS::JOINT::NextSegment(), and PNS::JOINT::Pos().

Referenced by AssembleLine().

◆ GetClearance()

int PNS::NODE::GetClearance ( const ITEM aA,
const ITEM aB,
bool  aUseClearanceEpsilon = true 
) const

Definition at line 103 of file pns_node.cpp.

104{
105 if( !m_ruleResolver )
106 return 100000;
107
108 if( aA->IsVirtual() || aB->IsVirtual() )
109 return 0;
110
111 return m_ruleResolver->Clearance( aA, aB, aUseClearanceEpsilon );
112}
virtual int Clearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true)=0

References PNS::RULE_RESOLVER::Clearance(), PNS::ITEM::IsVirtual(), and m_ruleResolver.

Referenced by PNS::ITEM::collideSimple(), PNS::SHOVE::getClearance(), PNS::ROUTER::markViolations(), NearestObstacle(), PNS::DIFF_PAIR_PLACER::propagateDpHeadForces(), PNS::VIA::PushoutForce(), and PNS::LINE_PLACER::rhMarkObstacles().

◆ GetCollisionQueryScope()

COLLISION_QUERY_SCOPE PNS::NODE::GetCollisionQueryScope ( ) const
inline

Definition at line 415 of file pns_node.h.

416 {
418 }

References m_collisionQueryScope.

Referenced by PNS::ITEM::collideSimple(), and PNS::VIA::PushoutForce().

◆ GetHoleClearance()

int PNS::NODE::GetHoleClearance ( const ITEM aA,
const ITEM aB,
bool  aUseClearanceEpsilon = true 
) const

Definition at line 115 of file pns_node.cpp.

116{
117 if( !m_ruleResolver )
118 return 0;
119
120 if( aA->IsVirtual() || aB->IsVirtual() )
121 return 0;
122
123 return m_ruleResolver->HoleClearance( aA, aB, aUseClearanceEpsilon );
124}
virtual int HoleClearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true)=0

References PNS::RULE_RESOLVER::HoleClearance(), PNS::ITEM::IsVirtual(), and m_ruleResolver.

Referenced by PNS::ITEM::collideSimple(), PNS::SHOVE::getHoleClearance(), PNS::ROUTER::markViolations(), NearestObstacle(), and PNS::VIA::PushoutForce().

◆ GetHoleToHoleClearance()

int PNS::NODE::GetHoleToHoleClearance ( const ITEM aA,
const ITEM aB,
bool  aUseClearanceEpsilon = true 
) const

Return the pre-set worst case clearance between any pair of items.

Definition at line 127 of file pns_node.cpp.

128{
129 if( !m_ruleResolver )
130 return 0;
131
132 if( aA->IsVirtual() || aB->IsVirtual() )
133 return 0;
134
135 return m_ruleResolver->HoleToHoleClearance( aA, aB, aUseClearanceEpsilon );
136}
virtual int HoleToHoleClearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true)=0

References PNS::RULE_RESOLVER::HoleToHoleClearance(), PNS::ITEM::IsVirtual(), and m_ruleResolver.

Referenced by PNS::ITEM::collideSimple(), NearestObstacle(), and PNS::VIA::PushoutForce().

◆ GetMaxClearance()

int PNS::NODE::GetMaxClearance ( ) const
inline

Set the worst-case clearance between any pair of items.

Definition at line 174 of file pns_node.h.

References m_maxClearance.

◆ GetParent()

NODE * PNS::NODE::GetParent ( void  ) const
inline

Check if this branch contains an updated version of the m_item from the root branch.

Definition at line 397 of file pns_node.h.

References m_parent.

◆ GetRuleResolver()

RULE_RESOLVER * PNS::NODE::GetRuleResolver ( ) const
inline

Return the number of joints.

Definition at line 191 of file pns_node.h.

References m_ruleResolver.

Referenced by PNS::TOPOLOGY::AssembleDiffPair(), and PNS::DIFF_PAIR_PLACER::FindDpPrimitivePair().

◆ GetUpdatedItems()

void PNS::NODE::GetUpdatedItems ( ITEM_VECTOR aRemoved,
ITEM_VECTOR aAdded 
)

Return the list of items removed and added in this branch with respect to the root branch.

Parameters
aRemovedremoved items.
aAddedadded items.

Definition at line 1384 of file pns_node.cpp.

1385{
1386 if( isRoot() )
1387 return;
1388
1389 if( m_override.size() )
1390 aRemoved.reserve( m_override.size() );
1391
1392 if( m_index->Size() )
1393 aAdded.reserve( m_index->Size() );
1394
1395 for( ITEM* item : m_override )
1396 aRemoved.push_back( item );
1397
1398 for( INDEX::ITEM_SET::iterator i = m_index->begin(); i != m_index->end(); ++i )
1399 aAdded.push_back( *i );
1400}
int Size() const
Returns number of items stored in the index.
Definition: pns_index.h:115
ITEM_SET::iterator end()
Definition: pns_index.h:118
ITEM_SET::iterator begin()
Definition: pns_index.h:117

References PNS::INDEX::begin(), PNS::INDEX::end(), isRoot(), m_index, m_override, and PNS::INDEX::Size().

Referenced by PNS::ROUTER::CommitRouting(), PNS::LINE_PLACER::FixRoute(), PNS_LOG_PLAYER::ReplayLog(), PNS::LINE_PLACER::simplifyNewLine(), and PNS::ROUTER::updateView().

◆ HasChildren()

bool PNS::NODE::HasChildren ( ) const
inline

Definition at line 392 of file pns_node.h.

393 {
394 return !m_children.empty();
395 }

References m_children.

◆ HitTest()

const ITEM_SET PNS::NODE::HitTest ( const VECTOR2I aPoint) const

Find all items that contain the point aPoint.

Parameters
aPointthe point.
Returns
the items.

Definition at line 535 of file pns_node.cpp.

536{
537 ITEM_SET items;
538
539 // fixme: we treat a point as an infinitely small circle - this is inefficient.
540 SHAPE_CIRCLE s( aPoint, 0 );
541 HIT_VISITOR visitor( items, aPoint );
542 visitor.SetWorld( this, nullptr );
543
544 m_index->Query( &s, m_maxClearance, visitor );
545
546 if( !isRoot() ) // fixme: could be made cleaner
547 {
548 ITEM_SET items_root;
549 visitor.SetWorld( m_root, nullptr );
550 HIT_VISITOR visitor_root( items_root, aPoint );
551 m_root->m_index->Query( &s, m_maxClearance, visitor_root );
552
553 for( ITEM* item : items_root.Items() )
554 {
555 if( !Overrides( item ) )
556 items.Add( item );
557 }
558 }
559
560 return items;
561}
int Query(const ITEM *aItem, int aMinDistance, Visitor &aVisitor) const
Searches items in the index that are in proximity of aItem.
Definition: pns_index.h:141

References PNS::ITEM_SET::Add(), isRoot(), PNS::ITEM_SET::Items(), m_index, m_maxClearance, m_root, Overrides(), PNS::INDEX::Query(), and PNS::OBSTACLE_VISITOR::SetWorld().

◆ isRoot()

bool PNS::NODE::isRoot ( ) const
inlineprivate

Definition at line 453 of file pns_node.h.

454 {
455 return m_parent == nullptr;
456 }

References m_parent.

Referenced by AllItemsInNet(), Branch(), Commit(), doRemove(), Dump(), FindJoint(), GetUpdatedItems(), HitTest(), QueryColliding(), QueryJoints(), releaseGarbage(), touchJoint(), and unlinkParent().

◆ JointCount()

int PNS::NODE::JointCount ( ) const
inline

Return the number of nodes in the inheritance chain (wrs to the root node).

Definition at line 197 of file pns_node.h.

References m_joints.

Referenced by PNS::SHOVE::shoveMainLoop().

◆ KillChildren()

◆ linkJoint()

void PNS::NODE::linkJoint ( const VECTOR2I aPos,
const LAYER_RANGE aLayers,
int  aNet,
ITEM aWhere 
)
private

Unlink an item from a joint.

Definition at line 1280 of file pns_node.cpp.

1281{
1282 JOINT& jt = touchJoint( aPos, aLayers, aNet );
1283
1284 jt.Link( aWhere );
1285}
JOINT & touchJoint(const VECTOR2I &aPos, const LAYER_RANGE &aLayers, int aNet)
Touch a joint and links it to an m_item.
Definition: pns_node.cpp:1218

References PNS::JOINT::Link(), and touchJoint().

Referenced by addArc(), addSegment(), addSolid(), addVia(), and rebuildJoint().

◆ LockJoint()

void PNS::NODE::LockJoint ( const VECTOR2I aPos,
const ITEM aItem,
bool  aLock 
)

Definition at line 1211 of file pns_node.cpp.

1212{
1213 JOINT& jt = touchJoint( aPos, aItem->Layers(), aItem->Net() );
1214 jt.Lock( aLock );
1215}

References PNS::ITEM::Layers(), PNS::JOINT::Lock(), PNS::ITEM::Net(), and touchJoint().

Referenced by PNS::SHOVE::ShoveLines().

◆ NearestObstacle()

NODE::OPT_OBSTACLE PNS::NODE::NearestObstacle ( const LINE aLine,
int  aKindMask = ITEM::ANY_T,
const std::set< ITEM * > *  aRestrictedSet = nullptr,
bool  aUseClearanceEpsilon = true 
)

Follow the line in search of an obstacle that is nearest to the starting to the line's starting point.

Parameters
aLinethe item to find collisions with
aKindMaskmask of obstacle types to take into account
aRestrictedSetis an optional set of items that should be considered as obstacles
aUseClearanceEpsilondetermines if the epsilon is subtracted from the hull size
Returns
the obstacle, if found, otherwise empty.

Definition at line 301 of file pns_node.cpp.

304{
305 OBSTACLES obstacleList;
306 obstacleList.reserve( 100 );
307
308 for( int i = 0; i < aLine->CLine().SegmentCount(); i++ )
309 {
310 const SEGMENT s( *aLine, aLine->CLine().CSegment( i ) );
311 QueryColliding( &s, obstacleList, aKindMask );
312 }
313
314 if( aLine->EndsWithVia() )
315 QueryColliding( &aLine->Via(), obstacleList, aKindMask );
316
317 if( obstacleList.empty() )
318 return OPT_OBSTACLE();
319
320 OBSTACLE nearest;
321 nearest.m_item = nullptr;
322 nearest.m_distFirst = INT_MAX;
323
324 auto updateNearest =
325 [&]( const SHAPE_LINE_CHAIN::INTERSECTION& pt, ITEM* obstacle,
326 const SHAPE_LINE_CHAIN& hull, bool isHole )
327 {
328 int dist = aLine->CLine().PathLength( pt.p, pt.index_their );
329
330 if( dist < nearest.m_distFirst )
331 {
332 nearest.m_distFirst = dist;
333 nearest.m_ipFirst = pt.p;
334 nearest.m_item = obstacle;
335 nearest.m_hull = hull;
336
337 obstacle->Mark( isHole ? obstacle->Marker() | MK_HOLE
338 : obstacle->Marker() & ~MK_HOLE );
339 }
340 };
341
342 SHAPE_LINE_CHAIN obstacleHull;
343 DEBUG_DECORATOR* debugDecorator = ROUTER::GetInstance()->GetInterface()->GetDebugDecorator();
344 std::vector<SHAPE_LINE_CHAIN::INTERSECTION> intersectingPts;
345 int layer = aLine->Layer();
346
347
348 for( const OBSTACLE& obstacle : obstacleList )
349 {
350 if( aRestrictedSet && aRestrictedSet->find( obstacle.m_item ) == aRestrictedSet->end() )
351 continue;
352
353 int clearance =
354 GetClearance( obstacle.m_item, aLine, aUseClearanceEpsilon ) + aLine->Width() / 2;
355
356 obstacleHull = obstacle.m_item->Hull( clearance, 0, layer );
357 //debugDecorator->AddLine( obstacleHull, 2, 40000, "obstacle-hull-test" );
358 //debugDecorator->AddLine( aLine->CLine(), 5, 40000, "obstacle-test-line" );
359
360 intersectingPts.clear();
361 HullIntersection( obstacleHull, aLine->CLine(), intersectingPts );
362
363 for( const auto& ip : intersectingPts )
364 {
365 //debugDecorator->AddPoint( ip.p, ip.valid?3:6, 100000, (const char *) wxString::Format("obstacle-isect-point-%d" ).c_str() );
366 if( ip.valid )
367 updateNearest( ip, obstacle.m_item, obstacleHull, false );
368 }
369
370 if( aLine->EndsWithVia() )
371 {
372 const VIA& via = aLine->Via();
373 // Don't use via.Drill(); it doesn't include the plating thickness
374
375 int viaHoleRadius = static_cast<const SHAPE_CIRCLE*>( via.Hole() )->GetRadius();
376
377 int viaClearance = GetClearance( obstacle.m_item, &via, aUseClearanceEpsilon )
378 + via.Diameter() / 2;
379 int holeClearance =
380 GetHoleClearance( obstacle.m_item, &via, aUseClearanceEpsilon ) + viaHoleRadius;
381
382 if( holeClearance > viaClearance )
383 viaClearance = holeClearance;
384
385 obstacleHull = obstacle.m_item->Hull( viaClearance, 0, layer );
386 //debugDecorator->AddLine( obstacleHull, 3 );
387
388 intersectingPts.clear();
389 HullIntersection( obstacleHull, aLine->CLine(), intersectingPts );
390
391 // obstacleHull.Intersect( aLine->CLine(), intersectingPts, true );
392
393 for( const SHAPE_LINE_CHAIN::INTERSECTION& ip : intersectingPts )
394 updateNearest( ip, obstacle.m_item, obstacleHull, false );
395 }
396
398 || !ROUTER::GetInstance()->GetInterface()->IsFlashedOnLayer( obstacle.m_item,
399 layer ) )
400 && obstacle.m_item->Hole() )
401 {
402 clearance = GetHoleClearance( obstacle.m_item, aLine, aUseClearanceEpsilon );
403 int copperClearance = GetClearance( obstacle.m_item, aLine, aUseClearanceEpsilon );
404
405 clearance = std::max( clearance, copperClearance );
406
407 obstacleHull = obstacle.m_item->HoleHull( clearance, aLine->Width(), layer );
408
409 intersectingPts.clear();
410 HullIntersection( obstacleHull, aLine->CLine(), intersectingPts );
411
412 for( const SHAPE_LINE_CHAIN::INTERSECTION& ip : intersectingPts )
413 updateNearest( ip, obstacle.m_item, obstacleHull, true );
414
415 if( aLine->EndsWithVia() )
416 {
417 const VIA& via = aLine->Via();
418 // Don't use via.Drill(); it doesn't include the plating thickness
419 int viaHoleRadius = static_cast<const SHAPE_CIRCLE*>( via.Hole() )->GetRadius();
420
421 int viaClearance = GetClearance( obstacle.m_item, &via, aUseClearanceEpsilon )
422 + via.Diameter() / 2;
423 int holeClearance = GetHoleClearance( obstacle.m_item, &via, aUseClearanceEpsilon )
424 + viaHoleRadius;
425 int holeToHole =
426 GetHoleToHoleClearance( obstacle.m_item, &via, aUseClearanceEpsilon )
427 + viaHoleRadius;
428
429 if( holeClearance > viaClearance )
430 viaClearance = holeClearance;
431
432 if( holeToHole > viaClearance )
433 viaClearance = holeToHole;
434
435 obstacleHull = obstacle.m_item->Hull( viaClearance, 0, layer );
436 //debugDecorator->AddLine( obstacleHull, 5 );
437
438 intersectingPts.clear();
439 HullIntersection( obstacleHull, aLine->CLine(), intersectingPts );
440
441 for( const SHAPE_LINE_CHAIN::INTERSECTION& ip : intersectingPts )
442 updateNearest( ip, obstacle.m_item, obstacleHull, true );
443 }
444 }
445 }
446
447 if( nearest.m_distFirst == INT_MAX )
448 nearest.m_item = obstacleList[0].m_item;
449
450 return nearest;
451}
int GetClearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true) const
Definition: pns_node.cpp:103
int GetHoleToHoleClearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true) const
Return the pre-set worst case clearance between any pair of items.
Definition: pns_node.cpp:127
int GetHoleClearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true) const
Definition: pns_node.cpp:115
virtual DEBUG_DECORATOR * GetDebugDecorator()=0
ROUTER_IFACE * GetInterface() const
Definition: pns_router.h:208
static ROUTER * GetInstance()
Definition: pns_router.cpp:78
void HullIntersection(const SHAPE_LINE_CHAIN &hull, const SHAPE_LINE_CHAIN &line, SHAPE_LINE_CHAIN::INTERSECTIONS &ips)
Definition: pns_utils.cpp:379
@ MK_HOLE
Definition: pns_item.h:45
@ VIA
Normal via.
Definition: router_tool.cpp:76
Represent an intersection between two line segments.
VECTOR2I p
< Point of intersection between our and their.
int index_their
When true, the corner [index_our] of the 'our' line lies exactly on 'their' line.

References PNS::LINE::CLine(), CQS_ALL_RULES, SHAPE_LINE_CHAIN::CSegment(), PNS::LINE::EndsWithVia(), GetClearance(), PNS::ROUTER_IFACE::GetDebugDecorator(), GetHoleClearance(), GetHoleToHoleClearance(), PNS::ROUTER::GetInstance(), PNS::ROUTER::GetInterface(), PNS::HullIntersection(), SHAPE_LINE_CHAIN::INTERSECTION::index_their, PNS::ITEM::Layer(), m_collisionQueryScope, PNS::OBSTACLE::m_distFirst, PNS::OBSTACLE::m_hull, PNS::OBSTACLE::m_ipFirst, PNS::OBSTACLE::m_item, PNS::MK_HOLE, SHAPE_LINE_CHAIN::INTERSECTION::p, SHAPE_LINE_CHAIN::PathLength(), QueryColliding(), via, PNS::LINE::Via(), and PNS::LINE::Width().

Referenced by PNS::LINE::ClipToNearestObstacle(), PNS::WALKAROUND::nearestObstacle(), PNS::LINE_PLACER::rhMarkObstacles(), and PNS::SHOVE::shoveIteration().

◆ operator=()

NODE & PNS::NODE::operator= ( const NODE aB)
private

Try to find matching joint and creates a new one if not found.

◆ Overrides()

bool PNS::NODE::Overrides ( ITEM aItem) const
inline

Definition at line 403 of file pns_node.h.

404 {
405 return m_override.find( aItem ) != m_override.end();
406 }

References m_override.

Referenced by AllItemsInNet(), HitTest(), QueryJoints(), and PNS::OBSTACLE_VISITOR::visit().

◆ QueryColliding()

int PNS::NODE::QueryColliding ( const ITEM aItem,
NODE::OBSTACLES aObstacles,
int  aKindMask = ITEM::ANY_T,
int  aLimitCount = -1,
bool  aDifferentNetsOnly = true,
int  aOverrideClearance = -1 
)

Find items colliding (closer than clearance) with the item aItem.

Parameters
aItemitem to check collisions against
aObstaclesset of colliding objects found
aKindMaskmask of obstacle types to take into account
aLimitCountstop looking for collisions after finding this number of colliding items
Returns
number of obstacles found

By default, virtual items cannot collide

Definition at line 271 of file pns_node.cpp.

273{
275 if( aItem->IsVirtual() )
276 return 0;
277
278 DEFAULT_OBSTACLE_VISITOR visitor( aObstacles, aItem, aKindMask, aDifferentNetsOnly, aOverrideClearance );
279
280#ifdef DEBUG
281 assert( allocNodes.find( this ) != allocNodes.end() );
282#endif
283
284 visitor.SetCountLimit( aLimitCount );
285 visitor.SetWorld( this, nullptr );
286
287 // first, look for colliding items in the local index
288 m_index->Query( aItem, m_maxClearance, visitor );
289
290 // if we haven't found enough items, look in the root branch as well.
291 if( !isRoot() && ( visitor.m_matchCount < aLimitCount || aLimitCount < 0 ) )
292 {
293 visitor.SetWorld( m_root, this );
294 m_root->m_index->Query( aItem, m_maxClearance, visitor );
295 }
296
297 return aObstacles.size();
298}

References isRoot(), PNS::ITEM::IsVirtual(), m_index, PNS::NODE::DEFAULT_OBSTACLE_VISITOR::m_matchCount, m_maxClearance, m_root, PNS::INDEX::Query(), PNS::NODE::DEFAULT_OBSTACLE_VISITOR::SetCountLimit(), and PNS::OBSTACLE_VISITOR::SetWorld().

Referenced by PNS::TOPOLOGY::AssembleCluster(), CheckColliding(), PNS::ROUTER::markViolations(), and NearestObstacle().

◆ QueryEdgeExclusions()

bool PNS::NODE::QueryEdgeExclusions ( const VECTOR2I aPos) const

Definition at line 726 of file pns_node.cpp.

727{
728 for( const std::unique_ptr<SHAPE>& edgeExclusion : m_edgeExclusions )
729 {
730 if( edgeExclusion->Collide( aPos ) )
731 return true;
732 }
733
734 return false;
735}

References m_edgeExclusions.

Referenced by PNS::ITEM::collideSimple().

◆ QueryJoints()

int PNS::NODE::QueryJoints ( const BOX2I aBox,
std::vector< JOINT * > &  aJoints,
LAYER_RANGE  aLayerMask = LAYER_RANGE::All(),
int  aKindMask = ITEM::ANY_T 
)

Definition at line 1581 of file pns_node.cpp.

1583{
1584 int n = 0;
1585
1586 aJoints.clear();
1587
1588 for( JOINT_MAP::value_type& j : m_joints )
1589 {
1590 if( !j.second.Layers().Overlaps( aLayerMask ) )
1591 continue;
1592
1593 if( aBox.Contains( j.second.Pos() ) && j.second.LinkCount( aKindMask ) )
1594 {
1595 aJoints.push_back( &j.second );
1596 n++;
1597 }
1598 }
1599
1600 if( isRoot() )
1601 return n;
1602
1603 for( JOINT_MAP::value_type& j : m_root->m_joints )
1604 {
1605 if( !Overrides( &j.second ) && j.second.Layers().Overlaps( aLayerMask ) )
1606 {
1607 if( aBox.Contains( j.second.Pos() ) && j.second.LinkCount( aKindMask ) )
1608 {
1609 aJoints.push_back( &j.second );
1610 n++;
1611 }
1612 }
1613 }
1614
1615 return n;
1616}
bool Contains(const Vec &aPoint) const
Definition: box2.h:134

References BOX2< Vec >::Contains(), isRoot(), m_joints, m_root, and Overrides().

Referenced by PNS::KEEP_TOPOLOGY_CONSTRAINT::Check(), and PNS::COMPONENT_DRAGGER::Start().

◆ rebuildJoint()

void PNS::NODE::rebuildJoint ( JOINT aJoint,
ITEM aItem 
)
private

Definition at line 773 of file pns_node.cpp.

774{
775 // We have to split a single joint (associated with a via or a pad, binding together multiple
776 // layers) into multiple independent joints. As I'm a lazy bastard, I simply delete the
777 // via/solid and all its links and re-insert them.
778
779 JOINT::LINKED_ITEMS links( aJoint->LinkList() );
780 JOINT::HASH_TAG tag;
781 int net = aItem->Net();
782
783 tag.net = net;
784 tag.pos = aJoint->Pos();
785
786 bool split;
787
788 do
789 {
790 split = false;
791 auto range = m_joints.equal_range( tag );
792
793 if( range.first == m_joints.end() )
794 break;
795
796 // find and remove all joints containing the via to be removed
797
798 for( auto f = range.first; f != range.second; ++f )
799 {
800 if( aItem->LayersOverlap( &f->second ) )
801 {
802 m_joints.erase( f );
803 split = true;
804 break;
805 }
806 }
807 } while( split );
808
809 // and re-link them, using the former via's link list
810 for( ITEM* link : links )
811 {
812 if( link != aItem )
813 linkJoint( tag.pos, link->Layers(), net, link );
814 }
815}
ITEM_SET::ENTRIES LINKED_ITEMS
Joints are hashed by their position, layers and net.
Definition: pns_joint.h:45
static std::vector< std::string > split(const std::string &aStr, const std::string &aDelim)
Split the input string into a vector of output strings.
Definition: string_utils.h:295

References PNS::ITEM::LayersOverlap(), linkJoint(), PNS::JOINT::LinkList(), m_joints, PNS::ITEM::Net(), PNS::JOINT::HASH_TAG::net, PNS::JOINT::HASH_TAG::pos, PNS::JOINT::Pos(), and split().

Referenced by removeSolidIndex(), and removeViaIndex().

◆ releaseChildren()

void PNS::NODE::releaseChildren ( )
private

Definition at line 1403 of file pns_node.cpp.

1404{
1405 // copy the kids as the NODE destructor erases the item from the parent node.
1406 std::set<NODE*> kids = m_children;
1407
1408 for( NODE* node : kids )
1409 {
1410 node->releaseChildren();
1411 delete node;
1412 }
1413}

References m_children.

Referenced by Commit(), and KillChildren().

◆ releaseGarbage()

void PNS::NODE::releaseGarbage ( )
private

Definition at line 1416 of file pns_node.cpp.

1417{
1418 if( !isRoot() )
1419 return;
1420
1421 for( ITEM* item : m_garbageItems )
1422 {
1423 if( !item->BelongsTo( this ) )
1424 delete item;
1425 }
1426
1427 m_garbageItems.clear();
1428}

References isRoot(), and m_garbageItems.

Referenced by Commit(), and ~NODE().

◆ Remove() [1/6]

◆ Remove() [2/6]

void PNS::NODE::Remove ( ITEM aItem)

Definition at line 880 of file pns_node.cpp.

881{
882 switch( aItem->Kind() )
883 {
884 case ITEM::ARC_T:
885 Remove( static_cast<ARC*>( aItem ) );
886 break;
887
888 case ITEM::SOLID_T:
889 Remove( static_cast<SOLID*>( aItem ) );
890 break;
891
892 case ITEM::SEGMENT_T:
893 Remove( static_cast<SEGMENT*>( aItem ) );
894 break;
895
896 case ITEM::LINE_T:
897 {
898 LINE* l = static_cast<LINE*>( aItem );
899
900 for ( LINKED_ITEM* s : l->Links() )
901 Remove( s );
902
903 break;
904 }
905
906 case ITEM::VIA_T:
907 Remove( static_cast<VIA*>( aItem ) );
908 break;
909
910 default:
911 break;
912 }
913}

References PNS::ITEM::ARC_T, PNS::ITEM::Kind(), PNS::ITEM::LINE_T, PNS::LINK_HOLDER::Links(), Remove(), PNS::ITEM::SEGMENT_T, PNS::ITEM::SOLID_T, and PNS::ITEM::VIA_T.

◆ Remove() [3/6]

void PNS::NODE::Remove ( LINE aLine)

Removes a line from this branch.

Parameters
aLineitem to remove

Definition at line 916 of file pns_node.cpp.

917{
918 // LINE does not have a separate remover, as LINEs are never truly a member of the tree
919 std::vector<LINKED_ITEM*>& segRefs = aLine.Links();
920
921 for( LINKED_ITEM* li : segRefs )
922 {
923 if( li->OfKind( ITEM::SEGMENT_T ) )
924 Remove( static_cast<SEGMENT*>( li ) );
925 else if( li->OfKind( ITEM::ARC_T ) )
926 Remove( static_cast<ARC*>( li ) );
927 }
928
929 aLine.SetOwner( nullptr );
930 aLine.ClearLinks();
931}

References PNS::ITEM::ARC_T, PNS::LINK_HOLDER::ClearLinks(), PNS::LINK_HOLDER::Links(), Remove(), PNS::ITEM::SEGMENT_T, and PNS::ITEM::SetOwner().

◆ Remove() [4/6]

void PNS::NODE::Remove ( SEGMENT aSegment)

Definition at line 866 of file pns_node.cpp.

867{
868 removeSegmentIndex( aSegment );
869 doRemove( aSegment );
870}
void removeSegmentIndex(SEGMENT *aSeg)
Definition: pns_node.cpp:759

References doRemove(), and removeSegmentIndex().

◆ Remove() [5/6]

void PNS::NODE::Remove ( SOLID aSolid)

Definition at line 852 of file pns_node.cpp.

853{
854 removeSolidIndex( aSolid );
855 doRemove( aSolid );
856}
void removeSolidIndex(SOLID *aSeg)
Definition: pns_node.cpp:826

References doRemove(), and removeSolidIndex().

◆ Remove() [6/6]

void PNS::NODE::Remove ( VIA aVia)

Definition at line 859 of file pns_node.cpp.

860{
861 removeViaIndex( aVia );
862 doRemove( aVia );
863}
void removeViaIndex(VIA *aVia)
Definition: pns_node.cpp:818

References doRemove(), and removeViaIndex().

◆ removeArcIndex()

void PNS::NODE::removeArcIndex ( ARC aVia)
private

Definition at line 766 of file pns_node.cpp.

767{
768 unlinkJoint( aArc->Anchor( 0 ), aArc->Layers(), aArc->Net(), aArc );
769 unlinkJoint( aArc->Anchor( 1 ), aArc->Layers(), aArc->Net(), aArc );
770}
void unlinkJoint(const VECTOR2I &aPos, const LAYER_RANGE &aLayers, int aNet, ITEM *aWhere)
Helpers for adding/removing items.
Definition: pns_node.cpp:1288

References PNS::ARC::Anchor(), PNS::ITEM::Layers(), PNS::ITEM::Net(), and unlinkJoint().

Referenced by Remove().

◆ RemoveByMarker()

void PNS::NODE::RemoveByMarker ( int  aMarker)

Definition at line 1496 of file pns_node.cpp.

1497{
1498 std::vector<ITEM*> garbage;
1499
1500 for( ITEM* item : *m_index )
1501 {
1502 if( item->Marker() & aMarker )
1503 garbage.emplace_back( item );
1504 }
1505
1506 for( ITEM* item : garbage )
1507 Remove( item );
1508}

References m_index, and Remove().

Referenced by PNS::SHOVE::ShoveLines(), and PNS::SHOVE::ShoveMultiLines().

◆ removeSegmentIndex()

void PNS::NODE::removeSegmentIndex ( SEGMENT aSeg)
private

Definition at line 759 of file pns_node.cpp.

760{
761 unlinkJoint( aSeg->Seg().A, aSeg->Layers(), aSeg->Net(), aSeg );
762 unlinkJoint( aSeg->Seg().B, aSeg->Layers(), aSeg->Net(), aSeg );
763}

References SEG::A, SEG::B, PNS::ITEM::Layers(), PNS::ITEM::Net(), PNS::SEGMENT::Seg(), and unlinkJoint().

Referenced by Remove().

◆ removeSolidIndex()

void PNS::NODE::removeSolidIndex ( SOLID aSeg)
private

Definition at line 826 of file pns_node.cpp.

827{
828 if( !aSolid->IsRoutable() )
829 return;
830
831 // fixme: redundant code
832 JOINT* jt = FindJoint( aSolid->Pos(), aSolid->Layers().Start(), aSolid->Net() );
833 assert( jt );
834 rebuildJoint( jt, aSolid );
835}
void rebuildJoint(JOINT *aJoint, ITEM *aItem)
Definition: pns_node.cpp:773

References FindJoint(), PNS::ITEM::IsRoutable(), PNS::ITEM::Layers(), PNS::ITEM::Net(), PNS::SOLID::Pos(), rebuildJoint(), and LAYER_RANGE::Start().

Referenced by Remove().

◆ removeViaIndex()

void PNS::NODE::removeViaIndex ( VIA aVia)
private

Definition at line 818 of file pns_node.cpp.

819{
820 JOINT* jt = FindJoint( aVia->Pos(), aVia->Layers().Start(), aVia->Net() );
821 assert( jt );
822 rebuildJoint( jt, aVia );
823}

References FindJoint(), PNS::ITEM::Layers(), PNS::ITEM::Net(), PNS::VIA::Pos(), rebuildJoint(), and LAYER_RANGE::Start().

Referenced by Remove().

◆ Replace() [1/2]

void PNS::NODE::Replace ( ITEM aOldItem,
std::unique_ptr< ITEM aNewItem 
)

Replace an item with another one.

Parameters
aOldItemitem to be removed
aNewItemitem add instead

Definition at line 838 of file pns_node.cpp.

839{
840 Remove( aOldItem );
841 Add( std::move( aNewItem ) );
842}

References Add(), and Remove().

Referenced by PNS::SHOVE::replaceItems(), and PNS::SHOVE::replaceLine().

◆ Replace() [2/2]

void PNS::NODE::Replace ( LINE aOldLine,
LINE aNewLine 
)

Definition at line 845 of file pns_node.cpp.

846{
847 Remove( aOldLine );
848 Add( aNewLine );
849}

References Add(), and Remove().

◆ SetCollisionQueryScope()

void PNS::NODE::SetCollisionQueryScope ( COLLISION_QUERY_SCOPE  aScope)
inline

Definition at line 410 of file pns_node.h.

411 {
412 m_collisionQueryScope = aScope;
413 }

References m_collisionQueryScope.

◆ SetMaxClearance()

void PNS::NODE::SetMaxClearance ( int  aClearance)
inline

Assign a clearance resolution function object.

Definition at line 180 of file pns_node.h.

References m_maxClearance.

Referenced by PNS_KICAD_IFACE_BASE::SyncWorld().

◆ SetRuleResolver()

void PNS::NODE::SetRuleResolver ( RULE_RESOLVER aFunc)
inline

Definition at line 186 of file pns_node.h.

187 {
188 m_ruleResolver = aFunc;
189 }

References m_ruleResolver.

Referenced by PNS_KICAD_IFACE_BASE::SyncWorld().

◆ touchJoint()

JOINT & PNS::NODE::touchJoint ( const VECTOR2I aPos,
const LAYER_RANGE aLayers,
int  aNet 
)
private

Touch a joint and links it to an m_item.

Definition at line 1218 of file pns_node.cpp.

1219{
1220 JOINT::HASH_TAG tag;
1221
1222 tag.pos = aPos;
1223 tag.net = aNet;
1224
1225 // try to find the joint in this node.
1226 JOINT_MAP::iterator f = m_joints.find( tag );
1227
1228 std::pair<JOINT_MAP::iterator, JOINT_MAP::iterator> range;
1229
1230 // not found and we are not root? find in the root and copy results here.
1231 if( f == m_joints.end() && !isRoot() )
1232 {
1233 range = m_root->m_joints.equal_range( tag );
1234
1235 for( f = range.first; f != range.second; ++f )
1236 m_joints.insert( *f );
1237 }
1238
1239 // now insert and combine overlapping joints
1240 JOINT jt( aPos, aLayers, aNet );
1241
1242 bool merged;
1243
1244 do
1245 {
1246 merged = false;
1247 range = m_joints.equal_range( tag );
1248
1249 if( range.first == m_joints.end() )
1250 break;
1251
1252 for( f = range.first; f != range.second; ++f )
1253 {
1254 if( aLayers.Overlaps( f->second.Layers() ) )
1255 {
1256 jt.Merge( f->second );
1257 m_joints.erase( f );
1258 merged = true;
1259 break;
1260 }
1261 }
1262 }
1263 while( merged );
1264
1265 return m_joints.insert( TagJointPair( tag, jt ) )->second;
1266}
bool Overlaps(const LAYER_RANGE &aOther) const
Definition: pns_layerset.h:67
JOINT_MAP::value_type TagJointPair
Definition: pns_node.h:473

References isRoot(), m_joints, m_root, PNS::JOINT::Merge(), PNS::JOINT::HASH_TAG::net, LAYER_RANGE::Overlaps(), and PNS::JOINT::HASH_TAG::pos.

Referenced by linkJoint(), LockJoint(), and unlinkJoint().

◆ unlinkJoint()

void PNS::NODE::unlinkJoint ( const VECTOR2I aPos,
const LAYER_RANGE aLayers,
int  aNet,
ITEM aWhere 
)
private

Helpers for adding/removing items.

Definition at line 1288 of file pns_node.cpp.

1289{
1290 // fixme: remove dangling joints
1291 JOINT& jt = touchJoint( aPos, aLayers, aNet );
1292
1293 jt.Unlink( aWhere );
1294}

References touchJoint(), and PNS::JOINT::Unlink().

Referenced by removeArcIndex(), and removeSegmentIndex().

◆ unlinkParent()

void PNS::NODE::unlinkParent ( )
private

Definition at line 176 of file pns_node.cpp.

177{
178 if( isRoot() )
179 return;
180
181 m_parent->m_children.erase( this );
182}

References isRoot(), m_children, and m_parent.

Referenced by ~NODE().

Member Data Documentation

◆ m_children

std::set<NODE*> PNS::NODE::m_children
private

list of nodes branched from this one

Definition at line 480 of file pns_node.h.

Referenced by Branch(), HasChildren(), releaseChildren(), unlinkParent(), and ~NODE().

◆ m_collisionQueryScope

COLLISION_QUERY_SCOPE PNS::NODE::m_collisionQueryScope
private

◆ m_depth

int PNS::NODE::m_depth
private

depth of the node (number of parent nodes in the inheritance chain)

Definition at line 488 of file pns_node.h.

Referenced by Branch(), Depth(), and NODE().

◆ m_edgeExclusions

std::vector< std::unique_ptr<SHAPE> > PNS::NODE::m_edgeExclusions
private

Definition at line 491 of file pns_node.h.

Referenced by AddEdgeExclusion(), and QueryEdgeExclusions().

◆ m_garbageItems

std::unordered_set<ITEM*> PNS::NODE::m_garbageItems
private

Definition at line 493 of file pns_node.h.

Referenced by doRemove(), and releaseGarbage().

◆ m_index

INDEX* PNS::NODE::m_index
private

◆ m_joints

JOINT_MAP PNS::NODE::m_joints
private

hash table with the joints, linking the items.

Joints are hashed by their position, layer set and net.

Definition at line 475 of file pns_node.h.

Referenced by Branch(), Dump(), FindJoint(), FixupVirtualVias(), JointCount(), QueryJoints(), rebuildJoint(), touchJoint(), and ~NODE().

◆ m_maxClearance

int PNS::NODE::m_maxClearance
private

worst case item-item clearance

Definition at line 485 of file pns_node.h.

Referenced by Branch(), GetMaxClearance(), HitTest(), NODE(), QueryColliding(), and SetMaxClearance().

◆ m_override

std::unordered_set<ITEM*> PNS::NODE::m_override
private

hash of root's items that have been changed in this node

Definition at line 482 of file pns_node.h.

Referenced by Branch(), Commit(), doRemove(), GetUpdatedItems(), and Overrides().

◆ m_parent

NODE* PNS::NODE::m_parent
private

node this node was branched from

Definition at line 478 of file pns_node.h.

Referenced by Branch(), GetParent(), isRoot(), NODE(), and unlinkParent().

◆ m_root

NODE* PNS::NODE::m_root
private

root node of the whole hierarchy

Definition at line 479 of file pns_node.h.

Referenced by AllItemsInNet(), Branch(), doRemove(), Dump(), FindJoint(), HitTest(), NODE(), QueryColliding(), QueryJoints(), and touchJoint().

◆ m_ruleResolver

RULE_RESOLVER* PNS::NODE::m_ruleResolver
private

Design rules resolver.

Definition at line 486 of file pns_node.h.

Referenced by Branch(), GetClearance(), GetHoleClearance(), GetHoleToHoleClearance(), GetRuleResolver(), NODE(), and SetRuleResolver().


The documentation for this class was generated from the following files: