1/* 2 * Copyright (C) 2007 Kevin Ollivier All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY 14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR 17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 18 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 19 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 20 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 */ 25 26#include "config.h" 27#include "Path.h" 28 29#include "AffineTransform.h" 30#include "FloatPoint.h" 31#include "FloatRect.h" 32#include "NotImplemented.h" 33#include "StrokeStyleApplier.h" 34 35#include <stdio.h> 36 37#include <wx/defs.h> 38#include <wx/graphics.h> 39 40namespace WebCore { 41 42int getWxWindRuleForWindRule(WindRule rule) 43{ 44 if (rule == RULE_EVENODD) 45 return wxODDEVEN_RULE; 46 47 return wxWINDING_RULE; 48} 49 50Path::Path() 51{ 52 m_path = 0; 53 // NB: This only supports the 'default' renderer as determined by wx on 54 // each platform. If an app uses a non-default renderer (e.g. Cairo on Win), 55 // there will be problems, but there's no way we can determine which 56 // renderer an app is using right now with wx API, so we will just handle 57 // the common case. 58#if USE(WXGC) 59 wxGraphicsRenderer* renderer = wxGraphicsRenderer::GetDefaultRenderer(); 60 if (renderer) { 61 wxGraphicsPath path = renderer->CreatePath(); 62 m_path = new wxGraphicsPath(path); 63 } 64#endif 65} 66 67Path::~Path() 68{ 69 clear(); 70} 71 72Path::Path(const Path& path) 73{ 74 m_path = new wxGraphicsPath(*path.m_path); 75} 76 77bool Path::contains(const FloatPoint& point, const WindRule rule) const 78{ 79#if USE(WXGC) 80 if (m_path) { 81#if wxCHECK_VERSION(2,9,0) 82 return m_path->Contains(point.x(), point.y(), static_cast<wxPolygonFillMode>(getWxWindRuleForWindRule(rule))); 83#else 84 return m_path->Contains(point.x(), point.y(), getWxWindRuleForWindRule(rule)); 85#endif 86 } 87#endif 88 return false; 89} 90 91void Path::translate(const FloatSize&) 92{ 93 notImplemented(); 94} 95 96FloatRect Path::boundingRect() const 97{ 98#if USE(WXGC) 99 if (m_path) { 100 return m_path->GetBox(); 101 } 102#endif 103 104 return FloatRect(); 105} 106 107FloatRect Path::strokeBoundingRect(StrokeStyleApplier* applier) 108{ 109 notImplemented(); 110 return FloatRect(); 111} 112 113Path& Path::operator=(const Path&) 114{ 115 notImplemented(); 116 return*this; 117} 118 119void Path::clear() 120{ 121 if (m_path) 122 delete m_path; 123 124#if USE(WXGC) 125 wxGraphicsRenderer* renderer = wxGraphicsRenderer::GetDefaultRenderer(); 126 if (renderer) { 127 wxGraphicsPath path = renderer->CreatePath(); 128 m_path = new wxGraphicsPath(path); 129 } 130#endif 131} 132 133void Path::moveTo(const FloatPoint& point) 134{ 135#if USE(WXGC) 136 if (m_path) 137 m_path->MoveToPoint(point.x(), point.y()); 138#endif 139} 140 141void Path::addLineTo(const FloatPoint& point) 142{ 143#if USE(WXGC) 144 if (m_path) 145 m_path->AddLineToPoint(point.x(), point.y()); 146#endif 147} 148 149void Path::addQuadCurveTo(const FloatPoint& control, const FloatPoint& end) 150{ 151#if USE(WXGC) 152 if (m_path) 153 m_path->AddQuadCurveToPoint(control.x(), control.y(), end.x(), end.y()); 154#endif 155} 156 157void Path::addBezierCurveTo(const FloatPoint& control1, const FloatPoint& control2, const FloatPoint& end) 158{ 159#if USE(WXGC) 160 if (m_path) 161 m_path->AddCurveToPoint(control1.x(), control1.y(), control2.x(), control2.y(), end.x(), end.y()); 162#endif 163} 164 165void Path::addArcTo(const FloatPoint& point1, const FloatPoint& point2, float radius) 166{ 167#if USE(WXGC) 168 if (m_path) 169 m_path->AddArcToPoint(point1.x(), point1.y(), point2.x(), point2.y(), radius); 170#endif 171} 172 173void Path::closeSubpath() 174{ 175#if USE(WXGC) 176 if (m_path) 177 m_path->CloseSubpath(); 178#endif 179} 180 181void Path::addArc(const FloatPoint& point, float radius, float startAngle, float endAngle, bool clockwise) 182{ 183#if USE(WXGC) 184 if (m_path) 185 m_path->AddArc(point.x(), point.y(), radius, startAngle, endAngle, clockwise); 186#endif 187} 188 189void Path::addRect(const FloatRect& rect) 190{ 191#if USE(WXGC) 192 if (m_path) 193 m_path->AddRectangle(rect.x(), rect.y(), rect.width(), rect.height()); 194#endif 195} 196 197void Path::addEllipse(const FloatRect& rect) 198{ 199#if USE(WXGC) 200 if (m_path) 201 m_path->AddEllipse(rect.x(), rect.y(), rect.width(), rect.height()); 202#endif 203} 204 205void Path::transform(const AffineTransform& transform) 206{ 207#if USE(WXGC) 208 if (m_path) 209 m_path->Transform(transform); 210#endif 211} 212 213void Path::apply(void* info, PathApplierFunction function) const 214{ 215 notImplemented(); 216} 217 218bool Path::isEmpty() const 219{ 220#if USE(WXGC) 221 if (m_path) { 222 wxDouble width, height; 223 m_path->GetBox(NULL, NULL, &width, &height); 224 return (width == 0 && height == 0); 225 } 226#endif 227 return true; 228} 229 230bool Path::hasCurrentPoint() const 231{ 232 return !isEmpty(); 233} 234 235} 236