KiCad PCB EDA Suite
CN_VISITOR Class Reference

#include <connectivity_algo.h>

Public Member Functions

 CN_VISITOR (CN_ITEM *aItem)
 
bool operator() (CN_ITEM *aCandidate)
 

Protected Member Functions

void checkZoneItemConnection (CN_ZONE_LAYER *aZoneLayer, CN_ITEM *aItem)
 
void checkZoneZoneConnection (CN_ZONE_LAYER *aZoneLayerA, CN_ZONE_LAYER *aZoneLayerB)
 The item we are looking for connections to. More...
 

Protected Attributes

CN_ITEMm_item
 

Detailed Description

Definition at line 288 of file connectivity_algo.h.

Constructor & Destructor Documentation

◆ CN_VISITOR()

CN_VISITOR::CN_VISITOR ( CN_ITEM aItem)
inline

Definition at line 291 of file connectivity_algo.h.

291  :
292  m_item( aItem )
293  {}
CN_ITEM * m_item

Member Function Documentation

◆ checkZoneItemConnection()

void CN_VISITOR::checkZoneItemConnection ( CN_ZONE_LAYER aZoneLayer,
CN_ITEM aItem 
)
protected

Definition at line 646 of file connectivity_algo.cpp.

647 {
648  if( aZoneLayer->Net() != aItem->Net() && !aItem->CanChangeNet() )
649  return;
650 
651  if( !aZoneLayer->BBox().Intersects( aItem->BBox() ) )
652  return;
653 
654  int accuracy = 0;
655 
656  if( aItem->Parent()->Type() == PCB_VIA_T
657  || aItem->Parent()->Type() == PCB_TRACE_T
658  || aItem->Parent()->Type() == PCB_ARC_T )
659  {
660  accuracy = ( static_cast<PCB_TRACK*>( aItem->Parent() )->GetWidth() + 1 ) / 2;
661  }
662 
663  for( int i = 0; i < aItem->AnchorCount(); ++i )
664  {
665  if( aZoneLayer->ContainsPoint( aItem->GetAnchor( i ), accuracy ) )
666  {
667  aZoneLayer->Connect( aItem );
668  aItem->Connect( aZoneLayer );
669  return;
670  }
671  }
672 }
const BOX2I & BBox()
bool ContainsPoint(const VECTOR2I &p, int aAccuracy=0) const
class PCB_ARC, an arc track segment on a copper layer
Definition: typeinfo.h:97
BOARD_CONNECTED_ITEM * Parent() const
int Net() const
allow parallel connection threads
class PCB_TRACK, a track segment (segment on a copper layer)
Definition: typeinfo.h:95
virtual int AnchorCount() const
bool Intersects(const BOX2< Vec > &aRect) const
Definition: box2.h:217
virtual const VECTOR2I GetAnchor(int n) const
bool CanChangeNet() const
void Connect(CN_ITEM *b)
class PCB_VIA, a via (like a track segment on a copper layer)
Definition: typeinfo.h:96
const BOX2I & BBox()
KICAD_T Type() const
Returns the type of object.
Definition: eda_item.h:113

References CN_ITEM::AnchorCount(), CN_ITEM::BBox(), CN_ZONE_LAYER::BBox(), CN_ITEM::CanChangeNet(), CN_ITEM::Connect(), CN_ZONE_LAYER::ContainsPoint(), CN_ITEM::GetAnchor(), BOX2< Vec >::Intersects(), CN_ITEM::Net(), CN_ITEM::Parent(), PCB_ARC_T, PCB_TRACE_T, PCB_VIA_T, and EDA_ITEM::Type().

Referenced by operator()().

◆ checkZoneZoneConnection()

void CN_VISITOR::checkZoneZoneConnection ( CN_ZONE_LAYER aZoneLayerA,
CN_ZONE_LAYER aZoneLayerB 
)
protected

The item we are looking for connections to.

Definition at line 674 of file connectivity_algo.cpp.

675 {
676  const ZONE* zoneA = static_cast<const ZONE*>( aZoneLayerA->Parent() );
677  const ZONE* zoneB = static_cast<const ZONE*>( aZoneLayerB->Parent() );
678 
679  if( aZoneLayerA->Layer() != aZoneLayerB->Layer() )
680  return;
681 
682  if( aZoneLayerB->Net() != aZoneLayerA->Net() )
683  return; // we only test zones belonging to the same net
684 
685  const BOX2I& boxA = aZoneLayerA->BBox();
686  const BOX2I& boxB = aZoneLayerB->BBox();
687 
688  int radiusA = 0;
689  int radiusB = 0;
690 
691  if( zoneA->GetFilledPolysUseThickness() )
692  radiusA = ( zoneA->GetMinThickness() + 1 ) / 2;
693 
694  if( zoneB->GetFilledPolysUseThickness() )
695  radiusB = ( zoneB->GetMinThickness() + 1 ) / 2;
696 
697  PCB_LAYER_ID layer = static_cast<PCB_LAYER_ID>( aZoneLayerA->Layer() );
698 
699  const SHAPE_LINE_CHAIN& outline =
700  zoneA->GetFilledPolysList( layer ).COutline( aZoneLayerA->SubpolyIndex() );
701 
702  for( int i = 0; i < outline.PointCount(); i++ )
703  {
704  if( !boxB.Contains( outline.CPoint( i ) ) )
705  continue;
706 
707  if( aZoneLayerB->ContainsPoint( outline.CPoint( i ), radiusA ) )
708  {
709  aZoneLayerA->Connect( aZoneLayerB );
710  aZoneLayerB->Connect( aZoneLayerA );
711  return;
712  }
713  }
714 
715  const SHAPE_LINE_CHAIN& outline2 =
716  zoneB->GetFilledPolysList( layer ).COutline( aZoneLayerB->SubpolyIndex() );
717 
718  for( int i = 0; i < outline2.PointCount(); i++ )
719  {
720  if( !boxA.Contains( outline2.CPoint( i ) ) )
721  continue;
722 
723  if( aZoneLayerA->ContainsPoint( outline2.CPoint( i ), radiusB ) )
724  {
725  aZoneLayerA->Connect( aZoneLayerB );
726  aZoneLayerB->Connect( aZoneLayerA );
727  return;
728  }
729  }
730 }
const BOX2I & BBox()
bool ContainsPoint(const VECTOR2I &p, int aAccuracy=0) const
const SHAPE_POLY_SET & GetFilledPolysList(PCB_LAYER_ID aLayer) const
Definition: zone.h:635
BOARD_CONNECTED_ITEM * Parent() const
int PointCount() const
Return the number of points (vertices) in this line chain.
int Net() const
allow parallel connection threads
const VECTOR2I & CPoint(int aIndex) const
Return a reference to a given point in the line chain.
int GetMinThickness() const
Definition: zone.h:244
bool Contains(const Vec &aPoint) const
Definition: box2.h:134
Handle a list of polygons defining a copper zone.
Definition: zone.h:56
int SubpolyIndex() const
Represent a polyline (an zero-thickness chain of connected line segments).
PCB_LAYER_ID
A quick note on layer IDs:
Definition: layer_ids.h:64
const SHAPE_LINE_CHAIN & COutline(int aIndex) const
virtual int Layer() const
Return the item's layer, for single-layered items only.
void Connect(CN_ITEM *b)
bool GetFilledPolysUseThickness() const
Definition: zone.h:689

References CN_ZONE_LAYER::BBox(), CN_ITEM::Connect(), BOX2< Vec >::Contains(), CN_ZONE_LAYER::ContainsPoint(), SHAPE_POLY_SET::COutline(), SHAPE_LINE_CHAIN::CPoint(), ZONE::GetFilledPolysList(), ZONE::GetFilledPolysUseThickness(), ZONE::GetMinThickness(), CN_ITEM::Layer(), CN_ITEM::Net(), CN_ITEM::Parent(), SHAPE_LINE_CHAIN::PointCount(), and CN_ZONE_LAYER::SubpolyIndex().

Referenced by operator()().

◆ operator()()

bool CN_VISITOR::operator() ( CN_ITEM aCandidate)

Definition at line 733 of file connectivity_algo.cpp.

734 {
735  const BOARD_CONNECTED_ITEM* parentA = aCandidate->Parent();
736  const BOARD_CONNECTED_ITEM* parentB = m_item->Parent();
737 
738  if( !aCandidate->Valid() || !m_item->Valid() )
739  return true;
740 
741  if( parentA == parentB )
742  return true;
743 
744  if( !( parentA->GetLayerSet() & parentB->GetLayerSet() ).any() )
745  return true;
746 
747  // If both m_item and aCandidate are marked dirty, they will both be searched
748  // Since we are reciprocal in our connection, we arbitrarily pick one of the connections
749  // to conduct the expensive search
750  if( aCandidate->Dirty() && aCandidate < m_item )
751  return true;
752 
753  // We should handle zone-zone connection separately
754  if ( parentA->Type() == PCB_ZONE_T && parentB->Type() == PCB_ZONE_T )
755  {
756  checkZoneZoneConnection( static_cast<CN_ZONE_LAYER*>( m_item ),
757  static_cast<CN_ZONE_LAYER*>( aCandidate ) );
758  return true;
759  }
760 
761  if( parentA->Type() == PCB_ZONE_T )
762  {
763  checkZoneItemConnection( static_cast<CN_ZONE_LAYER*>( aCandidate ), m_item );
764  return true;
765  }
766 
767  if( parentB->Type() == PCB_ZONE_T )
768  {
769  checkZoneItemConnection( static_cast<CN_ZONE_LAYER*>( m_item ), aCandidate );
770  return true;
771  }
772 
773  int accuracyA = 0;
774  int accuracyB = 0;
775 
776  if( parentA->Type() == PCB_VIA_T
777  || parentA->Type() == PCB_TRACE_T
778  || parentA->Type() == PCB_ARC_T)
779  accuracyA = ( static_cast<const PCB_TRACK*>( parentA )->GetWidth() + 1 ) / 2;
780 
781  if( parentB->Type() == PCB_VIA_T
782  || parentB->Type() == PCB_TRACE_T
783  || parentB->Type() == PCB_ARC_T )
784  accuracyB = ( static_cast<const PCB_TRACK*>( parentB )->GetWidth() + 1 ) / 2;
785 
786  // Items do not necessarily have reciprocity as we only check for anchors
787  // therefore, we check HitTest both directions A->B & B->A
788  for( int i = 0; i < aCandidate->AnchorCount(); ++i )
789  {
790  if( parentB->HitTest( wxPoint( aCandidate->GetAnchor( i ) ), accuracyA ) )
791  {
792  m_item->Connect( aCandidate );
793  aCandidate->Connect( m_item );
794  return true;
795  }
796  }
797 
798  for( int i = 0; i < m_item->AnchorCount(); ++i )
799  {
800  if( parentA->HitTest( wxPoint( m_item->GetAnchor( i ) ), accuracyB ) )
801  {
802  m_item->Connect( aCandidate );
803  aCandidate->Connect( m_item );
804  return true;
805  }
806  }
807 
808  return true;
809 };
void checkZoneItemConnection(CN_ZONE_LAYER *aZoneLayer, CN_ITEM *aItem)
class PCB_ARC, an arc track segment on a copper layer
Definition: typeinfo.h:97
bool Dirty() const
BOARD_CONNECTED_ITEM * Parent() const
A base class derived from BOARD_ITEM for items that can be connected and have a net,...
class PCB_TRACK, a track segment (segment on a copper layer)
Definition: typeinfo.h:95
virtual int AnchorCount() const
virtual bool HitTest(const wxPoint &aPosition, int aAccuracy=0) const
Test if aPosition is contained within or on the bounding box of an item.
Definition: eda_item.h:225
void checkZoneZoneConnection(CN_ZONE_LAYER *aZoneLayerA, CN_ZONE_LAYER *aZoneLayerB)
The item we are looking for connections to.
class ZONE, a copper pour area
Definition: typeinfo.h:105
virtual const VECTOR2I GetAnchor(int n) const
void Connect(CN_ITEM *b)
class PCB_VIA, a via (like a track segment on a copper layer)
Definition: typeinfo.h:96
CN_ITEM * m_item
virtual LSET GetLayerSet() const
Return a std::bitset of all layers on which the item physically resides.
Definition: board_item.h:176
bool Valid() const
KICAD_T Type() const
Returns the type of object.
Definition: eda_item.h:113

References CN_ITEM::AnchorCount(), checkZoneItemConnection(), checkZoneZoneConnection(), CN_ITEM::Connect(), CN_ITEM::Dirty(), CN_ITEM::GetAnchor(), BOARD_ITEM::GetLayerSet(), EDA_ITEM::HitTest(), m_item, CN_ITEM::Parent(), PCB_ARC_T, PCB_TRACE_T, PCB_VIA_T, PCB_ZONE_T, EDA_ITEM::Type(), and CN_ITEM::Valid().

Member Data Documentation

◆ m_item

CN_ITEM* CN_VISITOR::m_item
protected

Definition at line 303 of file connectivity_algo.h.

Referenced by operator()().


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