18e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project/* 28e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. 38e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Copyright (C) 2007 Alp Toker <alp@atoker.com> 4643ca7872b450ea4efacab6188849e5aac2ba161Steve Block * Copyright (C) 2008, 2009 Dirk Schulze <krit@webkit.org> 58e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Copyright (C) 2008 Nuanti Ltd. 6643ca7872b450ea4efacab6188849e5aac2ba161Steve Block * Copyright (C) 2009 Brent Fulgham <bfulgham@webkit.org> 781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch * Copyright (C) 2010, 2011 Igalia S.L. 8f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch * Copyright (C) Research In Motion Limited 2010. All rights reserved. 98e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Redistribution and use in source and binary forms, with or without 118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * modification, are permitted provided that the following conditions 128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * are met: 138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 1. Redistributions of source code must retain the above copyright 148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * notice, this list of conditions and the following disclaimer. 158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 2. Redistributions in binary form must reproduce the above copyright 168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * notice, this list of conditions and the following disclaimer in the 178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * documentation and/or other materials provided with the distribution. 188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY 208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR 238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project */ 318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "config.h" 338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "GraphicsContext.h" 348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 352daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#if USE(CAIRO) 368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 375e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block#include "AffineTransform.h" 38bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen#include "CairoUtilities.h" 39a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch#include "ContextShadow.h" 4081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch#include "FloatConversion.h" 418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "FloatRect.h" 428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Font.h" 43a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch#include "GraphicsContextPlatformPrivateCairo.h" 4468513a70bcd92384395513322f1b801e7bf9c729Steve Block#include "OwnPtrCairo.h" 458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "IntRect.h" 468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "NotImplemented.h" 478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Path.h" 488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Pattern.h" 492bde8e466a4451c7319e3a072d118917957d6554Steve Block#include "PlatformContextCairo.h" 502daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#include "PlatformPathCairo.h" 5128040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu#include "RefPtrCairo.h" 528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "SimpleFontData.h" 538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include <cairo.h> 548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include <math.h> 558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include <stdio.h> 568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include <wtf/MathExtras.h> 578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#if PLATFORM(GTK) 598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include <gdk/gdk.h> 608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include <pango/pango.h> 618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#elif PLATFORM(WIN) 628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include <cairo-win32.h> 638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#endif 648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 65e8b154fd68f9b33be40a3590e58347f353835f5cSteve Blockusing namespace std; 66e8b154fd68f9b33be40a3590e58347f353835f5cSteve Block 678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#ifndef M_PI 688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#define M_PI 3.14159265358979323846 698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#endif 708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectnamespace WebCore { 728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 73f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochstatic inline void setPlatformFill(GraphicsContext* context, cairo_t* cr) 74643ca7872b450ea4efacab6188849e5aac2ba161Steve Block{ 756c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen cairo_pattern_t* pattern = 0; 76643ca7872b450ea4efacab6188849e5aac2ba161Steve Block cairo_save(cr); 77f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 78f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch const GraphicsContextState& state = context->state(); 79f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch if (state.fillPattern) { 808a0914b749bbe7da7768e07a7db5c6d4bb09472bSteve Block AffineTransform affine; 81f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch pattern = state.fillPattern->createPlatformPattern(affine); 826c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen cairo_set_source(cr, pattern); 83f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch } else if (state.fillGradient) 84f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_set_source(cr, state.fillGradient->platformGradient()); 85643ca7872b450ea4efacab6188849e5aac2ba161Steve Block else 86f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, context->fillColor()); 87643ca7872b450ea4efacab6188849e5aac2ba161Steve Block cairo_clip_preserve(cr); 88f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_paint_with_alpha(cr, state.globalAlpha); 89643ca7872b450ea4efacab6188849e5aac2ba161Steve Block cairo_restore(cr); 906c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen if (pattern) 916c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen cairo_pattern_destroy(pattern); 92643ca7872b450ea4efacab6188849e5aac2ba161Steve Block} 93643ca7872b450ea4efacab6188849e5aac2ba161Steve Block 94f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochstatic inline void setPlatformStroke(GraphicsContext* context, cairo_t* cr) 95643ca7872b450ea4efacab6188849e5aac2ba161Steve Block{ 966c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen cairo_pattern_t* pattern = 0; 97643ca7872b450ea4efacab6188849e5aac2ba161Steve Block cairo_save(cr); 98f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 99f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch const GraphicsContextState& state = context->state(); 100f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch if (state.strokePattern) { 1018a0914b749bbe7da7768e07a7db5c6d4bb09472bSteve Block AffineTransform affine; 102f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch pattern = state.strokePattern->createPlatformPattern(affine); 1036c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen cairo_set_source(cr, pattern); 104f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch } else if (state.strokeGradient) 105f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_set_source(cr, state.strokeGradient->platformGradient()); 106643ca7872b450ea4efacab6188849e5aac2ba161Steve Block else { 107f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch Color strokeColor = colorWithOverrideAlpha(context->strokeColor().rgb(), context->strokeColor().alpha() / 255.f * state.globalAlpha); 108f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, strokeColor); 109643ca7872b450ea4efacab6188849e5aac2ba161Steve Block } 110f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch if (state.globalAlpha < 1.0f && (state.strokePattern || state.strokeGradient)) { 111643ca7872b450ea4efacab6188849e5aac2ba161Steve Block cairo_push_group(cr); 112f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_paint_with_alpha(cr, state.globalAlpha); 113643ca7872b450ea4efacab6188849e5aac2ba161Steve Block cairo_pop_group_to_source(cr); 114643ca7872b450ea4efacab6188849e5aac2ba161Steve Block } 115643ca7872b450ea4efacab6188849e5aac2ba161Steve Block cairo_stroke_preserve(cr); 116643ca7872b450ea4efacab6188849e5aac2ba161Steve Block cairo_restore(cr); 1176c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen if (pattern) 1186c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen cairo_pattern_destroy(pattern); 119643ca7872b450ea4efacab6188849e5aac2ba161Steve Block} 120643ca7872b450ea4efacab6188849e5aac2ba161Steve Block 1218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// A fillRect helper 1228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic inline void fillRectSourceOver(cairo_t* cr, const FloatRect& rect, const Color& col) 1238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 124f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, col); 1258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_rectangle(cr, rect.x(), rect.y(), rect.width(), rect.height()); 1268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_operator(cr, CAIRO_OPERATOR_OVER); 1278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill(cr); 1288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 130db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Blockstatic void addConvexPolygonToContext(cairo_t* context, size_t numPoints, const FloatPoint* points) 131db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block{ 132db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_move_to(context, points[0].x(), points[0].y()); 133db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block for (size_t i = 1; i < numPoints; i++) 134db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_line_to(context, points[i].x(), points[i].y()); 135db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_close_path(context); 136db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block} 137db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 138a94275402997c11dd2e778633dacf4b7e630a35dBen Murdochenum PathDrawingStyle { 139a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch Fill = 1, 140a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch Stroke = 2, 141a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch FillAndStroke = Fill + Stroke 142a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch}; 143643ca7872b450ea4efacab6188849e5aac2ba161Steve Block 144f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochstatic inline void drawPathShadow(GraphicsContext* context, PathDrawingStyle drawingStyle) 145643ca7872b450ea4efacab6188849e5aac2ba161Steve Block{ 146a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch ContextShadow* shadow = context->contextShadow(); 147a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch ASSERT(shadow); 148a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (shadow->m_type == ContextShadow::NoShadow) 149643ca7872b450ea4efacab6188849e5aac2ba161Steve Block return; 15068513a70bcd92384395513322f1b801e7bf9c729Steve Block 151a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch // Calculate the extents of the rendered solid paths. 1522bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cairoContext = context->platformContext()->cr(); 153f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch OwnPtr<cairo_path_t> path(cairo_copy_path(cairoContext)); 154a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch 155a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch FloatRect solidFigureExtents; 156a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch double x0 = 0; 157a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch double x1 = 0; 158a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch double y0 = 0; 159a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch double y1 = 0; 160a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (drawingStyle & Stroke) { 161a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch cairo_stroke_extents(cairoContext, &x0, &y0, &x1, &y1); 162a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch solidFigureExtents = FloatRect(x0, y0, x1 - x0, y1 - y0); 163a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch } 164a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (drawingStyle & Fill) { 165a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch cairo_fill_extents(cairoContext, &x0, &y0, &x1, &y1); 166a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch FloatRect fillExtents(x0, y0, x1 - x0, y1 - y0); 167a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch solidFigureExtents.unite(fillExtents); 168a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch } 16968513a70bcd92384395513322f1b801e7bf9c729Steve Block 170cad810f21b803229eb11403f9209855525a25d57Steve Block cairo_t* shadowContext = shadow->beginShadowLayer(context, solidFigureExtents); 171a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (!shadowContext) 172a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch return; 173643ca7872b450ea4efacab6188849e5aac2ba161Steve Block 174a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch // It's important to copy the context properties to the new shadow 175a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch // context to preserve things such as the fill rule and stroke width. 176a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch copyContextProperties(cairoContext, shadowContext); 177f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_append_path(shadowContext, path.get()); 178643ca7872b450ea4efacab6188849e5aac2ba161Steve Block 179a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (drawingStyle & Fill) 180f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setPlatformFill(context, shadowContext); 181a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (drawingStyle & Stroke) 182f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setPlatformStroke(context, shadowContext); 183643ca7872b450ea4efacab6188849e5aac2ba161Steve Block 184cad810f21b803229eb11403f9209855525a25d57Steve Block shadow->endShadowLayer(context); 185643ca7872b450ea4efacab6188849e5aac2ba161Steve Block} 186643ca7872b450ea4efacab6188849e5aac2ba161Steve Block 187f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochstatic void fillCurrentCairoPath(GraphicsContext* context, cairo_t* cairoContext) 188db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block{ 189db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_set_fill_rule(cairoContext, context->fillRule() == RULE_EVENODD ? CAIRO_FILL_RULE_EVEN_ODD : CAIRO_FILL_RULE_WINDING); 190f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch drawPathShadow(context, Fill); 191db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 192f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setPlatformFill(context, cairoContext); 193db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_new_path(cairoContext); 194db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block} 195db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 196f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochstatic void strokeCurrentCairoPath(GraphicsContext* context, cairo_t* cairoContext) 197db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block{ 198f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch drawPathShadow(context, Stroke); 199f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setPlatformStroke(context, cairoContext); 200db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_new_path(cairoContext); 201db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block} 202db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 2032bde8e466a4451c7319e3a072d118917957d6554Steve BlockGraphicsContext::GraphicsContext(cairo_t* cr) 2042daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch : m_updatingControlTints(false) 2058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 2062daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch m_data = new GraphicsContextPlatformPrivateToplevel(new PlatformContextCairo(cr)); 2072bde8e466a4451c7319e3a072d118917957d6554Steve Block} 2082bde8e466a4451c7319e3a072d118917957d6554Steve Block 2092bde8e466a4451c7319e3a072d118917957d6554Steve Blockvoid GraphicsContext::platformInit(PlatformContextCairo* platformContext) 2102bde8e466a4451c7319e3a072d118917957d6554Steve Block{ 2112bde8e466a4451c7319e3a072d118917957d6554Steve Block m_data = new GraphicsContextPlatformPrivate(platformContext); 2122bde8e466a4451c7319e3a072d118917957d6554Steve Block if (platformContext) 2132bde8e466a4451c7319e3a072d118917957d6554Steve Block m_data->syncContext(platformContext->cr()); 2142bde8e466a4451c7319e3a072d118917957d6554Steve Block else 2152bde8e466a4451c7319e3a072d118917957d6554Steve Block setPaintingDisabled(true); 2168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 218f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochvoid GraphicsContext::platformDestroy() 2198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 2208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project delete m_data; 2218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2238a0914b749bbe7da7768e07a7db5c6d4bb09472bSteve BlockAffineTransform GraphicsContext::getCTM() const 2245e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block{ 2252bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 2265e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block cairo_matrix_t m; 2275e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block cairo_get_matrix(cr, &m); 2285e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block return AffineTransform(m.xx, m.yx, m.xy, m.yy, m.x0, m.y0); 2295e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block} 2305e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block 2312bde8e466a4451c7319e3a072d118917957d6554Steve BlockPlatformContextCairo* GraphicsContext::platformContext() const 2328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 2332bde8e466a4451c7319e3a072d118917957d6554Steve Block return m_data->platformContext; 2348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::savePlatformState() 2378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 2382daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch platformContext()->save(); 2398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->save(); 240a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_data->shadowStack.append(m_data->shadow); 2418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::restorePlatformState() 2448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 245a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (m_data->shadowStack.isEmpty()) 246a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_data->shadow = ContextShadow(); 247a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch else { 248a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_data->shadow = m_data->shadowStack.last(); 249a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_data->shadowStack.removeLast(); 250a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch } 25181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch 2522daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch platformContext()->restore(); 25381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch m_data->restore(); 2548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// Draws a filled rectangle with a stroked border. 2578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::drawRect(const IntRect& rect) 2588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 2598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 2608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 2618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2622bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 2638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 2648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (fillColor().alpha()) 2668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fillRectSourceOver(cr, rect, fillColor()); 2678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (strokeStyle() != NoStroke) { 269f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, strokeColor()); 2708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project FloatRect r(rect); 2718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project r.inflate(-.5f); 2728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_rectangle(cr, r.x(), r.y(), r.width(), r.height()); 2738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_line_width(cr, 1.0); 2748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_stroke(cr); 2758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 2768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 2788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// This is only used to draw borders. 2818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::drawLine(const IntPoint& point1, const IntPoint& point2) 2828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 2838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 2848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 2858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project StrokeStyle style = strokeStyle(); 2878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (style == NoStroke) 2888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 2898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2902bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 2918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 2928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float width = strokeThickness(); 2948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (width < 1) 2958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project width = 1; 2968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project FloatPoint p1 = point1; 2988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project FloatPoint p2 = point2; 2998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project bool isVerticalLine = (p1.x() == p2.x()); 3008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project adjustLineToPixelBoundaries(p1, p2, width, style); 3028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_line_width(cr, width); 3038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int patWidth = 0; 3058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project switch (style) { 3068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case NoStroke: 3078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case SolidStroke: 3088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 3098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case DottedStroke: 3108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project patWidth = static_cast<int>(width); 3118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 3128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case DashedStroke: 3138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project patWidth = 3*static_cast<int>(width); 3148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 3158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 317f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, strokeColor()); 3188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_antialias(cr, CAIRO_ANTIALIAS_NONE); 3208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (patWidth) { 3228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Do a rect fill of our endpoints. This ensures we always have the 3238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // appearance of being a border. We then draw the actual dotted/dashed line. 3248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (isVerticalLine) { 3258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fillRectSourceOver(cr, FloatRect(p1.x() - width/2, p1.y() - width, width, width), strokeColor()); 3268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fillRectSourceOver(cr, FloatRect(p2.x() - width/2, p2.y(), width, width), strokeColor()); 3278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else { 3288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fillRectSourceOver(cr, FloatRect(p1.x() - width, p1.y() - width/2, width, width), strokeColor()); 3298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fillRectSourceOver(cr, FloatRect(p2.x(), p2.y() - width/2, width, width), strokeColor()); 3308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Example: 80 pixels with a width of 30 pixels. 3338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Remainder is 20. The maximum pixels of line we could paint 3348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // will be 50 pixels. 3358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int distance = (isVerticalLine ? (point2.y() - point1.y()) : (point2.x() - point1.x())) - 2*static_cast<int>(width); 3368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int remainder = distance%patWidth; 3378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int coverage = distance-remainder; 3388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int numSegments = coverage/patWidth; 3398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float patternOffset = 0; 3418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Special case 1px dotted borders for speed. 3428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (patWidth == 1) 3438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project patternOffset = 1.0; 3448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else { 345231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block bool evenNumberOfSegments = !(numSegments % 2); 3468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (remainder) 3478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project evenNumberOfSegments = !evenNumberOfSegments; 3488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (evenNumberOfSegments) { 3498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (remainder) { 3508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project patternOffset += patWidth - remainder; 351231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block patternOffset += remainder / 2; 352231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } else 353231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block patternOffset = patWidth / 2; 354231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } else if (!evenNumberOfSegments) { 3558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (remainder) 356231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block patternOffset = (patWidth - remainder) / 2; 3578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double dash = patWidth; 3618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_dash(cr, &dash, 1, patternOffset); 3628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_move_to(cr, p1.x(), p1.y()); 3658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_line_to(cr, p2.x(), p2.y()); 3668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_stroke(cr); 3688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 3698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 3708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// This method is only used to draw the little circles used in lists. 3728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::drawEllipse(const IntRect& rect) 3738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 3748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 3758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 3768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3772bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 3788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 3798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float yRadius = .5 * rect.height(); 3808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float xRadius = .5 * rect.width(); 3818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_translate(cr, rect.x() + xRadius, rect.y() + yRadius); 3828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_scale(cr, xRadius, yRadius); 3838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_arc(cr, 0., 0., 1., 0., 2 * M_PI); 3848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 3858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (fillColor().alpha()) { 387f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, fillColor()); 3888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill_preserve(cr); 3898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (strokeStyle() != NoStroke) { 392f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, strokeColor()); 3938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_line_width(cr, strokeThickness()); 3948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_stroke(cr); 395db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block } else 396db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_new_path(cr); 3978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 3988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::strokeArc(const IntRect& rect, int startAngle, int angleSpan) 4008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 4018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled() || strokeStyle() == NoStroke) 4028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 4038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int x = rect.x(); 4058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int y = rect.y(); 4068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float w = rect.width(); 4078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float h = rect.height(); 4088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float scaleFactor = h / w; 4098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float reverseScaleFactor = w / h; 4108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float hRadius = w / 2; 4128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float vRadius = h / 2; 4138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float fa = startAngle; 4148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float falen = fa + angleSpan; 4158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4162bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 4178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 4188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (w != h) 4208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_scale(cr, 1., scaleFactor); 421231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 4228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_arc_negative(cr, x + hRadius, (y + vRadius) * reverseScaleFactor, hRadius, -fa * M_PI/180, -falen * M_PI/180); 4238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (w != h) 4258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_scale(cr, 1., reverseScaleFactor); 4268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float width = strokeThickness(); 4288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int patWidth = 0; 429231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 4308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project switch (strokeStyle()) { 431231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case DottedStroke: 432231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block patWidth = static_cast<int>(width / 2); 433231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 434231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case DashedStroke: 435231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block patWidth = 3 * static_cast<int>(width / 2); 436231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 437231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block default: 438231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 4398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 441f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, strokeColor()); 4428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (patWidth) { 4448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Example: 80 pixels with a width of 30 pixels. 4458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Remainder is 20. The maximum pixels of line we could paint 4468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // will be 50 pixels. 4478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int distance; 4488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (hRadius == vRadius) 4498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project distance = static_cast<int>((M_PI * hRadius) / 2.0); 4508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else // We are elliptical and will have to estimate the distance 4518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project distance = static_cast<int>((M_PI * sqrtf((hRadius * hRadius + vRadius * vRadius) / 2.0)) / 2.0); 452231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 4538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int remainder = distance % patWidth; 4548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int coverage = distance - remainder; 4558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int numSegments = coverage / patWidth; 4568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project float patternOffset = 0.0; 4588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Special case 1px dotted borders for speed. 4598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (patWidth == 1) 4608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project patternOffset = 1.0; 4618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else { 462231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block bool evenNumberOfSegments = !(numSegments % 2); 4638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (remainder) 4648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project evenNumberOfSegments = !evenNumberOfSegments; 4658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (evenNumberOfSegments) { 4668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (remainder) { 4678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project patternOffset += patWidth - remainder; 4688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project patternOffset += remainder / 2.0; 4698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else 4708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project patternOffset = patWidth / 2.0; 4718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else { 4728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (remainder) 4738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project patternOffset = (patWidth - remainder) / 2.0; 4748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double dash = patWidth; 4788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_dash(cr, &dash, 1, patternOffset); 4798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_stroke(cr); 4828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 4838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 4848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::drawConvexPolygon(size_t npoints, const FloatPoint* points, bool shouldAntialias) 4868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 4878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 4888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 4898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (npoints <= 1) 4918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 4928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4932bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 4948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 4968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_antialias(cr, shouldAntialias ? CAIRO_ANTIALIAS_DEFAULT : CAIRO_ANTIALIAS_NONE); 497db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block addConvexPolygonToContext(cr, npoints, points); 4988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (fillColor().alpha()) { 500f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, fillColor()); 5018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, CAIRO_FILL_RULE_EVEN_ODD); 5028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill_preserve(cr); 5038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 5048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (strokeStyle() != NoStroke) { 506f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, strokeColor()); 5078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_line_width(cr, strokeThickness()); 5088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_stroke(cr); 509db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block } else 510db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_new_path(cr); 5118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 5138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 5148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5150617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsenvoid GraphicsContext::clipConvexPolygon(size_t numPoints, const FloatPoint* points, bool antialiased) 516ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{ 517ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block if (paintingDisabled()) 518ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block return; 519ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block 520ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block if (numPoints <= 1) 521ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block return; 522db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 5232bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 524db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 525db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_new_path(cr); 526db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_fill_rule_t savedFillRule = cairo_get_fill_rule(cr); 527db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_antialias_t savedAntialiasRule = cairo_get_antialias(cr); 528db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 5295abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick cairo_set_antialias(cr, antialiased ? CAIRO_ANTIALIAS_DEFAULT : CAIRO_ANTIALIAS_NONE); 530db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_set_fill_rule(cr, CAIRO_FILL_RULE_WINDING); 531db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block addConvexPolygonToContext(cr, numPoints, points); 532db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_clip(cr); 533db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 534db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_set_antialias(cr, savedAntialiasRule); 535db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block cairo_set_fill_rule(cr, savedFillRule); 536ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block} 537ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block 538f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochvoid GraphicsContext::fillPath(const Path& path) 5398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 5408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 5418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 5428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5432bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 544f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setPathOnCairoContext(cr, path.platformPath()->context()); 545f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch fillCurrentCairoPath(this, cr); 5468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 5478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 548f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochvoid GraphicsContext::strokePath(const Path& path) 5498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 5508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 5518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 5528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5532bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 554f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setPathOnCairoContext(cr, path.platformPath()->context()); 555f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch strokeCurrentCairoPath(this, cr); 556d06194330da2bb8da887d2e1adeacb3a5c1504b2Steve Block} 557d06194330da2bb8da887d2e1adeacb3a5c1504b2Steve Block 5588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::fillRect(const FloatRect& rect) 5598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 5608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 5618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 5628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5632bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 564e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke cairo_save(cr); 5658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_rectangle(cr, rect.x(), rect.y(), rect.width(), rect.height()); 566f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch fillCurrentCairoPath(this, cr); 567e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke cairo_restore(cr); 5688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 5698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 570a94275402997c11dd2e778633dacf4b7e630a35dBen Murdochvoid GraphicsContext::fillRect(const FloatRect& rect, const Color& color, ColorSpace) 5718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 5728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 5738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 5748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 575cad810f21b803229eb11403f9209855525a25d57Steve Block if (hasShadow()) 576a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_data->shadow.drawRectShadow(this, enclosingIntRect(rect)); 577a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch 5788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (color.alpha()) 5792bde8e466a4451c7319e3a072d118917957d6554Steve Block fillRectSourceOver(platformContext()->cr(), rect, color); 5808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 5818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::clip(const FloatRect& rect) 5838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 5848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 5858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 5868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5872bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 5888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_rectangle(cr, rect.x(), rect.y(), rect.width(), rect.height()); 5898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill_rule_t savedFillRule = cairo_get_fill_rule(cr); 5908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, CAIRO_FILL_RULE_WINDING); 5918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_clip(cr); 5928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, savedFillRule); 5938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->clip(rect); 5948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 5958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 596f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochvoid GraphicsContext::clipPath(const Path& path, WindRule clipRule) 597635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 598635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (paintingDisabled()) 599635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return; 600635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 6012bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 602f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setPathOnCairoContext(cr, path.platformPath()->context()); 603635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project cairo_set_fill_rule(cr, clipRule == RULE_EVENODD ? CAIRO_FILL_RULE_EVEN_ODD : CAIRO_FILL_RULE_WINDING); 604635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project cairo_clip(cr); 605635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 606635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 607f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochstatic inline void adjustFocusRingColor(Color& color) 608d0825bca7fe65beaee391d30da42e937db621564Steve Block{ 609f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch#if !PLATFORM(GTK) 610f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch // Force the alpha to 50%. This matches what the Mac does with outline rings. 611f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch color.setRGB(makeRGBA(color.red(), color.green(), color.blue(), 127)); 612f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch#endif 613f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch} 614f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 615f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochstatic inline void adjustFocusRingLineWidth(int& width) 616f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch{ 617f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch#if PLATFORM(GTK) 618f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch width = 2; 619f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch#endif 620f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch} 621f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 622f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochstatic inline StrokeStyle focusRingStrokeStyle() 623f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch{ 624f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch#if PLATFORM(GTK) 625f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch return DottedStroke; 626f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch#else 627f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch return SolidStroke; 628f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch#endif 629f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch} 630f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 631f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochvoid GraphicsContext::drawFocusRing(const Path& path, int width, int /* offset */, const Color& color) 632f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch{ 633f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch // FIXME: We should draw paths that describe a rectangle with rounded corners 634f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch // so as to be consistent with how we draw rectangular focus rings. 635f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch Color ringColor = color; 636f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch adjustFocusRingColor(ringColor); 637f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch adjustFocusRingLineWidth(width); 638f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 6392bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 640f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_save(cr); 641f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch appendWebCorePathToCairoContext(cr, path); 642f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, ringColor); 643f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_set_line_width(cr, width); 644f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setPlatformStrokeStyle(focusRingStrokeStyle()); 645f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_stroke(cr); 646f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_restore(cr); 647d0825bca7fe65beaee391d30da42e937db621564Steve Block} 648d0825bca7fe65beaee391d30da42e937db621564Steve Block 649d0825bca7fe65beaee391d30da42e937db621564Steve Blockvoid GraphicsContext::drawFocusRing(const Vector<IntRect>& rects, int width, int /* offset */, const Color& color) 6508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 6518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 6528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 6538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 6548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project unsigned rectCount = rects.size(); 6558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 6562bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 6578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 6588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_push_group(cr); 6598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_new_path(cr); 6608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 6618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#if PLATFORM(GTK) 662ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#ifdef GTK_API_VERSION_2 6638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project GdkRegion* reg = gdk_region_new(); 664ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#else 665ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block cairo_region_t* reg = cairo_region_create(); 666ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#endif 667ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block 6688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project for (unsigned i = 0; i < rectCount; i++) { 669ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#ifdef GTK_API_VERSION_2 6708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project GdkRectangle rect = rects[i]; 6718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gdk_region_union_with_rect(reg, &rect); 672ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#else 673ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block cairo_rectangle_int_t rect = rects[i]; 674ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block cairo_region_union_rectangle(reg, &rect); 675ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#endif 6768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 6778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gdk_cairo_region(cr, reg); 678ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#ifdef GTK_API_VERSION_2 6798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gdk_region_destroy(reg); 680ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#else 681ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block cairo_region_destroy(reg); 682ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#endif 6838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#else 684d0825bca7fe65beaee391d30da42e937db621564Steve Block int radius = (width - 1) / 2; 685a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch Path path; 686a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch for (unsigned i = 0; i < rectCount; ++i) { 687a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (i > 0) 688a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch path.clear(); 689a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch path.addRoundedRect(rects[i], FloatSize(radius, radius)); 690a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch appendWebCorePathToCairoContext(cr, path); 691a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch } 6928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#endif 693f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch Color ringColor = color; 694f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch adjustFocusRingColor(ringColor); 695f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch adjustFocusRingLineWidth(width); 696f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, ringColor); 697f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch cairo_set_line_width(cr, width); 698f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setPlatformStrokeStyle(focusRingStrokeStyle()); 6998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_operator(cr, CAIRO_OPERATOR_OVER); 7018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_stroke_preserve(cr); 7028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_operator(cr, CAIRO_OPERATOR_CLEAR); 7048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, CAIRO_FILL_RULE_WINDING); 7058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill(cr); 7068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_pop_group_to_source(cr); 7088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_operator(cr, CAIRO_OPERATOR_OVER); 7098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_paint(cr); 7108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 7118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 7128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 71381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochvoid GraphicsContext::drawLineForText(const FloatPoint& origin, float width, bool printing) 7148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 7158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 7168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 7178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 71881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch FloatPoint endPoint = origin + FloatSize(width, 0); 71981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch 72081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch // FIXME: Loss of precision here. Might consider rounding. 72181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch drawLine(IntPoint(origin.x(), origin.y()), IntPoint(endPoint.x(), endPoint.y())); 7228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 7238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 724ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#if !PLATFORM(GTK) 725ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#include "DrawErrorUnderline.h" 726ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#endif 727ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block 72881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochvoid GraphicsContext::drawLineForTextChecking(const FloatPoint& origin, float width, TextCheckingLineStyle style) 7298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 7308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 7318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 7328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7332bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 7348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 7358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7365ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen switch (style) { 7375ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen case TextCheckingSpellingLineStyle: 7388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_source_rgb(cr, 1, 0, 0); 7395ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen break; 7405ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen case TextCheckingGrammarLineStyle: 7415ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen cairo_set_source_rgb(cr, 0, 1, 0); 7425ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen break; 7435ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen default: 7445ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen cairo_restore(cr); 7455ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return; 7465ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen } 7478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#if PLATFORM(GTK) 7498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // We ignore most of the provided constants in favour of the platform style 7508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project pango_cairo_show_error_underline(cr, origin.x(), origin.y(), width, cMisspellingLineThickness); 7518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#else 752ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block drawErrorUnderline(cr, origin.x(), origin.y(), width, cMisspellingLineThickness); 7538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#endif 7548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 7568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 7578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7582daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben MurdochFloatRect GraphicsContext::roundToDevicePixels(const FloatRect& frect, RoundingMode) 7598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 7608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project FloatRect result; 7618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double x = frect.x(); 7628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double y = frect.y(); 7632bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 7648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_user_to_device(cr, &x, &y); 7658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project x = round(x); 7668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project y = round(y); 7678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_device_to_user(cr, &x, &y); 76881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch result.setX(narrowPrecisionToFloat(x)); 76981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch result.setY(narrowPrecisionToFloat(y)); 77081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch 77181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch // We must ensure width and height are at least 1 (or -1) when 77281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch // we're given float values in the range between 0 and 1 (or -1 and 0). 77381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch double width = frect.width(); 77481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch double height = frect.height(); 77581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch cairo_user_to_device_distance(cr, &width, &height); 77681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch if (width > -1 && width < 0) 77781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch width = -1; 77881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch else if (width > 0 && width < 1) 77981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch width = 1; 78081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch else 78181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch width = round(width); 78281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch if (height > -1 && width < 0) 78381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch height = -1; 78481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch else if (height > 0 && height < 1) 78581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch height = 1; 78681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch else 78781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch height = round(height); 78881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch cairo_device_to_user_distance(cr, &width, &height); 78981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch result.setWidth(narrowPrecisionToFloat(width)); 79081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch result.setHeight(narrowPrecisionToFloat(height)); 79181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch 7928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return result; 7938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 7948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::translate(float x, float y) 7968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 7978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 7988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 7998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8002bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 8018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_translate(cr, x, y); 8028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->translate(x, y); 8038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 805643ca7872b450ea4efacab6188849e5aac2ba161Steve Blockvoid GraphicsContext::setPlatformFillColor(const Color& col, ColorSpace colorSpace) 8068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Cairo contexts can't hold separate fill and stroke colors 8088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // so we set them just before we actually fill or stroke 8098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 811643ca7872b450ea4efacab6188849e5aac2ba161Steve Blockvoid GraphicsContext::setPlatformStrokeColor(const Color& col, ColorSpace colorSpace) 8128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Cairo contexts can't hold separate fill and stroke colors 8148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // so we set them just before we actually fill or stroke 8158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::setPlatformStrokeThickness(float strokeThickness) 8188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 8208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 8218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8222bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_line_width(platformContext()->cr(), strokeThickness); 8238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 825cad810f21b803229eb11403f9209855525a25d57Steve Blockvoid GraphicsContext::setPlatformStrokeStyle(StrokeStyle strokeStyle) 8268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project static double dashPattern[] = {5.0, 5.0}; 8288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project static double dotPattern[] = {1.0, 1.0}; 8298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 8318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 8328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project switch (strokeStyle) { 8348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case NoStroke: 8358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // FIXME: is it the right way to emulate NoStroke? 8362bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_line_width(platformContext()->cr(), 0); 8378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 8388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case SolidStroke: 8392bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_dash(platformContext()->cr(), 0, 0, 0); 8408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 8418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case DottedStroke: 8422bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_dash(platformContext()->cr(), dotPattern, 2, 0); 8438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 8448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case DashedStroke: 8452bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_dash(platformContext()->cr(), dashPattern, 2, 0); 8468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 8478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 8488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::setURLForRect(const KURL& link, const IntRect& destRect) 8518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project notImplemented(); 8538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8555e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Blockvoid GraphicsContext::concatCTM(const AffineTransform& transform) 8565e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block{ 8575e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block if (paintingDisabled()) 8585e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block return; 8595e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block 8602bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 8615e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block const cairo_matrix_t matrix = cairo_matrix_t(transform); 8625e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block cairo_transform(cr, &matrix); 8635e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block m_data->concatCTM(transform); 8645e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block} 8655e2bc6953fe6923165b8a5d7679939693a1d58d6Steve Block 86681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochvoid GraphicsContext::setCTM(const AffineTransform& transform) 86781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch{ 86881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch if (paintingDisabled()) 86981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch return; 87081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch 8712bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 87281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch const cairo_matrix_t matrix = cairo_matrix_t(transform); 87381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch cairo_set_matrix(cr, &matrix); 87481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch m_data->setCTM(transform); 87581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch} 87681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch 8778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::addInnerRoundedRectClip(const IntRect& rect, int thickness) 8788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 8808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 8818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8822bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 8838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project clip(rect); 8848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Path p; 8868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project FloatRect r(rect); 8878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Add outer ellipse 8888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project p.addEllipse(r); 8898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Add inner ellipse 8908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project r.inflate(-thickness); 8918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project p.addEllipse(r); 892db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block appendWebCorePathToCairoContext(cr, p); 8938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill_rule_t savedFillRule = cairo_get_fill_rule(cr); 8958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, CAIRO_FILL_RULE_EVEN_ODD); 8968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_clip(cr); 8978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, savedFillRule); 8988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 900a94275402997c11dd2e778633dacf4b7e630a35dBen Murdochvoid GraphicsContext::setPlatformShadow(FloatSize const& size, float blur, Color const& color, ColorSpace) 9018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 902a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch // Cairo doesn't support shadows natively, they are drawn manually in the draw* functions 903f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch if (m_state.shadowsIgnoreTransforms) { 904643ca7872b450ea4efacab6188849e5aac2ba161Steve Block // Meaning that this graphics context is associated with a CanvasRenderingContext 905643ca7872b450ea4efacab6188849e5aac2ba161Steve Block // We flip the height since CG and HTML5 Canvas have opposite Y axis 906f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch m_state.shadowOffset = FloatSize(size.width(), -size.height()); 907a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_data->shadow = ContextShadow(color, blur, FloatSize(size.width(), -size.height())); 908a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch } else 909a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_data->shadow = ContextShadow(color, blur, FloatSize(size.width(), size.height())); 910f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 911f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch m_data->shadow.setShadowsIgnoreTransforms(m_state.shadowsIgnoreTransforms); 912643ca7872b450ea4efacab6188849e5aac2ba161Steve Block} 913643ca7872b450ea4efacab6188849e5aac2ba161Steve Block 914a94275402997c11dd2e778633dacf4b7e630a35dBen MurdochContextShadow* GraphicsContext::contextShadow() 915643ca7872b450ea4efacab6188849e5aac2ba161Steve Block{ 916a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch return &m_data->shadow; 9178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::clearPlatformShadow() 9208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 921a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_data->shadow.clear(); 9228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::beginTransparencyLayer(float opacity) 9258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 9278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9292bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 9308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_push_group(cr); 9318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->layers.append(opacity); 9328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->beginTransparencyLayer(); 9338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::endTransparencyLayer() 9368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 9388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9402bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 9418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_pop_group_to_source(cr); 9438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_paint_with_alpha(cr, m_data->layers.last()); 9448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->layers.removeLast(); 9458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->endTransparencyLayer(); 9468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::clearRect(const FloatRect& rect) 9498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 9518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9532bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 9548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 9568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_rectangle(cr, rect.x(), rect.y(), rect.width(), rect.height()); 9578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_operator(cr, CAIRO_OPERATOR_CLEAR); 9588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill(cr); 9598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 9608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::strokeRect(const FloatRect& rect, float width) 9638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 9658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9672bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 9688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 9698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_rectangle(cr, rect.x(), rect.y(), rect.width(), rect.height()); 9708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_line_width(cr, width); 971f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch strokeCurrentCairoPath(this, cr); 9728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 9738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::setLineCap(LineCap lineCap) 9768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 9788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_line_cap_t cairoCap = CAIRO_LINE_CAP_BUTT; 9818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project switch (lineCap) { 982231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case ButtCap: 983231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block // no-op 984231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 985231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case RoundCap: 986231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block cairoCap = CAIRO_LINE_CAP_ROUND; 987231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 988231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case SquareCap: 989231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block cairoCap = CAIRO_LINE_CAP_SQUARE; 990231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 9918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 9922bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_line_cap(platformContext()->cr(), cairoCap); 9938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::setLineDash(const DashArray& dashes, float dashOffset) 9968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9972bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_dash(platformContext()->cr(), dashes.data(), dashes.size(), dashOffset); 9988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::setLineJoin(LineJoin lineJoin) 10018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 10028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 10038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 10048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_line_join_t cairoJoin = CAIRO_LINE_JOIN_MITER; 10068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project switch (lineJoin) { 1007231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case MiterJoin: 1008231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block // no-op 1009231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 1010231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case RoundJoin: 1011231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block cairoJoin = CAIRO_LINE_JOIN_ROUND; 1012231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 1013231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case BevelJoin: 1014231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block cairoJoin = CAIRO_LINE_JOIN_BEVEL; 1015231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 10168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 10172bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_line_join(platformContext()->cr(), cairoJoin); 10188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 10198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::setMiterLimit(float miter) 10218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 10228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 10238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 10248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10252bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_miter_limit(platformContext()->cr(), miter); 10268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 10278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::setAlpha(float alpha) 10298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1030f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch m_state.globalAlpha = alpha; 10318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 10328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectfloat GraphicsContext::getAlpha() 10348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1035f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch return m_state.globalAlpha; 10368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 10378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1038f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochvoid GraphicsContext::setPlatformCompositeOperation(CompositeOperator op) 10398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 10408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 10418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 10428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10432bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_operator(platformContext()->cr(), toCairoOperator(op)); 10448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 10458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::clip(const Path& path) 10478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 10488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 10498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 10508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10512bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 1052bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen OwnPtr<cairo_path_t> p(cairo_copy_path(path.platformPath()->context())); 1053bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen cairo_append_path(cr, p.get()); 10548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill_rule_t savedFillRule = cairo_get_fill_rule(cr); 10558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, CAIRO_FILL_RULE_WINDING); 10568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_clip(cr); 10578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, savedFillRule); 10588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->clip(path); 10598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 10608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1061cac0f67c402d107cdb10971b95719e2ff9c7c76bSteve Blockvoid GraphicsContext::canvasClip(const Path& path) 1062cac0f67c402d107cdb10971b95719e2ff9c7c76bSteve Block{ 1063cac0f67c402d107cdb10971b95719e2ff9c7c76bSteve Block clip(path); 1064cac0f67c402d107cdb10971b95719e2ff9c7c76bSteve Block} 1065cac0f67c402d107cdb10971b95719e2ff9c7c76bSteve Block 10668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::clipOut(const Path& path) 10678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 10688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 10698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 10708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10712bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 10728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double x1, y1, x2, y2; 10738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_clip_extents(cr, &x1, &y1, &x2, &y2); 10748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_rectangle(cr, x1, y1, x2 - x1, y2 - y1); 1075db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block appendWebCorePathToCairoContext(cr, path); 10768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill_rule_t savedFillRule = cairo_get_fill_rule(cr); 10788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, CAIRO_FILL_RULE_EVEN_ODD); 10798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_clip(cr); 10808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, savedFillRule); 10818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 10828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::rotate(float radians) 10848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 10858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 10868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 10878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10882bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_rotate(platformContext()->cr(), radians); 10898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->rotate(radians); 10908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 10918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::scale(const FloatSize& size) 10938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 10948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 10958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 10968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10972bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_scale(platformContext()->cr(), size.width(), size.height()); 10988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->scale(size); 10998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 11008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::clipOut(const IntRect& r) 11028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 11038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 11048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 11058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11062bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 11078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double x1, y1, x2, y2; 11088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_clip_extents(cr, &x1, &y1, &x2, &y2); 1109643ca7872b450ea4efacab6188849e5aac2ba161Steve Block cairo_rectangle(cr, x1, y1, x2 - x1, y2 - y1); 11108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_rectangle(cr, r.x(), r.y(), r.width(), r.height()); 11118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill_rule_t savedFillRule = cairo_get_fill_rule(cr); 11128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, CAIRO_FILL_RULE_EVEN_ODD); 11138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_clip(cr); 11148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_set_fill_rule(cr, savedFillRule); 11158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 11168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11175ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenstatic inline FloatPoint getPhase(const FloatRect& dest, const FloatRect& tile) 11185ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 11195ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen FloatPoint phase = dest.location(); 11205ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen phase.move(-tile.x(), -tile.y()); 11215ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 11225ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return phase; 11235ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 11245ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 1125643ca7872b450ea4efacab6188849e5aac2ba161Steve Blockvoid GraphicsContext::fillRoundedRect(const IntRect& r, const IntSize& topLeft, const IntSize& topRight, const IntSize& bottomLeft, const IntSize& bottomRight, const Color& color, ColorSpace colorSpace) 11268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 11278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 11288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 11298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1130cad810f21b803229eb11403f9209855525a25d57Steve Block if (hasShadow()) 1131a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_data->shadow.drawRectShadow(this, r, topLeft, topRight, bottomLeft, bottomRight); 1132a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch 11332bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_t* cr = platformContext()->cr(); 11348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_save(cr); 1135a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch Path path; 1136a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch path.addRoundedRect(r, topLeft, topRight, bottomLeft, bottomRight); 1137a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch appendWebCorePathToCairoContext(cr, path); 1138f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch setSourceRGBAFromColor(cr, color); 11398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_fill(cr); 11408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project cairo_restore(cr); 11418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 11428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#if PLATFORM(GTK) 11448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::setGdkExposeEvent(GdkEventExpose* expose) 11458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 11468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_data->expose = expose; 11478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 11488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectGdkEventExpose* GraphicsContext::gdkExposeEvent() const 11508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 11518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return m_data->expose; 11528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 11538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1154f05b935882198ccf7d81675736e3aeb089c5113aBen MurdochGdkWindow* GraphicsContext::gdkWindow() const 11558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 11568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!m_data->expose) 11578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return 0; 11588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1159f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch return m_data->expose->window; 11608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 11618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#endif 11628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1163635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectvoid GraphicsContext::setPlatformShouldAntialias(bool enable) 11648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 11658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (paintingDisabled()) 11668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 11678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // When true, use the default Cairo backend antialias mode (usually this 11698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // enables standard 'grayscale' antialiasing); false to explicitly disable 11708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // antialiasing. This is the same strategy as used in drawConvexPolygon(). 11712bde8e466a4451c7319e3a072d118917957d6554Steve Block cairo_set_antialias(platformContext()->cr(), enable ? CAIRO_ANTIALIAS_DEFAULT : CAIRO_ANTIALIAS_NONE); 11728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 11738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid GraphicsContext::setImageInterpolationQuality(InterpolationQuality) 11758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 11768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 11778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectInterpolationQuality GraphicsContext::imageInterpolationQuality() const 11798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 11808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return InterpolationDefault; 11818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 11828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} // namespace WebCore 11848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11852daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#endif // USE(CAIRO) 1186