KiCad PCB EDA Suite
router_tool.cpp
Go to the documentation of this file.
1 /*
2  * KiRouter - a push-and-(sometimes-)shove PCB router
3  *
4  * Copyright (C) 2013-2017 CERN
5  * Copyright (C) 2017-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 modify it
9  * under the terms of the GNU General Public License as published by the
10  * Free Software Foundation, either version 3 of the License, or (at your
11  * option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful, but
14  * WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16  * General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License along
19  * with this program. If not, see <http://www.gnu.org/licenses/>.
20  */
21 
22 #include <wx/numdlg.h>
23 #include <core/optional.h>
24 #include <functional>
25 using namespace std::placeholders;
26 #include "class_board.h"
27 #include "class_module.h"
28 #include "class_pad.h"
29 
30 #include <pcb_edit_frame.h>
31 #include <id.h>
32 #include <macros.h>
33 #include <pcbnew_id.h>
34 #include <view/view_controls.h>
35 #include <pcb_layer_widget.h>
36 #include <pcb_painter.h>
40 #include <base_units.h>
41 #include <confirm.h>
42 #include <bitmaps.h>
43 #include <collectors.h>
44 #include <tool/action_menu.h>
45 #include <tool/tool_manager.h>
46 #include <tool/grid_menu.h>
47 #include <tool/zoom_menu.h>
48 #include <tools/pcb_actions.h>
49 #include <tools/selection_tool.h>
50 #include <tools/grid_helper.h>
51 
52 #include "router_tool.h"
53 #include "pns_segment.h"
54 #include "pns_router.h"
55 #include "pns_itemset.h"
56 
57 using namespace KIGFX;
58 
63 {
64  // Via type
65  VIA_MASK = 0x03,
66  VIA = 0x00,
67  BLIND_VIA = 0x01,
68  MICROVIA = 0x02,
69 
70  // Select layer
72 };
73 
74 
75 // Actions, being statically-defined, require specialized I18N handling. We continue to
76 // use the _() macro so that string harvesting by the I18N framework doesn't have to be
77 // specialized, but we don't translate on initialization and instead do it in the getters.
78 
79 #undef _
80 #define _(s) s
81 
82 static const TOOL_ACTION ACT_UndoLastSegment( "pcbnew.InteractiveRouter.UndoLastSegment",
83  AS_CONTEXT,
84  WXK_BACK, "",
85  _( "Undo last segment" ), _( "Stops laying the current track." ),
87 
88 static const TOOL_ACTION ACT_EndTrack( "pcbnew.InteractiveRouter.EndTrack",
89  AS_CONTEXT,
90  WXK_END, "",
91  _( "Finish Track" ), _( "Stops laying the current track." ),
93 
94 static const TOOL_ACTION ACT_AutoEndRoute( "pcbnew.InteractiveRouter.AutoEndRoute",
95  AS_CONTEXT,
96  'F', "",
97  _( "Auto-finish Track" ), _( "Automagically finishes laying the current track." ) );
98 
99 static const TOOL_ACTION ACT_PlaceThroughVia( "pcbnew.InteractiveRouter.PlaceVia",
100  AS_CONTEXT,
101  'V', LEGACY_HK_NAME( "Add Through Via" ),
102  _( "Place Through Via" ),
103  _( "Adds a through-hole via at the end of currently routed track." ),
105 
106 static const TOOL_ACTION ACT_PlaceBlindVia( "pcbnew.InteractiveRouter.PlaceBlindVia",
107  AS_CONTEXT,
108  MD_ALT + MD_SHIFT + 'V', LEGACY_HK_NAME( "Add Blind/Buried Via" ),
109  _( "Place Blind/Buried Via" ),
110  _( "Adds a blind or buried via at the end of currently routed track."),
112 
113 static const TOOL_ACTION ACT_PlaceMicroVia( "pcbnew.InteractiveRouter.PlaceMicroVia",
114  AS_CONTEXT,
115  MD_CTRL + 'V', LEGACY_HK_NAME( "Add MicroVia" ),
116  _( "Place Microvia" ), _( "Adds a microvia at the end of currently routed track." ),
118 
119 static const TOOL_ACTION ACT_SelLayerAndPlaceThroughVia( "pcbnew.InteractiveRouter.SelLayerAndPlaceVia",
120  AS_CONTEXT,
121  '<', LEGACY_HK_NAME( "Select Layer and Add Through Via" ),
122  _( "Select Layer and Place Through Via..." ),
123  _( "Select a layer, then add a through-hole via at the end of currently routed track." ),
126 
127 static const TOOL_ACTION ACT_SelLayerAndPlaceBlindVia( "pcbnew.InteractiveRouter.SelLayerAndPlaceBlindVia",
128  AS_CONTEXT,
129  MD_ALT + '<', LEGACY_HK_NAME( "Select Layer and Add Blind/Buried Via" ),
130  _( "Select Layer and Place Blind/Buried Via..." ),
131  _( "Select a layer, then add a blind or buried via at the end of currently routed track."),
134 
135 static const TOOL_ACTION ACT_CustomTrackWidth( "pcbnew.InteractiveRouter.CustomTrackViaSize",
136  AS_CONTEXT,
137  'Q', LEGACY_HK_NAME( "Custom Track/Via Size" ),
138  _( "Custom Track/Via Size..." ),
139  _( "Shows a dialog for changing the track width and via size." ),
140  width_track_xpm );
141 
142 static const TOOL_ACTION ACT_SwitchPosture( "pcbnew.InteractiveRouter.SwitchPosture",
143  AS_CONTEXT,
144  '/', LEGACY_HK_NAME( "Switch Track Posture" ),
145  _( "Switch Track Posture" ),
146  _( "Switches posture of the currently routed track." ),
148 
149 static const TOOL_ACTION ACT_SwitchRounding( "pcbnew.InteractiveRouter.SwitchRounding",
150  AS_CONTEXT,
151  0, LEGACY_HK_NAME( "Switch Corner Rounding" ),
152  _( "Switch Corner Rounding" ),
153  _( "Switches the corner type of the currently routed track." ),
155 
156 #undef _
157 #define _(s) wxGetTranslation((s))
158 
159 
161  TOOL_BASE( "pcbnew.InteractiveRouter" )
162 {
163 }
164 
165 
167 {
168 public:
170  ACTION_MENU( true ),
171  m_frame( aFrame )
172  {
174  SetTitle( _( "Select Track/Via Width" ) );
175  }
176 
177 protected:
178  ACTION_MENU* create() const override
179  {
180  return new TRACK_WIDTH_MENU( m_frame );
181  }
182 
183  void update() override
184  {
185  EDA_UNITS units = m_frame.GetUserUnits();
187  bool useIndex = !bds.m_UseConnectedTrackWidth &&
188  !bds.UseCustomTrackViaSize();
189  wxString msg;
190 
191  Clear();
192 
193  Append( ID_POPUP_PCB_SELECT_AUTO_WIDTH, _( "Use Starting Track Width" ),
194  _( "Route using the width of the starting track." ), wxITEM_CHECK );
197 
198  Append( ID_POPUP_PCB_SELECT_USE_NETCLASS_VALUES, _( "Use Net Class Values" ),
199  _( "Use track and via sizes from the net class" ), wxITEM_CHECK );
201  useIndex && bds.GetTrackWidthIndex() == 0 && bds.GetViaSizeIndex() == 0 );
202 
203  Append( ID_POPUP_PCB_SELECT_CUSTOM_WIDTH, _( "Use Custom Values..." ),
204  _( "Specify custom track and via sizes" ), wxITEM_CHECK );
206 
207  AppendSeparator();
208 
209  // Append the list of tracks & via sizes
210  for( unsigned i = 0; i < bds.m_TrackWidthList.size(); i++ )
211  {
212  int width = bds.m_TrackWidthList[i];
213 
214  if( i == 0 )
215  msg = _( "Track netclass width" );
216  else
217  msg.Printf( _( "Track %s" ), MessageTextFromValue( units, width, true ) );
218 
219  int menuIdx = ID_POPUP_PCB_SELECT_WIDTH1 + i;
220  Append( menuIdx, msg, wxEmptyString, wxITEM_CHECK );
221  Check( menuIdx, useIndex && bds.GetTrackWidthIndex() == i );
222  }
223 
224  AppendSeparator();
225 
226  for( unsigned i = 0; i < bds.m_ViasDimensionsList.size(); i++ )
227  {
228  VIA_DIMENSION via = bds.m_ViasDimensionsList[i];
229 
230  if( i == 0 )
231  msg = _( "Via netclass values" );
232  else
233  {
234  if( via.m_Drill > 0 )
235  msg.Printf( _("Via %s, drill %s" ),
236  MessageTextFromValue( units, via.m_Diameter, true ),
237  MessageTextFromValue( units, via.m_Drill, true ) );
238  else
239  msg.Printf( _( "Via %s" ), MessageTextFromValue( units, via.m_Diameter, true ) );
240  }
241 
242  int menuIdx = ID_POPUP_PCB_SELECT_VIASIZE1 + i;
243  Append( menuIdx, msg, wxEmptyString, wxITEM_CHECK );
244  Check( menuIdx, useIndex && bds.GetViaSizeIndex() == i );
245  }
246  }
247 
248  OPT_TOOL_EVENT eventHandler( const wxMenuEvent& aEvent ) override
249  {
251  int id = aEvent.GetId();
252 
253  // On Windows, this handler can be called with an event ID not existing in any
254  // menuitem, so only set flags when we have an ID match.
255 
257  {
258  bds.UseCustomTrackViaSize( true );
259  bds.m_UseConnectedTrackWidth = false;
261  }
262  else if( id == ID_POPUP_PCB_SELECT_AUTO_WIDTH )
263  {
264  bds.UseCustomTrackViaSize( false );
265  bds.m_UseConnectedTrackWidth = true;
266  }
268  {
269  bds.UseCustomTrackViaSize( false );
270  bds.m_UseConnectedTrackWidth = false;
271  bds.SetViaSizeIndex( 0 );
272  bds.SetTrackWidthIndex( 0 );
273  }
275  {
276  bds.UseCustomTrackViaSize( false );
277  bds.m_UseConnectedTrackWidth = false;
279  }
281  {
282  bds.UseCustomTrackViaSize( false );
283  bds.m_UseConnectedTrackWidth = false;
285  }
286 
287  return OPT_TOOL_EVENT( PCB_ACTIONS::trackViaSizeChanged.MakeEvent() );
288  }
289 
290 private:
292 };
293 
294 
296 {
297 public:
299  ACTION_MENU( true ),
300  m_frame( aFrame )
301  {
303  SetTitle( _( "Select Differential Pair Dimensions" ) );
304  }
305 
306 protected:
307  ACTION_MENU* create() const override
308  {
309  return new DIFF_PAIR_MENU( m_frame );
310  }
311 
312  void update() override
313  {
314  EDA_UNITS units = m_frame.GetUserUnits();
316 
317  Clear();
318 
319  Append( ID_POPUP_PCB_SELECT_USE_NETCLASS_DIFFPAIR, _( "Use Net Class Values" ),
320  _( "Use differential pair dimensions from the net class" ), wxITEM_CHECK );
322  !bds.UseCustomDiffPairDimensions() && bds.GetDiffPairIndex() == 0 );
323 
324  Append( ID_POPUP_PCB_SELECT_CUSTOM_DIFFPAIR, _( "Use Custom Values..." ),
325  _( "Specify custom differential pair dimensions" ), wxITEM_CHECK );
327 
328  AppendSeparator();
329 
330  // Append the list of differential pair dimensions
331 
332  // Drop index 0 which is the current netclass dimensions (which are handled above)
333  for( unsigned i = 1; i < bds.m_DiffPairDimensionsList.size(); ++i )
334  {
336  wxString msg;
337 
338  msg << _( "Width " ) << MessageTextFromValue( units, diffPair.m_Width, true );
339 
340  if( diffPair.m_Gap > 0 )
341  msg << _( ", gap " ) << MessageTextFromValue( units, diffPair.m_Gap, true );
342 
343  if( diffPair.m_ViaGap > 0 )
344  msg << _( ", via gap " ) << MessageTextFromValue( units, diffPair.m_ViaGap, true );
345 
346  int menuIdx = ID_POPUP_PCB_SELECT_DIFFPAIR1 + i - 1;
347  Append( menuIdx, msg, wxEmptyString, wxITEM_CHECK );
348  Check( menuIdx, !bds.UseCustomDiffPairDimensions() && bds.GetDiffPairIndex() == i );
349  }
350  }
351 
352  OPT_TOOL_EVENT eventHandler( const wxMenuEvent& aEvent ) override
353  {
355  int id = aEvent.GetId();
356 
357  // On Windows, this handler can be called with an event ID not existing in any
358  // menuitem, so only set flags when we have an ID match.
359 
361  {
362  bds.UseCustomDiffPairDimensions( true );
363  TOOL_MANAGER* toolManager = m_frame.GetToolManager();
364  toolManager->RunAction( PCB_ACTIONS::routerDiffPairDialog, true );
365  }
367  {
368  bds.UseCustomDiffPairDimensions( false );
369  bds.SetDiffPairIndex( 0 );
370  }
372  {
373  bds.UseCustomDiffPairDimensions( false );
374  // remember that the menu doesn't contain index 0 (which is the netclass values)
376  }
377 
378  return OPT_TOOL_EVENT( PCB_ACTIONS::trackViaSizeChanged.MakeEvent() );
379  }
380 
381 private:
383 };
384 
385 
387 {
388 public:
390  ACTION_MENU( true ),
391  m_frame( aFrame ), m_mode( aMode ), m_trackViaMenu( aFrame ), m_diffPairMenu( aFrame ),
392  m_zoomMenu( &aFrame ), m_gridMenu( &aFrame )
393  {
394  SetTitle( _( "Interactive Router" ) );
395 
397 
398  AppendSeparator();
399 
402  Add( ACT_EndTrack );
405 
408 
409 // Add( ACT_AutoEndRoute ); // fixme: not implemented yet. Sorry.
417 
418  AppendSeparator();
419 
420  Add( &m_trackViaMenu );
421 
423  Add( &m_diffPairMenu );
424 
426 
427  AppendSeparator();
428 
429  Add( &m_zoomMenu );
430  Add( &m_gridMenu );
431  }
432 
433 private:
434  ACTION_MENU* create() const override
435  {
436  return new ROUTER_TOOL_MENU( m_frame, m_mode );
437  }
438 
445 };
446 
447 
449 {
450 }
451 
452 
454 {
455  return true;
456 }
457 
458 
460 {
461  if( aReason == RUN )
462  TOOL_BASE::Reset( aReason );
463 }
464 
465 
467 {
468 #ifdef DEBUG
469  if( aEvent.IsKeyPressed() )
470  {
471  switch( aEvent.KeyCode() )
472  {
473  case '0':
474  wxLogTrace( "PNS", "saving drag/route log...\n" );
475  m_router->DumpLog();
476  break;
477  }
478  }
479 #endif
480 }
481 
482 
484 {
485  int tl = getView()->GetTopLayer();
486 
487  if( m_startItem )
488  {
489  const LAYER_RANGE& ls = m_startItem->Layers();
490 
491  if( ls.Overlaps( tl ) )
492  return tl;
493  else
494  return ls.Start();
495  }
496 
497  return tl;
498 }
499 
500 
502 {
503  int al = frame()->GetActiveLayer();
504  int cl = m_router->GetCurrentLayer();
505 
506  if( cl != al )
507  {
508  m_router->SwitchLayer( al );
509  }
510 
511  OPT<int> newLayer = m_router->Sizes().PairedLayer( cl );
512 
513  if( !newLayer )
514  newLayer = m_router->Sizes().GetLayerTop();
515 
516  m_router->SwitchLayer( *newLayer );
517  frame()->SetActiveLayer( ToLAYER_ID( *newLayer ) );
518 }
519 
520 
521 static VIATYPE getViaTypeFromFlags( int aFlags )
522 {
523  switch( aFlags & VIA_ACTION_FLAGS::VIA_MASK )
524  {
526  return VIATYPE::THROUGH;
528  return VIATYPE::BLIND_BURIED;
530  return VIATYPE::MICROVIA;
531  default:
532  wxASSERT_MSG( false, "Unhandled via type" );
533  return VIATYPE::THROUGH;
534  }
535 }
536 
537 
539 {
540  if( aEvent.IsAction( &PCB_ACTIONS::layerTop ) )
541  return F_Cu;
542  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner1 ) )
543  return In1_Cu;
544  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner2 ) )
545  return In2_Cu;
546  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner3 ) )
547  return In3_Cu;
548  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner4 ) )
549  return In4_Cu;
550  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner5 ) )
551  return In5_Cu;
552  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner6 ) )
553  return In6_Cu;
554  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner7 ) )
555  return In7_Cu;
556  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner8 ) )
557  return In8_Cu;
558  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner9 ) )
559  return In9_Cu;
560  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner10 ) )
561  return In10_Cu;
562  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner11 ) )
563  return In11_Cu;
564  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner12 ) )
565  return In12_Cu;
566  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner13 ) )
567  return In13_Cu;
568  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner14 ) )
569  return In14_Cu;
570  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner15 ) )
571  return In15_Cu;
572  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner16 ) )
573  return In16_Cu;
574  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner17 ) )
575  return In17_Cu;
576  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner18 ) )
577  return In18_Cu;
578  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner19 ) )
579  return In19_Cu;
580  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner20 ) )
581  return In20_Cu;
582  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner21 ) )
583  return In21_Cu;
584  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner22 ) )
585  return In22_Cu;
586  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner23 ) )
587  return In23_Cu;
588  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner24 ) )
589  return In24_Cu;
590  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner25 ) )
591  return In25_Cu;
592  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner26 ) )
593  return In26_Cu;
594  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner27 ) )
595  return In27_Cu;
596  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner28 ) )
597  return In28_Cu;
598  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner29 ) )
599  return In29_Cu;
600  else if( aEvent.IsAction( &PCB_ACTIONS::layerInner30 ) )
601  return In30_Cu;
602  else if( aEvent.IsAction( &PCB_ACTIONS::layerBottom ) )
603  return B_Cu;
604  else
605  return UNDEFINED_LAYER;
606 }
607 
608 
610 {
611  // First see if this is one of the switch layer commands
612  LSEQ layers = LSET( board()->GetEnabledLayers() & LSET::AllCuMask() ).Seq();
613  int currentLayer = m_router->GetCurrentLayer();
614 
615  PCB_LAYER_ID targetLayer = UNDEFINED_LAYER;
616 
617  if( aEvent.IsAction( &PCB_ACTIONS::layerNext ) )
618  {
619  aEvent.PassEvent();
620 
621  size_t idx = 0;
622 
623  for( size_t i = 0; i < layers.size(); i++ )
624  {
625  if( layers[i] == currentLayer )
626  {
627  idx = i;
628  break;
629  }
630  }
631 
632  idx = ( idx + 1 ) % layers.size();
633  targetLayer = layers[idx];
634  }
635  else if( aEvent.IsAction( &PCB_ACTIONS::layerPrev ) )
636  {
637  aEvent.PassEvent();
638 
639  size_t idx = 0;
640 
641  for( size_t i = 0; i < layers.size(); i++ )
642  {
643  if( layers[i] == currentLayer )
644  {
645  idx = i;
646  break;
647  }
648  }
649 
650  idx = ( idx > 0 ) ? ( idx - 1 ) : ( layers.size() - 1 );
651  targetLayer = layers[idx];
652  }
653  else
654  {
655  targetLayer = getTargetLayerFromEvent( aEvent );
656 
657  if( targetLayer != UNDEFINED_LAYER )
658  {
659  aEvent.PassEvent();
660 
661  if( targetLayer == currentLayer )
662  return 0;
663  }
664  }
665 
667  const int layerCount = bds.GetCopperLayerCount();
668 
671 
673 
674  VIATYPE viaType = VIATYPE::THROUGH;
675  bool selectLayer = false;
676 
677  // Otherwise it is one of the router-specific via commands
678  if( targetLayer == UNDEFINED_LAYER )
679  {
680  const int actViaFlags = aEvent.Parameter<intptr_t>();
681  selectLayer = actViaFlags & VIA_ACTION_FLAGS::SELECT_LAYER;
682 
683  viaType = getViaTypeFromFlags( actViaFlags );
684 
685  // ask the user for a target layer
686  if( selectLayer )
687  {
688  wxPoint dlgPosition = wxGetMousePosition();
689 
690  targetLayer = frame()->SelectLayer(
691  static_cast<PCB_LAYER_ID>( currentLayer ), LSET::AllNonCuMask(), dlgPosition );
692 
693  // Reset the cursor to the position where the event occured
694  controls()->SetCursorPosition( aEvent.HasPosition() ? aEvent.Position() : dlgPosition );
695  }
696  }
697 
698  // fixme: P&S supports more than one fixed layer pair. Update the dialog?
699  sizes.ClearLayerPairs();
700 
701  if( !m_router->IsPlacingVia() )
702  {
703  // Cannot place microvias or blind vias if not allowed (obvious)
704  if( ( viaType == VIATYPE::BLIND_BURIED ) && ( !bds.m_BlindBuriedViaAllowed ) )
705  {
706  DisplayError( frame(),
707  _( "Blind/buried vias have to be enabled in Board Setup > Design Rules > Constraints." ) );
708  return false;
709  }
710 
711  if( ( viaType == VIATYPE::MICROVIA ) && ( !bds.m_MicroViasAllowed ) )
712  {
713  DisplayError( frame(),
714  _( "Microvias have to be enabled in Board Setup > Design Rules > Constraints." ) );
715  return false;
716  }
717 
718  // Can only place through vias on 2-layer boards
719  if( ( viaType != VIATYPE::THROUGH ) && ( layerCount <= 2 ) )
720  {
721  DisplayError( frame(), _( "Only through vias are allowed on 2 layer boards." ) );
722  return false;
723  }
724 
725  // Can only place microvias if we're on an outer layer, or directly adjacent to one
726  if( ( viaType == VIATYPE::MICROVIA ) && ( currentLayer > In1_Cu )
727  && ( currentLayer < layerCount - 2 ) )
728  {
729  DisplayError( frame(), _( "Microvias can be placed only between the outer layers "
730  "(F.Cu/B.Cu) and the ones directly adjacent to them." ) );
731  return false;
732  }
733  }
734 
735  // Convert blind/buried via to a through hole one, if it goes through all layers
736  if( viaType == VIATYPE::BLIND_BURIED
737  && ( ( targetLayer == B_Cu && currentLayer == F_Cu )
738  || ( targetLayer == F_Cu && currentLayer == B_Cu ) ) )
739  {
740  viaType = VIATYPE::THROUGH;
741  }
742 
743  switch( viaType )
744  {
745  case VIATYPE::THROUGH:
746  sizes.SetViaDiameter( bds.GetCurrentViaSize() );
747  sizes.SetViaDrill( bds.GetCurrentViaDrill() );
748 
749  if( targetLayer != UNDEFINED_LAYER )
750  {
751  // go from the current layer to the chosen layer
752  sizes.AddLayerPair( currentLayer, targetLayer );
753  }
754  else
755  {
756  // use the default layer pair
757  sizes.AddLayerPair( pairTop, pairBottom );
758  }
759  break;
760 
761  case VIATYPE::MICROVIA:
762  sizes.SetViaDiameter( bds.GetCurrentMicroViaSize() );
763  sizes.SetViaDrill( bds.GetCurrentMicroViaDrill() );
764 
765  wxASSERT_MSG( !selectLayer,
766  "Unexpected select layer for microvia (microvia layers are implicit)" );
767 
768  if( currentLayer == F_Cu || currentLayer == In1_Cu )
769  {
770  // front-side microvia
771  sizes.AddLayerPair( F_Cu, In1_Cu );
772  }
773  else if( currentLayer == B_Cu || currentLayer == layerCount - 2 )
774  {
775  // back-side microvia
776  sizes.AddLayerPair( B_Cu, layerCount - 2 );
777  }
778  else
779  {
780  wxASSERT_MSG( false,
781  "Invalid layer pair for microvia (must be on or adjacent to an outer layer)" );
782  }
783  break;
784 
786  sizes.SetViaDiameter( bds.GetCurrentViaSize() );
787  sizes.SetViaDrill( bds.GetCurrentViaDrill() );
788 
789  if( targetLayer != UNDEFINED_LAYER )
790  {
791  // go directly to the user specified layer
792  sizes.AddLayerPair( currentLayer, targetLayer );
793  }
794  else
795  {
796  if( currentLayer == pairTop || currentLayer == pairBottom )
797  {
798  // the current layer is on the defined layer pair,
799  // swap to the other side
800  sizes.AddLayerPair( pairTop, pairBottom );
801  }
802  else
803  {
804  // the current layer is not part of the current layer pair,
805  // so fallback and swap to the top layer of the pair by default
806  sizes.AddLayerPair( pairTop, currentLayer );
807  }
808  }
809  break;
810 
811  default:
812  wxASSERT( false );
813  break;
814  }
815 
816  sizes.SetViaType( viaType );
817 
818  m_router->UpdateSizes( sizes );
820 
821  if( m_router->RoutingInProgress() )
822  updateEndItem( aEvent );
823  else
824  updateStartItem( aEvent );
825 
826  m_router->Move( m_endSnapPoint, m_endItem ); // refresh
827 
828  return 0;
829 }
830 
831 
833 {
834  int routingLayer = getStartLayer( m_startItem );
835 
836  if( !IsCopperLayer( routingLayer ) )
837  {
838  DisplayError( frame(), _( "Tracks on Copper layers only" ) );
839  return false;
840  }
841 
842  PCB_EDIT_FRAME* editFrame = getEditFrame<PCB_EDIT_FRAME>();
843 
844  editFrame->SetActiveLayer( ToLAYER_ID( routingLayer ) );
845 
846  // Force layer visible
847  editFrame->GetLayerManager()->SetLayerVisible( routingLayer, true );
848 
849  // for some reason I don't understand, GetNetclass() may return null sometimes...
850  if( m_startItem && m_startItem->Net() >= 0 &&
852  {
853  highlightNet( true, m_startItem->Net() );
854  // Update track width and via size shown in main toolbar comboboxes
856  }
857  else
859 
860  controls()->ForceCursorPosition( false );
861  controls()->SetAutoPan( true );
862 
863  PNS::SIZES_SETTINGS sizes( m_router->Sizes() );
864 
865  sizes.Init( board(), m_startItem );
866  sizes.AddLayerPair( frame()->GetScreen()->m_Route_Layer_TOP,
867  frame()->GetScreen()->m_Route_Layer_BOTTOM );
868  m_router->UpdateSizes( sizes );
869 
870  if( !m_router->StartRouting( m_startSnapPoint, m_startItem, routingLayer ) )
871  {
873  highlightNet( false );
874  controls()->SetAutoPan( false );
875  return false;
876  }
877 
878  m_endItem = nullptr;
880 
881  frame()->UndoRedoBlock( true );
882 
883  return true;
884 }
885 
886 
888 {
890 
891  controls()->SetAutoPan( false );
892  controls()->ForceCursorPosition( false );
893  frame()->UndoRedoBlock( false );
894  highlightNet( false );
895 
896  return true;
897 }
898 
899 
901 {
902  if( !prepareInteractive() )
903  return;
904 
905  while( TOOL_EVENT* evt = Wait() )
906  {
907  frame()->GetCanvas()->SetCurrentCursor( wxCURSOR_PENCIL );
908 
909  // Don't crash if we missed an operation that cancelled routing.
910  if( !m_router->RoutingInProgress() )
911  {
912  if( evt->IsCancelInteractive() )
913  m_cancelled = true;
914 
915  break;
916  }
917 
918  handleCommonEvents( *evt );
919 
920  if( evt->IsMotion() )
921  {
922  m_router->SetOrthoMode( evt->Modifier( MD_CTRL ) );
923  updateEndItem( *evt );
925  }
926  else if( evt->IsAction( &ACT_UndoLastSegment ) )
927  {
929  updateEndItem( *evt );
931  }
932  else if( evt->IsClick( BUT_LEFT ) || evt->IsAction( &PCB_ACTIONS::routeSingleTrack ) )
933  {
934  updateEndItem( *evt );
935  bool needLayerSwitch = m_router->IsPlacingVia();
936  bool forceFinish = evt->Modifier( MD_SHIFT );
937 
938  if( m_router->FixRoute( m_endSnapPoint, m_endItem, forceFinish ) )
939  {
940  break;
941  }
942 
943  if( needLayerSwitch )
945 
946  // Synchronize the indicated layer
948  updateEndItem( *evt );
950  m_startItem = nullptr;
951  }
952  else if( evt->IsAction( &ACT_SwitchRounding ) )
953  {
955  updateEndItem( *evt );
956  m_router->Move( m_endSnapPoint, m_endItem ); // refresh
957  }
958  else if( evt->IsAction( &ACT_SwitchPosture ) )
959  {
961  updateEndItem( *evt );
962  m_router->Move( m_endSnapPoint, m_endItem ); // refresh
963  }
964  else if( evt->IsAction( &PCB_ACTIONS::layerChanged ) )
965  {
966  m_router->SwitchLayer( frame()->GetActiveLayer() );
967  updateEndItem( *evt );
968  m_router->Move( m_endSnapPoint, m_endItem ); // refresh
969  }
970  else if( evt->IsAction( &ACT_EndTrack ) || evt->IsDblClick( BUT_LEFT ) )
971  {
972  // Stop current routing:
974  break;
975  }
976  else if( evt->IsCancelInteractive() || evt->IsActivate()
977  || evt->IsUndoRedo()
978  || evt->IsAction( &PCB_ACTIONS::routerInlineDrag ) )
979  {
980  if( evt->IsCancelInteractive() && !m_router->RoutingInProgress() )
981  m_cancelled = true;
982 
983  if( evt->IsActivate() && !evt->IsMoveTool() )
984  m_cancelled = true;
985 
986  break;
987  }
988  else if( evt->IsKeyPressed() )
989  {
990  // wxWidgets fails to correctly translate shifted keycodes on the wxEVT_CHAR_HOOK
991  // event so we need to process the wxEVT_CHAR event that will follow as long as we
992  // pass the event.
993  evt->SetPassEvent();
994  }
995  }
996 
999 
1001 }
1002 
1003 
1005 {
1006  PNS::SIZES_SETTINGS sizes = m_router->Sizes();
1007  DIALOG_PNS_DIFF_PAIR_DIMENSIONS settingsDlg( frame(), sizes );
1008 
1009  if( settingsDlg.ShowModal() == wxID_OK )
1010  {
1011  m_router->UpdateSizes( sizes );
1012  m_savedSizes = sizes;
1013 
1015  bds.SetCustomDiffPairWidth( sizes.DiffPairWidth() );
1016  bds.SetCustomDiffPairGap( sizes.DiffPairGap() );
1017  bds.SetCustomDiffPairViaGap( sizes.DiffPairViaGap() );
1018  }
1019 
1020  return 0;
1021 }
1022 
1023 
1025 {
1026  DIALOG_PNS_SETTINGS settingsDlg( frame(), m_router->Settings() );
1027 
1028  settingsDlg.ShowModal();
1029 
1030  return 0;
1031 }
1032 
1033 
1035 {
1036  PNS::PNS_MODE mode = aEvent.Parameter<PNS::PNS_MODE>();
1037  PNS::ROUTING_SETTINGS& settings = m_router->Settings();
1038 
1039  settings.SetMode( mode );
1040 
1041  return 0;
1042 }
1043 
1044 
1046 {
1047  return m_router->Settings().Mode();
1048 }
1049 
1050 
1052 {
1055 }
1056 
1057 
1058 int ROUTER_TOOL::MainLoop( const TOOL_EVENT& aEvent )
1059 {
1060  PNS::ROUTER_MODE mode = aEvent.Parameter<PNS::ROUTER_MODE>();
1061  PCB_EDIT_FRAME* frame = getEditFrame<PCB_EDIT_FRAME>();
1062 
1063  // Deselect all items
1065 
1066  std::string tool = aEvent.GetCommandStr().get();
1067  frame->PushTool( tool );
1068  Activate();
1069 
1070  m_router->SetMode( mode );
1071 
1072  VIEW_CONTROLS* ctls = getViewControls();
1073  ctls->ShowCursor( true );
1074  ctls->ForceCursorPosition( false );
1075  m_cancelled = false;
1077 
1078  std::unique_ptr<ROUTER_TOOL_MENU> ctxMenu( new ROUTER_TOOL_MENU( *frame, mode ) );
1079  SetContextMenu( ctxMenu.get() );
1080 
1081  // Prime the pump
1082  if( aEvent.HasPosition() )
1084 
1085  // Main loop: keep receiving events
1086  while( TOOL_EVENT* evt = Wait() )
1087  {
1088  frame->GetCanvas()->SetCurrentCursor( wxCURSOR_PENCIL );
1089 
1090  if( evt->IsCancelInteractive() )
1091  {
1092  frame->PopTool( tool );
1093  break;
1094  }
1095  else if( evt->IsActivate() )
1096  {
1097  if( evt->IsMoveTool() )
1098  {
1099  // leave ourselves on the stack so we come back after the move
1100  break;
1101  }
1102  else
1103  {
1104  frame->PopTool( tool );
1105  break;
1106  }
1107  }
1108  else if( evt->Action() == TA_UNDO_REDO_PRE )
1109  {
1110  m_router->ClearWorld();
1111  }
1112  else if( evt->Action() == TA_UNDO_REDO_POST || evt->Action() == TA_MODEL_CHANGE )
1113  {
1114  m_router->SyncWorld();
1115  }
1116  else if( evt->IsMotion() )
1117  {
1118  updateStartItem( *evt );
1119  }
1120  else if( evt->IsAction( &PCB_ACTIONS::dragFreeAngle ) )
1121  {
1122  updateStartItem( *evt, true );
1124  }
1125  else if( evt->IsAction( &PCB_ACTIONS::drag45Degree ) )
1126  {
1127  updateStartItem( *evt, true );
1129  }
1130  else if( evt->IsAction( &PCB_ACTIONS::breakTrack ) )
1131  {
1132  updateStartItem( *evt, true );
1133  breakTrack( );
1134  }
1135  else if( evt->IsClick( BUT_LEFT )
1136  || evt->IsAction( &PCB_ACTIONS::routeSingleTrack )
1137  || evt->IsAction( &PCB_ACTIONS::routeDiffPair ) )
1138  {
1139  if( evt->IsAction( &PCB_ACTIONS::routeSingleTrack )
1140  || evt->IsAction( &PCB_ACTIONS::routeDiffPair ) )
1141  {
1142  mode = evt->Parameter<PNS::ROUTER_MODE>();
1143  }
1144 
1145  updateStartItem( *evt );
1146 
1147  if( evt->HasPosition() )
1148  {
1149  if( evt->Modifier( MD_CTRL ) )
1151  else
1152  performRouting();
1153  }
1154  }
1155  else if( evt->IsAction( &ACT_PlaceThroughVia ) )
1156  {
1158  }
1159  else if( evt->IsAction( &PCB_ACTIONS::layerChanged ) )
1160  {
1162  updateStartItem( *evt );
1163  }
1164  else if( evt->IsKeyPressed() )
1165  {
1166  // wxWidgets fails to correctly translate shifted keycodes on the wxEVT_CHAR_HOOK
1167  // event so we need to process the wxEVT_CHAR event that will follow as long as we
1168  // pass the event.
1169  evt->SetPassEvent();
1170  }
1171 
1172  if( m_cancelled )
1173  {
1174  frame->PopTool( tool );
1175  break;
1176  }
1177  }
1178 
1179  SetContextMenu( nullptr );
1180 
1181  // Store routing settings till the next invocation
1183 
1184  return 0;
1185 }
1186 
1187 
1189 {
1190  VIEW_CONTROLS* ctls = getViewControls();
1191 
1192  if( m_startItem && m_startItem->IsLocked() )
1193  {
1194  KIDIALOG dlg( frame(), _( "The selected item is locked." ), _( "Confirmation" ),
1195  wxOK | wxCANCEL | wxICON_WARNING );
1196  dlg.SetOKLabel( _( "Drag Anyway" ) );
1197  dlg.DoNotShowCheckbox( __FILE__, __LINE__ );
1198 
1199  if( dlg.ShowModal() == wxID_CANCEL )
1200  return;
1201  }
1202 
1203  bool dragStarted = m_router->StartDragging( m_startSnapPoint, m_startItem, aMode );
1204 
1205  if( !dragStarted )
1206  return;
1207 
1208  if( m_startItem && m_startItem->Net() >= 0 )
1209  highlightNet( true, m_startItem->Net() );
1210 
1211  ctls->SetAutoPan( true );
1213  frame()->UndoRedoBlock( true );
1214 
1215  while( TOOL_EVENT* evt = Wait() )
1216  {
1217  ctls->ForceCursorPosition( false );
1218 
1219  if( evt->IsMotion() )
1220  {
1221  updateEndItem( *evt );
1223  }
1224  else if( evt->IsClick( BUT_LEFT ) )
1225  {
1227  break;
1228  }
1229  else if( evt->IsCancelInteractive() || evt->IsActivate() || evt->IsUndoRedo() )
1230  {
1231  if( evt->IsCancelInteractive() && !m_startItem )
1232  m_cancelled = true;
1233 
1234  if( evt->IsActivate() && !evt->IsMoveTool() )
1235  m_cancelled = true;
1236 
1237  break;
1238  }
1239 
1240  handleCommonEvents( *evt );
1241  }
1242 
1243  if( m_router->RoutingInProgress() )
1244  m_router->StopRouting();
1245 
1246  m_startItem = nullptr;
1247 
1248  m_gridHelper->SetAuxAxes( false );
1249  frame()->UndoRedoBlock( false );
1250  ctls->SetAutoPan( false );
1251  ctls->ForceCursorPosition( false );
1252  highlightNet( false );
1253 }
1254 
1255 
1257 {
1258  /*
1259  * If the collection contains a trivial line corner (two connected segments)
1260  * or a non-fanout-via (a via with no more than two connected segments), then
1261  * trim the collection down to a single item (which one won't matter since
1262  * they're all connected).
1263  */
1264 
1265  // First make sure we've got something that *might* match.
1266  int vias = aCollector.CountType( PCB_VIA_T );
1267  int traces = aCollector.CountType( PCB_TRACE_T );
1268  int arcs = aCollector.CountType( PCB_ARC_T );
1269 
1270  if( arcs > 0 || vias > 1 || traces > 2 || vias + traces < 1 )
1271  return;
1272 
1273  // Fetch first TRACK (via or trace) as our reference
1274  TRACK* reference = nullptr;
1275 
1276  for( int i = 0; !reference && i < aCollector.GetCount(); i++ )
1277  reference = dynamic_cast<TRACK*>( aCollector[i] );
1278 
1279  int refNet = reference->GetNetCode();
1280 
1281  wxPoint refPoint( aPt.x, aPt.y );
1282  STATUS_FLAGS flags = reference->IsPointOnEnds( refPoint, -1 );
1283 
1284  if( flags & STARTPOINT )
1285  refPoint = reference->GetStart();
1286  else if( flags & ENDPOINT )
1287  refPoint = reference->GetEnd();
1288 
1289  // Check all items to ensure that any TRACKs are co-terminus with the reference and on
1290  // the same net.
1291  for( int i = 0; i < aCollector.GetCount(); i++ )
1292  {
1293  TRACK* neighbor = dynamic_cast<TRACK*>( aCollector[i] );
1294 
1295  if( neighbor && neighbor != reference )
1296  {
1297  if( neighbor->GetNetCode() != refNet )
1298  return;
1299 
1300  if( neighbor->GetStart() != refPoint && neighbor->GetEnd() != refPoint )
1301  return;
1302  }
1303  }
1304 
1305  // Selection meets criteria; trim it to the reference item.
1306  aCollector.Empty();
1307  aCollector.Append( reference );
1308 }
1309 
1310 
1312 {
1314  const auto& selection = m_toolMgr->GetTool<SELECTION_TOOL>()->GetSelection();
1315 
1316  if( selection.Size() == 1 )
1317  {
1318  const BOARD_ITEM* item = static_cast<const BOARD_ITEM*>( selection.Front() );
1319 
1320  if( item->Type() == PCB_TRACE_T || item->Type() == PCB_VIA_T || item->Type() == PCB_MODULE_T )
1321  return true;
1322  }
1323 
1324  return false;
1325 }
1326 
1327 
1329 {
1330  const auto& selection = m_toolMgr->GetTool<SELECTION_TOOL>()->GetSelection();
1331 
1332  if( selection.Empty() )
1334 
1335  if( selection.Size() != 1 )
1336  return 0;
1337 
1338  const BOARD_ITEM* item = static_cast<const BOARD_ITEM*>( selection.Front() );
1339 
1340  if( item->Type() != PCB_TRACE_T && item->Type() != PCB_VIA_T && item->Type() != PCB_MODULE_T )
1341  return 0;
1342 
1343  Activate();
1344 
1346  m_router->SyncWorld();
1347  m_startItem = nullptr;
1348 
1349  PNS::ITEM* startItem = nullptr;
1350  PNS::ITEM_SET itemsToDrag;
1351 
1352  if( item->Type() == PCB_MODULE_T )
1353  {
1354  const auto mod = static_cast<const MODULE*>(item);
1355  for ( const auto p : mod->Pads() )
1356  {
1357  auto solid = m_router->GetWorld()->FindItemByParent( p );
1358 
1359  if( solid )
1360  itemsToDrag.Add( solid );
1361  }
1362  }
1363  else
1364  {
1365  startItem = m_router->GetWorld()->FindItemByParent( static_cast<const BOARD_CONNECTED_ITEM*>( item ) );
1366 
1367  if( startItem)
1368  itemsToDrag.Add( startItem );
1369  }
1370 
1371  if( startItem && startItem->IsLocked() )
1372  {
1373  KIDIALOG dlg( frame(), _( "The selected item is locked." ), _( "Confirmation" ),
1374  wxOK | wxCANCEL | wxICON_WARNING );
1375  dlg.SetOKLabel( _( "Drag Anyway" ) );
1376  dlg.DoNotShowCheckbox( __FILE__, __LINE__ );
1377 
1378  if( dlg.ShowModal() == wxID_CANCEL )
1379  return 0;
1380  }
1381 
1382  VECTOR2I p0 = controls()->GetCursorPosition( false );
1383  VECTOR2I p = p0;
1384 
1385  if( startItem )
1386  p = snapToItem( true, startItem, p0 );
1387 
1388  int dragMode = aEvent.Parameter<int64_t> ();
1389 
1390  bool dragStarted = m_router->StartDragging( p, itemsToDrag, dragMode );
1391 
1392  if( !dragStarted )
1393  return 0;
1394 
1395  m_gridHelper->SetAuxAxes( true, p );
1396  controls()->ShowCursor( true );
1397  controls()->ForceCursorPosition( false );
1398  controls()->SetAutoPan( true );
1399  frame()->UndoRedoBlock( true );
1400 
1401  while( TOOL_EVENT* evt = Wait() )
1402  {
1403  frame()->GetCanvas()->SetCurrentCursor( wxCURSOR_ARROW );
1404 
1405  if( evt->IsCancelInteractive() )
1406  {
1407  break;
1408  }
1409  else if( evt->IsMotion() || evt->IsDrag( BUT_LEFT ) )
1410  {
1411  updateEndItem( *evt );
1413  }
1414  else if( evt->IsMouseUp( BUT_LEFT ) || evt->IsClick( BUT_LEFT ) )
1415  {
1416  updateEndItem( *evt );
1418  break;
1419  }
1420  }
1421 
1422  if( m_router->RoutingInProgress() )
1423  m_router->StopRouting();
1424 
1425  m_gridHelper->SetAuxAxes( false );
1426  controls()->SetAutoPan( false );
1427  controls()->ForceCursorPosition( false );
1428  frame()->UndoRedoBlock( false );
1429 
1430  return 0;
1431 }
1432 
1433 
1435 {
1436  const auto& selection = m_toolMgr->GetTool<SELECTION_TOOL>()->GetSelection();
1437 
1438  if( selection.Size() != 1 )
1439  return 0;
1440 
1441  const BOARD_CONNECTED_ITEM* item = static_cast<const BOARD_CONNECTED_ITEM*>( selection.Front() );
1442 
1443  if( item->Type() != PCB_TRACE_T )
1444  return 0;
1445 
1446  Activate();
1447 
1449  m_router->SyncWorld();
1451  m_startSnapPoint = snapToItem( true, m_startItem, controls()->GetCursorPosition() );
1452 
1453 
1454  if( m_startItem && m_startItem->IsLocked() )
1455  {
1456  KIDIALOG dlg( frame(), _( "The selected item is locked." ), _( "Confirmation" ),
1457  wxOK | wxCANCEL | wxICON_WARNING );
1458  dlg.SetOKLabel( _( "Break Track" ) );
1459  dlg.DoNotShowCheckbox( __FILE__, __LINE__ );
1460 
1461  if( dlg.ShowModal() == wxID_CANCEL )
1462  return 0;
1463  }
1464 
1465  frame()->UndoRedoBlock( true );
1466  breakTrack();
1467 
1468  if( m_router->RoutingInProgress() )
1469  m_router->StopRouting();
1470 
1471  frame()->UndoRedoBlock( false );
1472 
1473  return 0;
1474 }
1475 
1476 
1478 {
1480  DIALOG_TRACK_VIA_SIZE sizeDlg( frame(), bds );
1481 
1482  if( sizeDlg.ShowModal() )
1483  {
1484  bds.UseCustomTrackViaSize( true );
1486  }
1487 
1488  return 0;
1489 }
1490 
1491 
1493 {
1494  PNS::SIZES_SETTINGS sizes( m_router->Sizes() );
1495  sizes.ImportCurrent( board()->GetDesignSettings() );
1496  m_router->UpdateSizes( sizes );
1497 
1498  // Changing the track width can affect the placement, so call the
1499  // move routine without changing the destination
1501 
1502  return 0;
1503 }
1504 
1505 
1507 {
1509 
1519 
1525 
1560 
1563 }
void Empty()
Function Empty sets the list to empty.
Definition: collector.h:109
static TOOL_ACTION selectionClear
Clears the current selection.
Definition: pcb_actions.h:62
const wxString & FailureReason() const
Definition: pns_router.h:226
int GetCurrentMicroViaSize()
Function GetCurrentMicroViaSize.
static LSET AllCuMask(int aCuLayerCount=MAX_CU_LAYERS)
Function AllCuMask returns a mask holding the requested number of Cu PCB_LAYER_IDs.
Definition: lset.cpp:712
virtual void ShowCursor(bool aEnabled)
Function ShowCursor() Enables or disables display of cursor.
EDA_UNITS
Definition: common.h:198
void DisplayError(wxWindow *aParent, const wxString &aText, int aDisplayTime)
Display an error or warning message box with aMessage.
Definition: confirm.cpp:239
static TOOL_ACTION layerBottom
Definition: pcb_actions.h:265
ITEM.
Definition: pns_item.h:53
static TOOL_ACTION layerInner26
Definition: pcb_actions.h:260
Struct VIA_DIMENSION is a small helper container to handle a stock of specific vias each with unique ...
wxMenuItem * Add(const wxString &aLabel, int aId, const BITMAP_OPAQUE *aIcon)
Function Add() Adds a wxWidgets-style entry to the menu.
OPT_TOOL_EVENT eventHandler(const wxMenuEvent &aEvent) override
Event handler stub.
void SetMode(PNS_MODE aMode)
Sets the routing mode.
BOARD_CONNECTED_ITEM * Parent() const
Definition: pns_item.h:146
void DoNotShowCheckbox(wxString file, int line)
Shows the 'do not show again' checkbox
Definition: confirm.cpp:53
void SetTrackWidthIndex(unsigned aIndex)
Function SetTrackWidthIndex sets the current track width list index to aIndex.
int GetNetCode() const
Function GetNetCode.
static TOOL_ACTION layerNext
Definition: pcb_actions.h:266
PNS::PNS_MODE GetRouterMode()
static TOOL_ACTION layerInner2
Definition: pcb_actions.h:236
int MainLoop(const TOOL_EVENT &aEvent)
static TOOL_ACTION selectLayerPair
Definition: pcb_actions.h:124
static const TOOL_ACTION ACT_PlaceMicroVia("pcbnew.InteractiveRouter.PlaceMicroVia", AS_CONTEXT, MD_CTRL+ 'V', LEGACY_HK_NAME("Add MicroVia"), _("Place Microvia"), _("Adds a microvia at the end of currently routed track."), via_microvia_xpm, AF_NONE,(void *) VIA_ACTION_FLAGS::MICROVIA)
PCB_EDIT_FRAME & m_frame
GRID_HELPER * m_gridHelper
Definition: pns_tool_base.h:75
TOOL_EVENT * Wait(const TOOL_EVENT_LIST &aEventList=TOOL_EVENT(TC_ANY, TA_ANY))
Function Wait()
BOARD * board() const
int GetCurrentViaDrill() const
Function GetCurrentViaDrill.
#define LEGACY_HK_NAME(x)
Definition: actions.h:35
int DpDimensionsDialog(const TOOL_EVENT &aEvent)
Class CAIRO_GAL is the cairo implementation of the graphics abstraction layer.
Definition: color4d.cpp:175
PNS_MODE
Routing modes
static TOOL_ACTION layerInner5
Definition: pcb_actions.h:239
Normal via
Definition: router_tool.cpp:67
Helper class to create more flexible dialogs, including 'do not show again' checkbox handling.
Definition: confirm.h:44
bool finishInteractive()
void SetCustomDiffPairViaGap(int aGap)
Function SetCustomDiffPairViaGap Sets custom via gap for differential pairs (i.e.
blind/buried via
Definition: router_tool.cpp:68
Implementation of conversion functions that require both schematic and board internal units.
ACTION_MENU.
Definition: action_menu.h:44
This file is part of the common library.
static TOOL_ACTION layerInner6
Definition: pcb_actions.h:240
BOARD_ITEM is a base class for any item which can be embedded within the BOARD container class,...
static TOOL_ACTION routerDiffPairDialog
Definition: pcb_actions.h:186
std::vector< int > m_TrackWidthList
static TOOL_ACTION layerInner7
Definition: pcb_actions.h:241
static TOOL_ACTION layerInner8
Definition: pcb_actions.h:242
void SetCurrentCursor(wxStockCursor aStockCursorID)
Function SetCurrentCursor Set the current cursor shape for this panel.
const wxPoint & GetStart() const
Definition: class_track.h:118
const wxString & GetName() const
Definition: netclass.h:96
int GetCurrentMicroViaDrill()
Function GetCurrentMicroViaDrill.
VIEW_CONTROLS class definition.
static TOOL_ACTION layerInner21
Definition: pcb_actions.h:255
std::vector< DIFF_PAIR_DIMENSION > m_DiffPairDimensionsList
VECTOR2I m_startSnapPoint
Definition: pns_tool_base.h:69
int InlineDrag(const TOOL_EVENT &aEvent)
void CommitRouting()
Definition: pns_router.cpp:422
SELECTION_TOOL.
void setTransitions() override
This method is meant to be overridden in order to specify handlers for events.
NETCLASS * GetNetClass() const
Function GetNetClassPtr returns the NETCLASS for this item.
PCB_DRAW_PANEL_GAL * GetCanvas() const override
Return a pointer to GAL-based canvas of given EDA draw frame.
static TOOL_ACTION dragFreeAngle
Definition: pcb_actions.h:133
Tool is invoked after being inactive.
Definition: tool_base.h:81
TOOL_MANAGER * m_toolMgr
Definition: tool_base.h:219
void UseCustomDiffPairDimensions(bool aEnabled)
Function UseCustomDiffPairDimensions Enables/disables custom differential pair dimensions.
static LSET AllNonCuMask()
Function AllNonCuMask returns a mask holding all layer minus CU layers.
Definition: lset.cpp:735
static TOOL_ACTION cancelInteractive
Definition: actions.h:65
virtual void PushTool(const std::string &actionName)
NB: the definition of "tool" is different at the user level.
SIZES_SETTINGS m_savedSizes
Stores sizes settings between router invocations.
Definition: pns_tool_base.h:66
void SyncWorld()
Definition: pns_router.cpp:96
bool IsPlacingVia() const
Definition: pns_router.cpp:531
void ToggleRounded()
Definition: pns_router.cpp:540
Microvia
Definition: router_tool.cpp:71
bool IsKeyPressed() const
Definition: tool_event.h:352
bool RunAction(const std::string &aActionName, bool aNow=false, T aParam=NULL)
Function RunAction() Runs the specified action.
Definition: tool_manager.h:140
class ARC, an arc track segment on a copper layer
Definition: typeinfo.h:98
bool Overlaps(const LAYER_RANGE &aOther) const
Definition: pns_layerset.h:68
static TOOL_ACTION routerHighlightMode
Actions to enable switching modes via hotkey assignments.
Definition: pcb_actions.h:189
void PrimeTool(const VECTOR2D &aPosition)
Function PrimeTool() "Primes" a tool by sending a cursor left-click event with the mouse position set...
static TOOL_ACTION trackViaSizeChanged
Definition: pcb_actions.h:282
BOARD_DESIGN_SETTINGS & GetDesignSettings() const
Function GetDesignSettings.
Definition: class_board.h:551
static TOOL_ACTION drag45Degree
Definition: pcb_actions.h:132
static const TOOL_ACTION ACT_SwitchPosture("pcbnew.InteractiveRouter.SwitchPosture", AS_CONTEXT, '/', LEGACY_HK_NAME("Switch Track Posture"), _("Switch Track Posture"), _("Switches posture of the currently routed track."), change_entry_orient_xpm)
virtual void SetCursorPosition(const VECTOR2D &aPosition, bool aWarpView=true, bool aTriggeredByArrows=false, long aArrowCommand=0)=0
Moves cursor to the requested position expressed in world coordinates.
TRACK_WIDTH_MENU(PCB_EDIT_FRAME &aFrame)
static const TOOL_ACTION ACT_SwitchRounding("pcbnew.InteractiveRouter.SwitchRounding", AS_CONTEXT, 0, LEGACY_HK_NAME("Switch Corner Rounding"), _("Switch Corner Rounding"), _("Switches the corner type of the currently routed track."), switch_corner_rounding_shape_xpm)
void UndoRedoBlock(bool aBlock=true)
Function UndoRedoBlock Enables/disable undo and redo operations.
void SetViaDrill(int aDrill)
void SetContextMenu(ACTION_MENU *aMenu, CONTEXT_MENU_TRIGGER aTrigger=CMENU_BUTTON)
Function SetContextMenu()
SIZES_SETTINGS & Sizes()
Definition: pns_router.h:218
bool SetCurrentNetClass(const wxString &aNetClassName)
Function SetCurrentNetClass Must be called after a netclass selection (or after a netclass parameter ...
bool Init() override
Function Init() Init() is called once upon a registration of the tool.
void SwitchLayer(int layer)
Definition: pns_router.cpp:468
int CountType(KICAD_T aType)
Function CountType counts the number of items matching aType.
Definition: collector.h:216
void breakTrack()
LSEQ Seq(const PCB_LAYER_ID *aWishListSequence, unsigned aCount) const
Function Seq returns an LSEQ from the union of this LSET and a desired sequence.
Definition: lset.cpp:377
static TOOL_ACTION layerInner3
Definition: pcb_actions.h:237
BOARD_CONNECTED_ITEM is a base class derived from BOARD_ITEM for items that can be connected and have...
void Add(const LINE &aLine)
Definition: pns_itemset.cpp:32
ROUTER_TOOL_MENU(PCB_EDIT_FRAME &aFrame, PNS::ROUTER_MODE aMode)
static TOOL_ACTION layerInner24
Definition: pcb_actions.h:258
void Go(int(T::*aStateFunc)(const TOOL_EVENT &), const TOOL_EVENT_LIST &aConditions=TOOL_EVENT(TC_ANY, TA_ANY))
Function Go()
int ChangeRouterMode(const TOOL_EVENT &aEvent)
void SetOrthoMode(bool aEnable)
Definition: pns_router.cpp:546
Struct DIFF_PAIR_DIMENSION is a small helper container to handle a stock of specific differential pai...
static TOOL_ACTION layerInner11
Definition: pcb_actions.h:245
const VECTOR2I snapToItem(bool aEnabled, ITEM *aItem, VECTOR2I aP)
static const TOOL_ACTION ACT_EndTrack("pcbnew.InteractiveRouter.EndTrack", AS_CONTEXT, WXK_END, "", _("Finish Track"), _("Stops laying the current track."), checked_ok_xpm)
void ToggleViaPlacement()
Definition: pns_router.cpp:481
class TRACK, a track segment (segment on a copper layer)
Definition: typeinfo.h:96
void handleCommonEvents(const TOOL_EVENT &evt)
const BITMAP_OPAQUE via_microvia_xpm[1]
GRID_MENU m_gridMenu
This file contains miscellaneous commonly used macros and functions.
bool IsAction(const TOOL_ACTION *aAction) const
Function IsAction() Tests if the event contains an action issued upon activation of the given TOOL_AC...
Definition: tool_event.cpp:67
void ClearWorld()
Definition: pns_router.cpp:105
static TOOL_ACTION layerTop
Definition: pcb_actions.h:234
int Start() const
Definition: pns_layerset.h:83
void Append(EDA_ITEM *item)
Function Append adds an item to the end of the list.
Definition: collector.h:119
PCB_BASE_EDIT_FRAME * frame() const
void UndoLastSegment()
Definition: pns_router.cpp:413
virtual PCB_LAYER_ID GetActiveLayer() const
virtual void updateStartItem(const TOOL_EVENT &aEvent, bool aIgnorePads=false)
static TOOL_ACTION layerInner23
Definition: pcb_actions.h:257
void SetViaSizeIndex(unsigned aIndex)
Function SetViaSizeIndex sets the current via size list index to aIndex.
int onViaCommand(const TOOL_EVENT &aEvent)
static VIATYPE getViaTypeFromFlags(int aFlags)
TOOL_MANAGER.
Definition: tool_manager.h:51
int GetCount() const
Function GetCount returns the number of objects in the list.
Definition: collector.h:100
virtual void Reset(RESET_REASON aReason)=0
Function Reset() Brings the tool to a known, initial state.
class MODULE, a footprint
Definition: typeinfo.h:89
ACTION_MENU * create() const override
Returns an instance of this class. It has to be overridden in inheriting classes.
virtual void updateEndItem(const TOOL_EVENT &aEvent)
bool prepareInteractive()
void SetAuxAxes(bool aEnable, const VECTOR2I &aOrigin=VECTOR2I(0, 0))
PCB_LAYER_ID
A quick note on layer IDs:
static TOOL_ACTION routerSettingsDialog
Activation of the Push and Shove settings dialogs.
Definition: pcb_actions.h:185
#define _(s)
LSET is a set of PCB_LAYER_IDs.
static TOOL_ACTION layerInner13
Definition: pcb_actions.h:247
const PCBNEW_SELECTION & selection() const
void performRouting()
void BreakSegment(ITEM *aItem, const VECTOR2I &aP)
Definition: pns_router.cpp:567
static TOOL_ACTION layerPrev
Definition: pcb_actions.h:267
static const TOOL_ACTION ACT_AutoEndRoute("pcbnew.InteractiveRouter.AutoEndRoute", AS_CONTEXT, 'F', "", _("Auto-finish Track"), _("Automagically finishes laying the current track."))
const BITMAP_OPAQUE select_w_layer_xpm[1]
static const TOOL_ACTION ACT_UndoLastSegment("pcbnew.InteractiveRouter.UndoLastSegment", AS_CONTEXT, WXK_BACK, "", _("Undo last segment"), _("Stops laying the current track."), checked_ok_xpm)
static const char Default[]
the name of the default NETCLASS
Definition: netclass.h:80
static PCB_LAYER_ID getTargetLayerFromEvent(const TOOL_EVENT &aEvent)
void update() override
Update menu state stub.
unsigned GetViaSizeIndex() const
Function GetViaSizeIndex.
virtual void PopTool(const std::string &actionName)
static TOOL_ACTION layerInner25
Definition: pcb_actions.h:259
int Net() const
Definition: pns_item.h:149
static const TOOL_ACTION ACT_CustomTrackWidth("pcbnew.InteractiveRouter.CustomTrackViaSize", AS_CONTEXT, 'Q', LEGACY_HK_NAME("Custom Track/Via Size"), _("Custom Track/Via Size..."), _("Shows a dialog for changing the track width and via size."), width_track_xpm)
static TOOL_ACTION layerInner18
Definition: pcb_actions.h:252
T Parameter() const
Function Parameter() Returns a non-standard parameter assigned to the event.
Definition: tool_event.h:435
virtual int GetTopLayer() const
Definition: view.cpp:851
void SetCustomDiffPairWidth(int aWidth)
Function SetCustomDiffPairWidth Sets custom track width for differential pairs (i....
void SetIcon(const BITMAP_OPAQUE *aIcon)
Function SetIcon() Assigns an icon for the entry.
Definition: action_menu.cpp:70
TOOL_EVENT.
Definition: tool_event.h:171
VIATYPE
Definition: class_track.h:68
PNS::ROUTER_MODE m_mode
ITEM * m_startItem
Definition: pns_tool_base.h:67
bool FixRoute(const VECTOR2I &aP, ITEM *aItem, bool aForceFinish=false)
Definition: pns_router.cpp:391
OPT_TOOL_EVENT eventHandler(const wxMenuEvent &aEvent) override
Event handler stub.
unsigned GetTrackWidthIndex() const
Function GetTrackWidthIndex.
DIFF_PAIR_MENU(PCB_EDIT_FRAME &aFrame)
static TOOL_ACTION layerInner30
Definition: pcb_actions.h:264
ZOOM_MENU m_zoomMenu
static TOOL_ACTION layerInner29
Definition: pcb_actions.h:263
void Init(BOARD *aBoard, ITEM *aStartItem=NULL, int aNet=-1)
unsigned STATUS_FLAGS
Definition: base_struct.h:152
ROUTER * m_router
Definition: pns_tool_base.h:77
bool CanInlineDrag()
PNS_MODE Mode() const
Returns the routing mode.
VIEW_CONTROLS is an interface for classes handling user events controlling the view behaviour (such a...
PCB_LAYER_ID m_Route_Layer_BOTTOM
Definition: pcb_screen.h:46
void switchLayerOnViaPlacement()
PCB_EDIT_FRAME & m_frame
static TOOL_ACTION layerInner10
Definition: pcb_actions.h:244
virtual void ForceCursorPosition(bool aEnabled, const VECTOR2D &aPosition=VECTOR2D(0, 0))
Function ForceCursorPosition() Places the cursor immediately at a given point.
PCB_LAYER_WIDGET * GetLayerManager()
bool m_BlindBuriedViaAllowed
true to allow blind/buried vias
int SettingsDialog(const TOOL_EVENT &aEvent)
void SetDiffPairIndex(unsigned aIndex)
Function SetDiffPairIndex.
static const TOOL_ACTION ACT_SelLayerAndPlaceThroughVia("pcbnew.InteractiveRouter.SelLayerAndPlaceVia", AS_CONTEXT, '<', LEGACY_HK_NAME("Select Layer and Add Through Via"), _("Select Layer and Place Through Via..."), _("Select a layer, then add a through-hole via at the end of currently routed track."), select_w_layer_xpm, AF_NONE,(void *)(VIA_ACTION_FLAGS::VIA|VIA_ACTION_FLAGS::SELECT_LAYER))
int CustomTrackWidthDialog(const TOOL_EVENT &aEvent)
virtual void SetActiveLayer(PCB_LAYER_ID aLayer)
void SetCustomDiffPairGap(int aGap)
Function SetCustomDiffPairGap Sets custom gap for differential pairs (i.e.
void ImportCurrent(BOARD_DESIGN_SETTINGS &aSettings)
const BITMAP_OPAQUE via_buried_xpm[1]
Definition: via_buried.cpp:55
const BITMAP_OPAQUE switch_corner_rounding_shape_xpm[1]
static TOOL_ACTION routerWalkaroundMode
Definition: pcb_actions.h:191
void Move(const VECTOR2I &aP, ITEM *aItem)
Definition: pns_router.cpp:246
static TOOL_ACTION layerInner15
Definition: pcb_actions.h:249
const BITMAP_OPAQUE width_track_via_xpm[1]
int onTrackViaSizeChanged(const TOOL_EVENT &aEvent)
static TOOL_ACTION routerInlineDrag
Activation of the Push and Shove router (inline dragging mode)
Definition: pcb_actions.h:194
bool StartRouting(const VECTOR2I &aP, ITEM *aItem, int aLayer)
Definition: pns_router.cpp:191
static TOOL_ACTION layerInner28
Definition: pcb_actions.h:262
LSEQ is a sequence (and therefore also a set) of PCB_LAYER_IDs.
KIGFX::VIEW * getView() const
Function getView()
Definition: tool_base.cpp:36
virtual void SetAutoPan(bool aEnabled)
Function SetAutoPan Turns on/off auto panning (this feature is used when there is a tool active (eg.
static TOOL_ACTION layerInner27
Definition: pcb_actions.h:261
void SetViaType(VIATYPE aViaType)
Pad object description.
bool Empty() const
Checks if there is anything selected.
Definition: selection.h:121
static TOOL_ACTION inlineBreakTrack
Breaks track when router is not activated.
Definition: pcb_actions.h:130
ACTION_MENU * create() const override
Returns an instance of this class. It has to be overridden in inheriting classes.
static TOOL_ACTION layerInner17
Definition: pcb_actions.h:251
static TOOL_ACTION breakTrack
Break a single track into two segments at the cursor.
Definition: pcb_actions.h:127
static TOOL_ACTION layerInner20
Definition: pcb_actions.h:254
void StopRouting()
Definition: pns_router.cpp:431
virtual void highlightNet(bool aEnabled, int aNetcode=-1)
static const TOOL_ACTION ACT_PlaceThroughVia("pcbnew.InteractiveRouter.PlaceVia", AS_CONTEXT, 'V', LEGACY_HK_NAME("Add Through Via"), _("Place Through Via"), _("Adds a through-hole via at the end of currently routed track."), via_xpm, AF_NONE,(void *) VIA_ACTION_FLAGS::VIA)
void Reset(RESET_REASON aReason) override
Function Reset() Brings the tool to a known, initial state.
wxString MessageTextFromValue(EDA_UNITS aUnits, int aValue, bool aUseMils, EDA_DATA_TYPE aType)
Definition: base_units.cpp:124
ACTION_MENU * create() const override
Returns an instance of this class. It has to be overridden in inheriting classes.
OPT< std::string > GetCommandStr() const
Definition: tool_event.h:463
ROUTER_MODE
Definition: pns_router.h:67
PCB_EDIT_FRAME & m_frame
static TOOL_ACTION layerInner22
Definition: pcb_actions.h:256
int GetCurrentViaSize() const
Function GetCurrentViaSize.
static TOOL_ACTION layerChanged
Definition: pcb_actions.h:272
void UpdateSizes(const SIZES_SETTINGS &aSizes)
Applies stored settings.
Definition: pns_router.cpp:332
void SetTitle(const wxString &aTitle) override
Function SetTitle() Sets title for the menu.
Definition: action_menu.cpp:88
bool PassEvent() const
These give a tool a method of informing the TOOL_MANAGER that a particular event should be passed on ...
Definition: tool_event.h:255
KIGFX::VIEW_CONTROLS * controls() const
void SetMode(ROUTER_MODE aMode)
Definition: pns_router.cpp:555
void update() override
Update menu state stub.
STATUS_FLAGS IsPointOnEnds(const wxPoint &point, int min_dist=0) const
Function IsPointOnEnds returns STARTPOINT if point if near (dist = min_dist) start point,...
static TOOL_ACTION routeSingleTrack
Activation of the Push and Shove router.
Definition: pcb_actions.h:168
VECTOR2I m_endSnapPoint
Definition: pns_tool_base.h:73
Used when the right click button is pressed, or when the select tool is in effect.
Definition: collectors.h:240
TOOL_BASE.
Definition: tool_base.h:67
static TOOL_ACTION layerInner14
Definition: pcb_actions.h:248
TOOL_ACTION.
Definition: tool_action.h:46
static TOOL_ACTION layerInner9
Definition: pcb_actions.h:243
bool StartDragging(const VECTOR2I &aP, ITEM *aItem, int aDragMode=DM_ANY)
Definition: pns_router.cpp:131
#define ENDPOINT
ends. (Used to support dragging.)
Definition: base_struct.h:123
static void NeighboringSegmentFilter(const VECTOR2I &aPt, GENERAL_COLLECTOR &aCollector)
void performDragging(int aMode=PNS::DM_ANY)
bool OfKind(int aKindMask) const
Function OfKind()
Definition: pns_item.h:133
PCB_EDIT_FRAME is the main frame for Pcbnew.
void Clear()
Function Clear() Removes all the entries from the menu (as well as its title).
TOOL_EVENT MakeEvent() const
Function MakeEvent() Returns the event associated with the action (i.e.
Definition: tool_action.h:107
int Size() const
Returns the number of selected parts.
Definition: selection.h:127
bool IsLocked() const
Definition: pns_item.h:236
PCB_SCREEN * GetScreen() const override
Return a pointer to a BASE_SCREEN or one of its derivatives.
int InlineBreakTrack(const TOOL_EVENT &aEvent)
ITEM * FindItemByParent(const BOARD_CONNECTED_ITEM *aParent)
Definition: pns_node.cpp:1443
RESET_REASON
Determines the reason of reset for a tool
Definition: tool_base.h:79
static TOOL_ACTION layerInner16
Definition: pcb_actions.h:250
const wxPoint & GetEnd() const
Definition: class_track.h:115
std::vector< VIA_DIMENSION > m_ViasDimensionsList
boost::optional< T > OPT
Definition: optional.h:7
int ShowModal() override
Definition: confirm.cpp:95
bool IsCopperLayer(LAYER_NUM aLayerId)
Function IsCopperLayer tests whether a layer is a copper layer.
void Activate()
Function Activate() Runs the tool.
Implementing DIALOG_TRACK_VIA_SIZE_BASE.
int SelectCopperLayerPair(const TOOL_EVENT &aEvent)
Definition: sel_layer.cpp:261
static TOOL_ACTION layerInner4
Definition: pcb_actions.h:238
class VIA, a via (like a track segment on a copper layer)
Definition: typeinfo.h:97
unsigned GetDiffPairIndex() const
Function GetDiffPairIndex.
static const TOOL_ACTION ACT_PlaceBlindVia("pcbnew.InteractiveRouter.PlaceBlindVia", AS_CONTEXT, MD_ALT+MD_SHIFT+ 'V', LEGACY_HK_NAME("Add Blind/Buried Via"), _("Place Blind/Buried Via"), _("Adds a blind or buried via at the end of currently routed track."), via_buried_xpm, AF_NONE,(void *) VIA_ACTION_FLAGS::BLIND_VIA)
bool HasPosition() const
Returns if it this event has a valid position (true for mouse events and context-menu or hotkey-based...
Definition: tool_event.h:260
void AddLayerPair(int aL1, int aL2)
TOOL_MANAGER * GetToolManager() const
Return the MVC controller.
Definition: tools_holder.h:74
void DumpLog()
Definition: pns_router.cpp:508
bool m_MicroViasAllowed
true to allow micro vias
void SetLayerVisible(LAYER_NUM aLayer, bool isVisible)
Function SetLayerVisible sets aLayer visible or not.
BOARD * GetBoard() const
KIGFX::VIEW_CONTROLS * getViewControls() const
Function getViewControls()
Definition: tool_base.cpp:42
void FlipPosture()
Definition: pns_router.cpp:459
DIFF_PAIR_MENU m_diffPairMenu
const BITMAP_OPAQUE change_entry_orient_xpm[1]
bool RoutingInProgress() const
Definition: pns_router.cpp:117
int KeyCode() const
Definition: tool_event.h:347
static TOOL_ACTION layerInner19
Definition: pcb_actions.h:253
void SetViaDiameter(int aDiameter)
int getStartLayer(const PNS::ITEM *aItem)
TRACK_WIDTH_MENU m_trackViaMenu
static TOOL_ACTION layerInner1
Definition: pcb_actions.h:235
static TOOL_ACTION routerShoveMode
Definition: pcb_actions.h:190
NODE * GetWorld() const
Definition: pns_router.h:152
int GetCopperLayerCount() const
Function GetCopperLayerCount.
OPT< int > PairedLayer(int aLayerId)
const BITMAP_OPAQUE width_track_xpm[1]
Definition: width_track.cpp:39
PCB_LAYER_ID SelectLayer(PCB_LAYER_ID aDefaultLayer, LSET aNotAllowedLayersMask=LSET(), wxPoint aDlgPosition=wxDefaultPosition)
Install the dialog box for layer selection.
Definition: sel_layer.cpp:206
const BITMAP_OPAQUE via_xpm[1]
void SetActiveLayer(PCB_LAYER_ID aLayer) override
Function SetActiveLayer will change the currently active layer to aLayer and also update the PCB_LAYE...
ROUTING_SETTINGS & Settings()
Definition: pns_router.h:199
const BITMAP_OPAQUE checked_ok_xpm[1]
Definition: checked_ok.cpp:51
PCB_LAYER_ID ToLAYER_ID(int aLayer)
Definition: lset.cpp:849
VIA_ACTION_FLAGS
Flags used by via tool actions.
Definition: router_tool.cpp:62
const VECTOR2D Position() const
Returns mouse cursor position in world coordinates.
Definition: tool_event.h:274
static TOOL_ACTION selectionCursor
Select a single item under the cursor position.
Definition: pcb_actions.h:59
EDA_UNITS GetUserUnits() const
Return the user units currently in use.
LAYER_RANGE.
Definition: pns_layerset.h:32
const LAYER_RANGE & Layers() const
Definition: pns_item.h:151
PCB_LAYER_ID m_Route_Layer_TOP
Definition: pcb_screen.h:45
void UseCustomTrackViaSize(bool aEnabled)
Function UseCustomTrackViaSize Enables/disables custom track/via size settings.
VECTOR2D GetCursorPosition() const
Returns the current cursor position in world coordinates.
EDA_ITEM * Front() const
Definition: selection.h:184
static TOOL_ACTION layerInner12
Definition: pcb_actions.h:246
static const TOOL_ACTION ACT_SelLayerAndPlaceBlindVia("pcbnew.InteractiveRouter.SelLayerAndPlaceBlindVia", AS_CONTEXT, MD_ALT+'<', LEGACY_HK_NAME("Select Layer and Add Blind/Buried Via"), _("Select Layer and Place Blind/Buried Via..."), _("Select a layer, then add a blind or buried via at the end of currently routed track."), select_w_layer_xpm, AF_NONE,(void *)(VIA_ACTION_FLAGS::BLIND_VIA|VIA_ACTION_FLAGS::SELECT_LAYER))
OPT< TOOL_EVENT > OPT_TOOL_EVENT
Definition: tool_event.h:556
KICAD_T Type() const
Function Type()
Definition: base_struct.h:193
BOARD_DESIGN_SETTINGS contains design settings for a BOARD object.
#define STARTPOINT
When a line is selected, these flags indicate which.
Definition: base_struct.h:122
static TOOL_ACTION layerToggle
Definition: pcb_actions.h:270
int GetCurrentLayer() const
Definition: pns_router.cpp:500
static TOOL_ACTION routeDiffPair
Activation of the Push and Shove router (differential pair mode)
Definition: pcb_actions.h:171