KiCad PCB EDA Suite
Loading...
Searching...
No Matches
board_editor_control.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) 2014 CERN
5 * Copyright The KiCad Developers, see AUTHORS.txt for contributors.
6 * @author Maciej Suminski <[email protected]>
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, see <https://www.gnu.org/licenses/>.
20 */
21
23
24#include <algorithm>
25#include <climits>
26#include <functional>
27#include <memory>
28
29#include <pgm_base.h>
30#include <executable_names.h>
31#include <advanced_config.h>
32#include <bitmaps.h>
33#include <gestfich.h>
34#include <pcb_painter.h>
35#include <board.h>
36#include <board_commit.h>
38#include <collectors.h>
40#include <pcb_generator.h>
41#include <footprint.h>
42#include <pad.h>
43#include <pcb_target.h>
44#include <pcb_track.h>
45#include <zone.h>
46#include <pcb_marker.h>
47#include <confirm.h>
51#include <dialog_plot.h>
54#include <kiface_base.h>
55#include <kiway.h>
57#include <origin_viewitem.h>
58#include <pcb_edit_frame.h>
59#include <pcbnew_id.h>
60#include <project.h>
61#include <project/project_file.h> // LAST_PATH_TYPE
63#include <kiplatform/ui.h>
64#include <pcbnew_settings.h>
65#include <tool/tool_manager.h>
66#include <tool/tool_event.h>
67#include <tools/drawing_tool.h>
68#include <tools/pcb_actions.h>
73#include <tools/edit_tool.h>
76#include <richio.h>
77#include <router/router_tool.h>
78#include <view/view_controls.h>
79#include <view/view_group.h>
83#include <wx/filedlg.h>
84#include <wx/msgdlg.h>
85#include <wx/log.h>
86
88
89using namespace std::placeholders;
90
91
92namespace
93{
94
95using ZonePriorityMap = std::map<unsigned, std::vector<ZONE*>>;
96
97
98std::vector<ZONE*> getOverlappingZones( BOARD* aBoard, ZONE* aZone )
99{
100 std::vector<ZONE*> overlapping;
101 BOX2I bbox = aZone->GetBoundingBox();
102
103 for( ZONE* candidate : aBoard->Zones() )
104 {
105 if( candidate == aZone )
106 continue;
107
108 if( candidate->GetIsRuleArea() || candidate->IsTeardropArea() )
109 continue;
110
111 if( !( candidate->GetLayerSet() & aZone->GetLayerSet() ).any() )
112 continue;
113
114 if( !candidate->GetBoundingBox().Intersects( bbox ) )
115 continue;
116
117 // Check edge collision and containment (one zone entirely inside another)
118 SHAPE_POLY_SET aOutline = aZone->GetBoardOutline();
119 SHAPE_POLY_SET candidateOutline = candidate->GetBoardOutline();
120
121 if( aOutline.Collide( &candidateOutline )
122 || ( candidateOutline.TotalVertices() > 0 && aOutline.Contains( candidateOutline.CVertex( 0 ) ) )
123 || ( aOutline.TotalVertices() > 0 && candidateOutline.Contains( aOutline.CVertex( 0 ) ) ) )
124 {
125 overlapping.push_back( candidate );
126 }
127 }
128
129 return overlapping;
130}
131
132
133ZonePriorityMap buildPriorityMap( BOARD* aBoard, ZONE* aExclude )
134{
135 ZonePriorityMap byPriority;
136
137 for( ZONE* z : aBoard->Zones() )
138 {
139 if( z == aExclude || z->GetIsRuleArea() || z->IsTeardropArea() )
140 continue;
141
142 byPriority[z->GetAssignedPriority()].push_back( z );
143 }
144
145 return byPriority;
146}
147
148
161std::vector<ZONE*> findCascadeZones( const ZonePriorityMap& aByPriority,
162 unsigned aFromPriority, bool aCascadeUp,
163 bool& aViable )
164{
165 std::vector<ZONE*> result;
166 unsigned p = aFromPriority;
167 aViable = true;
168
169 for( auto it = aByPriority.find( p ); it != aByPriority.end();
170 it = aByPriority.find( p ) )
171 {
172 for( ZONE* z : it->second )
173 result.push_back( z );
174
175 if( aCascadeUp )
176 {
177 if( p == UINT_MAX )
178 {
179 aViable = false;
180 break;
181 }
182
183 p++;
184 }
185 else
186 {
187 if( p == 0 )
188 {
189 aViable = false;
190 break;
191 }
192
193 p--;
194 }
195 }
196
197 return result;
198}
199
200} // anonymous namespace
201
202
204{
205public:
217
218protected:
219 ACTION_MENU* create() const override
220 {
221 return new ZONE_PRIORITY_CONTEXT_MENU();
222 }
223
224 void update() override
225 {
227
228 if( !selTool )
229 return;
230
231 const PCB_SELECTION& selection = selTool->GetSelection();
232 bool canRaise = false;
233 bool canLower = false;
234
235 if( selection.Size() == 1 )
236 {
237 ZONE* zone = dynamic_cast<ZONE*>( selection[0] );
238
239 if( zone && !zone->GetIsRuleArea() && !zone->IsTeardropArea() )
240 {
241 BOARD* board = zone->GetBoard();
242 std::vector<ZONE*> overlapping = getOverlappingZones( board, zone );
243
244 for( ZONE* other : overlapping )
245 {
246 if( other->GetAssignedPriority() > zone->GetAssignedPriority() )
247 canRaise = true;
248
249 if( other->GetAssignedPriority() < zone->GetAssignedPriority() )
250 canLower = true;
251 }
252 }
253 }
254
255 Enable( PCB_ACTIONS::zonePriorityMoveToTop.GetUIId(), canRaise );
256 Enable( PCB_ACTIONS::zonePriorityRaise.GetUIId(), canRaise );
257 Enable( PCB_ACTIONS::zonePriorityLower.GetUIId(), canLower );
258 Enable( PCB_ACTIONS::zonePriorityMoveToBottom.GetUIId(), canLower );
259 }
260};
261
262
264{
265public:
267 ACTION_MENU( true )
268 {
270 SetTitle( _( "Zones" ) );
271
276
277 AppendSeparator();
278
283
284 AppendSeparator();
285
287
288 AppendSeparator();
289
291 }
292
293protected:
294 ACTION_MENU* create() const override
295 {
296 return new ZONE_CONTEXT_MENU();
297 }
298};
299
300
302{
303public:
314
315 ACTION_MENU* create() const override
316 {
317 return new LOCK_CONTEXT_MENU( this->m_tool );
318 }
319};
320
321
323 PCB_TOOL_BASE( "pcbnew.EditorControl" ),
324 m_frame( nullptr ),
325 m_inPlaceFootprint( false ),
326 m_placingFootprint( false )
327{
328 m_placeOrigin = std::make_unique<KIGFX::ORIGIN_VIEWITEM>( KIGFX::COLOR4D( 0.8, 0.0, 0.0, 1.0 ),
330}
331
332
336
337
339{
341
342 if( aReason == MODEL_RELOAD || aReason == GAL_SWITCH || aReason == REDRAW )
343 {
344 m_placeOrigin->SetPosition( getModel<BOARD>()->GetDesignSettings().GetAuxOrigin() );
345 getView()->Remove( m_placeOrigin.get() );
346 getView()->Add( m_placeOrigin.get() );
347 }
348}
349
350// Update left-toolbar Line modes group icon based on current settings
352{
354
355 if( !f )
356 return 0;
357
358 LEADER_MODE mode = GetAppSettings<PCBNEW_SETTINGS>( "pcbnew" )->m_AngleSnapMode;
359
360 switch( mode )
361 {
364 default:
366 }
367
368 return 0;
369}
370
372{
373 LEADER_MODE mode = aEvent.Parameter<LEADER_MODE>();
374 GetAppSettings<PCBNEW_SETTINGS>( "pcbnew" )->m_AngleSnapMode = mode;
375 m_toolMgr->PostAction( ACTIONS::refreshPreview );
377 return 0;
378}
379
380
382{
383 auto activeToolCondition =
384 [this]( const SELECTION& aSel )
385 {
386 return ( !m_frame->ToolStackIsEmpty() );
387 };
388
389 auto inactiveStateCondition =
390 [this]( const SELECTION& aSel )
391 {
392 return ( m_frame->ToolStackIsEmpty() && aSel.Size() == 0 );
393 };
394
395 auto placeModuleCondition =
396 [this]( const SELECTION& aSel )
397 {
398 return m_frame->IsCurrentTool( PCB_ACTIONS::placeFootprint ) && aSel.GetSize() == 0;
399 };
400
401 auto& ctxMenu = m_menu->GetMenu();
402
403 // "Cancel" goes at the top of the context menu when a tool is active
404 ctxMenu.AddItem( ACTIONS::cancelInteractive, activeToolCondition, 1 );
405 ctxMenu.AddSeparator( 1 );
406
407 // "Get and Place Footprint" should be available for Place Footprint tool
408 ctxMenu.AddItem( PCB_ACTIONS::getAndPlace, placeModuleCondition, 1000 );
409 ctxMenu.AddSeparator( 1000 );
410
411 // Finally, add the standard zoom & grid items
412 getEditFrame<PCB_BASE_FRAME>()->AddStandardSubMenus( *m_menu.get() );
413
414 std::shared_ptr<ZONE_CONTEXT_MENU> zoneMenu = std::make_shared<ZONE_CONTEXT_MENU>();
415 zoneMenu->SetTool( this );
416
417 std::shared_ptr<LOCK_CONTEXT_MENU> lockMenu = std::make_shared<LOCK_CONTEXT_MENU>( this );
418
419 // Add the PCB control menus to relevant other tools
420
421 PCB_SELECTION_TOOL* selTool = m_toolMgr->GetTool<PCB_SELECTION_TOOL>();
422
423 if( selTool )
424 {
425 TOOL_MENU& toolMenu = selTool->GetToolMenu();
426 CONDITIONAL_MENU& menu = toolMenu.GetMenu();
427
428 // Add "Get and Place Footprint" when Selection tool is in an inactive state
429 menu.AddItem( PCB_ACTIONS::getAndPlace, inactiveStateCondition );
430 menu.AddSeparator();
431
432 toolMenu.RegisterSubMenu( zoneMenu );
433 toolMenu.RegisterSubMenu( lockMenu );
434
435 menu.AddMenu( lockMenu.get(), SELECTION_CONDITIONS::NotEmpty, 100 );
436
437 menu.AddMenu( zoneMenu.get(), SELECTION_CONDITIONS::OnlyTypes( { PCB_ZONE_T } ), 100 );
438 }
439
440 DRAWING_TOOL* drawingTool = m_toolMgr->GetTool<DRAWING_TOOL>();
441
442 if( drawingTool )
443 {
444 TOOL_MENU& toolMenu = drawingTool->GetToolMenu();
445 CONDITIONAL_MENU& menu = toolMenu.GetMenu();
446
447 toolMenu.RegisterSubMenu( zoneMenu );
448
449 // Functor to say if the PCB_EDIT_FRAME is in a given mode
450 // Capture the tool pointer and tool mode by value
451 auto toolActiveFunctor =
452 [=]( DRAWING_TOOL::MODE aMode )
453 {
454 return [=]( const SELECTION& sel )
455 {
456 return drawingTool->GetDrawingMode() == aMode;
457 };
458 };
459
460 menu.AddMenu( zoneMenu.get(), toolActiveFunctor( DRAWING_TOOL::MODE::ZONE ), 300 );
461 }
462
463 // Ensure the left toolbar's Line modes group reflects the current setting at startup
464 if( m_toolMgr )
466
467 return true;
468}
469
470
472{
473 wxWindow* focus = wxWindow::FindFocus();
474
475 if( focus )
476 {
477 wxWindow* topLevel = focus;
478
479 while( topLevel && !topLevel->IsTopLevel() )
480 topLevel = topLevel->GetParent();
481
482 RULE_EDITOR_DIALOG_BASE* reDlg = dynamic_cast<RULE_EDITOR_DIALOG_BASE*>( topLevel );
483
484 if( reDlg )
485 {
486 wxCommandEvent evt;
487 reDlg->OnSave( evt );
488 return 0;
489 }
490 }
491
492 m_frame->SaveBoard();
493 return 0;
494}
495
496
498{
499 m_frame->SaveBoard( true );
500 return 0;
501}
502
503
505{
506 m_frame->SaveBoard( true, true );
507 return 0;
508}
509
510
512{
513 m_frame->ExportFootprintsToLibrary( false );
514 return 0;
515}
516
517
519{
520 PICKED_ITEMS_LIST undoCmd;
522 ITEM_PICKER wrapper( nullptr, undoItem, UNDO_REDO::PAGESETTINGS );
523
524 undoCmd.PushItem( wrapper );
525 undoCmd.SetDescription( _( "Page Settings" ) );
526 m_frame->SaveCopyInUndoList( undoCmd, UNDO_REDO::PAGESETTINGS );
527
528 DIALOG_PAGES_SETTINGS dlg( m_frame, m_frame->GetBoard()->GetEmbeddedFiles(), pcbIUScale.IU_PER_MILS,
531
532 if( dlg.ShowModal() == wxID_OK )
533 {
534 m_frame->GetCanvas()->GetView()->UpdateAllItemsConditionally(
535 [&]( KIGFX::VIEW_ITEM* aItem ) -> int
536 {
537 EDA_TEXT* text = dynamic_cast<EDA_TEXT*>( aItem );
538
539 if( text && text->HasTextVars() )
540 {
541 text->ClearRenderCache();
542 text->ClearBoundingBoxCache();
544 }
545
546 return 0;
547 } );
548
549 m_frame->OnModify();
550 }
551 else
552 {
553 m_frame->RollbackFromUndo();
554 }
555
556 return 0;
557}
558
559
561{
562 DIALOG_PLOT dlg( m_frame );
563 dlg.ShowQuasiModal();
564 return 0;
565}
566
567
569{
570 m_frame->ToggleSearch();
571 return 0;
572}
573
574
576{
577 m_frame->ShowFindDialog();
578 return 0;
579}
580
581
583{
584 m_frame->FindNext( aEvent.IsAction( &ACTIONS::findPrevious ) );
585 return 0;
586}
587
588
590{
591 m_frame->ShowFindByPropertiesDialog();
592 return 0;
593}
594
595
597{
598 getEditFrame<PCB_EDIT_FRAME>()->ShowBoardSetupDialog();
599 return 0;
600}
601
602
604{
605 getEditFrame<PCB_EDIT_FRAME>()->InstallNetlistFrame();
606 return 0;
607}
608
609
611{
612 wxString fullFileName = frame()->GetBoard()->GetFileName();
613 wxString path;
614 wxString name;
615 wxString ext;
616
617 wxFileName::SplitPath( fullFileName, &path, &name, &ext );
618 name += wxT( "." ) + wxString( FILEEXT::SpecctraSessionFileExtension );
619
620 fullFileName = wxFileSelector( _( "Specctra Session File" ), path, name,
621 wxT( "." ) + wxString( FILEEXT::SpecctraSessionFileExtension ),
622 FILEEXT::SpecctraSessionFileWildcard(), wxFD_OPEN | wxFD_CHANGE_DIR,
623 frame() );
624
625 if( !fullFileName.IsEmpty() )
626 getEditFrame<PCB_EDIT_FRAME>()->ImportSpecctraSession( fullFileName );
627
628 return 0;
629}
630
631
633{
634 wxString fullFileName = m_frame->GetLastPath( LAST_PATH_SPECCTRADSN );
635 wxFileName fn;
636
637 if( fullFileName.IsEmpty() )
638 {
639 fn = m_frame->GetBoard()->GetFileName();
641 }
642 else
643 {
644 fn = fullFileName;
645 }
646
647 fullFileName = wxFileSelector( _( "Specctra DSN File" ), fn.GetPath(), fn.GetFullName(),
649 wxFD_SAVE | wxFD_OVERWRITE_PROMPT | wxFD_CHANGE_DIR, frame() );
650
651 if( !fullFileName.IsEmpty() )
652 {
653 m_frame->SetLastPath( LAST_PATH_SPECCTRADSN, fullFileName );
654 getEditFrame<PCB_EDIT_FRAME>()->ExportSpecctraFile( fullFileName );
655 }
656
657 return 0;
658}
659
660
662{
663 wxCHECK( m_frame, 0 );
664
665 wxFileName fn = m_frame->Prj().GetProjectFullName();
666
667 // Use a different file extension for the board netlist so the schematic netlist file
668 // is accidentally overwritten.
669 fn.SetExt( wxT( "pcb_net" ) );
670
671 wxFileDialog dlg( m_frame, _( "Export Board Netlist" ), fn.GetPath(), fn.GetFullName(),
672 _( "KiCad board netlist files" ) + AddFileExtListToFilter( { "pcb_net" } ),
673 wxFD_SAVE | wxFD_OVERWRITE_PROMPT );
674
675 dlg.SetExtraControlCreator( &LEGACYFILEDLG_NETLIST_OPTIONS::Create );
676
678
679 if( dlg.ShowModal() == wxID_CANCEL )
680 return 0;
681
682 fn = dlg.GetPath();
683
684 if( !fn.IsDirWritable() )
685 {
686 DisplayErrorMessage( m_frame, wxString::Format( _( "Insufficient permissions to folder '%s'." ),
687 fn.GetPath() ) );
688 return 0;
689 }
690
692 dynamic_cast<const LEGACYFILEDLG_NETLIST_OPTIONS*>( dlg.GetExtraControl() );
693 wxCHECK( noh, 0 );
694
696
697 for( const FOOTPRINT* footprint : board()->Footprints() )
698 {
699 COMPONENT* component = new COMPONENT( footprint->GetFPID(), footprint->GetReference(),
700 footprint->GetValue(), footprint->GetPath(),
701 { footprint->m_Uuid } );
702
703 for( const PAD* pad : footprint->Pads() )
704 {
705 const wxString& netname = pad->GetShortNetname();
706
707 if( !netname.IsEmpty() )
708 component->AddNet( pad->GetNumber(), netname, pad->GetPinFunction(), pad->GetPinType() );
709 }
710
711 nlohmann::ordered_map<wxString, wxString> fields;
712
713 for( PCB_FIELD* field : footprint->GetFields() )
714 {
715 wxCHECK2( field, continue );
716
717 fields[field->GetCanonicalName()] = field->GetText();
718 }
719
720 component->SetFields( fields );
721
722 netlist.AddComponent( component );
723 }
724
725 try
726 {
727 FILE_OUTPUTFORMATTER formatter( fn.GetFullPath() );
728
729 netlist.Format( "pcb_netlist", &formatter, 0, noh->GetNetlistOptions() );
730 formatter.Finish();
731 }
732 catch( const IO_ERROR& ioe )
733 {
734 DisplayErrorMessage( m_frame, wxString::Format( _( "Failed to export netlist to '%s': %s" ),
735 fn.GetFullPath(), ioe.What() ) );
736 }
737
738 return 0;
739}
740
741
743{
744 PCB_PLOT_PARAMS plotSettings = m_frame->GetPlotSettings();
745
746 plotSettings.SetFormat( PLOT_FORMAT::GERBER );
747
748 m_frame->SetPlotSettings( plotSettings );
749
750 DIALOG_PLOT dlg( m_frame );
751 dlg.ShowQuasiModal( );
752
753 return 0;
754}
755
756
758{
759 int errors = 0;
760 wxString details;
761 bool quiet = aEvent.Parameter<bool>();
762
763 int duplicates = board()->RepairDuplicateItemUuids();
764
765 if( duplicates )
766 {
767 errors += duplicates;
768 details += wxString::Format( _( "%d duplicate IDs replaced.\n" ), duplicates );
769 }
770
771 for( FOOTPRINT* footprint : board()->Footprints() )
772 {
773 for( PAD* pad : footprint->Pads() )
774 {
775 BOARD_CONNECTED_ITEM* cItem = pad;
776
777 if( cItem->GetNetCode() )
778 {
779 NETINFO_ITEM* netinfo = cItem->GetNet();
780
781 if( netinfo && !board()->FindNet( netinfo->GetNetname() ) )
782 {
783 board()->Add( netinfo );
784
785 details += wxString::Format( _( "Orphaned net %s re-parented.\n" ),
786 netinfo->GetNetname() );
787 errors++;
788 }
789 }
790 }
791 }
792
793 for( PCB_TRACK* track : board()->Tracks() )
794 {
795 BOARD_CONNECTED_ITEM* cItem = track;
796
797 if( cItem->GetNetCode() )
798 {
799 NETINFO_ITEM* netinfo = cItem->GetNet();
800
801 if( netinfo && !board()->FindNet( netinfo->GetNetname() ) )
802 {
803 board()->Add( netinfo );
804
805 details += wxString::Format( _( "Orphaned net %s re-parented.\n" ),
806 netinfo->GetNetname() );
807 errors++;
808 }
809 }
810 }
811
812 /*******************************
813 * Your test here
814 */
815
816 /*******************************
817 * Inform the user
818 */
819
820 if( errors )
821 {
822 m_frame->OnModify();
823
824 wxString msg = wxString::Format( _( "%d potential problems repaired." ), errors );
825
826 if( !quiet )
827 DisplayInfoMessage( m_frame, msg, details );
828 }
829 else if( !quiet )
830 {
831 DisplayInfoMessage( m_frame, _( "No board problems found." ) );
832 }
833
834 return 0;
835}
836
837
839{
841 bool fetched = false;
842
844 [&]()
845 {
846 fetched = m_frame->FetchNetlistFromSchematic(
847 netlist, _( "Updating PCB requires a fully annotated schematic." ) );
848 } );
849
850 if( fetched )
851 {
852 DIALOG_UPDATE_PCB updateDialog( m_frame, &netlist );
853 updateDialog.ShowModal();
854 }
855
856 return 0;
857}
858
860{
861 if( Kiface().IsSingle() )
862 {
863 DisplayErrorMessage( m_frame, _( "Cannot update schematic because Pcbnew is opened in "
864 "stand-alone mode. In order to create or update PCBs "
865 "from schematics, you must launch the KiCad project "
866 "manager and create a project." ) );
867 return 0;
868 }
869
872
873 KIWAY_PLAYER* frame = m_frame->Kiway().Player( FRAME_SCH, false );
874
875 if( frame )
876 {
877 std::string payload;
878
879 if( wxWindow* blocking_win = frame->Kiway().GetBlockingDialog() )
880 blocking_win->Close( true );
881
882 m_frame->Kiway().ExpressMail( FRAME_SCH, MAIL_SCH_UPDATE, payload, m_frame );
883 }
884 return 0;
885}
886
887
889{
890 wxString msg;
891 PCB_EDIT_FRAME* boardFrame = m_frame;
892 PROJECT& project = boardFrame->Prj();
893 wxFileName schematic( project.GetProjectPath(), project.GetProjectName(),
895
896 if( !schematic.FileExists() )
897 {
898 wxFileName legacySchematic( project.GetProjectPath(), project.GetProjectName(),
900
901 if( legacySchematic.FileExists() )
902 {
903 schematic = legacySchematic;
904 }
905 else
906 {
907 msg.Printf( _( "Schematic file '%s' not found." ), schematic.GetFullPath() );
909 return 0;
910 }
911 }
912
913 if( Kiface().IsSingle() )
914 {
915 ExecuteFile( EESCHEMA_EXE, schematic.GetFullPath() );
916 }
917 else
918 {
920 [&]()
921 {
922 KIWAY_PLAYER* frame = m_frame->Kiway().Player( FRAME_SCH, false );
923
924 // Please: note: DIALOG_EDIT_LIBENTRY_FIELDS_IN_LIB::initBuffers() calls
925 // Kiway.Player( FRAME_SCH, true )
926 // therefore, the schematic editor is sometimes running, but the schematic project
927 // is not loaded, if the library editor was called, and the dialog field editor was used.
928 // On Linux, it happens the first time the schematic editor is launched, if
929 // library editor was running, and the dialog field editor was open
930 // On Windows, it happens always after the library editor was called,
931 // and the dialog field editor was used
932 if( !frame )
933 {
934 try
935 {
936 frame = boardFrame->Kiway().Player( FRAME_SCH, true );
937 }
938 catch( const IO_ERROR& err )
939 {
940 DisplayErrorMessage( boardFrame,
941 _( "Eeschema failed to load." ) + wxS( "\n" ) + err.What() );
942 return;
943 }
944 }
945
946 wxEventBlocker blocker( boardFrame );
947
948 // If Kiway() cannot create the eeschema frame, it shows a error message, and
949 // frame is null
950 if( !frame )
951 return;
952
953 if( !frame->IsShownOnScreen() ) // the frame exists, (created by the dialog field editor)
954 // but no project loaded.
955 {
956 frame->OpenProjectFiles( std::vector<wxString>( 1, schematic.GetFullPath() ) );
957 frame->Show( true );
958 }
959
960 // On Windows, Raise() does not bring the window on screen, when iconized or not shown
961 // On Linux, Raise() brings the window on screen, but this code works fine
962 if( frame->IsIconized() )
963 {
964 frame->Iconize( false );
965
966 // If an iconized frame was created by Pcbnew, Iconize( false ) is not enough
967 // to show the frame at its normal size: Maximize should be called.
968 frame->Maximize( false );
969 }
970
971 frame->Raise();
972 } );
973 }
974
975 return 0;
976}
977
978
980{
981 getEditFrame<PCB_EDIT_FRAME>()->ToggleLayersManager();
982 return 0;
983}
984
985
987{
988 getEditFrame<PCB_EDIT_FRAME>()->ToggleProperties();
989 return 0;
990}
991
992
994{
995 getEditFrame<PCB_EDIT_FRAME>()->ToggleNetInspector();
996 return 0;
997}
998
999
1001{
1002 getEditFrame<PCB_EDIT_FRAME>()->ToggleLibraryTree();
1003 return 0;
1004}
1005
1006
1008{
1009 getEditFrame<PCB_EDIT_FRAME>()->ToggleSearch();
1010 return 0;
1011}
1012
1013
1014// Track & via size control
1016{
1017 BOARD_DESIGN_SETTINGS& bds = getModel<BOARD>()->GetDesignSettings();
1018 PCB_SELECTION& selection = m_toolMgr->GetTool<PCB_SELECTION_TOOL>()->GetSelection();
1019
1020 if( m_frame->ToolStackIsEmpty()
1021 && SELECTION_CONDITIONS::OnlyTypes( { PCB_TRACE_T, PCB_ARC_T, PCB_VIA_T } )( selection ) )
1022 {
1023 BOARD_COMMIT commit( this );
1024
1025 for( EDA_ITEM* item : selection )
1026 {
1027 if( item->IsType( { PCB_TRACE_T, PCB_ARC_T } ) )
1028 {
1029 PCB_TRACK* track = static_cast<PCB_TRACK*>( item );
1030
1031 for( int i = 0; i < (int) bds.m_TrackWidthList.size(); ++i )
1032 {
1033 int candidate = bds.m_NetSettings->GetDefaultNetclass()->GetTrackWidth();
1034
1035 if( i > 0 )
1036 candidate = bds.m_TrackWidthList[ i ];
1037
1038 if( candidate > track->GetWidth() )
1039 {
1040 commit.Modify( track );
1041 track->SetWidth( candidate );
1042 break;
1043 }
1044 }
1045 }
1046 }
1047
1048 commit.Push( _( "Increase Track Width" ) );
1049 return 0;
1050 }
1051
1052 ROUTER_TOOL* routerTool = m_toolMgr->GetTool<ROUTER_TOOL>();
1053
1054 if( routerTool && routerTool->IsToolActive()
1055 && routerTool->Router()->Mode() == PNS::PNS_MODE_ROUTE_DIFF_PAIR )
1056 {
1057 int widthIndex = bds.GetNextDiffPairIndex( bds.GetDiffPairIndex(), true );
1058
1059 bds.SetDiffPairIndex( widthIndex );
1060 bds.UseCustomDiffPairDimensions( false );
1061
1063 }
1064 else
1065 {
1066 // Issue #24644: stepping the index unconditionally lets the first press both enter the
1067 // connected-width override and advance into the list, instead of no-op'ing.
1068 if( routerTool && routerTool->IsToolActive()
1071 {
1072 bds.m_TempOverrideTrackWidth = true;
1073 }
1074
1076 bds.UseCustomTrackViaSize( false );
1077
1079 }
1080
1081 return 0;
1082}
1083
1084
1086{
1087 BOARD_DESIGN_SETTINGS& bds = getModel<BOARD>()->GetDesignSettings();
1088 PCB_SELECTION& selection = m_toolMgr->GetTool<PCB_SELECTION_TOOL>()->GetSelection();
1089
1090 if( m_frame->ToolStackIsEmpty()
1091 && SELECTION_CONDITIONS::OnlyTypes( { PCB_TRACE_T, PCB_ARC_T, PCB_VIA_T } )( selection ) )
1092 {
1093 BOARD_COMMIT commit( this );
1094
1095 for( EDA_ITEM* item : selection )
1096 {
1097 if( item->IsType( { PCB_TRACE_T, PCB_ARC_T } ) )
1098 {
1099 PCB_TRACK* track = static_cast<PCB_TRACK*>( item );
1100
1101 for( int i = (int) bds.m_TrackWidthList.size() - 1; i >= 0; --i )
1102 {
1103 int candidate = bds.m_NetSettings->GetDefaultNetclass()->GetTrackWidth();
1104
1105 if( i > 0 )
1106 candidate = bds.m_TrackWidthList[ i ];
1107
1108 if( candidate < track->GetWidth() )
1109 {
1110 commit.Modify( track );
1111 track->SetWidth( candidate );
1112 break;
1113 }
1114 }
1115 }
1116 }
1117
1118 commit.Push( _( "Decrease Track Width" ) );
1119 return 0;
1120 }
1121
1122 ROUTER_TOOL* routerTool = m_toolMgr->GetTool<ROUTER_TOOL>();
1123
1124 if( routerTool && routerTool->IsToolActive()
1125 && routerTool->Router()->Mode() == PNS::PNS_MODE_ROUTE_DIFF_PAIR )
1126 {
1127 int widthIndex = bds.GetNextDiffPairIndex( bds.GetDiffPairIndex(), false );
1128
1129 bds.SetDiffPairIndex( widthIndex );
1130 bds.UseCustomDiffPairDimensions( false );
1131
1133 }
1134 else
1135 {
1136 // Issue #24644: mirror TrackWidthInc so the first invocation also advances into the
1137 // predefined list instead of merely flipping the override flag.
1138 if( routerTool && routerTool->IsToolActive()
1141 {
1142 bds.m_TempOverrideTrackWidth = true;
1143 }
1144
1146 bds.UseCustomTrackViaSize( false );
1147
1149 }
1150
1151 return 0;
1152}
1153
1154
1156{
1157 BOARD_DESIGN_SETTINGS& bds = getModel<BOARD>()->GetDesignSettings();
1158 PCB_SELECTION& selection = m_toolMgr->GetTool<PCB_SELECTION_TOOL>()->GetSelection();
1159
1160 if( m_frame->ToolStackIsEmpty()
1161 && SELECTION_CONDITIONS::OnlyTypes( { PCB_TRACE_T, PCB_ARC_T, PCB_VIA_T } )( selection ) )
1162 {
1163 BOARD_COMMIT commit( this );
1164
1165 for( EDA_ITEM* item : selection )
1166 {
1167 if( item->Type() == PCB_VIA_T )
1168 {
1169 PCB_VIA* via = static_cast<PCB_VIA*>( item );
1170
1171 for( int i = 0; i < (int) bds.m_ViasDimensionsList.size(); ++i )
1172 {
1175
1176 if( i> 0 )
1177 dims = bds.m_ViasDimensionsList[ i ];
1178
1179 // TODO(JE) padstacks
1180 if( dims.m_Diameter > via->GetWidth( PADSTACK::ALL_LAYERS ) )
1181 {
1182 commit.Modify( via );
1183 via->SetWidth( PADSTACK::ALL_LAYERS, dims.m_Diameter );
1184 via->SetDrill( dims.m_Drill );
1185 break;
1186 }
1187 }
1188 }
1189 }
1190
1191 commit.Push( _( "Increase Via Size" ) );
1192 }
1193 else
1194 {
1195 int sizeIndex = bds.GetNextViaSizeIndex( bds.GetViaSizeIndex(), true );
1196
1197 bds.SetViaSizeIndex( sizeIndex );
1198 bds.UseCustomTrackViaSize( false );
1199
1201 }
1202
1203 return 0;
1204}
1205
1206
1208{
1209 BOARD_DESIGN_SETTINGS& bds = getModel<BOARD>()->GetDesignSettings();
1210 PCB_SELECTION& selection = m_toolMgr->GetTool<PCB_SELECTION_TOOL>()->GetSelection();
1211
1212 if( m_frame->ToolStackIsEmpty()
1213 && SELECTION_CONDITIONS::OnlyTypes( { PCB_TRACE_T, PCB_ARC_T, PCB_VIA_T } )( selection ) )
1214 {
1215 BOARD_COMMIT commit( this );
1216
1217 for( EDA_ITEM* item : selection )
1218 {
1219 if( item->Type() == PCB_VIA_T )
1220 {
1221 PCB_VIA* via = static_cast<PCB_VIA*>( item );
1222
1223 for( int i = (int) bds.m_ViasDimensionsList.size() - 1; i >= 0; --i )
1224 {
1227
1228 if( i > 0 )
1229 dims = bds.m_ViasDimensionsList[ i ];
1230
1231 // TODO(JE) padstacks
1232 if( dims.m_Diameter < via->GetWidth( PADSTACK::ALL_LAYERS ) )
1233 {
1234 commit.Modify( via );
1235 via->SetWidth( PADSTACK::ALL_LAYERS, dims.m_Diameter );
1236 via->SetDrill( dims.m_Drill );
1237 break;
1238 }
1239 }
1240 }
1241 }
1242
1243 commit.Push( "Decrease Via Size" );
1244 }
1245 else
1246 {
1247 int sizeIndex = 0; // Assume we only have a single via size entry
1248
1249 // If there are more, cycle through them backwards
1250 if( bds.m_ViasDimensionsList.size() > 0 )
1251 sizeIndex = bds.GetNextViaSizeIndex( bds.GetViaSizeIndex(), false );
1252
1253 bds.SetViaSizeIndex( sizeIndex );
1254 bds.UseCustomTrackViaSize( false );
1255
1257 }
1258
1259 return 0;
1260}
1261
1262
1264{
1265 BOARD_DESIGN_SETTINGS& bds = getModel<BOARD>()->GetDesignSettings();
1266
1267 if( bds.UseCustomTrackViaSize() )
1268 {
1269 bds.UseCustomTrackViaSize( false );
1270 bds.m_UseConnectedTrackWidth = true;
1271 }
1272 else
1273 {
1275 }
1276
1277 return 0;
1278}
1279
1280
1282{
1283 if( m_inPlaceFootprint )
1284 return 0;
1285
1287
1288 FOOTPRINT* fp = aEvent.Parameter<FOOTPRINT*>();
1289 bool fromOtherCommand = fp != nullptr;
1291 BOARD_COMMIT commit( m_frame );
1293 COMMON_SETTINGS* common_settings = Pgm().GetCommonSettings();
1294
1295 m_toolMgr->RunAction( ACTIONS::selectionClear );
1296
1297 TOOL_EVENT pushedEvent = aEvent;
1298 m_frame->PushTool( aEvent );
1299
1300 auto setCursor =
1301 [&]()
1302 {
1303 m_frame->GetCanvas()->SetCurrentCursor( KICURSOR::PENCIL );
1304 };
1305
1306 auto cleanup =
1307 [&] ()
1308 {
1309 m_toolMgr->RunAction( ACTIONS::selectionClear );
1310 commit.Revert();
1311
1312 if( fromOtherCommand )
1313 {
1314 PICKED_ITEMS_LIST* undo = m_frame->PopCommandFromUndoList();
1315
1316 if( undo )
1317 {
1318 m_frame->PutDataInPreviousState( undo );
1319 m_frame->ClearListAndDeleteItems( undo );
1320 delete undo;
1321 }
1322 }
1323
1324 fp = nullptr;
1325 m_placingFootprint = false;
1326 };
1327
1328 Activate();
1329 // Must be done after Activate() so that it gets set into the correct context
1330 controls->ShowCursor( true );
1331 // Set initial cursor
1332 setCursor();
1333
1334 VECTOR2I cursorPos = controls->GetCursorPosition();
1335 bool ignorePrimePosition = false;
1336 bool reselect = false;
1337
1338 // Prime the pump
1339 if( fp )
1340 {
1341 m_placingFootprint = true;
1342 fp->SetPosition( cursorPos );
1343 m_toolMgr->RunAction<EDA_ITEM*>( ACTIONS::selectItem, fp );
1344 m_toolMgr->PostAction( ACTIONS::refreshPreview );
1345 }
1346 else if( aEvent.HasPosition() )
1347 {
1348 m_toolMgr->PrimeTool( aEvent.Position() );
1349 }
1350 else if( common_settings->m_Input.immediate_actions && !aEvent.IsReactivate() )
1351 {
1352 m_toolMgr->PrimeTool( { 0, 0 } );
1353 ignorePrimePosition = true;
1354 }
1355
1356 // Main loop: keep receiving events
1357 while( TOOL_EVENT* evt = Wait() )
1358 {
1359 setCursor();
1360 cursorPos = controls->GetCursorPosition( !evt->DisableGridSnapping() );
1361
1362 if( reselect && fp )
1363 m_toolMgr->RunAction<EDA_ITEM*>( ACTIONS::selectItem, fp );
1364
1365 if( evt->IsCancelInteractive() || ( fp && evt->IsAction( &ACTIONS::undo ) ) )
1366 {
1367 if( fp )
1368 {
1369 cleanup();
1370 }
1371 else
1372 {
1373 m_frame->PopTool( pushedEvent );
1374 break;
1375 }
1376 }
1377 else if( evt->IsActivate() )
1378 {
1379 if( fp )
1380 cleanup();
1381
1382 if( evt->IsMoveTool() )
1383 {
1384 // leave ourselves on the stack so we come back after the move
1385 break;
1386 }
1387 else
1388 {
1389 frame()->PopTool( pushedEvent );
1390 break;
1391 }
1392 }
1393 else if( evt->IsClick( BUT_LEFT ) )
1394 {
1395 if( !fp )
1396 {
1397 // Pick the footprint to be placed
1398 fp = m_frame->SelectFootprintFromLibrary();
1399
1400 if( fp == nullptr )
1401 continue;
1402
1403 // If we started with a hotkey which has a position then warp back to that.
1404 // Otherwise update to the current mouse position pinned inside the autoscroll
1405 // boundaries.
1406 if( evt->IsPrime() && !ignorePrimePosition )
1407 {
1408 cursorPos = evt->Position();
1409 getViewControls()->WarpMouseCursor( cursorPos, true );
1410 }
1411 else
1412 {
1414 cursorPos = getViewControls()->GetMousePosition();
1415 }
1416
1417 m_placingFootprint = true;
1418
1419 fp->SetLink( niluuid );
1420
1421 fp->SetFlags( IS_NEW ); // whatever
1422
1423 // Set parent so that clearance can be loaded
1424 fp->SetParent( board );
1425 board->UpdateUserUnits( fp, m_frame->GetCanvas()->GetView() );
1426
1427 for( PAD* pad : fp->Pads() )
1428 {
1429 pad->SetLocalRatsnestVisible( m_frame->GetPcbNewSettings()->m_Display.m_ShowGlobalRatsnest );
1430
1431 // Pads in the library all have orphaned nets. Replace with Default.
1432 pad->SetNetCode( 0 );
1433 }
1434
1435 // Put it on FRONT layer,
1436 // (Can be stored flipped if the lib is an archive built from a board)
1437 if( fp->IsFlipped() )
1438 fp->Flip( fp->GetPosition(), m_frame->GetPcbNewSettings()->m_FlipDirection );
1439
1440 fp->SetOrientation( ANGLE_0 );
1441 fp->SetPosition( cursorPos );
1442
1443 commit.Add( fp );
1444 m_toolMgr->RunAction<EDA_ITEM*>( ACTIONS::selectItem, fp );
1445
1446 m_toolMgr->PostAction( ACTIONS::refreshPreview );
1447 }
1448 else
1449 {
1450 m_toolMgr->RunAction( ACTIONS::selectionClear );
1451 commit.Push( _( "Place Footprint" ) );
1452 fp = nullptr; // to indicate that there is no footprint that we currently modify
1453 m_placingFootprint = false;
1454 }
1455 }
1456 else if( evt->IsClick( BUT_RIGHT ) )
1457 {
1458 m_menu->ShowContextMenu( selection() );
1459 }
1460 else if( fp && ( evt->IsMotion() || evt->IsAction( &ACTIONS::refreshPreview ) ) )
1461 {
1462 fp->SetPosition( cursorPos );
1463 selection().SetReferencePoint( cursorPos );
1464 getView()->Update( &selection() );
1465 getView()->Update( fp );
1466 }
1467 else if( fp && evt->IsAction( &PCB_ACTIONS::properties ) )
1468 {
1469 // Calling 'Properties' action clears the selection, so we need to restore it
1470 reselect = true;
1471 }
1472 else if( fp && ( ZONE_FILLER_TOOL::IsZoneFillAction( evt )
1473 || evt->IsAction( &ACTIONS::redo ) ) )
1474 {
1475 wxBell();
1476 }
1477 else
1478 {
1479 evt->SetPassEvent();
1480 }
1481
1482 // Enable autopanning and cursor capture only when there is a footprint to be placed
1483 controls->SetAutoPan( fp != nullptr );
1484 controls->CaptureCursor( fp != nullptr );
1485 }
1486
1487 controls->SetAutoPan( false );
1488 controls->CaptureCursor( false );
1489 m_frame->GetCanvas()->SetCurrentCursor( KICURSOR::ARROW );
1490
1491 return 0;
1492}
1493
1494
1496{
1497 return modifyLockSelected( TOGGLE );
1498}
1499
1500
1502{
1503 return modifyLockSelected( ON );
1504}
1505
1506
1508{
1509 return modifyLockSelected( OFF );
1510}
1511
1512
1514{
1515 PCB_SELECTION_TOOL* selTool = m_toolMgr->GetTool<PCB_SELECTION_TOOL>();
1516
1517 // RequestSelection populates from the cursor when empty and marks it IsHover(), letting us
1518 // clear it afterwards without disturbing a pre-existing selection.
1519 const PCB_SELECTION& selection = selTool->RequestSelection( nullptr );
1520
1521 BOARD_COMMIT commit( m_frame );
1522
1523 if( selection.Empty() )
1524 return 0;
1525
1526 const bool isHover = selection.IsHover();
1527
1528 // Resolve TOGGLE mode
1529 if( aMode == TOGGLE )
1530 {
1531 aMode = ON;
1532
1533 for( EDA_ITEM* item : selection )
1534 {
1535 if( !item->IsBOARD_ITEM() )
1536 continue;
1537
1538 if( static_cast<BOARD_ITEM*>( item )->IsLocked() )
1539 {
1540 aMode = OFF;
1541 break;
1542 }
1543 }
1544 }
1545
1546 for( EDA_ITEM* item : selection )
1547 {
1548 if( !item->IsBOARD_ITEM() )
1549 continue;
1550
1551 BOARD_ITEM* const board_item = static_cast<BOARD_ITEM*>( item );
1552
1553 // Disallow locking free pads - it's confusing and not persisted
1554 // through save/load anyway.
1555 if( board_item->Type() == PCB_PAD_T )
1556 continue;
1557
1558 EDA_GROUP* parent_group = board_item->GetParentGroup();
1559
1560 if( parent_group && parent_group->AsEdaItem()->Type() == PCB_GENERATOR_T )
1561 {
1562 PCB_GENERATOR* generator = static_cast<PCB_GENERATOR*>( parent_group );
1563
1564 if( generator && commit.GetStatus( generator ) != CHT_MODIFY )
1565 {
1566 commit.Modify( generator );
1567
1568 if( aMode == ON )
1569 generator->SetLocked( true );
1570 else
1571 generator->SetLocked( false );
1572 }
1573 }
1574
1575 commit.Modify( board_item );
1576
1577 if( aMode == ON )
1578 board_item->SetLocked( true );
1579 else
1580 board_item->SetLocked( false );
1581 }
1582
1583 if( !commit.Empty() )
1584 {
1585 commit.Push( aMode == ON ? _( "Lock" ) : _( "Unlock" ), SKIP_TEARDROPS );
1586
1587 m_toolMgr->PostEvent( EVENTS::SelectedEvent );
1588 m_frame->OnModify();
1589 }
1590
1591 if( isHover )
1592 m_toolMgr->RunAction( ACTIONS::selectionClear );
1593
1594 return 0;
1595}
1596
1597
1598static bool mergeZones( EDA_DRAW_FRAME* aFrame, BOARD_COMMIT& aCommit,
1599 std::vector<ZONE*>& aOriginZones, std::vector<ZONE*>& aMergedZones )
1600{
1601 aCommit.Modify( aOriginZones[0] );
1602
1603 aOriginZones[0]->Outline()->ClearArcs();
1604
1605 for( unsigned int i = 1; i < aOriginZones.size(); i++ )
1606 {
1607 SHAPE_POLY_SET otherOutline = aOriginZones[i]->Outline()->CloneDropTriangulation();
1608 otherOutline.ClearArcs();
1609 aOriginZones[0]->Outline()->BooleanAdd( otherOutline );
1610 }
1611
1612 aOriginZones[0]->Outline()->Simplify();
1613
1614 // We should have one polygon, possibly with holes. If we end up with two polygons (either
1615 // because the intersection was a single point or because the intersection was within one of
1616 // the zone's holes) then we can't merge.
1617 if( aOriginZones[0]->Outline()->IsSelfIntersecting() || aOriginZones[0]->Outline()->OutlineCount() > 1 )
1618 {
1619 DisplayErrorMessage( aFrame, _( "Zones have insufficient overlap for merging." ) );
1620 aCommit.Revert();
1621 return false;
1622 }
1623
1624 // Adopt the highest priority from all merged zones so the result maintains
1625 // the most aggressive fill ordering.
1626 unsigned highestPriority = aOriginZones[0]->GetAssignedPriority();
1627
1628 for( unsigned int i = 1; i < aOriginZones.size(); i++ )
1629 {
1630 highestPriority = std::max( highestPriority, aOriginZones[i]->GetAssignedPriority() );
1631 aCommit.Remove( aOriginZones[i] );
1632 }
1633
1634 aOriginZones[0]->SetAssignedPriority( highestPriority );
1635
1636 aMergedZones.push_back( aOriginZones[0] );
1637
1638 aOriginZones[0]->SetLocalFlags( 1 );
1639 aOriginZones[0]->HatchBorder();
1640 aOriginZones[0]->CacheTriangulation();
1641
1642 return true;
1643}
1644
1645
1647{
1648 const PCB_SELECTION& selection = m_toolMgr->GetTool<PCB_SELECTION_TOOL>()->GetSelection();
1650 BOARD_COMMIT commit( m_frame );
1651
1652 if( selection.Size() < 2 )
1653 return 0;
1654
1655 int netcode = -1;
1656
1657 ZONE* firstZone = nullptr;
1658 std::vector<ZONE*> toMerge, merged;
1659
1660 for( EDA_ITEM* item : selection )
1661 {
1662 ZONE* curr_area = dynamic_cast<ZONE*>( item );
1663
1664 if( !curr_area )
1665 continue;
1666
1667 if( !firstZone )
1668 firstZone = curr_area;
1669
1670 netcode = curr_area->GetNetCode();
1671
1672 if( firstZone->GetNetCode() != netcode )
1673 {
1674 wxLogMessage( _( "Some zone netcodes did not match and were not merged." ) );
1675 continue;
1676 }
1677
1678 if( curr_area->GetIsRuleArea() != firstZone->GetIsRuleArea() )
1679 {
1680 wxLogMessage( _( "Some zones were rule areas and were not merged." ) );
1681 continue;
1682 }
1683
1684 if( curr_area->GetLayerSet() != firstZone->GetLayerSet() )
1685 {
1686 wxLogMessage( _( "Some zone layer sets did not match and were not merged." ) );
1687 continue;
1688 }
1689
1690 bool intersects = curr_area == firstZone;
1691
1692 for( ZONE* candidate : toMerge )
1693 {
1694 if( intersects )
1695 break;
1696
1697 if( board->TestZoneIntersection( curr_area, candidate ) )
1698 intersects = true;
1699 }
1700
1701 if( !intersects )
1702 {
1703 wxLogMessage( _( "Some zones did not intersect and were not merged." ) );
1704 continue;
1705 }
1706
1707 toMerge.push_back( curr_area );
1708 }
1709
1710 m_toolMgr->RunAction( ACTIONS::selectionClear );
1711
1712 if( !toMerge.empty() )
1713 {
1714 if( mergeZones( m_frame, commit, toMerge, merged ) )
1715 {
1716 commit.Push( _( "Merge Zones" ) );
1717
1718 for( EDA_ITEM* item : merged )
1719 m_toolMgr->RunAction( ACTIONS::selectItem, item );
1720 }
1721 }
1722
1723 return 0;
1724}
1725
1726
1728{
1729 PCB_SELECTION_TOOL* selTool = m_toolMgr->GetTool<PCB_SELECTION_TOOL>();
1730 const PCB_SELECTION& selection = selTool->GetSelection();
1731
1732 // because this pops up the zone editor, it would be confusing to handle multiple zones,
1733 // so just handle single selections containing exactly one zone
1734 if( selection.Size() != 1 )
1735 return 0;
1736
1737 ZONE* oldZone = dynamic_cast<ZONE*>( selection[0] );
1738
1739 if( !oldZone )
1740 return 0;
1741
1742 ZONE_SETTINGS zoneSettings;
1743 zoneSettings << *oldZone;
1744 int dialogResult;
1745
1746 if( oldZone->GetIsRuleArea() )
1747 dialogResult = InvokeRuleAreaEditor( m_frame, &zoneSettings, board() );
1748 else if( oldZone->IsOnCopperLayer() )
1749 dialogResult = InvokeCopperZonesEditor( m_frame, nullptr, &zoneSettings );
1750 else
1751 dialogResult = InvokeNonCopperZonesEditor( m_frame, &zoneSettings );
1752
1753 if( dialogResult != wxID_OK )
1754 return 0;
1755
1756 // duplicate the zone
1757 BOARD_COMMIT commit( m_frame );
1758
1759 std::unique_ptr<ZONE> newZone = std::make_unique<ZONE>( *oldZone );
1760 newZone->ClearSelected();
1761 newZone->UnFill();
1762 zoneSettings.ExportSetting( *newZone );
1763
1764 // If the new zone is on the same layer(s) as the initial zone,
1765 // offset it a bit so it can more easily be picked.
1766 if( oldZone->GetLayerSet() == zoneSettings.m_Layers )
1767 newZone->Move( VECTOR2I( pcbIUScale.IU_PER_MM, pcbIUScale.IU_PER_MM ) );
1768
1769 commit.Add( newZone.release() );
1770 commit.Push( _( "Duplicate Zone" ) );
1771
1772 return 0;
1773}
1774
1775
1777{
1778 const PCB_SELECTION& selection = m_toolMgr->GetTool<PCB_SELECTION_TOOL>()->GetSelection();
1779
1780 if( selection.Size() != 1 )
1781 return 0;
1782
1783 ZONE* zone = dynamic_cast<ZONE*>( selection[0] );
1784
1785 if( !zone || zone->GetIsRuleArea() || zone->IsTeardropArea() )
1786 return 0;
1787
1788 std::vector<ZONE*> overlapping = getOverlappingZones( board(), zone );
1789
1790 unsigned maxOverlapping = zone->GetAssignedPriority();
1791
1792 for( ZONE* other : overlapping )
1793 maxOverlapping = std::max( maxOverlapping, other->GetAssignedPriority() );
1794
1795 if( zone->GetAssignedPriority() >= maxOverlapping )
1796 return 0;
1797
1798 // Two options to place our zone above all overlapping zones.
1799 // Pick whichever viable option displaces fewer other zones.
1800 ZonePriorityMap byPriority = buildPriorityMap( board(), zone );
1801
1802 // Option A: take maxOverlapping, cascade displaced zones down
1803 bool cascadeDownViable = false;
1804 std::vector<ZONE*> cascadeDown =
1805 findCascadeZones( byPriority, maxOverlapping, false, cascadeDownViable );
1806
1807 // Option B: take maxOverlapping + 1, cascade displaced zones up
1808 bool cascadeUpViable = false;
1809 std::vector<ZONE*> cascadeUp;
1810 bool canCascadeUp = ( maxOverlapping < UINT_MAX );
1811
1812 if( canCascadeUp )
1813 cascadeUp = findCascadeZones( byPriority, maxOverlapping + 1, true, cascadeUpViable );
1814
1815 if( !cascadeDownViable && !cascadeUpViable )
1816 return 0;
1817
1818 BOARD_COMMIT commit( m_frame );
1819 commit.Modify( zone );
1820
1821 bool useDown = cascadeDownViable
1822 && ( !cascadeUpViable || cascadeDown.size() <= cascadeUp.size() );
1823
1824 if( useDown )
1825 {
1826 zone->SetAssignedPriority( maxOverlapping );
1827
1828 for( ZONE* z : cascadeDown )
1829 {
1830 commit.Modify( z );
1832 z->SetNeedRefill( true );
1833 }
1834 }
1835 else
1836 {
1837 zone->SetAssignedPriority( maxOverlapping + 1 );
1838
1839 for( ZONE* z : cascadeUp )
1840 {
1841 commit.Modify( z );
1843 z->SetNeedRefill( true );
1844 }
1845 }
1846
1847 zone->SetNeedRefill( true );
1848 commit.Push( _( "Move Zone to Top Priority" ) );
1849
1850 return 0;
1851}
1852
1853
1855{
1856 const PCB_SELECTION& selection = m_toolMgr->GetTool<PCB_SELECTION_TOOL>()->GetSelection();
1857
1858 if( selection.Size() != 1 )
1859 return 0;
1860
1861 ZONE* zone = dynamic_cast<ZONE*>( selection[0] );
1862
1863 if( !zone || zone->GetIsRuleArea() || zone->IsTeardropArea() )
1864 return 0;
1865
1866 std::vector<ZONE*> overlapping = getOverlappingZones( board(), zone );
1867
1868 // Find the overlapping zone with the lowest priority still above ours
1869 ZONE* target = nullptr;
1870 unsigned zonePriority = zone->GetAssignedPriority();
1871
1872 for( ZONE* other : overlapping )
1873 {
1874 if( other->GetAssignedPriority() > zonePriority )
1875 {
1876 if( !target || other->GetAssignedPriority() < target->GetAssignedPriority() )
1877 target = other;
1878 }
1879 }
1880
1881 if( !target )
1882 return 0;
1883
1884 BOARD_COMMIT commit( m_frame );
1885 commit.Modify( zone );
1886
1887 // Place our zone just above the target without modifying any other zone
1888 if( target->GetAssignedPriority() < UINT_MAX )
1889 {
1890 zone->SetAssignedPriority( target->GetAssignedPriority() + 1 );
1891 }
1892 else
1893 {
1894 // Can't go above UINT_MAX; swap as last resort
1895 commit.Modify( target );
1896 zone->SetAssignedPriority( UINT_MAX );
1897 target->SetAssignedPriority( zonePriority );
1898 target->SetNeedRefill( true );
1899 }
1900
1901 zone->SetNeedRefill( true );
1902 commit.Push( _( "Raise Zone Priority" ) );
1903
1904 return 0;
1905}
1906
1907
1909{
1910 const PCB_SELECTION& selection = m_toolMgr->GetTool<PCB_SELECTION_TOOL>()->GetSelection();
1911
1912 if( selection.Size() != 1 )
1913 return 0;
1914
1915 ZONE* zone = dynamic_cast<ZONE*>( selection[0] );
1916
1917 if( !zone || zone->GetIsRuleArea() || zone->IsTeardropArea() )
1918 return 0;
1919
1920 std::vector<ZONE*> overlapping = getOverlappingZones( board(), zone );
1921
1922 // Find the overlapping zone with the highest priority still below ours
1923 ZONE* target = nullptr;
1924 unsigned zonePriority = zone->GetAssignedPriority();
1925
1926 for( ZONE* other : overlapping )
1927 {
1928 if( other->GetAssignedPriority() < zonePriority )
1929 {
1930 if( !target || other->GetAssignedPriority() > target->GetAssignedPriority() )
1931 target = other;
1932 }
1933 }
1934
1935 if( !target )
1936 return 0;
1937
1938 BOARD_COMMIT commit( m_frame );
1939 commit.Modify( zone );
1940
1941 // Place our zone just below the target without modifying any other zone
1942 if( target->GetAssignedPriority() > 0 )
1943 {
1944 zone->SetAssignedPriority( target->GetAssignedPriority() - 1 );
1945 }
1946 else
1947 {
1948 // Can't go below 0; swap as last resort
1949 commit.Modify( target );
1950 zone->SetAssignedPriority( 0 );
1951 target->SetAssignedPriority( zonePriority );
1952 target->SetNeedRefill( true );
1953 }
1954
1955 zone->SetNeedRefill( true );
1956 commit.Push( _( "Lower Zone Priority" ) );
1957
1958 return 0;
1959}
1960
1961
1963{
1964 const PCB_SELECTION& selection = m_toolMgr->GetTool<PCB_SELECTION_TOOL>()->GetSelection();
1965
1966 if( selection.Size() != 1 )
1967 return 0;
1968
1969 ZONE* zone = dynamic_cast<ZONE*>( selection[0] );
1970
1971 if( !zone || zone->GetIsRuleArea() || zone->IsTeardropArea() )
1972 return 0;
1973
1974 std::vector<ZONE*> overlapping = getOverlappingZones( board(), zone );
1975
1976 unsigned minOverlapping = zone->GetAssignedPriority();
1977
1978 for( ZONE* other : overlapping )
1979 minOverlapping = std::min( minOverlapping, other->GetAssignedPriority() );
1980
1981 if( zone->GetAssignedPriority() <= minOverlapping )
1982 return 0;
1983
1984 // Two options to place our zone below all overlapping zones.
1985 // Pick whichever viable option displaces fewer other zones.
1986 ZonePriorityMap byPriority = buildPriorityMap( board(), zone );
1987
1988 // Option A: take minOverlapping, cascade displaced zones up
1989 bool cascadeUpViable = false;
1990 std::vector<ZONE*> cascadeUp =
1991 findCascadeZones( byPriority, minOverlapping, true, cascadeUpViable );
1992
1993 // Option B: take minOverlapping - 1, cascade displaced zones down
1994 bool cascadeDownViable = false;
1995 std::vector<ZONE*> cascadeDown;
1996 bool canCascadeDown = ( minOverlapping > 0 );
1997
1998 if( canCascadeDown )
1999 {
2000 cascadeDown =
2001 findCascadeZones( byPriority, minOverlapping - 1, false, cascadeDownViable );
2002 }
2003
2004 if( !cascadeUpViable && !cascadeDownViable )
2005 return 0;
2006
2007 BOARD_COMMIT commit( m_frame );
2008 commit.Modify( zone );
2009
2010 bool useUp = cascadeUpViable
2011 && ( !cascadeDownViable || cascadeUp.size() <= cascadeDown.size() );
2012
2013 if( useUp )
2014 {
2015 zone->SetAssignedPriority( minOverlapping );
2016
2017 for( ZONE* z : cascadeUp )
2018 {
2019 commit.Modify( z );
2021 z->SetNeedRefill( true );
2022 }
2023 }
2024 else
2025 {
2026 zone->SetAssignedPriority( minOverlapping - 1 );
2027
2028 for( ZONE* z : cascadeDown )
2029 {
2030 commit.Modify( z );
2032 z->SetNeedRefill( true );
2033 }
2034 }
2035
2036 zone->SetNeedRefill( true );
2037 commit.Push( _( "Move Zone to Bottom Priority" ) );
2038
2039 return 0;
2040}
2041
2042
2044{
2045 doCrossProbePcbToSch( aEvent, false );
2046 return 0;
2047}
2048
2049
2051{
2052 doCrossProbePcbToSch( aEvent, true );
2053 return 0;
2054}
2055
2056
2058{
2059 // Don't get in an infinite loop PCB -> SCH -> PCB -> SCH -> ...
2060 if( m_frame->m_ProbingSchToPcb )
2061 return;
2062
2063 PCB_SELECTION_TOOL* selTool = m_toolMgr->GetTool<PCB_SELECTION_TOOL>();
2064 const PCB_SELECTION& selection = selTool->GetSelection();
2065 EDA_ITEM* focusItem = nullptr;
2066
2067 if( aEvent.Matches( EVENTS::PointSelectedEvent ) )
2068 focusItem = selection.GetLastAddedItem();
2069
2070 m_frame->SendSelectItemsToSch( selection.GetItems(), focusItem, aForce );
2071
2072 // Update 3D viewer highlighting
2073 m_frame->Update3DView( false, frame()->GetPcbNewSettings()->m_Display.m_Live3DRefresh );
2074}
2075
2076
2078{
2079 PCB_SELECTION_TOOL* selectionTool = m_toolMgr->GetTool<PCB_SELECTION_TOOL>();
2080
2081 const PCB_SELECTION& selection = selectionTool->RequestSelection(
2082 []( const VECTOR2I& aPt, GENERAL_COLLECTOR& aCollector, PCB_SELECTION_TOOL* sTool )
2083 {
2084 // Iterate from the back so we don't have to worry about removals.
2085 for( int i = aCollector.GetCount() - 1; i >= 0; --i )
2086 {
2087 if( !dynamic_cast<BOARD_CONNECTED_ITEM*>( aCollector[ i ] ) )
2088 aCollector.Remove( aCollector[ i ] );
2089 }
2090
2091 sTool->FilterCollectorForLockedItems( aCollector );
2092 } );
2093
2094 std::set<wxString> netNames;
2095 std::set<int> netCodes;
2096
2097 for( EDA_ITEM* item : selection )
2098 {
2099 const NETINFO_ITEM& net = *static_cast<BOARD_CONNECTED_ITEM*>( item )->GetNet();
2100
2101 if( !net.HasAutoGeneratedNetname() )
2102 {
2103 netNames.insert( net.GetNetname() );
2104 netCodes.insert( net.GetNetCode() );
2105 }
2106 }
2107
2108 if( netNames.empty() )
2109 {
2110 m_frame->ShowInfoBarError( _( "Selection contains no items with labeled nets." ) );
2111 return 0;
2112 }
2113
2114 selectionTool->ClearSelection();
2115 for( const int& code : netCodes )
2116 {
2117 m_toolMgr->RunAction( PCB_ACTIONS::selectNet, code );
2118 }
2119 canvas()->ForceRefresh();
2120
2121 DIALOG_ASSIGN_NETCLASS dlg( m_frame, netNames, board()->GetNetClassAssignmentCandidates(),
2122 [this]( const std::vector<wxString>& aNetNames )
2123 {
2124 PCB_SELECTION_TOOL* selTool = m_toolMgr->GetTool<PCB_SELECTION_TOOL>();
2125 selTool->ClearSelection();
2126
2127 for( const wxString& curr_netName : aNetNames )
2128 {
2129 int curr_netCode = board()->GetNetInfo().GetNetItem( curr_netName )->GetNetCode();
2130
2131 if( curr_netCode > 0 )
2132 selTool->SelectAllItemsOnNet( curr_netCode );
2133 }
2134
2135 canvas()->ForceRefresh();
2136 m_frame->UpdateMsgPanel();
2137 } );
2138
2139 if( dlg.ShowModal() == wxID_OK )
2140 {
2142 // Refresh UI that depends on netclasses, such as the properties panel
2144 }
2145
2146 return 0;
2147}
2148
2149
2151{
2152 PCB_SELECTION_TOOL* selTool = m_toolMgr->GetTool<PCB_SELECTION_TOOL>();
2153 const PCB_SELECTION& selection = selTool->RequestSelection( EDIT_TOOL::FootprintFilter );
2154
2155 if( selection.Empty() )
2156 {
2157 // Giant hack: by default we assign Edit Table to the same hotkey, so give the table
2158 // tool a chance to handle it if we can't.
2159 if( PCB_EDIT_TABLE_TOOL* tableTool = m_toolMgr->GetTool<PCB_EDIT_TABLE_TOOL>() )
2160 tableTool->EditTable( aEvent );
2161
2162 return 0;
2163 }
2164
2165 FOOTPRINT* fp = selection.FirstOfKind<FOOTPRINT>();
2166
2167 if( !fp )
2168 return 0;
2169
2171
2172 if( KIWAY_PLAYER* frame = editFrame->Kiway().Player( FRAME_FOOTPRINT_EDITOR, true ) )
2173 {
2174 FOOTPRINT_EDIT_FRAME* fp_editor = static_cast<FOOTPRINT_EDIT_FRAME*>( frame );
2175
2177 fp_editor->LoadFootprintFromBoard( fp );
2178 else if( aEvent.IsAction( &PCB_ACTIONS::editLibFpInFpEditor ) )
2179 fp_editor->LoadFootprintFromLibrary( fp->GetFPID() );
2180
2181 fp_editor->Show( true );
2182 fp_editor->Raise(); // Iconize( false );
2183 }
2184
2185 if( selection.IsHover() )
2186 m_toolMgr->RunAction( ACTIONS::selectionClear );
2187
2188 return 0;
2189}
2190
2191
2193 EDA_ITEM* originViewItem, const VECTOR2D& aPosition )
2194{
2195 aFrame->GetDesignSettings().SetAuxOrigin( VECTOR2I( aPosition ) );
2196 originViewItem->SetPosition( aPosition );
2197 aView->MarkDirty();
2198 aFrame->OnModify();
2199}
2200
2201
2203{
2205 {
2206 m_frame->SaveCopyInUndoList( m_placeOrigin.get(), UNDO_REDO::GRIDORIGIN );
2208 return 0;
2209 }
2210
2211 if( aEvent.IsAction( &PCB_ACTIONS::drillSetOrigin ) )
2212 {
2213 VECTOR2I origin = aEvent.Parameter<VECTOR2I>();
2214 m_frame->SaveCopyInUndoList( m_placeOrigin.get(), UNDO_REDO::GRIDORIGIN );
2215 DoSetDrillOrigin( getView(), m_frame, m_placeOrigin.get(), origin );
2216 return 0;
2217 }
2218
2219 PCB_PICKER_TOOL* picker = m_toolMgr->GetTool<PCB_PICKER_TOOL>();
2220
2221 // Deactivate other tools; particularly important if another PICKER is currently running
2222 Activate();
2223
2224 picker->SetCursor( KICURSOR::PLACE );
2225 picker->ClearHandlers();
2226
2227 picker->SetClickHandler(
2228 [this] ( const VECTOR2D& pt ) -> bool
2229 {
2230 m_frame->SaveCopyInUndoList( m_placeOrigin.get(), UNDO_REDO::DRILLORIGIN );
2232 return false; // drill origin is a one-shot; don't continue with tool
2233 } );
2234
2235 m_toolMgr->RunAction( ACTIONS::pickerTool, &aEvent );
2236
2237 return 0;
2238}
2239
2240
2242{
2251
2257
2264
2265 if( ADVANCED_CFG::GetCfg().m_ShowPcbnewExportNetlist && m_frame && m_frame->GetExportNetlistAction() )
2266 Go( &BOARD_EDITOR_CONTROL::ExportNetlist, m_frame->GetExportNetlistAction()->MakeEvent() );
2267
2276
2283
2284 // Track & via size control
2290
2291 // Zone actions
2298
2299 // Placing tools
2304
2307
2308 // Cross-select
2314
2315 // Other
2319
2321
2331 // Line modes: explicit, next, and notification
2336}
const char * name
constexpr EDA_IU_SCALE pcbIUScale
Definition base_units.h:121
KIFACE_BASE & Kiface()
Global KIFACE_BASE "get" accessor.
#define SKIP_TEARDROPS
static bool mergeZones(EDA_DRAW_FRAME *aFrame, BOARD_COMMIT &aCommit, std::vector< ZONE * > &aOriginZones, std::vector< ZONE * > &aMergedZones)
BOX2< VECTOR2I > BOX2I
Definition box2.h:918
static TOOL_ACTION updatePcbFromSchematic
Definition actions.h:260
static TOOL_ACTION cancelInteractive
Definition actions.h:68
static TOOL_ACTION revert
Definition actions.h:58
static TOOL_ACTION selectItem
Select an item (specified as the event parameter).
Definition actions.h:223
static TOOL_ACTION saveAs
Definition actions.h:55
static TOOL_ACTION pickerTool
Definition actions.h:249
static TOOL_ACTION findPrevious
Definition actions.h:116
static TOOL_ACTION plot
Definition actions.h:61
static TOOL_ACTION open
Definition actions.h:53
static TOOL_ACTION findNext
Definition actions.h:115
static TOOL_ACTION pageSettings
Definition actions.h:59
static TOOL_ACTION showSearch
Definition actions.h:112
static TOOL_ACTION undo
Definition actions.h:71
static TOOL_ACTION save
Definition actions.h:54
static TOOL_ACTION redo
Definition actions.h:72
static TOOL_ACTION updateSchematicFromPcb
Definition actions.h:261
static TOOL_ACTION selectionClear
Clear the current selection.
Definition actions.h:220
static TOOL_ACTION showProperties
Definition actions.h:262
static TOOL_ACTION doNew
Definition actions.h:50
static TOOL_ACTION saveCopy
Definition actions.h:56
static TOOL_ACTION refreshPreview
Definition actions.h:155
static TOOL_ACTION find
Definition actions.h:113
ACTION_MENU(bool isContextMenu, TOOL_INTERACTIVE *aTool=nullptr)
Default constructor.
TOOL_MANAGER * getToolManager() const
Return an instance of TOOL_MANAGER class.
void SetTitle(const wxString &aTitle) override
Set title for the menu.
void SetIcon(BITMAPS aIcon)
Assign an icon for the entry.
wxMenuItem * Add(const wxString &aLabel, int aId, BITMAPS aIcon)
Add a wxWidgets-style entry to the menu.
friend class TOOL_INTERACTIVE
TOOL_INTERACTIVE * m_tool
Creator of the menu.
static const ADVANCED_CFG & GetCfg()
Get the singleton instance's config, which is shared by all consumers.
static wxString m_DrawingSheetFileName
the name of the drawing sheet file, or empty to use the default drawing sheet
Definition base_screen.h:81
virtual void Push(const wxString &aMessage=wxEmptyString, int aCommitFlags=0) override
Execute the changes.
virtual void Revert() override
Revert the commit by restoring the modified items state.
A base class derived from BOARD_ITEM for items that can be connected and have a net,...
NETINFO_ITEM * GetNet() const
Return #NET_INFO object for a given item.
Container for design settings for a BOARD object.
void UseCustomTrackViaSize(bool aEnabled)
Enables/disables custom track/via size settings.
std::shared_ptr< NET_SETTINGS > m_NetSettings
int GetNextDiffPairIndex(int aIndex, bool aForward) const
Compute the next diff pair dimensions list index when cycling predefined sizes, skipping the index-0 ...
void SetViaSizeIndex(int aIndex)
Set the current via size list index to aIndex.
int GetNextTrackWidthIndex(int aIndex, bool aForward) const
Compute the next track width list index when cycling predefined sizes, skipping the index-0 netclass ...
void SetAuxOrigin(const VECTOR2I &aOrigin)
void SetTrackWidthIndex(int aIndex)
Set the current track width list index to aIndex.
void UseCustomDiffPairDimensions(bool aEnabled)
Enables/disables custom differential pair dimensions.
int GetNextViaSizeIndex(int aIndex, bool aForward) const
Compute the next via size list index when cycling predefined sizes, skipping the index-0 netclass pla...
std::vector< int > m_TrackWidthList
std::vector< VIA_DIMENSION > m_ViasDimensionsList
int ExportNetlist(const TOOL_EVENT &aEvent)
int UnlockSelected(const TOOL_EVENT &aEvent)
Run the drill origin tool for setting the origin for drill and pick-and-place files.
int Save(const TOOL_EVENT &aEvent)
int ImportNetlist(const TOOL_EVENT &aEvent)
int GenerateDrillFiles(const TOOL_EVENT &aEvent)
int ZoneMerge(const TOOL_EVENT &aEvent)
Duplicate a zone onto a layer (prompts for new layer)
int CrossProbeToSch(const TOOL_EVENT &aEvent)
Equivalent to the above, but initiated by the user.
int ZonePriorityMoveToTop(const TOOL_EVENT &aEvent)
int GenBOMFileFromBoard(const TOOL_EVENT &aEvent)
static void DoSetDrillOrigin(KIGFX::VIEW *aView, PCB_BASE_FRAME *aFrame, EDA_ITEM *aItem, const VECTOR2D &aPoint)
int UpdatePCBFromSchematic(const TOOL_EVENT &aEvent)
std::unique_ptr< KIGFX::ORIGIN_VIEWITEM > m_placeOrigin
int ShowEeschema(const TOOL_EVENT &aEvent)
int ExportFootprints(const TOOL_EVENT &aEvent)
int SaveAs(const TOOL_EVENT &aEvent)
int AssignNetclass(const TOOL_EVENT &aEvent)
int ToggleNetInspector(const TOOL_EVENT &aEvent)
int UpdateSchematicFromPCB(const TOOL_EVENT &aEvent)
int ZonePriorityRaise(const TOOL_EVENT &aEvent)
int ExplicitCrossProbeToSch(const TOOL_EVENT &aEvent)
Assign a netclass to a labelled net.
int ExportHyperlynx(const TOOL_EVENT &aEvent)
int ToggleSearch(const TOOL_EVENT &aEvent)
int DrillOrigin(const TOOL_EVENT &aEvent)
Low-level access (below undo) to setting the drill origin.
MODIFY_MODE
< How to modify a property for selected items.
int ViaSizeDec(const TOOL_EVENT &aEvent)
void Reset(RESET_REASON aReason) override
Bring the tool to a known, initial state.
int RepairBoard(const TOOL_EVENT &aEvent)
int ZoneDuplicate(const TOOL_EVENT &aEvent)
int ToggleLayersManager(const TOOL_EVENT &aEvent)
int ImportSpecctraSession(const TOOL_EVENT &aEvent)
bool Init() override
Init() is called once upon a registration of the tool.
int PlaceFootprint(const TOOL_EVENT &aEvent)
Display a dialog to select a footprint to be added and allows the user to set its position.
int BoardSetup(const TOOL_EVENT &aEvent)
int ZonePriorityLower(const TOOL_EVENT &aEvent)
int modifyLockSelected(MODIFY_MODE aMode)
Set up handlers for various events.
void setTransitions() override
This method is meant to be overridden in order to specify handlers for events.
int TrackWidthInc(const TOOL_EVENT &aEvent)
int GenerateODBPPFiles(const TOOL_EVENT &aEvent)
int ToggleLockSelected(const TOOL_EVENT &aEvent)
Lock selected items.
int AutoTrackWidth(const TOOL_EVENT &aEvent)
int LockSelected(const TOOL_EVENT &aEvent)
Unlock selected items.
int PageSettings(const TOOL_EVENT &aEvent)
int ExportSpecctraDSN(const TOOL_EVENT &aEvent)
int FindByProperties(const TOOL_EVENT &aEvent)
int FindNext(const TOOL_EVENT &aEvent)
int ToggleLibraryTree(const TOOL_EVENT &aEvent)
int ExportGenCAD(const TOOL_EVENT &aEvent)
Export GenCAD 1.4 format.
int ViaSizeInc(const TOOL_EVENT &aEvent)
int New(const TOOL_EVENT &aEvent)
int OnAngleSnapModeChanged(const TOOL_EVENT &aEvent)
int ExportCmpFile(const TOOL_EVENT &aEvent)
int Find(const TOOL_EVENT &aEvent)
int GenFootprintsReport(const TOOL_EVENT &aEvent)
void doCrossProbePcbToSch(const TOOL_EVENT &aEvent, bool aForce)
int GenD356File(const TOOL_EVENT &aEvent)
int Plot(const TOOL_EVENT &aEvent)
int ExportIDF(const TOOL_EVENT &aEvent)
int TrackWidthDec(const TOOL_EVENT &aEvent)
int Revert(const TOOL_EVENT &aEvent)
int Search(const TOOL_EVENT &aEvent)
int GenIPC2581File(const TOOL_EVENT &aEvent)
int ExportVRML(const TOOL_EVENT &aEvent)
int Open(const TOOL_EVENT &aEvent)
int SaveCopy(const TOOL_EVENT &aEvent)
int ChangeLineMode(const TOOL_EVENT &aEvent)
int GeneratePosFile(const TOOL_EVENT &aEvent)
int EditFpInFpEditor(const TOOL_EVENT &aEvent)
Notify Eeschema about selected items.
int ZonePriorityMoveToBottom(const TOOL_EVENT &aEvent)
int GenerateGerbers(const TOOL_EVENT &aEvent)
int ToggleProperties(const TOOL_EVENT &aEvent)
int OpenNonKicadBoard(const TOOL_EVENT &aEvent)
int ExportSTEP(const TOOL_EVENT &aEvent)
A base class for any item which can be embedded within the BOARD container class, and therefore insta...
Definition board_item.h:81
void SetLocked(bool aLocked) override
Definition board_item.h:356
virtual const BOARD * GetBoard() const
Return the BOARD in which this BOARD_ITEM resides, or NULL if none.
Information pertinent to a Pcbnew printed circuit board.
Definition board.h:372
const NETINFO_LIST & GetNetInfo() const
Definition board.h:1086
void Add(BOARD_ITEM *aItem, ADD_MODE aMode=ADD_MODE::INSERT, bool aSkipConnectivity=false) override
Removes an item from the container.
Definition board.cpp:1295
const ZONES & Zones() const
Definition board.h:424
void SynchronizeNetsAndNetClasses(bool aResetTrackAndViaSizes)
Copy NETCLASS info to each NET, based on NET membership in a NETCLASS.
Definition board.cpp:3004
int RepairDuplicateItemUuids()
Rebind duplicate attached-item UUIDs so each live board item has a unique ID.
Definition board.cpp:2114
int GetCount() const
Return the number of objects in the list.
Definition collector.h:79
void Remove(int aIndex)
Remove the item at aIndex (first position is 0).
Definition collector.h:107
COMMIT & Remove(EDA_ITEM *aItem, BASE_SCREEN *aScreen=nullptr)
Remove a new item from the model.
Definition commit.h:86
bool Empty() const
Definition commit.h:134
COMMIT & Modify(EDA_ITEM *aItem, BASE_SCREEN *aScreen=nullptr, RECURSE_MODE aRecurse=RECURSE_MODE::NO_RECURSE)
Modify a given item in the model.
Definition commit.h:102
COMMIT & Add(EDA_ITEM *aItem, BASE_SCREEN *aScreen=nullptr)
Add a new item to the model.
Definition commit.h:74
int GetStatus(EDA_ITEM *aItem, BASE_SCREEN *aScreen=nullptr)
Returns status of an item.
Definition commit.cpp:191
Store all of the related component information found in a netlist.
void AddNet(const wxString &aPinName, const wxString &aNetName, const wxString &aPinFunction, const wxString &aPinType)
void SetFields(nlohmann::ordered_map< wxString, wxString > aFields)
void AddItem(const TOOL_ACTION &aAction, const SELECTION_CONDITION &aCondition, int aOrder=ANY_ORDER)
Add a menu entry to run a TOOL_ACTION on selected items.
void AddSeparator(int aOrder=ANY_ORDER)
Add a separator to the menu.
void AddMenu(ACTION_MENU *aMenu, const SELECTION_CONDITION &aCondition=SELECTION_CONDITIONS::ShowAlways, int aOrder=ANY_ORDER)
Add a submenu to the menu.
CONDITIONAL_MENU(TOOL_INTERACTIVE *aTool)
void SetWksFileName(const wxString &aFilename)
A dialog to set the plot options and create plot files in various formats.
Definition dialog_plot.h:37
int ShowModal() override
Tool responsible for drawing graphical elements like lines, arcs, circles, etc.
MODE GetDrawingMode() const
Return the current drawing mode of the DRAWING_TOOL or MODE::NONE if not currently in any drawing mod...
void SelectToolbarAction(const TOOL_ACTION &aAction)
Select the given action in the toolbar group which contains it, if any.
The base class for create windows for drawing purpose.
void ForceRefresh()
Force a redraw.
A set of EDA_ITEMs (i.e., without duplicates).
Definition eda_group.h:42
virtual EDA_ITEM * AsEdaItem()=0
A base class for most all the KiCad significant classes used in schematics and boards.
Definition eda_item.h:96
virtual void SetPosition(const VECTOR2I &aPos)
Definition eda_item.h:283
void SetFlags(EDA_ITEM_FLAGS aMask)
Definition eda_item.h:152
virtual EDA_GROUP * GetParentGroup() const
Definition eda_item.h:114
KICAD_T Type() const
Returns the type of object.
Definition eda_item.h:108
virtual void SetParent(EDA_ITEM *aParent)
Definition eda_item.cpp:89
A mix-in class (via multiple inheritance) that handles texts such as labels, parts,...
Definition eda_text.h:89
static const TOOL_EVENT ClearedEvent
Definition actions.h:343
static const TOOL_EVENT SelectedEvent
Definition actions.h:341
static const TOOL_EVENT SelectedItemsModified
Selected items were moved, this can be very high frequency on the canvas, use with care.
Definition actions.h:348
static const TOOL_EVENT PointSelectedEvent
Definition actions.h:340
static const TOOL_EVENT UnselectedEvent
Definition actions.h:342
Used for text file output.
Definition richio.h:470
bool Finish() override
Flushes the temp file to disk and atomically renames it over the final target path.
Definition richio.cpp:642
void LoadFootprintFromLibrary(LIB_ID aFPID)
bool LoadFootprintFromBoard(FOOTPRINT *aFootprint)
Load a footprint from the main board into the Footprint Editor.
void SetPosition(const VECTOR2I &aPos) override
void SetLink(const KIID &aLink)
Definition footprint.h:1176
void SetOrientation(const EDA_ANGLE &aNewAngle)
std::deque< PAD * > & Pads()
Definition footprint.h:375
bool IsFlipped() const
Definition footprint.h:614
const LIB_ID & GetFPID() const
Definition footprint.h:441
void Flip(const VECTOR2I &aCentre, FLIP_DIRECTION aFlipDirection) override
Flip this object, i.e.
VECTOR2I GetPosition() const override
Definition footprint.h:403
Used when the right click button is pressed, or when the select tool is in effect.
Definition collectors.h:203
Hold an error message and may be used when throwing exceptions containing meaningful error messages.
virtual const wxString What() const
A composite of Problem() and Where()
A color representation with 4 components: red, green, blue, alpha.
Definition color4d.h:101
An interface for classes handling user events controlling the view behavior such as zooming,...
virtual void WarpMouseCursor(const VECTOR2D &aPosition, bool aWorldCoordinates=false, bool aWarpView=false)=0
If enabled (.
virtual VECTOR2D GetMousePosition(bool aWorldCoordinates=true) const =0
Return the current mouse pointer position.
virtual void PinCursorInsideNonAutoscrollArea(bool aWarpMouseCursor)=0
An abstract base class for deriving all objects that can be added to a VIEW.
Definition view_item.h:82
Hold a (potentially large) number of VIEW_ITEMs and renders them on a graphics device provided by the...
Definition view.h:63
virtual void Add(VIEW_ITEM *aItem, int aDrawPriority=-1)
Add a VIEW_ITEM to the view.
Definition view.cpp:300
virtual void Remove(VIEW_ITEM *aItem)
Remove a VIEW_ITEM from the view.
Definition view.cpp:404
virtual void Update(const VIEW_ITEM *aItem, int aUpdateFlags) const
For dynamic VIEWs, inform the associated VIEW that the graphical representation of this item has chan...
Definition view.cpp:1835
void MarkDirty()
Force redraw of view on the next rendering.
Definition view.h:677
PROJECT & Prj() const
Return a reference to the PROJECT associated with this KIWAY.
KIWAY & Kiway() const
Return a reference to the KIWAY that this object has an opportunity to participate in.
A wxFrame capable of the OpenProjectFiles function, meaning it can load a portion of a KiCad project.
virtual KIWAY_PLAYER * Player(FRAME_T aFrameType, bool doCreate=true, wxTopLevelWindow *aParent=nullptr)
Return the KIWAY_PLAYER* given a FRAME_T.
Definition kiway.cpp:398
Helper widget to add controls to a wxFileDialog to set netlist configuration options.
static wxWindow * Create(wxWindow *aParent)
ACTION_MENU * create() const override
Return an instance of this class. It has to be overridden in inheriting classes.
LOCK_CONTEXT_MENU(TOOL_INTERACTIVE *aTool)
int GetViaDiameter() const
Definition netclass.h:139
int GetViaDrill() const
Definition netclass.h:147
int GetTrackWidth() const
Definition netclass.h:131
Handle the data for a net.
Definition netinfo.h:46
const wxString & GetNetname() const
Definition netinfo.h:100
int GetNetCode() const
Definition netinfo.h:94
bool HasAutoGeneratedNetname() const
NETINFO_ITEM * GetNetItem(int aNetCode) const
Store information read from a netlist along with the flags used to update the NETLIST in the BOARD.
std::shared_ptr< NETCLASS > GetDefaultNetclass() const
Gets the default netclass for the project.
static constexpr PCB_LAYER_ID ALL_LAYERS
! Temporary layer identifier to identify code that is not padstack-aware
Definition padstack.h:177
Definition pad.h:61
static TOOL_ACTION lineModeFree
Unconstrained angle mode (icon lines_any)
static TOOL_ACTION zonesManager
static TOOL_ACTION generateBOM
static TOOL_ACTION exportGenCAD
static TOOL_ACTION zoneFillAll
static TOOL_ACTION showLayersManager
static TOOL_ACTION trackWidthDec
static TOOL_ACTION generateDrillFiles
static TOOL_ACTION exportVRML
static TOOL_ACTION generateD356File
static TOOL_ACTION exportCmpFile
static TOOL_ACTION trackViaSizeChanged
static TOOL_ACTION exportSpecctraDSN
static TOOL_ACTION trackWidthInc
static TOOL_ACTION autoTrackWidth
static TOOL_ACTION generateIPC2581File
static TOOL_ACTION getAndPlace
Find an item and start moving.
static TOOL_ACTION generateODBPPFile
static TOOL_ACTION drawZoneCutout
static TOOL_ACTION openNonKicadBoard
static TOOL_ACTION viaSizeDec
static TOOL_ACTION zoneFill
static TOOL_ACTION properties
Activation of the edit tool.
static TOOL_ACTION editFpInFpEditor
static TOOL_ACTION toggleLock
static TOOL_ACTION drillResetOrigin
static TOOL_ACTION lineMode45
45-degree-or-orthogonal mode (icon hv45mode)
static TOOL_ACTION zonePriorityMoveToBottom
static TOOL_ACTION zonePriorityMoveToTop
static TOOL_ACTION viaSizeInc
static TOOL_ACTION angleSnapModeChanged
Notification event when angle mode changes.
static TOOL_ACTION zoneUnfill
static TOOL_ACTION generatePosFile
static TOOL_ACTION drillOrigin
static TOOL_ACTION assignNetClass
static TOOL_ACTION repairBoard
static TOOL_ACTION exportSTEP
static TOOL_ACTION showNetInspector
static TOOL_ACTION findByProperties
Find items by property criteria or expression.
static TOOL_ACTION generateGerbers
static TOOL_ACTION generateReportFile
static TOOL_ACTION exportHyperlynx
static TOOL_ACTION zonePriorityLower
static TOOL_ACTION exportIDF
static TOOL_ACTION zoneDuplicate
Duplicate zone onto another layer.
static TOOL_ACTION importNetlist
static TOOL_ACTION drawSimilarZone
static TOOL_ACTION boardSetup
static TOOL_ACTION showEeschema
static TOOL_ACTION showDesignBlockPanel
static TOOL_ACTION zoneUnfillAll
static TOOL_ACTION selectNet
Select all connections belonging to a single net.
Definition pcb_actions.h:78
static TOOL_ACTION lineMode90
90-degree-only mode (icon lines90)
static TOOL_ACTION editLibFpInFpEditor
static TOOL_ACTION zoneMerge
static TOOL_ACTION drillSetOrigin
static TOOL_ACTION unlock
static TOOL_ACTION exportFootprints
static TOOL_ACTION placeFootprint
static TOOL_ACTION zonePriorityRaise
static TOOL_ACTION importSpecctraSession
static TOOL_ACTION selectOnSchematic
Select symbols/pins on schematic corresponding to selected footprints/pads.
Definition pcb_actions.h:99
static TOOL_ACTION lock
Common, abstract interface for edit frames.
Base PCB main window class for Pcbnew, Gerbview, and CvPcb footprint viewer.
void OnModify() override
Must be called after a change in order to set the "modify" flag and update other data structures and ...
virtual BOARD_DESIGN_SETTINGS & GetDesignSettings() const
Return the BOARD_DESIGN_SETTINGS for the open project.
The main frame for Pcbnew.
void SetLocked(bool aLocked) override
Generic tool for picking an item.
Parameters and options when plotting/printing a board.
void SetFormat(PLOT_FORMAT aFormat)
static bool HasUnlockedItems(const SELECTION &aSelection)
Test if any selected items are unlocked.
static bool HasLockedItems(const SELECTION &aSelection)
Test if any selected items are locked.
The selection tool: currently supports:
PCB_SELECTION & RequestSelection(CLIENT_SELECTION_FILTER aClientFilter)
Return the current selection, filtered according to aClientFilter.
int ClearSelection(const TOOL_EVENT &aEvent)
PCB_SELECTION & GetSelection()
void FilterCollectorForLockedItems(GENERAL_COLLECTOR &aCollector)
In the PCB editor strip out any locked items unless the OverrideLocks checkbox is set.
void SelectAllItemsOnNet(int aNetCode, bool aSelect=true)
Select all items with the given net code.
T * frame() const
KIGFX::VIEW_CONTROLS * controls() const
PCB_TOOL_BASE(TOOL_ID aId, const std::string &aName)
Constructor.
BOARD * board() const
PCB_DRAW_PANEL_GAL * canvas() const
const PCB_SELECTION & selection() const
FOOTPRINT * footprint() const
virtual void SetWidth(int aWidth)
Definition pcb_track.h:86
virtual int GetWidth() const
Definition pcb_track.h:87
virtual COMMON_SETTINGS * GetCommonSettings() const
Definition pgm_base.cpp:528
A holder to handle information on schematic or board items.
void PushItem(const ITEM_PICKER &aItem)
Push aItem to the top of the list.
void SetDescription(const wxString &aDescription)
void SetClickHandler(CLICK_HANDLER aHandler)
Set a handler for mouse click event.
Definition picker_tool.h:77
void SetCursor(KICURSOR aCursor)
Definition picker_tool.h:60
ROUTER_MODE Mode() const
Definition pns_router.h:158
RouterState GetState() const
Definition pns_router.h:160
ROUTER * Router() const
Container for project specific data.
Definition project.h:62
virtual void OnSave(wxCommandEvent &aEvent)=0
static bool NotEmpty(const SELECTION &aSelection)
Test if there are any items selected.
static bool ShowAlways(const SELECTION &aSelection)
The default condition function (always returns true).
static SELECTION_CONDITION OnlyTypes(std::vector< KICAD_T > aTypes)
Create a functor that tests if the selected items are only of given types.
int Size() const
Returns the number of selected parts.
Definition selection.h:117
void SetReferencePoint(const VECTOR2I &aP)
Represent a set of closed polygons.
void ClearArcs()
Removes all arc references from all the outlines and holes in the polyset.
bool Collide(const SHAPE *aShape, int aClearance=0, int *aActual=nullptr, VECTOR2I *aLocation=nullptr) const override
Check if the boundary of shape (this) lies closer to the shape aShape than aClearance,...
int TotalVertices() const
Return total number of vertices stored in the set.
const VECTOR2I & CVertex(int aIndex, int aOutline, int aHole) const
Return the index-th vertex in a given hole outline within a given outline.
bool Contains(const VECTOR2I &aP, int aSubpolyIndex=-1, int aAccuracy=0, bool aUseBBoxCaches=false) const
Return true if a given subpolygon contains the point aP.
T * getEditFrame() const
Return the application window object, casted to requested user type.
Definition tool_base.h:182
T * getModel() const
Return the model object if it matches the requested type.
Definition tool_base.h:195
KIGFX::VIEW_CONTROLS * getViewControls() const
Return the instance of VIEW_CONTROLS object used in the application.
Definition tool_base.cpp:40
TOOL_MANAGER * m_toolMgr
Definition tool_base.h:220
KIGFX::VIEW * getView() const
Returns the instance of #VIEW object used in the application.
Definition tool_base.cpp:34
bool IsToolActive() const
Definition tool_base.cpp:28
RESET_REASON
Determine the reason of reset for a tool.
Definition tool_base.h:74
@ REDRAW
Full drawing refresh.
Definition tool_base.h:79
@ MODEL_RELOAD
Model changes (the sheet for a schematic)
Definition tool_base.h:76
@ GAL_SWITCH
Rendering engine changes.
Definition tool_base.h:78
Generic, UI-independent tool event.
Definition tool_event.h:167
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:256
bool Matches(const TOOL_EVENT &aEvent) const
Test whether two events match in terms of category & action or command.
Definition tool_event.h:388
const VECTOR2D Position() const
Return mouse cursor position in world coordinates.
Definition tool_event.h:289
bool IsReactivate() const
Control whether the tool is first being pushed to the stack or being reactivated after a pause.
Definition tool_event.h:269
bool IsAction(const TOOL_ACTION *aAction) const
Test if the event contains an action issued upon activation of the given TOOL_ACTION.
T Parameter() const
Return a parameter assigned to the event.
Definition tool_event.h:469
void RunMainStack(std::function< void()> aFunc)
Call a function using the main stack.
void Go(int(T::*aStateFunc)(const TOOL_EVENT &), const TOOL_EVENT_LIST &aConditions=TOOL_EVENT(TC_ANY, TA_ANY))
Define which state (aStateFunc) to go when a certain event arrives (aConditions).
TOOL_MENU & GetToolMenu()
std::unique_ptr< TOOL_MENU > m_menu
The functions below are not yet implemented - their interface may change.
TOOL_EVENT * Wait(const TOOL_EVENT_LIST &aEventList=TOOL_EVENT(TC_ANY, TA_ANY))
Suspend execution of the tool until an event specified in aEventList arrives.
void Activate()
Run the tool.
Manage a CONDITIONAL_MENU and some number of CONTEXT_MENUs as sub-menus.
Definition tool_menu.h:39
CONDITIONAL_MENU & GetMenu()
Definition tool_menu.cpp:40
void RegisterSubMenu(std::shared_ptr< ACTION_MENU > aSubMenu)
Store a submenu of this menu model.
Definition tool_menu.cpp:46
ACTION_MENU * create() const override
Return an instance of this class. It has to be overridden in inheriting classes.
static bool IsZoneFillAction(const TOOL_EVENT *aEvent)
ACTION_MENU * create() const override
Return an instance of this class. It has to be overridden in inheriting classes.
void update() override
Update menu state stub.
ZONE_SETTINGS handles zones parameters.
void ExportSetting(ZONE &aTarget, bool aFullExport=true) const
Function ExportSetting copy settings to a given zone.
Handle a list of polygons defining a copper zone.
Definition zone.h:70
void SetNeedRefill(bool aNeedRefill)
Definition zone.h:310
bool GetIsRuleArea() const
Accessors to parameters used in Rule Area zones:
Definition zone.h:811
const BOX2I GetBoundingBox() const override
Definition zone.cpp:737
SHAPE_POLY_SET GetBoardOutline() const
Definition zone.cpp:835
bool IsTeardropArea() const
Definition zone.h:786
virtual LSET GetLayerSet() const override
Return a std::bitset of all layers on which the item physically resides.
Definition zone.h:133
bool IsOnCopperLayer() const override
Definition zone.cpp:574
void SetAssignedPriority(unsigned aPriority)
Definition zone.h:117
unsigned GetAssignedPriority() const
Definition zone.h:122
@ CHT_MODIFY
Definition commit.h:40
void DisplayInfoMessage(wxWindow *aParent, const wxString &aMessage, const wxString &aExtraInfo)
Display an informational message box with aMessage.
Definition confirm.cpp:245
void DisplayErrorMessage(wxWindow *aParent, const wxString &aText, const wxString &aExtraInfo)
Display an error message with aMessage.
Definition confirm.cpp:217
This file is part of the common library.
@ PLACE
Definition cursors.h:94
@ ARROW
Definition cursors.h:42
@ PENCIL
Definition cursors.h:48
int InvokeCopperZonesEditor(PCB_BASE_FRAME *aCaller, ZONE *aZone, ZONE_SETTINGS *aSettings, CONVERT_SETTINGS *aConvertSettings)
Function InvokeCopperZonesEditor invokes up a modal dialog window for copper zone editing.
int InvokeNonCopperZonesEditor(PCB_BASE_FRAME *aParent, ZONE_SETTINGS *aSettings, CONVERT_SETTINGS *aConvertSettings)
Function InvokeNonCopperZonesEditor invokes up a modal dialog window for non-copper zone editing.
int InvokeRuleAreaEditor(PCB_BASE_FRAME *aCaller, ZONE_SETTINGS *aZoneSettings, BOARD *aBoard, CONVERT_SETTINGS *aConvertSettings)
Function InvokeRuleAreaEditor invokes up a modal dialog window for copper zone editing.
#define _(s)
static constexpr EDA_ANGLE ANGLE_0
Definition eda_angle.h:411
#define IS_NEW
New item, just created.
KiCad executable names.
const wxString EESCHEMA_EXE
@ FRAME_SCH
Definition frame_type.h:30
@ FRAME_FOOTPRINT_EDITOR
Definition frame_type.h:39
LEADER_MODE
The kind of the leader line.
@ DEG45
45 Degree only
@ DIRECT
Unconstrained point-to-point.
@ DEG90
90 Degree only
int ExecuteFile(const wxString &aEditorName, const wxString &aFileName, wxProcess *aCallback, bool aFileForKicad)
Call the executable file aEditorName with the parameter aFileName.
Definition gestfich.cpp:160
static const std::string LegacySchematicFileExtension
static const std::string KiCadSchematicFileExtension
static const std::string SpecctraDsnFileExtension
static const std::string SpecctraSessionFileExtension
static wxString SpecctraSessionFileWildcard()
static wxString SpecctraDsnFileWildcard()
KIID niluuid(0)
@ MAIL_SCH_UPDATE
Definition mail_type.h:44
@ REPAINT
Item needs to be redrawn.
Definition view_item.h:54
@ GEOMETRY
Position or shape has changed.
Definition view_item.h:51
void AllowNetworkFileSystems(wxDialog *aDialog)
Configure a file dialog to show network and virtual file systems.
Definition wxgtk/ui.cpp:448
@ PNS_MODE_ROUTE_DIFF_PAIR
Definition pns_router.h:69
#define MAX_PAGE_SIZE_PCBNEW_MILS
Definition page_info.h:31
PGM_BASE & Pgm()
The global program "get" accessor.
see class PGM_BASE
@ LAST_PATH_SPECCTRADSN
T * GetAppSettings(const char *aFilename)
std::vector< FAB_LAYER_COLOR > dummy
Container to handle a stock of specific vias each with unique diameter and drill sizes in the BOARD c...
std::string netlist
std::string path
wxString result
Test unit parsing edge cases and error handling.
@ BUT_LEFT
Definition tool_event.h:128
@ BUT_RIGHT
Definition tool_event.h:129
@ PCB_GENERATOR_T
class PCB_GENERATOR, generator on a layer
Definition typeinfo.h:84
@ PCB_VIA_T
class PCB_VIA, a via (like a track segment on a copper layer)
Definition typeinfo.h:90
@ PCB_PAD_T
class PAD, a pad in a footprint
Definition typeinfo.h:80
VECTOR2< int32_t > VECTOR2I
Definition vector2d.h:683
VECTOR2< double > VECTOR2D
Definition vector2d.h:682
wxString AddFileExtListToFilter(const std::vector< std::string > &aExts)
Build the wildcard extension file dialog wildcard filter to add to the base message dialog.
Definition of file extensions used in Kicad.