KiCad PCB EDA Suite
dialog_plot_schematic.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) 1992-2018 Jean-Pierre Charras jp.charras at wanadoo.fr
5  * Copyright (C) 1992-2010 Lorenzo Marcantonio
6  * Copyright (C) 2011 Wayne Stambaugh <stambaughw@gmail.com>
7  * Copyright (C) 1992-2020 KiCad Developers, see AUTHORS.txt for contributors.
8  *
9  * This program is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU General Public License
11  * as published by the Free Software Foundation; either version 2
12  * of the License, or (at your option) any later version.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, you may find one here:
21  * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
22  * or you may search the http://www.gnu.org website for the version 2 license,
23  * or you may write to the Free Software Foundation, Inc.,
24  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
25  */
26 
27 #include <bitmaps.h>
28 #include <dialog_plot_schematic.h>
29 #include <eeschema_settings.h>
30 #include <kiface_i.h>
31 #include <pgm_base.h>
33 #include <ws_painter.h>
34 #include <sch_painter.h>
35 #include <schematic.h>
36 
37 // static members (static to remember last state):
40 
41 
43  : DIALOG_PLOT_SCHEMATIC_BASE( parent ),
44  m_parent( parent ),
45  m_plotFormat( PLOT_FORMAT::UNDEFINED ),
46  m_HPGLPenSize( 1.0 ),
47  m_defaultLineWidth( parent, m_lineWidthLabel, m_lineWidthCtrl, m_lineWidthUnits, true ),
48  m_penWidth( parent, m_penWidthLabel, m_penWidthCtrl, m_penWidthUnits, true )
49 {
50  m_configChanged = false;
51 
52  m_browseButton->SetBitmap( KiBitmap( folder_xpm ) );
53 
54  // We use a sdbSizer to get platform-dependent ordering of the action buttons, but
55  // that requires us to correct the button labels here.
56  m_sdbSizer1OK->SetLabel( _( "Plot All Pages" ) );
57  m_sdbSizer1Apply->SetLabel( _( "Plot Current Page" ) );
58  m_sdbSizer1Cancel->SetLabel( _( "Close" ) );
59  m_sdbSizer1->Layout();
60 
61  m_sdbSizer1OK->SetDefault();
62  initDlg();
63 
64  // Now all widgets have the size fixed, call FinishDialogSettings
66 }
67 
68 
69 // Initialize the dialog options:
71 {
72  auto cfg = dynamic_cast<EESCHEMA_SETTINGS*>( Kiface().KifaceSettings() );
73  wxASSERT( cfg );
74 
75  if( cfg )
76  {
77  for( COLOR_SETTINGS* settings : Pgm().GetSettingsManager().GetColorSettingsList() )
78  {
79  int idx = m_colorTheme->Append( settings->GetName(), static_cast<void*>( settings ) );
80 
81  if( settings->GetFilename() == cfg->m_PlotPanel.color_theme )
82  m_colorTheme->SetSelection( idx );
83  }
84 
85  m_colorTheme->Enable( cfg->m_PlotPanel.color );
86 
87  m_plotBackgroundColor->Enable( cfg->m_PlotPanel.color );
88  m_plotBackgroundColor->SetValue( cfg->m_PlotPanel.background_color );
89 
90  // Set color or B&W plot option
91  setModeColor( cfg->m_PlotPanel.color );
92 
93  // Set plot or not frame reference option
94  setPlotFrameRef( cfg->m_PlotPanel.frame_reference );
95 
96  // Set HPGL plot origin to center of paper of left bottom corner
97  SetPlotOriginCenter( cfg->m_PlotPanel.hpgl_origin );
98 
99  m_HPGLPaperSizeSelect = cfg->m_PlotPanel.hpgl_paper_size;
100 
101  // HPGL Pen Size is stored in mm in config
102  m_HPGLPenSize = cfg->m_PlotPanel.hpgl_pen_size * IU_PER_MM;
103 
104  // Switch to the last save plot format
105  PLOT_FORMAT fmt = static_cast<PLOT_FORMAT>( cfg->m_PlotPanel.format );
106 
107  switch( fmt )
108  {
109  default:
110  case PLOT_FORMAT::POST: m_plotFormatOpt->SetSelection( 0 ); break;
111  case PLOT_FORMAT::PDF: m_plotFormatOpt->SetSelection( 1 ); break;
112  case PLOT_FORMAT::SVG: m_plotFormatOpt->SetSelection( 2 ); break;
113  case PLOT_FORMAT::DXF: m_plotFormatOpt->SetSelection( 3 ); break;
114  case PLOT_FORMAT::HPGL: m_plotFormatOpt->SetSelection( 4 ); break;
115  }
116 
117  if( fmt == PLOT_FORMAT::DXF || fmt == PLOT_FORMAT::HPGL )
118  m_plotBackgroundColor->Disable();
119 
120  // Set the default line width (pen width which should be used for
121  // items that do not have a pen size defined (like frame ref)
122  // the default line width is stored in mils in config
123  m_defaultLineWidth.SetValue( Mils2iu( cfg->m_Drawing.default_line_thickness ) );
124  }
125 
126  // Initialize HPGL specific widgets
128 
129  // Plot directory
131  wxString path = settings.m_PlotDirectoryName;
132 #ifdef __WINDOWS__
133  path.Replace( '/', '\\' );
134 #endif
135  m_outputDirectoryName->SetValue( path );
136 }
137 
138 
144 {
145  // Build the absolute path of current output directory to preselect it in the file browser.
146  wxString path = ExpandEnvVarSubstitutions( m_outputDirectoryName->GetValue(), &Prj() );
147  path = Prj().AbsolutePath( path );
148 
149  wxDirDialog dirDialog( this, _( "Select Output Directory" ), path );
150 
151  if( dirDialog.ShowModal() == wxID_CANCEL )
152  return;
153 
154  wxFileName dirName = wxFileName::DirName( dirDialog.GetPath() );
155 
156  wxFileName fn( Prj().AbsolutePath( m_parent->Schematic().Root().GetFileName() ) );
157  wxString defaultPath = fn.GetPathWithSep();
158  wxString msg;
159  msg.Printf( _( "Do you want to use a path relative to\n\"%s\"" ), GetChars( defaultPath ) );
160 
161  wxMessageDialog dialog( this, msg, _( "Plot Output Directory" ),
162  wxYES_NO | wxICON_QUESTION | wxYES_DEFAULT );
163 
164  // relative directory selected
165  if( dialog.ShowModal() == wxID_YES )
166  {
167  if( !dirName.MakeRelativeTo( defaultPath ) )
168  wxMessageBox( _( "Cannot make path relative (target volume different from file "
169  "volume)!" ), _( "Plot Output Directory" ), wxOK | wxICON_ERROR );
170  }
171 
172  m_outputDirectoryName->SetValue( dirName.GetFullPath() );
173 }
174 
175 
177 {
178  switch( m_plotFormatOpt->GetSelection() )
179  {
180  default:
181  case 0:
182  return PLOT_FORMAT::POST;
183  case 1:
184  return PLOT_FORMAT::PDF;
185  case 2:
186  return PLOT_FORMAT::SVG;
187  case 3:
188  return PLOT_FORMAT::DXF;
189  case 4:
190  return PLOT_FORMAT::HPGL;
191  }
192 }
193 
194 
195 void DIALOG_PLOT_SCHEMATIC::OnPageSizeSelected( wxCommandEvent& event )
196 {
198  m_HPGLPaperSizeSelect = m_paperSizeOption->GetSelection();
199  else
200  m_pageSizeSelect = m_paperSizeOption->GetSelection();
201 }
202 
203 
204 void DIALOG_PLOT_SCHEMATIC::OnUpdateUI( wxUpdateUIEvent& event )
205 {
207 
208  if( fmt != m_plotFormat )
209  {
210  m_plotFormat = fmt;
211 
212  wxArrayString paperSizes;
213  paperSizes.push_back( _( "Schematic size" ) );
214 
215  int selection;
216 
217  if( fmt == PLOT_FORMAT::HPGL )
218  {
219  paperSizes.push_back( _( "A4" ) );
220  paperSizes.push_back( _( "A3" ) );
221  paperSizes.push_back( _( "A2" ) );
222  paperSizes.push_back( _( "A1" ) );
223  paperSizes.push_back( _( "A0" ) );
224  paperSizes.push_back( _( "A" ) );
225  paperSizes.push_back( _( "B" ) );
226  paperSizes.push_back( _( "C" ) );
227  paperSizes.push_back( _( "D" ) );
228  paperSizes.push_back( _( "E" ) );
229 
230  selection = m_HPGLPaperSizeSelect;
231  }
232  else
233  {
234  paperSizes.push_back( _( "A4" ) );
235  paperSizes.push_back( _( "A" ) );
236 
237  selection = m_pageSizeSelect;
238  }
239 
240  m_paperSizeOption->Set( paperSizes );
241  m_paperSizeOption->SetSelection( selection );
242 
244  fmt == PLOT_FORMAT::POST || fmt == PLOT_FORMAT::PDF || fmt == PLOT_FORMAT::SVG );
245 
246  m_plotOriginTitle->Enable( fmt == PLOT_FORMAT::HPGL );
247  m_plotOriginOpt->Enable( fmt == PLOT_FORMAT::HPGL );
249 
250  m_plotBackgroundColor->Enable(
251  fmt == PLOT_FORMAT::POST || fmt == PLOT_FORMAT::PDF || fmt == PLOT_FORMAT::SVG );
252 
253  m_colorTheme->Enable( fmt != PLOT_FORMAT::HPGL );
254  m_ModeColorOption->Enable( fmt != PLOT_FORMAT::HPGL );
255  }
256 }
257 
258 
260 {
262 
263  EESCHEMA_SETTINGS* cfg = dynamic_cast<EESCHEMA_SETTINGS*>( Kiface().KifaceSettings() );
264  wxASSERT( cfg );
265 
267 
268  if( cfg )
269  {
271  cfg->m_PlotPanel.color = getModeColor();
272  cfg->m_PlotPanel.color_theme = colors->GetFilename();
274  cfg->m_PlotPanel.format = static_cast<int>( GetPlotFileFormat() );
277 
278  // HPGL Pen Size is stored in mm in config
279  cfg->m_PlotPanel.hpgl_pen_size = m_HPGLPenSize / IU_PER_MM;
280  }
281 
282  aSettings->LoadColors( colors );
283  aSettings->SetDefaultPenWidth( (int) m_defaultLineWidth.GetValue() );
284 
285  if( m_plotBackgroundColor->GetValue() )
286  aSettings->SetBackgroundColor( colors->GetColor( LAYER_SCHEMATIC_BACKGROUND ) );
287  else
288  aSettings->SetBackgroundColor( COLOR4D::UNSPECIFIED );
289 
290  // Plot directory
291  wxString path = m_outputDirectoryName->GetValue();
292  path.Replace( '\\', '/' );
293 
295 
296  if( settings.m_PlotDirectoryName != path )
297  m_configChanged = true;
298 
299  settings.m_PlotDirectoryName = path;
300 }
301 
302 
304 {
305  int selection = m_colorTheme->GetSelection();
306  return static_cast<COLOR_SETTINGS*>( m_colorTheme->GetClientData( selection ) );
307 }
308 
309 
310 void DIALOG_PLOT_SCHEMATIC::OnPlotCurrent( wxCommandEvent& event )
311 {
312  PlotSchematic( false );
313 }
314 
315 
316 void DIALOG_PLOT_SCHEMATIC::OnPlotAll( wxCommandEvent& event )
317 {
318  PlotSchematic( true );
319 }
320 
321 
323 {
325 
326  getPlotOptions( &renderSettings );
327 
328  switch( GetPlotFileFormat() )
329  {
330  default:
331  case PLOT_FORMAT::POST:
332  createPSFile( aPlotAll, getPlotFrameRef(), &renderSettings );
333  break;
334  case PLOT_FORMAT::DXF:
335  CreateDXFFile( aPlotAll, getPlotFrameRef(), &renderSettings );
336  break;
337  case PLOT_FORMAT::PDF:
338  createPDFFile( aPlotAll, getPlotFrameRef(), &renderSettings );
339  break;
340  case PLOT_FORMAT::SVG:
341  createSVGFile( aPlotAll, getPlotFrameRef(), &renderSettings );
342  break;
343  case PLOT_FORMAT::HPGL:
344  createHPGLFile( aPlotAll, getPlotFrameRef(), &renderSettings );
345  break;
346  }
347 }
348 
349 
350 wxFileName DIALOG_PLOT_SCHEMATIC::createPlotFileName( wxString& aPlotFileName,
351  wxString& aExtension,
352  REPORTER* aReporter )
353 {
354  wxString path = ExpandEnvVarSubstitutions( m_outputDirectoryName->GetValue(), &Prj() );
355  wxFileName outputDir = wxFileName::DirName( path );
356 
357  wxString plotFileName = Prj().AbsolutePath( aPlotFileName + wxT( "." ) + aExtension);
358 
359  if( !EnsureFileDirectoryExists( &outputDir, plotFileName, aReporter ) )
360  {
361  wxString msg = wxString::Format( _( "Could not write plot files to folder \"%s\"." ),
362  outputDir.GetPath() );
363  aReporter->Report( msg, RPT_SEVERITY_ERROR );
364  }
365 
366  wxFileName fn( plotFileName );
367  fn.SetPath( outputDir.GetFullPath() );
368  return fn;
369 }
void PlotSchematic(bool aPlotAll)
const BITMAP_OPAQUE folder_xpm[1]
Definition: folder.cpp:20
KIWAY Kiway & Pgm(), KFCTL_STANDALONE
The global Program "get" accessor.
Definition: single_top.cpp:104
void OnOutputDirectoryBrowseClicked(wxCommandEvent &event) override
Set the m_outputDirectoryName variable to the selected directory from directory dialog.
RENDER_SETTINGS Contains all the knowledge about how graphical objects are drawn on any output surfac...
void OnUpdateUI(wxUpdateUIEvent &event) override
wxStdDialogButtonSizer * m_sdbSizer1
void SetPlotOriginCenter(bool aCenter)
SCHEMATIC_SETTINGS & Settings() const
Definition: schematic.cpp:138
DIALOG_PLOT_SCHEMATIC(SCH_EDIT_FRAME *parent)
void FinishDialogSettings()
In all dialogs, we must call the same functions to fix minimal dlg size, the default position and per...
COLOR_SETTINGS * getColorSettings()
void OnPlotCurrent(wxCommandEvent &event) override
KIGFX::SCH_RENDER_SETTINGS * GetRenderSettings()
Class DIALOG_PLOT_SCHEMATIC_BASE.
Schematic editor (Eeschema) main window.
void CreateDXFFile(bool aPlotAll, bool aPlotFrameRef, RENDER_SETTINGS *aRenderSettings)
const wxString ExpandEnvVarSubstitutions(const wxString &aString, PROJECT *aProject)
Replace any environment variable & text variable references with their values.
Definition: common.cpp:574
void getPlotOptions(RENDER_SETTINGS *aSettings)
REPORTER is a pure virtual class used to derive REPORTER objects from.
Definition: reporter.h:64
void createSVGFile(bool aPlotAll, bool aPlotFrameRef, RENDER_SETTINGS *aSettings)
void OnPageSizeSelected(wxCommandEvent &event) override
virtual REPORTER & Report(const wxString &aText, SEVERITY aSeverity=RPT_SEVERITY_UNDEFINED)=0
Function Report is a pure virtual function to override in the derived object.
VTBL_ENTRY const wxString AbsolutePath(const wxString &aFileName) const
Function AbsolutePath fixes up aFileName if it is relative to the project's directory to be an absolu...
Definition: project.cpp:270
wxBitmap KiBitmap(BITMAP_DEF aBitmap)
Construct a wxBitmap from a memory record, held in a BITMAP_DEF.
Definition: bitmap.cpp:80
void OnPlotAll(wxCommandEvent &event) override
void setPlotFrameRef(bool aPlot)
PLOT_FORMAT
Enum PlotFormat is the set of supported output plot formats.
Definition: plotter.h:51
PROJECT & Prj() const
Function Prj returns a reference to the PROJECT "associated with" this KIWAY.
bool EnsureFileDirectoryExists(wxFileName *aTargetFullFileName, const wxString &aBaseFilename, REPORTER *aReporter)
Make aTargetFullFileName absolute and create the path of this file if it doesn't yet exist.
Definition: common.cpp:602
KIFACE_I & Kiface()
Global KIFACE_I "get" accessor.
SCHEMATIC & Schematic() const
void createPSFile(bool aPlotAll, bool aPlotFrameRef, RENDER_SETTINGS *aSettings)
wxString GetFileName() const
Return the filename corresponding to this sheet.
Definition: sch_sheet.h:496
SETTINGS_MANAGER * GetSettingsManager()
virtual void SetBackgroundColor(const COLOR4D &aColor)=0
Sets the background color.
SCH_SHEET & Root() const
Definition: schematic.h:97
static const wxChar * GetChars(const wxString &s)
Function GetChars returns a wxChar* to the actual wxChar* data within a wxString, and is helpful for ...
Definition: macros.h:153
see class PGM_BASE
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, CPTREE &aTree)
Function Format outputs a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
Definition: ptree.cpp:205
#define _(s)
Definition: 3d_actions.cpp:33
virtual void SetValue(int aValue)
Function SetValue Sets new value (in Internal Units) for the text field, taking care of units convers...
void createPDFFile(bool aPlotAll, bool aPlotFrameRef, RENDER_SETTINGS *aRenderSettings)
These settings were stored in SCH_BASE_FRAME previously.
virtual long long int GetValue()
Function GetValue Returns the current value in Internal Units.
SCH_RENDER_SETTINGS Stores schematic-specific render settings.
Definition: sch_painter.h:70
Color settings are a bit different than most of the settings objects in that there can be more than o...
void createHPGLFile(bool aPlotAll, bool aPlotFrameRef, RENDER_SETTINGS *aRenderSettings)
void SetDefaultPenWidth(int aWidth)
virtual void LoadColors(const COLOR_SETTINGS *aSettings)
wxFileName createPlotFileName(wxString &aPlotFileName, wxString &aExtension, REPORTER *aReporter=NULL)
Create a file name with an absolute path name.
static VRML_COLOR colors[VRML_COLOR_LAST]
void Enable(bool aEnable)
Function Enable Enables/diasables the label, widget and units label.
void setModeColor(bool aColor)