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-2021 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 <common.h> // For ExpandEnvVarSubstitutions
30 #include <dialog_plot_schematic.h>
31 #include <eeschema_settings.h>
32 #include <kiface_base.h>
33 #include <locale_io.h>
34 #include <plotters/plotter_hpgl.h>
35 #include <plotters/plotter_dxf.h>
37 #include <reporter.h>
38 #include <trace_helpers.h>
41 
42 #include <sch_edit_frame.h>
43 #include <sch_painter.h>
44 #include <schematic.h>
45 #include <sch_screen.h>
46 
47 #include <wx/dirdlg.h>
48 #include <wx/msgdlg.h>
49 #include <wx/stdpaths.h>
50 #include <wx/log.h>
51 
52 
53 // static members (static to remember last state):
56 
57 
71 };
72 
73 
74 static const wxChar* plot_sheet_list( int aSize )
75 {
76  switch( aSize )
77  {
78  default:
79  case PAGE_DEFAULT: return nullptr;
80  case HPGL_PAGE_SIZE_A5: return wxT( "A5" );
81  case HPGL_PAGE_SIZE_A4: return wxT( "A4" );
82  case HPGL_PAGE_SIZE_A3: return wxT( "A3" );
83  case HPGL_PAGE_SIZE_A2: return wxT( "A2" );
84  case HPGL_PAGE_SIZE_A1: return wxT( "A1" );
85  case HPGL_PAGE_SIZE_A0: return wxT( "A0" );
86  case HPGL_PAGE_SIZE_A: return wxT( "A" );
87  case HPGL_PAGE_SIZE_B: return wxT( "B" );
88  case HPGL_PAGE_SIZE_C: return wxT( "C" );
89  case HPGL_PAGE_SIZE_D: return wxT( "D" );
90  case HPGL_PAGE_SIZE_E: return wxT( "E" );
91  }
92 }
93 
94 
96  : DIALOG_PLOT_SCHEMATIC_BASE( parent ),
97  m_parent( parent ),
98  m_plotFormat( PLOT_FORMAT::UNDEFINED ),
99  m_HPGLPenSize( 1.0 ),
100  m_defaultLineWidth( parent, m_lineWidthLabel, m_lineWidthCtrl, m_lineWidthUnits ),
101  m_penWidth( parent, m_penWidthLabel, m_penWidthCtrl, m_penWidthUnits )
102 {
103  m_configChanged = false;
104 
106 
107  m_MessagesBox->SetFileName( Prj().GetProjectPath() + wxT( "report.txt" ) );
108 
109  // We use a sdbSizer to get platform-dependent ordering of the action buttons, but
110  // that requires us to correct the button labels here.
111  m_sdbSizer1OK->SetLabel( _( "Plot All Pages" ) );
112  m_sdbSizer1Apply->SetLabel( _( "Plot Current Page" ) );
113  m_sdbSizer1Cancel->SetLabel( _( "Close" ) );
114  m_sdbSizer1->Layout();
115 
116  m_sdbSizer1OK->SetDefault();
117  initDlg();
118 
119  // Now all widgets have the size fixed, call FinishDialogSettings
121 }
122 
123 
125 {
126  auto cfg = dynamic_cast<EESCHEMA_SETTINGS*>( Kiface().KifaceSettings() );
127  wxASSERT( cfg );
128 
129  if( cfg )
130  {
132  {
133  int idx = m_colorTheme->Append( settings->GetName(), static_cast<void*>( settings ) );
134 
135  if( settings->GetFilename() == cfg->m_PlotPanel.color_theme )
136  m_colorTheme->SetSelection( idx );
137  }
138 
139  m_colorTheme->Enable( cfg->m_PlotPanel.color );
140 
141  m_plotBackgroundColor->Enable( cfg->m_PlotPanel.color );
142  m_plotBackgroundColor->SetValue( cfg->m_PlotPanel.background_color );
143 
144  // Set color or B&W plot option
145  setModeColor( cfg->m_PlotPanel.color );
146 
147  // Set plot or not frame reference option
148  setPlotDrawingSheet( cfg->m_PlotPanel.frame_reference );
149 
150  // HPGL plot origin and unit system configuration
151  m_plotOriginOpt->SetSelection( cfg->m_PlotPanel.hpgl_origin );
152 
153  m_HPGLPaperSizeSelect = cfg->m_PlotPanel.hpgl_paper_size;
154 
155  // HPGL Pen Size is stored in mm in config
156  m_HPGLPenSize = cfg->m_PlotPanel.hpgl_pen_size * IU_PER_MM;
157 
158  // Switch to the last save plot format
159  PLOT_FORMAT fmt = static_cast<PLOT_FORMAT>( cfg->m_PlotPanel.format );
160 
161  switch( fmt )
162  {
163  default:
164  case PLOT_FORMAT::POST: m_plotFormatOpt->SetSelection( 0 ); break;
165  case PLOT_FORMAT::PDF: m_plotFormatOpt->SetSelection( 1 ); break;
166  case PLOT_FORMAT::SVG: m_plotFormatOpt->SetSelection( 2 ); break;
167  case PLOT_FORMAT::DXF: m_plotFormatOpt->SetSelection( 3 ); break;
168  case PLOT_FORMAT::HPGL: m_plotFormatOpt->SetSelection( 4 ); break;
169  }
170 
171  if( fmt == PLOT_FORMAT::DXF || fmt == PLOT_FORMAT::HPGL )
172  m_plotBackgroundColor->Disable();
173 
174  // Set the default line width (pen width which should be used for
175  // items that do not have a pen size defined (like frame ref)
176  // the default line width is stored in mils in config
177  m_defaultLineWidth.SetValue( Mils2iu( cfg->m_Drawing.default_line_thickness ) );
178  }
179 
180  // Initialize HPGL specific widgets
182 
183  // Plot directory
185  wxString path = settings.m_PlotDirectoryName;
186 #ifdef __WINDOWS__
187  path.Replace( '/', '\\' );
188 #endif
189  m_outputDirectoryName->SetValue( path );
190 }
191 
192 
198 {
199  // Build the absolute path of current output directory to preselect it in the file browser.
200  wxString path = ExpandEnvVarSubstitutions( m_outputDirectoryName->GetValue(), &Prj() );
201 
202  // When editing a schematic that is not part of a project in the stand alone mode, the
203  // project path is not defined so point to the users document path to save the plot files.
204  if( Prj().IsNullProject() )
205  {
206  path = wxStandardPaths::Get().GetDocumentsDir();
207  }
208  else
209  {
210  // Build the absolute path of current output directory to preselect it in the file browser.
212  path = Prj().AbsolutePath( path );
213  }
214 
215  wxDirDialog dirDialog( this, _( "Select Output Directory" ), path );
216 
217  if( dirDialog.ShowModal() == wxID_CANCEL )
218  return;
219 
220  wxFileName dirName = wxFileName::DirName( dirDialog.GetPath() );
221 
222  wxFileName fn( Prj().AbsolutePath( m_parent->Schematic().Root().GetFileName() ) );
223  wxString defaultPath = fn.GetPathWithSep();
224  wxString msg;
225  wxFileName relPathTest; // Used to test if we can make the path relative
226 
227  relPathTest.Assign( dirDialog.GetPath() );
228 
229  // Test if making the path relative is possible before asking the user if they want to do it
230  if( relPathTest.MakeRelativeTo( defaultPath ) )
231  {
232  msg.Printf( _( "Do you want to use a path relative to\n'%s'?" ), defaultPath );
233 
234  wxMessageDialog dialog( this, msg, _( "Plot Output Directory" ),
235  wxYES_NO | wxICON_QUESTION | wxYES_DEFAULT );
236 
237  if( dialog.ShowModal() == wxID_YES )
238  dirName.MakeRelativeTo( defaultPath );
239  }
240 
241  m_outputDirectoryName->SetValue( dirName.GetFullPath() );
242 }
243 
244 
246 {
247  switch( m_plotFormatOpt->GetSelection() )
248  {
249  default:
250  case 0: return PLOT_FORMAT::POST;
251  case 1: return PLOT_FORMAT::PDF;
252  case 2: return PLOT_FORMAT::SVG;
253  case 3: return PLOT_FORMAT::DXF;
254  case 4: return PLOT_FORMAT::HPGL;
255  }
256 }
257 
258 
259 void DIALOG_PLOT_SCHEMATIC::OnPageSizeSelected( wxCommandEvent& event )
260 {
262  m_HPGLPaperSizeSelect = m_paperSizeOption->GetSelection();
263  else
264  m_pageSizeSelect = m_paperSizeOption->GetSelection();
265 }
266 
267 
268 void DIALOG_PLOT_SCHEMATIC::OnUpdateUI( wxUpdateUIEvent& event )
269 {
271 
272  if( fmt != m_plotFormat )
273  {
274  m_plotFormat = fmt;
275 
276  wxArrayString paperSizes;
277  paperSizes.push_back( _( "Schematic size" ) );
278 
279  int selection;
280 
281  if( fmt == PLOT_FORMAT::HPGL )
282  {
283  paperSizes.push_back( _( "A5" ) );
284  paperSizes.push_back( _( "A4" ) );
285  paperSizes.push_back( _( "A3" ) );
286  paperSizes.push_back( _( "A2" ) );
287  paperSizes.push_back( _( "A1" ) );
288  paperSizes.push_back( _( "A0" ) );
289  paperSizes.push_back( _( "A" ) );
290  paperSizes.push_back( _( "B" ) );
291  paperSizes.push_back( _( "C" ) );
292  paperSizes.push_back( _( "D" ) );
293  paperSizes.push_back( _( "E" ) );
294 
295  selection = m_HPGLPaperSizeSelect;
296  }
297  else
298  {
299  paperSizes.push_back( _( "A4" ) );
300  paperSizes.push_back( _( "A" ) );
301 
302  selection = m_pageSizeSelect;
303  }
304 
305  m_paperSizeOption->Set( paperSizes );
306  m_paperSizeOption->SetSelection( selection );
307 
309  fmt == PLOT_FORMAT::POST || fmt == PLOT_FORMAT::PDF || fmt == PLOT_FORMAT::SVG );
310 
311  m_plotOriginTitle->Enable( fmt == PLOT_FORMAT::HPGL );
312  m_plotOriginOpt->Enable( fmt == PLOT_FORMAT::HPGL );
314 
315  m_plotBackgroundColor->Enable(
316  fmt == PLOT_FORMAT::POST || fmt == PLOT_FORMAT::PDF || fmt == PLOT_FORMAT::SVG );
317 
318  m_colorTheme->Enable( fmt != PLOT_FORMAT::HPGL );
319  m_ModeColorOption->Enable( fmt != PLOT_FORMAT::HPGL );
320  }
321 }
322 
323 
325 {
327 
328  EESCHEMA_SETTINGS* cfg = dynamic_cast<EESCHEMA_SETTINGS*>( Kiface().KifaceSettings() );
329  wxASSERT( cfg );
330 
331  COLOR_SETTINGS* colors = getColorSettings();
332 
333  if( cfg )
334  {
336  cfg->m_PlotPanel.color = getModeColor();
337  cfg->m_PlotPanel.color_theme = colors->GetFilename();
339  cfg->m_PlotPanel.format = static_cast<int>( GetPlotFileFormat() );
340  cfg->m_PlotPanel.hpgl_origin = m_plotOriginOpt->GetSelection();
342 
343  // HPGL Pen Size is stored in mm in config
345  }
346 
347  aSettings->LoadColors( colors );
348  aSettings->SetDefaultPenWidth( (int) m_defaultLineWidth.GetValue() );
349 
350  if( m_plotBackgroundColor->GetValue() )
351  aSettings->SetBackgroundColor( colors->GetColor( LAYER_SCHEMATIC_BACKGROUND ) );
352  else
353  aSettings->SetBackgroundColor( COLOR4D::UNSPECIFIED );
354 
355  // Plot directory
356  wxString path = m_outputDirectoryName->GetValue();
357  path.Replace( '\\', '/' );
358 
360 
361  if( settings.m_PlotDirectoryName != path )
362  m_configChanged = true;
363 
364  settings.m_PlotDirectoryName = path;
365 }
366 
367 
369 {
370  int selection = m_colorTheme->GetSelection();
371 
372  if( selection < 0 )
373  return m_parent->GetSettingsManager()->GetColorSettings( "_builtin_default" );
374 
375  return static_cast<COLOR_SETTINGS*>( m_colorTheme->GetClientData( selection ) );
376 }
377 
378 
379 void DIALOG_PLOT_SCHEMATIC::OnPlotCurrent( wxCommandEvent& event )
380 {
381  plotSchematic( false );
382 }
383 
384 
385 void DIALOG_PLOT_SCHEMATIC::OnPlotAll( wxCommandEvent& event )
386 {
387  plotSchematic( true );
388 }
389 
390 
392 {
394 
395  getPlotOptions( &renderSettings );
396 
397  switch( GetPlotFileFormat() )
398  {
399  default:
400  case PLOT_FORMAT::POST:
401  createPSFiles( aPlotAll, getPlotDrawingSheet(), &renderSettings );
402  break;
403  case PLOT_FORMAT::DXF:
404  createDXFFiles( aPlotAll, getPlotDrawingSheet(), &renderSettings );
405  break;
406  case PLOT_FORMAT::PDF:
407  createPDFFile( aPlotAll, getPlotDrawingSheet(), &renderSettings );
408  break;
409  case PLOT_FORMAT::SVG:
410  createSVGFiles( aPlotAll, getPlotDrawingSheet(), &renderSettings );
411  break;
412  case PLOT_FORMAT::HPGL:
413  createHPGLFiles( aPlotAll, getPlotDrawingSheet(), &renderSettings );
414  break;
415  }
416 }
417 
418 
419 wxFileName DIALOG_PLOT_SCHEMATIC::createPlotFileName( const wxString& aPlotFileName,
420  const wxString& aExtension,
421  REPORTER* aReporter )
422 {
423  wxFileName retv;
424  wxFileName tmp;
425 
426  tmp.SetPath( getOutputPath() );
427  retv.SetPath( tmp.GetPath() );
428 
429  if( !aPlotFileName.IsEmpty() )
430  retv.SetName( aPlotFileName );
431  else
432  retv.SetName( _( "Schematic" ) );
433 
434  retv.SetExt( aExtension );
435 
436  if( !EnsureFileDirectoryExists( &tmp, retv.GetFullName(), aReporter ) || !tmp.IsDirWritable() )
437  {
438  wxString msg = wxString::Format( _( "Failed to write plot files to folder '%s'." ),
439  tmp.GetPath() );
440  aReporter->Report( msg, RPT_SEVERITY_ERROR );
441  retv.Clear();
442 
444  settings.m_PlotDirectoryName.Clear();
445 
446  m_configChanged = true;
447  }
448  else
449  {
450  retv.SetPath( tmp.GetPath() );
451  }
452 
453  wxLogTrace( tracePathsAndFiles, "Writing plot file '%s'.", retv.GetFullPath() );
454 
455  return retv;
456 }
457 
458 
459 void DIALOG_PLOT_SCHEMATIC::createDXFFiles( bool aPlotAll, bool aPlotDrawingSheet,
460  RENDER_SETTINGS* aRenderSettings )
461 {
462  SCH_EDIT_FRAME* schframe = m_parent;
463  SCH_SHEET_PATH oldsheetpath = schframe->GetCurrentSheet();
464 
465  /* When printing all pages, the printed page is not the current page. In complex hierarchies,
466  * we must update symbol references and other parameters in the given printed SCH_SCREEN,
467  * according to the sheet path because in complex hierarchies a SCH_SCREEN (a drawing ) is
468  * shared between many sheets and symbol references depend on the actual sheet path used.
469  */
470  SCH_SHEET_LIST sheetList;
471 
472  if( aPlotAll )
473  {
474  sheetList.BuildSheetList( &schframe->Schematic().Root(), true );
475  sheetList.SortByPageNumbers();
476  }
477  else
478  {
479  sheetList.push_back( schframe->GetCurrentSheet() );
480  }
481 
482  REPORTER& reporter = m_MessagesBox->Reporter();
483 
484  for( unsigned i = 0; i < sheetList.size(); i++ )
485  {
486  schframe->SetCurrentSheet( sheetList[i] );
488  schframe->SetSheetNumberAndCount();
489 
490  SCH_SCREEN* screen = schframe->GetCurrentSheet().LastScreen();
491  wxPoint plot_offset;
492  wxString msg;
493 
494  try
495  {
496  wxString fname = schframe->GetUniqueFilenameForCurrentSheet();
497 
498  // The sub sheet can be in a sub_hierarchy, but we plot the file in the
499  // main project folder (or the folder specified by the caller),
500  // so replace separators to create a unique filename:
501  fname.Replace( "/", "_" );
502  fname.Replace( "\\", "_" );
503  wxString ext = DXF_PLOTTER::GetDefaultFileExtension();
504  wxFileName plotFileName = createPlotFileName( fname, ext, &reporter );
505 
506  if( !plotFileName.IsOk() )
507  return;
508 
509  if( plotOneSheetDXF( plotFileName.GetFullPath(), screen, aRenderSettings,
510  plot_offset, 1.0, aPlotDrawingSheet ) )
511  {
512  msg.Printf( _( "Plotted to '%s'." ), plotFileName.GetFullPath() );
513  reporter.Report( msg, RPT_SEVERITY_ACTION );
514  }
515  else // Error
516  {
517  msg.Printf( _( "Failed to create file '%s'." ), plotFileName.GetFullPath() );
518  reporter.Report( msg, RPT_SEVERITY_ERROR );
519  }
520  }
521  catch( IO_ERROR& e )
522  {
523  msg.Printf( wxT( "DXF Plotter exception: %s"), e.What() );
524  reporter.Report( msg, RPT_SEVERITY_ERROR );
525  schframe->SetCurrentSheet( oldsheetpath );
527  schframe->SetSheetNumberAndCount();
528  return;
529  }
530  }
531 
532  reporter.ReportTail( _( "Done." ), RPT_SEVERITY_INFO );
533 
534  schframe->SetCurrentSheet( oldsheetpath );
536  schframe->SetSheetNumberAndCount();
537 }
538 
539 
540 bool DIALOG_PLOT_SCHEMATIC::plotOneSheetDXF( const wxString& aFileName,
541  SCH_SCREEN* aScreen,
542  RENDER_SETTINGS* aRenderSettings,
543  const wxPoint& aPlotOffset,
544  double aScale,
545  bool aPlotFrameRef )
546 {
547  aRenderSettings->LoadColors( getColorSettings() );
548  aRenderSettings->SetDefaultPenWidth( 0 );
549 
550  const PAGE_INFO& pageInfo = aScreen->GetPageSettings();
551  DXF_PLOTTER* plotter = new DXF_PLOTTER();
552 
553  plotter->SetRenderSettings( aRenderSettings );
554  plotter->SetPageSettings( pageInfo );
555  plotter->SetColorMode( getModeColor() );
556 
557  // Currently, plot units are in decimil
558  plotter->SetViewport( aPlotOffset, IU_PER_MILS/10, aScale, false );
559 
560  // Init :
561  plotter->SetCreator( wxT( "Eeschema-DXF" ) );
562 
563  if( ! plotter->OpenFile( aFileName ) )
564  {
565  delete plotter;
566  return false;
567  }
568 
569  LOCALE_IO toggle;
570 
571  plotter->StartPlot();
572 
573  if( aPlotFrameRef )
574  {
575  PlotDrawingSheet( plotter, &m_parent->Prj(), m_parent->GetTitleBlock(), pageInfo,
576  aScreen->GetPageNumber(), aScreen->GetPageCount(),
577  m_parent->GetScreenDesc(), aScreen->GetFileName(),
578  plotter->GetColorMode() ?
580  COLOR4D::BLACK, aScreen->GetVirtualPageNumber() == 1 );
581  }
582 
583  aScreen->Plot( plotter );
584 
585  // finish
586  plotter->EndPlot();
587  delete plotter;
588 
589  return true;
590 }
591 
592 
594 {
596 
597  if( m_HPGLPenSize > Millimeter2iu( 2 ) )
599 
600  if( m_HPGLPenSize < Millimeter2iu( 0.01 ) )
601  m_HPGLPenSize = Millimeter2iu( 0.01 );
602 }
603 
604 
605 void DIALOG_PLOT_SCHEMATIC::createHPGLFiles( bool aPlotAll, bool aPlotFrameRef,
606  RENDER_SETTINGS* aRenderSettings )
607 {
608  SCH_SCREEN* screen = m_parent->GetScreen();
609  SCH_SHEET_PATH oldsheetpath = m_parent->GetCurrentSheet();
610 
611  /* When printing all pages, the printed page is not the current page. In complex hierarchies,
612  * we must update symbol references and other parameters in the given printed SCH_SCREEN,
613  * according to the sheet path because in complex hierarchies a SCH_SCREEN (a drawing ) is
614  * shared between many sheets and symbol references depend on the actual sheet path used.
615  */
616  SCH_SHEET_LIST sheetList;
617 
618  if( aPlotAll )
619  {
620  sheetList.BuildSheetList( &m_parent->Schematic().Root(), true );
621  sheetList.SortByPageNumbers();
622  }
623  else
624  {
625  sheetList.push_back( m_parent->GetCurrentSheet() );
626  }
627 
628  REPORTER& reporter = m_MessagesBox->Reporter();
629 
630  setHpglPenWidth();
631 
632  for( unsigned i = 0; i < sheetList.size(); i++ )
633  {
634  m_parent->SetCurrentSheet( sheetList[i] );
637 
638  screen = m_parent->GetCurrentSheet().LastScreen();
639 
640  if( !screen ) // LastScreen() may return NULL
641  screen = m_parent->GetScreen();
642 
643  const PAGE_INFO& curPage = screen->GetPageSettings();
644 
645  PAGE_INFO plotPage = curPage;
646 
647  // if plotting on a page size other than curPage
648  if( m_paperSizeOption->GetSelection() != PAGE_DEFAULT )
649  plotPage.SetType( plot_sheet_list( m_paperSizeOption->GetSelection() ) );
650 
651  // Calculation of conversion scales.
652  double plot_scale = (double) plotPage.GetWidthMils() / curPage.GetWidthMils();
653 
654  // Calculate offsets
655  wxPoint plotOffset;
656  wxString msg;
657 
659  {
660  plotOffset.x = plotPage.GetWidthIU() / 2;
661  plotOffset.y = -plotPage.GetHeightIU() / 2;
662  }
663 
664  try
665  {
666  wxString fname = m_parent->GetUniqueFilenameForCurrentSheet();
667  // The sub sheet can be in a sub_hierarchy, but we plot the file in the
668  // main project folder (or the folder specified by the caller),
669  // so replace separators to create a unique filename:
670  fname.Replace( "/", "_" );
671  fname.Replace( "\\", "_" );
672  wxString ext = HPGL_PLOTTER::GetDefaultFileExtension();
673  wxFileName plotFileName = createPlotFileName( fname, ext, &reporter );
674 
675  if( !plotFileName.IsOk() )
676  return;
677 
678  LOCALE_IO toggle;
679 
680  if( plotOneSheetHpgl( plotFileName.GetFullPath(), screen, plotPage, aRenderSettings,
681  plotOffset, plot_scale, aPlotFrameRef, getPlotOriginAndUnits() ) )
682  {
683  msg.Printf( _( "Plotted to '%s'." ), plotFileName.GetFullPath() );
684  reporter.Report( msg, RPT_SEVERITY_ACTION );
685  }
686  else
687  {
688  msg.Printf( _( "Failed to create file '%s'." ), plotFileName.GetFullPath() );
689  reporter.Report( msg, RPT_SEVERITY_ERROR );
690  }
691  }
692  catch( IO_ERROR& e )
693  {
694  msg.Printf( wxT( "HPGL Plotter exception: %s"), e.What() );
695  reporter.Report( msg, RPT_SEVERITY_ERROR );
696  }
697  }
698 
699  reporter.ReportTail( _( "Done." ), RPT_SEVERITY_INFO );
700 
701  m_parent->SetCurrentSheet( oldsheetpath );
704 }
705 
706 
707 bool DIALOG_PLOT_SCHEMATIC::plotOneSheetHpgl( const wxString& aFileName,
708  SCH_SCREEN* aScreen,
709  const PAGE_INFO& aPageInfo,
710  RENDER_SETTINGS* aRenderSettings,
711  const wxPoint& aPlot0ffset,
712  double aScale,
713  bool aPlotFrameRef,
714  HPGL_PLOT_ORIGIN_AND_UNITS aOriginAndUnits )
715 {
716  HPGL_PLOTTER* plotter = new HPGL_PLOTTER();
717  // Currently, plot units are in decimil
718 
719  plotter->SetPageSettings( aPageInfo );
720  plotter->SetRenderSettings( aRenderSettings );
721  plotter->RenderSettings()->LoadColors( getColorSettings() );
722  plotter->SetColorMode( getModeColor() );
723  plotter->SetViewport( aPlot0ffset, IU_PER_MILS/10, aScale, false );
724 
725  // TODO this could be configurable
726  plotter->SetTargetChordLength( Millimeter2iu( 0.6 ) );
727 
728  switch( aOriginAndUnits )
729  {
732  default:
733  plotter->SetUserCoords( false );
734  break;
736  plotter->SetUserCoords( true );
737  plotter->SetUserCoordsFit( false );
738  break;
740  plotter->SetUserCoords( true );
741  plotter->SetUserCoordsFit( true );
742  break;
743  }
744 
745  // Init :
746  plotter->SetCreator( wxT( "Eeschema-HPGL" ) );
747 
748  if( !plotter->OpenFile( aFileName ) )
749  {
750  delete plotter;
751  return false;
752  }
753 
754  LOCALE_IO toggle;
755 
756  // Pen num and pen speed are not initialized here.
757  // Default HPGL driver values are used
758  plotter->SetPenDiameter( m_HPGLPenSize );
759  plotter->StartPlot();
760 
761  if( aPlotFrameRef )
762  {
763  PlotDrawingSheet( plotter, &m_parent->Prj(), m_parent->GetTitleBlock(), aPageInfo,
764  aScreen->GetPageNumber(), aScreen->GetPageCount(),
766  aScreen->GetVirtualPageNumber() == 1 );
767  }
768 
769  aScreen->Plot( plotter );
770 
771  plotter->EndPlot();
772  delete plotter;
773 
774  return true;
775 }
776 
777 
778 void DIALOG_PLOT_SCHEMATIC::createPDFFile( bool aPlotAll, bool aPlotDrawingSheet,
779  RENDER_SETTINGS* aRenderSettings )
780 {
781  SCH_SHEET_PATH oldsheetpath = m_parent->GetCurrentSheet(); // sheetpath is saved here
782 
783  /* When printing all pages, the printed page is not the current page. In complex hierarchies,
784  * we must update symbol references and other parameters in the given printed SCH_SCREEN,
785  * according to the sheet path because in complex hierarchies a SCH_SCREEN (a drawing ) is
786  * shared between many sheets and symbol references depend on the actual sheet path used.
787  */
788  SCH_SHEET_LIST sheetList;
789 
790  if( aPlotAll )
791  {
792  sheetList.BuildSheetList( &m_parent->Schematic().Root(), true );
793  sheetList.SortByPageNumbers();
794  }
795  else
796  {
797  sheetList.push_back( m_parent->GetCurrentSheet() );
798  }
799 
800  // Allocate the plotter and set the job level parameter
801  PDF_PLOTTER* plotter = new PDF_PLOTTER();
802  plotter->SetRenderSettings( aRenderSettings );
803  plotter->SetColorMode( getModeColor() );
804  plotter->SetCreator( wxT( "Eeschema-PDF" ) );
805  plotter->SetTitle( m_parent->GetTitleBlock().GetTitle() );
806 
807  wxString msg;
808  wxFileName plotFileName;
809  REPORTER& reporter = m_MessagesBox->Reporter();
810  LOCALE_IO toggle; // Switch the locale to standard C
811 
812  for( unsigned i = 0; i < sheetList.size(); i++ )
813  {
814  m_parent->SetCurrentSheet( sheetList[i] );
818 
819  if( i == 0 )
820  {
821  try
822  {
823  wxString fname = m_parent->GetUniqueFilenameForCurrentSheet();
824 
825  // The sub sheet can be in a sub_hierarchy, but we plot the file in the main
826  // project folder (or the folder specified by the caller), so replace separators
827  // to create a unique filename:
828  fname.Replace( "/", "_" );
829  fname.Replace( "\\", "_" );
830  wxString ext = PDF_PLOTTER::GetDefaultFileExtension();
831  plotFileName = createPlotFileName( fname, ext, &reporter );
832 
833  if( !plotFileName.IsOk() )
834  return;
835 
836  if( !plotter->OpenFile( plotFileName.GetFullPath() ) )
837  {
838  msg.Printf( _( "Failed to create file '%s'." ), plotFileName.GetFullPath() );
839  reporter.Report( msg, RPT_SEVERITY_ERROR );
840  delete plotter;
841  return;
842  }
843 
844  // Open the plotter and do the first page
845  setupPlotPagePDF( plotter, screen );
846  plotter->StartPlot();
847  }
848  catch( const IO_ERROR& e )
849  {
850  // Cannot plot PDF file
851  msg.Printf( wxT( "PDF Plotter exception: %s" ), e.What() );
852  reporter.Report( msg, RPT_SEVERITY_ERROR );
853 
854  restoreEnvironment( plotter, oldsheetpath );
855  return;
856  }
857 
858  }
859  else
860  {
861  /* For the following pages you need to close the (finished) page,
862  * reconfigure, and then start a new one */
863  plotter->ClosePage();
864  setupPlotPagePDF( plotter, screen );
865  plotter->StartPage();
866  }
867 
868  plotOneSheetPDF( plotter, screen, aPlotDrawingSheet );
869  }
870 
871  // Everything done, close the plot and restore the environment
872  msg.Printf( _( "Plotted to '%s'.\n" ), plotFileName.GetFullPath() );
873  reporter.Report( msg, RPT_SEVERITY_ACTION );
874  reporter.ReportTail( _( "Done." ), RPT_SEVERITY_INFO );
875 
876  restoreEnvironment( plotter, oldsheetpath );
877 }
878 
879 
881  SCH_SHEET_PATH& aOldsheetpath )
882 {
883  aPlotter->EndPlot();
884  delete aPlotter;
885 
886  // Restore the previous sheet
887  m_parent->SetCurrentSheet( aOldsheetpath );
890 }
891 
892 
894  bool aPlotDrawingSheet )
895 {
896  if( m_plotBackgroundColor->GetValue() )
897  {
898  aPlotter->SetColor( aPlotter->RenderSettings()->GetBackgroundColor() );
899  wxPoint end( aPlotter->PageSettings().GetWidthIU(),
900  aPlotter->PageSettings().GetHeightIU() );
901  aPlotter->Rect( wxPoint( 0, 0 ), end, FILL_TYPE::FILLED_SHAPE, 1.0 );
902  }
903 
904  if( aPlotDrawingSheet )
905  {
907 
908  if( aPlotter->GetColorMode() )
910 
911  PlotDrawingSheet( aPlotter, &aScreen->Schematic()->Prj(), m_parent->GetTitleBlock(),
912  m_parent->GetPageSettings(), aScreen->GetPageNumber(),
913  aScreen->GetPageCount(), m_parent->GetScreenDesc(),
914  aScreen->GetFileName(), color, aScreen->GetVirtualPageNumber() == 1 );
915  }
916 
917  aScreen->Plot( aPlotter );
918 }
919 
920 
922 {
923  PAGE_INFO plotPage; // page size selected to plot
924 
925  // Considerations on page size and scaling requests
926  const PAGE_INFO& actualPage = aScreen->GetPageSettings(); // page size selected in schematic
927 
928  switch( m_pageSizeSelect )
929  {
930  case PAGE_SIZE_A:
931  plotPage.SetType( wxT( "A" ) );
932  plotPage.SetPortrait( actualPage.IsPortrait() );
933  break;
934 
935  case PAGE_SIZE_A4:
936  plotPage.SetType( wxT( "A4" ) );
937  plotPage.SetPortrait( actualPage.IsPortrait() );
938  break;
939 
940  case PAGE_SIZE_AUTO:
941  default:
942  plotPage = actualPage;
943  break;
944  }
945 
946  double scalex = (double) plotPage.GetWidthMils() / actualPage.GetWidthMils();
947  double scaley = (double) plotPage.GetHeightMils() / actualPage.GetHeightMils();
948  double scale = std::min( scalex, scaley );
949  aPlotter->SetPageSettings( plotPage );
950 
951  // Currently, plot units are in decimil
952  aPlotter->SetViewport( wxPoint( 0, 0 ), IU_PER_MILS/10, scale, false );
953 }
954 
955 
956 void DIALOG_PLOT_SCHEMATIC::createPSFiles( bool aPlotAll, bool aPlotFrameRef,
957  RENDER_SETTINGS* aRenderSettings )
958 {
959  SCH_SHEET_PATH oldsheetpath = m_parent->GetCurrentSheet(); // sheetpath is saved here
960  PAGE_INFO plotPage; // page size selected to plot
961  wxString msg;
962  REPORTER& reporter = m_MessagesBox->Reporter();
963 
964  /* When printing all pages, the printed page is not the current page.
965  * In complex hierarchies, we must update symbol references and other parameters in the
966  * given printed SCH_SCREEN, accordant to the sheet path because in complex hierarchies
967  * a SCH_SCREEN (a drawing ) is shared between many sheets and symbol references
968  * depend on the actual sheet path used.
969  */
970  SCH_SHEET_LIST sheetList;
971 
972  if( aPlotAll )
973  {
974  sheetList.BuildSheetList( &m_parent->Schematic().Root(), true );
975  sheetList.SortByPageNumbers();
976  }
977  else
978  {
979  sheetList.push_back( m_parent->GetCurrentSheet() );
980  }
981 
982  for( unsigned i = 0; i < sheetList.size(); i++ )
983  {
984  m_parent->SetCurrentSheet( sheetList[i] );
987 
989  PAGE_INFO actualPage = screen->GetPageSettings();
990 
991  switch( m_pageSizeSelect )
992  {
993  case PAGE_SIZE_A:
994  plotPage.SetType( wxT( "A" ) );
995  plotPage.SetPortrait( actualPage.IsPortrait() );
996  break;
997 
998  case PAGE_SIZE_A4:
999  plotPage.SetType( wxT( "A4" ) );
1000  plotPage.SetPortrait( actualPage.IsPortrait() );
1001  break;
1002 
1003  case PAGE_SIZE_AUTO:
1004  default:
1005  plotPage = actualPage;
1006  break;
1007  }
1008 
1009  double scalex = (double) plotPage.GetWidthMils() / actualPage.GetWidthMils();
1010  double scaley = (double) plotPage.GetHeightMils() / actualPage.GetHeightMils();
1011  double scale = std::min( scalex, scaley );
1012  wxPoint plot_offset;
1013 
1014  try
1015  {
1016  wxString fname = m_parent->GetUniqueFilenameForCurrentSheet();
1017 
1018  // The sub sheet can be in a sub_hierarchy, but we plot the file in the
1019  // main project folder (or the folder specified by the caller),
1020  // so replace separators to create a unique filename:
1021  fname.Replace( "/", "_" );
1022  fname.Replace ("\\", "_" );
1023  wxString ext = PS_PLOTTER::GetDefaultFileExtension();
1024  wxFileName plotFileName = createPlotFileName( fname, ext, &reporter );
1025 
1026  if( !plotFileName.IsOk() )
1027  return;
1028 
1029  if( plotOneSheetPS( plotFileName.GetFullPath(), screen, aRenderSettings, plotPage,
1030  plot_offset, scale, aPlotFrameRef ) )
1031  {
1032  msg.Printf( _( "Plotted to '%s'." ), plotFileName.GetFullPath() );
1033  reporter.Report( msg, RPT_SEVERITY_ACTION );
1034  }
1035  else
1036  {
1037  // Error
1038  msg.Printf( _( "Failed to create file '%s'." ), plotFileName.GetFullPath() );
1039  reporter.Report( msg, RPT_SEVERITY_ERROR );
1040  }
1041 
1042  }
1043  catch( IO_ERROR& e )
1044  {
1045  msg.Printf( wxT( "PS Plotter exception: %s"), e.What() );
1046  reporter.Report( msg, RPT_SEVERITY_ERROR );
1047  }
1048  }
1049 
1050  reporter.ReportTail( _( "Done." ), RPT_SEVERITY_INFO );
1051 
1052  m_parent->SetCurrentSheet( oldsheetpath );
1055 }
1056 
1057 
1058 bool DIALOG_PLOT_SCHEMATIC::plotOneSheetPS( const wxString& aFileName,
1059  SCH_SCREEN* aScreen,
1060  RENDER_SETTINGS* aRenderSettings,
1061  const PAGE_INFO& aPageInfo,
1062  const wxPoint& aPlot0ffset,
1063  double aScale,
1064  bool aPlotFrameRef )
1065 {
1066  PS_PLOTTER* plotter = new PS_PLOTTER();
1067  plotter->SetRenderSettings( aRenderSettings );
1068  plotter->SetPageSettings( aPageInfo );
1069  plotter->SetColorMode( getModeColor() );
1070 
1071  // Currently, plot units are in decimil
1072  plotter->SetViewport( aPlot0ffset, IU_PER_MILS/10, aScale, false );
1073 
1074  // Init :
1075  plotter->SetCreator( wxT( "Eeschema-PS" ) );
1076 
1077  if( ! plotter->OpenFile( aFileName ) )
1078  {
1079  delete plotter;
1080  return false;
1081  }
1082 
1083  LOCALE_IO toggle; // Switch the locale to standard C
1084 
1085  plotter->StartPlot();
1086 
1087  if( m_plotBackgroundColor->GetValue() )
1088  {
1090  wxPoint end( plotter->PageSettings().GetWidthIU(), plotter->PageSettings().GetHeightIU() );
1091  plotter->Rect( wxPoint( 0, 0 ), end, FILL_TYPE::FILLED_SHAPE, 1.0 );
1092  }
1093 
1094  if( aPlotFrameRef )
1095  {
1096  PlotDrawingSheet( plotter, &aScreen->Schematic()->Prj(), m_parent->GetTitleBlock(),
1097  aPageInfo, aScreen->GetPageNumber(), aScreen->GetPageCount(),
1098  m_parent->GetScreenDesc(), aScreen->GetFileName(),
1099  plotter->GetColorMode() ?
1101  COLOR4D::BLACK, aScreen->GetVirtualPageNumber() == 1 );
1102  }
1103 
1104  aScreen->Plot( plotter );
1105 
1106  plotter->EndPlot();
1107  delete plotter;
1108 
1109  return true;
1110 }
1111 
1112 
1113 void DIALOG_PLOT_SCHEMATIC::createSVGFiles( bool aPrintAll, bool aPrintFrameRef,
1114  RENDER_SETTINGS* aRenderSettings )
1115 {
1116  wxString msg;
1117  REPORTER& reporter = m_MessagesBox->Reporter();
1118  SCH_SHEET_PATH oldsheetpath = m_parent->GetCurrentSheet();
1119  SCH_SHEET_LIST sheetList;
1120 
1121  if( aPrintAll )
1122  {
1123  sheetList.BuildSheetList( &m_parent->Schematic().Root(), true );
1124  sheetList.SortByPageNumbers();
1125  }
1126  else
1127  {
1128  sheetList.push_back( m_parent->GetCurrentSheet() );
1129  }
1130 
1131  for( unsigned i = 0; i < sheetList.size(); i++ )
1132  {
1133  SCH_SCREEN* screen;
1134  m_parent->SetCurrentSheet( sheetList[i] );
1137  screen = m_parent->GetCurrentSheet().LastScreen();
1138 
1139  try
1140  {
1141  wxString fname = m_parent->GetUniqueFilenameForCurrentSheet();
1142 
1143  // The sub sheet can be in a sub_hierarchy, but we plot the file in the
1144  // main project folder (or the folder specified by the caller),
1145  // so replace separators to create a unique filename:
1146  fname.Replace( "/", "_" );
1147  fname.Replace( "\\", "_" );
1148  wxString ext = SVG_PLOTTER::GetDefaultFileExtension();
1149  wxFileName plotFileName = createPlotFileName( fname, ext, &reporter );
1150 
1151  if( !plotFileName.IsOk() )
1152  return;
1153 
1154  bool success = plotOneSheetSVG( plotFileName.GetFullPath(), screen, aRenderSettings,
1155  getModeColor() ? false : true, aPrintFrameRef );
1156 
1157  if( !success )
1158  {
1159  msg.Printf( _( "Failed to create file '%s'." ), plotFileName.GetFullPath() );
1160  reporter.Report( msg, RPT_SEVERITY_ERROR );
1161  }
1162  else
1163  {
1164  msg.Printf( _( "Plotted to '%s'." ), plotFileName.GetFullPath() );
1165  reporter.Report( msg, RPT_SEVERITY_ACTION );
1166  }
1167  }
1168  catch( const IO_ERROR& e )
1169  {
1170  // Cannot plot SVG file
1171  msg.Printf( wxT( "SVG Plotter exception: %s" ), e.What() );
1172  reporter.Report( msg, RPT_SEVERITY_ERROR );
1173  break;
1174  }
1175  }
1176 
1177  reporter.ReportTail( _( "Done" ), RPT_SEVERITY_INFO );
1178 
1179  m_parent->SetCurrentSheet( oldsheetpath );
1182 }
1183 
1184 
1185 bool DIALOG_PLOT_SCHEMATIC::plotOneSheetSVG( const wxString& aFileName,
1186  SCH_SCREEN* aScreen,
1187  RENDER_SETTINGS* aRenderSettings,
1188  bool aPlotBlackAndWhite,
1189  bool aPlotFrameRef )
1190 {
1191  const PAGE_INFO& pageInfo = aScreen->GetPageSettings();
1192 
1193  SVG_PLOTTER* plotter = new SVG_PLOTTER();
1194  plotter->SetRenderSettings( aRenderSettings );
1195  plotter->SetPageSettings( pageInfo );
1196  plotter->SetColorMode( aPlotBlackAndWhite ? false : true );
1197  wxPoint plot_offset;
1198  double scale = 1.0;
1199 
1200  // Currently, plot units are in decimil
1201  plotter->SetViewport( plot_offset, IU_PER_MILS/10, scale, false );
1202 
1203  // Init :
1204  plotter->SetCreator( wxT( "Eeschema-SVG" ) );
1205 
1206  if( ! plotter->OpenFile( aFileName ) )
1207  {
1208  delete plotter;
1209  return false;
1210  }
1211 
1212  LOCALE_IO toggle;
1213 
1214  plotter->StartPlot();
1215 
1216  if( m_plotBackgroundColor->GetValue() )
1217  {
1219  wxPoint end( plotter->PageSettings().GetWidthIU(),
1220  plotter->PageSettings().GetHeightIU() );
1221  plotter->Rect( wxPoint( 0, 0 ), end, FILL_TYPE::FILLED_SHAPE, 1.0 );
1222  }
1223 
1224  if( aPlotFrameRef )
1225  {
1226  PlotDrawingSheet( plotter, &aScreen->Schematic()->Prj(), m_parent->GetTitleBlock(),
1227  pageInfo, aScreen->GetPageNumber(), aScreen->GetPageCount(),
1228  m_parent->GetScreenDesc(), aScreen->GetFileName(),
1229  plotter->GetColorMode() ?
1231  COLOR4D::BLACK, aScreen->GetVirtualPageNumber() == 1 );
1232  }
1233 
1234  aScreen->Plot( plotter );
1235 
1236  plotter->EndPlot();
1237  delete plotter;
1238 
1239  return true;
1240 }
1241 
1242 
1244 {
1245  wxString msg;
1246  wxString extMsg;
1247  wxFileName fn;
1248 
1249  extMsg.Printf( _( "Falling back to user path '%s'." ),
1250  wxStandardPaths::Get().GetDocumentsDir() );
1251 
1252  // Build the absolute path of current output directory to preselect it in the file browser.
1253  wxString path = ExpandEnvVarSubstitutions( m_outputDirectoryName->GetValue(), &Prj() );
1254 
1255  fn.SetPath( path );
1256 
1257  // If the contents of the path edit control results in an absolute path, return it as is.
1258  if( fn.IsAbsolute() )
1259  return path;
1260 
1261  // When editing a schematic that is not part of a project in the stand alone mode, the
1262  // project path is not defined.
1263  if( Prj().IsNullProject() )
1264  {
1265  SCH_SCREEN* screen = m_parent->Schematic().RootScreen();
1266 
1267  if( screen && !screen->GetFileName().IsEmpty() )
1268  {
1269  fn = screen->GetFileName();
1270  msg.Printf( _( "Cannot normalize path '%s%s'." ), fn.GetPathWithSep(), path );
1271  fn.SetPath( fn.GetPathWithSep() + path );
1272 
1273  // Normalize always returns true for a non-empty file name so clear the file name
1274  // and extension so that only the path is normalized.
1275  fn.SetName( wxEmptyString );
1276  fn.SetExt( wxEmptyString );
1277 
1278  if( fn.Normalize() )
1279  {
1280  path = fn.GetPath();
1281  }
1282  else
1283  {
1284  wxMessageDialog dlg( this, msg, _( "Warning" ), wxOK | wxCENTER | wxRESIZE_BORDER
1285  | wxICON_EXCLAMATION | wxSTAY_ON_TOP );
1286 
1287  dlg.SetExtendedMessage( extMsg );
1288  dlg.ShowModal();
1289 
1290  path = wxStandardPaths::Get().GetDocumentsDir();
1291  }
1292  }
1293  else
1294  {
1295  msg = _( "No project or path defined for the current schematic." );
1296 
1297  wxMessageDialog dlg( this, msg, _( "Warning" ), wxOK | wxCENTER | wxRESIZE_BORDER
1298  | wxICON_EXCLAMATION | wxSTAY_ON_TOP );
1299  dlg.SetExtendedMessage( extMsg );
1300  dlg.ShowModal();
1301 
1302  // Always fall back to user's document path if no other absolute path can be normalized.
1303  path = wxStandardPaths::Get().GetDocumentsDir();
1304  }
1305  }
1306  else
1307  {
1308  msg.Printf( _( "Cannot normalize path '%s%s'." ), Prj().GetProjectPath(), path );
1309 
1310  // Build the absolute path of current output directory and the project path.
1311  fn.SetPath( Prj().GetProjectPath() + path );
1312 
1313  if( fn.Normalize() )
1314  {
1315  path = fn.GetPath();
1316  }
1317  else
1318  {
1319  wxMessageDialog dlg( this, msg, _( "Warning" ),
1320  wxOK | wxCENTER | wxRESIZE_BORDER | wxICON_EXCLAMATION |
1321  wxSTAY_ON_TOP );
1322 
1323  dlg.SetExtendedMessage( extMsg );
1324  dlg.ShowModal();
1325 
1326  path = wxStandardPaths::Get().GetDocumentsDir();
1327  }
1328  }
1329 
1330  return path;
1331 }
static wxString GetDefaultFileExtension()
void SetCurrentSheet(const SCH_SHEET_PATH &aSheet)
A container for handling SCH_SHEET_PATH objects in a flattened hierarchy.
virtual bool EndPlot() override
HPGL end of plot: sort and emit graphics, pen return and release.
virtual void SetViewport(const wxPoint &aOffset, double aIusPerDecimil, double aScale, bool aMirror) override
Set the plot offset and scaling for the current plot.
Definition: PS_plotter.cpp:420
void Plot(PLOTTER *aPlotter) const
Plot all the schematic objects to aPlotter.
Definition: sch_screen.cpp:770
const wxString & GetFileName() const
Definition: sch_screen.h:145
virtual void SetCreator(const wxString &aCreator)
Definition: plotter.h:174
void plotOneSheetPDF(PLOTTER *aPlotter, SCH_SCREEN *aScreen, bool aPlotDrawingSheet)
static wxString GetDefaultFileExtension()
SETTINGS_MANAGER * GetSettingsManager() const
void OnOutputDirectoryBrowseClicked(wxCommandEvent &event) override
Set the m_outputDirectoryName variable to the selected directory from directory dialog.
Instantiate the current locale within a scope in which you are expecting exceptions to be thrown.
Definition: locale_io.h:40
virtual void SetViewport(const wxPoint &aOffset, double aIusPerDecimil, double aScale, bool aMirror) override
Set the plot offset and scaling for the current plot.
Container for all the knowledge about how graphical objects are drawn on any output surface/device.
virtual bool EndPlot() override
void OnUpdateUI(wxUpdateUIEvent &event) override
std::vector< COLOR_SETTINGS * > GetColorSettingsList()
virtual const COLOR4D & GetBackgroundColor()=0
Return current background color settings.
int GetHeightMils() const
Definition: page_info.h:133
KIFACE_BASE & Kiface()
Global KIFACE_BASE "get" accessor.
virtual void Rect(const wxPoint &p1, const wxPoint &p2, FILL_TYPE fill, int width=USE_DEFAULT_LINE_WIDTH)=0
virtual void SetViewport(const wxPoint &aOffset, double aIusPerDecimil, double aScale, bool aMirror) override
Set the scale/position for the DXF plot.
virtual void StartPage()
Start a new page in the PDF document.
static constexpr double IU_PER_MM
Mock up a conversion function.
virtual void SetTitle(const wxString &aTitle)
Definition: plotter.h:176
virtual bool OpenFile(const wxString &aFullFilename)
Open or create the plot file aFullFilename.
Definition: plotter.cpp:76
wxStdDialogButtonSizer * m_sdbSizer1
static wxString GetDefaultFileExtension()
virtual void SetColorMode(bool aColorMode)
Plot in B/W or color.
Definition: plotter.h:152
wxString GetFilename() const
Definition: json_settings.h:72
SCHEMATIC_SETTINGS & Settings() const
Definition: schematic.cpp:167
int color
Definition: DXF_plotter.cpp:57
DIALOG_PLOT_SCHEMATIC(SCH_EDIT_FRAME *parent)
int GetVirtualPageNumber() const
Definition: base_screen.h:75
virtual bool EndPlot() override
Definition: PS_plotter.cpp:960
virtual REPORTER & ReportTail(const wxString &aText, SEVERITY aSeverity=RPT_SEVERITY_UNDEFINED)
Places the report at the end of the list, for objects that support report ordering.
Definition: reporter.h:99
void SetRenderSettings(RENDER_SETTINGS *aSettings)
Definition: plotter.h:155
const wxChar *const tracePathsAndFiles
Flag to enable path and file name debug output.
static const wxChar * plot_sheet_list(int aSize)
bool SetType(const wxString &aStandardPageDescriptionName, bool aIsPortrait=false)
Set the name of the page type and also the sizes and margins commonly associated with that type name.
Definition: page_info.cpp:119
bool plotOneSheetPS(const wxString &aFileName, SCH_SCREEN *aScreen, RENDER_SETTINGS *aRenderSettings, const PAGE_INFO &aPageInfo, const wxPoint &aPlot0ffset, double aScale, bool aPlotFrameRef)
virtual void SetPenDiameter(double diameter)
wxFileName createPlotFileName(const wxString &aPlotFileName, const wxString &aExtension, REPORTER *aReporter=nullptr)
Create a file name with an absolute path name.
const COLOR4D & GetLayerColor(int aLayer) const
Return the color used to draw a layer.
COLOR_SETTINGS * getColorSettings()
void setPlotDrawingSheet(bool aPlot)
int GetPageCount() const
Definition: base_screen.h:72
bool plotOneSheetSVG(const wxString &aFileName, SCH_SCREEN *aScreen, RENDER_SETTINGS *aRenderSettings, bool aPlotBlackAndWhite, bool aPlotFrameRef)
void OnPlotCurrent(wxCommandEvent &event) override
KIGFX::SCH_RENDER_SETTINGS * GetRenderSettings()
Class DIALOG_PLOT_SCHEMATIC_BASE.
Schematic editor (Eeschema) main window.
Definition: color4d.h:44
const wxString ExpandEnvVarSubstitutions(const wxString &aString, PROJECT *aProject)
Replace any environment variable & text variable references with their values.
Definition: common.cpp:279
void createPDFFile(bool aPlotAll, bool aPlotDrawingSheet, RENDER_SETTINGS *aRenderSettings)
void getPlotOptions(RENDER_SETTINGS *aSettings)
A pure virtual class used to derive REPORTER objects from.
Definition: reporter.h:70
bool plotOneSheetDXF(const wxString &aFileName, SCH_SCREEN *aScreen, RENDER_SETTINGS *aRenderSettings, const wxPoint &aPlotOffset, double aScale, bool aPlotFrameRef)
void UpdateAllScreenReferences()
Update all the symbol references for this sheet path.
virtual void SetColor(const COLOR4D &color) override
The SetColor implementation is split with the subclasses: The PSLIKE computes the rgb values,...
void OnPageSizeSelected(wxCommandEvent &event) override
const PAGE_INFO & GetPageSettings() const
Definition: sch_screen.h:132
virtual bool StartPlot() override
At the start of the HPGL plot pen speed and number are requested.
virtual REPORTER & Report(const wxString &aText, SEVERITY aSeverity=RPT_SEVERITY_UNDEFINED)=0
Report a string with a given severity.
HPGL_PLOT_ORIGIN_AND_UNITS
void restoreEnvironment(PDF_PLOTTER *aPlotter, SCH_SHEET_PATH &aOldsheetpath)
Everything done, close the plot and restore the environment.
virtual const wxString AbsolutePath(const wxString &aFileName) const
Fix up aFileName if it is relative to the project's directory to be an absolute path and filename.
Definition: project.cpp:269
const wxString & GetPageNumber() const
Definition: base_screen.cpp:71
virtual void SetViewport(const wxPoint &aOffset, double aIusPerDecimil, double aScale, bool aMirror) override
Set the plot offset and scaling for the current plot.
void SetUserCoordsFit(bool user_coords_fit)
Set whether the user coordinate system is fit to content.
Definition: plotter_hpgl.h:59
void setupPlotPagePDF(PLOTTER *aPlotter, SCH_SCREEN *aScreen)
static wxString GetDefaultFileExtension()
Definition: plotter_dxf.h:47
SCH_SCREEN * GetScreen() const override
Return a pointer to a BASE_SCREEN or one of its derivatives.
wxString GetScreenDesc() const override
Return a human-readable description of the current screen.
void createDXFFiles(bool aPlotAll, bool aPlotDrawingSheet, RENDER_SETTINGS *aRenderSettings)
virtual bool EndPlot() override
virtual void ClosePage()
Close the current page in the PDF document (and emit its compressed stream).
virtual bool StartPlot() override
The code within this function (and the CloseFilePS function) creates postscript files whose contents ...
Definition: PS_plotter.cpp:803
void plotSchematic(bool aPlotAll)
void OnPlotAll(wxCommandEvent &event) override
virtual void SetColor(const COLOR4D &color) override
The SetColor implementation is split with the subclasses: The PSLIKE computes the rgb values,...
Definition: PS_plotter.cpp:62
virtual bool StartPlot() override
Open the DXF plot with a skeleton header.
virtual const wxString What() const
A composite of Problem() and Where()
Definition: exceptions.cpp:30
bool plotOneSheetHpgl(const wxString &aFileName, SCH_SCREEN *aScreen, const PAGE_INFO &aPageInfo, RENDER_SETTINGS *aRenderSettings, const wxPoint &aPlot0ffset, double aScale, bool aPlotFrameRef, HPGL_PLOT_ORIGIN_AND_UNITS aOriginAndUnits)
PLOT_FORMAT
The set of supported output plot formats.
Definition: plotter.h:67
Describe the page size and margins of a paper page on which to eventually print or plot.
Definition: page_info.h:53
PROJECT & Prj() const
Return 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:307
Plotting engine (HPGL)
void BuildSheetList(SCH_SHEET *aSheet, bool aCheckIntegrity)
Build the list of sheets and their sheet path from aSheet.
SCHEMATIC & Schematic() const
void createHPGLFiles(bool aPlotAll, bool aPlotFrameRef, RENDER_SETTINGS *aRenderSettings)
virtual bool EndPlot() override
virtual bool StartPlot() override
Create SVG file header.
#define _(s)
wxLogTrace helper definitions.
Handle access to a stack of flattened SCH_SHEET objects by way of a path for creating a flattened sch...
wxString GetFileName() const
Return the filename corresponding to this sheet.
Definition: sch_sheet.h:315
wxBitmap KiBitmap(BITMAPS aBitmap, int aHeightTag)
Construct a wxBitmap from an image identifier Returns the image from the active theme if the image ha...
Definition: bitmap.cpp:105
Plotting engine (DXF)
virtual bool IsNullProject() const
Check if this project is a null project (i.e.
Definition: project.cpp:134
virtual void SetViewport(const wxPoint &aOffset, double aIusPerDecimil, double aScale, bool aMirror)=0
Set the plot offset and scaling for the current plot.
virtual void SetColor(const COLOR4D &color)=0
PROJECT & Prj() const override
Return a reference to the project this schematic is part of.
Definition: schematic.h:75
Plotting engines similar to ps (PostScript, Gerber, svg)
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, const CPTREE &aTree)
Output a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
Definition: ptree.cpp:200
const PAGE_INFO & GetPageSettings() const override
void finishDialogSettings()
In all dialogs, we must call the same functions to fix minimal dlg size, the default position and per...
COLOR_SETTINGS * GetColorSettings(const wxString &aName="user")
Retrieves a color settings object that applications can read colors from.
void SetTargetChordLength(double chord_len)
Set the target length of chords used to draw approximated circles and arcs.
Base plotter engine class.
Definition: plotter.h:121
COLOR4D GetColor(int aLayer) const
void createPSFiles(bool aPlotAll, bool aPlotFrameRef, RENDER_SETTINGS *aSettings)
virtual void SetBackgroundColor(const COLOR4D &aColor)=0
Set the background color.
SCH_SHEET & Root() const
Definition: schematic.h:92
RENDER_SETTINGS * RenderSettings()
Definition: plotter.h:156
const int scale
SCH_SCREEN * LastScreen()
void SetSheetNumberAndCount()
Set the m_ScreenNumber and m_NumberOfScreens members for screens.
bool IsPortrait() const
Definition: page_info.h:117
void SetUserCoords(bool user_coords)
Switch to the user coordinate system.
Definition: plotter_hpgl.h:56
SCHEMATIC * Schematic() const
Definition: sch_screen.cpp:90
const TITLE_BLOCK & GetTitleBlock() const override
HPGL_PLOT_ORIGIN_AND_UNITS getPlotOriginAndUnits()
virtual void SetValue(int aValue)
Set new value (in Internal Units) for the text field, taking care of units conversion.
virtual void Rect(const wxPoint &p1, const wxPoint &p2, FILL_TYPE fill, int width=USE_DEFAULT_LINE_WIDTH) override
void PlotDrawingSheet(PLOTTER *plotter, const PROJECT *aProject, const TITLE_BLOCK &aTitleBlock, const PAGE_INFO &aPageInfo, const wxString &aSheetNumber, int aSheetCount, const wxString &aSheetDesc, const wxString &aFilename, COLOR4D aColor, bool aIsFirstPage)
void SortByPageNumbers(bool aUpdateVirtualPageNums=true)
Sort the list of sheets by page number.
static wxString GetDefaultFileExtension()
Definition: plotter_hpgl.h:43
#define IU_PER_MILS
Definition: plotter.cpp:136
virtual void Rect(const wxPoint &p1, const wxPoint &p2, FILL_TYPE fill, int width=USE_DEFAULT_LINE_WIDTH) override
Definition: PS_plotter.cpp:580
The common library.
These settings were stored in SCH_BASE_FRAME previously.
wxString GetUniqueFilenameForCurrentSheet()
virtual long long int GetValue()
Return the current value in Internal Units.
Store schematic specific render settings.
Definition: sch_painter.h:70
virtual bool OpenFile(const wxString &aFullFilename) override
Open or create the plot file aFullFilename.
Color settings are a bit different than most of the settings objects in that there can be more than o...
SCH_SHEET_PATH & GetCurrentSheet() const
const wxString & GetTitle() const
Definition: title_block.h:63
WX_HTML_REPORT_PANEL * m_MessagesBox
SCH_SCREEN * RootScreen() const
Helper to retrieve the screen of the root sheet.
Definition: schematic.cpp:117
void SetDefaultPenWidth(int aWidth)
void SetFileName(const wxString &aReportFileName)
virtual bool StartPlot() override
The PDF engine supports multiple pages; the first one is opened 'for free' the following are to be cl...
virtual void LoadColors(const COLOR_SETTINGS *aSettings)
void createSVGFiles(bool aPrintAll, bool aPrintFrameRef, RENDER_SETTINGS *aRenderSettings)
PAGE_INFO & PageSettings()
Definition: plotter.h:159
static constexpr int Millimeter2iu(double mm)
void SetPortrait(bool aIsPortrait)
Rotate the paper page 90 degrees.
Definition: page_info.cpp:186
Hold an error message and may be used when throwing exceptions containing meaningful error messages.
Definition: ki_exception.h:75
wxString getOutputPath()
Determine the best absolute path to plot files given the contents of the path edit control.
void Enable(bool aEnable)
Enable/disable the label, widget and units label.
int GetWidthMils() const
Definition: page_info.h:130
virtual void SetPageSettings(const PAGE_INFO &aPageSettings)
Definition: plotter.h:158
A color representation with 4 components: red, green, blue, alpha.
Definition: color4d.h:103
void setModeColor(bool aColor)
bool GetColorMode() const
Definition: plotter.h:153