CHANGED: Library editors are now usable with no project loaded

Fixes https://gitlab.com/kicad/code/kicad/-/issues/3688
This commit is contained in:
Jon Evans 2020-08-07 15:22:15 -04:00
parent db501c2002
commit dcc484e114
11 changed files with 229 additions and 131 deletions

View File

@ -886,7 +886,9 @@ bool EDA_DRAW_FRAME::LibraryFileBrowser( bool doOpen, wxFileName& aFilename,
}
else
{
wxFileDialog dlg( this, prompt, Prj().GetProjectPath(), aFilename.GetFullName() ,
wxString dir = Prj().IsNullProject() ? aFilename.GetFullPath() : Prj().GetProjectPath();
wxFileDialog dlg( this, prompt, dir, aFilename.GetFullName(),
wildcard, doOpen ? wxFD_OPEN | wxFD_FILE_MUST_EXIST
: wxFD_SAVE | wxFD_CHANGE_DIR | wxFD_OVERWRITE_PROMPT );

View File

@ -132,6 +132,12 @@ const wxString PROJECT::GetProjectName() const
}
bool PROJECT::IsNullProject() const
{
return m_project_name.GetName().IsEmpty();
}
const wxString PROJECT::SymbolLibTableName() const
{
return libTableName( "sym-lib-table" );

View File

@ -217,66 +217,82 @@ PANEL_SYM_LIB_TABLE::PANEL_SYM_LIB_TABLE( DIALOG_EDIT_LIBRARY_TABLES* aParent,
m_parent( aParent ),
m_lastBrowseDir( aProjectBasePath )
{
// For user info, shows the table filenames:
m_GblTableFilename->SetLabel( aGlobalTablePath );
m_PrjTableFilename->SetLabel( aProjectTablePath );
// wxGrid only supports user owned tables if they exist past end of ~wxGrid(),
// so make it a grid owned table.
m_global_grid->SetTable( new SYMBOL_LIB_TABLE_GRID( *aGlobal ), true );
m_project_grid->SetTable( new SYMBOL_LIB_TABLE_GRID( *aProject ), true );
m_global_grid->SetTable( new SYMBOL_LIB_TABLE_GRID( *aGlobal ), true );
// Give a bit more room for combobox editors
m_global_grid->SetDefaultRowSize( m_global_grid->GetDefaultRowSize() + 4 );
m_project_grid->SetDefaultRowSize( m_project_grid->GetDefaultRowSize() + 4 );
// add Cut, Copy, and Paste to wxGrids
m_global_grid->PushEventHandler( new SYMBOL_GRID_TRICKS( m_parent, m_global_grid ) );
m_project_grid->PushEventHandler( new SYMBOL_GRID_TRICKS( m_parent, m_project_grid ) );
m_path_subs_grid->PushEventHandler( new GRID_TRICKS( m_path_subs_grid ) );
m_global_grid->SetSelectionMode( wxGrid::wxGridSelectRows );
m_project_grid->SetSelectionMode( wxGrid::wxGridSelectRows );
m_global_grid->AutoSizeColumns( false );
m_project_grid->AutoSizeColumns( false );
// For user info, shows the table filenames:
m_GblTableFilename->SetLabel( aGlobalTablePath );
wxArrayString pluginChoices;
pluginChoices.Add( SCH_IO_MGR::ShowType( SCH_IO_MGR::SCH_KICAD ) );
pluginChoices.Add( SCH_IO_MGR::ShowType( SCH_IO_MGR::SCH_LEGACY ) );
populateEnvironReadOnlyTable();
auto setupGrid =
[&]( WX_GRID* aGrid )
{
// Give a bit more room for combobox editors
aGrid->SetDefaultRowSize( aGrid->GetDefaultRowSize() + 4 );
for( wxGrid* g : { m_global_grid, m_project_grid } )
// add Cut, Copy, and Paste to wxGrids
aGrid->PushEventHandler( new SYMBOL_GRID_TRICKS( m_parent, aGrid ) );
aGrid->SetSelectionMode( wxGrid::wxGridSelectRows );
aGrid->AutoSizeColumns( false );
// Set special attributes
wxGridCellAttr* attr;
attr = new wxGridCellAttr;
attr->SetEditor( new GRID_CELL_SYMLIB_EDITOR( m_parent, &m_lastBrowseDir,
KiCadSymbolLibFileWildcard() ) );
aGrid->SetColAttr( COL_URI, attr );
attr = new wxGridCellAttr;
attr->SetEditor( new wxGridCellChoiceEditor( pluginChoices ) );
aGrid->SetColAttr( COL_TYPE, attr );
attr = new wxGridCellAttr;
attr->SetRenderer( new wxGridCellBoolRenderer() );
attr->SetReadOnly(); // not really; we delegate interactivity to GRID_TRICKS
aGrid->SetColAttr( COL_ENABLED, attr );
// all but COL_OPTIONS, which is edited with Option Editor anyways.
aGrid->AutoSizeColumn( COL_NICKNAME, false );
aGrid->AutoSizeColumn( COL_TYPE, false );
aGrid->AutoSizeColumn( COL_URI, false );
aGrid->AutoSizeColumn( COL_DESCR, false );
aGrid->AutoSizeColumn( COL_ENABLED, false );
// would set this to width of title, if it was easily known.
aGrid->SetColSize( COL_OPTIONS, 80 );
// Gives a selection to each grid, mainly for delete button. wxGrid's wake up with
// a currentCell which is sometimes not highlighted.
if( aGrid->GetNumberRows() > 0 )
aGrid->SelectRow( 0 );
};
setupGrid( m_global_grid );
if( aProject )
{
// Set special attributes
wxGridCellAttr* attr;
attr = new wxGridCellAttr;
attr->SetEditor( new GRID_CELL_SYMLIB_EDITOR( m_parent, &m_lastBrowseDir,
KiCadSymbolLibFileWildcard() ) );
g->SetColAttr( COL_URI, attr );
attr = new wxGridCellAttr;
attr->SetEditor( new wxGridCellChoiceEditor( pluginChoices ) );
g->SetColAttr( COL_TYPE, attr );
attr = new wxGridCellAttr;
attr->SetRenderer( new wxGridCellBoolRenderer() );
attr->SetReadOnly(); // not really; we delegate interactivity to GRID_TRICKS
g->SetColAttr( COL_ENABLED, attr );
// all but COL_OPTIONS, which is edited with Option Editor anyways.
g->AutoSizeColumn( COL_NICKNAME, false );
g->AutoSizeColumn( COL_TYPE, false );
g->AutoSizeColumn( COL_URI, false );
g->AutoSizeColumn( COL_DESCR, false );
g->AutoSizeColumn( COL_ENABLED, false );
// would set this to width of title, if it was easily known.
g->SetColSize( COL_OPTIONS, 80 );
m_PrjTableFilename->SetLabel( aProjectTablePath );
m_project_grid->SetTable( new SYMBOL_LIB_TABLE_GRID( *aProject ), true );
setupGrid( m_project_grid );
}
else
{
m_pageNdx = 0;
m_auinotebook->DeletePage( 1 );
m_project_grid = nullptr;
}
// add Cut, Copy, and Paste to wxGrids
m_path_subs_grid->PushEventHandler( new GRID_TRICKS( m_path_subs_grid ) );
populateEnvironReadOnlyTable();
// select the last selected page
m_auinotebook->SetSelection( m_pageNdx );
@ -294,14 +310,6 @@ PANEL_SYM_LIB_TABLE::PANEL_SYM_LIB_TABLE( DIALOG_EDIT_LIBRARY_TABLES* aParent,
m_move_up_button->SetBitmap( KiBitmap( small_up_xpm ) );
m_move_down_button->SetBitmap( KiBitmap( small_down_xpm ) );
m_browse_button->SetBitmap( KiBitmap( folder_xpm ) );
// Gives a selection to each grid, mainly for delete button. wxGrid's wake up with
// a currentCell which is sometimes not highlighted.
if( m_global_grid->GetNumberRows() > 0 )
m_global_grid->SelectRow( 0 );
if( m_project_grid->GetNumberRows() > 0 )
m_project_grid->SelectRow( 0 );
}
@ -315,7 +323,10 @@ PANEL_SYM_LIB_TABLE::~PANEL_SYM_LIB_TABLE()
// Delete the GRID_TRICKS.
// Any additional event handlers should be popped before the window is deleted.
m_global_grid->PopEventHandler( true );
m_project_grid->PopEventHandler( true );
if( m_project_grid )
m_project_grid->PopEventHandler( true );
m_path_subs_grid->PopEventHandler( true );
}
@ -324,6 +335,9 @@ bool PANEL_SYM_LIB_TABLE::verifyTables()
{
for( SYMBOL_LIB_TABLE_GRID* model : { global_model(), project_model() } )
{
if( !model )
continue;
for( int r = 0; r < model->GetNumberRows(); )
{
wxString nick = model->GetValue( r, COL_NICKNAME ).Trim( false ).Trim();
@ -368,6 +382,9 @@ bool PANEL_SYM_LIB_TABLE::verifyTables()
// check for duplicate nickNames, separately in each table.
for( SYMBOL_LIB_TABLE_GRID* model : { global_model(), project_model() } )
{
if( !model )
continue;
for( int r1 = 0; r1 < model->GetNumberRows() - 1; ++r1 )
{
wxString nick1 = model->GetValue( r1, COL_NICKNAME );
@ -399,6 +416,9 @@ bool PANEL_SYM_LIB_TABLE::verifyTables()
for( SYMBOL_LIB_TABLE* table : { global_model(), project_model() } )
{
if( !table )
continue;
for( unsigned int r = 0; r < table->GetCount(); ++r )
{
SYMBOL_LIB_TABLE_ROW& row = dynamic_cast<SYMBOL_LIB_TABLE_ROW&>( table->At( r ) );
@ -682,7 +702,7 @@ bool PANEL_SYM_LIB_TABLE::TransferDataFromWindow()
m_globalTable->reindex();
}
if( *project_model() != *m_projectTable )
if( project_model() && *project_model() != *m_projectTable )
{
m_parent->m_ProjectTableChanged = true;
@ -708,6 +728,9 @@ void PANEL_SYM_LIB_TABLE::populateEnvironReadOnlyTable()
for( SYMBOL_LIB_TABLE_GRID* tbl : { global_model(), project_model() } )
{
if( !tbl )
continue;
for( int row = 0; row < tbl->GetNumberRows(); ++row )
{
wxString uri = tbl->GetValue( row, COL_URI );
@ -783,7 +806,7 @@ SYMBOL_LIB_TABLE_GRID* PANEL_SYM_LIB_TABLE::global_model() const
SYMBOL_LIB_TABLE_GRID* PANEL_SYM_LIB_TABLE::project_model() const
{
return (SYMBOL_LIB_TABLE_GRID*) m_project_grid->GetTable();
return m_project_grid ? (SYMBOL_LIB_TABLE_GRID*) m_project_grid->GetTable() : nullptr;
}
@ -804,12 +827,16 @@ void InvokeSchEditSymbolLibTable( KIWAY* aKiway, wxWindow *aParent )
SYMBOL_LIB_TABLE* globalTable = &SYMBOL_LIB_TABLE::GetGlobalLibTable();
wxString globalTablePath = SYMBOL_LIB_TABLE::GetGlobalTableFileName();
SYMBOL_LIB_TABLE* projectTable = aKiway->Prj().SchSymbolLibTable();
SYMBOL_LIB_TABLE* projectTable = nullptr;
wxString projectPath = aKiway->Prj().GetProjectPath();
wxFileName projectTableFn( projectPath, SYMBOL_LIB_TABLE::GetSymbolLibTableFileName() );
wxString msg;
wxString currentLib;
// Don't allow editing project tables if no project is open
if( !aKiway->Prj().IsNullProject() )
projectTable = aKiway->Prj().SchSymbolLibTable();
if( libEditor )
{
currentLib = libEditor->GetCurLib();
@ -860,7 +887,7 @@ void InvokeSchEditSymbolLibTable( KIWAY* aKiway, wxWindow *aParent )
}
}
if( dlg.m_ProjectTableChanged )
if( projectTable && dlg.m_ProjectTableChanged )
{
try
{
@ -879,7 +906,7 @@ void InvokeSchEditSymbolLibTable( KIWAY* aKiway, wxWindow *aParent )
if( libEditor )
{
// Check if the currently selected symbol library been removed or disabled.
if( !currentLib.empty() && !projectTable->HasLibrary( currentLib, true ) )
if( !currentLib.empty() && projectTable && !projectTable->HasLibrary( currentLib, true ) )
{
libEditor->SetCurLib( wxEmptyString );
libEditor->emptyScreen();

View File

@ -656,6 +656,23 @@ void LIB_EDIT_FRAME::RegenerateLibraryTree()
SYMBOL_LIB_TABLE* LIB_EDIT_FRAME::selectSymLibTable( bool aOptional )
{
// If no project is loaded, always work with the global table
if( Prj().IsNullProject() )
{
SYMBOL_LIB_TABLE* ret = &SYMBOL_LIB_TABLE::GetGlobalLibTable();
if( aOptional )
{
wxMessageDialog dlg( this, _( "Add the library to the global library table?" ),
_( "Add To Global Library Table" ), wxYES_NO );
if( dlg.ShowModal() != wxID_OK )
ret = nullptr;
}
return ret;
}
wxArrayString libTableNames;
libTableNames.Add( _( "Global" ) );
libTableNames.Add( _( "Project" ) );

View File

@ -109,6 +109,14 @@ public:
*/
VTBL_ENTRY const wxString GetProjectName() const;
/**
* Checks if this project is a null project (i.e. the default project object created when
* no real project is open). The null project still presents all the same project interface,
* but is not backed by any files, so saving it makes no sense.
* @return true if this is a bull project
*/
VTBL_ENTRY bool IsNullProject() const;
/**
* Return the name of the sheet identified by the given UUID.
*/

View File

@ -262,9 +262,7 @@ void KICAD_MANAGER_FRAME::RecreateLauncher()
void KICAD_MANAGER_FRAME::SyncToolbars()
{
m_launcher->Toggle( KICAD_MANAGER_ACTIONS::editSchematic, m_active_project );
m_launcher->Toggle( KICAD_MANAGER_ACTIONS::editSymbols, m_active_project );
m_launcher->Toggle( KICAD_MANAGER_ACTIONS::editPCB, m_active_project );
m_launcher->Toggle( KICAD_MANAGER_ACTIONS::editFootprints, m_active_project );
m_launcher->Refresh();
}

View File

@ -368,26 +368,12 @@ PANEL_FP_LIB_TABLE::PANEL_FP_LIB_TABLE( DIALOG_EDIT_LIBRARY_TABLES* aParent,
{
// For user info, shows the table filenames:
m_GblTableFilename->SetLabel( aGlobalTblPath );
m_PrjTableFilename->SetLabel( aProjectTblPath );
m_global_grid->SetTable( new FP_LIB_TABLE_GRID( *aGlobal ), true );
m_project_grid->SetTable( new FP_LIB_TABLE_GRID( *aProject ), true );
// Give a bit more room for wxChoice editors
m_global_grid->SetDefaultRowSize( m_global_grid->GetDefaultRowSize() + 4 );
m_project_grid->SetDefaultRowSize( m_project_grid->GetDefaultRowSize() + 4 );
m_global_grid->SetTable( new FP_LIB_TABLE_GRID( *aGlobal ), true );
// add Cut, Copy, and Paste to wxGrids
m_global_grid->PushEventHandler( new FP_GRID_TRICKS( m_parent, m_global_grid ) );
m_project_grid->PushEventHandler( new FP_GRID_TRICKS( m_parent, m_project_grid ) );
m_path_subs_grid->PushEventHandler( new GRID_TRICKS( m_path_subs_grid ) );
m_global_grid->SetSelectionMode( wxGrid::wxGridSelectRows );
m_project_grid->SetSelectionMode( wxGrid::wxGridSelectRows );
m_global_grid->AutoSizeColumns( false );
m_project_grid->AutoSizeColumns( false );
wxArrayString choices;
choices.Add( IO_MGR::ShowType( IO_MGR::KICAD_SEXP ) );
@ -402,33 +388,64 @@ PANEL_FP_LIB_TABLE::PANEL_FP_LIB_TABLE( DIALOG_EDIT_LIBRARY_TABLES* aParent,
choices.Add( IO_MGR::ShowType( IO_MGR::PCAD ) );
*/
auto setupGrid =
[&]( WX_GRID* aGrid )
{
// Give a bit more room for wxChoice editors
aGrid->SetDefaultRowSize( aGrid->GetDefaultRowSize() + 4 );
// add Cut, Copy, and Paste to wxGrids
aGrid->PushEventHandler( new FP_GRID_TRICKS( m_parent, aGrid ) );
aGrid->SetSelectionMode( wxGrid::wxGridSelectRows );
aGrid->AutoSizeColumns( false );
wxGridCellAttr* attr;
attr = new wxGridCellAttr;
attr->SetEditor( new GRID_CELL_PATH_EDITOR( m_parent, &m_lastBrowseDir,
wxEmptyString ) );
aGrid->SetColAttr( COL_URI, attr );
attr = new wxGridCellAttr;
attr->SetEditor( new wxGridCellChoiceEditor( choices ) );
aGrid->SetColAttr( COL_TYPE, attr );
attr = new wxGridCellAttr;
attr->SetRenderer( new wxGridCellBoolRenderer() );
attr->SetReadOnly(); // not really; we delegate interactivity to GRID_TRICKS
aGrid->SetColAttr( COL_ENABLED, attr );
// all but COL_OPTIONS, which is edited with Option Editor anyways.
aGrid->AutoSizeColumn( COL_NICKNAME, false );
aGrid->AutoSizeColumn( COL_TYPE, false );
aGrid->AutoSizeColumn( COL_URI, false );
aGrid->AutoSizeColumn( COL_DESCR, false );
// would set this to width of title, if it was easily known.
aGrid->SetColSize( COL_OPTIONS, 80 );
// Gives a selection to each grid, mainly for delete button. wxGrid's wake up with
// a currentCell which is sometimes not highlighted.
if( aGrid->GetNumberRows() > 0 )
aGrid->SelectRow( 0 );
};
setupGrid( m_global_grid );
populateEnvironReadOnlyTable();
for( wxGrid* g : { m_global_grid, m_project_grid } )
if( aProject )
{
wxGridCellAttr* attr;
attr = new wxGridCellAttr;
attr->SetEditor( new GRID_CELL_PATH_EDITOR( m_parent, &m_lastBrowseDir, wxEmptyString ) );
g->SetColAttr( COL_URI, attr );
attr = new wxGridCellAttr;
attr->SetEditor( new wxGridCellChoiceEditor( choices ) );
g->SetColAttr( COL_TYPE, attr );
attr = new wxGridCellAttr;
attr->SetRenderer( new wxGridCellBoolRenderer() );
attr->SetReadOnly(); // not really; we delegate interactivity to GRID_TRICKS
g->SetColAttr( COL_ENABLED, attr );
// all but COL_OPTIONS, which is edited with Option Editor anyways.
g->AutoSizeColumn( COL_NICKNAME, false );
g->AutoSizeColumn( COL_TYPE, false );
g->AutoSizeColumn( COL_URI, false );
g->AutoSizeColumn( COL_DESCR, false );
// would set this to width of title, if it was easily known.
g->SetColSize( COL_OPTIONS, 80 );
m_PrjTableFilename->SetLabel( aProjectTblPath );
m_project_grid->SetTable( new FP_LIB_TABLE_GRID( *aProject ), true );
setupGrid( m_project_grid );
}
else
{
m_pageNdx = 0;
m_auinotebook->DeletePage( 1 );
m_project_grid = nullptr;
}
m_path_subs_grid->SetColLabelValue( 0, _( "Name" ) );
@ -457,14 +474,6 @@ PANEL_FP_LIB_TABLE::PANEL_FP_LIB_TABLE( DIALOG_EDIT_LIBRARY_TABLES* aParent,
m_browseButton->SetWidthPadding( 4 );
m_browseButton->SetMinSize( buttonSize );
// Gives a selection to each grid, mainly for delete button. wxGrid's wake up with
// a currentCell which is sometimes not highlighted.
if( m_global_grid->GetNumberRows() > 0 )
m_global_grid->SelectRow( 0 );
if( m_project_grid->GetNumberRows() > 0 )
m_project_grid->SelectRow( 0 );
// Populate the browse library options
wxMenu* browseMenu = m_browseButton->GetSplitButtonMenu();
@ -493,7 +502,10 @@ PANEL_FP_LIB_TABLE::~PANEL_FP_LIB_TABLE()
// Delete the GRID_TRICKS.
// Any additional event handlers should be popped before the window is deleted.
m_global_grid->PopEventHandler( true );
m_project_grid->PopEventHandler( true );
if( m_project_grid )
m_project_grid->PopEventHandler( true );
m_path_subs_grid->PopEventHandler( true );
}
@ -502,6 +514,9 @@ bool PANEL_FP_LIB_TABLE::verifyTables()
{
for( FP_LIB_TABLE_GRID* model : { global_model(), project_model() } )
{
if( !model )
continue;
for( int r = 0; r < model->GetNumberRows(); )
{
wxString nick = model->GetValue( r, COL_NICKNAME ).Trim( false ).Trim();
@ -546,6 +561,9 @@ bool PANEL_FP_LIB_TABLE::verifyTables()
// check for duplicate nickNames, separately in each table.
for( FP_LIB_TABLE_GRID* model : { global_model(), project_model() } )
{
if( !model )
continue;
for( int r1 = 0; r1 < model->GetNumberRows() - 1; ++r1 )
{
wxString nick1 = model->GetValue( r1, COL_NICKNAME );
@ -909,7 +927,7 @@ bool PANEL_FP_LIB_TABLE::TransferDataFromWindow()
m_global->reindex();
}
if( *project_model() != *m_project )
if( project_model() && *project_model() != *m_project )
{
m_parent->m_ProjectTableChanged = true;
@ -940,6 +958,9 @@ void PANEL_FP_LIB_TABLE::populateEnvironReadOnlyTable()
for( FP_LIB_TABLE_GRID* tbl : { global_model(), project_model() } )
{
if( !tbl )
continue;
for( int row = 0; row < tbl->GetNumberRows(); ++row )
{
wxString uri = tbl->GetValue( row, COL_URI );
@ -1010,6 +1031,9 @@ void InvokePcbLibTableEditor( KIWAY* aKiway, wxWindow* aCaller )
DIALOG_EDIT_LIBRARY_TABLES dlg( aCaller, _( "Footprint Libraries" ) );
dlg.SetKiway( &dlg, aKiway );
if( aKiway->Prj().IsNullProject() )
projectTable = nullptr;
dlg.InstallPanel( new PANEL_FP_LIB_TABLE( &dlg, globalTable, globalTablePath,
projectTable, projectTablePath,
aKiway->Prj().GetProjectPath() ) );
@ -1030,7 +1054,7 @@ void InvokePcbLibTableEditor( KIWAY* aKiway, wxWindow* aCaller )
}
}
if( dlg.m_ProjectTableChanged )
if( projectTable && dlg.m_ProjectTableChanged )
{
try
{

View File

@ -77,7 +77,7 @@ private:
FP_LIB_TABLE_GRID* project_model() const
{
return (FP_LIB_TABLE_GRID*) m_project_grid->GetTable();
return m_project_grid ? (FP_LIB_TABLE_GRID*) m_project_grid->GetTable() : nullptr;
}
FP_LIB_TABLE_GRID* cur_model() const

View File

@ -375,13 +375,14 @@ void FOOTPRINT_EDIT_FRAME::Export_Module( MODULE* aModule )
}
wxString PCB_BASE_EDIT_FRAME::CreateNewLibrary(const wxString& aLibName )
wxString PCB_BASE_EDIT_FRAME::CreateNewLibrary( const wxString& aLibName,
const wxString& aProposedName )
{
// Kicad cannot write legacy format libraries, only .pretty new format
// because the legacy format cannot handle current features.
// The footprint library is actually a directory
wxString initialPath = wxPathOnly( Prj().GetProjectFullName() );
wxString initialPath = aProposedName.IsEmpty() ? Prj().GetProjectPath() : aProposedName;
wxFileName fn;
bool doAdd = false;
@ -490,18 +491,32 @@ bool PCB_BASE_EDIT_FRAME::AddLibrary( const wxString& aFilename )
bool saveInGlobalTable = false;
bool saveInProjectTable = false;
wxArrayString libTableNames;
libTableNames.Add( _( "Global" ) );
libTableNames.Add( _( "Project" ) );
switch( SelectSingleOption( this, _( "Select Library Table" ),
_( "Choose the Library Table to add the library to:" ),
libTableNames ) )
if( Prj().IsNullProject() )
{
case 0: saveInGlobalTable = true; break;
case 1: saveInProjectTable = true; break;
default: return false;
saveInGlobalTable = true;
}
else
{
wxArrayString libTableNames;
libTableNames.Add( _( "Global" ) );
libTableNames.Add( _( "Project" ) );
switch( SelectSingleOption( this, _( "Select Library Table" ),
_( "Choose the Library Table to add the library to:" ), libTableNames ) )
{
case 0:
saveInGlobalTable = true;
break;
case 1:
saveInProjectTable = true;
break;
default:
return false;
}
}
wxString type = IO_MGR::ShowType( IO_MGR::GuessPluginTypeFromLibPath( libPath ) );

View File

@ -384,7 +384,7 @@ MODULE* FOOTPRINT_EDIT_FRAME::SelectFootprintFromBoard( BOARD* aPcb )
bool FOOTPRINT_EDIT_FRAME::SaveLibraryAs( const wxString& aLibraryPath )
{
const wxString& curLibPath = aLibraryPath;
wxString dstLibPath = CreateNewLibrary();
wxString dstLibPath = CreateNewLibrary( wxEmptyString, aLibraryPath );
if( !dstLibPath )
return false; // user aborted in CreateNewLibrary()

View File

@ -44,17 +44,18 @@ public:
virtual ~PCB_BASE_EDIT_FRAME();
/**
* Function CreateNewLibrary
* If a library name is given, creates a new footprint library in the project folder
* with the given name. If no library name is given it prompts user for a library path,
* then creates a new footprint library at that location.
* If library exists, user is warned about that, and is given a chance
* to abort the new creation, and in that case existing library is first deleted.
* @param aProposedName is the inital path and filename shown in the file chooser dialog
*
* @return wxString - the newly created library path if library was successfully
* created, else wxEmptyString because user aborted or error.
*/
wxString CreateNewLibrary(const wxString& aLibName = wxEmptyString);
wxString CreateNewLibrary( const wxString& aLibName = wxEmptyString,
const wxString& aProposedName = wxEmptyString );
/**
* Function AddLibrary