KiCad PCB EDA Suite
symbedit.cpp
Go to the documentation of this file.
1 /*
2  * This program source code file is part of KiCad, a free EDA CAD application.
3  *
4  * Copyright (C) 2004 Jean-Pierre Charras, jp.charras at wanadoo.fr
5  * Copyright (C) 2008 Wayne Stambaugh <stambaughw@gmail.com>
6  * Copyright (C) 2004-2017 KiCad Developers, see AUTHORS.txt for contributors.
7  *
8  * This program is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License
10  * as published by the Free Software Foundation; either version 2
11  * of the License, or (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, you may find one here:
20  * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
21  * or you may search the http://www.gnu.org website for the version 2 license,
22  * or you may write to the Free Software Foundation, Inc.,
23  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
24  */
25 
31 #include <fctsys.h>
32 #include <kiway.h>
33 #include <pgm_base.h>
34 #include <class_drawpanel.h>
35 #include <confirm.h>
36 #include <kicad_string.h>
37 #include <gestfich.h>
38 
39 #include <lib_edit_frame.h>
40 #include <class_libentry.h>
42 #include <sch_legacy_plugin.h>
43 #include <properties.h>
44 
45 
47 {
48  LIB_PART* part = GetCurPart();
49 
50  // Exit if no library entry is selected or a command is in progress.
51  if( !part || ( GetDrawItem() && GetDrawItem()->GetFlags() ) )
52  return;
53 
54  PROJECT& prj = Prj();
55  SEARCH_STACK* search = prj.SchSearchS();
56 
58 
59  wxString default_path = prj.GetRString( PROJECT::SCH_LIB_PATH );
60 
61  if( !default_path )
62  default_path = search->LastVisitedPath();
63 
64  wxFileDialog dlg( this, _( "Import Symbol" ), default_path,
65  wxEmptyString, SchematicSymbolFileWildcard(),
66  wxFD_OPEN | wxFD_FILE_MUST_EXIST );
67 
68  if( dlg.ShowModal() == wxID_CANCEL )
69  return;
70 
71  SetCrossHairPosition( wxPoint( 0, 0 ) );
74 
75  wxString filename = dlg.GetPath();
76 
77  prj.SetRString( PROJECT::SCH_LIB_PATH, filename );
78 
79  wxArrayString symbols;
80  SCH_PLUGIN::SCH_PLUGIN_RELEASER pi( SCH_IO_MGR::FindPlugin( SCH_IO_MGR::SCH_LEGACY ) );
81 
82  wxString msg;
83 
84  try
85  {
86  pi->EnumerateSymbolLib( symbols, filename );
87  }
88  catch( const IO_ERROR& ioe )
89  {
90  msg.Printf( _( "Cannot import symbol library \"%s\"." ), filename );
91  DisplayErrorMessage( this, msg, ioe.What() );
92  return;
93  }
94 
95  if( symbols.empty() )
96  {
97  msg.Printf( _( "Symbol library file \"%s\" is empty." ), filename );
98  DisplayError( this, msg );
99  return;
100  }
101 
102  if( symbols.GetCount() > 1 )
103  {
104  msg.Printf( _( "More than one symbol found in symbol file \"%s\"." ), filename );
105  wxMessageBox( msg, _( "Warning" ), wxOK | wxICON_EXCLAMATION, this );
106  }
107 
108  LIB_ALIAS* alias = nullptr;
109 
110  try
111  {
112  alias = pi->LoadSymbol( filename, symbols[0] );
113  }
114  catch( const IO_ERROR& )
115  {
116  return;
117  }
118 
119  wxCHECK_RET( alias && alias->GetPart(), "Invalid symbol." );
120 
121  SaveCopyInUndoList( part );
122 
123  LIB_PART* first = alias->GetPart();
124  LIB_ITEMS_CONTAINER& drawList = first->GetDrawItems();
125 
126  for( LIB_ITEM& item : drawList )
127  {
128  if( item.Type() == LIB_FIELD_T )
129  continue;
130 
131  if( item.GetUnit() )
132  item.SetUnit( m_unit );
133 
134  if( item.GetConvert() )
135  item.SetConvert( m_convert );
136 
137  item.SetFlags( IS_NEW | SELECTED );
138 
139  LIB_ITEM* newItem = (LIB_ITEM*) item.Clone();
140 
141  newItem->SetParent( part );
142  part->AddDrawItem( newItem );
143  }
144 
145  part->RemoveDuplicateDrawItems();
146  part->ClearSelectedItems();
147 
148  OnModify();
149  m_canvas->Refresh();
150 }
151 
152 
154 {
155  // Export the current part as a symbol (.sym file)
156  // this is the current part without its aliases and doc file
157  // because a .sym file is used to import graphics in a part being edited
158  LIB_PART* part = GetCurPart();
159 
160  if( !part || part->GetDrawItems().empty() )
161  return;
162 
163  PROJECT& prj = Prj();
164  SEARCH_STACK* search = prj.SchSearchS();
165 
166  wxString default_path = prj.GetRString( PROJECT::SCH_LIB_PATH );
167 
168  if( !default_path )
169  default_path = search->LastVisitedPath();
170 
171  wxFileDialog dlg( this, _( "Export Symbol" ), default_path,
172  part->GetName() + "." + SchematicSymbolFileExtension,
174  wxFD_SAVE | wxFD_OVERWRITE_PROMPT );
175 
176  if( dlg.ShowModal() == wxID_CANCEL )
177  return;
178 
179  wxFileName fn = dlg.GetPath();
180 
181  /* The GTK file chooser doesn't return the file extension added to
182  * file name so add it here. */
183  if( fn.GetExt().IsEmpty() )
184  fn.SetExt( SchematicSymbolFileExtension );
185 
186  prj.SetRString( PROJECT::SCH_LIB_PATH, fn.GetPath() );
187 
188  if( fn.FileExists() )
189  {
190  wxRemove( fn.GetFullPath() );
191  }
192 
193  wxString msg;
194  msg.Printf( _( "Saving symbol in \"%s\"" ), fn.GetPath() );
195  SetStatusText( msg );
196 
197  SCH_PLUGIN::SCH_PLUGIN_RELEASER pi( SCH_IO_MGR::FindPlugin( SCH_IO_MGR::SCH_LEGACY ) );
198 
199  try
200  {
201  PROPERTIES nodoc_props; // Doc file is useless for a .sym file
202  nodoc_props[ SCH_LEGACY_PLUGIN::PropNoDocFile ] = "";
203  pi->CreateSymbolLib( fn.GetFullPath(), &nodoc_props );
204 
205  LIB_PART* saved_part = new LIB_PART( *part );
206  saved_part->RemoveAllAliases(); // useless in a .sym file
207  pi->SaveSymbol( fn.GetFullPath(), saved_part, &nodoc_props );
208  }
209  catch( const IO_ERROR& ioe )
210  {
211  msg.Printf( _( "An error occurred attempting to save symbol file \"%s\"" ),
212  fn.GetFullPath() );
213  DisplayErrorMessage( this, msg, ioe.What() );
214  }
215 }
216 
217 
219 {
220  if( LIB_PART* part = GetCurPart() )
221  {
222  const wxPoint& cross_hair = GetCrossHairPosition();
223 
224  wxPoint offset( -cross_hair.x, cross_hair.y );
225  part->SetOffset( offset );
226  OnModify();
227 
228  // Redraw the symbol
229  RedrawScreen( wxPoint( 0, 0 ), true );
230  m_canvas->Refresh();
231  }
232 }
wxString SchematicSymbolFileWildcard()
virtual void CreateSymbolLib(const wxString &aLibraryPath, const PROPERTIES *aProperties=NULL)
Create a new empty symbol library at aLibraryPath.
Definition: sch_plugin.cpp:126
void SaveOneSymbol()
Saves the current symbol to a symbol file.
Definition: symbedit.cpp:153
Part library alias object definition.
virtual LIB_ALIAS * LoadSymbol(const wxString &aLibraryPath, const wxString &aAliasName, const PROPERTIES *aProperties=NULL)
Load a LIB_ALIAS object having aAliasName from the aLibraryPath containing a library format that this...
Definition: sch_plugin.cpp:93
Class PROJECT holds project specific data.
Definition: project.h:56
static int m_convert
void DisplayErrorMessage(wxWindow *aParent, const wxString &aText, const wxString &aExtraInfo)
Function DisplayErrorMessage displays an error message with aMessage.
Definition: confirm.cpp:199
This file is part of the common library TODO brief description.
virtual void Refresh(bool eraseBackground=true, const wxRect *rect=NULL) override
Update the board display after modifying it by a python script (note: it is automatically called by a...
Definition: draw_panel.cpp:338
This file is part of the common library.
virtual EDA_ITEM * Clone() const
Function Clone creates a duplicate of this item with linked list members set to NULL.
bool empty(int aType=UNDEFINED_TYPE)
Definition: multivector.h:224
virtual void EnumerateSymbolLib(wxArrayString &aAliasNameList, const wxString &aLibraryPath, const PROPERTIES *aProperties=NULL)
Populate a list of LIB_PART alias names contained within the library aLibraryPath.
Definition: sch_plugin.cpp:75
void OnModify()
Must be called after a schematic change in order to set the "modify" flag of the current screen...
void LoadOneSymbol()
Read a component symbol file (*.sym ) and add graphic items to the current component.
Definition: symbedit.cpp:46
Class SEARCH_STACK looks for files in a number of places.
Definition: search_stack.h:41
void ClearSelectedItems()
Clears all the draw items marked by a block select.
void MoveCursorToCrossHair()
Function MoveCursorToCrossHair warps the cursor to the current cross hair position.
Definition: draw_panel.cpp:360
Class PROPERTIES is a name/value tuple with unique names and optional values.
Definition: properties.h:34
The base class for drawable items used by schematic library components.
Definition: lib_draw_item.h:66
void AddDrawItem(LIB_ITEM *aItem)
Add a new draw aItem to the draw object list.
#define IS_NEW
New item, just created.
Definition: base_struct.h:109
PROJECT & Prj() const
Function Prj returns a reference to the PROJECT "associated with" this KIWAY.
#define SELECTED
Definition: base_struct.h:116
LIB_PART * GetCurPart() const
Return the current part being edited or NULL if none selected.
void SetParent(EDA_ITEM *aParent)
Definition: base_struct.h:224
LIB_ITEMS_CONTAINER & GetDrawItems()
Return a reference to the draw item list.
Class LIB_ITEM definition.
Define a library symbol object.
The common library.
static const char * PropNoDocFile
const char* PropBuffering
void RemoveDuplicateDrawItems()
Remove duplicate draw items from list.
VTBL_ENTRY void SetRString(RSTRING_T aStringId, const wxString &aString)
Function SetRString stores a "retained string", which is any session and project specific string iden...
Definition: project.cpp:171
LIB_PART * GetPart() const
Get the shared LIB_PART.
const wxString SchematicSymbolFileExtension
Helper object to release a SCH_PLUGIN in the context of a potential thrown exception through its dest...
Definition: sch_io_mgr.h:523
EDA_DRAW_PANEL * m_canvas
The area to draw on.
Definition: draw_frame.h:106
void RedrawScreen(const wxPoint &aCenterPoint, bool aWarpPointer)
Function RedrawScreen redraws the entire screen area by updating the scroll bars and mouse pointer in...
Definition: zoom.cpp:46
VTBL_ENTRY const wxString & GetRString(RSTRING_T aStringId)
Function GetRString returns a "retained string", which is any session and project specific string ide...
Definition: project.cpp:186
virtual const wxString What() const
A composite of Problem() and Where()
Definition: exceptions.cpp:33
see class PGM_BASE
void RemoveAllAliases()
static int m_unit
const wxString LastVisitedPath(const wxString &aSubPathToSearch=wxEmptyString)
Function LastVisitedPath is a quirky function inherited from old code that seems to serve particular ...
void SaveCopyInUndoList(EDA_ITEM *ItemToCopy, UNDO_REDO_T undoType=UR_LIBEDIT)
Create a copy of the current component, and save it in the undo list.
LIB_ITEM * GetDrawItem() const
void SetIgnoreMouseEvents(bool aIgnore)
const wxString & GetName() const
Definition of class LIB_EDIT_FRAME.
virtual void SaveSymbol(const wxString &aLibraryPath, const LIB_PART *aSymbol, const PROPERTIES *aProperties=NULL)
Write aSymbol to an existing library located at aLibraryPath.
Definition: sch_plugin.cpp:102
void PlaceAnchor()
Places an anchor reference coordinate for the current component.
Definition: symbedit.cpp:218
void SetCrossHairPosition(const wxPoint &aPosition, bool aSnapToGrid=true)
Function SetCrossHairPosition sets the screen cross hair position to aPosition in logical (drawing) u...
void DisplayError(wxWindow *parent, const wxString &text, int displaytime)
Function DisplayError displays an error or warning message box with aMessage.
Definition: confirm.cpp:185
wxPoint GetCrossHairPosition(bool aInvertY=false) const
Function GetCrossHairPosition return the current cross hair position in logical (drawing) coordinates...
Struct IO_ERROR is a class used to hold an error message and may be used when throwing exceptions con...
Definition: ki_exception.h:76