1 /*
2  * This program source code file is part of KiCad, a free EDA CAD application.
3  *
4  * Copyright (C) 2016-2021 KiCad Developers, see AUTHORS.txt for contributors.
5  *
6  * This program is free software: you can redistribute it and/or modify it
7  * under the terms of the GNU General Public License as published by the
8  * Free Software Foundation, either version 3 of the License, or (at your
9  * option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful, but
12  * WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License along
17  * with this program.  If not, see <http://www.gnu.org/licenses/>.
18  */
19 
20 /**
21  * Plotting engine (DXF)
22  *
23  * @file plotter_dxf.h
24  */
25 
26 #pragma once
27 
28 #include "plotter.h"
29 
30 
31 class DXF_PLOTTER : public PLOTTER
32 {
33 public:
DXF_PLOTTER()34     DXF_PLOTTER() : m_textAsLines( false )
35     {
36         m_textAsLines = true;
37         m_currentColor = COLOR4D::BLACK;
38         m_currentLineType = PLOT_DASH_TYPE::SOLID;
39         SetUnits( DXF_UNITS::INCHES );
40     }
41 
GetPlotterType()42     virtual PLOT_FORMAT GetPlotterType() const override
43     {
44         return PLOT_FORMAT::DXF;
45     }
46 
GetDefaultFileExtension()47     static wxString GetDefaultFileExtension()
48     {
49         return wxString( wxT( "dxf" ) );
50     }
51 
52     /**
53      * DXF handles NATIVE text emitting TEXT entities
54      */
SetTextMode(PLOT_TEXT_MODE mode)55     virtual void SetTextMode( PLOT_TEXT_MODE mode ) override
56     {
57         if( mode != PLOT_TEXT_MODE::DEFAULT )
58             m_textAsLines = ( mode != PLOT_TEXT_MODE::NATIVE );
59     }
60 
61     /**
62      * Open the DXF plot with a skeleton header.
63      */
64     virtual bool StartPlot() override;
65     virtual bool EndPlot() override;
66 
67     // For now we don't use 'thick' primitives, so no line width
68     virtual void SetCurrentLineWidth( int width, void* aData = nullptr ) override
69     {
70         m_currentPenWidth = 0;
71     }
72 
73     virtual void SetDash( PLOT_DASH_TYPE dashed ) override;
74 
75     /**
76      * The DXF exporter handles 'colors' as layers...
77      */
78     virtual void SetColor( const COLOR4D& color ) override;
79 
80     /**
81      * Set the scale/position for the DXF plot.
82      *
83      * The DXF engine doesn't support line widths and mirroring. The output
84      * coordinate system is in the first quadrant (in mm).
85      */
86     virtual void SetViewport( const wxPoint& aOffset, double aIusPerDecimil,
87                               double aScale, bool aMirror ) override;
88 
89     /**
90      * DXF rectangle: fill not supported.
91      */
92     virtual void Rect( const wxPoint& p1, const wxPoint& p2, FILL_T fill,
93                        int width = USE_DEFAULT_LINE_WIDTH ) override;
94 
95     /**
96      * DXF circle: full functionality; it even does 'fills' drawing a
97      * circle with a dual-arc polyline wide as the radius.
98      *
99      * I could use this trick to do other filled primitives.
100      */
101     virtual void Circle( const wxPoint& pos, int diametre, FILL_T fill,
102                          int width = USE_DEFAULT_LINE_WIDTH ) override;
103 
104     /**
105      * DXF polygon: doesn't fill it but at least it close the filled ones
106      * DXF does not know thick outline.
107      *
108      * It does not know thick segments, therefore filled polygons with thick outline
109      * are converted to inflated polygon by aWidth/2.
110      */
111     virtual void PlotPoly( const std::vector< wxPoint >& aCornerList, FILL_T aFill,
112                            int aWidth = USE_DEFAULT_LINE_WIDTH, void* aData = nullptr ) override;
113     virtual void ThickSegment( const wxPoint& start, const wxPoint& end, int width,
114                                OUTLINE_MODE tracemode, void* aData ) override;
115     virtual void Arc( const wxPoint& centre, double StAngle, double EndAngle,
116                       int rayon, FILL_T fill, int width = USE_DEFAULT_LINE_WIDTH ) override;
117     virtual void PenTo( const wxPoint& pos, char plume ) override;
118 
119     /**
120      * DXF round pad: always done in sketch mode; it could be filled but it isn't
121      * pretty if other kinds of pad aren't...
122      */
123     virtual void FlashPadCircle( const wxPoint& pos, int diametre,
124                                  OUTLINE_MODE trace_mode, void* aData ) override;
125 
126     /**
127      * DXF oval pad: always done in sketch mode.
128      */
129     virtual void FlashPadOval( const wxPoint& pos, const wxSize& size, double orient,
130                                OUTLINE_MODE trace_mode, void* aData ) override;
131 
132     /**
133      * DXF rectangular pad: always done in sketch mode.
134      */
135     virtual void FlashPadRect( const wxPoint& pos, const wxSize& size,
136                                double orient, OUTLINE_MODE trace_mode, void* aData ) override;
137     virtual void FlashPadRoundRect( const wxPoint& aPadPos, const wxSize& aSize,
138                                     int aCornerRadius, double aOrient,
139                                     OUTLINE_MODE aTraceMode, void* aData ) override;
140     virtual void FlashPadCustom( const wxPoint& aPadPos, const wxSize& aSize, double aOrient,
141                                  SHAPE_POLY_SET* aPolygons,
142                                  OUTLINE_MODE aTraceMode, void* aData ) override;
143 
144     /**
145      * DXF trapezoidal pad: only sketch mode is supported.
146      */
147     virtual void FlashPadTrapez( const wxPoint& aPadPos, const wxPoint *aCorners,
148                                  double aPadOrient, OUTLINE_MODE aTraceMode, void* aData ) override;
149     virtual void FlashRegularPolygon( const wxPoint& aShapePos, int aDiameter, int aCornerCount,
150                             double aOrient, OUTLINE_MODE aTraceMode, void* aData ) override;
151 
152     virtual void Text( const wxPoint&              aPos,
153                        const COLOR4D&              aColor,
154                        const wxString&             aText,
155                        double                      aOrient,
156                        const wxSize&               aSize,
157                        enum EDA_TEXT_HJUSTIFY_T    aH_justify,
158                        enum EDA_TEXT_VJUSTIFY_T    aV_justify,
159                        int                         aWidth,
160                        bool                        aItalic,
161                        bool                        aBold,
162                        bool                        aMultilineAllowed = false,
163                        void* aData = nullptr ) override;
164 
165 
166     /**
167      * Set the units to use for plotting the DXF file.
168      *
169      * @param aUnit - The units to use
170      */
171     void SetUnits( DXF_UNITS aUnit );
172 
173     /**
174      * The units currently enabled for plotting
175      *
176      * @return The currently configured units
177      */
GetUnits()178     DXF_UNITS GetUnits() const
179     {
180         return m_plotUnits;
181     }
182 
183     /**
184      * Get the scale factor to apply to convert the device units to be in the
185      * currently set units.
186      *
187      * @return Scaling factor to apply for unit conversion
188      */
GetUnitScaling()189     double GetUnitScaling() const
190     {
191         return m_unitScalingFactor;
192     }
193 
194     /**
195      * Get the correct value for the $MEASUREMENT field given the current units
196      *
197      * @return the $MEASUREMENT directive field value
198      */
GetMeasurementDirective()199     unsigned int GetMeasurementDirective() const
200     {
201         return m_measurementDirective;
202     }
203 
204 protected:
205     bool           m_textAsLines;
206     COLOR4D        m_currentColor;
207     PLOT_DASH_TYPE m_currentLineType;
208 
209     DXF_UNITS      m_plotUnits;
210     double         m_unitScalingFactor;
211     unsigned int   m_measurementDirective;
212 };
213