KiCad PCB EDA Suite
plot_board_layers.cpp
Go to the documentation of this file.
1 
8 /*
9  * This program source code file is part of KiCad, a free EDA CAD application.
10  *
11  * Copyright (C) 1992-2016 KiCad Developers, see AUTHORS.txt for contributors.
12  *
13  * This program is free software; you can redistribute it and/or
14  * modify it under the terms of the GNU General Public License
15  * as published by the Free Software Foundation; either version 2
16  * of the License, or (at your option) any later version.
17  *
18  * This program is distributed in the hope that it will be useful,
19  * but WITHOUT ANY WARRANTY; without even the implied warranty of
20  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21  * GNU General Public License for more details.
22  *
23  * You should have received a copy of the GNU General Public License
24  * along with this program; if not, you may find one here:
25  * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
26  * or you may search the http://www.gnu.org website for the version 2 license,
27  * or you may write to the Free Software Foundation, Inc.,
28  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
29  */
30 
31 
32 #include <fctsys.h>
33 #include <common.h>
34 #include <plot_common.h>
35 #include <base_struct.h>
36 #include <drawtxt.h>
37 #include <trigo.h>
38 #include <wxBasePcbFrame.h>
39 #include <macros.h>
40 
41 #include <class_board.h>
42 #include <class_module.h>
43 #include <class_track.h>
44 #include <class_edge_mod.h>
45 #include <class_pcb_text.h>
46 #include <class_zone.h>
47 #include <class_drawsegment.h>
48 #include <class_mire.h>
49 #include <class_dimension.h>
50 
51 #include <pcbnew.h>
52 #include <pcbplot.h>
53 #include <plot_auxiliary_data.h>
54 
55 // Local
56 /* Plot a solder mask layer.
57  * Solder mask layers have a minimum thickness value and cannot be drawn like standard layers,
58  * unless the minimum thickness is 0.
59  */
60 static void PlotSolderMaskLayer( BOARD *aBoard, PLOTTER* aPlotter,
61  LSET aLayerMask, const PCB_PLOT_PARAMS& aPlotOpt,
62  int aMinThickness );
63 
64 /* Creates the plot for silkscreen layers
65  * Silkscreen layers have specific requirement for pads (not filled) and texts
66  * (with option to remove them from some copper areas (pads...)
67  */
68 void PlotSilkScreen( BOARD *aBoard, PLOTTER* aPlotter, LSET aLayerMask,
69  const PCB_PLOT_PARAMS& aPlotOpt )
70 {
71  BRDITEMS_PLOTTER itemplotter( aPlotter, aBoard, aPlotOpt );
72  itemplotter.SetLayerSet( aLayerMask );
73 
74  // Plot edge layer and graphic items
75  itemplotter.PlotBoardGraphicItems();
76 
77  // Plot footprint outlines :
78  itemplotter.Plot_Edges_Modules();
79 
80  // Plot pads (creates pads outlines, for pads on silkscreen layers)
81  LSET layersmask_plotpads = aLayerMask;
82 
83  // Calculate the mask layers of allowed layers for pads
84 
85  if( !aPlotOpt.GetPlotPadsOnSilkLayer() ) // Do not plot pads on silk screen layers
86  layersmask_plotpads.set( B_SilkS, false ).set( F_SilkS, false );
87 
88  if( layersmask_plotpads.any() )
89  {
90  for( MODULE* Module = aBoard->m_Modules; Module; Module = Module->Next() )
91  {
92  aPlotter->StartBlock( NULL );
93 
94  for( D_PAD * pad = Module->Pads(); pad; pad = pad->Next() )
95  {
96  // See if the pad is on this layer
97  LSET masklayer = pad->GetLayerSet();
98  if( !( masklayer & layersmask_plotpads ).any() )
99  continue;
100 
101  COLOR4D color = COLOR4D::BLACK;
102 
103  if( layersmask_plotpads[B_SilkS] )
104  color = aBoard->GetLayerColor( B_SilkS );
105 
106  if( layersmask_plotpads[F_SilkS] )
107  color = ( color == COLOR4D::BLACK) ? aBoard->GetLayerColor( F_SilkS ) : color;
108 
109  itemplotter.PlotPad( pad, color, SKETCH );
110  }
111 
112  aPlotter->EndBlock( NULL );
113  }
114  }
115 
116  // Plot footprints fields (ref, value ...)
117  for( MODULE* module = aBoard->m_Modules; module; module = module->Next() )
118  {
119  if( ! itemplotter.PlotAllTextsModule( module ) )
120  {
121  wxLogMessage( _( "Your BOARD has a bad layer number for footprint %s" ),
122  GetChars( module->GetReference() ) );
123  }
124  }
125 
126  // Plot filled areas
127  aPlotter->StartBlock( NULL );
128 
129  for( int ii = 0; ii < aBoard->GetAreaCount(); ii++ )
130  {
131  ZONE_CONTAINER* edge_zone = aBoard->GetArea( ii );
132 
133  if( !aLayerMask[ edge_zone->GetLayer() ] )
134  continue;
135 
136  itemplotter.PlotFilledAreas( edge_zone );
137  }
138 
139  aPlotter->EndBlock( NULL );
140 
141  // Plot segments used to fill zone areas (outdated, but here for old boards
142  // compatibility):
143  for( SEGZONE* seg = aBoard->m_Zone; seg; seg = seg->Next() )
144  {
145  if( !aLayerMask[ seg->GetLayer() ] )
146  continue;
147 
148  aPlotter->ThickSegment( seg->GetStart(), seg->GetEnd(), seg->GetWidth(),
149  itemplotter.GetPlotMode(), NULL );
150  }
151 }
152 
153 void PlotOneBoardLayer( BOARD *aBoard, PLOTTER* aPlotter, LAYER_ID aLayer,
154  const PCB_PLOT_PARAMS& aPlotOpt )
155 {
156  PCB_PLOT_PARAMS plotOpt = aPlotOpt;
157  int soldermask_min_thickness = aBoard->GetDesignSettings().m_SolderMaskMinWidth;
158 
159  // Set a default color and the text mode for this layer
160  aPlotter->SetColor( aPlotOpt.GetColor() );
161  aPlotter->SetTextMode( aPlotOpt.GetTextMode() );
162 
163  // Specify that the contents of the "Edges Pcb" layer are to be plotted
164  // in addition to the contents of the currently specified layer.
165  LSET layer_mask( aLayer );
166 
167  if( !aPlotOpt.GetExcludeEdgeLayer() )
168  layer_mask.set( Edge_Cuts );
169 
170  if( IsCopperLayer( aLayer ) )
171  {
172  // Skip NPTH pads on copper layers ( only if hole size == pad size ):
173  // Drill mark will be plotted,
174  // if drill mark is SMALL_DRILL_SHAPE or FULL_DRILL_SHAPE
175  if( plotOpt.GetFormat() == PLOT_FORMAT_DXF )
176  {
177  plotOpt.SetSkipPlotNPTH_Pads( false );
178  PlotLayerOutlines( aBoard, aPlotter, layer_mask, plotOpt );
179  }
180  else
181  {
182  plotOpt.SetSkipPlotNPTH_Pads( true );
183  PlotStandardLayer( aBoard, aPlotter, layer_mask, plotOpt );
184  }
185  }
186  else
187  {
188  switch( aLayer )
189  {
190  case B_Mask:
191  case F_Mask:
192  plotOpt.SetSkipPlotNPTH_Pads( false );
193  // Disable plot pad holes
195 
196  // Plot solder mask:
197  if( soldermask_min_thickness == 0 )
198  {
199  if( plotOpt.GetFormat() == PLOT_FORMAT_DXF )
200  PlotLayerOutlines( aBoard, aPlotter, layer_mask, plotOpt );
201  else
202  PlotStandardLayer( aBoard, aPlotter, layer_mask, plotOpt );
203  }
204  else
205  PlotSolderMaskLayer( aBoard, aPlotter, layer_mask, plotOpt,
206  soldermask_min_thickness );
207 
208  break;
209 
210  case B_Adhes:
211  case F_Adhes:
212  case B_Paste:
213  case F_Paste:
214  plotOpt.SetSkipPlotNPTH_Pads( false );
215  // Disable plot pad holes
217 
218  if( plotOpt.GetFormat() == PLOT_FORMAT_DXF )
219  PlotLayerOutlines( aBoard, aPlotter, layer_mask, plotOpt );
220  else
221  PlotStandardLayer( aBoard, aPlotter, layer_mask, plotOpt );
222  break;
223 
224  case F_SilkS:
225  case B_SilkS:
226  if( plotOpt.GetFormat() == PLOT_FORMAT_DXF )
227  PlotLayerOutlines( aBoard, aPlotter, layer_mask, plotOpt );
228  else
229  PlotSilkScreen( aBoard, aPlotter, layer_mask, plotOpt );
230 
231  // Gerber: Subtract soldermask from silkscreen if enabled
232  if( aPlotter->GetPlotterType() == PLOT_FORMAT_GERBER
233  && plotOpt.GetSubtractMaskFromSilk() )
234  {
235  if( aLayer == F_SilkS )
236  layer_mask = LSET( F_Mask );
237  else
238  layer_mask = LSET( B_Mask );
239 
240  // Create the mask to subtract by creating a negative layer polarity
241  aPlotter->SetLayerPolarity( false );
242 
243  // Disable plot pad holes
245 
246  // Plot the mask
247  PlotStandardLayer( aBoard, aPlotter, layer_mask, plotOpt );
248  }
249  break;
250 
251  // These layers are plotted like silk screen layers.
252  // Mainly, pads on these layers are not filled.
253  // This is not necessary the best choice.
254  case Dwgs_User:
255  case Cmts_User:
256  case Eco1_User:
257  case Eco2_User:
258  case Edge_Cuts:
259  case Margin:
260  case F_CrtYd:
261  case B_CrtYd:
262  case F_Fab:
263  case B_Fab:
264  plotOpt.SetSkipPlotNPTH_Pads( false );
266 
267  if( plotOpt.GetFormat() == PLOT_FORMAT_DXF )
268  PlotLayerOutlines( aBoard, aPlotter, layer_mask, plotOpt );
269  else
270  PlotSilkScreen( aBoard, aPlotter, layer_mask, plotOpt );
271  break;
272 
273  default:
274  plotOpt.SetSkipPlotNPTH_Pads( false );
276 
277  if( plotOpt.GetFormat() == PLOT_FORMAT_DXF )
278  PlotLayerOutlines( aBoard, aPlotter, layer_mask, plotOpt );
279  else
280  PlotStandardLayer( aBoard, aPlotter, layer_mask, plotOpt );
281  break;
282  }
283  }
284 }
285 
286 
287 /* Plot a copper layer or mask.
288  * Silk screen layers are not plotted here.
289  */
290 void PlotStandardLayer( BOARD *aBoard, PLOTTER* aPlotter,
291  LSET aLayerMask, const PCB_PLOT_PARAMS& aPlotOpt )
292 {
293  BRDITEMS_PLOTTER itemplotter( aPlotter, aBoard, aPlotOpt );
294 
295  itemplotter.SetLayerSet( aLayerMask );
296 
297  EDA_DRAW_MODE_T plotMode = aPlotOpt.GetPlotMode();
298 
299  // Plot edge layer and graphic items
300  itemplotter.PlotBoardGraphicItems();
301 
302  // Draw footprint shapes without pads (pads will plotted later)
303  // We plot here module texts, but they are usually on silkscreen layer,
304  // so they are not plot here but plot by PlotSilkScreen()
305  // Plot footprints fields (ref, value ...)
306  for( MODULE* module = aBoard->m_Modules; module; module = module->Next() )
307  {
308  if( ! itemplotter.PlotAllTextsModule( module ) )
309  {
310  wxLogMessage( _( "Your BOARD has a bad layer number for footprint %s" ),
311  GetChars( module->GetReference() ) );
312  }
313  }
314 
315  for( MODULE* module = aBoard->m_Modules; module; module = module->Next() )
316  {
317  for( BOARD_ITEM* item = module->GraphicalItems(); item; item = item->Next() )
318  {
319  if( !aLayerMask[ item->GetLayer() ] )
320  continue;
321 
322  switch( item->Type() )
323  {
324  case PCB_MODULE_EDGE_T:
325  itemplotter.Plot_1_EdgeModule( (EDGE_MODULE*) item );
326  break;
327 
328  default:
329  break;
330  }
331  }
332  }
333 
334  // Plot footprint pads
335  for( MODULE* module = aBoard->m_Modules; module; module = module->Next() )
336  {
337  aPlotter->StartBlock( NULL );
338 
339  for( D_PAD* pad = module->Pads(); pad; pad = pad->Next() )
340  {
341  if( (pad->GetLayerSet() & aLayerMask) == 0 )
342  continue;
343 
344  wxSize margin;
345  double width_adj = 0;
346 
347  if( ( aLayerMask & LSET::AllCuMask() ).any() )
348  width_adj = itemplotter.getFineWidthAdj();
349 
350  static const LSET speed( 4, B_Mask, F_Mask, B_Paste, F_Paste );
351 
352  LSET anded = ( speed & aLayerMask );
353 
354  if( anded == LSET( F_Mask ) || anded == LSET( B_Mask ) )
355  {
356  margin.x = margin.y = pad->GetSolderMaskMargin();
357  }
358  else if( anded == LSET( F_Paste ) || anded == LSET( B_Paste ) )
359  {
360  margin = pad->GetSolderPasteMargin();
361  }
362 
363  // Now offset the pad size by margin + width_adj
364  // this is easy for most shapes, but not for a trapezoid
365  wxSize padPlotsSize;
366  wxSize extraSize = margin * 2;
367  extraSize.x += width_adj;
368  extraSize.y += width_adj;
369  wxSize deltaSize = pad->GetDelta(); // has meaning only for trapezoidal pads
370 
371  if( pad->GetShape() == PAD_SHAPE_TRAPEZOID )
372  { // The easy way is to use BuildPadPolygon to calculate
373  // size and delta of the trapezoidal pad after offseting:
374  wxPoint coord[4];
375  pad->BuildPadPolygon( coord, extraSize/2, 0.0 );
376  // Calculate the size and delta from polygon corners coordinates:
377  // coord[0] is the lower left
378  // coord[1] is the upper left
379  // coord[2] is the upper right
380  // coord[3] is the lower right
381 
382  // the size is the distance between middle of segments
383  // (left/right or top/bottom)
384  // size X is the dist between left and right middle points:
385  padPlotsSize.x = ( ( -coord[0].x + coord[3].x ) // the lower segment X length
386  + ( -coord[1].x + coord[2].x ) ) // the upper segment X length
387  / 2; // the Y size is the half sum
388  // size Y is the dist between top and bottom middle points:
389  padPlotsSize.y = ( ( coord[0].y - coord[1].y ) // the left segment Y lenght
390  + ( coord[3].y - coord[2].y ) ) // the right segment Y lenght
391  / 2; // the Y size is the half sum
392 
393  // calculate the delta ( difference of lenght between 2 opposite edges )
394  // The delta.x is the delta along the X axis, therefore the delta of Y lenghts
395  wxSize delta;
396 
397  if( coord[0].y != coord[3].y )
398  delta.x = coord[0].y - coord[3].y;
399  else
400  delta.y = coord[1].x - coord[0].x;
401 
402  pad->SetDelta( delta );
403  }
404  else
405  padPlotsSize = pad->GetSize() + extraSize;
406 
407  // Don't draw a null size item :
408  if( padPlotsSize.x <= 0 || padPlotsSize.y <= 0 )
409  continue;
410 
411  COLOR4D color = COLOR4D::BLACK;
412 
413  if( pad->GetLayerSet()[B_Cu] )
414  color = aBoard->GetVisibleElementColor( PAD_BK_VISIBLE );
415 
416  if( pad->GetLayerSet()[F_Cu] )
417  color = color.LegacyMix( aBoard->GetVisibleElementColor( PAD_FR_VISIBLE ) );
418 
419  // Temporary set the pad size to the required plot size:
420  wxSize tmppadsize = pad->GetSize();
421  pad->SetSize( padPlotsSize );
422 
423  switch( pad->GetShape() )
424  {
425  case PAD_SHAPE_CIRCLE:
426  case PAD_SHAPE_OVAL:
427  if( aPlotOpt.GetSkipPlotNPTH_Pads() &&
428  (pad->GetSize() == pad->GetDrillSize()) &&
429  (pad->GetAttribute() == PAD_ATTRIB_HOLE_NOT_PLATED) )
430  break;
431 
432  // Fall through:
433  case PAD_SHAPE_TRAPEZOID:
434  case PAD_SHAPE_RECT:
435  case PAD_SHAPE_ROUNDRECT:
436  default:
437  itemplotter.PlotPad( pad, color, plotMode );
438  break;
439  }
440 
441  pad->SetSize( tmppadsize ); // Restore the pad size
442  pad->SetDelta( deltaSize );
443  }
444 
445  aPlotter->EndBlock( NULL );
446  }
447 
448  // Plot vias on copper layers, and if aPlotOpt.GetPlotViaOnMaskLayer() is true,
449  // plot them on solder mask
450 
451  GBR_METADATA gbr_metadata;
452 
453  bool isOnCopperLayer = ( aLayerMask & LSET::AllCuMask() ).any();
454 
455  if( isOnCopperLayer )
456  {
459  }
460 
461  aPlotter->StartBlock( NULL );
462 
463  for( TRACK* track = aBoard->m_Track; track; track = track->Next() )
464  {
465  const VIA* Via = dyn_cast<const VIA*>( track );
466 
467  if( !Via )
468  continue;
469 
470  // vias are not plotted if not on selected layer, but if layer
471  // is SOLDERMASK_LAYER_BACK or SOLDERMASK_LAYER_FRONT,vias are drawn,
472  // only if they are on the corresponding external copper layer
473  LSET via_mask_layer = Via->GetLayerSet();
474 
475  if( aPlotOpt.GetPlotViaOnMaskLayer() )
476  {
477  if( via_mask_layer[B_Cu] )
478  via_mask_layer.set( B_Mask );
479 
480  if( via_mask_layer[F_Cu] )
481  via_mask_layer.set( F_Mask );
482  }
483 
484  if( !( via_mask_layer & aLayerMask ).any() )
485  continue;
486 
487  int via_margin = 0;
488  double width_adj = 0;
489 
490  // If the current layer is a solder mask, use the global mask
491  // clearance for vias
492  if( aLayerMask[B_Mask] || aLayerMask[F_Mask] )
493  via_margin = aBoard->GetDesignSettings().m_SolderMaskMargin;
494 
495  if( ( aLayerMask & LSET::AllCuMask() ).any() )
496  width_adj = itemplotter.getFineWidthAdj();
497 
498  int diameter = Via->GetWidth() + 2 * via_margin + width_adj;
499 
500  // Don't draw a null size item :
501  if( diameter <= 0 )
502  continue;
503 
504  // Some vias can be not connected (no net).
505  // Set the m_NotInNet for these vias to force a empty net name in gerber file
506  gbr_metadata.m_NetlistMetadata.m_NotInNet = Via->GetNetname().IsEmpty();
507 
508  gbr_metadata.SetNetName( Via->GetNetname() );
509 
510  COLOR4D color = aBoard->GetVisibleElementColor( VIAS_VISIBLE + Via->GetViaType() );
511  // Set plot color (change WHITE to LIGHTGRAY because
512  // the white items are not seen on a white paper or screen
513  aPlotter->SetColor( color != WHITE ? color : LIGHTGRAY);
514  aPlotter->FlashPadCircle( Via->GetStart(), diameter, plotMode, &gbr_metadata );
515  }
516 
517  aPlotter->EndBlock( NULL );
518  aPlotter->StartBlock( NULL );
520 
521  // Plot tracks (not vias) :
522  for( TRACK* track = aBoard->m_Track; track; track = track->Next() )
523  {
524  if( track->Type() == PCB_VIA_T )
525  continue;
526 
527  if( !aLayerMask[track->GetLayer()] )
528  continue;
529 
530  // Some track segments can be not connected (no net).
531  // Set the m_NotInNet for these segments to force a empty net name in gerber file
532  gbr_metadata.m_NetlistMetadata.m_NotInNet = track->GetNetname().IsEmpty();
533 
534  gbr_metadata.SetNetName( track->GetNetname() );
535  int width = track->GetWidth() + itemplotter.getFineWidthAdj();
536  aPlotter->SetColor( itemplotter.getColor( track->GetLayer() ) );
537  aPlotter->ThickSegment( track->GetStart(), track->GetEnd(), width, plotMode, &gbr_metadata );
538  }
539 
540  aPlotter->EndBlock( NULL );
541 
542  // Plot zones (outdated, for old boards compatibility):
543  for( TRACK* track = aBoard->m_Zone; track; track = track->Next() )
544  {
545  if( !aLayerMask[track->GetLayer()] )
546  continue;
547 
548  int width = track->GetWidth() + itemplotter.getFineWidthAdj();
549  aPlotter->SetColor( itemplotter.getColor( track->GetLayer() ) );
550  aPlotter->ThickSegment( track->GetStart(), track->GetEnd(), width, plotMode, NULL );
551  }
552 
553  // Plot filled ares
554  aPlotter->StartBlock( NULL );
555  for( int ii = 0; ii < aBoard->GetAreaCount(); ii++ )
556  {
557  ZONE_CONTAINER* zone = aBoard->GetArea( ii );
558 
559  if( !aLayerMask[zone->GetLayer()] )
560  continue;
561 
562  itemplotter.PlotFilledAreas( zone );
563  }
564  aPlotter->EndBlock( NULL );
565 
566  // Adding drill marks, if required and if the plotter is able to plot them:
568  itemplotter.PlotDrillMarks();
569 }
570 
571 
572 // Seems like we want to plot from back to front?
573 static const LAYER_ID plot_seq[] = {
574 
575  B_Adhes, // 32
576  F_Adhes,
577  B_Paste,
578  F_Paste,
579  B_SilkS,
580  B_Mask,
581  F_Mask,
582  Dwgs_User,
583  Cmts_User,
584  Eco1_User,
585  Eco2_User,
586  Edge_Cuts,
587  Margin,
588 
589  F_CrtYd, // CrtYd & Body are footprint only
590  B_CrtYd,
591  F_Fab,
592  B_Fab,
593 
594  B_Cu,
595  In30_Cu,
596  In29_Cu,
597  In28_Cu,
598  In27_Cu,
599  In26_Cu,
600  In25_Cu,
601  In24_Cu,
602  In23_Cu,
603  In22_Cu,
604  In21_Cu,
605  In20_Cu,
606  In19_Cu,
607  In18_Cu,
608  In17_Cu,
609  In16_Cu,
610  In15_Cu,
611  In14_Cu,
612  In13_Cu,
613  In12_Cu,
614  In11_Cu,
615  In10_Cu,
616  In9_Cu,
617  In8_Cu,
618  In7_Cu,
619  In6_Cu,
620  In5_Cu,
621  In4_Cu,
622  In3_Cu,
623  In2_Cu,
624  In1_Cu,
625  F_Cu,
626 
627  F_SilkS,
628 };
629 
630 
631 /* Plot outlines of copper, for copper layer
632  */
633 void PlotLayerOutlines( BOARD* aBoard, PLOTTER* aPlotter,
634  LSET aLayerMask, const PCB_PLOT_PARAMS& aPlotOpt )
635 {
636 
637  BRDITEMS_PLOTTER itemplotter( aPlotter, aBoard, aPlotOpt );
638  itemplotter.SetLayerSet( aLayerMask );
639 
640  SHAPE_POLY_SET outlines;
641 
642  for( LSEQ seq = aLayerMask.Seq( plot_seq, DIM( plot_seq ) ); seq; ++seq )
643  {
644  LAYER_ID layer = *seq;
645 
646  outlines.RemoveAllContours();
647  aBoard->ConvertBrdLayerToPolygonalContours( layer, outlines );
648 
649  outlines.Simplify( SHAPE_POLY_SET::PM_FAST );
650 
651  // Plot outlines
652  std::vector< wxPoint > cornerList;
653 
654  // Now we have one or more basic polygons: plot each polygon
655  for( int ii = 0; ii < outlines.OutlineCount(); ii++ )
656  {
657  for(int kk = 0; kk <= outlines.HoleCount (ii); kk++ )
658  {
659  cornerList.clear();
660  const SHAPE_LINE_CHAIN& path = (kk == 0) ? outlines.COutline( ii ) : outlines.CHole( ii, kk - 1 );
661 
662  for( int jj = 0; jj < path.PointCount(); jj++ )
663  cornerList.push_back( wxPoint( path.CPoint( jj ).x , path.CPoint( jj ).y ) );
664 
665 
666  // Ensure the polygon is closed
667  if( cornerList[0] != cornerList[cornerList.size() - 1] )
668  cornerList.push_back( cornerList[0] );
669 
670  aPlotter->PlotPoly( cornerList, NO_FILL );
671  }
672  }
673 
674  // Plot pad holes
676  {
677  for( MODULE* module = aBoard->m_Modules; module; module = module->Next() )
678  {
679  for( D_PAD* pad = module->Pads(); pad; pad = pad->Next() )
680  {
681  wxSize hole = pad->GetDrillSize();
682 
683  if( hole.x == 0 || hole.y == 0 )
684  continue;
685 
686  if( hole.x == hole.y )
687  aPlotter->Circle( pad->GetPosition(), hole.x, NO_FILL );
688  else
689  {
690  wxPoint drl_start, drl_end;
691  int width;
692  pad->GetOblongDrillGeometry( drl_start, drl_end, width );
693  aPlotter->ThickSegment( pad->GetPosition() + drl_start,
694  pad->GetPosition() + drl_end, width, SKETCH, NULL );
695  }
696  }
697  }
698  }
699 
700  // Plot vias holes
701  for( TRACK* track = aBoard->m_Track; track; track = track->Next() )
702  {
703  const VIA* via = dyn_cast<const VIA*>( track );
704 
705  if( via && via->IsOnLayer( layer ) ) // via holes can be not through holes
706  {
707  aPlotter->Circle( via->GetPosition(), via->GetDrillValue(), NO_FILL );
708  }
709  }
710  }
711 }
712 
713 
714 /* Plot a solder mask layer.
715  * Solder mask layers have a minimum thickness value and cannot be drawn like standard layers,
716  * unless the minimum thickness is 0.
717  * Currently the algo is:
718  * 1 - build all pad shapes as polygons with a size inflated by
719  * mask clearance + (min width solder mask /2)
720  * 2 - Merge shapes
721  * 3 - deflate result by (min width solder mask /2)
722  * 4 - ORing result by all pad shapes as polygons with a size inflated by
723  * mask clearance only (because deflate sometimes creates shape artifacts)
724  * 5 - draw result as polygons
725  *
726  * TODO:
727  * make this calculation only for shapes with clearance near than (min width solder mask)
728  * (using DRC algo)
729  * plot all other shapes by flashing the basing shape
730  * (shapes will be better, and calculations faster)
731  */
732 void PlotSolderMaskLayer( BOARD *aBoard, PLOTTER* aPlotter,
733  LSET aLayerMask, const PCB_PLOT_PARAMS& aPlotOpt,
734  int aMinThickness )
735 {
736  LAYER_ID layer = aLayerMask[B_Mask] ? B_Mask : F_Mask;
737  int inflate = aMinThickness/2;
738 
739  BRDITEMS_PLOTTER itemplotter( aPlotter, aBoard, aPlotOpt );
740  itemplotter.SetLayerSet( aLayerMask );
741 
742  // Plot edge layer and graphic items
743  // They do not have a solder Mask margin, because they are only graphic items
744  // on this layer (like logos), not actually areas around pads.
745  itemplotter.PlotBoardGraphicItems();
746 
747  for( MODULE* module = aBoard->m_Modules; module; module = module->Next() )
748  {
749  for( BOARD_ITEM* item = module->GraphicalItems(); item; item = item->Next() )
750  {
751  if( layer != item->GetLayer() )
752  continue;
753 
754  switch( item->Type() )
755  {
756  case PCB_MODULE_EDGE_T:
757  itemplotter.Plot_1_EdgeModule( (EDGE_MODULE*) item );
758  break;
759 
760  default:
761  break;
762  }
763  }
764  }
765 
766  // Build polygons for each pad shape.
767  // the size of the shape on solder mask should be:
768  // size of pad + clearance around the pad.
769  // clearance = solder mask clearance + extra margin
770  // extra margin is half the min width for solder mask
771  // This extra margin is used to merge too close shapes
772  // (distance < aMinThickness), and will be removed when creating
773  // the actual shapes
774  SHAPE_POLY_SET areas; // Contains shapes to plot
775  SHAPE_POLY_SET initialPolys; // Contains exact shapes to plot
776 
777  /* calculates the coeff to compensate radius reduction of holes clearance
778  * due to the segment approx ( 1 /cos( PI/circleToSegmentsCount )
779  */
780  int circleToSegmentsCount = 32;
781  double correction = 1.0 / cos( M_PI / circleToSegmentsCount );
782 
783  // Plot pads
784  for( MODULE* module = aBoard->m_Modules; module; module = module->Next() )
785  {
786  // add shapes with exact size
787  module->TransformPadsShapesWithClearanceToPolygon( layer,
788  initialPolys, 0,
789  circleToSegmentsCount, correction );
790  // add shapes inflated by aMinThickness/2
791  module->TransformPadsShapesWithClearanceToPolygon( layer,
792  areas, inflate,
793  circleToSegmentsCount, correction );
794  }
795 
796  // Plot vias on solder masks, if aPlotOpt.GetPlotViaOnMaskLayer() is true,
797  if( aPlotOpt.GetPlotViaOnMaskLayer() )
798  {
799  // The current layer is a solder mask,
800  // use the global mask clearance for vias
801  int via_clearance = aBoard->GetDesignSettings().m_SolderMaskMargin;
802  int via_margin = via_clearance + inflate;
803 
804  for( TRACK* track = aBoard->m_Track; track; track = track->Next() )
805  {
806  const VIA* via = dyn_cast<const VIA*>( track );
807 
808  if( !via )
809  continue;
810 
811  // vias are plotted only if they are on the corresponding
812  // external copper layer
813  LSET via_set = via->GetLayerSet();
814 
815  if( via_set[B_Cu] )
816  via_set.set( B_Mask );
817 
818  if( via_set[F_Cu] )
819  via_set.set( F_Mask );
820 
821  if( !( via_set & aLayerMask ).any() )
822  continue;
823 
824  via->TransformShapeWithClearanceToPolygon( areas, via_margin,
825  circleToSegmentsCount,
826  correction );
827  via->TransformShapeWithClearanceToPolygon( initialPolys, via_clearance,
828  circleToSegmentsCount,
829  correction );
830  }
831  }
832 
833  // Add filled zone areas.
834 #if 0 // Set to 1 if a solder mask margin must be applied to zones on solder mask
835  int zone_margin = aBoard->GetDesignSettings().m_SolderMaskMargin;
836 #else
837  int zone_margin = 0;
838 #endif
839 
840  for( int ii = 0; ii < aBoard->GetAreaCount(); ii++ )
841  {
842  ZONE_CONTAINER* zone = aBoard->GetArea( ii );
843 
844  if( zone->GetLayer() != layer )
845  continue;
846 
848  inflate+zone_margin, false );
850  zone_margin, false );
851  }
852 
853  // To avoid a lot of code, use a ZONE_CONTAINER
854  // to handle and plot polygons, because our polygons look exactly like
855  // filled areas in zones
856  // Note, also this code is not optimized: it creates a lot of copy/duplicate data
857  // However it is not complex, and fast enough for plot purposes (copy/convert data
858  // is only a very small calculation time for these calculations)
859  ZONE_CONTAINER zone( aBoard );
860  zone.SetArcSegmentCount( 32 );
861  zone.SetMinThickness( 0 ); // trace polygons only
862  zone.SetLayer ( layer );
863 
864  areas.BooleanAdd( initialPolys, SHAPE_POLY_SET::PM_FAST );
865  areas.Inflate( -inflate, circleToSegmentsCount );
866 
867  // Combine the current areas to initial areas. This is mandatory because
868  // inflate/deflate transform is not perfect, and we want the initial areas perfectly kept
869  areas.BooleanAdd( initialPolys, SHAPE_POLY_SET::PM_FAST );
871 
872  zone.AddFilledPolysList( areas );
873 
874  itemplotter.PlotFilledAreas( &zone );
875 }
876 
877 
878 
884 static void initializePlotter( PLOTTER *aPlotter, BOARD * aBoard,
885  PCB_PLOT_PARAMS *aPlotOpts )
886 {
887  PAGE_INFO pageA4( wxT( "A4" ) );
888  const PAGE_INFO& pageInfo = aBoard->GetPageSettings();
889  const PAGE_INFO* sheet_info;
890  double paperscale; // Page-to-paper ratio
891  wxSize paperSizeIU;
892  wxSize pageSizeIU( pageInfo.GetSizeIU() );
893  bool autocenter = false;
894 
895  /* Special options: to fit the sheet to an A4 sheet replace
896  the paper size. However there is a difference between
897  the autoscale and the a4paper option:
898  - Autoscale fits the board to the paper size
899  - A4paper fits the original paper size to an A4 sheet
900  - Both of them fit the board to an A4 sheet
901  */
902  if( aPlotOpts->GetA4Output() ) // Fit paper to A4
903  {
904  sheet_info = &pageA4;
905  paperSizeIU = pageA4.GetSizeIU();
906  paperscale = (double) paperSizeIU.x / pageSizeIU.x;
907  autocenter = true;
908  }
909  else
910  {
911  sheet_info = &pageInfo;
912  paperSizeIU = pageSizeIU;
913  paperscale = 1;
914 
915  // Need autocentering only if scale is not 1:1
916  autocenter = (aPlotOpts->GetScale() != 1.0);
917  }
918 
919  EDA_RECT bbox = aBoard->ComputeBoundingBox();
920  wxPoint boardCenter = bbox.Centre();
921  wxSize boardSize = bbox.GetSize();
922 
923  double compound_scale;
924 
925  /* Fit to 80% of the page if asked; it could be that the board is empty,
926  * in this case regress to 1:1 scale */
927  if( aPlotOpts->GetAutoScale() && boardSize.x > 0 && boardSize.y > 0 )
928  {
929  double xscale = (paperSizeIU.x * 0.8) / boardSize.x;
930  double yscale = (paperSizeIU.y * 0.8) / boardSize.y;
931 
932  compound_scale = std::min( xscale, yscale ) * paperscale;
933  }
934  else
935  compound_scale = aPlotOpts->GetScale() * paperscale;
936 
937 
938  /* For the plot offset we have to keep in mind the auxiliary origin
939  too: if autoscaling is off we check that plot option (i.e. autoscaling
940  overrides auxiliary origin) */
941  wxPoint offset( 0, 0);
942 
943  if( autocenter )
944  {
945  offset.x = KiROUND( boardCenter.x - ( paperSizeIU.x / 2.0 ) / compound_scale );
946  offset.y = KiROUND( boardCenter.y - ( paperSizeIU.y / 2.0 ) / compound_scale );
947  }
948  else
949  {
950  if( aPlotOpts->GetUseAuxOrigin() )
951  offset = aBoard->GetAuxOrigin();
952  }
953 
954  /* Configure the plotter object with all the stuff computed and
955  most of that taken from the options */
956  aPlotter->SetPageSettings( *sheet_info );
957 
958  aPlotter->SetViewport( offset, IU_PER_MILS/10, compound_scale,
959  aPlotOpts->GetMirror() );
960  // has meaning only for gerber plotter. Must be called only after SetViewport
961  aPlotter->SetGerberCoordinatesFormat( aPlotOpts->GetGerberPrecision() );
962 
963  aPlotter->SetDefaultLineWidth( aPlotOpts->GetLineWidth() );
964  aPlotter->SetCreator( wxT( "PCBNEW" ) );
965  aPlotter->SetColorMode( false ); // default is plot in Black and White.
966  aPlotter->SetTextMode( aPlotOpts->GetTextMode() );
967 }
968 
971 static void FillNegativeKnockout( PLOTTER *aPlotter, const EDA_RECT &aBbbox )
972 {
973  const int margin = 5 * IU_PER_MM; // Add a 5 mm margin around the board
974  aPlotter->SetNegative( true );
975  aPlotter->SetColor( WHITE ); // Which will be plotted as black
976  EDA_RECT area = aBbbox;
977  area.Inflate( margin );
978  aPlotter->Rect( area.GetOrigin(), area.GetEnd(), FILLED_SHAPE );
979  aPlotter->SetColor( BLACK );
980 }
981 
984 static void ConfigureHPGLPenSizes( HPGL_PLOTTER *aPlotter,
985  PCB_PLOT_PARAMS *aPlotOpts )
986 {
987  /* Compute pen_dim (the value is given in mils) in pcb units,
988  with plot scale (if Scale is 2, pen diameter value is always m_HPGLPenDiam
989  so apparent pen diam is actually pen diam / Scale */
990  int pen_diam = KiROUND( aPlotOpts->GetHPGLPenDiameter() * IU_PER_MILS /
991  aPlotOpts->GetScale() );
992 
993  // Set HPGL-specific options and start
994  aPlotter->SetPenSpeed( aPlotOpts->GetHPGLPenSpeed() );
995  aPlotter->SetPenNumber( aPlotOpts->GetHPGLPenNum() );
996  aPlotter->SetPenDiameter( pen_diam );
997 }
998 
1005  int aLayer,
1006  const wxString& aFullFileName,
1007  const wxString& aSheetDesc )
1008 {
1009  // Create the plotter driver and set the few plotter specific
1010  // options
1011  PLOTTER* plotter = NULL;
1012 
1013  switch( aPlotOpts->GetFormat() )
1014  {
1015  case PLOT_FORMAT_DXF:
1016  plotter = new DXF_PLOTTER();
1017  break;
1018 
1019  case PLOT_FORMAT_POST:
1020  PS_PLOTTER* PS_plotter;
1021  PS_plotter = new PS_PLOTTER();
1022  PS_plotter->SetScaleAdjust( aPlotOpts->GetFineScaleAdjustX(),
1023  aPlotOpts->GetFineScaleAdjustY() );
1024  plotter = PS_plotter;
1025  break;
1026 
1027  case PLOT_FORMAT_PDF:
1028  plotter = new PDF_PLOTTER();
1029  break;
1030 
1031  case PLOT_FORMAT_HPGL:
1032  HPGL_PLOTTER* HPGL_plotter;
1033  HPGL_plotter = new HPGL_PLOTTER();
1034 
1035  /* HPGL options are a little more convoluted to compute, so
1036  they're split in an other function */
1037  ConfigureHPGLPenSizes( HPGL_plotter, aPlotOpts );
1038  plotter = HPGL_plotter;
1039  break;
1040 
1041  case PLOT_FORMAT_GERBER:
1042  plotter = new GERBER_PLOTTER();
1043  break;
1044 
1045  case PLOT_FORMAT_SVG:
1046  plotter = new SVG_PLOTTER();
1047  break;
1048 
1049  default:
1050  wxASSERT( false );
1051  return NULL;
1052  }
1053 
1054  // Compute the viewport and set the other options
1055 
1056  // page layout is not mirrored, so temporary change mirror option
1057  // just to plot the page layout
1058  PCB_PLOT_PARAMS plotOpts = *aPlotOpts;
1059 
1060  if( plotOpts.GetPlotFrameRef() && plotOpts.GetMirror() )
1061  plotOpts.SetMirror( false );
1062 
1063  initializePlotter( plotter, aBoard, &plotOpts );
1064 
1065  if( plotter->OpenFile( aFullFileName ) )
1066  {
1067  plotter->ClearHeaderLinesList();
1068 
1069  // For the Gerber "file function" attribute, set the layer number
1070  if( plotter->GetPlotterType() == PLOT_FORMAT_GERBER )
1071  {
1072  bool useX2mode = plotOpts.GetUseGerberAttributes();
1073 
1074  if( useX2mode )
1075  {
1076  AddGerberX2Attribute( plotter, aBoard, aLayer, false );
1077  GERBER_PLOTTER* gbrplotter = static_cast <GERBER_PLOTTER*> ( plotter );
1078  gbrplotter->UseX2Attributes( true );
1079  gbrplotter->UseX2NetAttributes( plotOpts.GetIncludeGerberNetlistInfo() );
1080  }
1081  else
1082  {
1083  AddGerberX2Attribute( plotter, aBoard, aLayer, true );
1084  }
1085  }
1086 
1087  plotter->StartPlot();
1088 
1089  // Plot the frame reference if requested
1090  if( aPlotOpts->GetPlotFrameRef() )
1091  {
1092  PlotWorkSheet( plotter, aBoard->GetTitleBlock(),
1093  aBoard->GetPageSettings(),
1094  1, 1, // Only one page
1095  aSheetDesc, aBoard->GetFileName() );
1096 
1097  if( aPlotOpts->GetMirror() )
1098  initializePlotter( plotter, aBoard, aPlotOpts );
1099  }
1100 
1101  /* When plotting a negative board: draw a black rectangle
1102  * (background for plot board in white) and switch the current
1103  * color to WHITE; note the color inversion is actually done
1104  * in the driver (if supported) */
1105  if( aPlotOpts->GetNegative() )
1106  {
1107  EDA_RECT bbox = aBoard->ComputeBoundingBox();
1108  FillNegativeKnockout( plotter, bbox );
1109  }
1110 
1111  return plotter;
1112  }
1113 
1114  delete plotter;
1115  return NULL;
1116 }
static LSET AllCuMask(int aCuLayerCount=MAX_CU_LAYERS)
Function AllCuMask returns a mask holding the requested number of Cu LAYER_IDs.
Definition: lset.cpp:638
#define DIM(x)
of elements in an array
Definition: macros.h:98
int m_SolderMaskMargin
Solder mask margin.
bool GetMirror() const
Class ZONE_CONTAINER handles a list of polygons defining a copper zone.
Definition: class_zone.h:78
bool GetSubtractMaskFromSilk() const
bool IsOnLayer(LAYER_ID aLayer) const override
Function IsOnLayer tests to see if this object is on the given layer.
bool GetAutoScale() const
int GetHPGLPenDiameter() const
virtual void SetCreator(const wxString &aCreator)
Definition: plot_common.h:151
double GetScale() const
PCB_TARGET class definition.
static const LAYER_ID plot_seq[]
void UseX2NetAttributes(bool aEnable)
Definition: plot_common.h:1112
virtual void EndBlock(void *aData)
calling this function allows to define the end of a group of drawing items for instance in SVG or Ger...
Definition: plot_common.h:436
TEXTE_PCB class definition.
virtual LSET GetLayerSet() const override
Function GetLayerSet returns a "layer mask", which is a bitmap of all layers on which the TRACK segme...
static int KiROUND(double v)
KiROUND rounds a floating point number to an int using "round halfway cases away from zero"...
Definition: common.h:107
like PAD_STANDARD, but not plated mechanical use only, no connection allowed
Definition: pad_shapes.h:63
static void initializePlotter(PLOTTER *aPlotter, BOARD *aBoard, PCB_PLOT_PARAMS *aPlotOpts)
Set up most plot options for plotting a board (especially the viewport) Important thing: page size is...
void BooleanAdd(const SHAPE_POLY_SET &b, POLYGON_MODE aFastMode)
Performs boolean polyset union For aFastMode meaning, see function booleanOp
virtual bool StartPlot()=0
Class BOARD_ITEM is a base class for any item which can be embedded within the BOARD container class...
void ConvertBrdLayerToPolygonalContours(LAYER_ID aLayer, SHAPE_POLY_SET &aOutlines)
Function ConvertBrdLayerToPolygonalContours Build a set of polygons which are the outlines of copper ...
virtual void SetColor(COLOR4D color)=0
static void FillNegativeKnockout(PLOTTER *aPlotter, const EDA_RECT &aBbbox)
Prefill in black an area a little bigger than the board to prepare for the negative plot...
bool GetUseGerberAttributes() const
int PointCount() const
Function PointCount()
EDA_RECT ComputeBoundingBox(bool aBoardEdgesOnly=false) const
Function ComputeBoundingBox calculates the bounding box containing all board items (or board edge seg...
void PlotPad(D_PAD *aPad, COLOR4D aColor, EDA_DRAW_MODE_T aPlotMode)
Plot a pad.
virtual bool OpenFile(const wxString &aFullFilename)
Open or create the plot file aFullFilename.
void SetNetAttribType(int aNetAttribType)
Class BOARD to handle a board.
void SetScaleAdjust(double scaleX, double scaleY)
Set the 'fine' scaling for the postscript engine.
Definition: plot_common.h:663
virtual void SetLayerPolarity(bool aPositive)
Function SetLayerPolarity sets current Gerber layer polarity to positive or negative by writing %LPD*...
Definition: plot_common.h:401
void PlotStandardLayer(BOARD *aBoard, PLOTTER *aPlotter, LSET aLayerMask, const PCB_PLOT_PARAMS &aPlotOpt)
Function PlotStandardLayer plot copper or technical layers.
LSEQ Seq(const LAYER_ID *aWishListSequence, unsigned aCount) const
Function Seq returns an LSEQ from the union of this LSET and a desired sequence.
Definition: lset.cpp:336
COLOR4D GetLayerColor(LAYER_ID aLayer) const
Function GetLayerColor gets a layer color for any valid layer, including non-copper ones...
virtual void SetLayer(LAYER_ID aLayer)
Function SetLayer sets the layer this item is on.
MODULE * Next() const
Definition: class_module.h:99
void PlotSilkScreen(BOARD *aBoard, PLOTTER *aPlotter, LSET aLayerMask, const PCB_PLOT_PARAMS &aPlotOpt)
Function PlotSilkScreen plot silkscreen layers which have specific requirements, mainly for pads...
int HoleCount(int aOutline) const
Returns the number of holes in a given outline
void PlotDrillMarks()
Function PlotDrillMarks Draw a drill mark for pads and vias.
void SetMirror(bool aFlag)
virtual void SetPenDiameter(double diameter)
virtual void StartBlock(void *aData)
calling this function allows to define the beginning of a group of drawing items, for instance in SVG...
Definition: plot_common.h:427
bool PlotAllTextsModule(MODULE *aModule)
Classes to handle copper zones.
DLIST< SEGZONE > m_Zone
Definition: class_board.h:245
void SetArcSegmentCount(int aArcSegCount)
Definition: class_zone.h:197
void AddGerberX2Attribute(PLOTTER *aPlotter, const BOARD *aBoard, LAYER_NUM aLayer, bool aUseX1CompatibilityMode)
Function AddGerberX2Attribute Calculates some X2 attributes, as defined in the Gerber file format spe...
Definition: pcbplot.cpp:272
const SHAPE_LINE_CHAIN & CHole(int aOutline, int aHole) const
bool GetUseAuxOrigin() const
int OutlineCount() const
Returns the number of outlines in the set
void SetDrillMarksType(DrillMarksType aVal)
virtual void PlotPoly(const std::vector< wxPoint > &aCornerList, FILL_T aFill, int aWidth=USE_DEFAULT_LINE_WIDTH, void *aData=NULL)=0
Function PlotPoly.
virtual void SetPageSettings(const PAGE_INFO &aPageSettings)
LAYER_ID GetLayer() const
Function GetLayer returns the primary layer this item is on.
void AddFilledPolysList(SHAPE_POLY_SET &aPolysList)
Function AddFilledPolysList sets the list of filled polygons.
Definition: class_zone.h:596
void TransformOutlinesShapeWithClearanceToPolygon(SHAPE_POLY_SET &aCornerBuffer, int aMinClearanceValue, bool aUseNetClearance)
Function TransformOutlinesShapeWithClearanceToPolygon Convert the outlines shape to a polygon with no...
class EDGE_MODULE, a footprint edge
Definition: typeinfo.h:106
static const int delta[8][2]
Definition: solve.cpp:112
Casted dyn_cast(From aObject)
Function dyn_cast()
Definition: typeinfo.h:73
double GetFineScaleAdjustX() const
virtual void SetGerberCoordinatesFormat(int aResolution, bool aUseInches=false)
Definition: plot_common.h:415
void PlotWorkSheet(PLOTTER *plotter, const TITLE_BLOCK &aTitleBlock, const PAGE_INFO &aPageInfo, int aSheetNumber, int aNumberOfSheets, const wxString &aSheetDesc, const wxString &aFilename)
Functions relatives to tracks, vias and segments used to fill zones.
This file contains miscellaneous commonly used macros and functions.
bool GetA4Output() const
void PlotFilledAreas(ZONE_CONTAINER *aZone)
SEGZONE * Next() const
Definition: class_track.h:362
bool GetExcludeEdgeLayer() const
Board plot function definition file.
static void PlotSolderMaskLayer(BOARD *aBoard, PLOTTER *aPlotter, LSET aLayerMask, const PCB_PLOT_PARAMS &aPlotOpt, int aMinThickness)
BOARD_ITEM * Next() const
const wxPoint & GetOrigin() const
DIMENSION class definition.
virtual void FlashPadCircle(const wxPoint &aPadPos, int aDiameter, EDA_DRAW_MODE_T aTraceMode, void *aData)=0
virtual function FlashPadCircle
void PlotLayerOutlines(BOARD *aBoard, PLOTTER *aPlotter, LSET aLayerMask, const PCB_PLOT_PARAMS &aPlotOpt)
Function PlotLayerOutlines plot copper outline of a copper layer.
DrillMarksType GetDrillMarksType() const
bool GetIncludeGerberNetlistInfo() const
Class LSET is a set of LAYER_IDs.
Classes used in Pcbnew, CvPcb and GerbView.
void SetLayerSet(LSET aLayerMask)
Definition: pcbplot.h:104
void Inflate(int aFactor, int aCircleSegmentsCount)
Performs outline inflation/deflation, using round corners.
int GetLineWidth() const
VIATYPE_T GetViaType() const
Definition: class_track.h:442
int GetHPGLPenNum() const
const wxString & GetFileName() const
Definition: class_board.h:237
Class SHAPE_POLY_SET.
EDA_DRAW_MODE_T
Definition: eda_text.h:62
PlotTextMode GetTextMode() const
Class PAGE_INFO describes the page size and margins of a paper page on which to eventually print or p...
void PlotBoardGraphicItems()
plot items like text and graphics, but not tracks and modules
virtual void SetTextMode(PlotTextMode mode)
Change the current text mode.
Definition: plot_common.h:410
const wxPoint & GetStart() const
Definition: class_track.h:120
virtual void SetPenSpeed(int speed)
Definition: plot_common.h:586
void Plot_1_EdgeModule(EDGE_MODULE *aEdge)
D_PAD * Next() const
Definition: class_pad.h:106
void SetSkipPlotNPTH_Pads(bool aSkip)
BOARD_DESIGN_SETTINGS & GetDesignSettings() const
Function GetDesignSettings.
Definition: class_board.h:530
bool GetPlotViaOnMaskLayer() const
const SHAPE_LINE_CHAIN & COutline(int aIndex) const
Common plot library Plot settings, and plotting engines (Postscript, Gerber, HPGL and DXF) ...
void Simplify(POLYGON_MODE aFastMode)
Simplifies the polyset (merges overlapping polys, eliminates degeneracy/self-intersections) For aFast...
int GetAreaCount() const
Function GetAreaCount.
Definition: class_board.h:1051
static void ConfigureHPGLPenSizes(HPGL_PLOTTER *aPlotter, PCB_PLOT_PARAMS *aPlotOpts)
Calculate the effective size of HPGL pens and set them in the plotter object.
wxPoint Centre() const
PlotFormat GetFormat() const
Class PCB_PLOT_PARAMS handles plot parameters and options when plotting/printing a board...
void TransformShapeWithClearanceToPolygon(SHAPE_POLY_SET &aCornerBuffer, int aClearanceValue, int aCircleToSegmentsCount, double aCorrectionFactor) const
Function TransformShapeWithClearanceToPolygon Convert the track shape to a closed polygon Used in fil...
PLOTTER * StartPlotBoard(BOARD *aBoard, PCB_PLOT_PARAMS *aPlotOpts, int aLayer, const wxString &aFullFileName, const wxString &aSheetDesc)
Open a new plotfile using the options (and especially the format) specified in the options and prepar...
void Fracture(POLYGON_MODE aFastMode)
Converts a set of polygons with holes to a singe outline with "slits"/"fractures" connecting the oute...
Class LSEQ is a sequence (and therefore also a set) of LAYER_IDs.
const PAGE_INFO & GetPageSettings() const
Definition: class_board.h:545
COLOR4D GetColor() const
virtual void SetViewport(const wxPoint &aOffset, double aIusPerDecimil, double aScale, bool aMirror)=0
Set the plot offset and scaling for the current plot.
aperture used for connected items like tracks (not vias)
const wxPoint GetEnd() const
virtual void SetDefaultLineWidth(int width)=0
Set the default line width.
const wxPoint & GetAuxOrigin() const
Definition: class_board.h:332
void SetNetName(const wxString &aNetname)
Base plotter engine class.
Definition: plot_common.h:86
bool GetSkipPlotNPTH_Pads() const
TRACK * Next() const
Definition: class_track.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:92
TITLE_BLOCK & GetTitleBlock()
Definition: class_board.h:551
const wxString & GetNetname() const
Function GetNetname.
ZONE_CONTAINER * GetArea(int index) const
Function GetArea returns the Area (Zone Container) at a given index.
Definition: class_board.h:1022
Class to handle a graphic segment.
int GetDrillValue() const
Function GetDrillValue "calculates" the drill value for vias (m-Drill if > 0, or default drill value ...
Class BOARD holds information pertinent to a Pcbnew printed circuit board.
Definition: class_board.h:166
LAYER_ID
Enum LAYER_ID is the set of PCB layers.
DLIST< MODULE > m_Modules
Definition: class_board.h:243
Class SHAPE_LINE_CHAIN.
bool GetNegative() const
int GetWidth() const
Definition: class_track.h:114
virtual PlotFormat GetPlotterType() const =0
Returns the effective plot engine in use.
virtual void ThickSegment(const wxPoint &start, const wxPoint &end, int width, EDA_DRAW_MODE_T tracemode, void *aData)
COLOR4D GetVisibleElementColor(int aPCB_VISIBLE)
Function GetVisibleElementColor returns the color of a pcb visible element.
bool GetPlotFrameRef() const
virtual void SetPenNumber(int number)
Definition: plot_common.h:591
void RemoveAllContours()
Removes all outlines & holes (clears) the polygon set.
int GetHPGLPenSpeed() const
EDA_DRAW_MODE_T GetPlotMode() const
Class EDA_RECT handles the component boundary box.
bool GetPlotPadsOnSilkLayer() const
The common library.
virtual void Rect(const wxPoint &p1, const wxPoint &p2, FILL_T fill, int width=USE_DEFAULT_LINE_WIDTH)=0
const wxPoint & GetPosition() const override
Definition: class_track.h:415
void ClearHeaderLinesList()
Function ClearHeaderLinesList remove all lines from the list of free lines to print at the beginning ...
Definition: plot_common.h:175
Definition: colors.h:49
bool IsCopperLayer(LAYER_NUM aLayerId)
Function IsCopperLayer tests whether a layer is a copper layer.
This file is part of the common libary.
void SetApertureAttrib(GBR_APERTURE_METADATA::GBR_APERTURE_ATTRIB aApertAttribute)
bool m_NotInNet
true if a pad of a footprint cannot be connected (for instance a mechanical NPTH, ot a not named pad)...
class VIA, a via (like a track segment on a copper layer)
Definition: typeinfo.h:108
int getFineWidthAdj()
Definition: pcbplot.h:95
DLIST< TRACK > m_Track
Definition: class_board.h:244
GBR_NETLIST_METADATA m_NetlistMetadata
Module description (excepted pads)
Definition: colors.h:45
Basic classes for most KiCad items.
EDGE_MODULE class definition.
void SetMinThickness(int aMinThickness)
Definition: class_zone.h:210
const wxSize & GetSize() const
const VECTOR2I & CPoint(int aIndex) const
Function CPoint()
print info associated to a net (TO.N attribute)
void PlotOneBoardLayer(BOARD *aBoard, PLOTTER *aPlotter, LAYER_ID aLayer, const PCB_PLOT_PARAMS &aPlotOpt)
Function PlotOneBoardLayer main function to plot one copper or technical layer.
void UseX2Attributes(bool aEnable)
Definition: plot_common.h:1111
COLOR4D getColor(LAYER_NUM aLayer)
Function getColor.
virtual void SetNegative(bool _negative)
Definition: plot_common.h:111
virtual void Circle(const wxPoint &pos, int diametre, FILL_T fill, int width=USE_DEFAULT_LINE_WIDTH)=0
virtual void SetColorMode(bool _color_mode)
Definition: plot_common.h:116
double GetFineScaleAdjustY() const
EDA_RECT & Inflate(wxCoord dx, wxCoord dy)
Function Inflate inflates the rectangle horizontally by dx and vertically by dy.
int m_SolderMaskMinWidth
Solder mask min width.
#define min(a, b)
Definition: auxiliary.h:85
Class COLOR4D is the color representation with 4 components: red, green, blue, alpha.
Definition: color4d.h:39
int GetGerberPrecision() const