KiCad PCB EDA Suite
Loading...
Searching...
No Matches
dialog_erc.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) 2015 Jean-Pierre Charras, jp.charras at wanadoo.fr
5 * Copyright (C) 2012 Wayne Stambaugh <[email protected]>
6 * Copyright The KiCad Developers, see AUTHORS.txt for contributors.
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#include <advanced_config.h>
24#include <gestfich.h>
25#include <sch_screen.h>
26#include <sch_edit_frame.h>
27#include <widgets/wx_infobar.h>
28#include <project.h>
29#include <kiface_base.h>
30#include <reporter.h>
32#include <sch_marker.h>
33#include <connection_graph.h>
34#include <tools/sch_actions.h>
36#include <dialog_erc.h>
37#include <erc/erc.h>
38#include <erc/erc_report.h>
39#include <id.h>
40#include <confirm.h>
44#include <string_utils.h>
45#include <kiplatform/ui.h>
46#include <confirm.h>
47
48#include <wx/ffile.h>
49#include <wx/filedlg.h>
50#include <wx/hyperlink.h>
51#include <wx/msgdlg.h>
52#include <sch_edit_tool.h>
53
54
55wxDEFINE_EVENT( EDA_EVT_CLOSE_ERC_DIALOG, wxCommandEvent );
56
57
58// Route marker exclusion through the provider so its cached severity counts stay in sync.
59static void setMarkerExcluded( const std::shared_ptr<RC_ITEMS_PROVIDER>& aProvider,
60 SCH_MARKER* aMarker, bool aExcluded,
61 const wxString& aComment = wxEmptyString )
62{
63 static_cast<SHEETLIST_ERC_ITEMS_PROVIDER&>( *aProvider ).SetMarkerExcluded( aMarker, aExcluded,
64 aComment );
65}
66
67
68// wxWidgets spends *far* too long calculating column widths (most of it, believe it or
69// not, in repeatedly creating/destroying a wxDC to do the measurement in).
70// Use default column widths instead.
71static int DEFAULT_SINGLE_COL_WIDTH = 660;
72
73
74static SCHEMATIC* g_lastERCSchematic = nullptr;
75static bool g_lastERCRun = false;
76
77static std::vector<std::pair<wxString, int>> g_lastERCIgnored;
78
79
81 DIALOG_ERC_BASE( parent ),
83 m_parent( parent ),
84 m_markerTreeModel( nullptr ),
85 m_running( false ),
86 m_ercRun( false ),
87 m_centerMarkerOnIdle( nullptr ),
88 m_crossprobe( true ),
90 m_showAllErrors( false )
91{
92 m_currentSchematic = &parent->Schematic();
93
94 SetName( DIALOG_ERC_WINDOW_NAME ); // Set a window name to be able to find it
96
97 m_bMenu->SetBitmap( KiBitmapBundle( BITMAPS::config ) );
98
99 m_messages->SetImmediateMode();
100
101 m_markerProvider = std::make_shared<SHEETLIST_ERC_ITEMS_PROVIDER>( &m_parent->Schematic() );
102
104 m_markerDataView->AssociateModel( m_markerTreeModel );
106
107 // Prevent RTL locales from mirroring the text in the data views
108 m_markerDataView->SetLayoutDirection( wxLayout_LeftToRight );
109 m_ignoredList->SetLayoutDirection( wxLayout_LeftToRight );
110
111 m_ignoredList->InsertColumn( 0, wxEmptyString, wxLIST_FORMAT_LEFT, DEFAULT_SINGLE_COL_WIDTH );
112
114 {
116
117 for( const auto& [ str, code ] : g_lastERCIgnored )
118 {
119 wxListItem listItem;
120 listItem.SetId( m_ignoredList->GetItemCount() );
121 listItem.SetText( str );
122 listItem.SetData( code );
123
124 m_ignoredList->InsertItem( listItem );
125 }
126 }
127
128 m_notebook->SetSelection( 0 );
129
130 SetupStandardButtons( { { wxID_OK, _( "Run ERC" ) },
131 { wxID_CANCEL, _( "Close" ) } } );
132
133 m_violationsTitleTemplate = m_notebook->GetPageText( 0 );
134 m_ignoredTitleTemplate = m_notebook->GetPageText( 1 );
135
136 m_errorsBadge->SetMaximumNumber( 999 );
137 m_warningsBadge->SetMaximumNumber( 999 );
138 m_exclusionsBadge->SetMaximumNumber( 999 );
139
141
142 Layout();
143
144 SetFocus();
145
147 {
148 m_crossprobe = cfg->m_ERCDialog.crossprobe;
149 m_scroll_on_crossprobe = cfg->m_ERCDialog.scroll_on_crossprobe;
150 m_showAllErrors = cfg->m_ERCDialog.show_all_errors;
151 }
152
153 // Now all widgets have the size fixed, call FinishDialogSettings
155}
156
157
159{
162
163 g_lastERCIgnored.clear();
164
165 for( int ii = 0; ii < m_ignoredList->GetItemCount(); ++ii )
166 g_lastERCIgnored.push_back( { m_ignoredList->GetItemText( ii ), m_ignoredList->GetItemData( ii ) } );
167
169 {
170 cfg->m_ERCDialog.crossprobe = m_crossprobe;
171 cfg->m_ERCDialog.scroll_on_crossprobe = m_scroll_on_crossprobe;
172 cfg->m_ERCDialog.show_all_errors = m_showAllErrors;
173 }
174
175 m_markerTreeModel->DecRef();
176}
177
178
180{
181 if( m_parent->CheckAnnotate(
182 []( ERCE_T, const wxString&, SCH_REFERENCE*, SCH_REFERENCE* )
183 {
184 },
186 true,
188 {
189 if( !m_infoBar->IsShownOnScreen() )
190 {
191 wxHyperlinkCtrl* button = new wxHyperlinkCtrl( m_infoBar, wxID_ANY, _( "Show Annotation dialog" ),
192 wxEmptyString );
193
194 button->Bind( wxEVT_COMMAND_HYPERLINK, std::function<void( wxHyperlinkEvent& aEvent )>(
195 [&]( wxHyperlinkEvent& aEvent )
196 {
197 wxHtmlLinkEvent htmlEvent( aEvent.GetId(), wxHtmlLinkInfo( aEvent.GetURL() ) );
198 OnLinkClicked( htmlEvent );
199 } ) );
200
201 m_infoBar->RemoveAllButtons();
202 m_infoBar->AddButton( button );
203 m_infoBar->ShowMessage( _( "Schematic is not fully annotated. ERC results will be incomplete." ) );
204 }
205 }
206 else
207 {
208 if( m_infoBar->IsShownOnScreen() )
209 {
210 m_infoBar->RemoveAllButtons();
211 m_infoBar->Hide();
212 }
213 }
214}
215
216
218{
219 int severities = 0;
220
221 if( m_showErrors->GetValue() )
222 severities |= RPT_SEVERITY_ERROR;
223
224 if( m_showWarnings->GetValue() )
225 severities |= RPT_SEVERITY_WARNING;
226
227 if( m_showExclusions->GetValue() )
228 severities |= RPT_SEVERITY_EXCLUSION;
229
230 return severities;
231}
232
233
234void DIALOG_ERC::OnMenu( wxCommandEvent& event )
235{
236 // Build a pop menu:
237 wxMenu menu;
238
239 menu.Append( 4206, _( "Cross-probe Selected Items" ),
240 _( "Highlight corresponding items on canvas when selected in the ERC list" ),
241 wxITEM_CHECK );
242 menu.Check( 4206, m_crossprobe );
243
244 menu.Append( 4207, _( "Center on Cross-probe" ),
245 _( "When cross-probing, scroll the canvas so that the item is visible" ),
246 wxITEM_CHECK );
247 menu.Check( 4207, m_scroll_on_crossprobe );
248
249 menu.Append( 4208, _( "Show all errors" ),
250 _( "Show duplicate ERC markers on all applicable pins" ),
251 wxITEM_CHECK );
252 menu.Check( 4208, m_showAllErrors );
253
254 // menu_id is the selected submenu id from the popup menu or wxID_NONE
255 int menu_id = m_bMenu->GetPopupMenuSelectionFromUser( menu );
256
257 if( menu_id == 0 || menu_id == 4206 )
258 {
260 }
261 else if( menu_id == 1 || menu_id == 4207 )
262 {
264 }
265 else if( menu_id == 2 || menu_id == 4208 )
266 {
268 }
269}
270
271
272void DIALOG_ERC::OnCharHook( wxKeyEvent& aEvt )
273{
274 if( int hotkey = aEvt.GetKeyCode() )
275 {
276 if( aEvt.ControlDown() )
277 hotkey |= MD_CTRL;
278 if( aEvt.ShiftDown() )
279 hotkey |= MD_SHIFT;
280 if( aEvt.AltDown() )
281 hotkey |= MD_ALT;
282
283 if( hotkey == ACTIONS::excludeMarker.GetHotKey() )
284 {
286 return;
287 }
288 }
289
291}
292
293
295{
296 UpdateData();
297 return true;
298}
299
300
302{
303 // If ERC checks ever get slow enough we'll want a progress indicator...
304 //
305 // double cur = (double) m_progress.load() / m_maxProgress;
306 // cur = std::max( 0.0, std::min( cur, 1.0 ) );
307 //
308 // m_gauge->SetValue( KiROUND( cur * 1000.0 ) );
309 // wxSafeYield( this );
310
311 return !m_cancelled;
312}
313
314
315void DIALOG_ERC::AdvancePhase( const wxString& aMessage )
316{
317 // Will also call Report( aMessage ):
319 SetCurrentProgress( 0.0 );
320}
321
322
323void DIALOG_ERC::Report( const wxString& aMessage )
324{
325 m_messages->Report( aMessage );
326}
327
328
334
335
337{
338 int numErrors = 0;
339 int numWarnings = 0;
340 int numExcluded = 0;
341
342 int numMarkers = 0;
343
344 if( m_markerProvider )
345 {
346 numMarkers += m_markerProvider->GetCount();
347 numErrors += m_markerProvider->GetCount( RPT_SEVERITY_ERROR );
348 numWarnings += m_markerProvider->GetCount( RPT_SEVERITY_WARNING );
349 numExcluded += m_markerProvider->GetCount( RPT_SEVERITY_EXCLUSION );
350 }
351
352 bool markersOverflowed = false;
353
354 // We don't currently have a limit on ERC violations, so the above is always false.
355
356 wxString num;
357 wxString msg;
358
359 if( m_ercRun )
360 {
361 num.Printf( markersOverflowed ? wxT( "%d+" ) : wxT( "%d" ), numMarkers );
362 msg.Printf( m_violationsTitleTemplate, num );
363 }
364 else
365 {
367 msg.Replace( wxT( "(%s)" ), wxEmptyString );
368 }
369
370 m_notebook->SetPageText( 0, msg );
371
372 if( m_ercRun )
373 {
374 num.Printf( wxT( "%d" ), m_ignoredList->GetItemCount() );
375 msg.sprintf( m_ignoredTitleTemplate, num );
376 }
377 else
378 {
380 msg.Replace( wxT( "(%s)" ), wxEmptyString );
381 }
382
383 m_notebook->SetPageText( 1, msg );
384
385 if( !m_ercRun && numErrors == 0 )
386 numErrors = -1;
387
388 if( !m_ercRun && numWarnings == 0 )
389 numWarnings = -1;
390
391 m_errorsBadge->UpdateNumber( numErrors, RPT_SEVERITY_ERROR );
392 m_warningsBadge->UpdateNumber( numWarnings, RPT_SEVERITY_WARNING );
393 m_exclusionsBadge->UpdateNumber( numExcluded, RPT_SEVERITY_EXCLUSION );
394}
395
396
397void DIALOG_ERC::OnDeleteOneClick( wxCommandEvent& aEvent )
398{
399 if( m_notebook->GetSelection() == 0 )
400 {
401 // Clear the selection. It may be the selected ERC marker.
402 m_parent->GetToolManager()->RunAction( ACTIONS::selectionClear );
403
404 m_markerTreeModel->DeleteCurrentItem( true );
405
406 // redraw the schematic
408 }
409
411}
412
413
414void DIALOG_ERC::OnDeleteAllClick( wxCommandEvent& event )
415{
416 bool includeExclusions = false;
417 int numExcluded = 0;
418
419 if( m_markerProvider )
420 numExcluded += m_markerProvider->GetCount( RPT_SEVERITY_EXCLUSION );
421
422 if( numExcluded > 0 )
423 {
424 KICAD_MESSAGE_DIALOG dlg( this, _( "Delete exclusions too?" ), _( "Delete All Markers" ),
425 wxYES_NO | wxCANCEL | wxCENTER | wxICON_QUESTION );
426 dlg.SetYesNoLabels( _( "Errors and Warnings Only" ),
427 _( "Errors, Warnings and Exclusions" ) );
428
429 int ret = dlg.ShowModal();
430
431 if( ret == wxID_CANCEL )
432 return;
433 else if( ret == wxID_NO )
434 includeExclusions = true;
435 }
436
437 deleteAllMarkers( includeExclusions );
438 m_ercRun = false;
439
440 // redraw the schematic
443}
444
445
446void DIALOG_ERC::OnCancelClick( wxCommandEvent& aEvent )
447{
448 if( m_running )
449 {
450 m_cancelled = true;
451 return;
452 }
453
454 m_parent->ClearFocus();
455
456 aEvent.Skip();
457}
458
459
460void DIALOG_ERC::OnCloseErcDialog( wxCloseEvent& aEvent )
461{
462 m_parent->ClearFocus();
463
464 // Dialog is mode-less so let the parent know that it needs to be destroyed.
465 if( !IsModal() && !IsQuasiModal() )
466 {
467 if( wxWindow* parent = GetParent() )
468 wxQueueEvent( parent, new wxCommandEvent( EDA_EVT_CLOSE_ERC_DIALOG, wxID_ANY ) );
469 }
470
471 aEvent.Skip();
472}
473
474
475void DIALOG_ERC::OnLinkClicked( wxHtmlLinkEvent& event )
476{
477 m_parent->OnAnnotate();
478}
479
480
481void DIALOG_ERC::OnRunERCClick( wxCommandEvent& event )
482{
483 wxBusyCursor busy;
484
485 SCHEMATIC* sch = &m_parent->Schematic();
486
488
489 sch->RecordERCExclusions();
490 deleteAllMarkers( true );
491
492 std::vector<std::reference_wrapper<RC_ITEM>> violations = ERC_ITEM::GetItemsWithSeverities();
493 m_ignoredList->DeleteAllItems();
494
495 for( std::reference_wrapper<RC_ITEM>& item : violations )
496 {
497 if( sch->ErcSettings().GetSeverity( item.get().GetErrorCode() ) == RPT_SEVERITY_IGNORE )
498 {
499 wxListItem listItem;
500 listItem.SetId( m_ignoredList->GetItemCount() );
501 listItem.SetText( wxT( " • " ) + item.get().GetErrorText( true ) );
502 listItem.SetData( item.get().GetErrorCode() );
503
504 m_ignoredList->InsertItem( listItem );
505 }
506 }
507
508 m_ignoredList->SetColumnWidth( 0, m_ignoredList->GetParent()->GetClientSize().x - 20 );
509
510 m_cancelled = false;
511 Raise();
512
513 m_runningResultsBook->ChangeSelection( 0 ); // Display the "Tests Running..." tab
514 m_messages->Clear();
515 Update(); // Repaint only, don't enter the full event loop
516
517 m_running = true;
518 m_sdbSizer1Cancel->SetLabel( _( "Cancel" ) );
519 m_sdbSizer1OK->Enable( false );
520 m_deleteOneMarker->Enable( false );
521 m_deleteAllMarkers->Enable( false );
522 m_saveReport->Enable( false );
523
524 int itemsNotAnnotated = m_parent->CheckAnnotate(
525 []( ERCE_T aType, const wxString& aMsg, SCH_REFERENCE* aItemA, SCH_REFERENCE* aItemB )
526 {
527 std::shared_ptr<ERC_ITEM> ercItem = ERC_ITEM::Create( aType );
528 ercItem->SetErrorMessage( aMsg );
529
530 if( aItemB )
531 ercItem->SetItems( aItemA->GetSymbol(), aItemB->GetSymbol() );
532 else
533 ercItem->SetItems( aItemA->GetSymbol() );
534
535 SCH_MARKER* marker = new SCH_MARKER( std::move( ercItem ), aItemA->GetSymbol()->GetPosition() );
536 aItemA->GetSheetPath().LastScreen()->Append( marker );
537 },
539 true,
541
542 testErc();
543
544 if( itemsNotAnnotated )
545 {
546 m_messages->ReportHead( wxString::Format( _( "%d symbol(s) require annotation.<br><br>" ),
547 itemsNotAnnotated ),
549 }
550
551 if( m_cancelled )
552 m_messages->Report( _( "-------- ERC cancelled by user.<br><br>" ), RPT_SEVERITY_INFO );
553 else
554 m_messages->Report( _( "Done.<br><br>" ), RPT_SEVERITY_INFO );
555
556 Raise();
557 Update(); // Repaint only, don't enter the full event loop
558
559 m_running = false;
560 m_sdbSizer1Cancel->SetLabel( _( "Close" ) );
561 m_sdbSizer1OK->Enable( true );
562 m_deleteOneMarker->Enable( true );
563 m_deleteAllMarkers->Enable( true );
564 m_saveReport->Enable( true );
565
566 if( !m_cancelled )
567 {
568 m_sdbSizer1Cancel->SetDefault();
569
570 // wxWidgets has a tendency to keep both buttons highlighted without the following:
571 m_sdbSizer1OK->Enable( false );
572
573 wxMilliSleep( 500 );
574 m_runningResultsBook->ChangeSelection( 1 );
576
577 // now re-enable m_sdbSizerOK button
578 m_sdbSizer1OK->Enable( true );
579 }
580
581 m_ercRun = true;
584 // set float level again, it can be lost due to window events during test run
586}
587
588
590{
591 WINDOW_THAWER thawer( m_parent );
592
593 m_parent->GetCanvas()->GetView()->RefreshDrawingSheetPageInfo();
594 m_parent->GetCanvas()->Refresh();
595}
596
597
599{
600 wxFileName fn;
601
602 SCHEMATIC* sch = &m_parent->Schematic();
603
604 SCH_SCREENS screens( sch->Root() );
605 ERC_TESTER tester( sch, m_showAllErrors );
606
607 {
608 wxBusyCursor dummy;
609 tester.RunTests( m_parent->GetCanvas()->GetView()->GetDrawingSheet(), m_parent,
610 m_parent->Kiway().KiFACE( KIWAY::FACE_CVPCB ), &m_parent->Prj(), this );
611 }
612
613 // Update marker list:
615
616 // Display new markers from the current screen:
617 for( SCH_ITEM* marker : m_parent->GetScreen()->Items().OfType( SCH_MARKER_T ) )
618 {
619 m_parent->GetCanvas()->GetView()->Remove( marker );
620 m_parent->GetCanvas()->GetView()->Add( marker );
621 }
622
623 m_parent->GetCanvas()->Refresh();
624}
625
626
627void DIALOG_ERC::OnERCItemSelected( wxDataViewEvent& aEvent )
628{
629 if( !m_crossprobe )
630 {
631 aEvent.Skip();
632 return;
633 }
634
635 const KIID& itemID = RC_TREE_MODEL::ToUUID( aEvent.GetItem() );
636 SCH_SHEET_PATH sheet;
637 SCH_ITEM* item = m_parent->Schematic().ResolveItem( itemID, &sheet, true );
638
640 {
641 // we already came from a cross-probe of the marker in the document; don't go
642 // around in circles
643 }
644 else if( item && item->GetClass() != wxT( "DELETED_SHEET_ITEM" ) )
645 {
646 const RC_TREE_NODE* node = RC_TREE_MODEL::ToNode( aEvent.GetItem() );
647
648 if( node )
649 {
650 // Determine the owning sheet for sheet-specific items
651 std::shared_ptr<ERC_ITEM> ercItem = std::static_pointer_cast<ERC_ITEM>( node->m_RcItem );
652
653 switch( node->m_Type )
654 {
656 if( ercItem->IsSheetSpecific() )
657 sheet = ercItem->GetSpecificSheetPath();
658 break;
660 if( ercItem->MainItemHasSheetPath() )
661 sheet = ercItem->GetMainItemSheetPath();
662 break;
664 if( ercItem->AuxItemHasSheetPath() )
665 sheet = ercItem->GetAuxItemSheetPath();
666 break;
667 default:
668 break;
669 }
670 }
671
672 WINDOW_THAWER thawer( m_parent );
673
674 if( !sheet.empty() && sheet != m_parent->GetCurrentSheet() )
675 {
676 m_parent->GetToolManager()->RunAction<SCH_SHEET_PATH*>( SCH_ACTIONS::changeSheet, &sheet );
677 m_parent->RedrawScreen( m_parent->GetScreen()->m_ScrollCenter, false );
678 }
679
680 m_parent->FocusOnItem( item, m_scroll_on_crossprobe );
682 }
683
684 aEvent.Skip();
685}
686
687
688void DIALOG_ERC::OnERCItemDClick( wxDataViewEvent& aEvent )
689{
690 if( aEvent.GetItem().IsOk() )
691 {
692 // turn control over to m_parent, hide this DIALOG_ERC window,
693 // no destruction so we can preserve listbox cursor
694 if( !IsModal() )
695 Show( false );
696 }
697
698 aEvent.Skip();
699}
700
701
702void DIALOG_ERC::OnERCItemRClick( wxDataViewEvent& aEvent )
703{
704 TOOL_MANAGER* toolMgr = m_parent->GetToolManager();
705 SCH_INSPECTION_TOOL* inspectionTool = toolMgr->GetTool<SCH_INSPECTION_TOOL>();
706 SCH_EDIT_TOOL* editTool = toolMgr->GetTool<SCH_EDIT_TOOL>();
707 RC_TREE_NODE* node = RC_TREE_MODEL::ToNode( aEvent.GetItem() );
708
709 if( !node )
710 return;
711
712 ERC_SETTINGS& settings = m_parent->Schematic().ErcSettings();
713
714 std::shared_ptr<RC_ITEM> rcItem = node->m_RcItem;
715 wxString listName;
716 wxMenu menu;
717
718 switch( settings.GetSeverity( rcItem->GetErrorCode() ) )
719 {
720 case RPT_SEVERITY_ERROR: listName = _( "errors" ); break;
721 case RPT_SEVERITY_WARNING: listName = _( "warnings" ); break;
722 default: listName = _( "appropriate" ); break;
723 }
724
725 enum MENU_IDS
726 {
727 ID_EDIT_EXCLUSION_COMMENT = 4467,
728 ID_REMOVE_EXCLUSION,
729 ID_REMOVE_EXCLUSION_ALL,
730 ID_ADD_EXCLUSION,
731 ID_ADD_EXCLUSION_WITH_COMMENT,
732 ID_ADD_EXCLUSION_ALL,
733 ID_INSPECT_VIOLATION,
734 ID_FIX_VIOLATION,
735 ID_EDIT_PIN_CONFLICT_MAP,
736 ID_EDIT_CONNECTION_GRID,
737 ID_SET_SEVERITY_TO_ERROR,
738 ID_SET_SEVERITY_TO_WARNING,
739 ID_SET_SEVERITY_TO_IGNORE,
740 ID_EDIT_SEVERITIES,
741 };
742
743 if( rcItem->GetParent()->IsExcluded() )
744 {
745 menu.Append( ID_REMOVE_EXCLUSION,
746 _( "Remove exclusion for this violation" ),
747 wxString::Format( _( "It will be placed back in the %s list" ), listName ) );
748
749 menu.Append( ID_EDIT_EXCLUSION_COMMENT,
750 _( "Edit exclusion comment..." ) );
751 }
752 else
753 {
754 menu.Append( ID_ADD_EXCLUSION,
755 _( "Exclude this violation" ),
756 wxString::Format( _( "It will be excluded from the %s list" ), listName ) );
757
758 menu.Append( ID_ADD_EXCLUSION_WITH_COMMENT,
759 _( "Exclude with comment..." ),
760 wxString::Format( _( "It will be excluded from the %s list" ), listName ) );
761 }
762
763 menu.AppendSeparator();
764
765 wxString inspectERCErrorMenuText = inspectionTool->InspectERCErrorMenuText( rcItem );
766 wxString fixERCErrorMenuText = editTool->FixERCErrorMenuText( rcItem );
767
768 if( !inspectERCErrorMenuText.IsEmpty() || !fixERCErrorMenuText.IsEmpty() )
769 {
770 if( !inspectERCErrorMenuText.IsEmpty() )
771 menu.Append( ID_INSPECT_VIOLATION, inspectERCErrorMenuText );
772
773 if( !fixERCErrorMenuText.IsEmpty() )
774 menu.Append( ID_FIX_VIOLATION, fixERCErrorMenuText );
775
776 menu.AppendSeparator();
777 }
778
779 if( rcItem->GetErrorCode() == ERCE_PIN_TO_PIN_WARNING
780 || rcItem->GetErrorCode() == ERCE_PIN_TO_PIN_ERROR )
781 {
782 // Pin to pin severities edited through pin conflict map
783 }
784 else if( settings.GetSeverity( rcItem->GetErrorCode() ) == RPT_SEVERITY_WARNING )
785 {
786 menu.Append( ID_SET_SEVERITY_TO_ERROR,
787 wxString::Format( _( "Change severity to Error for all '%s' violations" ),
788 rcItem->GetErrorText( true ) ),
789 _( "Violation severities can also be edited in Schematic Setup" ) );
790 }
791 else
792 {
793 menu.Append( ID_SET_SEVERITY_TO_WARNING,
794 wxString::Format( _( "Change severity to Warning for all '%s' violations" ),
795 rcItem->GetErrorText( true ) ),
796 _( "Violation severities can also be edited in Schematic Setup" ) );
797 }
798
799 menu.Append( ID_SET_SEVERITY_TO_IGNORE,
800 wxString::Format( _( "Ignore all '%s' violations" ), rcItem->GetErrorText( true ) ),
801 _( "Violations will not be checked or reported" ) );
802
803 menu.AppendSeparator();
804
805 if( rcItem->GetErrorCode() == ERCE_PIN_TO_PIN_WARNING
806 || rcItem->GetErrorCode() == ERCE_PIN_TO_PIN_ERROR )
807 {
808 menu.Append( ID_EDIT_PIN_CONFLICT_MAP,
809 _( "Edit pin-to-pin conflict map..." ),
810 _( "Open the Schematic Setup dialog" ) );
811 }
812 else
813 {
814 menu.Append( ID_EDIT_SEVERITIES,
815 _( "Edit violation severities..." ),
816 _( "Open the Schematic Setup dialog" ) );
817 }
818
819 if( rcItem->GetErrorCode() == ERCE_ENDPOINT_OFF_GRID )
820 {
821 menu.Append( ID_EDIT_CONNECTION_GRID,
822 _( "Edit connection grid spacing..." ),
823 _( "Open the Schematic Setup dialog" ) );
824 }
825
826 bool modified = false;
827 int command = GetPopupMenuSelectionFromUser( menu );
828
829 switch( command )
830 {
831 case ID_EDIT_EXCLUSION_COMMENT:
832 if( SCH_MARKER* marker = dynamic_cast<SCH_MARKER*>( node->m_RcItem->GetParent() ) )
833 {
834 WX_TEXT_ENTRY_DIALOG dlg( this, wxEmptyString, _( "Exclusion Comment" ), marker->GetComment(), true );
835
836 if( dlg.ShowModal() == wxID_CANCEL )
837 break;
838
839 setMarkerExcluded( m_markerProvider, marker, true, dlg.GetValue() );
840
841 // Update view
842 static_cast<RC_TREE_MODEL*>( aEvent.GetModel() )->ValueChanged( node );
843 modified = true;
844 }
845
846 break;
847
848 case ID_REMOVE_EXCLUSION:
849 if( SCH_MARKER* marker = dynamic_cast<SCH_MARKER*>( node->m_RcItem->GetParent() ) )
850 {
851 setMarkerExcluded( m_markerProvider, marker, false );
852 m_parent->GetCanvas()->GetView()->Update( marker );
853
854 // The restored severity may fall outside the current filter, so re-filter when it no
855 // longer matches instead of leaving a stale node in the view.
856 if( getSeverities() & marker->GetSeverity() )
857 static_cast<RC_TREE_MODEL*>( aEvent.GetModel() )->ValueChanged( node );
858 else
859 static_cast<RC_TREE_MODEL*>( aEvent.GetModel() )->Update( m_markerProvider,
860 getSeverities() );
861
862 modified = true;
863 }
864
865 break;
866
867 case ID_ADD_EXCLUSION:
868 case ID_ADD_EXCLUSION_WITH_COMMENT:
869 if( SCH_MARKER* marker = dynamic_cast<SCH_MARKER*>( node->m_RcItem->GetParent() ) )
870 {
871 wxString comment;
872
873 if( command == ID_ADD_EXCLUSION_WITH_COMMENT )
874 {
875 WX_TEXT_ENTRY_DIALOG dlg( this, wxEmptyString, _( "Exclusion Comment" ), wxEmptyString, true );
876
877 if( dlg.ShowModal() == wxID_CANCEL )
878 break;
879
880 comment = dlg.GetValue();
881 }
882
883 setMarkerExcluded( m_markerProvider, marker, true, comment );
884
885 m_parent->GetCanvas()->GetView()->Update( marker );
886
887 // The marker survives as an exclusion, so when exclusions are hidden it must leave
888 // the filtered view without being counted as deleted; a rebuild re-filters cleanly.
890 static_cast<RC_TREE_MODEL*>( aEvent.GetModel() )->ValueChanged( node );
891 else
892 static_cast<RC_TREE_MODEL*>( aEvent.GetModel() )->Update( m_markerProvider,
893 getSeverities() );
894
895 modified = true;
896 }
897
898 break;
899
900 case ID_INSPECT_VIOLATION:
901 inspectionTool->InspectERCError( node->m_RcItem );
902 break;
903
904 case ID_FIX_VIOLATION:
905 editTool->FixERCError( node->m_RcItem );
906 break;
907
908 case ID_SET_SEVERITY_TO_ERROR:
909 settings.SetSeverity( rcItem->GetErrorCode(), RPT_SEVERITY_ERROR );
910
911 for( SCH_ITEM* item : m_parent->GetScreen()->Items().OfType( SCH_MARKER_T ) )
912 {
913 SCH_MARKER* marker = static_cast<SCH_MARKER*>( item );
914
915 if( marker->GetRCItem()->GetErrorCode() == rcItem->GetErrorCode() )
916 m_parent->GetCanvas()->GetView()->Update( marker );
917 }
918
919 // Rebuild model and view
920 static_cast<RC_TREE_MODEL*>( aEvent.GetModel() )->Update( m_markerProvider, getSeverities() );
921 modified = true;
922 break;
923
924 case ID_SET_SEVERITY_TO_WARNING:
925 settings.SetSeverity( rcItem->GetErrorCode(), RPT_SEVERITY_WARNING );
926
927 for( SCH_ITEM* item : m_parent->GetScreen()->Items().OfType( SCH_MARKER_T ) )
928 {
929 SCH_MARKER* marker = static_cast<SCH_MARKER*>( item );
930
931 if( marker->GetRCItem()->GetErrorCode() == rcItem->GetErrorCode() )
932 m_parent->GetCanvas()->GetView()->Update( marker );
933 }
934
935 // Rebuild model and view
936 static_cast<RC_TREE_MODEL*>( aEvent.GetModel() )->Update( m_markerProvider, getSeverities() );
937 modified = true;
938 break;
939
940 case ID_SET_SEVERITY_TO_IGNORE:
941 {
942 settings.SetSeverity( rcItem->GetErrorCode(), RPT_SEVERITY_IGNORE );
943
944 if( rcItem->GetErrorCode() == ERCE_PIN_TO_PIN_ERROR )
946
947 wxListItem listItem;
948 listItem.SetId( m_ignoredList->GetItemCount() );
949 listItem.SetText( wxT( " • " ) + rcItem->GetErrorText( true ) );
950 listItem.SetData( rcItem->GetErrorCode() );
951
952 m_ignoredList->InsertItem( listItem );
953
954 // Clear the selection before deleting markers. It may be some selected ERC markers.
955 // Deleting a selected marker without deselecting it first generates a crash
956 m_parent->GetToolManager()->RunAction( ACTIONS::selectionClear );
957
958 SCH_SCREENS ScreenList( m_parent->Schematic().Root() );
959 ScreenList.DeleteMarkers( MARKER_BASE::MARKER_ERC, rcItem->GetErrorCode() );
960
961 // Rebuild model and view
962 static_cast<RC_TREE_MODEL*>( aEvent.GetModel() )->Update( m_markerProvider, getSeverities() );
963 modified = true;
964 break;
965 }
966
967 case ID_EDIT_PIN_CONFLICT_MAP:
968 m_parent->ShowSchematicSetupDialog( _( "Pin Conflicts Map" ) );
969 break;
970
971 case ID_EDIT_SEVERITIES:
972 m_parent->ShowSchematicSetupDialog( _( "Violation Severity" ) );
973 break;
974
975 case ID_EDIT_CONNECTION_GRID:
976 m_parent->ShowSchematicSetupDialog( _( "Formatting" ) );
977 break;
978 }
979
980 if( modified )
981 {
984 m_parent->OnModify();
985 }
986}
987
988
989void DIALOG_ERC::OnIgnoredItemRClick( wxListEvent& event )
990{
991 ERC_SETTINGS& settings = m_parent->Schematic().ErcSettings();
992 int errorCode = (int) event.m_item.GetData();
993 wxMenu menu;
994
995 menu.Append( RPT_SEVERITY_ERROR, _( "Error" ), wxEmptyString, wxITEM_RADIO );
996 menu.Append( RPT_SEVERITY_WARNING, _( "Warning" ), wxEmptyString, wxITEM_RADIO );
997 menu.Append( RPT_SEVERITY_IGNORE, _( "Ignore" ), wxEmptyString, wxITEM_RADIO );
998
999 menu.Check( settings.GetSeverity( errorCode ), true );
1000
1001 int severity = GetPopupMenuSelectionFromUser( menu );
1002
1003 if( severity > 0 )
1004 {
1005 if( settings.GetSeverity( errorCode ) != severity )
1006 {
1007 settings.SetSeverity( errorCode, (SEVERITY) severity );
1008
1011 m_parent->OnModify();
1012 }
1013 }
1014}
1015
1016
1018{
1019 if( m_notebook->IsShown() )
1020 {
1021 if( m_notebook->GetSelection() != 0 )
1022 m_notebook->SetSelection( 0 );
1023
1024 m_markerTreeModel->PrevMarker();
1025 }
1026}
1027
1028
1030{
1031 if( m_notebook->IsShown() )
1032 {
1033 if( m_notebook->GetSelection() != 0 )
1034 m_notebook->SetSelection( 0 );
1035
1036 m_markerTreeModel->NextMarker();
1037 }
1038}
1039
1040
1042{
1043 if( m_notebook->IsShown() )
1044 {
1045 m_notebook->SetSelection( 0 );
1046 m_markerTreeModel->SelectMarker( aMarker );
1047
1048 // wxWidgets on some platforms fails to correctly ensure that a selected item is
1049 // visible, so we have to do it in a separate idle event.
1050 m_centerMarkerOnIdle = aMarker;
1051 Bind( wxEVT_IDLE, &DIALOG_ERC::centerMarkerIdleHandler, this );
1052 }
1053}
1054
1055
1056void DIALOG_ERC::centerMarkerIdleHandler( wxIdleEvent& aEvent )
1057{
1058 if( m_markerTreeModel->GetView()->IsFrozen() )
1059 return;
1060
1061 m_markerTreeModel->CenterMarker( m_centerMarkerOnIdle );
1062 m_centerMarkerOnIdle = nullptr;
1063 Unbind( wxEVT_IDLE, &DIALOG_ERC::centerMarkerIdleHandler, this );
1064}
1065
1066
1068{
1069 SCH_MARKER* marker = aMarker;
1070
1071 if( marker != nullptr )
1072 m_markerTreeModel->SelectMarker( marker );
1073
1074 RC_TREE_NODE* node = nullptr;
1075
1076 if( m_notebook->GetSelection() == 0 )
1077 {
1078 node = RC_TREE_MODEL::ToNode( m_markerDataView->GetCurrentItem() );
1079
1080 if( node && node->m_RcItem )
1081 marker = dynamic_cast<SCH_MARKER*>( node->m_RcItem->GetParent() );
1082 }
1083
1084 if( !marker || marker->IsExcluded() )
1085 return;
1086
1087 // Route through the provider so its cached counts stay in sync even when the dialog is not on
1088 // the violations tab and has no tree node to refresh.
1089 setMarkerExcluded( m_markerProvider, marker, true );
1090 m_parent->GetCanvas()->GetView()->Update( marker );
1091
1092 if( node )
1093 {
1094 // The marker survives as an exclusion, so when exclusions are hidden it must leave the
1095 // filtered view without being counted as deleted; a rebuild re-filters cleanly.
1097 m_markerTreeModel->ValueChanged( node );
1098 else
1100 }
1101
1104 m_parent->OnModify();
1105}
1106
1107
1108void DIALOG_ERC::OnEditViolationSeverities( wxHyperlinkEvent& aEvent )
1109{
1110 m_parent->ShowSchematicSetupDialog( _( "Violation Severity" ) );
1111}
1112
1113
1114void DIALOG_ERC::OnSeverity( wxCommandEvent& aEvent )
1115{
1116 if( aEvent.GetEventObject() == m_showAll )
1117 {
1118 m_showErrors->SetValue( true );
1119 m_showWarnings->SetValue( aEvent.IsChecked() );
1120 m_showExclusions->SetValue( aEvent.IsChecked() );
1121 }
1122
1123 UpdateData();
1124}
1125
1126
1127void DIALOG_ERC::deleteAllMarkers( bool aIncludeExclusions )
1128{
1129 // Clear current selection list to avoid selection of deleted items
1130 // Freeze to avoid repainting the dialog, which can cause a RePaint()
1131 // of the screen as well
1132 Freeze();
1133
1134 m_parent->GetToolManager()->RunAction( ACTIONS::selectionClear );
1135
1136 m_markerTreeModel->DeleteItems( false, aIncludeExclusions, false );
1137
1138 SCH_SCREENS screens( m_parent->Schematic().Root() );
1139 screens.DeleteAllMarkers( MARKER_BASE::MARKER_ERC, aIncludeExclusions );
1140
1141 // DeleteItems() only decremented the cached counts for markers matching the current filter,
1142 // but DeleteAllMarkers() removed hidden severities too; rebuild to resync the counts.
1144
1145 Thaw();
1146}
1147
1148
1149void DIALOG_ERC::OnSaveReport( wxCommandEvent& aEvent )
1150{
1151 wxFileName fn( wxS( "ERC." ) + wxString( FILEEXT::ReportFileExtension ) );
1152
1153 wxFileDialog dlg( this, _( "Save Report File" ), Prj().GetProjectPath(), fn.GetFullName(),
1155 wxFD_SAVE | wxFD_OVERWRITE_PROMPT );
1156
1158
1159 if( dlg.ShowModal() != wxID_OK )
1160 return;
1161
1162 fn = dlg.GetPath();
1163
1164 if( fn.GetExt().IsEmpty() )
1165 fn.SetExt( FILEEXT::ReportFileExtension );
1166
1167 if( !fn.IsAbsolute() )
1168 {
1169 wxString prj_path = Prj().GetProjectPath();
1170 fn.MakeAbsolute( prj_path );
1171 }
1172
1173 ERC_REPORT reportWriter( &m_parent->Schematic(), m_parent->GetUserUnits(), m_markerProvider );
1174
1175 bool success = false;
1176 if( fn.GetExt() == FILEEXT::JsonFileExtension )
1177 success = reportWriter.WriteJsonReport( fn.GetFullPath() );
1178 else
1179 success = reportWriter.WriteTextReport( fn.GetFullPath() );
1180
1181 if( success )
1182 m_messages->Report( wxString::Format( _( "Report file '%s' created." ), fn.GetFullPath() ) );
1183 else
1184 DisplayErrorMessage( this, wxString::Format( _( "Failed to create file '%s'." ), fn.GetFullPath() ) );
1185}
wxBitmapBundle KiBitmapBundle(BITMAPS aBitmap, int aMinHeight)
Definition bitmap.cpp:106
static TOOL_ACTION excludeMarker
Definition actions.h:125
static TOOL_ACTION selectionClear
Clear the current selection.
Definition actions.h:220
wxButton * m_saveReport
wxButton * m_sdbSizer1Cancel
wxSimplebook * m_runningResultsBook
wxCheckBox * m_showExclusions
NUMBER_BADGE * m_errorsBadge
WX_INFOBAR * m_infoBar
STD_BITMAP_BUTTON * m_bMenu
wxCheckBox * m_showErrors
wxNotebook * m_notebook
wxCheckBox * m_showAll
NUMBER_BADGE * m_exclusionsBadge
wxListCtrl * m_ignoredList
WX_HTML_REPORT_BOX * m_messages
wxDataViewCtrl * m_markerDataView
wxButton * m_deleteAllMarkers
NUMBER_BADGE * m_warningsBadge
wxButton * m_deleteOneMarker
wxCheckBox * m_showWarnings
wxButton * m_sdbSizer1OK
DIALOG_ERC_BASE(wxWindow *parent, wxWindowID id=wxID_ANY, const wxString &title=_("Electrical Rules Checker"), const wxPoint &pos=wxDefaultPosition, const wxSize &size=wxSize(-1,-1), long style=wxDEFAULT_DIALOG_STYLE|wxRESIZE_BORDER)
void OnMenu(wxCommandEvent &aEvent) override
void ExcludeMarker(SCH_MARKER *aMarker=nullptr)
Exclude aMarker from the ERC list.
void OnIgnoredItemRClick(wxListEvent &aEvent) override
const SCH_MARKER * m_centerMarkerOnIdle
Definition dialog_erc.h:115
void OnERCItemDClick(wxDataViewEvent &aEvent) override
std::shared_ptr< RC_ITEMS_PROVIDER > m_markerProvider
Definition dialog_erc.h:109
bool TransferDataToWindow() override
bool m_ercRun
Definition dialog_erc.h:113
bool m_crossprobe
Definition dialog_erc.h:117
DIALOG_ERC(SCH_EDIT_FRAME *parent)
bool m_scroll_on_crossprobe
Definition dialog_erc.h:118
void testErc()
void SelectMarker(const SCH_MARKER *aMarker)
bool updateUI() override
SCH_EDIT_FRAME * m_parent
Definition dialog_erc.h:103
wxString m_violationsTitleTemplate
Definition dialog_erc.h:106
void OnERCItemRClick(wxDataViewEvent &aEvent) override
void centerMarkerIdleHandler(wxIdleEvent &aEvent)
void OnDeleteAllClick(wxCommandEvent &event) override
void OnLinkClicked(wxHtmlLinkEvent &event) override
void OnCharHook(wxKeyEvent &aEvt) override
void OnRunERCClick(wxCommandEvent &event) override
void deleteAllMarkers(bool aIncludeExclusions)
wxString m_ignoredTitleTemplate
Definition dialog_erc.h:107
void OnDeleteOneClick(wxCommandEvent &event) override
void UpdateData()
void OnSaveReport(wxCommandEvent &aEvent) override
int getSeverities()
void PrevMarker()
void NextMarker()
SCHEMATIC * m_currentSchematic
Definition dialog_erc.h:104
void OnEditViolationSeverities(wxHyperlinkEvent &aEvent) override
void UpdateAnnotationWarning()
void redrawDrawPanel()
void Report(const wxString &aMessage) override
Display aMessage in the progress bar dialog.
void OnERCItemSelected(wxDataViewEvent &aEvent) override
RC_TREE_MODEL * m_markerTreeModel
Definition dialog_erc.h:110
void updateDisplayedCounts()
void OnSeverity(wxCommandEvent &aEvent) override
bool m_running
Definition dialog_erc.h:112
bool m_showAllErrors
Definition dialog_erc.h:119
void OnCloseErcDialog(wxCloseEvent &event) override
void OnCancelClick(wxCommandEvent &event) override
bool Show(bool show) override
void SetupStandardButtons(std::map< int, wxString > aLabels={})
bool IsQuasiModal() const
Definition dialog_shim.h:90
void finishDialogSettings()
In all dialogs, we must call the same functions to fix minimal dlg size, the default position and per...
virtual void OnCharHook(wxKeyEvent &aEvt)
int ShowModal() override
static std::shared_ptr< ERC_ITEM > Create(int aErrorCode)
Constructs an ERC_ITEM for the given error code.
Definition erc_item.cpp:292
static std::vector< std::reference_wrapper< RC_ITEM > > GetItemsWithSeverities()
Definition erc_item.h:72
bool WriteJsonReport(const wxString &aFullFileName)
Writes a JSON formatted ERC Report to the given file path in the c-locale.
bool WriteTextReport(const wxString &aFullFileName)
Writes the text report also available via GetTextReport directly to a given file path.
Container for ERC settings.
SEVERITY GetSeverity(int aErrorCode) const
void SetSeverity(int aErrorCode, SEVERITY aSeverity)
void RunTests(DS_PROXY_VIEW_ITEM *aDrawingSheet, SCH_EDIT_FRAME *aEditFrame, KIFACE *aCvPcb, PROJECT *aProject, PROGRESS_REPORTER *aProgressReporter)
Definition erc.cpp:2480
A specialisation of the RC_TREE_MODEL class to enable ERC errors / warnings to be resolved in a speci...
Definition erc_item.h:34
Definition kiid.h:44
PROJECT & Prj() const
Return a reference to the PROJECT associated with this KIWAY.
@ FACE_CVPCB
Definition kiway.h:320
bool IsExcluded() const
Definition marker_base.h:89
std::shared_ptr< RC_ITEM > GetRCItem() const
virtual void AdvancePhase() override
Use the next available virtual zone of the dialog progress bar.
virtual void SetCurrentProgress(double aProgress) override
Set the progress value to aProgress (0..1).
virtual void AdvancePhase()=0
Use the next available virtual zone of the dialog progress bar.
virtual const wxString GetProjectPath() const
Return the full path of the project.
Definition project.cpp:183
int GetErrorCode() const
Definition rc_item.h:157
MARKER_BASE * GetParent() const
Definition rc_item.h:132
static RC_TREE_NODE * ToNode(wxDataViewItem aItem)
Definition rc_item.h:267
void ValueChanged(RC_TREE_NODE *aNode)
Definition rc_item.cpp:617
void Update(std::shared_ptr< RC_ITEMS_PROVIDER > aProvider, int aSeverities)
Definition rc_item.cpp:419
static KIID ToUUID(wxDataViewItem aItem)
Definition rc_item.cpp:223
std::shared_ptr< RC_ITEM > m_RcItem
Definition rc_item.h:246
NODE_TYPE m_Type
Definition rc_item.h:245
Holds all the data relating to one schematic.
Definition schematic.h:90
void RecordERCExclusions()
Scan existing markers and record data from any that are Excluded.
SCH_SHEET & Root() const
Definition schematic.h:134
ERC_SETTINGS & ErcSettings() const
static TOOL_ACTION changeSheet
Schematic editor (Eeschema) main window.
SCHEMATIC & Schematic() const
void InspectERCError(const std::shared_ptr< RC_ITEM > &aERCItem)
wxString InspectERCErrorMenuText(const std::shared_ptr< RC_ITEM > &aERCItem)
Base class for any item which can be embedded within the SCHEMATIC container class,...
Definition sch_item.h:162
wxString GetClass() const override
Return the class name.
Definition sch_item.h:172
A helper to define a symbol's reference designator in a schematic.
const SCH_SHEET_PATH & GetSheetPath() const
SCH_SYMBOL * GetSymbol() const
Container class that holds multiple SCH_SCREEN objects in a hierarchy.
Definition sch_screen.h:746
void DeleteMarkers(enum MARKER_BASE::MARKER_T aMarkerTyp, int aErrorCode, bool aIncludeExclusions=true)
Delete all markers of a particular type and error code.
void DeleteAllMarkers(enum MARKER_BASE::MARKER_T aMarkerType, bool aIncludeExclusions)
Delete all electronic rules check markers of aMarkerType from all the screens in the list.
void Append(SCH_ITEM *aItem, bool aUpdateLibSymbol=true)
Handle access to a stack of flattened SCH_SHEET objects by way of a path for creating a flattened sch...
bool empty() const
Forwarded method from std::vector.
SCH_SCREEN * LastScreen()
VECTOR2I GetPosition() const override
Definition sch_symbol.h:913
An implementation of the RC_ITEM_LIST interface which uses the global SHEETLIST to fulfill the contra...
void SetMarkerExcluded(SCH_MARKER *aMarker, bool aExcluded, const wxString &aComment=wxEmptyString)
Set the exclusion state of a marker while keeping the cached severity counts in sync.
Master controller class:
A KICAD version of wxTextEntryDialog which supports the various improvements/work-arounds from DIALOG...
wxString GetValue() const
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.
#define KICAD_MESSAGE_DIALOG
Definition confirm.h:48
static bool g_lastERCRun
static void setMarkerExcluded(const std::shared_ptr< RC_ITEMS_PROVIDER > &aProvider, SCH_MARKER *aMarker, bool aExcluded, const wxString &aComment=wxEmptyString)
wxDEFINE_EVENT(EDA_EVT_CLOSE_ERC_DIALOG, wxCommandEvent)
static std::vector< std::pair< wxString, int > > g_lastERCIgnored
static SCHEMATIC * g_lastERCSchematic
#define DIALOG_ERC_WINDOW_NAME
Definition dialog_erc.h:35
#define _(s)
static int DEFAULT_SINGLE_COL_WIDTH
ERCE_T
ERC error codes.
@ ERCE_ENDPOINT_OFF_GRID
Pin or wire-end off grid.
@ ERCE_PIN_TO_PIN_WARNING
@ ERCE_PIN_TO_PIN_ERROR
static const std::string ReportFileExtension
static const std::string JsonFileExtension
static wxString JsonFileWildcard()
static wxString ReportFileWildcard()
void SetFloatLevel(wxWindow *aWindow)
Intended to set the floating window level in macOS on a window.
Definition wxgtk/ui.cpp:437
void ForceFocus(wxWindow *aWindow)
Pass the current focus to the window.
Definition wxgtk/ui.cpp:126
void AllowNetworkFileSystems(wxDialog *aDialog)
Configure a file dialog to show network and virtual file systems.
Definition wxgtk/ui.cpp:448
SEVERITY
@ RPT_SEVERITY_WARNING
@ RPT_SEVERITY_ERROR
@ RPT_SEVERITY_EXCLUSION
@ RPT_SEVERITY_IGNORE
@ RPT_SEVERITY_INFO
@ ANNOTATE_ALL
Annotate the full schematic.
@ SYMBOL_FILTER_NON_POWER
T * GetAppSettings(const char *aFilename)
std::vector< FAB_LAYER_COLOR > dummy
@ MD_ALT
Definition tool_event.h:141
@ MD_CTRL
Definition tool_event.h:140
@ MD_SHIFT
Definition tool_event.h:139
@ SCH_MARKER_T
Definition typeinfo.h:155
Definition of file extensions used in Kicad.