Home | History | Annotate | Download | only in graphics
      1 /*
      2  * Copyright (C) 2003, 2006, 2007, 2008, 2009 Apple Inc. All rights reserved.
      3  * Copyright (C) 2008-2009 Torch Mobile, Inc.
      4  *
      5  * Redistribution and use in source and binary forms, with or without
      6  * modification, are permitted provided that the following conditions
      7  * are met:
      8  * 1. Redistributions of source code must retain the above copyright
      9  *    notice, this list of conditions and the following disclaimer.
     10  * 2. Redistributions in binary form must reproduce the above copyright
     11  *    notice, this list of conditions and the following disclaimer in the
     12  *    documentation and/or other materials provided with the distribution.
     13  *
     14  * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
     15  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     16  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     17  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE COMPUTER, INC. OR
     18  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
     19  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
     20  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
     21  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
     22  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     23  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     24  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     25  */
     26 
     27 #ifndef GraphicsContext_h
     28 #define GraphicsContext_h
     29 
     30 #include "ColorSpace.h"
     31 #include "DashArray.h"
     32 #include "FloatRect.h"
     33 #include "Image.h"
     34 #include "IntRect.h"
     35 #include "Path.h"
     36 #include "TextDirection.h"
     37 #include <wtf/Noncopyable.h>
     38 #include <wtf/Platform.h>
     39 
     40 #if PLATFORM(CG)
     41 typedef struct CGContext PlatformGraphicsContext;
     42 #elif PLATFORM(CAIRO)
     43 typedef struct _cairo PlatformGraphicsContext;
     44 #elif PLATFORM(OPENVG)
     45 namespace WebCore {
     46 class SurfaceOpenVG;
     47 }
     48 typedef class WebCore::SurfaceOpenVG PlatformGraphicsContext;
     49 #elif PLATFORM(QT)
     50 QT_BEGIN_NAMESPACE
     51 class QPainter;
     52 QT_END_NAMESPACE
     53 typedef QPainter PlatformGraphicsContext;
     54 #elif PLATFORM(WX)
     55 class wxGCDC;
     56 class wxWindowDC;
     57 
     58 // wxGraphicsContext allows us to support Path, etc.
     59 // but on some platforms, e.g. Linux, it requires fairly
     60 // new software.
     61 #if USE(WXGC)
     62 // On OS X, wxGCDC is just a typedef for wxDC, so use wxDC explicitly to make
     63 // the linker happy.
     64 #ifdef __APPLE__
     65     class wxDC;
     66     typedef wxDC PlatformGraphicsContext;
     67 #else
     68     typedef wxGCDC PlatformGraphicsContext;
     69 #endif
     70 #else
     71     typedef wxWindowDC PlatformGraphicsContext;
     72 #endif
     73 #elif PLATFORM(SKIA)
     74 #if PLATFORM(ANDROID)
     75 namespace WebCore {
     76 class PlatformGraphicsContext;
     77 }
     78 class SkPaint;
     79 struct SkPoint;
     80 #else
     81 typedef class PlatformContextSkia PlatformGraphicsContext;
     82 #endif
     83 #elif PLATFORM(HAIKU)
     84 class BView;
     85 typedef BView PlatformGraphicsContext;
     86 struct pattern;
     87 #elif OS(WINCE)
     88 typedef struct HDC__ PlatformGraphicsContext;
     89 #else
     90 typedef void PlatformGraphicsContext;
     91 #endif
     92 
     93 #if PLATFORM(GTK)
     94 typedef struct _GdkDrawable GdkDrawable;
     95 typedef struct _GdkEventExpose GdkEventExpose;
     96 #endif
     97 
     98 #if PLATFORM(WIN)
     99 typedef struct HDC__* HDC;
    100 #if !PLATFORM(CG)
    101 // UInt8 is defined in CoreFoundation/CFBase.h
    102 typedef unsigned char UInt8;
    103 #endif
    104 #endif
    105 
    106 #if PLATFORM(QT) && defined(Q_WS_WIN)
    107 #include <windows.h>
    108 #endif
    109 
    110 namespace WebCore {
    111 
    112 #if OS(WINCE) && !PLATFORM(QT)
    113     class SharedBitmap;
    114     class SimpleFontData;
    115     class GlyphBuffer;
    116 #endif
    117 
    118     const int cMisspellingLineThickness = 3;
    119     const int cMisspellingLinePatternWidth = 4;
    120     const int cMisspellingLinePatternGapWidth = 1;
    121 
    122     class AffineTransform;
    123     class Font;
    124     class Generator;
    125     class Gradient;
    126     class GraphicsContextPlatformPrivate;
    127     class GraphicsContextPrivate;
    128     class ImageBuffer;
    129     class KURL;
    130     class Path;
    131     class Pattern;
    132     class TextRun;
    133 
    134     // These bits can be ORed together for a total of 8 possible text drawing modes.
    135     const int cTextInvisible = 0;
    136     const int cTextFill = 1;
    137     const int cTextStroke = 2;
    138     const int cTextClip = 4;
    139 
    140     enum StrokeStyle {
    141         NoStroke,
    142         SolidStroke,
    143         DottedStroke,
    144         DashedStroke
    145     };
    146 
    147     enum InterpolationQuality {
    148         InterpolationDefault,
    149         InterpolationNone,
    150         InterpolationLow,
    151         InterpolationMedium,
    152         InterpolationHigh
    153     };
    154 
    155     class GraphicsContext : public Noncopyable {
    156     public:
    157         GraphicsContext(PlatformGraphicsContext*);
    158         ~GraphicsContext();
    159 
    160 #if !OS(WINCE) || PLATFORM(QT)
    161         PlatformGraphicsContext* platformContext() const;
    162 #endif
    163 
    164         float strokeThickness() const;
    165         void setStrokeThickness(float);
    166         StrokeStyle strokeStyle() const;
    167         void setStrokeStyle(const StrokeStyle& style);
    168         Color strokeColor() const;
    169         ColorSpace strokeColorSpace() const;
    170         void setStrokeColor(const Color&, ColorSpace);
    171 
    172         void setStrokePattern(PassRefPtr<Pattern>);
    173         Pattern* strokePattern() const;
    174 
    175         void setStrokeGradient(PassRefPtr<Gradient>);
    176         Gradient* strokeGradient() const;
    177 
    178         WindRule fillRule() const;
    179         void setFillRule(WindRule);
    180         Color fillColor() const;
    181         ColorSpace fillColorSpace() const;
    182         void setFillColor(const Color&, ColorSpace);
    183 
    184         void setFillPattern(PassRefPtr<Pattern>);
    185         Pattern* fillPattern() const;
    186 
    187         void setFillGradient(PassRefPtr<Gradient>);
    188         Gradient* fillGradient() const;
    189 
    190         void setShadowsIgnoreTransforms(bool);
    191 
    192         void setShouldAntialias(bool);
    193         bool shouldAntialias() const;
    194 
    195 #if PLATFORM(CG)
    196         void applyStrokePattern();
    197         void applyFillPattern();
    198 #endif
    199 
    200 #if PLATFORM(ANDROID)
    201         // initialize a paint for bitmaps
    202         void setupBitmapPaint(SkPaint*);
    203         // initialize a paint for filling
    204         void setupFillPaint(SkPaint*);
    205         // initialize a paint for stroking
    206         void setupStrokePaint(SkPaint*);
    207         // initialize a paint for a shadow, or if false is returned, the
    208         // parameters are left untouched
    209         bool setupShadowPaint(SkPaint* paint, SkPoint* offset);
    210         // returns true if there is a valid (non-transparent) fill color
    211         bool willFill() const;
    212         // returns true if there is a valid (non-transparent) stroke color
    213         bool willStroke() const;
    214 
    215         // may return NULL, since we lazily allocate the path. This is the path
    216         // that is drawn by drawPath()
    217         const SkPath* getCurrPath() const;
    218 
    219         /** platform-specific factory method to return a bitmap graphicscontext,
    220          called by <canvas> when we need to draw offscreen. Caller is responsible for
    221          deleting the context. Use drawOffscreenContext() to draw the context's image
    222          onto another graphics context.
    223          */
    224         static GraphicsContext* createOffscreenContext(int width, int height);
    225 #endif
    226 
    227         void save();
    228         void restore();
    229 
    230         // These draw methods will do both stroking and filling.
    231         // FIXME: ...except drawRect(), which fills properly but always strokes
    232         // using a 1-pixel stroke inset from the rect borders (of the correct
    233         // stroke color).
    234         void drawRect(const IntRect&);
    235         void drawLine(const IntPoint&, const IntPoint&);
    236         void drawEllipse(const IntRect&);
    237         void drawConvexPolygon(size_t numPoints, const FloatPoint*, bool shouldAntialias = false);
    238 
    239         void drawPath();
    240         void fillPath();
    241         void strokePath();
    242 
    243         // Arc drawing (used by border-radius in CSS) just supports stroking at the moment.
    244         void strokeArc(const IntRect&, int startAngle, int angleSpan);
    245 
    246         void fillRect(const FloatRect&);
    247         void fillRect(const FloatRect&, const Color&, ColorSpace);
    248         void fillRect(const FloatRect&, Generator&);
    249         void fillRoundedRect(const IntRect&, const IntSize& topLeft, const IntSize& topRight, const IntSize& bottomLeft, const IntSize& bottomRight, const Color&, ColorSpace);
    250 
    251         void clearRect(const FloatRect&);
    252 
    253         void strokeRect(const FloatRect&);
    254         void strokeRect(const FloatRect&, float lineWidth);
    255 
    256         void drawImage(Image*, ColorSpace styleColorSpace, const IntPoint&, CompositeOperator = CompositeSourceOver);
    257         void drawImage(Image*, ColorSpace styleColorSpace, const IntRect&, CompositeOperator = CompositeSourceOver, bool useLowQualityScale = false);
    258         void drawImage(Image*, ColorSpace styleColorSpace, const IntPoint& destPoint, const IntRect& srcRect, CompositeOperator = CompositeSourceOver);
    259         void drawImage(Image*, ColorSpace styleColorSpace, const IntRect& destRect, const IntRect& srcRect, CompositeOperator = CompositeSourceOver, bool useLowQualityScale = false);
    260         void drawImage(Image*, ColorSpace styleColorSpace, const FloatRect& destRect, const FloatRect& srcRect = FloatRect(0, 0, -1, -1),
    261                        CompositeOperator = CompositeSourceOver, bool useLowQualityScale = false);
    262         void drawTiledImage(Image*, ColorSpace styleColorSpace, const IntRect& destRect, const IntPoint& srcPoint, const IntSize& tileSize,
    263                        CompositeOperator = CompositeSourceOver, bool useLowQualityScale = false);
    264         void drawTiledImage(Image*, ColorSpace styleColorSpace, const IntRect& destRect, const IntRect& srcRect,
    265                             Image::TileRule hRule = Image::StretchTile, Image::TileRule vRule = Image::StretchTile,
    266                             CompositeOperator = CompositeSourceOver, bool useLowQualityScale = false);
    267 
    268         void setImageInterpolationQuality(InterpolationQuality);
    269         InterpolationQuality imageInterpolationQuality() const;
    270 
    271         void clip(const FloatRect&);
    272         void addRoundedRectClip(const IntRect&, const IntSize& topLeft, const IntSize& topRight, const IntSize& bottomLeft, const IntSize& bottomRight);
    273         void addInnerRoundedRectClip(const IntRect&, int thickness);
    274         void clipOut(const IntRect&);
    275         void clipOutEllipseInRect(const IntRect&);
    276         void clipOutRoundedRect(const IntRect&, const IntSize& topLeft, const IntSize& topRight, const IntSize& bottomLeft, const IntSize& bottomRight);
    277         void clipPath(WindRule);
    278         void clipToImageBuffer(const FloatRect&, const ImageBuffer*);
    279 
    280         int textDrawingMode();
    281         void setTextDrawingMode(int);
    282 
    283         void drawText(const Font&, const TextRun&, const IntPoint&, int from = 0, int to = -1);
    284         void drawBidiText(const Font&, const TextRun&, const FloatPoint&);
    285         void drawHighlightForText(const Font&, const TextRun&, const IntPoint&, int h, const Color& backgroundColor, ColorSpace, int from = 0, int to = -1);
    286 
    287         FloatRect roundToDevicePixels(const FloatRect&);
    288 
    289         void drawLineForText(const IntPoint&, int width, bool printing);
    290         void drawLineForMisspellingOrBadGrammar(const IntPoint&, int width, bool grammar);
    291 
    292         bool paintingDisabled() const;
    293         void setPaintingDisabled(bool);
    294 
    295         bool updatingControlTints() const;
    296         void setUpdatingControlTints(bool);
    297 
    298         void beginTransparencyLayer(float opacity);
    299         void endTransparencyLayer();
    300 
    301         void setShadow(const IntSize&, int blur, const Color&, ColorSpace);
    302         bool getShadow(IntSize&, int&, Color&) const;
    303         void clearShadow();
    304 
    305         void drawFocusRing(const Vector<IntRect>&, int width, int offset, const Color&);
    306         void drawFocusRing(const Vector<Path>&, int width, int offset, const Color&);
    307 
    308         void setLineCap(LineCap);
    309         void setLineDash(const DashArray&, float dashOffset);
    310         void setLineJoin(LineJoin);
    311         void setMiterLimit(float);
    312 
    313         void setAlpha(float);
    314 #if PLATFORM(CAIRO)
    315         float getAlpha();
    316         void createPlatformShadow(PassOwnPtr<ImageBuffer> buffer, const Color& shadowColor, const FloatRect& shadowRect, float kernelSize);
    317         static void calculateShadowBufferDimensions(IntSize& shadowBufferSize, FloatRect& shadowRect, float& kernelSize, const FloatRect& sourceRect, const IntSize& shadowSize, int shadowBlur);
    318 #endif
    319 
    320         void setCompositeOperation(CompositeOperator);
    321 
    322         void beginPath();
    323         void addPath(const Path&);
    324 
    325         void clip(const Path&);
    326 
    327         // This clip function is used only by <canvas> code. It allows
    328         // implementations to handle clipping on the canvas differently since
    329         // the disipline is different.
    330         void canvasClip(const Path&);
    331         void clipOut(const Path&);
    332 
    333         void scale(const FloatSize&);
    334         void rotate(float angleInRadians);
    335         void translate(const FloatSize& size) { translate(size.width(), size.height()); }
    336         void translate(float x, float y);
    337         IntPoint origin();
    338 
    339         void setURLForRect(const KURL&, const IntRect&);
    340 
    341         void concatCTM(const AffineTransform&);
    342         AffineTransform getCTM() const;
    343 
    344 #if OS(WINCE) && !PLATFORM(QT)
    345         void setBitmap(PassRefPtr<SharedBitmap>);
    346         const TransformationMatrix& affineTransform() const;
    347         TransformationMatrix& affineTransform();
    348         void resetAffineTransform();
    349         void fillRect(const FloatRect&, const Gradient*);
    350         void drawText(const SimpleFontData* fontData, const GlyphBuffer& glyphBuffer, int from, int numGlyphs, const FloatPoint& point);
    351         void drawFrameControl(const IntRect& rect, unsigned type, unsigned state);
    352         void drawFocusRect(const IntRect& rect);
    353         void paintTextField(const IntRect& rect, unsigned state);
    354         void drawBitmap(SharedBitmap*, const IntRect& dstRect, const IntRect& srcRect, CompositeOperator compositeOp);
    355         void drawBitmapPattern(SharedBitmap*, const FloatRect& tileRectIn, const AffineTransform& patternTransform, const FloatPoint& phase, CompositeOperator op, const FloatRect& destRect, const IntSize& origSourceSize);
    356         void drawIcon(HICON icon, const IntRect& dstRect, UINT flags);
    357         HDC getWindowsContext(const IntRect&, bool supportAlphaBlend = false, bool mayCreateBitmap = true); // The passed in rect is used to create a bitmap for compositing inside transparency layers.
    358         void releaseWindowsContext(HDC, const IntRect&, bool supportAlphaBlend = false, bool mayCreateBitmap = true);    // The passed in HDC should be the one handed back by getWindowsContext.
    359         void drawRoundCorner(bool newClip, RECT clipRect, RECT rectWin, HDC dc, int width, int height);
    360 #elif PLATFORM(WIN)
    361         GraphicsContext(HDC, bool hasAlpha = false); // FIXME: To be removed.
    362         bool inTransparencyLayer() const;
    363         HDC getWindowsContext(const IntRect&, bool supportAlphaBlend = true, bool mayCreateBitmap = true); // The passed in rect is used to create a bitmap for compositing inside transparency layers.
    364         void releaseWindowsContext(HDC, const IntRect&, bool supportAlphaBlend = true, bool mayCreateBitmap = true);    // The passed in HDC should be the one handed back by getWindowsContext.
    365 
    366         // When set to true, child windows should be rendered into this context
    367         // rather than allowing them just to render to the screen. Defaults to
    368         // false.
    369         // FIXME: This is a layering violation. GraphicsContext shouldn't know
    370         // what a "window" is. It would be much more appropriate for this flag
    371         // to be passed as a parameter alongside the GraphicsContext, but doing
    372         // that would require lots of changes in cross-platform code that we
    373         // aren't sure we want to make.
    374         void setShouldIncludeChildWindows(bool);
    375         bool shouldIncludeChildWindows() const;
    376 
    377         class WindowsBitmap : public Noncopyable {
    378         public:
    379             WindowsBitmap(HDC, IntSize);
    380             ~WindowsBitmap();
    381 
    382             HDC hdc() const { return m_hdc; }
    383             UInt8* buffer() const { return m_bitmapBuffer; }
    384             unsigned bufferLength() const { return m_bitmapBufferLength; }
    385             IntSize size() const { return m_size; }
    386             unsigned bytesPerRow() const { return m_bytesPerRow; }
    387 
    388         private:
    389             HDC m_hdc;
    390             HBITMAP m_bitmap;
    391             UInt8* m_bitmapBuffer;
    392             unsigned m_bitmapBufferLength;
    393             IntSize m_size;
    394             unsigned m_bytesPerRow;
    395         };
    396 
    397         WindowsBitmap* createWindowsBitmap(IntSize);
    398         // The bitmap should be non-premultiplied.
    399         void drawWindowsBitmap(WindowsBitmap*, const IntPoint&);
    400 #endif
    401 
    402 #if (PLATFORM(QT) && defined(Q_WS_WIN)) || (PLATFORM(WX) && OS(WINDOWS))
    403         HDC getWindowsContext(const IntRect&, bool supportAlphaBlend = true, bool mayCreateBitmap = true);
    404         void releaseWindowsContext(HDC, const IntRect&, bool supportAlphaBlend = true, bool mayCreateBitmap = true);
    405         bool shouldIncludeChildWindows() const { return false; }
    406 #endif
    407 
    408 #if PLATFORM(WX)
    409         bool inTransparencyLayer() const { return false; }
    410 #endif
    411 
    412 #if PLATFORM(QT)
    413         bool inTransparencyLayer() const;
    414         PlatformPath* currentPath();
    415         QPen pen();
    416 #endif
    417 
    418 #if PLATFORM(GTK)
    419         void setGdkExposeEvent(GdkEventExpose*);
    420         GdkDrawable* gdkDrawable() const;
    421         GdkEventExpose* gdkExposeEvent() const;
    422 #endif
    423 
    424 #if PLATFORM(HAIKU)
    425         pattern getHaikuStrokeStyle();
    426 #endif
    427 
    428     private:
    429         void savePlatformState();
    430         void restorePlatformState();
    431 
    432         void setPlatformTextDrawingMode(int);
    433         void setPlatformFont(const Font& font);
    434 
    435         void setPlatformStrokeColor(const Color&, ColorSpace);
    436         void setPlatformStrokeStyle(const StrokeStyle&);
    437         void setPlatformStrokeThickness(float);
    438         void setPlatformStrokeGradient(Gradient*);
    439         void setPlatformStrokePattern(Pattern*);
    440 
    441         void setPlatformFillColor(const Color&, ColorSpace);
    442         void setPlatformFillGradient(Gradient*);
    443         void setPlatformFillPattern(Pattern*);
    444 
    445         void setPlatformShouldAntialias(bool b);
    446 
    447         void setPlatformShadow(const IntSize&, int blur, const Color&, ColorSpace);
    448         void clearPlatformShadow();
    449 
    450         static void adjustLineToPixelBoundaries(FloatPoint& p1, FloatPoint& p2, float strokeWidth, const StrokeStyle&);
    451 
    452         static GraphicsContextPrivate* createGraphicsContextPrivate();
    453         static void destroyGraphicsContextPrivate(GraphicsContextPrivate*);
    454 
    455         GraphicsContextPrivate* m_common;
    456         GraphicsContextPlatformPrivate* m_data; // Deprecated; m_commmon can just be downcasted. To be removed.
    457     };
    458 
    459 } // namespace WebCore
    460 
    461 #endif // GraphicsContext_h
    462