SkXPSDevice.h revision da5a1b8cd80bbea1dfdb474c6917a1f13a0e7f9e
1/*
2 * Copyright 2011 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8#ifndef SkXPSDevice_DEFINED
9#define SkXPSDevice_DEFINED
10
11#include "SkTypes.h"
12#include <ObjBase.h>
13#include <XpsObjectModel.h>
14
15#include "SkAutoCoInitialize.h"
16#include "SkBitmapDevice.h"
17#include "SkBitSet.h"
18#include "SkCanvas.h"
19#include "SkColor.h"
20#include "SkPaint.h"
21#include "SkPath.h"
22#include "SkPoint.h"
23#include "SkShader.h"
24#include "SkSize.h"
25#include "SkTArray.h"
26#include "SkTScopedComPtr.h"
27#include "SkTypeface.h"
28
29//#define SK_XPS_USE_DETERMINISTIC_IDS
30
31/** \class SkXPSDevice
32
33    The drawing context for the XPS backend.
34*/
35class SkXPSDevice : public SkBitmapDevice {
36public:
37    SK_API SkXPSDevice();
38    SK_API virtual ~SkXPSDevice();
39
40    virtual bool beginPortfolio(SkWStream* outputStream);
41    /**
42      @param unitsPerMeter converts geometry units into physical units.
43      @param pixelsPerMeter resolution to use when geometry must be rasterized.
44      @param trimSize final page size in physical units.
45                      The top left of the trim is the origin of physical space.
46      @param mediaBox The size of the physical media in physical units.
47                      The top and left must be less than zero.
48                      The bottom and right must be greater than the trimSize.
49                      The default is to coincide with the trimSize.
50      @param bleedBox The size of the bleed box in physical units.
51                      Must be contained within the mediaBox.
52                      The default is to coincide with the mediaBox.
53      @param artBox The size of the content box in physical units.
54                    Must be contained within the trimSize.
55                    The default is to coincide with the trimSize.
56      @param cropBox The size of the recommended view port in physical units.
57                     Must be contained within the mediaBox.
58                     The default is to coincide with the mediaBox.
59     */
60    virtual bool beginSheet(
61        const SkVector& unitsPerMeter,
62        const SkVector& pixelsPerMeter,
63        const SkSize& trimSize,
64        const SkRect* mediaBox = NULL,
65        const SkRect* bleedBox = NULL,
66        const SkRect* artBox = NULL,
67        const SkRect* cropBox = NULL);
68
69    virtual bool endSheet();
70    virtual bool endPortfolio();
71
72protected:
73    virtual void clear(SkColor color) SK_OVERRIDE;
74
75    virtual void drawPaint(const SkDraw&, const SkPaint& paint) SK_OVERRIDE;
76
77    virtual void drawPoints(
78        const SkDraw&,
79        SkCanvas::PointMode mode,
80        size_t count, const SkPoint[],
81        const SkPaint& paint) SK_OVERRIDE;
82
83    virtual void drawRect(
84        const SkDraw&,
85        const SkRect& r,
86        const SkPaint& paint) SK_OVERRIDE;
87
88    virtual void drawRRect(
89        const SkDraw&,
90        const SkRRect&,
91        const SkPaint& paint) SK_OVERRIDE;
92
93    virtual void drawPath(
94        const SkDraw&,
95        const SkPath& platonicPath,
96        const SkPaint& paint,
97        const SkMatrix* prePathMatrix,
98        bool pathIsMutable) SK_OVERRIDE;
99
100    virtual void drawBitmap(
101        const SkDraw&,
102        const SkBitmap& bitmap,
103        const SkMatrix& matrix,
104        const SkPaint& paint) SK_OVERRIDE;
105
106    virtual void drawSprite(
107        const SkDraw&,
108        const SkBitmap& bitmap,
109        int x, int y,
110        const SkPaint& paint) SK_OVERRIDE;
111
112    virtual void drawText(
113        const SkDraw&,
114        const void* text, size_t len,
115        SkScalar x, SkScalar y,
116        const SkPaint& paint) SK_OVERRIDE;
117
118    virtual void drawPosText(
119        const SkDraw&,
120        const void* text, size_t len,
121        const SkScalar pos[], SkScalar constY, int scalarsPerPos,
122        const SkPaint& paint) SK_OVERRIDE;
123
124    virtual void drawTextOnPath(
125        const SkDraw&,
126        const void* text, size_t len,
127        const SkPath& path,
128        const SkMatrix* matrix,
129        const SkPaint& paint) SK_OVERRIDE;
130
131    virtual void drawVertices(
132        const SkDraw&,
133        SkCanvas::VertexMode,
134        int vertexCount, const SkPoint verts[],
135        const SkPoint texs[], const SkColor colors[],
136        SkXfermode* xmode,
137        const uint16_t indices[], int indexCount,
138        const SkPaint& paint) SK_OVERRIDE;
139
140    virtual void drawDevice(
141        const SkDraw&,
142        SkBaseDevice* device,
143        int x, int y,
144        const SkPaint& paint) SK_OVERRIDE;
145
146    virtual bool allowImageFilter(const SkImageFilter*) SK_OVERRIDE;
147
148private:
149    class TypefaceUse : ::SkNoncopyable {
150    public:
151        SkFontID typefaceId;
152        int ttcIndex;
153        SkStream* fontData;
154        IXpsOMFontResource* xpsFont;
155        SkBitSet* glyphsUsed;
156
157        explicit TypefaceUse();
158        ~TypefaceUse();
159    };
160    friend static HRESULT subset_typeface(TypefaceUse* current);
161
162    SkXPSDevice(IXpsOMObjectFactory* xpsFactory);
163
164    SkAutoCoInitialize fAutoCo;
165    SkTScopedComPtr<IXpsOMObjectFactory> fXpsFactory;
166    SkTScopedComPtr<IStream> fOutputStream;
167    SkTScopedComPtr<IXpsOMPackageWriter> fPackageWriter;
168
169    unsigned int fCurrentPage;
170    SkTScopedComPtr<IXpsOMCanvas> fCurrentXpsCanvas;
171    SkSize fCurrentCanvasSize;
172    SkVector fCurrentUnitsPerMeter;
173    SkVector fCurrentPixelsPerMeter;
174
175    SkTArray<TypefaceUse, true> fTypefaces;
176
177    /** Creates a GUID based id and places it into buffer.
178        buffer should have space for at least GUID_ID_LEN wide characters.
179        The string will always be wchar null terminated.
180        XXXXXXXXsXXXXsXXXXsXXXXsXXXXXXXXXXXX0
181        The string may begin with a digit,
182        and so may not be suitable as a bare resource key.
183     */
184    HRESULT createId(wchar_t* buffer, size_t bufferSize, wchar_t sep = '-');
185#ifdef SK_XPS_USE_DETERMINISTIC_IDS
186    decltype(GUID::Data1) fNextId = 0;
187#endif
188
189    HRESULT initXpsDocumentWriter(IXpsOMImageResource* image);
190
191    HRESULT createXpsPage(
192        const XPS_SIZE& pageSize,
193        IXpsOMPage** page);
194
195    HRESULT createXpsThumbnail(
196        IXpsOMPage* page, const unsigned int pageNumber,
197        IXpsOMImageResource** image);
198
199    void internalDrawRect(
200        const SkDraw&,
201        const SkRect& r,
202        bool transformRect,
203        const SkPaint& paint);
204
205    HRESULT createXpsBrush(
206        const SkPaint& skPaint,
207        IXpsOMBrush** xpsBrush,
208        const SkMatrix* parentTransform = NULL);
209
210    HRESULT createXpsSolidColorBrush(
211        const SkColor skColor, const SkAlpha alpha,
212        IXpsOMBrush** xpsBrush);
213
214    HRESULT createXpsImageBrush(
215        const SkBitmap& bitmap,
216        const SkMatrix& localMatrix,
217        const SkShader::TileMode (&xy)[2],
218        const SkAlpha alpha,
219        IXpsOMTileBrush** xpsBrush);
220
221    HRESULT createXpsLinearGradient(
222        SkShader::GradientInfo info,
223        const SkAlpha alpha,
224        const SkMatrix& localMatrix,
225        IXpsOMMatrixTransform* xpsMatrixToUse,
226        IXpsOMBrush** xpsBrush);
227
228    HRESULT createXpsRadialGradient(
229        SkShader::GradientInfo info,
230        const SkAlpha alpha,
231        const SkMatrix& localMatrix,
232        IXpsOMMatrixTransform* xpsMatrixToUse,
233        IXpsOMBrush** xpsBrush);
234
235    HRESULT createXpsGradientStop(
236        const SkColor skColor,
237        const SkScalar offset,
238        IXpsOMGradientStop** xpsGradStop);
239
240    HRESULT createXpsTransform(
241        const SkMatrix& matrix,
242        IXpsOMMatrixTransform ** xpsTransform);
243
244    HRESULT createXpsRect(
245        const SkRect& rect,
246        BOOL stroke, BOOL fill,
247        IXpsOMGeometryFigure** xpsRect);
248
249    HRESULT createXpsQuad(
250        const SkPoint (&points)[4],
251        BOOL stroke, BOOL fill,
252        IXpsOMGeometryFigure** xpsQuad);
253
254    HRESULT CreateTypefaceUse(
255        const SkPaint& paint,
256        TypefaceUse** fontResource);
257
258    HRESULT AddGlyphs(
259        const SkDraw& d,
260        IXpsOMObjectFactory* xpsFactory,
261        IXpsOMCanvas* canvas,
262        TypefaceUse* font,
263        LPCWSTR text,
264        XPS_GLYPH_INDEX* xpsGlyphs,
265        UINT32 xpsGlyphsLen,
266        XPS_POINT *origin,
267        FLOAT fontSize,
268        XPS_STYLE_SIMULATION sims,
269        const SkMatrix& transform,
270        const SkPaint& paint);
271
272    HRESULT addXpsPathGeometry(
273        IXpsOMGeometryFigureCollection* figures,
274        BOOL stroke, BOOL fill, const SkPath& path);
275
276    HRESULT createPath(
277        IXpsOMGeometryFigure* figure,
278        IXpsOMVisualCollection* visuals,
279        IXpsOMPath** path);
280
281    HRESULT sideOfClamp(
282        const SkRect& leftPoints, const XPS_RECT& left,
283        IXpsOMImageResource* imageResource,
284        IXpsOMVisualCollection* visuals);
285
286    HRESULT cornerOfClamp(
287        const SkRect& tlPoints,
288        const SkColor color,
289        IXpsOMVisualCollection* visuals);
290
291    HRESULT clip(
292        IXpsOMVisual* xpsVisual,
293        const SkDraw& d);
294    HRESULT clipToPath(
295        IXpsOMVisual* xpsVisual,
296        const SkPath& clipPath,
297        XPS_FILL_RULE fillRule);
298
299    HRESULT drawInverseWindingPath(
300        const SkDraw& d,
301        const SkPath& devicePath,
302        IXpsOMPath* xpsPath);
303
304    HRESULT shadePath(
305        IXpsOMPath* shadedPath,
306        const SkPaint& shaderPaint,
307        const SkMatrix& matrix,
308        BOOL* fill, BOOL* stroke);
309
310    void convertToPpm(
311        const SkMaskFilter* filter,
312        SkMatrix* matrix,
313        SkVector* ppuScale,
314        const SkIRect& clip, SkIRect* clipIRect);
315
316    HRESULT applyMask(
317        const SkDraw& d,
318        const SkMask& mask,
319        const SkVector& ppuScale,
320        IXpsOMPath* shadedPath);
321
322    virtual SkBaseDevice* onCreateDevice(const SkImageInfo&, Usage) SK_OVERRIDE;
323
324    // Disable the default copy and assign implementation.
325    SkXPSDevice(const SkXPSDevice&);
326    void operator=(const SkXPSDevice&);
327
328    typedef SkBitmapDevice INHERITED;
329};
330
331#endif
332