96 m_world = std::make_unique<NODE>( );
135 ret.
Add( obstacle.m_item,
false );
146 return m_placer->CurrentNode()->HitTest( aP );
159 if( aStartItems.
Empty() )
175 m_dragger = std::make_unique<COMPONENT_DRAGGER>(
this );
186 m_dragger = std::make_unique<DRAGGER>(
this );
203 if(
m_dragger->Start( aP, aStartItems ) )
218 if(
Settings().AllowDRCViolations() )
231 wxString failureReason;
236 if( item->Parent() && item->Parent()->GetLayer() ==
Edge_Cuts )
239 if( !item->Layers().Overlaps( aLayer ) )
242 if( item->IsRoutable() )
244 failureReason = wxEmptyString;
251 switch( parent->
Type() )
258 failureReason =
_(
"Cannot start routing from a non-plated hole." );
265 ZONE* zone =
static_cast<ZONE*
>( parent );
274 failureReason =
_(
"Rule area disallows tracks." );
283 failureReason =
_(
"Cannot start routing from a text item." );
288 failureReason =
_(
"Cannot start routing from a graphic." );
296 if( !failureReason.IsEmpty() )
309 dummyStartSeg.
Append( startPoint );
310 dummyStartSeg.
Append( startPoint,
true );
312 dummyStartLine.
SetShape( dummyStartSeg );
314 dummyStartLine.
SetNet( aStartItem ? aStartItem->
Net() : 0 );
319 ITEM_SET dummyStartSet( &dummyStartLine );
324 for(
ITEM* item : highlightedItems )
335 SetFailureReason(
_(
"Cannot start a differential pair in the middle of nowhere." ) );
351 LINE dummyStartLineA;
352 LINE dummyStartLineB;
360 dummyStartLineA.
SetShape( dummyStartSegA );
365 dummyStartLineB.
SetShape( dummyStartSegB );
376 dummyStartSet.
Add( dummyStartLineA );
377 dummyStartSet.
Add( dummyStartLineB );
380 for(
ITEM* item : highlightedItems )
413 m_placer = std::make_unique<LINE_PLACER>(
this );
417 m_placer = std::make_unique<DIFF_PAIR_PLACER>(
this );
421 m_placer = std::make_unique<MEANDER_PLACER>(
this );
425 m_placer = std::make_unique<DP_MEANDER_PLACER>(
this );
429 m_placer = std::make_unique<MEANDER_SKEW_PLACER>(
this );
441 if(
m_placer->Start( aP, aStartItem ) )
491 if( placer ==
nullptr )
519 aOtherEndLayers = it->
Layers();
532 if( placer ==
nullptr )
552 Move( otherEnd, ¤t );
554 }
while(
Placer()->CurrentEnd() != moveResultPoint && triesLeft );
559 return FixRoute( otherEnd, ¤t,
false );
570 if( placer ==
nullptr )
586 int nextLayer = otherEndLayers.
Overlaps( currentLayer ) ? currentLayer : otherEndLayers.
Start();
592 Move( currentEnd, ¤t );
613 [&](
ITEM* currentItem,
ITEM* itemToMark )
615 std::unique_ptr<ITEM> tmp( itemToMark->Clone() );
618 bool removeOriginal =
true;
619 bool holeOnly = ( ( itemToMark->Marker() &
MK_HOLE )
625 clearance = aNode->
GetClearance( currentItem, itemToMark );
628 tmp->SetLayer( currentItem->
Layer() );
634 SOLID* solid =
static_cast<SOLID*
>( tmp.get() );
641 removeOriginal =
false;
645 if( itemToMark->IsCompoundShapePrimitive() )
649 removeOriginal =
false;
656 aRemoved.push_back( itemToMark );
667 LINE* l =
static_cast<LINE*
>( item );
684 if( draggedItems.
Contains( obs.m_item ) )
687 obs.m_item->Mark( obs.m_item->Marker() |
MK_VIOLATION );
688 updateItem( item, obs.m_item );
693 LINE* line =
static_cast<LINE*
>( item );
716 for(
ITEM* item : added )
723 for(
ITEM* item : removed )
744 bool ret =
m_placer->Move( aP, aEndItem );
752 const LINE* l =
static_cast<const LINE*
>( item );
763 if( holeClearance +
via.Drill() / 2 > viaClearance +
via.Diameter() / 2 )
764 viaClearance = holeClearance +
via.Drill() / 2 -
via.Diameter() / 2;
779 std::vector<PNS::ITEM*>& aHeads )
781 NODE *node =
nullptr;
786 node =
m_placer->CurrentNode(
true );
802 for(
auto item : current.
CItems() )
804 aHeads.push_back( item.item->Clone() );
820 for(
ITEM* item : removed )
822 bool is_changed =
false;
828 for( NODE::ITEM_VECTOR::iterator added_it = added.begin();
829 added_it != added.end(); ++added_it )
831 if( ( *added_it )->Parent() && ( *added_it )->Parent() == item->Parent() )
833 changed.push_back( *added_it );
834 added.erase( added_it );
841 if( !is_changed && !item->IsVirtual() )
845 for(
ITEM* item : added )
847 if( !item->IsVirtual() )
853 for(
ITEM* item : changed )
855 if( !item->IsVirtual() )
876 rv =
m_placer->FixRoute( aP, aEndItem, aForceFinish );
917 std::vector<int> nets;
957 return m_placer->SetLayer( aLayer );
967 bool toggle = !
m_placer->IsPlacingVia();
985 return std::vector<int>();
1021 case DIRECTION_45::CORNER_MODE::MITERED_45: mode = DIRECTION_45::CORNER_MODE::ROUNDED_45;
break;
1022 case DIRECTION_45::CORNER_MODE::ROUNDED_45: mode = DIRECTION_45::CORNER_MODE::MITERED_90;
break;
1023 case DIRECTION_45::CORNER_MODE::MITERED_90: mode = DIRECTION_45::CORNER_MODE::ROUNDED_90;
break;
1024 case DIRECTION_45::CORNER_MODE::ROUNDED_90: mode = DIRECTION_45::CORNER_MODE::MITERED_45;
break;
A base class for any item which can be embedded within the BOARD container class, and therefore insta...
KICAD_T Type() const
Returns the type of object.
Represent a contiguous set of PCB layers.
bool IsMultilayer() const
bool Overlaps(const LAYER_RANGE &aOther) const
static bool FindDpPrimitivePair(NODE *aWorld, const VECTOR2I &aP, ITEM *aItem, DP_PRIMITIVE_PAIR &aPair, wxString *aErrorMsg=nullptr)
Store starting/ending primitives (pads, vias or segments) for a differential pair.
const VECTOR2I & AnchorN() const
const VECTOR2I & AnchorP() const
virtual const ITEM_SET Traces()=0
Function Traces()
int Count(int aKindMask=-1) const
void Add(const LINE &aLine)
bool Contains(ITEM *aItem) const
const ENTRIES & CItems() const
Base class for PNS router board items.
virtual int Layer() const
void SetLayer(int aLayer)
const LAYER_RANGE & Layers() const
virtual VECTOR2I Anchor(int n) const
A 2D point on a given set of layers and belonging to a certain net, that links together a number of b...
Single track placement algorithm.
const LINE Trace() const
Return the complete routed line.
const std::vector< int > CurrentNets() const override
Return the net code of currently routed track.
NODE * CurrentNode(bool aLoopsRemoved=false) const override
Return the most recent world state.
bool SplitAdjacentSegments(NODE *aNode, ITEM *aSeg, const VECTOR2I &aP)
Check if point aP lies on segment aSeg.
int CurrentLayer() const override
Return the layer of currently routed track.
const VECTOR2I & CurrentEnd() const override
Return the current end of the line being placed.
const VECTOR2I & CurrentStart() const override
Return the current start of the line being placed.
Represents a track on a PCB, connecting two non-trivial joints (that is, vias, pads,...
ITEM * GetBlockingObstacle() const
void SetShape(const SHAPE_LINE_CHAIN &aLine)
Return the shape of the line.
void SetWidth(int aWidth)
Return line width.
void Log(EVENT_TYPE evt, const VECTOR2I &pos=VECTOR2I(), const ITEM *item=nullptr, const SIZES_SETTINGS *sizes=nullptr)
Keep the router "world" - i.e.
std::vector< ITEM * > ITEM_VECTOR
int GetClearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true) const
@ CQS_IGNORE_HOLE_CLEARANCE
check everything except hole2hole / hole2copper
@ CQS_ALL_RULES
check all rules
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.
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.
std::vector< OBSTACLE > OBSTACLES
int GetHoleClearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true) const
JOINT * FindJoint(const VECTOR2I &aPos, int aLayer, int aNet)
Search for a joint at a given position, layer and belonging to given net.
virtual const VECTOR2I & CurrentEnd() const =0
Function CurrentEnd()
virtual void RemoveItem(ITEM *aItem)=0
virtual void UpdateItem(ITEM *aItem)=0
virtual void UpdateNet(int aNetCode)=0
virtual DEBUG_DECORATOR * GetDebugDecorator()=0
virtual void HideItem(ITEM *aItem)=0
virtual void AddItem(ITEM *aItem)=0
virtual void EraseView()=0
virtual void SyncWorld(NODE *aNode)=0
virtual void DisplayItem(const ITEM *aItem, int aClearance, bool aEdit=false, bool aIsHeadTrace=false)=0
virtual bool IsFlashedOnLayer(const PNS::ITEM *aItem, int aLayer) const =0
void updateView(NODE *aNode, ITEM_SET &aCurrent, bool aDragging=false)
void SetMode(ROUTER_MODE aMode)
bool moveDragging(const VECTOR2I &aP, ITEM *aItem)
bool SwitchLayer(int layer)
void ClearViewDecorations()
PLACEMENT_ALGO * Placer()
void UpdateSizes(const SIZES_SETTINGS &aSizes)
Applies stored settings.
void SetFailureReason(const wxString &aReason)
bool getNearestRatnestAnchor(VECTOR2I &aOtherEnd, LAYER_RANGE &aOtherEndLayers)
const std::vector< int > GetCurrentNets() const
bool m_forceMarkObstaclesMode
std::unique_ptr< DRAG_ALGO > m_dragger
void SetInterface(ROUTER_IFACE *aIface)
void markViolations(NODE *aNode, ITEM_SET &aCurrent, NODE::ITEM_VECTOR &aRemoved)
std::unique_ptr< PLACEMENT_ALGO > m_placer
bool isStartingPointRoutable(const VECTOR2I &aWhere, ITEM *aItem, int aLayer)
bool IsPlacingVia() const
RULE_RESOLVER * GetRuleResolver() const
const ITEM_SET QueryHoverItems(const VECTOR2I &aP, bool aUseClearance=false)
ROUTING_SETTINGS & Settings()
bool FixRoute(const VECTOR2I &aP, ITEM *aItem, bool aForceFinish=false)
bool movePlacing(const VECTOR2I &aP, ITEM *aItem)
bool RoutingInProgress() const
static ROUTER * GetInstance()
void BreakSegment(ITEM *aItem, const VECTOR2I &aP)
void SetOrthoMode(bool aEnable)
bool StartDragging(const VECTOR2I &aP, ITEM *aItem, int aDragMode=DM_ANY)
bool StartRouting(const VECTOR2I &aP, ITEM *aItem, int aLayer)
int GetCurrentLayer() const
void GetUpdatedItems(std::vector< PNS::ITEM * > &aRemoved, std::vector< PNS::ITEM * > &aAdded, std::vector< PNS::ITEM * > &aHeads)
std::unique_ptr< NODE > m_world
void ToggleViaPlacement()
ROUTING_SETTINGS * m_settings
bool Move(const VECTOR2I &aP, ITEM *aItem)
void SetCornerMode(DIRECTION_45::CORNER_MODE aMode)
DIRECTION_45::CORNER_MODE GetCornerMode() const
virtual void ClearCacheForItem(const ITEM *aItem)
virtual int Clearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true)=0
virtual void ClearCaches()
virtual int HoleClearance(const ITEM *aA, const ITEM *aB, bool aUseClearanceEpsilon=true)=0
int DiffPairWidth() const
const SHAPE * Hole() const override
void SetShape(SHAPE *shape)
bool NearestUnconnectedAnchorPoint(const LINE *aTrack, VECTOR2I &aPoint, LAYER_RANGE &aLayers)
ITEM * NearestUnconnectedItem(JOINT *aStart, int *aAnchor=nullptr, int aKindMask=ITEM::ANY_T)
Represent a polyline containing arcs as well as line segments: A chain of connected line and/or arc s...
void Append(int aX, int aY, bool aAllowDuplication=false)
Append a new point at the end of the line chain.
virtual SHAPE * Clone() const
Return a dynamically allocated copy of the shape.
Handle a list of polygons defining a copper zone.
wxString GetZoneName() const
static bool empty(const wxTextEntryBase *aCtrl)
Push and Shove diff pair dimensions (gap) settings dialog.
@ RM_MarkObstacles
Ignore collisions, mark obstacles.
static ROUTER * theRouter
@ PNS_MODE_ROUTE_DIFF_PAIR
@ PNS_MODE_TUNE_DIFF_PAIR
@ PNS_MODE_TUNE_DIFF_PAIR_SKEW
@ NPTH
like PAD_PTH, but not plated
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, const CPTREE &aTree)
Output a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
Hold an object colliding with another object, along with some useful data about the collision.
@ PCB_SHAPE_T
class PCB_SHAPE, a segment not on copper layers
@ PCB_FP_SHAPE_T
class FP_SHAPE, a footprint edge
@ PCB_FP_TEXTBOX_T
class FP_TEXTBOX, wrapped text in a footprint
@ PCB_TEXTBOX_T
class PCB_TEXTBOX, wrapped text on a layer
@ PCB_ZONE_T
class ZONE, a copper pour area
@ PCB_TEXT_T
class PCB_TEXT, text on a layer
@ PCB_FP_ZONE_T
class ZONE, managed by a footprint
@ PCB_PAD_T
class PAD, a pad in a footprint
@ PCB_FP_TEXT_T
class FP_TEXT, text in a footprint