1 /* 2 Copyright 2008 Brad Hards <bradh@frogmouth.net> 3 Copyright 2009 - 2010 Inge Wallin <inge@lysator.liu.se> 4 5 This library is free software; you can redistribute it and/or 6 modify it under the terms of the GNU Lesser General Public 7 License as published by the Free Software Foundation; either 8 version 2.1 of the License, or (at your option) any later version. 9 10 This library is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 Lesser General Public License for more details. 14 15 You should have received a copy of the GNU Lesser General Public 16 License along with this library. If not, see <http://www.gnu.org/licenses/>. 17 */ 18 19 #ifndef EMFOUTPUTPAINTERSTRATEGY_H 20 #define EMFOUTPUTPAINTERSTRATEGY_H 21 22 #include "kovectorimage_export.h" 23 24 #include <QList> 25 #include <QPainter> 26 #include <QRect> // also provides QSize, QPoint 27 #include <QString> 28 #include <QVariant> 29 30 #include "EmfEnums.h" 31 #include "EmfHeader.h" 32 #include "EmfRecords.h" 33 #include "EmfOutput.h" 34 35 36 /** 37 \file 38 39 Primary definitions for EMF output strategies 40 */ 41 42 /** 43 Namespace for Enhanced Metafile (EMF) classes 44 */ 45 namespace Libemf 46 { 47 48 class EmrTextObject; 49 50 /** 51 QPainter based output strategy for EMF Parser. 52 53 This class allows rendering of an EMF file to a QPixmap or any other QPaintDevice. 54 */ 55 class KOVECTORIMAGE_EXPORT OutputPainterStrategy : public AbstractOutput 56 { 57 public: 58 /** 59 Constructor. 60 61 This will probably need to take an enum to say what sort of output 62 we want. 63 */ 64 OutputPainterStrategy(); 65 OutputPainterStrategy( QPainter &painter, QSize &size, 66 bool keepAspectRatio = false ); 67 ~OutputPainterStrategy() override; 68 69 void init( const Header *header ) override; 70 void cleanup( const Header *header ) override; 71 void eof() override; 72 73 /** 74 The image that has been rendered to. 75 */ 76 QImage *image(); 77 78 void createPen( quint32 ihPen, quint32 penStyle, quint32 x, quint32 y, 79 quint8 red, quint8 green, quint8 blue, quint8 reserved ) override; 80 void createBrushIndirect( quint32 ihBrush, quint32 BrushStyle, quint8 red, 81 quint8 green, quint8 blue, quint8 reserved, 82 quint32 BrushHatch ) override; 83 void createMonoBrush( quint32 ihBrush, Bitmap *bitmap ) override; 84 void selectObject( const quint32 ihObject ) override; 85 void deleteObject( const quint32 ihObject ) override; 86 void arc( const QRect &box, const QPoint &start, const QPoint &end ) override; 87 void chord( const QRect &box, const QPoint &start, const QPoint &end ) override; 88 void pie( const QRect &box, const QPoint &start, const QPoint &end ) override; 89 void ellipse( const QRect &box ) override; 90 void rectangle( const QRect &box ) override; 91 void setMapMode( const quint32 mapMode ) override; 92 void setMetaRgn() override; 93 void setWindowOrgEx( const QPoint &origin ) override; 94 void setWindowExtEx( const QSize &size ) override; 95 void setViewportOrgEx( const QPoint &origin ) override; 96 void setViewportExtEx( const QSize &size ) override; 97 void beginPath() override; 98 void closeFigure() override; 99 void endPath() override; 100 void setBkMode( const quint32 backgroundMode ) override; 101 void setPolyFillMode( const quint32 polyFillMode ) override; 102 void setLayout( const quint32 layoutMode ) override; 103 void extCreateFontIndirectW( const ExtCreateFontIndirectWRecord &extCreateFontIndirectW ) override; 104 void setTextAlign( const quint32 textAlignMode ) override; 105 void setTextColor( const quint8 red, const quint8 green, const quint8 blue, 106 const quint8 reserved ) override; 107 void setBkColor( const quint8 red, const quint8 green, const quint8 blue, 108 const quint8 reserved ) override; 109 void setPixelV( QPoint &point, quint8 red, quint8 green, quint8 blue, quint8 reserved ) override; 110 void modifyWorldTransform( quint32 mode, float M11, float M12, 111 float M21, float M22, float Dx, float Dy ) override; 112 void setWorldTransform( float M11, float M12, float M21, 113 float M22, float Dx, float Dy ) override; 114 void extTextOut( const QRect &bounds, const EmrTextObject &textObject ) override; 115 void moveToEx( const qint32 x, const qint32 y ) override; 116 void saveDC() override; 117 void restoreDC( const qint32 savedDC ) override; 118 void lineTo( const QPoint &finishPoint ) override; 119 void arcTo( const QRect &box, const QPoint &start, const QPoint &end ) override; 120 void polygon16( const QRect &bounds, const QList<QPoint> points ) override; 121 void polyLine16( const QRect &bounds, const QList<QPoint> points ) override; 122 void polyPolygon16( const QRect &bounds, const QList< QVector< QPoint > > &points ) override; 123 void polyPolyLine16( const QRect &bounds, const QList< QVector< QPoint > > &points ) override; 124 void polyLine( const QRect &bounds, const QList<QPoint> points ) override; 125 void polyLineTo16( const QRect &bounds, const QList<QPoint> points ) override; 126 void polyBezier16( const QRect &bounds, const QList<QPoint> points ) override; 127 void polyBezierTo16( const QRect &bounds, const QList<QPoint> points ) override; 128 void fillPath( const QRect &bounds ) override; 129 void strokeAndFillPath( const QRect &bounds ) override; 130 void strokePath( const QRect &bounds ) override; 131 void setClipPath( const quint32 regionMode ) override; 132 void bitBlt( BitBltRecord &bitBltRecord ) override; 133 void setStretchBltMode( const quint32 stretchMode ) override; 134 void stretchDiBits( StretchDiBitsRecord &stretchDiBitsRecord ) override; 135 136 private: 137 void printPainterTransform(const char *leadText); 138 139 /// For debugging purposes: Draw the boundary box. 140 void paintBounds(const Header *header); 141 142 /// Recalculate the world transform and then apply it to the painter 143 /// This must be called at the end of every function that changes the transform. 144 void recalculateWorldTransform(); 145 146 /** 147 Select a stock object. 148 149 See [MS-EMF] Section 2.1.31. 150 151 \param ihObject the stock object value 152 */ 153 void selectStockObject( const quint32 ihObject ); 154 155 156 /** 157 Helper routine to convert the EMF angle (centrepoint + radial endpoint) into 158 the Qt format (in degress - may need to multiply by 16 for some purposes) 159 */ 160 qreal angleFromArc( const QPoint ¢rePoint, const QPoint &radialPoint ); 161 162 /** 163 Calculate the angular difference (span) between two angles 164 165 This should always be positive. 166 */ 167 qreal angularSpan( const qreal startAngle, const qreal endAngle ); 168 169 /** 170 Convert the EMF font weight scale (0..1000) to Qt equivalent. 171 172 This is a bit rough - the EMF spec only says 400 is normal, and 173 700 is bold. 174 */ 175 int convertFontWeight( quint32 emfWeight ); 176 177 178 Header *m_header; // Save to be able to retain scaling. 179 180 int m_painterSaves; // The number of times that save() was called. 181 QSize m_outputSize; 182 bool m_keepAspectRatio; 183 184 QMap<quint32, QVariant> m_objectTable; 185 186 QPainterPath *m_path; 187 bool m_currentlyBuildingPath; 188 189 QPainter *m_painter; 190 QTransform m_worldTransform; // The transform inside the EMF. 191 QTransform m_outputTransform; // The transform that the painter already had 192 qreal m_outputScale; 193 194 // Everything that has to do with window and viewport calculation 195 QPoint m_windowOrg; 196 QSize m_windowExt; 197 QPoint m_viewportOrg; 198 QSize m_viewportExt; 199 bool m_windowExtIsSet; 200 bool m_viewportExtIsSet; 201 bool m_windowViewportIsSet; 202 203 #if 0 204 // This matrix is needed because the window / viewport calculation 205 // is not the last one in the chain. After that one comes the 206 // transform that the painter already has when the painting 207 // starts, and that one has to be saved and reapplied again after 208 // the window / viewport calculation is redone. 209 QTransform m_outputTransform; 210 #endif 211 212 // ---------------------------------------------------------------- 213 // The playback device context 214 215 // The Playback Device Context (PDC) contains the following: 216 // - bitmap 217 // - brush (part of the painter) 218 // - palette 219 // - font (part of the painter) 220 // - pen (part of the painter) 221 // - region 222 // - drawing mode 223 // - mapping mode 224 // FIXME: what more? textalign? textpen? 225 226 /** 227 The current text pen 228 */ 229 QPen m_textPen; 230 231 /** 232 The current fill rule 233 */ 234 enum Qt::FillRule m_fillRule; 235 236 /** 237 The current map mode 238 */ 239 MapMode m_mapMode; 240 /** 241 The current text alignment mode 242 */ 243 quint32 m_textAlignMode; 244 245 /** 246 The current coordinates 247 */ 248 QPoint m_currentCoords; 249 }; 250 251 } 252 253 #endif 254