Commit c50efb48 authored by jean-pierre charras's avatar jean-pierre charras

pcbnew: better code to read/modify/delete footprints in module libraries.

parent ec7475f3
...@@ -45,11 +45,6 @@ parameter is a double) ...@@ -45,11 +45,6 @@ parameter is a double)
Workaround: Workaround:
Use a version > 2.9.1 Use a version > 2.9.1
Currently ( 2011, april 12 ) the 2.9.2 is not yet finalized
(and can be found only on the wxWidgets snv server)
can be fixed by replacing the file <wxWidgets-2.9.1>/src/common/xlocale.cpp
by the corresponding file from the 2.9.2 version (from wxWidgets svn server)
************************************************************************************* *************************************************************************************
wxGTK version: All wxGTK version: All
......
/************************/ /*
/* Menu "CONFIRMATION" */ * confirm.cpp
/* Function get_Message */ * utilities to display some error, warning and info short messges
/* Test requires ESC */ */
/************************/
#include "fctsys.h" #include "fctsys.h"
#include "common.h" #include "common.h"
enum id_dialog {
ID_TIMOUT = 1500
};
/* Class for displaying messages, similar to wxMessageDialog,
* but can be erased after a time out expires.
*
* @note - Do not use the time feature. It is broken by design because
* the dialog is shown as modal and wxWidgets will assert when
* compiled in the debug mode. This is because the dialog steals
* the event queue when dialog is modal so the timer event never
* gets to the dialog event handle. Using dialogs to display
* transient is brain dead anyway. Use the message panel or some
* other method.
*/
class WinEDA_MessageDialog : public wxMessageDialog
{
private:
int m_LifeTime;
wxTimer m_Timer;
public:
WinEDA_MessageDialog( wxWindow * parent, const wxString &msg,
const wxString &title, int style, int lifetime );
~WinEDA_MessageDialog() { };
void OnTimeOut( wxTimerEvent& event );
DECLARE_EVENT_TABLE()
};
BEGIN_EVENT_TABLE( WinEDA_MessageDialog, wxMessageDialog )
EVT_TIMER( ID_TIMOUT, WinEDA_MessageDialog::OnTimeOut )
END_EVENT_TABLE()
WinEDA_MessageDialog::WinEDA_MessageDialog( wxWindow* parent,
const wxString& msg,
const wxString& title,
int style,
int lifetime ) :
wxMessageDialog( parent, msg, title, style )
{
m_LifeTime = lifetime;
m_Timer.SetOwner( this, ID_TIMOUT );
if( m_LifeTime > 0 )
m_Timer.Start( 100 * m_LifeTime, wxTIMER_ONE_SHOT );
}
void WinEDA_MessageDialog::OnTimeOut( wxTimerEvent& event )
{
m_Timer.Stop();
EndModal( wxID_YES ); /* Does not work, I do not know why (this
* function is correctly called after time out).
* See not above as to why this doesn't work. */
}
/* Display an error or warning message. /* Display an error or warning message.
* If display time > 0 the dialog disappears after displayTime 0.1 seconds * TODO:
* If display time > 0 the dialog disappears after displayTime ( in 0.1 second )
* *
*/ */
void DisplayError( wxWindow* parent, const wxString& text, int displaytime ) void DisplayError( wxWindow* parent, const wxString& text, int displaytime )
...@@ -76,12 +17,11 @@ void DisplayError( wxWindow* parent, const wxString& text, int displaytime ) ...@@ -76,12 +17,11 @@ void DisplayError( wxWindow* parent, const wxString& text, int displaytime )
wxMessageDialog* dialog; wxMessageDialog* dialog;
if( displaytime > 0 ) if( displaytime > 0 )
dialog = new WinEDA_MessageDialog( parent, text, _( "Warning" ), dialog = new wxMessageDialog( parent, text, _( "Warning" ),
wxOK | wxICON_INFORMATION, wxOK | wxCENTRE | wxICON_INFORMATION );
displaytime );
else else
dialog = new WinEDA_MessageDialog( parent, text, _( "Error" ), dialog = new wxMessageDialog( parent, text, _( "Error" ),
wxOK | wxICON_ERROR, 0 ); wxOK | wxCENTRE | wxICON_ERROR );
dialog->ShowModal(); dialog->ShowModal();
dialog->Destroy(); dialog->Destroy();
...@@ -89,14 +29,16 @@ void DisplayError( wxWindow* parent, const wxString& text, int displaytime ) ...@@ -89,14 +29,16 @@ void DisplayError( wxWindow* parent, const wxString& text, int displaytime )
/* Display an informational message. /* Display an informational message.
* TODO:
* If display time > 0 the message disappears after displayTime (in 0.1 second )
*/ */
void DisplayInfoMessage( wxWindow* parent, const wxString& text, void DisplayInfoMessage( wxWindow* parent, const wxString& text,
int displaytime ) int displaytime )
{ {
wxMessageDialog* dialog; wxMessageDialog* dialog;
dialog = new WinEDA_MessageDialog( parent, text, _( "Info:" ), dialog = new wxMessageDialog( parent, text, _( "Info:" ),
wxOK | wxICON_INFORMATION, displaytime ); wxOK | wxCENTRE | wxICON_INFORMATION );
dialog->ShowModal(); dialog->ShowModal();
dialog->Destroy(); dialog->Destroy();
......
...@@ -93,6 +93,7 @@ set(PCBNEW_SRCS ...@@ -93,6 +93,7 @@ set(PCBNEW_SRCS
block.cpp block.cpp
block_module_editor.cpp block_module_editor.cpp
build_BOM_from_board.cpp build_BOM_from_board.cpp
class_footprint_library.cpp
class_pcb_layer_widget.cpp class_pcb_layer_widget.cpp
clean.cpp clean.cpp
connect.cpp connect.cpp
......
/**
* @file class_footprint_library.cpp
* Helper class to read/write footprint libraries.
*/
#include "fctsys.h"
#include "kicad_string.h"
#include "pcbnew.h"
#include "wxPcbStruct.h"
#include "richio.h"
#include "filter_reader.h"
#include "class_footprint_library.h"
/*
* Module library header format:
* LIBRARY HEADER-datetime
* $INDEX
* List of modules names (1 name per line)
* $EndIndex
* List of descriptions of Modules
* $EndLIBRARY
*/
FOOTPRINT_LIBRARY::FOOTPRINT_LIBRARY( FILE * aFile, FILTER_READER * aReader )
{
wxASSERT( m_reader || m_file );
m_file = aFile;
m_reader = aReader;
m_LineNum = 0;
}
/* function IsLibrary
* Read the library file Header
* return > 0 if this file is a footprint lib
* (currentlu return 1 but could be a value > 1 for future file formats
*/
int FOOTPRINT_LIBRARY::IsLibrary( )
{
char *line;
char buffer[1024];
if( m_reader )
{
m_reader->ReadLine();
line = m_reader->Line();
}
else
{
line = buffer;
GetLine( m_file, line, &m_LineNum );
}
StrPurge( line );
if( strnicmp( line, ENTETE_LIBRAIRIE, L_ENTETE_LIB ) == 0 )
return 1;
return 0;
}
/*
* function RebuildIndex
* Read the full library file and build the list od footprints found
* and do not use the $INDEX ... $EndINDEX section
*/
bool FOOTPRINT_LIBRARY::RebuildIndex()
{
m_List.Clear();
char name[1024];
if( m_reader )
{
while( m_reader->ReadLine() )
{
char * line = m_reader->Line();
StrPurge( line );
if( strnicmp( line, "$MODULE", 7 ) == 0 )
{
sscanf( line + 7, " %s", name );
m_List.Add( FROM_UTF8( name ) );
}
}
}
else
{
char line[1024];
while( GetLine( m_file, line, &m_LineNum ) )
{
if( strnicmp( line, "$MODULE", 7 ) == 0 )
{
sscanf( line + 7, " %s", name );
m_List.Add( FROM_UTF8( name ) );
}
}
}
return true;
}
/* function ReadSectionIndex
* Read the $INDEX ... $EndINDEX section
* list of footprints is stored in m_List
*/
bool FOOTPRINT_LIBRARY::ReadSectionIndex()
{
// Some broken INDEX sections have more than one section
// So we must read the next line after $EndINDEX tag,
// to see if this is not a new $INDEX tag.
bool exit = false;
if( m_reader )
{
while( m_reader->ReadLine() )
{
char * line = m_reader->Line();
StrPurge( line );
if( strnicmp( line, "$INDEX", 6 ) == 0 )
{
exit = false;
while( m_reader->ReadLine() )
{
StrPurge( line );
m_List.Add( FROM_UTF8( line ) );
if( strnicmp( line, "$EndINDEX", 9 ) == 0 )
{
exit = true;
break;
}
}
}
else if( exit )
break;
}
}
else
{
char line[1024];
while( GetLine( m_file, line, &m_LineNum ) )
{
if( strnicmp( line, "$INDEX", 6 ) == 0 )
{
exit = false;
while( GetLine( m_file, line, &m_LineNum ) )
{
StrPurge( line );
m_List.Add( FROM_UTF8( line ) );
if( strnicmp( line, "$EndINDEX", 9 ) == 0 )
{
exit = true;
break;
}
}
}
else if( exit )
break;
}
}
return true;
}
/* Function WriteHeader
* Write the library header
*/
bool FOOTPRINT_LIBRARY::WriteHeader()
{
char line[256];
fprintf( m_file, "%s %s\n", ENTETE_LIBRAIRIE, DateAndTime( line ) );
fprintf( m_file, "# encoding utf-8\n");
return true;
}
/* Function WriteSectionIndex
* Write the $INDEX ... $EndINDEX section.
* This section is filled by names in m_List
*/
bool FOOTPRINT_LIBRARY::WriteSectionIndex()
{
fputs( "$INDEX\n", m_file );
for( unsigned ii = 0; ii < m_List.GetCount(); ii++ )
{
fprintf( m_file, "%s\n", TO_UTF8( m_List[ii] ) );
}
fputs( "$EndINDEX\n", m_file );
return true;
}
/* Function WriteEndOfFile
* Write the last line section.
*/
bool FOOTPRINT_LIBRARY::WriteEndOfFile()
{
fputs( "$EndLIBRARY\n", m_file );
return true;
}
/*
* Function FindInList
* Search for aName int m_List and return true if found
*/
bool FOOTPRINT_LIBRARY::FindInList( const wxString & aName )
{
for( unsigned ii = 0; ii < m_List.GetCount(); ii++ )
{
if( m_List[ii].CmpNoCase( aName ) == 0 )
return true;
}
return false;
}
/**
* Function RemoveFromList
* Search for aName int m_List and remove it
* @return true if found and removed
*/
bool FOOTPRINT_LIBRARY::RemoveFromList( const wxString & aName )
{
for( unsigned ii = 0; ii < m_List.GetCount(); ii++ )
{
if( m_List[ii].CmpNoCase( aName ) == 0 )
{
m_List.RemoveAt(ii);
return true;
}
}
return false;
}
/**
* Function SortList
* Sort m_List in alphabetic order
*/
void FOOTPRINT_LIBRARY::SortList()
{
m_List.Sort();
}
/* Helper class to read/write footprints libraries
*/
#ifndef _FOOTPRINT_LIBRARY_H_
#define _FOOTPRINT_LIBRARY_H_
#include "filter_reader.h"
class FOOTPRINT_LIBRARY
{
public:
wxArrayString m_List; // list of footprints, used to read/write INDEX section
wxString m_LibraryName; // the full library name
int m_LineNum; // the line count
private:
FILTER_READER * m_reader; // FILTER_READER to read file. id NULL, use m_file
FILE * m_file; // footprint file to read/write.
public:
/**
* ctor
* @param aFile = a FILE * pointer used for write operations,
* and read operations when aReader = NULL
* @param aReader = a FILTER_READER pointer used for read operations
* If NULL, a direct aFILE read is used
*/
FOOTPRINT_LIBRARY( FILE * aFile, FILTER_READER * aReader = NULL );
~FOOTPRINT_LIBRARY() { }
/**
* function IsLibrary
* Read the library file Header
* return > 0 if this file is a footprint lib
* (currentlu return 1 but could be a value > 1 for future file formats
*/
int IsLibrary( );
/**
* function RebuildIndex
* Read the full library file and build the list od footprints found
* Do not use the $INDEX ... $EndINDEX section
*/
bool RebuildIndex();
/**
* function ReadSectionIndex
* Read the $INDEX ... $EndINDEX section
* list of footprints is stored in m_List
*/
bool ReadSectionIndex();
/**
* Function WriteHeader
* Write the library header
*/
bool WriteHeader();
/**
* Function WriteSectionIndex
* Write the $INDEX ... $EndINDEX section.
* This section is filled by names in m_List
*/
bool WriteSectionIndex();
/**
* Function WriteEndOfFile
* Write the last line section.
*/
bool WriteEndOfFile();
/**
* Function FindInList
* Search for aName int m_List
* @return true if found
*/
bool FindInList( const wxString & aName );
/**
* Function RemoveFromList
* Search for aName int m_List and remove it
* @return true if found and removed
*/
bool RemoveFromList( const wxString & aName );
/**
* Function SortList
* Sort m_List in alphabetic order
*/
void SortList();
};
#endif
...@@ -15,6 +15,7 @@ ...@@ -15,6 +15,7 @@
#include "dialog_helpers.h" #include "dialog_helpers.h"
#include "richio.h" #include "richio.h"
#include "filter_reader.h" #include "filter_reader.h"
#include "class_footprint_library.h"
/* /*
* Module library header format: * Module library header format:
...@@ -152,7 +153,6 @@ MODULE* WinEDA_ModuleEditFrame::Import_Module( ) ...@@ -152,7 +153,6 @@ MODULE* WinEDA_ModuleEditFrame::Import_Module( )
void WinEDA_ModuleEditFrame::Export_Module( MODULE* aModule, bool aCreateSysLib ) void WinEDA_ModuleEditFrame::Export_Module( MODULE* aModule, bool aCreateSysLib )
{ {
wxFileName fn; wxFileName fn;
char Line[1025];
FILE* file; FILE* file;
wxString msg, path, title, wildcard; wxString msg, path, title, wildcard;
wxConfig* Config = wxGetApp().m_EDA_Config; wxConfig* Config = wxGetApp().m_EDA_Config;
...@@ -192,20 +192,18 @@ void WinEDA_ModuleEditFrame::Export_Module( MODULE* aModule, bool aCreateSysLib ...@@ -192,20 +192,18 @@ void WinEDA_ModuleEditFrame::Export_Module( MODULE* aModule, bool aCreateSysLib
Config->Write( EXPORT_IMPORT_LASTPATH_KEY, fn.GetPath() ); Config->Write( EXPORT_IMPORT_LASTPATH_KEY, fn.GetPath() );
} }
// Switch the locale to standard C (needed to read floating point numbers // Switch the locale to standard C (needed to read/write floating point numbers
// like 1.3) // like 1.3)
SetLocaleTo_C_standard(); SetLocaleTo_C_standard();
fprintf( file, "%s %s\n", ENTETE_LIBRAIRIE, DateAndTime( Line ) ); FOOTPRINT_LIBRARY libexport( file );
fprintf( file, "# encoding utf-8\n"); libexport.WriteHeader();
fputs( "$INDEX\n", file ); libexport.m_List.Add(aModule->m_LibRef);
libexport.WriteSectionIndex();
fprintf( file, "%s\n", TO_UTF8( aModule->m_LibRef ) );
fputs( "$EndINDEX\n", file );
GetBoard()->m_Modules->Save( file ); GetBoard()->m_Modules->Save( file );
fputs( "$EndLIBRARY\n", file ); libexport.WriteEndOfFile();
fclose( file ); fclose( file );
SetLocaleTo_Default(); // revert to the current locale SetLocaleTo_Default(); // revert to the current locale
...@@ -220,9 +218,9 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname ...@@ -220,9 +218,9 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname
{ {
wxFileName newFileName; wxFileName newFileName;
wxFileName oldFileName; wxFileName oldFileName;
int ii, NoFound = 1, LineNum = 0; int LineNum = 0;
char Line[1024], Name[256]; char Line[1024], Name[256];
FILE* dest, * lib_module; FILE* out_file, * lib_module;
wxString CmpName, msg; wxString CmpName, msg;
CmpName = Select_1_Module_From_List( this, CmpName = Select_1_Module_From_List( this,
...@@ -245,44 +243,28 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname ...@@ -245,44 +243,28 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname
wxT( "rt" ) ) ) == NULL ) wxT( "rt" ) ) ) == NULL )
{ {
wxString msg; wxString msg;
msg = _( "Library " ) + oldFileName.GetFullPath() + _( " not found" ); msg.Printf( _( "Library %s not found" ), GetChars(oldFileName.GetFullPath()) );
DisplayError( this, msg ); DisplayError( this, msg );
return; return;
} }
/* Read header. */ FOOTPRINT_LIBRARY input_lib( lib_module );
GetLine( lib_module, Line, &LineNum );
if( strnicmp( Line, ENTETE_LIBRAIRIE, L_ENTETE_LIB ) != 0 ) /* Read header. */
if( ! input_lib.IsLibrary() )
{ {
DisplayError( this, _( "Not a Library file" ) );
fclose( lib_module ); fclose( lib_module );
wxString msg;
msg.Printf( _( "%s is not a Library file" ), GetChars(oldFileName.GetFullPath()) );
DisplayError( this, msg );
return; return;
} }
/* Read module names. */ /* Read module names. */
while( GetLine( lib_module, Line, &LineNum ) ) input_lib.RebuildIndex();
{ bool found = input_lib.FindInList( CmpName );
if( strnicmp( Line, "$INDEX", 6 ) == 0 ) if( !found )
{
while( GetLine( lib_module, Line, &LineNum ) )
{
StrPurge( Line );
msg = FROM_UTF8( Line );
if( CmpName.CmpNoCase( msg ) == 0 ) /* New module? */
{
NoFound = 0; break;
}
if( strnicmp( Line, "$EndINDEX", 9 ) == 0 )
break;
}
}
if( strnicmp( Line, "$EndINDEX", 9 ) == 0 )
break;
}
if( NoFound )
{ {
fclose( lib_module ); fclose( lib_module );
msg.Printf( _( "Module [%s] not found" ), GetChars( CmpName ) ); msg.Printf( _( "Module [%s] not found" ), GetChars( CmpName ) );
...@@ -294,7 +276,7 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname ...@@ -294,7 +276,7 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname
newFileName = oldFileName; newFileName = oldFileName;
newFileName.SetExt( FILETMP_EXT ); newFileName.SetExt( FILETMP_EXT );
if( ( dest = wxFopen( newFileName.GetFullPath(), wxT( "wt" ) ) ) == NULL ) if( ( out_file = wxFopen( newFileName.GetFullPath(), wxT( "wt" ) ) ) == NULL )
{ {
fclose( lib_module ); fclose( lib_module );
wxString msg; wxString msg;
...@@ -305,48 +287,29 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname ...@@ -305,48 +287,29 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname
wxBeginBusyCursor(); wxBeginBusyCursor();
/* Create header with new date. */ FOOTPRINT_LIBRARY output_lib( out_file );
fprintf( dest, ENTETE_LIBRAIRIE ); output_lib.m_List = input_lib.m_List;
fprintf( dest, " %s\n", DateAndTime( Line ) );
fprintf( dest, "# encoding utf-8\n");
fprintf( dest, "$INDEX\n" );
fseek( lib_module, 0, 0 ); output_lib.WriteHeader();
GetLine( lib_module, Line, &ii ); output_lib.RemoveFromList(CmpName);
output_lib.SortList();
while( GetLine( lib_module, Line, &ii ) ) output_lib.WriteSectionIndex();
{
if( strnicmp( Line, "$M", 2 ) == 0 )
break;
if( strnicmp( Line, "$INDEX", 6 ) == 0 )
{
while( GetLine( lib_module, Line, &ii ) )
{
if( strnicmp( Line, "$EndINDEX", 9 ) == 0 )
break;
StrPurge( Line );
msg = FROM_UTF8( Line );
if( CmpName.CmpNoCase( msg ) != 0 )
fprintf( dest, "%s\n", Line );
}
}
if( strnicmp( Line, "$EndINDEX", 9 ) == 0 )
break;
}
fprintf( dest, "$EndINDEX\n" );
/* Copy modules. */ /* Copy modules. */
rewind( lib_module );
LineNum = input_lib.m_LineNum;
bool copylines = false;
while( GetLine( lib_module, Line, &LineNum ) ) while( GetLine( lib_module, Line, &LineNum ) )
{ {
StrPurge( Line ); StrPurge( Line );
if( strnicmp( Line, "$MODULE", 7 ) == 0 ) if( strnicmp( Line, "$MODULE", 7 ) == 0 )
{ {
copylines = true;
sscanf( Line + 7, " %s", Name ); sscanf( Line + 7, " %s", Name );
msg = FROM_UTF8( Name ); msg = FROM_UTF8( Name );
if( msg.CmpNoCase( CmpName ) == 0 ) if( msg.CmpNoCase( CmpName ) == 0 )
{ {
/* Delete old module. */ /* Delete old module (i.e. do not copy description to out_file). */
while( GetLine( lib_module, Line, &LineNum ) ) while( GetLine( lib_module, Line, &LineNum ) )
{ {
if( strnicmp( Line, "$EndMODULE", 9 ) == 0 ) if( strnicmp( Line, "$EndMODULE", 9 ) == 0 )
...@@ -356,11 +319,12 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname ...@@ -356,11 +319,12 @@ void WinEDA_ModuleEditFrame::Delete_Module_In_Library( const wxString& aLibname
continue; continue;
} }
} }
fprintf( dest, "%s\n", Line ); if( copylines )
fprintf( out_file, "%s\n", Line );
} }
fclose( lib_module ); fclose( lib_module );
fclose( dest ); fclose( out_file );
wxEndBusyCursor(); wxEndBusyCursor();
...@@ -448,12 +412,10 @@ void PCB_BASE_FRAME::Archive_Modules( const wxString& LibName, bool NewModulesOn ...@@ -448,12 +412,10 @@ void PCB_BASE_FRAME::Archive_Modules( const wxString& LibName, bool NewModulesOn
DisplayError( this, msg ); DisplayError( this, msg );
return; return;
} }
char Line[256]; FOOTPRINT_LIBRARY new_lib( lib_module );
fprintf( lib_module, "%s %s\n", ENTETE_LIBRAIRIE, DateAndTime( Line ) ); new_lib.WriteHeader();
fprintf( lib_module, "# encoding utf-8\n"); new_lib.WriteSectionIndex();
fputs( "$INDEX\n", lib_module ); new_lib.WriteEndOfFile();
fputs( "$EndINDEX\n", lib_module );
fputs( "$EndLIBRARY\n", lib_module );
fclose( lib_module ); fclose( lib_module );
} }
...@@ -498,13 +460,11 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName, ...@@ -498,13 +460,11 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName,
{ {
wxFileName oldFileName; wxFileName oldFileName;
wxFileName newFileName; wxFileName newFileName;
int newmodule, end;
int LineNum = 0, tmp; int LineNum = 0, tmp;
char Name[256], Line[1024]; char Name[256], Line[1024];
wxString Name_Cmp; wxString Name_Cmp;
wxString msg; wxString msg;
FILE* lib_module, * dest; FILE* lib_module, * dest;
bool added = true;
if( aModule == NULL ) if( aModule == NULL )
return false; return false;
...@@ -541,9 +501,10 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName, ...@@ -541,9 +501,10 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName,
return false; return false;
} }
/* Read library file : library header */ /* Read library file */
GetLine( lib_module, Line, &LineNum ); FOOTPRINT_LIBRARY input_lib( lib_module );
if( strnicmp( Line, ENTETE_LIBRAIRIE, L_ENTETE_LIB ) != 0 )
if( ! input_lib.IsLibrary() )
{ {
fclose( lib_module ); fclose( lib_module );
msg.Printf( _( "File %s is not a eeschema library" ), msg.Printf( _( "File %s is not a eeschema library" ),
...@@ -553,53 +514,26 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName, ...@@ -553,53 +514,26 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName,
} }
/* Read footprints in lib: - search for an existing footprint */ /* Read footprints in lib: - search for an existing footprint */
newmodule = 1; end = 0; input_lib.RebuildIndex();
while( !end && GetLine( lib_module, Line, &LineNum ) ) bool module_exists = input_lib.FindInList( Name_Cmp );
{ if( module_exists )
if( strncmp( Line, "$INDEX", 6 ) != 0 )
continue;
while( GetLine( lib_module, Line, &LineNum ) )
{
if( strncmp( Line, "$EndINDEX", 9 ) == 0 )
{
end = 1; break;
}
StrPurge( Line );
msg = FROM_UTF8( Line );
if( Name_Cmp.CmpNoCase( msg ) == 0 ) /* an existing footprint is
* found */
{ {
added = false; // an existing footprint is found in current lib
newmodule = 0;
if( aDisplayDialog ) if( aDisplayDialog )
{ {
msg = _( "Module exists\n Line: " ); msg = _( "Module exists\n Line: " );
msg << LineNum; msg << LineNum;
SetStatusText( msg ); SetStatusText( msg );
} }
if( !aOverwrite ) /* Do not save the given footprint: an old if( !aOverwrite ) // Do not save the given footprint: an old one exists
* one exists */
{ {
fclose( lib_module ); fclose( lib_module );
return 1; return 1;
} }
end = 1; break;
}
}
} }
fclose( lib_module );
/* Creates the new library */ /* Creates the new library */
if( ( lib_module = wxFopen( aLibName, wxT( "rt" ) ) ) == NULL )
{
DisplayError( this, wxT( "Librairi.cpp: Error oldlib not found" ) );
return false;
}
newFileName = aLibName; newFileName = aLibName;
newFileName.SetExt( FILETMP_EXT ); newFileName.SetExt( FILETMP_EXT );
...@@ -617,35 +551,27 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName, ...@@ -617,35 +551,27 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName,
// like 1.3) // like 1.3)
SetLocaleTo_C_standard(); SetLocaleTo_C_standard();
FOOTPRINT_LIBRARY output_lib( dest );
output_lib.m_List = input_lib.m_List;
if( ! module_exists )
output_lib.m_List.Add( Name_Cmp );
output_lib.SortList();
/* Create the library header with a new date */ /* Create the library header with a new date */
fprintf( dest, ENTETE_LIBRAIRIE ); output_lib.WriteHeader();
fprintf( dest, " %s\n", DateAndTime( Line ) ); output_lib.WriteSectionIndex();
fprintf( dest, "# encoding utf-8\n");
fprintf( dest, "$INDEX\n" );
LineNum = 0; LineNum = 0;
rewind( lib_module);
GetLine( lib_module, Line, &LineNum ); GetLine( lib_module, Line, &LineNum );
while( GetLine( lib_module, Line, &LineNum ) ) while( GetLine( lib_module, Line, &LineNum ) )
{ {
StrPurge( Line ); StrPurge( Line );
if( strnicmp( Line, "$MODULE", 7 ) == 0 ) if( strnicmp( Line, "$MODULE", 7 ) == 0 )
break; break;
if( strnicmp( Line, "$INDEX", 6 ) == 0 )
{
while( GetLine( lib_module, Line, &LineNum ) )
{
if( strnicmp( Line, "$EndINDEX", 9 ) == 0 )
break;
fprintf( dest, "%s\n", Line );
} }
}
if( newmodule )
fprintf( dest, "%s\n", TO_UTF8( Name_Cmp ) );
if( strnicmp( Line, "$EndINDEX", 9 ) == 0 )
break;
}
fprintf( dest, "$EndINDEX\n" );
/* Copy footprints, until the old footprint to delete */ /* Copy footprints, until the old footprint to delete */
while( GetLine( lib_module, Line, &LineNum ) ) while( GetLine( lib_module, Line, &LineNum ) )
...@@ -675,9 +601,10 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName, ...@@ -675,9 +601,10 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName,
/* Write the new footprint ( append it to the list of footprint ) */ /* Write the new footprint ( append it to the list of footprint ) */
tmp = aModule->m_TimeStamp; aModule->m_TimeStamp = 0; tmp = aModule->m_TimeStamp; aModule->m_TimeStamp = 0;
aModule->Save( dest ); aModule->Save( dest );
fprintf( dest, "$EndLIBRARY\n" );
aModule->m_TimeStamp = tmp; aModule->m_TimeStamp = tmp;
output_lib.WriteEndOfFile();
fclose( dest ); fclose( dest );
fclose( lib_module ); fclose( lib_module );
SetLocaleTo_Default(); // revert to the current locale SetLocaleTo_Default(); // revert to the current locale
...@@ -704,7 +631,7 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName, ...@@ -704,7 +631,7 @@ bool PCB_BASE_FRAME::Save_Module_In_Library( const wxString& aLibName,
if( aDisplayDialog ) if( aDisplayDialog )
{ {
msg = _( "Component " ); msg += Name_Cmp; msg = _( "Component " ); msg += Name_Cmp;
msg += added ? _( " added in " ) : _( " replaced in " ); msg += module_exists ? _( " replaced in " ) : _( " added in " );
msg += aLibName; msg += aLibName;
SetStatusText( msg ); SetStatusText( msg );
} }
...@@ -800,7 +727,6 @@ int WinEDA_ModuleEditFrame::Create_Librairie( const wxString& LibName ) ...@@ -800,7 +727,6 @@ int WinEDA_ModuleEditFrame::Create_Librairie( const wxString& LibName )
{ {
FILE* lib_module; FILE* lib_module;
wxString msg; wxString msg;
char cbuf[256];
if( wxFileExists( LibName ) ) if( wxFileExists( LibName ) )
{ {
...@@ -816,18 +742,10 @@ int WinEDA_ModuleEditFrame::Create_Librairie( const wxString& LibName ) ...@@ -816,18 +742,10 @@ int WinEDA_ModuleEditFrame::Create_Librairie( const wxString& LibName )
return -1; return -1;
} }
/* Write the header of the new library. */ FOOTPRINT_LIBRARY new_lib( lib_module );
if( fprintf( lib_module, ENTETE_LIBRAIRIE ) == 0 ) new_lib.WriteHeader();
{ new_lib.WriteSectionIndex();
msg = _( "Create error " ) + LibName; new_lib.WriteEndOfFile();
DisplayError( this, msg );
fclose( lib_module );
return -1;
}
fprintf( lib_module, " %s\n", DateAndTime( cbuf ) );
fputs( "$INDEX\n", lib_module );
fputs( "$EndINDEX\n", lib_module );
fclose( lib_module ); fclose( lib_module );
return 1; return 1;
......
...@@ -17,6 +17,7 @@ ...@@ -17,6 +17,7 @@
#include "dialog_helpers.h" #include "dialog_helpers.h"
#include "filter_reader.h" #include "filter_reader.h"
#include "footprint_info.h" #include "footprint_info.h"
#include "class_footprint_library.h"
static void DisplayCmpDoc( wxString& Name ); static void DisplayCmpDoc( wxString& Name );
...@@ -194,9 +195,7 @@ MODULE* PCB_BASE_FRAME::Get_Librairie_Module( const wxString& aLibraryFullFilena ...@@ -194,9 +195,7 @@ MODULE* PCB_BASE_FRAME::Get_Librairie_Module( const wxString& aLibraryFullFilena
const wxString& aModuleName, const wxString& aModuleName,
bool aDisplayMessageError ) bool aDisplayMessageError )
{ {
int found = 0;
wxFileName fn; wxFileName fn;
char* Line;
wxString Name; wxString Name;
wxString msg, tmp; wxString msg, tmp;
MODULE* NewModule; MODULE* NewModule;
...@@ -244,11 +243,9 @@ MODULE* PCB_BASE_FRAME::Get_Librairie_Module( const wxString& aLibraryFullFilena ...@@ -244,11 +243,9 @@ MODULE* PCB_BASE_FRAME::Get_Librairie_Module( const wxString& aLibraryFullFilena
msg.Printf( _( "Scan Lib: %s" ), GetChars( tmp ) ); msg.Printf( _( "Scan Lib: %s" ), GetChars( tmp ) );
SetStatusText( msg ); SetStatusText( msg );
/* Reading header ENTETE_LIBRAIRIE */ FOOTPRINT_LIBRARY curr_lib( file, &reader );
reader.ReadLine();
Line = reader.Line(); if( !curr_lib.IsLibrary() )
StrPurge( Line );
if( strnicmp( Line, ENTETE_LIBRAIRIE, L_ENTETE_LIB ) != 0 )
{ {
msg.Printf( _( "<%s> is not a valid Kicad PCB footprint library file." ), msg.Printf( _( "<%s> is not a valid Kicad PCB footprint library file." ),
GetChars( tmp ) ); GetChars( tmp ) );
...@@ -258,47 +255,23 @@ MODULE* PCB_BASE_FRAME::Get_Librairie_Module( const wxString& aLibraryFullFilena ...@@ -258,47 +255,23 @@ MODULE* PCB_BASE_FRAME::Get_Librairie_Module( const wxString& aLibraryFullFilena
} }
/* Reading the list of modules in the library. */ /* Reading the list of modules in the library. */
found = 0; curr_lib.ReadSectionIndex();
while( !found && reader.ReadLine() ) bool found = curr_lib.FindInList( aModuleName );
{
Line = reader.Line();
if( strnicmp( Line, "$MODULE", 6 ) == 0 )
break;
if( strnicmp( Line, "$INDEX", 6 ) == 0 )
{
while( reader.ReadLine() )
{
Line = reader.Line();
if( strnicmp( Line, "$EndINDEX", 9 ) == 0 )
break;
StrPurge( Line );
msg = FROM_UTF8( Line );
if( msg.CmpNoCase( aModuleName ) == 0 )
{
found = 1;
break; /* found! */
}
}
}
}
/* Read library. */ /* Read library. */
while( found && reader.ReadLine() ) if( found )
{ {
Line = reader.Line(); fileReader.Rewind();
if( Line[0] != '$' ) while( reader.ReadLine() )
continue; {
char * line = reader.Line();
if( Line[1] != 'M' ) StrPurge( line + 8 );
continue;
if( strnicmp( Line, "$MODULE", 7 ) != 0 ) if( strnicmp( line, "$MODULE", 7 ) != 0 )
continue; continue;
StrPurge( Line + 8 );
// Read module name. // Read module name.
Name = FROM_UTF8( Line + 8 ); Name = FROM_UTF8( line + 8 );
if( Name.CmpNoCase( aModuleName ) == 0 ) if( Name.CmpNoCase( aModuleName ) == 0 )
{ {
...@@ -314,6 +287,7 @@ MODULE* PCB_BASE_FRAME::Get_Librairie_Module( const wxString& aLibraryFullFilena ...@@ -314,6 +287,7 @@ MODULE* PCB_BASE_FRAME::Get_Librairie_Module( const wxString& aLibraryFullFilena
return NewModule; return NewModule;
} }
} }
}
if( one_lib ) if( one_lib )
break; break;
...@@ -384,6 +358,8 @@ wxString PCB_BASE_FRAME::Select_1_Module_From_List( EDA_DRAW_FRAME* aWindow, ...@@ -384,6 +358,8 @@ wxString PCB_BASE_FRAME::Select_1_Module_From_List( EDA_DRAW_FRAME* aWindow,
for( unsigned ii = 0; ii < MList.GetCount(); ii++ ) for( unsigned ii = 0; ii < MList.GetCount(); ii++ )
footprint_names_list.Add( MList.GetItem(ii).m_Module ); footprint_names_list.Add( MList.GetItem(ii).m_Module );
if( footprint_names_list.GetCount() )
{
msg.Printf( _( "Modules [%d items]" ), footprint_names_list.GetCount() ); msg.Printf( _( "Modules [%d items]" ), footprint_names_list.GetCount() );
WinEDAListBox dlg( aWindow, msg, footprint_names_list, OldName, WinEDAListBox dlg( aWindow, msg, footprint_names_list, OldName,
DisplayCmpDoc, GetComponentDialogPosition() ); DisplayCmpDoc, GetComponentDialogPosition() );
...@@ -392,6 +368,12 @@ wxString PCB_BASE_FRAME::Select_1_Module_From_List( EDA_DRAW_FRAME* aWindow, ...@@ -392,6 +368,12 @@ wxString PCB_BASE_FRAME::Select_1_Module_From_List( EDA_DRAW_FRAME* aWindow,
CmpName = dlg.GetTextSelection(); CmpName = dlg.GetTextSelection();
else else
CmpName.Empty(); CmpName.Empty();
}
else
{
DisplayError( aWindow, _("No footprint found") );
CmpName.Empty();
}
if( CmpName != wxEmptyString ) if( CmpName != wxEmptyString )
OldName = CmpName; OldName = CmpName;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment