Gerbview: Add drill file history and minor enhancements.

This commit is contained in:
jean-pierre charras 2011-03-17 20:14:45 +01:00
parent a338e0e5b3
commit 59534f519c
18 changed files with 2450 additions and 92 deletions

File diff suppressed because it is too large Load Diff

After

Width:  |  Height:  |  Size: 77 KiB

View File

@ -7,7 +7,6 @@
#include <wx/fontdlg.h>
#include <wx/clipbrd.h>
#include <wx/statline.h>
#include <wx/aboutdlg.h>
#include <wx/platinfo.h>
#include "build_version.h"
@ -196,11 +195,16 @@ void EDA_BASE_FRAME::DisplayActivity( int PerCent, const wxString& Text )
/*
* Update the list of past projects.
* Update the list of recent opened files.
*/
void EDA_BASE_FRAME::SetLastProject( const wxString& FullFileName )
void EDA_BASE_FRAME::UpdateFileHistory( const wxString& FullFileName,
wxFileHistory * aFileHistory )
{
wxGetApp().m_fileHistory.AddFileToHistory( FullFileName );
wxFileHistory * fileHistory = aFileHistory;
if( fileHistory == NULL )
fileHistory = & wxGetApp().m_fileHistory;
fileHistory->AddFileToHistory( FullFileName );
ReCreateMenuBar();
}
@ -208,25 +212,30 @@ void EDA_BASE_FRAME::SetLastProject( const wxString& FullFileName )
/*
* Fetch the file name from the file history list.
*/
wxString EDA_BASE_FRAME::GetFileFromHistory( int cmdId, const wxString& type )
wxString EDA_BASE_FRAME::GetFileFromHistory( int cmdId, const wxString& type,
wxFileHistory * aFileHistory )
{
wxString fn, msg;
size_t i;
int baseId = wxGetApp().m_fileHistory.GetBaseId();
wxFileHistory * fileHistory = aFileHistory;
if( fileHistory == NULL )
fileHistory = & wxGetApp().m_fileHistory;
int baseId = fileHistory->GetBaseId();
wxASSERT( cmdId >= baseId
&& cmdId < baseId + ( int )wxGetApp().m_fileHistory.GetCount() );
&& cmdId < baseId + ( int )fileHistory->GetCount() );
i = ( size_t )( cmdId - baseId );
if( i < wxGetApp().m_fileHistory.GetCount() )
if( i < fileHistory->GetCount() )
{
fn = wxGetApp().m_fileHistory.GetHistoryFile( i );
fn = fileHistory->GetHistoryFile( i );
if( !wxFileName::FileExists( fn ) )
{
msg = type + _( " file <" ) + fn + _( "> was not found." );
DisplayError( this, msg );
wxGetApp().m_fileHistory.RemoveFileFromHistory( i );
fileHistory->RemoveFileFromHistory( i );
fn = wxEmptyString;
ReCreateMenuBar();
}

View File

@ -300,7 +300,7 @@ void CVPCB_MAINFRAME::OnCloseWindow( wxCloseEvent& Event )
if( m_NetlistFileName.IsOk() )
{
SetLastProject( m_NetlistFileName.GetFullPath() );
UpdateFileHistory( m_NetlistFileName.GetFullPath() );
}
m_modified = false;
@ -461,7 +461,7 @@ void CVPCB_MAINFRAME::LoadNetList( wxCommandEvent& event )
if( ReadNetList() )
{
SetLastProject( m_NetlistFileName.GetFullPath() );
UpdateFileHistory( m_NetlistFileName.GetFullPath() );
SetTitle( wxGetApp().GetTitle() + wxT( " " ) + GetBuildVersion() +
wxT( " " ) + m_NetlistFileName.GetFullPath() );

View File

@ -60,7 +60,7 @@ void WinEDA_App::MacOpenFile(const wxString &fileName)
if( frame->ReadNetList() )
{
frame->SetLastProject( filename.GetFullPath() );
frame->UpdateFileHistory( filename.GetFullPath() );
frame->SetTitle( wxGetApp().GetTitle() + wxT( " " ) + GetBuildVersion() +
wxT( " " ) + filename.GetFullPath() );

View File

@ -155,7 +155,7 @@ bool SCH_EDIT_FRAME::LoadOneEEProject( const wxString& FileName, bool IsNew )
return false;
if( g_RootSheet->GetScreen()->GetFileName() != m_DefaultSchematicFileName )
SetLastProject( g_RootSheet->GetScreen()->GetFileName() );
UpdateFileHistory( g_RootSheet->GetScreen()->GetFileName() );
}
FullFileName = FileName;

View File

@ -374,7 +374,7 @@ void SCH_EDIT_FRAME::OnCloseWindow( wxCloseEvent& Event )
if( !g_RootSheet->GetScreen()->GetFileName().IsEmpty()
&& (g_RootSheet->GetScreen()->GetDrawItems() != NULL) )
SetLastProject( g_RootSheet->GetScreen()->GetFileName() );
UpdateFileHistory( g_RootSheet->GetScreen()->GetFileName() );
ClearProjectDrawList( g_RootSheet->GetScreen(), TRUE );

View File

@ -3,11 +3,11 @@
/**********************************************************/
#include "fctsys.h"
#include "appl_wxstruct.h"
#include "class_drawpanel.h"
#include "confirm.h"
#include "common.h"
#include "gestfich.h"
#include "appl_wxstruct.h"
#include "gerbview.h"
#include "kicad_device_context.h"
@ -23,19 +23,20 @@ EVT_CLOSE( GERBVIEW_FRAME::OnCloseWindow )
EVT_SIZE( GERBVIEW_FRAME::OnSize )
EVT_TOOL( wxID_FILE, GERBVIEW_FRAME::Files_io )
EVT_TOOL( ID_INC_LAYER_AND_APPEND_FILE, GERBVIEW_FRAME::Files_io )
EVT_TOOL( ID_GERBVIEW_ERASE_ALL, GERBVIEW_FRAME::Files_io )
EVT_TOOL( ID_GERBVIEW_LOAD_DRILL_FILE, GERBVIEW_FRAME::Files_io )
EVT_TOOL( ID_GERBVIEW_LOAD_DCODE_FILE, GERBVIEW_FRAME::Files_io )
EVT_TOOL( ID_NEW_BOARD, GERBVIEW_FRAME::Files_io )
// Menu Files:
EVT_MENU( wxID_FILE, GERBVIEW_FRAME::Files_io )
EVT_MENU( ID_MENU_INC_LAYER_AND_APPEND_FILE, GERBVIEW_FRAME::Files_io )
EVT_MENU( ID_NEW_BOARD, GERBVIEW_FRAME::Files_io )
EVT_MENU( ID_GEN_PLOT, GERBVIEW_FRAME::ToPlotter )
EVT_MENU( ID_GERBVIEW_EXPORT_TO_PCBNEW, GERBVIEW_FRAME::ExportDataInPcbnewFormat )
EVT_MENU_RANGE( wxID_FILE1, wxID_FILE9, GERBVIEW_FRAME::OnFileHistory )
EVT_MENU_RANGE( wxID_FILE1, wxID_FILE9, GERBVIEW_FRAME::OnGbrFileHistory )
EVT_MENU_RANGE( ID_GERBVIEW_DRILL_FILE1, ID_GERBVIEW_DRILL_FILE9,
GERBVIEW_FRAME::OnDrlFileHistory )
EVT_MENU( ID_EXIT, GERBVIEW_FRAME::Process_Special_Functions )

View File

@ -1,11 +1,36 @@
/********************************/
/* excellon_read_drill_file.cpp */
/********************************/
/*
/**
* @file excellon_read_drill_file.cpp
* Functions to read drill files (EXCELLON format) created by PcbNew
* These files use only a subset of EXCELLON commands.
* Here is a sample, in decimal format:
*/
/*
* This program source code file is part of KICAD, a free EDA CAD application.
*
* Copyright (C) 1992-2011 Jean-Pierre Charras <jean-pierre.charras@gipsa-lab.inpg.fr>
* Copyright (C) 1992-2011 Kicad Developers, see change_log.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, you may find one here:
* http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* or you may search the http://www.gnu.org website for the version 2 license,
* or you may write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
/*
* Here is a sample of drill files created by pcbnew, in decimal format:
* (Note: coordinates formats are same as Gerber, and T commands are near Gerber D commands).
* M48
* ;DRILL file {PCBnew (2011-03-14 BZR 2894)-testing} date 15/03/2011 14:23:22
@ -119,7 +144,10 @@ static EXCELLON_CMD excellon_G_CmdList[] =
* DCode can easily store T code (tool size) as round (or oval) shape
* Drill commands are similar to flashed gerber items
* Routing commands are similar to Gerber polygons
* coordinates have the same format as Gerber.
* coordinates have the same format as Gerber, can be given in:
* decimal format (i.i. floating notation format)
* integer 2.4 format in imperial units,
* integer 3.2 or 3.3 format (metric units).
*/
bool GERBVIEW_FRAME::Read_EXCELLON_File( const wxString& aFullFileName )
{
@ -213,7 +241,7 @@ bool EXCELLON_IMAGE::Read_EXCELLON_File( FILE * aFile,
case 'I':
case 'J': /* Auxiliary Move command */
m_IJPos = ReadIJCoord( text );
if( *text == '*' ) // command like X35142Y15945J504*
if( *text == '*' ) // command like X35142Y15945J504
{
Execute_Drill_Command( text);
}

View File

@ -15,19 +15,35 @@
/* Load a Gerber file selected from history list on current layer
* Previous data is deleted
*/
void GERBVIEW_FRAME::OnFileHistory( wxCommandEvent& event )
void GERBVIEW_FRAME::OnGbrFileHistory( wxCommandEvent& event )
{
wxString fn;
fn = GetFileFromHistory( event.GetId(), _( "Printed circuit board" ) );
fn = GetFileFromHistory( event.GetId(), _( "Gerber files" ) );
if( fn != wxEmptyString )
if( !fn.IsEmpty() )
{
Erase_Current_Layer( false );
LoadGerberFiles( fn );
}
}
/* Load a Drll (Excellon) file selected from history list on current layer
* Previous data is deleted
*/
void GERBVIEW_FRAME::OnDrlFileHistory( wxCommandEvent& event )
{
wxString fn;
fn = GetFileFromHistory( event.GetId(), _( "Drill files" ), &m_drillFileHistory );
if( !fn.IsEmpty() )
{
Erase_Current_Layer( false );
LoadExcellonFiles( fn );
}
}
/* File commands. */
void GERBVIEW_FRAME::Files_io( wxCommandEvent& event )
@ -41,31 +57,7 @@ void GERBVIEW_FRAME::Files_io( wxCommandEvent& event )
LoadGerberFiles( wxEmptyString );
break;
case ID_MENU_INC_LAYER_AND_APPEND_FILE:
case ID_INC_LAYER_AND_APPEND_FILE:
{
int origLayer = getNextAvailableLayer();
if( origLayer != NO_AVAILABLE_LAYERS )
{
setActiveLayer( origLayer );
Erase_Current_Layer( false );
if( !LoadGerberFiles( wxEmptyString ) )
setActiveLayer( origLayer );
}
else
{
wxString msg;
msg.Printf( _( "GerbView only supports a maximum of %d layers. You must first \
clear an existing layer to load any new layers." ), NB_LAYERS );
wxMessageBox( msg );
}
}
break;
case ID_NEW_BOARD:
case ID_GERBVIEW_ERASE_ALL:
Clear_Pcb( true );
Zoom_Automatique( false );
DrawPanel->Refresh();
@ -170,7 +162,7 @@ bool GERBVIEW_FRAME::LoadGerberFiles( const wxString& aFullFileName )
if( Read_GERBER_File( filename.GetFullPath(), filename.GetFullPath() ) )
{
SetLastProject( GetScreen()->GetFileName() );
UpdateFileHistory( GetScreen()->GetFileName() );
layer = getNextAvailableLayer( layer );
@ -254,6 +246,9 @@ bool GERBVIEW_FRAME::LoadExcellonFiles( const wxString& aFullFileName )
if( Read_EXCELLON_File( filename.GetFullPath() ) )
{
// Update the list of recentdrill files.
UpdateFileHistory( filename.GetFullPath(), &m_drillFileHistory );
layer = getNextAvailableLayer( layer );
if( layer == NO_AVAILABLE_LAYERS )

View File

@ -46,6 +46,7 @@ GERBVIEW_FRAME::GERBVIEW_FRAME( wxWindow* father,
m_SelLayerBox = NULL;
m_DCodeSelector = NULL;
m_displayMode = 0;
m_drillFileHistory.SetBaseId(ID_GERBVIEW_DRILL_FILE1);
if( DrawPanel )
DrawPanel->m_Block_Enable = true;
@ -205,6 +206,12 @@ void GERBVIEW_FRAME::LoadSettings()
long tmp;
config->Read( GerbviewShowDCodes, &tmp, 1 );
SetElementVisibility( DCODES_VISIBLE, tmp );
// because we have 2 file historues, we must read this one
// using a specific path
config->SetPath( wxT("drl_files") );
m_drillFileHistory.Load( *config );
config->SetPath( wxT("..") );
}
@ -237,6 +244,12 @@ void GERBVIEW_FRAME::SaveSettings()
config->Write( GerbviewShowPageSizeOption, pageSize_opt );
config->Write( GerbviewShowDCodes, IsElementVisible( DCODES_VISIBLE ) );
// Save the drill file history list
// because we have 2 file historues, we must save this one
// in a specific path
config->SetPath(wxT("drl_files") );
m_drillFileHistory.Save( *config );
config->SetPath( wxT("..") );
}

View File

@ -5,10 +5,8 @@
#ifndef WX_GERBER_STRUCT_H
#define WX_GERBER_STRUCT_H
#include "id.h"
#include "param_config.h"
#include "class_gerbview_layer_widget.h"
#include "class_layerchoicebox.h"
@ -29,6 +27,7 @@ class GERBVIEW_FRAME : public PCB_BASE_FRAME
protected:
GERBER_LAYER_WIDGET* m_LayersManager;
wxFileHistory m_drillFileHistory; // Auxiliary file history used to store drill files history
public:
WinEDALayerChoiceBox* m_SelLayerBox;
@ -392,7 +391,8 @@ public: GERBVIEW_FRAME( wxWindow* father, const wxString& title,
GRTraceMode trace_mode );
void Files_io( wxCommandEvent& event );
void OnFileHistory( wxCommandEvent& event );
void OnGbrFileHistory( wxCommandEvent& event );
void OnDrlFileHistory( wxCommandEvent& event );
/**
* function LoadGerberFiles

View File

@ -18,15 +18,26 @@ enum gerbview_ids
ID_GERBVIEW_SHOW_LIST_DCODES = 1,
ID_GERBVIEW_LOAD_DRILL_FILE,
ID_GERBVIEW_LOAD_DCODE_FILE,
ID_GERBVIEW_ERASE_ALL,
ID_TOOLBARH_GERBER_SELECT_ACTIVE_DCODE,
ID_MENU_INC_LAYER_AND_APPEND_FILE,
ID_INC_LAYER_AND_APPEND_FILE,
ID_GERBVIEW_SHOW_SOURCE,
ID_GERBVIEW_EXPORT_TO_PCBNEW,
ID_MENU_GERBVIEW_SHOW_HIDE_LAYERS_MANAGER_DIALOG,
ID_MENU_GERBVIEW_SELECT_PREFERED_EDITOR,
// IDs for drill file history (wxID_FILEnn is already in use)
ID_GERBVIEW_DRILL_FILE,
ID_GERBVIEW_DRILL_FILE1,
ID_GERBVIEW_DRILL_FILE2,
ID_GERBVIEW_DRILL_FILE3,
ID_GERBVIEW_DRILL_FILE4,
ID_GERBVIEW_DRILL_FILE5,
ID_GERBVIEW_DRILL_FILE6,
ID_GERBVIEW_DRILL_FILE7,
ID_GERBVIEW_DRILL_FILE8,
ID_GERBVIEW_DRILL_FILE9,
ID_TOOLBARH_GERBVIEW_SELECT_ACTIVE_LAYER,
ID_GERBVIEW_GLOBAL_DELETE,
ID_GERBVIEW_OPTIONS_SETUP,

View File

@ -6,6 +6,7 @@
#include "appl_wxstruct.h"
#include "common.h"
//#include "macros.h"
#include "gerbview.h"
#include "bitmaps.h"
@ -28,37 +29,62 @@ void GERBVIEW_FRAME::ReCreateMenuBar( void )
// Recreate all menus:
wxMenu* filesMenu = new wxMenu;
filesMenu->Append( wxID_FILE, _( "Load Gerber File" ),
_( "Load a new Gerber file on the current layer. Previous data will be deleted" ),
FALSE );
ADD_MENUITEM_WITH_HELP( filesMenu, wxID_FILE, _( "Load Gerber File" ),
_(
"Load a new Gerber file on the current layer. Previous data will be deleted" ),
open_xpm );
filesMenu->Append( ID_MENU_INC_LAYER_AND_APPEND_FILE,
_( "Inc Layer and load Gerber file" ),
_( "Increment layer number, and Load Gerber file" ),
FALSE );
ADD_MENUITEM_WITH_HELP( filesMenu, ID_GERBVIEW_LOAD_DRILL_FILE,
_( "Load EXCELLON Drill File" ),
_( "Load excellon drill file" ),
open_xpm );
filesMenu->Append( ID_GERBVIEW_LOAD_DCODE_FILE, _( "Load DCodes" ),
_( "Load D-Codes File" ), FALSE );
ADD_MENUITEM_WITH_HELP( filesMenu, ID_GERBVIEW_LOAD_DCODE_FILE,
_( "Load DCodes" ),
_( "Load D-Codes File" ),
open_xpm );
filesMenu->Append( ID_GERBVIEW_LOAD_DRILL_FILE, _( "Load EXCELLON Drill File" ),
_( "Load excellon drill file" ), FALSE );
// Open Recent submenus
wxMenu* openRecentGbrMenu = new wxMenu();
wxGetApp().m_fileHistory.AddFilesToMenu( openRecentGbrMenu );
ADD_MENUITEM_WITH_HELP_AND_SUBMENU( filesMenu, openRecentGbrMenu,
wxID_ANY, _( "Open &Recent Gerber File" ),
_( "Open a recent opened Gerber file" ),
open_project_xpm );
wxMenu* openRecentDrlMenu = new wxMenu();
m_drillFileHistory.AddFilesToMenu( openRecentDrlMenu );
ADD_MENUITEM_WITH_HELP_AND_SUBMENU( filesMenu, openRecentDrlMenu,
wxID_ANY, _( "Open &Recent Drill File" ),
_( "Open a recent opened drill file" ),
open_project_xpm );
filesMenu->Append( ID_NEW_BOARD, _( "&Clear All" ),
_( "Clear all layers. All data will be deleted" ), FALSE );
filesMenu->AppendSeparator();
filesMenu->Append( ID_GERBVIEW_EXPORT_TO_PCBNEW, _( "&Export to Pcbnew" ),
_( "Export data in pcbnew format" ), FALSE );
ADD_MENUITEM_WITH_HELP( filesMenu, ID_GERBVIEW_ERASE_ALL,
_( "&Clear All" ),
_( "Clear all layers. All data will be deleted" ),
delete_body_xpm );
filesMenu->AppendSeparator();
ADD_MENUITEM_WITH_HELP( filesMenu, ID_GERBVIEW_EXPORT_TO_PCBNEW,
_( "&Export to Pcbnew" ),
_( "Export data in pcbnew format" ),
export_xpm );
filesMenu->AppendSeparator();
filesMenu->Append( wxID_PRINT, _( "P&rint" ), _( "Print gerber" ) );
ADD_MENUITEM_WITH_HELP( filesMenu, wxID_PRINT,
_( "P&rint" ),
_( "Print gerber" ),
print_button );
filesMenu->AppendSeparator();
filesMenu->Append( ID_EXIT, _( "E&xit" ), _( "Quit Gerbview" ) );
wxGetApp().m_fileHistory.AddFilesToMenu( filesMenu );
ADD_MENUITEM_WITH_HELP( filesMenu, ID_EXIT,
_( "E&xit" ),
_( "Quit Gerbview" ),
exit_xpm );
// Configuration and preferences:
wxMenu* configmenu = new wxMenu;
@ -85,6 +111,7 @@ void GERBVIEW_FRAME::ReCreateMenuBar( void )
_( "&Show Source" ),
_( "Show source file for the current layer" ),
tools_xpm );
miscellaneous_menu->AppendSeparator();
ADD_MENUITEM_WITH_HELP( miscellaneous_menu, ID_GERBVIEW_GLOBAL_DELETE,
_( "&Clear Layer" ),

View File

@ -14,6 +14,7 @@
#include <wx/wxhtml.h>
#include <wx/laywin.h>
#include <wx/aui/aui.h>
#include <wx/docview.h>
#include "colors.h"
#include "common.h"
@ -189,8 +190,25 @@ public:
*/
virtual void SetLanguage( wxCommandEvent& event );
wxString GetFileFromHistory( int cmdId, const wxString& type );
void SetLastProject( const wxString& FullFileName );
/**
* function GetFileFromHistory
* Fetch the file name from the file history list.
* @param aFileHistory = the wxFileHistory in use. If null,
* the main application file history is used
* @return a wxString containing the selected filename
*/
wxString GetFileFromHistory( int cmdId, const wxString& type,
wxFileHistory * aFileHistory = NULL);
/**
* Function UpdateFileHistory
* Update the list of recent opened files.
* @param aFileHistory = the wxFileHistory in use. If NULL,
* the main application file history is used
*/
void UpdateFileHistory( const wxString& FullFileName,
wxFileHistory * aFileHistory = NULL );
void DisplayActivity( int PerCent, const wxString& Text );
virtual void ReCreateMenuBar();
};

View File

@ -135,7 +135,7 @@ void WinEDA_MainFrame::OnCloseWindow( wxCloseEvent& Event )
{
int px, py;
SetLastProject( m_ProjectFileName.GetFullPath() );
UpdateFileHistory( m_ProjectFileName.GetFullPath() );
if( !IsIconized() ) // save main frame position and size
{

View File

@ -78,7 +78,7 @@ void WinEDA_MainFrame::OnLoadProject( wxCommandEvent& event )
style = wxFD_OPEN | wxFD_FILE_MUST_EXIST;
}
SetLastProject( m_ProjectFileName.GetFullPath() );
UpdateFileHistory( m_ProjectFileName.GetFullPath() );
wxFileDialog dlg( this, title, wxGetCwd(), wxEmptyString,
ProjectFileWildcard, style );
@ -99,7 +99,7 @@ void WinEDA_MainFrame::OnLoadProject( wxCommandEvent& event )
CreateNewProject( m_ProjectFileName.GetFullPath() );
}
SetLastProject( m_ProjectFileName.GetFullPath() );
UpdateFileHistory( m_ProjectFileName.GetFullPath() );
}
wxLogDebug( wxT( "Loading Kicad project file: " ) +
@ -123,7 +123,7 @@ void WinEDA_MainFrame::OnLoadProject( wxCommandEvent& event )
SetTitle( wxGetApp().GetTitle() + wxT( " " ) + GetBuildVersion() +
wxT( " " ) + m_ProjectFileName.GetFullPath() );
SetLastProject( m_ProjectFileName.GetFullPath() );
UpdateFileHistory( m_ProjectFileName.GetFullPath() );
m_LeftWin->ReCreateTreePrj();
PrintMsg( _( "Working dir: " ) + m_ProjectFileName.GetPath() +

View File

@ -253,7 +253,7 @@ this file again." ) );
GetScreen()->GetFileName().Replace( WIN_STRING_DIR_SEP, UNIX_STRING_DIR_SEP );
SetTitle( GetScreen()->GetFileName() );
SetLastProject( GetScreen()->GetFileName() );
UpdateFileHistory( GetScreen()->GetFileName() );
/* Rebuild the new pad list (for drc and ratsnet control ...) */
GetBoard()->m_Status_Pcb = 0;

View File

@ -166,7 +166,7 @@ Changing extension to .brd." ), GetChars( fn.GetFullPath() ) );
wxSetWorkingDirectory( fn.GetPath() );
frame->GetScreen()->SetFileName( fn.GetFullPath( wxPATH_UNIX ) );
frame->SetTitle( frame->GetScreen()->GetFileName() );
frame->SetLastProject( frame->GetScreen()->GetFileName() );
frame->UpdateFileHistory( frame->GetScreen()->GetFileName() );
frame->OnModify(); // Ready to save the new empty board
wxString msg;