KiCad PCB EDA Suite
connectivity_data.cpp
Go to the documentation of this file.
1 /*
2  * This program source code file is part of KICAD, a free EDA CAD application.
3  *
4  * Copyright (C) 2017 CERN
5  * Copyright (C) 2018-2020 KiCad Developers, see AUTHORS.txt for contributors.
6  * @author Tomasz Wlostowski <tomasz.wlostowski@cern.ch>
7  *
8  * This program is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License
10  * as published by the Free Software Foundation; either version 2
11  * of the License, or (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, you may find one here:
20  * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
21  * or you may search the http://www.gnu.org website for the version 2 license,
22  * or you may write to the Free Software Foundation, Inc.,
23  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
24  */
25 
26 #ifdef PROFILE
27 #include <profile.h>
28 #endif
29 
30 #include <thread>
31 #include <algorithm>
32 #include <future>
33 
37 
38 #include <ratsnest/ratsnest_data.h>
39 
41 {
42  m_connAlgo.reset( new CN_CONNECTIVITY_ALGO );
43  m_progressReporter = nullptr;
44  m_fromToCache.reset( new FROM_TO_CACHE );
45 }
46 
47 
48 CONNECTIVITY_DATA::CONNECTIVITY_DATA( const std::vector<BOARD_ITEM*>& aItems, bool aSkipRatsnest )
49  : m_skipRatsnest( aSkipRatsnest )
50 {
51  Build( aItems );
52  m_progressReporter = nullptr;
53  m_fromToCache.reset( new FROM_TO_CACHE );
54 }
55 
56 
58 {
59  Clear();
60 }
61 
62 
64 {
65  m_connAlgo->Add( aItem );
66  return true;
67 }
68 
69 
71 {
72  m_connAlgo->Remove( aItem );
73  return true;
74 }
75 
76 
78 {
79  m_connAlgo->Remove( aItem );
80  m_connAlgo->Add( aItem );
81  return true;
82 }
83 
84 
86 {
87  m_connAlgo.reset( new CN_CONNECTIVITY_ALGO );
88  m_connAlgo->Build( aBoard, aReporter );
89 
90  m_netclassMap.clear();
91 
92  for( NETINFO_ITEM* net : aBoard->GetNetInfo() )
93  if( net->GetNetClass()->GetName() != NETCLASS::Default )
94  m_netclassMap[ net->GetNetCode() ] = net->GetNetClass()->GetName();
95 
97 }
98 
99 
100 void CONNECTIVITY_DATA::Build( const std::vector<BOARD_ITEM*>& aItems )
101 {
102  m_connAlgo.reset( new CN_CONNECTIVITY_ALGO );
103  m_connAlgo->Build( aItems );
104 
106 }
107 
108 
109 void CONNECTIVITY_DATA::Move( const VECTOR2I& aDelta )
110 {
111  m_connAlgo->ForEachAnchor( [&aDelta]( CN_ANCHOR& anchor )
112  {
113  anchor.Move( aDelta );
114  } );
115 }
116 
117 
119 {
120  #ifdef PROFILE
121  PROF_COUNTER rnUpdate( "update-ratsnest" );
122  #endif
123  std::vector<RN_NET*> dirty_nets;
124 
125  // Start with net 1 as net 0 is reserved for not-connected
126  // Nets without nodes are also ignored
127  std::copy_if( m_nets.begin() + 1, m_nets.end(), std::back_inserter( dirty_nets ),
128  [] ( RN_NET* aNet ) { return aNet->IsDirty() && aNet->GetNodeCount() > 0; } );
129 
130  // We don't want to spin up a new thread for fewer than 8 nets (overhead costs)
131  size_t parallelThreadCount = std::min<size_t>( std::thread::hardware_concurrency(),
132  ( dirty_nets.size() + 7 ) / 8 );
133 
134  std::atomic<size_t> nextNet( 0 );
135  std::vector<std::future<size_t>> returns( parallelThreadCount );
136 
137  auto update_lambda = [&nextNet, &dirty_nets]() -> size_t
138  {
139  for( size_t i = nextNet++; i < dirty_nets.size(); i = nextNet++ )
140  dirty_nets[i]->Update();
141 
142  return 1;
143  };
144 
145  if( parallelThreadCount == 1 )
146  update_lambda();
147  else
148  {
149  for( size_t ii = 0; ii < parallelThreadCount; ++ii )
150  returns[ii] = std::async( std::launch::async, update_lambda );
151 
152  // Finalize the ratsnest threads
153  for( size_t ii = 0; ii < parallelThreadCount; ++ii )
154  returns[ii].wait();
155  }
156 
157  #ifdef PROFILE
158  rnUpdate.Show();
159  #endif /* PROFILE */
160 }
161 
162 
163 void CONNECTIVITY_DATA::addRatsnestCluster( const std::shared_ptr<CN_CLUSTER>& aCluster )
164 {
165  auto rnNet = m_nets[ aCluster->OriginNet() ];
166 
167  rnNet->AddCluster( aCluster );
168 }
169 
170 
172 {
173  m_connAlgo->PropagateNets( aCommit );
174 
175  int lastNet = m_connAlgo->NetCount();
176 
177  if( lastNet >= (int) m_nets.size() )
178  {
179  unsigned int prevSize = m_nets.size();
180  m_nets.resize( lastNet + 1 );
181 
182  for( unsigned int i = prevSize; i < m_nets.size(); i++ )
183  m_nets[i] = new RN_NET;
184  }
185 
186  auto clusters = m_connAlgo->GetClusters();
187 
188  int dirtyNets = 0;
189 
190  for( int net = 0; net < lastNet; net++ )
191  {
192  if( m_connAlgo->IsNetDirty( net ) )
193  {
194  m_nets[net]->Clear();
195  dirtyNets++;
196  }
197  }
198 
199  for( const auto& c : clusters )
200  {
201  int net = c->OriginNet();
202 
203  // Don't add intentionally-kept zone islands to the ratsnest
204  if( c->IsOrphaned() && c->Size() == 1 )
205  {
206  if( dynamic_cast<CN_ZONE_LAYER*>( *c->begin() ) )
207  continue;
208  }
209 
210  if( m_connAlgo->IsNetDirty( net ) )
211  {
212  addRatsnestCluster( c );
213  }
214  }
215 
216  m_connAlgo->ClearDirtyFlags();
217 
218  if( !m_skipRatsnest )
219  updateRatsnest();
220 }
221 
222 
223 void CONNECTIVITY_DATA::BlockRatsnestItems( const std::vector<BOARD_ITEM*>& aItems )
224 {
225  std::vector<BOARD_CONNECTED_ITEM*> citems;
226 
227  for( auto item : aItems )
228  {
229  if( item->Type() == PCB_FOOTPRINT_T )
230  {
231  for( PAD* pad : static_cast<FOOTPRINT*>(item)->Pads() )
232  citems.push_back( pad );
233  }
234  else
235  {
236  if( auto citem = dynamic_cast<BOARD_CONNECTED_ITEM*>( item ) )
237  citems.push_back( citem );
238  }
239  }
240 
241  for( const auto& item : citems )
242  {
243  if ( m_connAlgo->ItemExists( item ) )
244  {
245  auto& entry = m_connAlgo->ItemEntry( item );
246 
247  for( const auto& cnItem : entry.GetItems() )
248  {
249  for( auto anchor : cnItem->Anchors() )
250  anchor->SetNoLine( true );
251  }
252  }
253  }
254 }
255 
256 
258 {
259  return m_connAlgo->NetCount();
260 }
261 
262 
263 void CONNECTIVITY_DATA::FindIsolatedCopperIslands( ZONE* aZone, std::vector<int>& aIslands )
264 {
265  // TODO(JE) ZONES
266 #if 0
267  m_connAlgo->FindIsolatedCopperIslands( aZone, aIslands );
268 #endif
269 }
270 
271 void CONNECTIVITY_DATA::FindIsolatedCopperIslands( std::vector<CN_ZONE_ISOLATED_ISLAND_LIST>& aZones )
272 {
273  m_connAlgo->FindIsolatedCopperIslands( aZones );
274 }
275 
276 
277 void CONNECTIVITY_DATA::ComputeDynamicRatsnest( const std::vector<BOARD_ITEM*>& aItems,
278  const CONNECTIVITY_DATA* aDynamicData )
279 {
280  if( !aDynamicData )
281  return;
282 
283  m_dynamicRatsnest.clear();
284 
285  // This gets connections between the stationary board and the
286  // moving selection
287  for( unsigned int nc = 1; nc < aDynamicData->m_nets.size(); nc++ )
288  {
289  auto dynNet = aDynamicData->m_nets[nc];
290 
291  if( dynNet->GetNodeCount() != 0 )
292  {
293  auto ourNet = m_nets[nc];
294  CN_ANCHOR_PTR nodeA, nodeB;
295 
296  if( ourNet->NearestBicoloredPair( *dynNet, nodeA, nodeB ) )
297  {
298  RN_DYNAMIC_LINE l;
299  l.a = nodeA->Pos();
300  l.b = nodeB->Pos();
301  l.netCode = nc;
302 
303  m_dynamicRatsnest.push_back( l );
304  }
305  }
306  }
307 
308  // This gets the ratsnest for internal connections in the moving set
309  const auto& edges = GetRatsnestForItems( aItems );
310 
311  for( const auto& edge : edges )
312  {
313  const auto& nodeA = edge.GetSourceNode();
314  const auto& nodeB = edge.GetTargetNode();
315  RN_DYNAMIC_LINE l;
316 
317  // Use the parents' positions
318  l.a = nodeA->Parent()->GetPosition();
319  l.b = nodeB->Parent()->GetPosition();
320  l.netCode = 0;
321  m_dynamicRatsnest.push_back( l );
322  }
323 }
324 
325 
327 {
328  m_connAlgo->ForEachAnchor( []( CN_ANCHOR& anchor )
329  {
330  anchor.SetNoLine( false );
331  } );
333 }
334 
335 
337 {
338  m_dynamicRatsnest.clear();
339 }
340 
341 
343 {
344  m_connAlgo->PropagateNets();
345 }
346 
348  std::vector<KICAD_T> aTypes ) const
349 {
350  CN_CONNECTIVITY_ALGO::ITEM_MAP_ENTRY &entry = m_connAlgo->ItemEntry( aItem );
351 
352  auto matchType = [&]( KICAD_T aItemType )
353  {
354  if( aTypes.empty() )
355  return true;
356 
357  return std::count( aTypes.begin(), aTypes.end(), aItemType ) > 0;
358  };
359 
360  for( CN_ITEM* citem : entry.GetItems() )
361  {
362  for( CN_ITEM* connected : citem->ConnectedItems() )
363  {
364  if( connected->Valid()
365  && connected->Layers().Overlaps( aLayer )
366  && connected->Net() == aItem->GetNetCode()
367  && matchType( connected->Parent()->Type() ) )
368  {
369  return true;
370  }
371  }
372  }
373 
374  return false;
375 }
376 
377 
379 {
380  unsigned int unconnected = 0;
381 
382  for( auto net : m_nets )
383  {
384  if( !net )
385  continue;
386 
387  const auto& edges = net->GetUnconnected();
388 
389  if( edges.empty() )
390  continue;
391 
392  unconnected += edges.size();
393  }
394 
395  return unconnected;
396 }
397 
398 
400 {
401  for( auto net : m_nets )
402  delete net;
403 
404  m_nets.clear();
405 }
406 
407 
408 const std::vector<BOARD_CONNECTED_ITEM*> CONNECTIVITY_DATA::GetConnectedItems(
409  const BOARD_CONNECTED_ITEM* aItem,
410  const KICAD_T aTypes[],
411  bool aIgnoreNetcodes ) const
412 {
413  std::vector<BOARD_CONNECTED_ITEM*> rv;
414  const auto clusters = m_connAlgo->SearchClusters(
415  aIgnoreNetcodes ?
418  aIgnoreNetcodes ? -1 : aItem->GetNetCode() );
419 
420  for( auto cl : clusters )
421  {
422  if( cl->Contains( aItem ) )
423  {
424  for( const auto item : *cl )
425  {
426  if( item->Valid() )
427  rv.push_back( item->Parent() );
428  }
429  }
430  }
431 
432  return rv;
433 }
434 
435 
436 const std::vector<BOARD_CONNECTED_ITEM*> CONNECTIVITY_DATA::GetNetItems( int aNetCode,
437  const KICAD_T aTypes[] ) const
438 {
439  std::vector<BOARD_CONNECTED_ITEM*> items;
440  items.reserve( 32 );
441 
442  std::bitset<MAX_STRUCT_TYPE_ID> type_bits;
443 
444  for( unsigned int i = 0; aTypes[i] != EOT; ++i )
445  {
446  wxASSERT( aTypes[i] < MAX_STRUCT_TYPE_ID );
447  type_bits.set( aTypes[i] );
448  }
449 
450  m_connAlgo->ForEachItem( [&]( CN_ITEM& aItem ) {
451  if( aItem.Valid() && ( aItem.Net() == aNetCode ) && type_bits[aItem.Parent()->Type()] )
452  items.push_back( aItem.Parent() );
453  } );
454 
455  std::sort( items.begin(), items.end() );
456  items.erase( std::unique( items.begin(), items.end() ), items.end() );
457  return items;
458 }
459 
460 
461 bool CONNECTIVITY_DATA::CheckConnectivity( std::vector<CN_DISJOINT_NET_ENTRY>& aReport )
462 {
464 
465  for( auto net : m_nets )
466  {
467  if( net )
468  {
469  for( const auto& edge : net->GetEdges() )
470  {
472  ent.net = edge.GetSourceNode()->Parent()->GetNetCode();
473  ent.a = edge.GetSourceNode()->Parent();
474  ent.b = edge.GetTargetNode()->Parent();
475  ent.anchorA = edge.GetSourceNode()->Pos();
476  ent.anchorB = edge.GetTargetNode()->Pos();
477  aReport.push_back( ent );
478  }
479  }
480  }
481 
482  return aReport.empty();
483 }
484 
485 
486 const std::vector<TRACK*> CONNECTIVITY_DATA::GetConnectedTracks( const BOARD_CONNECTED_ITEM* aItem )
487 const
488 {
489  auto& entry = m_connAlgo->ItemEntry( aItem );
490 
491  std::set<TRACK*> tracks;
492  std::vector<TRACK*> rv;
493 
494  for( auto citem : entry.GetItems() )
495  {
496  for( auto connected : citem->ConnectedItems() )
497  {
498  if( connected->Valid() &&
499  ( connected->Parent()->Type() == PCB_TRACE_T ||
500  connected->Parent()->Type() == PCB_VIA_T ||
501  connected->Parent()->Type() == PCB_ARC_T ) )
502  tracks.insert( static_cast<TRACK*> ( connected->Parent() ) );
503  }
504  }
505 
506  std::copy( tracks.begin(), tracks.end(), std::back_inserter( rv ) );
507  return rv;
508 }
509 
510 
512  std::set<PAD*>* pads ) const
513 {
514  for( CN_ITEM* citem : m_connAlgo->ItemEntry( aItem ).GetItems() )
515  {
516  for( CN_ITEM* connected : citem->ConnectedItems() )
517  {
518  if( connected->Valid() && connected->Parent()->Type() == PCB_PAD_T )
519  pads->insert( static_cast<PAD*> ( connected->Parent() ) );
520  }
521  }
522 }
523 
524 
525 const std::vector<PAD*> CONNECTIVITY_DATA::GetConnectedPads( const BOARD_CONNECTED_ITEM* aItem )
526 const
527 {
528  std::set<PAD*> pads;
529  std::vector<PAD*> rv;
530 
531  GetConnectedPads( aItem, &pads );
532 
533  std::copy( pads.begin(), pads.end(), std::back_inserter( rv ) );
534  return rv;
535 }
536 
537 
538 unsigned int CONNECTIVITY_DATA::GetNodeCount( int aNet ) const
539 {
540  int sum = 0;
541 
542  if( aNet < 0 ) // Node count for all nets
543  {
544  for( const RN_NET* net : m_nets )
545  sum += net->GetNodeCount();
546  }
547  else if( aNet < (int) m_nets.size() )
548  {
549  sum = m_nets[aNet]->GetNodeCount();
550  }
551 
552  return sum;
553 }
554 
555 
556 unsigned int CONNECTIVITY_DATA::GetPadCount( int aNet ) const
557 {
558  int n = 0;
559 
560  for( CN_ITEM* pad : m_connAlgo->ItemList() )
561  {
562  if( !pad->Valid() || pad->Parent()->Type() != PCB_PAD_T)
563  continue;
564 
565  PAD* dpad = static_cast<PAD*>( pad->Parent() );
566 
567  if( aNet < 0 || aNet == dpad->GetNetCode() )
568  n++;
569  }
570 
571  return n;
572 }
573 
574 
575 void CONNECTIVITY_DATA::GetUnconnectedEdges( std::vector<CN_EDGE>& aEdges) const
576 {
577  for( const RN_NET* rnNet : m_nets )
578  {
579  if( rnNet )
580  {
581  for( const CN_EDGE& edge : rnNet->GetEdges() )
582  aEdges.push_back( edge );
583  }
584  }
585 }
586 
587 
589 {
590  auto items = GetConnectivityAlgo()->ItemEntry( aTrack ).GetItems();
591 
592  // Not in the connectivity system. This is a bug!
593  if( items.empty() )
594  {
595  wxFAIL_MSG( "track not in connectivity system" );
596  return false;
597  }
598 
599  CN_ITEM* citem = items.front();
600 
601  if( !citem->Valid() )
602  return false;
603 
604  for( const std::shared_ptr<CN_ANCHOR>& anchor : citem->Anchors() )
605  {
606  if( anchor->IsDangling() )
607  {
608  if( aPos )
609  *aPos = static_cast<wxPoint>( anchor->Pos() );
610 
611  return true;
612  }
613  }
614 
615  // Test if a via is only connected on one layer
616  if( aTrack->Type() == PCB_VIA_T )
617  {
618  const CN_ITEM::CONNECTED_ITEMS& connected = citem->ConnectedItems();
619 
620  // This is a bit redundant but better safe than sorry here
621  if( connected.empty() )
622  {
623  if( aPos )
624  *aPos = aTrack->GetPosition();
625 
626  return true;
627  }
628 
629  // Here, we check if the via is connected only to items on a single layer
630  int first_layer = connected.front()->Layer();
631 
632  for( auto& item : connected )
633  {
634  if( item->Layer() != first_layer )
635  return false;
636  }
637 
638  if( aPos )
639  *aPos = aTrack->GetPosition();
640 
641  return true;
642  }
643 
644  return false;
645 }
646 
647 
648 const std::vector<BOARD_CONNECTED_ITEM*> CONNECTIVITY_DATA::GetConnectedItemsAtAnchor(
649  const BOARD_CONNECTED_ITEM* aItem, const VECTOR2I& aAnchor, const KICAD_T aTypes[] ) const
650 {
651  auto& entry = m_connAlgo->ItemEntry( aItem );
652  std::vector<BOARD_CONNECTED_ITEM* > rv;
653 
654  for( auto cnItem : entry.GetItems() )
655  {
656  for( auto connected : cnItem->ConnectedItems() )
657  {
658  for( auto anchor : connected->Anchors() )
659  {
660  if( anchor->Pos() == aAnchor )
661  {
662  for( int i = 0; aTypes[i] > 0; i++ )
663  {
664  if( connected->Valid() && connected->Parent()->Type() == aTypes[i] )
665  {
666  rv.push_back( connected->Parent() );
667  break;
668  }
669  }
670 
671  break;
672  }
673  }
674  }
675  }
676 
677  return rv;
678 }
679 
680 
682 {
683  if ( aNet < 0 || aNet >= (int) m_nets.size() )
684  {
685  return nullptr;
686  }
687 
688  return m_nets[ aNet ];
689 }
690 
691 
693 {
694  if ( aItem->Type() == PCB_FOOTPRINT_T)
695  {
696  for( PAD* pad : static_cast<FOOTPRINT*>( aItem )->Pads() )
697  m_connAlgo->MarkNetAsDirty( pad->GetNetCode() );
698  }
699  if (aItem->IsConnected() )
700  {
701  m_connAlgo->MarkNetAsDirty( static_cast<BOARD_CONNECTED_ITEM*>( aItem )->GetNetCode() );
702  }
703 }
704 
705 
707 {
708  m_progressReporter = aReporter;
709  m_connAlgo->SetProgressReporter( m_progressReporter );
710 }
711 
712 
713 const std::vector<CN_EDGE> CONNECTIVITY_DATA::GetRatsnestForItems( std::vector<BOARD_ITEM*> aItems )
714 {
715  std::set<int> nets;
716  std::vector<CN_EDGE> edges;
717  std::set<BOARD_CONNECTED_ITEM*> item_set;
718 
719  for( auto item : aItems )
720  {
721  if( item->Type() == PCB_FOOTPRINT_T )
722  {
723  FOOTPRINT* footprint = static_cast<FOOTPRINT*>( item );
724 
725  for( PAD* pad : footprint->Pads() )
726  {
727  nets.insert( pad->GetNetCode() );
728  item_set.insert( pad );
729  }
730  }
731  else if( auto conn_item = dyn_cast<BOARD_CONNECTED_ITEM*>( item ) )
732  {
733  item_set.insert( conn_item );
734  nets.insert( conn_item->GetNetCode() );
735  }
736  }
737 
738  for( const auto& netcode : nets )
739  {
740  const auto& net = GetRatsnestForNet( netcode );
741 
742  for( const auto& edge : net->GetEdges() )
743  {
744  auto srcNode = edge.GetSourceNode();
745  auto dstNode = edge.GetTargetNode();
746 
747  auto srcParent = srcNode->Parent();
748  auto dstParent = dstNode->Parent();
749 
750  bool srcFound = ( item_set.find(srcParent) != item_set.end() );
751  bool dstFound = ( item_set.find(dstParent) != item_set.end() );
752 
753  if ( srcFound && dstFound )
754  edges.push_back( edge );
755  }
756  }
757 
758  return edges;
759 }
760 
761 
762 const std::vector<CN_EDGE> CONNECTIVITY_DATA::GetRatsnestForComponent( FOOTPRINT* aComponent, bool aSkipInternalConnections )
763 {
764  std::set<int> nets;
765  std::set<const PAD*> pads;
766  std::vector<CN_EDGE> edges;
767 
768  for( auto pad : aComponent->Pads() )
769  {
770  nets.insert( pad->GetNetCode() );
771  pads.insert( pad );
772  }
773 
774  for( const auto& netcode : nets )
775  {
776  const auto& net = GetRatsnestForNet( netcode );
777 
778  for( const auto& edge : net->GetEdges() )
779  {
780  auto srcNode = edge.GetSourceNode();
781  auto dstNode = edge.GetTargetNode();
782 
783  const PAD* srcParent = static_cast<const PAD*>( srcNode->Parent() );
784  const PAD* dstParent = static_cast<const PAD*>( dstNode->Parent() );
785 
786  bool srcFound = ( pads.find(srcParent) != pads.end() );
787  bool dstFound = ( pads.find(dstParent) != pads.end() );
788 
789  if ( srcFound && dstFound && !aSkipInternalConnections )
790  {
791  edges.push_back( edge );
792  }
793  else if ( srcFound || dstFound )
794  {
795  edges.push_back( edge );
796  }
797  }
798  }
799 
800  return edges;
801 }
802 
803 
std::vector< CN_ITEM * > CONNECTED_ITEMS
const CONNECTED_ITEMS & ConnectedItems() const
const std::vector< TRACK * > GetConnectedTracks(const BOARD_CONNECTED_ITEM *aItem) const
void Clear()
Function Clear() Erases the connectivity database.
const std::vector< CN_EDGE > GetRatsnestForComponent(FOOTPRINT *aComponent, bool aSkipInternalConnections=false)
bool IsConnectedOnLayer(const BOARD_CONNECTED_ITEM *aItem, int aLayer, std::vector< KICAD_T > aTypes={}) const
unsigned int GetNodeCount(int aNet=-1) const
const std::vector< BOARD_CONNECTED_ITEM * > GetConnectedItemsAtAnchor(const BOARD_CONNECTED_ITEM *aItem, const VECTOR2I &aAnchor, const KICAD_T aTypes[]) const
Function GetConnectedItemsAtAnchor() Returns a list of items connected to a source item aItem at posi...
bool TestTrackEndpointDangling(TRACK *aTrack, wxPoint *aPos=nullptr)
A base class for any item which can be embedded within the BOARD container class, and therefore insta...
Definition: board_item.h:82
A progress reporter for use in multi-threaded environments.
std::shared_ptr< CN_CONNECTIVITY_ALGO > m_connAlgo
Class that computes missing connections on a PCB.
PROGRESS_REPORTER * m_progressReporter
const std::list< CN_ITEM * > GetItems() const
std::shared_ptr< CN_CONNECTIVITY_ALGO > GetConnectivityAlgo() const
bool Update(BOARD_ITEM *aItem)
Function Update() Updates the connectivity data for an item.
const std::vector< BOARD_CONNECTED_ITEM * > GetNetItems(int aNetCode, const KICAD_T aTypes[]) const
Function GetNetItems() Returns the list of items that belong to a certain net.
void RecalculateRatsnest(BOARD_COMMIT *aCommit=nullptr)
Function RecalculateRatsnest() Updates the ratsnest for the board.
std::shared_ptr< FROM_TO_CACHE > m_fromToCache
class ARC, an arc track segment on a copper layer
Definition: typeinfo.h:97
const NETINFO_LIST & GetNetInfo() const
Definition: board.h:752
class PAD, a pad in a footprint
Definition: typeinfo.h:89
BOARD_CONNECTED_ITEM * Parent() const
CN_ANCHORS & Anchors()
A small class to help profiling.
Definition: profile.h:45
BOARD_CONNECTED_ITEM * b
A base class derived from BOARD_ITEM for items that can be connected and have a net,...
std::vector< RN_DYNAMIC_LINE > m_dynamicRatsnest
int Net() const
allow parallel connection threads
VECTOR2I anchorB
search types array terminator (End Of Types)
Definition: typeinfo.h:81
KICAD_T
The set of class identification values stored in EDA_ITEM::m_structType.
Definition: typeinfo.h:77
class TRACK, a track segment (segment on a copper layer)
Definition: typeinfo.h:95
PADS & Pads()
Definition: footprint.h:164
unsigned int GetPadCount(int aNet=-1) const
void Build(BOARD *aBoard, PROGRESS_REPORTER *aReporter=nullptr)
Function Build() Builds the connectivity database for the board aBoard.
VECTOR2I anchorA
static const char Default[]
the name of the default NETCLASS
Definition: netclass.h:49
const std::vector< BOARD_CONNECTED_ITEM * > GetConnectedItems(const BOARD_CONNECTED_ITEM *aItem, const KICAD_T aTypes[], bool aIgnoreNetcodes=false) const
Function GetConnectedItems() Returns a list of items connected to a source item aItem.
std::map< int, wxString > m_netclassMap
Map of netcode -> netclass the net is a member of; used for ratsnest painting.
unsigned int GetUnconnectedCount() const
Function GetUnconnectedCount() Returns the number of remaining edges in the ratsnest.
void PropagateNets()
Function PropagateNets() Propagates the net codes from the source pads to the tracks/vias.
ZONE handles a list of polygons defining a copper zone.
Definition: zone.h:57
void ClearDynamicRatsnest()
Function ClearDynamicRatsnest() Erases the temporary dynamic ratsnest (i.e.
void SetProgressReporter(PROGRESS_REPORTER *aReporter)
bool Remove(BOARD_ITEM *aItem)
Function Remove() Removes an item from the connectivity data.
void MarkItemNetAsDirty(BOARD_ITEM *aItem)
std::vector< RN_NET * > m_nets
class FOOTPRINT, a footprint
Definition: typeinfo.h:88
void GetUnconnectedEdges(std::vector< CN_EDGE > &aEdges) const
bool Add(BOARD_ITEM *aItem)
Function Add() Adds an item to the connectivity data.
void BlockRatsnestItems(const std::vector< BOARD_ITEM * > &aItems)
RN_NET * GetRatsnestForNet(int aNet)
Function GetRatsnestForNet() Returns the ratsnest, expressed as a set of graph edges for a given net.
BOARD_CONNECTED_ITEM * a
Handle the data for a net.
Definition: netinfo.h:64
bool CheckConnectivity(std::vector< CN_DISJOINT_NET_ENTRY > &aReport)
void ComputeDynamicRatsnest(const std::vector< BOARD_ITEM * > &aItems, const CONNECTIVITY_DATA *aDynamicData)
Function ComputeDynamicRatsnest() Calculates the temporary dynamic ratsnest (i.e.
void FindIsolatedCopperIslands(ZONE *aZone, std::vector< int > &aIslands)
Function FindIsolatedCopperIslands() Searches for copper islands in zone aZone that are not connected...
Information pertinent to a Pcbnew printed circuit board.
Definition: board.h:190
std::shared_ptr< CN_ANCHOR > CN_ANCHOR_PTR
int net
void SetNoLine(bool aEnable)
Return true if this node can be a target for ratsnest lines.
wxPoint GetPosition() const override
Definition: track.h:106
int GetNetCount() const
Function GetNetCount() Returns the total number of nets in the connectivity database.
virtual bool IsConnected() const
Returns information if the object is derived from BOARD_CONNECTED_ITEM.
Definition: board_item.h:136
class VIA, a via (like a track segment on a copper layer)
Definition: typeinfo.h:96
Describe ratsnest for a single net.
Definition: ratsnest_data.h:61
void Show(std::ostream &aStream=std::cerr)
Print the elapsed time (in a suitable unit) to a stream.
Definition: profile.h:102
const std::vector< PAD * > GetConnectedPads(const BOARD_CONNECTED_ITEM *aItem) const
void Move(const VECTOR2I &aPos)
Definition: pad.h:60
void HideDynamicRatsnest()
Hides the temporary dynamic ratsnest lines.
void addRatsnestCluster(const std::shared_ptr< CN_CLUSTER > &aCluster)
void Move(const VECTOR2I &aDelta)
Moves the connectivity list anchors.
Definition: track.h:83
const std::vector< CN_EDGE > GetRatsnestForItems(const std::vector< BOARD_ITEM * > aItems)
bool Valid() const
KICAD_T Type() const
Returns the type of object.
Definition: eda_item.h:162