CHANGED: Reannotation in eeschema now always keeps symbol units

Ensures that symbol units are never modified after re-annotation.
This commit is contained in:
Roberto Fernandez Bautista 2021-04-27 15:52:32 +01:00 committed by Wayne Stambaugh
parent 0c91bea751
commit 0f85f61e5f
7 changed files with 40 additions and 66 deletions

View File

@ -129,7 +129,6 @@ void SCH_EDIT_FRAME::AnnotateSymbols( ANNOTATE_SCOPE_T aAnnotateScope,
int aStartNumber,
bool aResetAnnotation,
bool aRepairTimestamps,
bool aLockUnits,
REPORTER& aReporter )
{
EE_SELECTION_TOOL* selTool = m_toolManager->GetTool<EE_SELECTION_TOOL>();
@ -162,23 +161,20 @@ void SCH_EDIT_FRAME::AnnotateSymbols( ANNOTATE_SCOPE_T aAnnotateScope,
}
}
// If units must be locked, collect all the sets that must be annotated together.
if( aLockUnits )
// Collect all the sets that must be annotated together.
switch( aAnnotateScope )
{
switch( aAnnotateScope )
{
case ANNOTATE_ALL:
sheets.GetMultiUnitSymbols( lockedSymbols );
break;
case ANNOTATE_ALL:
sheets.GetMultiUnitSymbols( lockedSymbols );
break;
case ANNOTATE_CURRENT_SHEET:
currentSheet.GetMultiUnitSymbols( lockedSymbols );
break;
case ANNOTATE_CURRENT_SHEET:
currentSheet.GetMultiUnitSymbols( lockedSymbols );
break;
case ANNOTATE_SELECTION:
selection.GetMultiUnitSymbols( lockedSymbols, currentSheet );
break;
}
case ANNOTATE_SELECTION:
selection.GetMultiUnitSymbols( lockedSymbols, currentSheet );
break;
}
// Store previous annotations for building info messages

View File

@ -299,12 +299,28 @@ void SCH_REFERENCE_LIST::Annotate( bool aUseSheetNum, int aSheetIntervalId, int
int originalSize = GetCount();
// We don't want to reannotate the additional references even if not annotated
// so we change the m_isNew flag to be false after splitting
// For multi units components, store the list of already used full references.
// The algorithm tries to allocate the new reference to components having the same
// old reference.
// This algo works fine as long as the previous annotation has no duplicates.
// But when a hierarchy is reannotated with this option, the previous anotation can
// have duplicate references, and obviously we must fix these duplicate.
// therefore do not try to allocate a full reference more than once when trying
// to keep this order of multi units.
// inUseRefs keep trace of previously allocated references
std::unordered_set<wxString> inUseRefs;
for( size_t i = 0; i < aAdditionalRefs.GetCount(); i++ )
{
SCH_REFERENCE additionalRef = aAdditionalRefs[i];
additionalRef.Split();
// Add the additional reference to the multi-unit set if annotated
if( !additionalRef.m_isNew )
inUseRefs.insert( buildFullReference( additionalRef ) );
// We don't want to reannotate the additional references even if not annotated
// so we change the m_isNew flag to be false after splitting
additionalRef.m_isNew = false;
AddItem( additionalRef ); //add to this container
}
@ -328,18 +344,6 @@ void SCH_REFERENCE_LIST::Annotate( bool aUseSheetNum, int aSheetIntervalId, int
else
minRefId = aStartNumber + 1;
// For multi units components, when "keep order of multi unit" option is selected,
// store the list of already used full references.
// The algorithm try to allocate the new reference to components having the same
// old reference.
// This algo works fine as long as the previous annotation has no duplicates.
// But when a hierarchy is reannotated with this option, the previous anotation can
// have duplicate references, and obviously we must fix these duplicate.
// therefore do not try to allocate a full reference more than once when trying
// to keep this order of multi units.
// inUseRefs keep trace of previously allocated references
std::unordered_set<wxString> inUseRefs;
// This is the list of all Id already in use for a given reference prefix.
// Will be refilled for each new reference prefix.
std::vector<int>idList;
@ -395,7 +399,6 @@ void SCH_REFERENCE_LIST::Annotate( bool aUseSheetNum, int aSheetIntervalId, int
ref_unit.m_numRef = LastReferenceNumber;
}
ref_unit.m_unit = 1;
ref_unit.m_flag = 1;
ref_unit.m_isNew = false;
continue;
@ -409,9 +412,6 @@ void SCH_REFERENCE_LIST::Annotate( bool aUseSheetNum, int aSheetIntervalId, int
LastReferenceNumber = CreateFirstFreeRefId( idList, minRefId );
ref_unit.m_numRef = LastReferenceNumber;
if( !ref_unit.IsUnitsLocked() && !lockedList )
ref_unit.m_unit = 1;
ref_unit.m_flag = 1;
}
@ -453,7 +453,6 @@ void SCH_REFERENCE_LIST::Annotate( bool aUseSheetNum, int aSheetIntervalId, int
if( inUseRefs.find( ref_candidate ) == inUseRefs.end() )
{
flatList[jj].m_numRef = ref_unit.m_numRef;
flatList[jj].m_unit = thisRef.m_unit;
flatList[jj].m_isNew = false;
flatList[jj].m_flag = 1;
// lock this new full reference
@ -504,11 +503,9 @@ void SCH_REFERENCE_LIST::Annotate( bool aUseSheetNum, int aSheetIntervalId, int
continue;
// Component without reference number found, annotate it if possible
if( !cmp_unit.IsUnitsLocked()
|| ( cmp_unit.m_unit == Unit ) )
if( cmp_unit.m_unit == Unit )
{
cmp_unit.m_numRef = ref_unit.m_numRef;
cmp_unit.m_unit = Unit;
cmp_unit.m_flag = 1;
cmp_unit.m_isNew = false;
break;
@ -743,9 +740,6 @@ void SCH_REFERENCE::Split()
{
m_isNew = true;
if( !IsUnitsLocked() )
m_unit = 0x7FFFFFFF;
refText.erase( ll ); // delete last char
SetRefStr( refText );
@ -753,9 +747,6 @@ void SCH_REFERENCE::Split()
else if( isdigit( refText[ll] ) == 0 )
{
m_isNew = true;
if( !IsUnitsLocked() )
m_unit = 0x7FFFFFFF;
}
else
{

View File

@ -56,7 +56,6 @@ private:
// User functions:
bool GetResetItems();
bool GetLockUnits();
ANNOTATE_SCOPE_T GetScope();
@ -173,7 +172,7 @@ void DIALOG_ANNOTATE::OnApplyClick( wxCommandEvent& event )
m_MessageWindow->SetLazyUpdate( true ); // Don't update after each message
m_Parent->AnnotateSymbols( GetScope(), GetSortOrder(), GetAnnotateAlgo(),
GetStartNumber(), GetResetItems(), true, GetLockUnits(), reporter );
GetStartNumber(), GetResetItems(), true, reporter );
m_MessageWindow->Flush( true ); // Now update to show all messages
@ -217,12 +216,6 @@ bool DIALOG_ANNOTATE::GetResetItems()
}
bool DIALOG_ANNOTATE::GetLockUnits()
{
return m_rbOptions->GetSelection() == 2;
}
ANNOTATE_SCOPE_T DIALOG_ANNOTATE::GetScope()
{
switch( m_rbScope->GetSelection() )

View File

@ -81,7 +81,7 @@ DIALOG_ANNOTATE_BASE::DIALOG_ANNOTATE_BASE( wxWindow* parent, wxWindowID id, con
fgSizer1->Add( sbSizer1, 0, wxALL|wxEXPAND, 5 );
wxString m_rbOptionsChoices[] = { _("Keep existing annotations"), _("Reset existing annotations"), _("Reset, but keep order of multi-unit parts") };
wxString m_rbOptionsChoices[] = { _("Keep existing annotations"), _("Reset existing annotations") };
int m_rbOptionsNChoices = sizeof( m_rbOptionsChoices ) / sizeof( wxString );
m_rbOptions = new wxRadioBox( this, wxID_ANY, _("Options"), wxDefaultPosition, wxDefaultSize, m_rbOptionsNChoices, m_rbOptionsChoices, 1, wxRA_SPECIFY_COLS );
m_rbOptions->SetSelection( 0 );

View File

@ -541,7 +541,7 @@
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="choices">&quot;Keep existing annotations&quot; &quot;Reset existing annotations&quot; &quot;Reset, but keep order of multi-unit parts&quot;</property>
<property name="choices">&quot;Keep existing annotations&quot; &quot;Reset existing annotations&quot;</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>

View File

@ -378,7 +378,9 @@ public:
void DeleteAnnotation( ANNOTATE_SCOPE_T aAnnotateScope, bool* appendUndo );
/**
* Annotate the symbols in the schematic that are not currently annotated.
* Annotate the symbols in the schematic that are not currently annotated. Multi-unit symbols
* are annotated together. E.g. if two components were R8A and R8B, they may become R3A and
* R3B, but not R3A and R3C or R3C and R4D.
*
* @param aAnnotateScope See #ANNOTATE_SCOPE_T
* @param aSortOption Define the annotation order. See #ANNOTATE_ORDER_T.
@ -390,13 +392,6 @@ public:
* Otherwise, keep the existing time stamps. This option
* could change previous annotation because time stamps are
* used to handle annotation in complex hierarchies.
* @param aLockUnits When both aLockUnits and aResetAnnotation are true, all unit
* associations should be kept when reannotating. That is, if two
* components were R8A and R8B, they may become R3A and R3B, but not
* R3A and R3C or R3C and R4D.
* When aResetAnnotation is true but aLockUnits is false, the usual
* behavior of annotating each part individually is performed.
* When aResetAnnotation is false, this option has no effect.
* @param aReporter A sink for error messages. Use NULL_REPORTER if you don't need errors.
*
* When the sheet number is used in annotation, each sheet annotation starts from sheet
@ -405,7 +400,7 @@ public:
*/
void AnnotateSymbols( ANNOTATE_SCOPE_T aAnnotateScope, ANNOTATE_ORDER_T aSortOption,
ANNOTATE_ALGO_T aAlgoOption, int aStartNumber, bool aResetAnnotation,
bool aRepairTimestamps, bool aLockUnits, REPORTER& aReporter );
bool aRepairTimestamps, REPORTER& aReporter );
/**
* Check for annotation errors.

View File

@ -92,8 +92,8 @@ public:
* Attempt to split the reference designator into a name (U) and number (1).
*
* If the last character is '?' or not a digit, the reference is tagged as not annotated.
* For symbols with multiple parts per package that are not already annotated, sets m_unit
* to a max value (0x7FFFFFFF).
* For symbols with multiple parts per package that are not already annotated, keeps the unit
* number the same. E.g. U?A or U?B
*/
void Split();
@ -257,8 +257,7 @@ public:
* Attempt to split all reference designators into a name (U) and number (1).
*
* If the last character is '?' or not a digit, the reference is tagged as not annotated.
* For symbols with multiple parts per package that are not already annotated, set m_unit
* to a max value (0x7FFFFFFF).
* For symbols with multiple parts, keeps the unit number intact
* @see SCH_REFERENCE::Split()
*/
void SplitReferences()