Fold annotation error reporting into ERC.

Fixes https://gitlab.com/kicad/code/kicad/issues/6938
This commit is contained in:
Jeff Young 2021-01-24 22:25:32 +00:00
parent 72eb7c7143
commit 0a1a5ea669
10 changed files with 133 additions and 116 deletions

View File

@ -1,7 +1,7 @@
/* /*
* This program source code file is part of KiCad, a free EDA CAD application. * This program source code file is part of KiCad, a free EDA CAD application.
* *
* Copyright (C) 2004-2020 KiCad Developers, see AUTHORS.txt for contributors. * Copyright (C) 2004-2021 KiCad Developers, see AUTHORS.txt for contributors.
* *
* This program is free software; you can redistribute it and/or * This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -23,12 +23,11 @@
#include <algorithm> #include <algorithm>
#include <sch_draw_panel.h>
#include <confirm.h> #include <confirm.h>
#include <reporter.h> #include <reporter.h>
#include <sch_edit_frame.h> #include <sch_edit_frame.h>
#include <schematic.h> #include <schematic.h>
#include <erc_settings.h>
#include <sch_reference_list.h> #include <sch_reference_list.h>
#include <class_library.h> #include <class_library.h>
@ -243,8 +242,15 @@ void SCH_EDIT_FRAME::AnnotateComponents( bool aAnnotateSchematic,
} }
// Final control (just in case ... ). // Final control (just in case ... ).
if( !CheckAnnotate( aReporter, !aAnnotateSchematic ) ) if( !CheckAnnotate(
[ &aReporter ]( ERCE_T , const wxString& aMsg, SCH_REFERENCE* , SCH_REFERENCE* )
{
aReporter.Report( aMsg, RPT_SEVERITY_ERROR );
},
!aAnnotateSchematic ) )
{
aReporter.ReportTail( _( "Annotation complete." ), RPT_SEVERITY_ACTION ); aReporter.ReportTail( _( "Annotation complete." ), RPT_SEVERITY_ACTION );
}
// Update on screen references, that can be modified by previous calculations: // Update on screen references, that can be modified by previous calculations:
GetCurrentSheet().UpdateAllScreenReferences(); GetCurrentSheet().UpdateAllScreenReferences();
@ -259,7 +265,7 @@ void SCH_EDIT_FRAME::AnnotateComponents( bool aAnnotateSchematic,
} }
int SCH_EDIT_FRAME::CheckAnnotate( REPORTER& aReporter, bool aOneSheetOnly ) int SCH_EDIT_FRAME::CheckAnnotate( ANNOTATION_ERROR_HANDLER aErrorHandler, bool aOneSheetOnly )
{ {
SCH_REFERENCE_LIST referenceList; SCH_REFERENCE_LIST referenceList;
constexpr bool includePowerSymbols = false; constexpr bool includePowerSymbols = false;
@ -274,5 +280,5 @@ int SCH_EDIT_FRAME::CheckAnnotate( REPORTER& aReporter, bool aOneSheetOnly )
if( referenceList.GetCount() == 0 ) if( referenceList.GetCount() == 0 )
return 0; return 0;
return referenceList.CheckAnnotation( aReporter ); return referenceList.CheckAnnotation( aErrorHandler );
} }

View File

@ -1,14 +1,9 @@
/**
* @file component_references_lister.cpp
* @brief functions to create a component flat list and to annotate schematic.
*/
/* /*
* This program source code file is part of KiCad, a free EDA CAD application. * This program source code file is part of KiCad, a free EDA CAD application.
* *
* Copyright (C) 1992-2018 jean-pierre Charras <jp.charras at wanadoo.fr> * Copyright (C) 1992-2018 jean-pierre Charras <jp.charras at wanadoo.fr>
* Copyright (C) 1992-2011 Wayne Stambaugh <stambaughw@verizon.net> * Copyright (C) 1992-2011 Wayne Stambaugh <stambaughw@verizon.net>
* Copyright (C) 1992-2020 KiCad Developers, see AUTHORS.txt for contributors. * Copyright (C) 1992-2021 KiCad Developers, see AUTHORS.txt for contributors.
* *
* This program is free software; you can redistribute it and/or * This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -28,6 +23,11 @@
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/ */
/**
* @file component_references_lister.cpp
* @brief functions to create a component flat list and to annotate schematic.
*/
#include <sch_reference_list.h> #include <sch_reference_list.h>
#include <wx/regex.h> #include <wx/regex.h>
@ -36,8 +36,7 @@
#include <unordered_set> #include <unordered_set>
#include <refdes_utils.h> #include <refdes_utils.h>
#include <reporter.h> #include <erc_settings.h>
#include <sch_component.h> #include <sch_component.h>
#include <sch_edit_frame.h> #include <sch_edit_frame.h>
@ -496,7 +495,7 @@ void SCH_REFERENCE_LIST::Annotate( bool aUseSheetNum, int aSheetIntervalId, int
} }
} }
int SCH_REFERENCE_LIST::CheckAnnotation( REPORTER& aReporter ) int SCH_REFERENCE_LIST::CheckAnnotation( ANNOTATION_ERROR_HANDLER aHandler )
{ {
int error = 0; int error = 0;
wxString tmp; wxString tmp;
@ -521,8 +520,7 @@ int SCH_REFERENCE_LIST::CheckAnnotation( REPORTER& aReporter )
tmp = wxT( "?" ); tmp = wxT( "?" );
if( ( flatList[ii].m_unit > 0 ) if( ( flatList[ii].m_unit > 0 ) && ( flatList[ii].m_unit < 0x7FFFFFFF ) )
&& ( flatList[ii].m_unit < 0x7FFFFFFF ) )
{ {
msg.Printf( _( "Item not annotated: %s%s (unit %d)\n" ), msg.Printf( _( "Item not annotated: %s%s (unit %d)\n" ),
flatList[ii].GetRef(), flatList[ii].GetRef(),
@ -536,37 +534,34 @@ int SCH_REFERENCE_LIST::CheckAnnotation( REPORTER& aReporter )
tmp ); tmp );
} }
aReporter.Report( msg, RPT_SEVERITY_WARNING ); aHandler( ERCE_UNANNOTATED, msg, &flatList[ii], nullptr );
error++; error++;
break; break;
} }
// Error if unit number selected does not exist ( greater than the number of // Error if unit number selected does not exist (greater than the number of units in
// parts in the component ). This can happen if a component has changed in a // the component). This can happen if a component has changed in a library after a
// library after a previous annotation. // previous annotation.
if( std::max( flatList[ii].GetLibPart()->GetUnitCount(), 1 ) if( std::max( flatList[ii].GetLibPart()->GetUnitCount(), 1 ) < flatList[ii].m_unit )
< flatList[ii].m_unit )
{ {
if( flatList[ii].m_numRef >= 0 ) if( flatList[ii].m_numRef >= 0 )
tmp << flatList[ii].m_numRef; tmp << flatList[ii].m_numRef;
else else
tmp = wxT( "?" ); tmp = wxT( "?" );
msg.Printf( _( "Error: symbol %s%s unit %d and symbol has only %d units defined\n" ), msg.Printf( _( "Error: symbol %s%s%s (unit %d) exceeds units defined (%d)\n" ),
flatList[ii].GetRef(), flatList[ii].GetRef(),
tmp, tmp,
LIB_PART::SubReference( flatList[ii].m_unit ),
flatList[ii].m_unit, flatList[ii].m_unit,
flatList[ii].GetLibPart()->GetUnitCount() ); flatList[ii].GetLibPart()->GetUnitCount() );
aReporter.Report( msg, RPT_SEVERITY_ERROR ); aHandler( ERCE_EXTRA_UNITS, msg, &flatList[ii], nullptr );
error++; error++;
break; break;
} }
} }
if( error )
return error;
// count the duplicated elements (if all are annotated) // count the duplicated elements (if all are annotated)
int imax = flatList.size() - 1; int imax = flatList.size() - 1;
@ -577,7 +572,9 @@ int SCH_REFERENCE_LIST::CheckAnnotation( REPORTER& aReporter )
if( ( flatList[ii].CompareRef( flatList[ii + 1] ) != 0 ) if( ( flatList[ii].CompareRef( flatList[ii + 1] ) != 0 )
|| ( flatList[ii].m_numRef != flatList[ ii + 1].m_numRef ) ) || ( flatList[ii].m_numRef != flatList[ ii + 1].m_numRef ) )
{
continue; continue;
}
// Same reference found. If same unit, error! // Same reference found. If same unit, error!
if( flatList[ii].m_unit == flatList[ ii + 1].m_unit ) if( flatList[ii].m_unit == flatList[ ii + 1].m_unit )
@ -587,22 +584,21 @@ int SCH_REFERENCE_LIST::CheckAnnotation( REPORTER& aReporter )
else else
tmp = wxT( "?" ); tmp = wxT( "?" );
if( ( flatList[ii].m_unit > 0 ) if( ( flatList[ii].m_unit > 0 ) && ( flatList[ii].m_unit < 0x7FFFFFFF ) )
&& ( flatList[ii].m_unit < 0x7FFFFFFF ) )
{ {
msg.Printf( _( "Multiple item %s%s (unit %d)\n" ), msg.Printf( _( "Duplicate items %s%s%s\n" ),
flatList[ii].GetRef(), flatList[ii].GetRef(),
tmp, tmp,
flatList[ii].m_unit ); LIB_PART::SubReference( flatList[ii].m_unit ) );
} }
else else
{ {
msg.Printf( _( "Multiple item %s%s\n" ), msg.Printf( _( "Duplicate items %s%s\n" ),
flatList[ii].GetRef(), flatList[ii].GetRef(),
tmp ); tmp );
} }
aReporter.Report( msg, RPT_SEVERITY_ERROR ); aHandler( ERCE_DUPLICATE_REFERENCE, msg, &flatList[ii], &flatList[ii+1] );
error++; error++;
continue; continue;
} }
@ -620,19 +616,19 @@ int SCH_REFERENCE_LIST::CheckAnnotation( REPORTER& aReporter )
if( ( flatList[ii].m_unit > 0 ) if( ( flatList[ii].m_unit > 0 )
&& ( flatList[ii].m_unit < 0x7FFFFFFF ) ) && ( flatList[ii].m_unit < 0x7FFFFFFF ) )
{ {
msg.Printf( _( "Multiple item %s%s (unit %d)\n" ), msg.Printf( _( "Duplicate items %s%s%s\n" ),
flatList[ii].GetRef(), flatList[ii].GetRef(),
tmp, tmp,
flatList[ii].m_unit ); LIB_PART::SubReference( flatList[ii].m_unit ) );
} }
else else
{ {
msg.Printf( _( "Multiple item %s%s\n" ), msg.Printf( _( "Duplicate items %s%s\n" ),
flatList[ii].GetRef(), flatList[ii].GetRef(),
tmp ); tmp );
} }
aReporter.Report( msg, RPT_SEVERITY_ERROR ); aHandler( ERCE_DUPLICATE_REFERENCE, msg, &flatList[ii], &flatList[ii+1] );
error++; error++;
} }
@ -651,7 +647,7 @@ int SCH_REFERENCE_LIST::CheckAnnotation( REPORTER& aReporter )
LIB_PART::SubReference( flatList[next].m_unit ), LIB_PART::SubReference( flatList[next].m_unit ),
flatList[next].m_value ); flatList[next].m_value );
aReporter.Report( msg, RPT_SEVERITY_ERROR ); aHandler( ERCE_DIFFERENT_UNIT_VALUE, msg, &flatList[ii], &flatList[ii+1] );
error++; error++;
} }
} }

View File

@ -3,7 +3,7 @@
* *
* Copyright (C) 2015 Jean-Pierre Charras, jp.charras at wanadoo.fr * Copyright (C) 2015 Jean-Pierre Charras, jp.charras at wanadoo.fr
* Copyright (C) 2012 Wayne Stambaugh <stambaughw@gmail.com> * Copyright (C) 2012 Wayne Stambaugh <stambaughw@gmail.com>
* Copyright (C) 1992-2020 KiCad Developers, see AUTHORS.txt for contributors. * Copyright (C) 1992-2021 KiCad Developers, see AUTHORS.txt for contributors.
* *
* This program is free software; you can redistribute it and/or * This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -86,7 +86,7 @@ DIALOG_ERC::DIALOG_ERC( SCH_EDIT_FRAME* parent ) :
m_warningsBadge->SetMaximumNumber( 999 ); m_warningsBadge->SetMaximumNumber( 999 );
m_exclusionsBadge->SetMaximumNumber( 999 ); m_exclusionsBadge->SetMaximumNumber( 999 );
if( m_parent->CheckAnnotate( NULL_REPORTER::GetInstance(), false ) ) if( m_parent->CheckAnnotate( []( ERCE_T, const wxString&, SCH_REFERENCE*, SCH_REFERENCE* ) {} ) )
{ {
wxHyperlinkCtrl* button = new wxHyperlinkCtrl( m_infoBar, wxID_ANY, wxHyperlinkCtrl* button = new wxHyperlinkCtrl( m_infoBar, wxID_ANY,
_("Show Annotation dialog"), _("Show Annotation dialog"),
@ -102,7 +102,8 @@ DIALOG_ERC::DIALOG_ERC( SCH_EDIT_FRAME* parent ) :
m_infoBar->RemoveAllButtons(); m_infoBar->RemoveAllButtons();
m_infoBar->AddButton( button ); m_infoBar->AddButton( button );
m_infoBar->ShowMessage( _( "Annotation is incomplete. ERC cannot be run." ) ); m_infoBar->ShowMessage( _( "Schematic is not fully annotated. "
"ERC results will be incomplete." ) );
} }
// Now all widgets have the size fixed, call FinishDialogSettings // Now all widgets have the size fixed, call FinishDialogSettings
@ -263,24 +264,6 @@ void DIALOG_ERC::OnRunERCClick( wxCommandEvent& event )
SCHEMATIC* sch = &m_parent->Schematic(); SCHEMATIC* sch = &m_parent->Schematic();
// Build the whole sheet list in hierarchy (sheet, not screen)
sch->GetSheets().AnnotatePowerSymbols();
if( m_parent->CheckAnnotate( NULL_REPORTER::GetInstance(), false ) )
{
m_notebook->ChangeSelection( 0 ); // Display the "Tests Running..." tab
m_messages->Clear();
m_messages->Report( _( "Annotation not complete. ERC cannot be run." )
+ wxT( " <a href='annotate'>" )
+ _( "Show Annotation dialog." )
+ wxT( "</a>" ) );
m_messages->Flush();
m_infoBar->Hide(); // No need for duplicated error messages
return;
}
m_infoBar->Hide(); m_infoBar->Hide();
m_parent->RecordERCExclusions(); m_parent->RecordERCExclusions();
@ -296,6 +279,22 @@ void DIALOG_ERC::OnRunERCClick( wxCommandEvent& event )
m_buttondelmarkers->Enable( false ); m_buttondelmarkers->Enable( false );
m_saveReport->Enable( false ); m_saveReport->Enable( false );
sch->GetSheets().AnnotatePowerSymbols();
m_parent->CheckAnnotate(
[]( ERCE_T aType, const wxString& aMsg, SCH_REFERENCE* aItemA, SCH_REFERENCE* aItemB )
{
std::shared_ptr<ERC_ITEM> ercItem = ERC_ITEM::Create( aType );
ercItem->SetErrorMessage( aMsg );
if( aItemB )
ercItem->SetItems( aItemA->GetSymbol(), aItemB->GetSymbol() );
else
ercItem->SetItems( aItemA->GetSymbol() );
SCH_MARKER* marker = new SCH_MARKER( ercItem, aItemA->GetSymbol()->GetPosition() );
aItemA->GetSheetPath().LastScreen()->Append( marker );
} );
testErc(); testErc();
if( m_cancelled ) if( m_cancelled )
@ -341,19 +340,6 @@ void DIALOG_ERC::testErc()
// Build the whole sheet list in hierarchy (sheet, not screen) // Build the whole sheet list in hierarchy (sheet, not screen)
sch->GetSheets().AnnotatePowerSymbols(); sch->GetSheets().AnnotatePowerSymbols();
if( m_parent->CheckAnnotate( NULL_REPORTER::GetInstance(), false ) )
{
Report( _( "Annotation not complete. ERC cannot be run." )
+ wxT( " <a href='annotate'>" )
+ _( "Show Annotation dialog." )
+ wxT( "</a>" ) );
m_infoBar->Hide(); // No need for duplicated error messages
return;
}
m_infoBar->Hide();
SCH_SCREENS screens( sch->Root() ); SCH_SCREENS screens( sch->Root() );
ERC_SETTINGS& settings = sch->ErcSettings(); ERC_SETTINGS& settings = sch->ErcSettings();
ERC_TESTER tester( sch ); ERC_TESTER tester( sch );

View File

@ -23,11 +23,6 @@
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/ */
/**
* @file erc.cpp
* @brief Electrical Rules Check implementation.
*/
#include "connection_graph.h" #include "connection_graph.h"
#include <erc.h> #include <erc.h>
#include <kicad_string.h> #include <kicad_string.h>
@ -48,7 +43,6 @@
* output, or a passive pin ) * output, or a passive pin )
*/ */
/* /*
* Minimal ERC requirements: * Minimal ERC requirements:
* All pins *must* be connected (except ELECTRICAL_PINTYPE::PT_NC). * All pins *must* be connected (except ELECTRICAL_PINTYPE::PT_NC).
@ -57,16 +51,6 @@
* This ensures a forgotten connection will be detected. * This ensures a forgotten connection will be detected.
*/ */
/* Messages for conflicts :
* ELECTRICAL_PINTYPE::PT_INPUT, ELECTRICAL_PINTYPE::PT_OUTPUT, ELECTRICAL_PINTYPE:PT_:BIDI,
* ELECTRICAL_PINTYPE::PT_TRISTATE, ELECTRICAL_PINTYPE::PT_PASSIVE,
* ELECTRICAL_PINTYPE::PT_UNSPECIFIED, ELECTRICAL_PINTYPE::PT_POWER_IN,
* ELECTRICAL_PINTYPE::PT_POWER_OUT, ELECTRICAL_PINTYPE::PT_OPENCOLLECTOR,
* ELECTRICAL_PINTYPE::PT_OPENEMITTER, ELECTRICAL_PINTYPE::PT_NC
*
* These messages are used to show the ERC matrix in ERC dialog
*/
// Messages for matrix rows: // Messages for matrix rows:
const wxString CommentERC_H[] = const wxString CommentERC_H[] =
{ {
@ -75,6 +59,7 @@ const wxString CommentERC_H[] =
_( "Bidirectional Pin" ), _( "Bidirectional Pin" ),
_( "Tri-State Pin" ), _( "Tri-State Pin" ),
_( "Passive Pin" ), _( "Passive Pin" ),
_( "Free Pin" ),
_( "Unspecified Pin" ), _( "Unspecified Pin" ),
_( "Power Input Pin" ), _( "Power Input Pin" ),
_( "Power Output Pin" ), _( "Power Output Pin" ),
@ -91,6 +76,7 @@ const wxString CommentERC_V[] =
_( "Bidirectional Pin" ), _( "Bidirectional Pin" ),
_( "Tri-State Pin" ), _( "Tri-State Pin" ),
_( "Passive Pin" ), _( "Passive Pin" ),
_( "Free Pin" ),
_( "Unspecified Pin" ), _( "Unspecified Pin" ),
_( "Power Input Pin" ), _( "Power Input Pin" ),
_( "Power Output Pin" ), _( "Power Output Pin" ),

View File

@ -134,6 +134,22 @@ ERC_ITEM ERC_ITEM::libSymbolIssues( ERCE_LIB_SYMBOL_ISSUES,
_( "Library symbol issue" ), _( "Library symbol issue" ),
wxT( "lib_symbol_issues" ) ); wxT( "lib_symbol_issues" ) );
ERC_ITEM ERC_ITEM::unannotated( ERCE_UNANNOTATED,
_( "Symbol is not annotated" ),
wxT( "unannotated" ) );
ERC_ITEM ERC_ITEM::extraUnits( ERCE_EXTRA_UNITS,
_( "Symbol has more units than are defined" ),
wxT( "extra_units" ) );
ERC_ITEM ERC_ITEM::differentUnitValue( ERCE_DIFFERENT_UNIT_VALUE,
_( "Units of same symbol have different values" ),
wxT( "unit_value_mismatch" ) );
ERC_ITEM ERC_ITEM::duplicateReference( ERCE_DUPLICATE_REFERENCE,
_( "Duplicate reference designators" ),
wxT( "duplicate_reference" ) );
std::vector<std::reference_wrapper<RC_ITEM>> ERC_ITEM::allItemTypes( { std::vector<std::reference_wrapper<RC_ITEM>> ERC_ITEM::allItemTypes( {
ERC_ITEM::heading_connections, ERC_ITEM::heading_connections,
ERC_ITEM::pinNotConnected, ERC_ITEM::pinNotConnected,
@ -146,7 +162,10 @@ std::vector<std::reference_wrapper<RC_ITEM>> ERC_ITEM::allItemTypes( {
ERC_ITEM::wireDangling, ERC_ITEM::wireDangling,
ERC_ITEM::heading_conflicts, ERC_ITEM::heading_conflicts,
ERC_ITEM::duplicateReference,
ERC_ITEM::pinTableWarning, ERC_ITEM::pinTableWarning,
ERC_ITEM::differentUnitValue,
ERC_ITEM::differentUnitFootprint,
ERC_ITEM::differentUnitNet, ERC_ITEM::differentUnitNet,
ERC_ITEM::duplicateSheetName, ERC_ITEM::duplicateSheetName,
ERC_ITEM::hierLabelMismatch, ERC_ITEM::hierLabelMismatch,
@ -157,11 +176,12 @@ std::vector<std::reference_wrapper<RC_ITEM>> ERC_ITEM::allItemTypes( {
ERC_ITEM::netNotBusMember, ERC_ITEM::netNotBusMember,
ERC_ITEM::heading_misc, ERC_ITEM::heading_misc,
ERC_ITEM::unannotated,
ERC_ITEM::unresolvedVariable, ERC_ITEM::unresolvedVariable,
ERC_ITEM::similarLabels, ERC_ITEM::similarLabels,
ERC_ITEM::busLabelSyntax, ERC_ITEM::busLabelSyntax,
ERC_ITEM::libSymbolIssues, ERC_ITEM::libSymbolIssues,
ERC_ITEM::differentUnitFootprint, ERC_ITEM::extraUnits,
} ); } );
@ -193,6 +213,10 @@ std::shared_ptr<ERC_ITEM> ERC_ITEM::Create( int aErrorCode )
case ERCE_UNRESOLVED_VARIABLE: return std::make_shared<ERC_ITEM>( unresolvedVariable ); case ERCE_UNRESOLVED_VARIABLE: return std::make_shared<ERC_ITEM>( unresolvedVariable );
case ERCE_WIRE_DANGLING: return std::make_shared<ERC_ITEM>( wireDangling ); case ERCE_WIRE_DANGLING: return std::make_shared<ERC_ITEM>( wireDangling );
case ERCE_LIB_SYMBOL_ISSUES: return std::make_shared<ERC_ITEM>( libSymbolIssues ); case ERCE_LIB_SYMBOL_ISSUES: return std::make_shared<ERC_ITEM>( libSymbolIssues );
case ERCE_UNANNOTATED: return std::make_shared<ERC_ITEM>( unannotated );
case ERCE_EXTRA_UNITS: return std::make_shared<ERC_ITEM>( extraUnits );
case ERCE_DIFFERENT_UNIT_VALUE: return std::make_shared<ERC_ITEM>( differentUnitValue );
case ERCE_DUPLICATE_REFERENCE: return std::make_shared<ERC_ITEM>( duplicateReference );
case ERCE_UNSPECIFIED: case ERCE_UNSPECIFIED:
default: default:
wxFAIL_MSG( "Unknown ERC error code" ); wxFAIL_MSG( "Unknown ERC error code" );

View File

@ -94,6 +94,10 @@ private:
static ERC_ITEM unresolvedVariable; static ERC_ITEM unresolvedVariable;
static ERC_ITEM wireDangling; static ERC_ITEM wireDangling;
static ERC_ITEM libSymbolIssues; static ERC_ITEM libSymbolIssues;
static ERC_ITEM unannotated;
static ERC_ITEM extraUnits;
static ERC_ITEM differentUnitValue;
static ERC_ITEM duplicateReference;
/// True if this item is specific to a sheet instance (as opposed to applying to all instances) /// True if this item is specific to a sheet instance (as opposed to applying to all instances)
bool m_sheetSpecific; bool m_sheetSpecific;

View File

@ -2,6 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application. * This program source code file is part of KiCad, a free EDA CAD application.
* *
* Copyright (C) 2018-2020 CERN * Copyright (C) 2018-2020 CERN
* Copyright (C) 2020-2021 KiCad Developers, see AUTHORS.txt for contributors.
* @author Jon Evans <jon@craftyjon.com> * @author Jon Evans <jon@craftyjon.com>
* *
* This program is free software; you can redistribute it and/or * This program is free software; you can redistribute it and/or
@ -64,12 +65,19 @@ enum ERCE_T
ERCE_WIRE_DANGLING, ///< Some wires are not connected to anything else. ERCE_WIRE_DANGLING, ///< Some wires are not connected to anything else.
ERCE_LIB_SYMBOL_ISSUES, ///< Library symbol changed from current symbol in schematic or ERCE_LIB_SYMBOL_ISSUES, ///< Library symbol changed from current symbol in schematic or
///< the library symbol link no longer valid. ///< the library symbol link no longer valid.
ERCE_LAST = ERCE_LIB_SYMBOL_ISSUES, ERCE_UNANNOTATED, ///< Symbol has not been annotated.
ERCE_EXTRA_UNITS, ///< Symbol has more units than are defined.
ERCE_DIFFERENT_UNIT_VALUE, ///< Units of same symbol have different values.
ERCE_DUPLICATE_REFERENCE, ///< More than one symbol with the same reference.
ERCE_LAST = ERCE_DUPLICATE_REFERENCE,
// Errors after this point will not automatically appear in the Severities Panel // Errors after this point will not automatically appear in the Severities Panel
ERCE_PIN_TO_PIN_WARNING, // pin connected to an other pin: warning level ERCE_PIN_TO_PIN_WARNING, // pin connected to an other pin: warning level
ERCE_PIN_TO_PIN_ERROR, // pin connected to an other pin: error level ERCE_PIN_TO_PIN_ERROR, // pin connected to an other pin: error level
ERCE_ANNOTATION_ACTION // Not actually an error; just an action performed during
// annotation which is passed back through the error handler.
}; };
/// The values a pin-to-pin entry in the pin matrix can take on /// The values a pin-to-pin entry in the pin matrix can take on
@ -166,6 +174,7 @@ private:
static PIN_ERROR m_defaultPinMap[ELECTRICAL_PINTYPES_TOTAL][ELECTRICAL_PINTYPES_TOTAL]; static PIN_ERROR m_defaultPinMap[ELECTRICAL_PINTYPES_TOTAL][ELECTRICAL_PINTYPES_TOTAL];
}; };
/** /**
* An implementation of the RC_ITEM_LIST interface which uses the global SHEETLIST * An implementation of the RC_ITEM_LIST interface which uses the global SHEETLIST
* to fulfill the contract. * to fulfill the contract.

View File

@ -166,7 +166,7 @@ bool SCH_EDIT_FRAME::ReadyToNetlist( bool aSilent, bool aSilentAnnotate )
Schematic().GetSheets().AnnotatePowerSymbols(); Schematic().GetSheets().AnnotatePowerSymbols();
// Components must be annotated // Components must be annotated
if( CheckAnnotate( NULL_REPORTER::GetInstance(), false ) ) if( CheckAnnotate( []( ERCE_T, const wxString&, SCH_REFERENCE*, SCH_REFERENCE* ) {} ) )
{ {
if( aSilentAnnotate ) if( aSilentAnnotate )
{ {
@ -179,11 +179,12 @@ bool SCH_EDIT_FRAME::ReadyToNetlist( bool aSilent, bool aSilentAnnotate )
return false; return false;
// Schematic must be annotated: call Annotate dialog and tell the user why. // Schematic must be annotated: call Annotate dialog and tell the user why.
ModalAnnotate( ModalAnnotate( _( "Exporting netlist requires a completely annotated schematic." ) );
_( "Exporting the netlist requires a completely annotated schematic." ) );
if( CheckAnnotate( NULL_REPORTER::GetInstance(), false ) ) if( CheckAnnotate( []( ERCE_T, const wxString&, SCH_REFERENCE*, SCH_REFERENCE* ) {} ) )
{
return false; return false;
}
} }
} }

View File

@ -3,7 +3,7 @@
* *
* Copyright (C) 2015 Jean-Pierre Charras, jp.charras wanadoo.fr * Copyright (C) 2015 Jean-Pierre Charras, jp.charras wanadoo.fr
* Copyright (C) 2008 Wayne Stambaugh <stambaughw@gmail.com> * Copyright (C) 2008 Wayne Stambaugh <stambaughw@gmail.com>
* Copyright (C) 2004-2020 KiCad Developers, see AUTHORS.txt for contributors. * Copyright (C) 2004-2021 KiCad Developers, see AUTHORS.txt for contributors.
* *
* This program is free software; you can redistribute it and/or * This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -449,11 +449,11 @@ public:
* between parts. * between parts.
* *
* @return Number of annotation errors found. * @return Number of annotation errors found.
* @param aReporter A sink for error messages. Use NULL_REPORTER if you don't need errors. * @param aReporter A handler for error reporting.
* @param aOneSheetOnly Check the current sheet only if true. Otherwise check * @param aOneSheetOnly Check the current sheet only if true. Otherwise check the entire
* the entire schematic. * schematic.
*/ */
int CheckAnnotate( REPORTER& aReporter, bool aOneSheetOnly ); int CheckAnnotate( ANNOTATION_ERROR_HANDLER aErrorHandler, bool aOneSheetOnly = false );
/** /**
* Run a modal version of the Annotate dialog for a specific purpose. * Run a modal version of the Annotate dialog for a specific purpose.
@ -478,25 +478,21 @@ public:
void DisplayCurrentSheet(); void DisplayCurrentSheet();
/** /**
* Use the wxWidgets print code to draw an image of the current sheet onto * Use the wxWidgets print code to draw an image of the current sheet onto the clipboard.
* the clipboard.
*/ */
void DrawCurrentSheetToClipboard(); void DrawCurrentSheetToClipboard();
/** /**
* Called when modifying the page settings. * Called when modifying the page settings.
* In derived classes it can be used to modify parameters like draw area size, * In derived classes it can be used to modify parameters like draw area size, and any other
* and any other local parameter related to the page settings. * local parameter related to the page settings.
*/ */
void OnPageSettingsChange() override; void OnPageSettingsChange() override;
/** /**
* @return a filename that can be used in plot and print functions * @return a filename that can be used in plot and print functions for the current screen
* for the current screen and sheet path. * and sheet path. This filename is unique and must be used instead of the screen filename
* This filename is unique and must be used instead of the screen filename * when one must create files for each sheet in the hierarchy.
* (or screen filename) when one must creates file for each sheet in the
* hierarchy. because in complex hierarchies a sheet and a SCH_SCREEN is
* used more than once
* Name is &ltroot sheet filename&gt-&ltsheet path&gt and has no extension. * Name is &ltroot sheet filename&gt-&ltsheet path&gt and has no extension.
* However if filename is too long name is &ltsheet filename&gt-&ltsheet number&gt * However if filename is too long name is &ltsheet filename&gt-&ltsheet number&gt
*/ */
@ -532,10 +528,10 @@ public:
/** /**
* Save \a aSheet to a schematic file. * Save \a aSheet to a schematic file.
* *
* @param aSheet A pointer to the #SCH_SHEET object to save. A NULL pointer saves * @param aSheet A pointer to the #SCH_SHEET object to save. A NULL pointer saves the
* the current screen only. * current screen only.
* @param aSaveUnderNewName Controls how the file is to be saved;: using previous name * @param aSaveUnderNewName Controls how the file is to be saved;: using previous name
* or under a new name . * or under a new name.
* @return True if the file has been saved. * @return True if the file has been saved.
*/ */
bool SaveEEFile( SCH_SHEET* aSheet, bool SaveEEFile( SCH_SHEET* aSheet,

View File

@ -3,7 +3,7 @@
* *
* Copyright (C) 1992-2011 jean-pierre Charras <jean-pierre.charras@gipsa-lab.inpg.fr> * Copyright (C) 1992-2011 jean-pierre Charras <jean-pierre.charras@gipsa-lab.inpg.fr>
* Copyright (C) 1992-2011 Wayne Stambaugh <stambaughw@verizon.net> * Copyright (C) 1992-2011 Wayne Stambaugh <stambaughw@verizon.net>
* Copyright (C) 1992-2020 KiCad Developers, see authors.txt for contributors. * Copyright (C) 1992-2021 KiCad Developers, see authors.txt for contributors.
* *
* This program is free software; you can redistribute it and/or * This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -33,6 +33,7 @@
#include <sch_sheet_path.h> #include <sch_sheet_path.h>
#include <sch_component.h> #include <sch_component.h>
#include <sch_text.h> #include <sch_text.h>
#include <erc_settings.h>
#include <map> #include <map>
@ -184,6 +185,13 @@ public:
}; };
/**
* Defines a standard error handler for annotation errors.
*/
typedef std::function<void( ERCE_T aType, const wxString& aMsg, SCH_REFERENCE* aItemA,
SCH_REFERENCE* aItemB )> ANNOTATION_ERROR_HANDLER;
/** /**
* SCH_REFERENCE_LIST * SCH_REFERENCE_LIST
* is used to create a flattened list of symbols because in a complex hierarchy, a symbol * is used to create a flattened list of symbols because in a complex hierarchy, a symbol
@ -193,6 +201,7 @@ public:
*/ */
class SCH_REFERENCE_LIST class SCH_REFERENCE_LIST
{ {
private: private:
std::vector<SCH_REFERENCE> flatList; std::vector<SCH_REFERENCE> flatList;
@ -296,10 +305,10 @@ public:
* <li>Symbols with multiple parts per package with invalid part count.</li> * <li>Symbols with multiple parts per package with invalid part count.</li>
* </ul> * </ul>
* </p> * </p>
* @param aReporter A sink for error messages. Use NULL_REPORTER if you don't need errors. * @param aErrorHandler A handler for errors.
* @return The number of errors found. * @return The number of errors found.
*/ */
int CheckAnnotation( REPORTER& aReporter ); int CheckAnnotation( ANNOTATION_ERROR_HANDLER aErrorHandler );
/** /**
* Function SortByXCoordinate * Function SortByXCoordinate