Symbol editor: fix crash caused by broken root symbol name.
The symbol editor selection criteria did not include LIB_FIELD objects which allowed the root symbol name to be changed causing broken derived symbol links. Disable the symbols fields from being edited when a derived part is shown in the editor to prevent this. Add a missing warning that deleting a root symbol used to derive other symbols would also delete all derived symbols from a library. Give the user a chance to cancel the delete operation in this case. Fixes kicad/code/kicad#3654
This commit is contained in:
parent
eb3d32f967
commit
bec878640c
|
@ -642,6 +642,15 @@ void LIB_MANAGER::GetRootSymbolNames( const wxString& aLibraryName,
|
|||
}
|
||||
|
||||
|
||||
bool LIB_MANAGER:: HasDerivedSymbols( const wxString& aSymbolName,
|
||||
const wxString& aLibraryName )
|
||||
{
|
||||
LIB_BUFFER& libBuf = getLibraryBuffer( aLibraryName );
|
||||
|
||||
return libBuf.HasDerivedSymbols( aSymbolName );
|
||||
}
|
||||
|
||||
|
||||
wxString LIB_MANAGER::getLibraryName( const wxString& aFilePath )
|
||||
{
|
||||
wxFileName fn( aFilePath );
|
||||
|
|
|
@ -290,6 +290,14 @@ public:
|
|||
|
||||
void GetRootSymbolNames( const wxString& aLibName, wxArrayString& aRootSymbolNames );
|
||||
|
||||
/**
|
||||
* Check if symbol \a aSymbolName in library \a aLibraryName is a root symbol that
|
||||
* has derived symbols.
|
||||
*
|
||||
* @return true if \aSymbolName in \a aLibraryName has derived symbols.
|
||||
*/
|
||||
bool HasDerivedSymbols( const wxString& aSymbolName, const wxString& aLibraryName );
|
||||
|
||||
private:
|
||||
///> Extracts library name basing on the file name
|
||||
static wxString getLibraryName( const wxString& aFilePath );
|
||||
|
|
|
@ -460,7 +460,7 @@ void LIB_EDIT_FRAME::savePartAs()
|
|||
|
||||
if( new_lib.IsEmpty() )
|
||||
{
|
||||
DisplayError( NULL, _( "No library specified. Symbol could not be saved." ) );
|
||||
DisplayError( this, _( "No library specified. Symbol could not be saved." ) );
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -471,7 +471,7 @@ void LIB_EDIT_FRAME::savePartAs()
|
|||
|
||||
if( new_name.IsEmpty() )
|
||||
{
|
||||
DisplayError( NULL, _( "No symbol name specified. Symbol could not be saved." ) );
|
||||
DisplayError( this, _( "No symbol name specified. Symbol could not be saved." ) );
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -487,7 +487,6 @@ void LIB_EDIT_FRAME::savePartAs()
|
|||
LIB_PART new_part( *part );
|
||||
new_part.SetName( new_name );
|
||||
|
||||
fixDuplicateAliases( &new_part, new_lib );
|
||||
m_libMgr->UpdatePart( &new_part, new_lib );
|
||||
SyncLibraries( false );
|
||||
m_treePane->GetLibTree()->SelectLibId( LIB_ID( new_lib, new_part.GetName() ) );
|
||||
|
@ -539,13 +538,33 @@ void LIB_EDIT_FRAME::DeletePartFromLibrary()
|
|||
LIB_ID libId = getTargetLibId();
|
||||
|
||||
if( m_libMgr->IsPartModified( libId.GetLibItemName(), libId.GetLibNickname() )
|
||||
&& !IsOK( this, _( wxString::Format( "Component %s has been modified\n"
|
||||
&& !IsOK( this, _( wxString::Format( "The symbol \"%s\" has been modified\n"
|
||||
"Do you want to remove it from the library?",
|
||||
libId.GetUniStringLibItemName() ) ) ) )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if( m_libMgr->HasDerivedSymbols( libId.GetLibItemName(), libId.GetLibNickname() ) )
|
||||
{
|
||||
wxString msg;
|
||||
|
||||
msg.Printf( _( "The symbol \"%s\" is used to derive other symbols.\n"
|
||||
"Deleting this symbol will delete all of the symbols derived from it.\n\n"
|
||||
"Do you wish to delete this symbol and all of it's derivatives?" ),
|
||||
libId.GetLibItemName().wx_str() );
|
||||
|
||||
wxMessageDialog::ButtonLabel yesButtonLabel( _( "Delete Symbol" ) );
|
||||
wxMessageDialog::ButtonLabel noButtonLabel( _( "Keep Symbol" ) );
|
||||
|
||||
wxMessageDialog dlg( this, msg, _( "Warning" ),
|
||||
wxYES_NO | wxYES_DEFAULT | wxICON_QUESTION | wxCENTER );
|
||||
dlg.SetYesNoLabels( yesButtonLabel, noButtonLabel );
|
||||
|
||||
if( dlg.ShowModal() == wxID_NO )
|
||||
return;
|
||||
}
|
||||
|
||||
if( isCurrentPart( libId ) )
|
||||
emptyScreen();
|
||||
|
||||
|
|
|
@ -1083,17 +1083,31 @@ bool EE_SELECTION_TOOL::doSelectionMenu( EE_COLLECTOR* aCollector )
|
|||
bool EE_SELECTION_TOOL::Selectable( const EDA_ITEM* aItem, bool checkVisibilityOnly ) const
|
||||
{
|
||||
// NOTE: in the future this is where eeschema layer/itemtype visibility will be handled
|
||||
LIB_EDIT_FRAME* editFrame = dynamic_cast< LIB_EDIT_FRAME* >( m_frame );
|
||||
|
||||
wxCHECK( editFrame, false );
|
||||
|
||||
switch( aItem->Type() )
|
||||
{
|
||||
case SCH_PIN_T:
|
||||
if( !static_cast<const SCH_PIN*>( aItem )->IsVisible() && !m_frame->GetShowAllPins() )
|
||||
if( !static_cast<const SCH_PIN*>( aItem )->IsVisible() && !editFrame->GetShowAllPins() )
|
||||
return false;
|
||||
break;
|
||||
|
||||
case LIB_PART_T: // In libedit we do not want to select the symbol itself.
|
||||
return false;
|
||||
|
||||
case LIB_FIELD_T:
|
||||
{
|
||||
LIB_PART* currentPart = editFrame->GetCurPart();
|
||||
|
||||
// Nothing in derived symbols is editable at the moment.
|
||||
if( currentPart && currentPart->IsAlias() )
|
||||
return false;
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case LIB_ARC_T:
|
||||
case LIB_CIRCLE_T:
|
||||
case LIB_TEXT_T:
|
||||
|
@ -1102,7 +1116,6 @@ bool EE_SELECTION_TOOL::Selectable( const EDA_ITEM* aItem, bool checkVisibilityO
|
|||
case LIB_BEZIER_T:
|
||||
case LIB_PIN_T:
|
||||
{
|
||||
LIB_EDIT_FRAME* editFrame = (LIB_EDIT_FRAME*) m_frame;
|
||||
LIB_ITEM* lib_item = (LIB_ITEM*) aItem;
|
||||
|
||||
if( lib_item->GetUnit() && lib_item->GetUnit() != editFrame->GetUnit() )
|
||||
|
@ -1113,6 +1126,7 @@ bool EE_SELECTION_TOOL::Selectable( const EDA_ITEM* aItem, bool checkVisibilityO
|
|||
|
||||
break;
|
||||
}
|
||||
|
||||
case SCH_MARKER_T: // Always selectable
|
||||
return true;
|
||||
|
||||
|
|
Loading…
Reference in New Issue