SkPathOpsTypes.h revision ab87d7abf1df007c90bef2e916294ca325d81c81
107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com/*
207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com * Copyright 2012 Google Inc.
307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com *
407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com * Use of this source code is governed by a BSD-style license that can be
507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com * found in the LICENSE file.
607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com */
707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#ifndef SkPathOpsTypes_DEFINED
807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#define SkPathOpsTypes_DEFINED
907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
1007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#include <float.h>  // for FLT_EPSILON
1107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#include <math.h>   // for fabs, sqrt
1207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
1307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#include "SkFloatingPoint.h"
14277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com#include "SkPath.h"
1507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#include "SkPathOps.h"
1607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#include "SkPathOpsDebug.h"
1707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#include "SkScalar.h"
1807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
1907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comenum SkPathOpsMask {
2007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    kWinding_PathOpsMask = -1,
2107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    kNo_PathOpsMask = 0,
2207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    kEvenOdd_PathOpsMask = 1
2307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com};
2407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
2555888e44171ffd48b591d19256884a969fe4da17caryclarkclass SkChunkAlloc;
2654359294a7c9dc54802d512a5d891a35c1663392caryclarkclass SkOpCoincidence;
2754359294a7c9dc54802d512a5d891a35c1663392caryclarkclass SkOpContour;
28624637cc8ec22c000409704d0b403ac1b81ad4b0caryclarkclass SkOpContourHead;
2926ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclarkclass SkIntersections;
3026ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclarkclass SkIntersectionHelper;
3154359294a7c9dc54802d512a5d891a35c1663392caryclark
32ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clarkenum class SkOpPhase : char {
33ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    kNoChange,
34ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    kIntersecting,
35ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    kWalking,
36ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    kFixWinding,
37ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark};
38ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark
3954359294a7c9dc54802d512a5d891a35c1663392caryclarkclass SkOpGlobalState {
4054359294a7c9dc54802d512a5d891a35c1663392caryclarkpublic:
4155888e44171ffd48b591d19256884a969fe4da17caryclark    SkOpGlobalState(SkOpContourHead* head,
4255888e44171ffd48b591d19256884a969fe4da17caryclark                    SkChunkAlloc* allocator  SkDEBUGPARAMS(bool debugSkipAssert)
43d4349723fac9c0fd4dcf8c275fb7c756bdfdff7bcaryclark                    SkDEBUGPARAMS(const char* testName));
4454359294a7c9dc54802d512a5d891a35c1663392caryclark
45624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark    enum {
46624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark        kMaxWindingTries = 10
47624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark    };
48624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark
4929b2563afb1677515739f1d24fb27733626eca92caryclark    bool allocatedOpSpan() const {
5029b2563afb1677515739f1d24fb27733626eca92caryclark        return fAllocatedOpSpan;
5129b2563afb1677515739f1d24fb27733626eca92caryclark    }
5229b2563afb1677515739f1d24fb27733626eca92caryclark
5355888e44171ffd48b591d19256884a969fe4da17caryclark    SkChunkAlloc* allocator() {
5455888e44171ffd48b591d19256884a969fe4da17caryclark        return fAllocator;
5555888e44171ffd48b591d19256884a969fe4da17caryclark    }
5655888e44171ffd48b591d19256884a969fe4da17caryclark
5726ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    bool angleCoincidence() const {
5854359294a7c9dc54802d512a5d891a35c1663392caryclark        return fAngleCoincidence;
5954359294a7c9dc54802d512a5d891a35c1663392caryclark    }
6054359294a7c9dc54802d512a5d891a35c1663392caryclark
614e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark    void bumpNested() {
624e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark        ++fNested;
634e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark    }
644e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark
654e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark    void clearNested() {
664e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark        fNested = 0;
674e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark    }
684e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark
6954359294a7c9dc54802d512a5d891a35c1663392caryclark    SkOpCoincidence* coincidence() {
7054359294a7c9dc54802d512a5d891a35c1663392caryclark        return fCoincidence;
7154359294a7c9dc54802d512a5d891a35c1663392caryclark    }
7254359294a7c9dc54802d512a5d891a35c1663392caryclark
73624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark    SkOpContourHead* contourHead() {
74624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark        return fContourHead;
75624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark    }
76624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark
7754359294a7c9dc54802d512a5d891a35c1663392caryclark#ifdef SK_DEBUG
7855888e44171ffd48b591d19256884a969fe4da17caryclark    const class SkOpAngle* debugAngle(int id) const;
7955888e44171ffd48b591d19256884a969fe4da17caryclark    const SkOpCoincidence* debugCoincidence() const;
8030b9fdd6a1d607bde20c793af65b5e2e8a1737cacaryclark    SkOpContour* debugContour(int id) const;
8154359294a7c9dc54802d512a5d891a35c1663392caryclark    const class SkOpPtT* debugPtT(int id) const;
8227c8eb8ffd7e221693d840c2b9279d53fe6f03d4caryclark    bool debugRunFail() const;
8354359294a7c9dc54802d512a5d891a35c1663392caryclark    const class SkOpSegment* debugSegment(int id) const;
84dae6b97705fde08958b1a36fa6ce685d28fc692ccaryclark    bool debugSkipAssert() const { return fDebugSkipAssert; }
8554359294a7c9dc54802d512a5d891a35c1663392caryclark    const class SkOpSpanBase* debugSpan(int id) const;
86d4349723fac9c0fd4dcf8c275fb7c756bdfdff7bcaryclark    const char* debugTestName() const { return fDebugTestName; }
874e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark#endif
884e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark
8926ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark#if DEBUG_T_SECT_LOOP_COUNT
9026ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    void debugAddLoopCount(SkIntersections* , const SkIntersectionHelper& ,
9126ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark        const SkIntersectionHelper& );
9226ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    void debugDoYourWorst(SkOpGlobalState* );
9326ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    void debugLoopReport();
9426ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    void debugResetLoopCounts();
9526ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark#endif
9626ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark
9755888e44171ffd48b591d19256884a969fe4da17caryclark#if DEBUG_COINCIDENCE
9855888e44171ffd48b591d19256884a969fe4da17caryclark    void debugSetCheckHealth(bool check) { fDebugCheckHealth = check; }
9955888e44171ffd48b591d19256884a969fe4da17caryclark    bool debugCheckHealth() const { return fDebugCheckHealth; }
10055888e44171ffd48b591d19256884a969fe4da17caryclark#endif
10155888e44171ffd48b591d19256884a969fe4da17caryclark
102ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark#if DEBUG_VALIDATE || DEBUG_COIN
103ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    void debugSetPhase(const char* funcName  DEBUG_COIN_DECLARE_PARAMS()) const;
104ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark#endif
105ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark
106ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark#if DEBUG_COIN
107ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    void debugAddToCoinChangedDict();
108ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    void debugAddToGlobalCoinDicts();
109ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    SkPathOpsDebug::CoinDict* debugCoinChangedDict() { return &fCoinChangedDict; }
110ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    const SkPathOpsDebug::CoinDictEntry& debugCoinDictEntry() const { return fCoinDictEntry; }
111ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark
112ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    static void DumpCoinDict();
113ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark#endif
114ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark
115ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark
1164e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark    int nested() const {
1174e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark        return fNested;
1184e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark    }
11954359294a7c9dc54802d512a5d891a35c1663392caryclark
1204e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark#ifdef SK_DEBUG
12154359294a7c9dc54802d512a5d891a35c1663392caryclark    int nextAngleID() {
12254359294a7c9dc54802d512a5d891a35c1663392caryclark        return ++fAngleID;
12354359294a7c9dc54802d512a5d891a35c1663392caryclark    }
12454359294a7c9dc54802d512a5d891a35c1663392caryclark
12526ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    int nextCoinID() {
12626ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark        return ++fCoinID;
12726ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    }
12826ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark
12954359294a7c9dc54802d512a5d891a35c1663392caryclark    int nextContourID() {
13054359294a7c9dc54802d512a5d891a35c1663392caryclark        return ++fContourID;
13154359294a7c9dc54802d512a5d891a35c1663392caryclark    }
13226ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark
13354359294a7c9dc54802d512a5d891a35c1663392caryclark    int nextPtTID() {
13454359294a7c9dc54802d512a5d891a35c1663392caryclark        return ++fPtTID;
13554359294a7c9dc54802d512a5d891a35c1663392caryclark    }
13654359294a7c9dc54802d512a5d891a35c1663392caryclark
13754359294a7c9dc54802d512a5d891a35c1663392caryclark    int nextSegmentID() {
13854359294a7c9dc54802d512a5d891a35c1663392caryclark        return ++fSegmentID;
13954359294a7c9dc54802d512a5d891a35c1663392caryclark    }
14054359294a7c9dc54802d512a5d891a35c1663392caryclark
14154359294a7c9dc54802d512a5d891a35c1663392caryclark    int nextSpanID() {
14254359294a7c9dc54802d512a5d891a35c1663392caryclark        return ++fSpanID;
14354359294a7c9dc54802d512a5d891a35c1663392caryclark    }
14454359294a7c9dc54802d512a5d891a35c1663392caryclark#endif
14554359294a7c9dc54802d512a5d891a35c1663392caryclark
146ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    SkOpPhase phase() const {
14754359294a7c9dc54802d512a5d891a35c1663392caryclark        return fPhase;
14854359294a7c9dc54802d512a5d891a35c1663392caryclark    }
14929b2563afb1677515739f1d24fb27733626eca92caryclark
15029b2563afb1677515739f1d24fb27733626eca92caryclark    void resetAllocatedOpSpan() {
15129b2563afb1677515739f1d24fb27733626eca92caryclark        fAllocatedOpSpan = false;
15229b2563afb1677515739f1d24fb27733626eca92caryclark    }
15329b2563afb1677515739f1d24fb27733626eca92caryclark
15429b2563afb1677515739f1d24fb27733626eca92caryclark    void setAllocatedOpSpan() {
15529b2563afb1677515739f1d24fb27733626eca92caryclark        fAllocatedOpSpan = true;
15629b2563afb1677515739f1d24fb27733626eca92caryclark    }
15754359294a7c9dc54802d512a5d891a35c1663392caryclark
15854359294a7c9dc54802d512a5d891a35c1663392caryclark    void setAngleCoincidence() {
15954359294a7c9dc54802d512a5d891a35c1663392caryclark        fAngleCoincidence = true;
16054359294a7c9dc54802d512a5d891a35c1663392caryclark    }
16155888e44171ffd48b591d19256884a969fe4da17caryclark
16255888e44171ffd48b591d19256884a969fe4da17caryclark    void setCoincidence(SkOpCoincidence* coincidence) {
16355888e44171ffd48b591d19256884a969fe4da17caryclark        fCoincidence = coincidence;
16455888e44171ffd48b591d19256884a969fe4da17caryclark    }
16554359294a7c9dc54802d512a5d891a35c1663392caryclark
166624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark    void setContourHead(SkOpContourHead* contourHead) {
167624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark        fContourHead = contourHead;
168624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark    }
169624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark
170ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    void setPhase(SkOpPhase phase) {
171ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark        if (SkOpPhase::kNoChange == phase) {
172ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark            return;
173ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark        }
17454359294a7c9dc54802d512a5d891a35c1663392caryclark        SkASSERT(fPhase != phase);
17554359294a7c9dc54802d512a5d891a35c1663392caryclark        fPhase = phase;
17654359294a7c9dc54802d512a5d891a35c1663392caryclark    }
17754359294a7c9dc54802d512a5d891a35c1663392caryclark
17854359294a7c9dc54802d512a5d891a35c1663392caryclark    // called in very rare cases where angles are sorted incorrectly -- signfies op will fail
17954359294a7c9dc54802d512a5d891a35c1663392caryclark    void setWindingFailed() {
18054359294a7c9dc54802d512a5d891a35c1663392caryclark        fWindingFailed = true;
18154359294a7c9dc54802d512a5d891a35c1663392caryclark    }
18254359294a7c9dc54802d512a5d891a35c1663392caryclark
18354359294a7c9dc54802d512a5d891a35c1663392caryclark    bool windingFailed() const {
18454359294a7c9dc54802d512a5d891a35c1663392caryclark        return fWindingFailed;
18554359294a7c9dc54802d512a5d891a35c1663392caryclark    }
18654359294a7c9dc54802d512a5d891a35c1663392caryclark
18754359294a7c9dc54802d512a5d891a35c1663392caryclarkprivate:
18855888e44171ffd48b591d19256884a969fe4da17caryclark    SkChunkAlloc* fAllocator;
18954359294a7c9dc54802d512a5d891a35c1663392caryclark    SkOpCoincidence* fCoincidence;
190624637cc8ec22c000409704d0b403ac1b81ad4b0caryclark    SkOpContourHead* fContourHead;
1914e1a4c9399b8bb0897218f3ec10c254d3bb97463caryclark    int fNested;
19229b2563afb1677515739f1d24fb27733626eca92caryclark    bool fAllocatedOpSpan;
19354359294a7c9dc54802d512a5d891a35c1663392caryclark    bool fWindingFailed;
19454359294a7c9dc54802d512a5d891a35c1663392caryclark    bool fAngleCoincidence;
195ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    SkOpPhase fPhase;
19654359294a7c9dc54802d512a5d891a35c1663392caryclark#ifdef SK_DEBUG
197d4349723fac9c0fd4dcf8c275fb7c756bdfdff7bcaryclark    const char* fDebugTestName;
198ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    void* fDebugReporter;
19954359294a7c9dc54802d512a5d891a35c1663392caryclark    int fAngleID;
20026ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    int fCoinID;
20154359294a7c9dc54802d512a5d891a35c1663392caryclark    int fContourID;
20254359294a7c9dc54802d512a5d891a35c1663392caryclark    int fPtTID;
20354359294a7c9dc54802d512a5d891a35c1663392caryclark    int fSegmentID;
20454359294a7c9dc54802d512a5d891a35c1663392caryclark    int fSpanID;
205dae6b97705fde08958b1a36fa6ce685d28fc692ccaryclark    bool fDebugSkipAssert;
20654359294a7c9dc54802d512a5d891a35c1663392caryclark#endif
20726ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark#if DEBUG_T_SECT_LOOP_COUNT
20826ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    int fDebugLoopCount[3];
20926ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    SkPath::Verb fDebugWorstVerb[6];
21026ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    SkPoint fDebugWorstPts[24];
21126ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark    float fDebugWorstWeight[6];
21226ad22ab61539e3d3b6bc5e0da8dcebbd52a53decaryclark#endif
213ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark#if DEBUG_COIN
214ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    SkPathOpsDebug::CoinDict fCoinChangedDict;
215ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    SkPathOpsDebug::CoinDict fCoinVisitedDict;
216ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    SkPathOpsDebug::CoinDictEntry fCoinDictEntry;
217ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark    const char* fPreviousFuncName;
218ab87d7abf1df007c90bef2e916294ca325d81c81Cary Clark#endif
21955888e44171ffd48b591d19256884a969fe4da17caryclark#if DEBUG_COINCIDENCE
22055888e44171ffd48b591d19256884a969fe4da17caryclark    bool fDebugCheckHealth;
22155888e44171ffd48b591d19256884a969fe4da17caryclark#endif
22254359294a7c9dc54802d512a5d891a35c1663392caryclark};
22354359294a7c9dc54802d512a5d891a35c1663392caryclark
224cdeff81bdb2e5cde422b6850634c5d3977fcbae9caryclark#ifdef SK_DEBUG
22530b9fdd6a1d607bde20c793af65b5e2e8a1737cacaryclark#if DEBUG_COINCIDENCE
22630b9fdd6a1d607bde20c793af65b5e2e8a1737cacaryclark#define SkOPASSERT(cond) SkASSERT((this->globalState() && \
22730b9fdd6a1d607bde20c793af65b5e2e8a1737cacaryclark        (this->globalState()->debugCheckHealth() || \
22830b9fdd6a1d607bde20c793af65b5e2e8a1737cacaryclark        this->globalState()->debugSkipAssert())) || (cond))
22930b9fdd6a1d607bde20c793af65b5e2e8a1737cacaryclark#else
230e25a4f6cbeaccfdc34cf031103f0fbc3e53a3ee5caryclark#define SkOPASSERT(cond) SkASSERT((this->globalState() && \
23130b9fdd6a1d607bde20c793af65b5e2e8a1737cacaryclark        this->globalState()->debugSkipAssert()) || (cond))
23230b9fdd6a1d607bde20c793af65b5e2e8a1737cacaryclark#endif
2331597628fa38d24f23ad505bfb40e70e7c8617457caryclark#define SkOPOBJASSERT(obj, cond) SkASSERT((obj->debugGlobalState() && \
23430b9fdd6a1d607bde20c793af65b5e2e8a1737cacaryclark        obj->debugGlobalState()->debugSkipAssert()) || (cond))
235cdeff81bdb2e5cde422b6850634c5d3977fcbae9caryclark#else
236cdeff81bdb2e5cde422b6850634c5d3977fcbae9caryclark#define SkOPASSERT(cond)
237cdeff81bdb2e5cde422b6850634c5d3977fcbae9caryclark#define SkOPOBJASSERT(obj, cond)
238cdeff81bdb2e5cde422b6850634c5d3977fcbae9caryclark#endif
2391597628fa38d24f23ad505bfb40e70e7c8617457caryclark
240c3f63570c35a1e2bc84b33906c6401d6f3062bf2caryclark@google.com// Use Almost Equal when comparing coordinates. Use epsilon to compare T values.
2414fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.combool AlmostEqualUlps(float a, float b);
2424fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.cominline bool AlmostEqualUlps(double a, double b) {
2434fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com    return AlmostEqualUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
24407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
24507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
24655888e44171ffd48b591d19256884a969fe4da17caryclarkbool AlmostEqualUlpsNoNormalCheck(float a, float b);
24755888e44171ffd48b591d19256884a969fe4da17caryclarkinline bool AlmostEqualUlpsNoNormalCheck(double a, double b) {
24855888e44171ffd48b591d19256884a969fe4da17caryclark    return AlmostEqualUlpsNoNormalCheck(SkDoubleToScalar(a), SkDoubleToScalar(b));
24955888e44171ffd48b591d19256884a969fe4da17caryclark}
25055888e44171ffd48b591d19256884a969fe4da17caryclark
251b669300a9753893ef900207c38aeff2d467764e5caryclarkbool AlmostEqualUlps_Pin(float a, float b);
252b669300a9753893ef900207c38aeff2d467764e5caryclarkinline bool AlmostEqualUlps_Pin(double a, double b) {
253b669300a9753893ef900207c38aeff2d467764e5caryclark    return AlmostEqualUlps_Pin(SkDoubleToScalar(a), SkDoubleToScalar(b));
254b669300a9753893ef900207c38aeff2d467764e5caryclark}
255b669300a9753893ef900207c38aeff2d467764e5caryclark
2567eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com// Use Almost Dequal when comparing should not special case denormalized values.
2577eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.combool AlmostDequalUlps(float a, float b);
2582db7fe7d3b7ee875e1099a22f0af17520696f5d7commit-bot@chromium.orgbool AlmostDequalUlps(double a, double b);
2597eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com
260570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.combool NotAlmostEqualUlps(float a, float b);
261570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.cominline bool NotAlmostEqualUlps(double a, double b) {
262570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com    return NotAlmostEqualUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
263570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com}
264570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com
265b669300a9753893ef900207c38aeff2d467764e5caryclarkbool NotAlmostEqualUlps_Pin(float a, float b);
266b669300a9753893ef900207c38aeff2d467764e5caryclarkinline bool NotAlmostEqualUlps_Pin(double a, double b) {
267b669300a9753893ef900207c38aeff2d467764e5caryclark    return NotAlmostEqualUlps_Pin(SkDoubleToScalar(a), SkDoubleToScalar(b));
268b669300a9753893ef900207c38aeff2d467764e5caryclark}
269b669300a9753893ef900207c38aeff2d467764e5caryclark
2707eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.combool NotAlmostDequalUlps(float a, float b);
2717eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.cominline bool NotAlmostDequalUlps(double a, double b) {
2727eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com    return NotAlmostDequalUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
2737eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com}
2747eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com
275570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com// Use Almost Bequal when comparing coordinates in conjunction with between.
276570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.combool AlmostBequalUlps(float a, float b);
277570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.cominline bool AlmostBequalUlps(double a, double b) {
278570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com    return AlmostBequalUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
279570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com}
280570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com
281a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.combool AlmostPequalUlps(float a, float b);
282a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.cominline bool AlmostPequalUlps(double a, double b) {
283a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.com    return AlmostPequalUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
284a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.com}
285a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.com
2864fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.combool RoughlyEqualUlps(float a, float b);
2874fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.cominline bool RoughlyEqualUlps(double a, double b) {
2884fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com    return RoughlyEqualUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
28907e97fccd2d85076cd22ef411b0773ab92a18abecaryclark@google.com}
29007e97fccd2d85076cd22ef411b0773ab92a18abecaryclark@google.com
291570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.combool AlmostLessUlps(float a, float b);
292570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.cominline bool AlmostLessUlps(double a, double b) {
293570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com    return AlmostLessUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
294570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com}
295570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com
296570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.combool AlmostLessOrEqualUlps(float a, float b);
297570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.cominline bool AlmostLessOrEqualUlps(double a, double b) {
298570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com    return AlmostLessOrEqualUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
299570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com}
300570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com
301fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.combool AlmostBetweenUlps(float a, float b, float c);
3024fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.cominline bool AlmostBetweenUlps(double a, double b, double c) {
3034fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com    return AlmostBetweenUlps(SkDoubleToScalar(a), SkDoubleToScalar(b), SkDoubleToScalar(c));
3044fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com}
3054fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com
3064fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.comint UlpsDistance(float a, float b);
3074fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.cominline int UlpsDistance(double a, double b) {
3084fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com    return UlpsDistance(SkDoubleToScalar(a), SkDoubleToScalar(b));
309fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com}
310fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com
31107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// FLT_EPSILON == 1.19209290E-07 == 1 / (2 ^ 23)
31207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// DBL_EPSILON == 2.22045e-16
31307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_CUBED = FLT_EPSILON * FLT_EPSILON * FLT_EPSILON;
31407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_HALF = FLT_EPSILON / 2;
315cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.comconst double FLT_EPSILON_DOUBLE = FLT_EPSILON * 2;
3164431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orgconst double FLT_EPSILON_ORDERABLE_ERR = FLT_EPSILON * 16;
31707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_SQUARED = FLT_EPSILON * FLT_EPSILON;
31807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_SQRT = sqrt(FLT_EPSILON);
31907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_INVERSE = 1 / FLT_EPSILON;
32007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double DBL_EPSILON_ERR = DBL_EPSILON * 4;  // FIXME: tune -- allow a few bits of error
321cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.comconst double DBL_EPSILON_SUBDIVIDE_ERR = DBL_EPSILON * 16;
32207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double ROUGH_EPSILON = FLT_EPSILON * 64;
32307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double MORE_ROUGH_EPSILON = FLT_EPSILON * 256;
324dac1d17027dcaa5596885a9f333979418b35001ccaryclarkconst double WAY_ROUGH_EPSILON = FLT_EPSILON * 2048;
32554359294a7c9dc54802d512a5d891a35c1663392caryclarkconst double BUMP_EPSILON = FLT_EPSILON * 4096;
326dac1d17027dcaa5596885a9f333979418b35001ccaryclark
32755888e44171ffd48b591d19256884a969fe4da17caryclarkconst SkScalar INVERSE_NUMBER_RANGE = FLT_EPSILON_ORDERABLE_ERR;
32855888e44171ffd48b591d19256884a969fe4da17caryclark
329dac1d17027dcaa5596885a9f333979418b35001ccaryclarkinline bool zero_or_one(double x) {
330dac1d17027dcaa5596885a9f333979418b35001ccaryclark    return x == 0 || x == 1;
331dac1d17027dcaa5596885a9f333979418b35001ccaryclark}
33207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
33307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero(double x) {
33407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON;
33507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
33607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
33707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_zero(double x) {
33807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < DBL_EPSILON_ERR;
33907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
34007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
341cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool precisely_subdivide_zero(double x) {
342cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return fabs(x) < DBL_EPSILON_SUBDIVIDE_ERR;
343cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
344cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
34507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero(float x) {
34607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON;
34707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
34807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
34907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_cubed(double x) {
35007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON_CUBED;
35107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
35207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
35307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_half(double x) {
35407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON_HALF;
35507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
35607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
357cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool approximately_zero_double(double x) {
358cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return fabs(x) < FLT_EPSILON_DOUBLE;
359cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
360cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
3614431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_zero_orderable(double x) {
3624431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return fabs(x) < FLT_EPSILON_ORDERABLE_ERR;
3634431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
3644431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
36507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_squared(double x) {
36607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON_SQUARED;
36707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
36807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
36907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_sqrt(double x) {
37007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON_SQRT;
37107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
37207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
373cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool roughly_zero(double x) {
374cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return fabs(x) < ROUGH_EPSILON;
375cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
376cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
37707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_inverse(double x) {
37807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) > FLT_EPSILON_INVERSE;
37907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
38007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
38107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_when_compared_to(double x, double y) {
3824431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x == 0 || fabs(x) < fabs(y * FLT_EPSILON);
38307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
38407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
38554359294a7c9dc54802d512a5d891a35c1663392caryclarkinline bool precisely_zero_when_compared_to(double x, double y) {
38654359294a7c9dc54802d512a5d891a35c1663392caryclark    return x == 0 || fabs(x) < fabs(y * DBL_EPSILON);
38754359294a7c9dc54802d512a5d891a35c1663392caryclark}
38854359294a7c9dc54802d512a5d891a35c1663392caryclark
38955888e44171ffd48b591d19256884a969fe4da17caryclarkinline bool roughly_zero_when_compared_to(double x, double y) {
39055888e44171ffd48b591d19256884a969fe4da17caryclark    return x == 0 || fabs(x) < fabs(y * ROUGH_EPSILON);
39155888e44171ffd48b591d19256884a969fe4da17caryclark}
39255888e44171ffd48b591d19256884a969fe4da17caryclark
39307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// Use this for comparing Ts in the range of 0 to 1. For general numbers (larger and smaller) use
39407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// AlmostEqualUlps instead.
39507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_equal(double x, double y) {
39607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return approximately_zero(x - y);
39707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
39807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
39907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_equal(double x, double y) {
40007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return precisely_zero(x - y);
40107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
40207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
403cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool precisely_subdivide_equal(double x, double y) {
404cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return precisely_subdivide_zero(x - y);
405cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
406cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
40707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_equal_half(double x, double y) {
40807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return approximately_zero_half(x - y);
40907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
41007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
411cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool approximately_equal_double(double x, double y) {
412cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return approximately_zero_double(x - y);
413cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
414cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
4154431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_equal_orderable(double x, double y) {
4164431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return approximately_zero_orderable(x - y);
4174431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4184431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
41907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_equal_squared(double x, double y) {
42007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return approximately_equal(x, y);
42107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
42207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
42307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_greater(double x, double y) {
42407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x - FLT_EPSILON >= y;
42507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
42607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
4274431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_greater_double(double x, double y) {
4284431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x - FLT_EPSILON_DOUBLE >= y;
4294431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4304431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
4314431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_greater_orderable(double x, double y) {
4324431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x - FLT_EPSILON_ORDERABLE_ERR >= y;
4334431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4344431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
43507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_greater_or_equal(double x, double y) {
43607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x + FLT_EPSILON > y;
43707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
43807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
4394431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_greater_or_equal_double(double x, double y) {
4404431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x + FLT_EPSILON_DOUBLE > y;
4414431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4424431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
4434431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_greater_or_equal_orderable(double x, double y) {
4444431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x + FLT_EPSILON_ORDERABLE_ERR > y;
4454431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4464431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
44707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_lesser(double x, double y) {
44807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x + FLT_EPSILON <= y;
44907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
45007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
4514431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_lesser_double(double x, double y) {
4524431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x + FLT_EPSILON_DOUBLE <= y;
4534431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4544431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
4554431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_lesser_orderable(double x, double y) {
4564431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x + FLT_EPSILON_ORDERABLE_ERR <= y;
4574431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4584431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
45907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_lesser_or_equal(double x, double y) {
46007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x - FLT_EPSILON < y;
46107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
46207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
4634431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_lesser_or_equal_double(double x, double y) {
4644431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x - FLT_EPSILON_DOUBLE < y;
4654431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4664431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
4674431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_lesser_or_equal_orderable(double x, double y) {
4684431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x - FLT_EPSILON_ORDERABLE_ERR < y;
4694431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4704431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
47107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_greater_than_one(double x) {
47207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > 1 - FLT_EPSILON;
47307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
47407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
47507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_greater_than_one(double x) {
47607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > 1 - DBL_EPSILON_ERR;
47707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
47807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
47907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_less_than_zero(double x) {
48007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < FLT_EPSILON;
48107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
48207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
48307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_less_than_zero(double x) {
48407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < DBL_EPSILON_ERR;
48507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
48607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
48707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_negative(double x) {
48807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < FLT_EPSILON;
48907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
49007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
4914431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_negative_orderable(double x) {
4924431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x < FLT_EPSILON_ORDERABLE_ERR;
4934431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
4944431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
49507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_negative(double x) {
49607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < DBL_EPSILON_ERR;
49707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
49807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
49907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_one_or_less(double x) {
50007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < 1 + FLT_EPSILON;
50107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
50207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
5034431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_one_or_less_double(double x) {
5044431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x < 1 + FLT_EPSILON_DOUBLE;
5054431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
5064431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
50707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_positive(double x) {
50807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > -FLT_EPSILON;
50907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
51007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
51107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_positive_squared(double x) {
51207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > -(FLT_EPSILON_SQUARED);
51307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
51407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
51507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_or_more(double x) {
51607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > -FLT_EPSILON;
51707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
51807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
5194431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_zero_or_more_double(double x) {
5204431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x > -FLT_EPSILON_DOUBLE;
5214431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
5224431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
5234431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_between_orderable(double a, double b, double c) {
5244431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return a <= c
5254431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org            ? approximately_negative_orderable(a - b) && approximately_negative_orderable(b - c)
5264431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org            : approximately_negative_orderable(b - a) && approximately_negative_orderable(c - b);
5274431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
5284431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
52907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_between(double a, double b, double c) {
53007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return a <= c ? approximately_negative(a - b) && approximately_negative(b - c)
53107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com            : approximately_negative(b - a) && approximately_negative(c - b);
53207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
5330361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.com
5340361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.cominline bool precisely_between(double a, double b, double c) {
5350361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.com    return a <= c ? precisely_negative(a - b) && precisely_negative(b - c)
5360361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.com            : precisely_negative(b - a) && precisely_negative(c - b);
5370361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.com}
53807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
53907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// returns true if (a <= b <= c) || (a >= b >= c)
54007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool between(double a, double b, double c) {
54154359294a7c9dc54802d512a5d891a35c1663392caryclark    SkASSERT(((a <= b && b <= c) || (a >= b && b >= c)) == ((a - b) * (c - b) <= 0)
54254359294a7c9dc54802d512a5d891a35c1663392caryclark            || (precisely_zero(a) && precisely_zero(b) && precisely_zero(c)));
54307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return (a - b) * (c - b) <= 0;
54407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
54507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
546dac1d17027dcaa5596885a9f333979418b35001ccaryclarkinline bool roughly_equal(double x, double y) {
547dac1d17027dcaa5596885a9f333979418b35001ccaryclark    return fabs(x - y) < ROUGH_EPSILON;
548dac1d17027dcaa5596885a9f333979418b35001ccaryclark}
549dac1d17027dcaa5596885a9f333979418b35001ccaryclark
55054359294a7c9dc54802d512a5d891a35c1663392caryclarkinline bool roughly_negative(double x) {
55154359294a7c9dc54802d512a5d891a35c1663392caryclark    return x < ROUGH_EPSILON;
55254359294a7c9dc54802d512a5d891a35c1663392caryclark}
55354359294a7c9dc54802d512a5d891a35c1663392caryclark
55454359294a7c9dc54802d512a5d891a35c1663392caryclarkinline bool roughly_between(double a, double b, double c) {
55554359294a7c9dc54802d512a5d891a35c1663392caryclark    return a <= c ? roughly_negative(a - b) && roughly_negative(b - c)
55654359294a7c9dc54802d512a5d891a35c1663392caryclark            : roughly_negative(b - a) && roughly_negative(c - b);
55754359294a7c9dc54802d512a5d891a35c1663392caryclark}
55854359294a7c9dc54802d512a5d891a35c1663392caryclark
55907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool more_roughly_equal(double x, double y) {
56007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x - y) < MORE_ROUGH_EPSILON;
56107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
56207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
56307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDPoint;
56407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDVector;
56507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDLine;
56607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDQuad;
5671049f1246e7be4ccb68001361efceb8933e6f81ccaryclarkstruct SkDConic;
56807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDCubic;
56907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDRect;
57007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
571277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.cominline SkPath::Verb SkPathOpsPointsToVerb(int points) {
572277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    int verb = (1 << points) >> 1;
573277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com#ifdef SK_DEBUG
574277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    switch (points) {
575277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case 0: SkASSERT(SkPath::kMove_Verb == verb); break;
576277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case 1: SkASSERT(SkPath::kLine_Verb == verb); break;
577277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case 2: SkASSERT(SkPath::kQuad_Verb == verb); break;
578277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case 3: SkASSERT(SkPath::kCubic_Verb == verb); break;
579330313a8a8343876ee596da39da06a5d69badd9cmtklein@google.com        default: SkDEBUGFAIL("should not be here");
580277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    }
581277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com#endif
582277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    return (SkPath::Verb)verb;
583277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com}
584277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com
585277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.cominline int SkPathOpsVerbToPoints(SkPath::Verb verb) {
5861049f1246e7be4ccb68001361efceb8933e6f81ccaryclark    int points = (int) verb - (((int) verb + 1) >> 2);
587277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com#ifdef SK_DEBUG
588277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    switch (verb) {
589277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case SkPath::kLine_Verb: SkASSERT(1 == points); break;
590277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case SkPath::kQuad_Verb: SkASSERT(2 == points); break;
5911049f1246e7be4ccb68001361efceb8933e6f81ccaryclark        case SkPath::kConic_Verb: SkASSERT(2 == points); break;
592277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case SkPath::kCubic_Verb: SkASSERT(3 == points); break;
593330313a8a8343876ee596da39da06a5d69badd9cmtklein@google.com        default: SkDEBUGFAIL("should not get here");
594277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    }
595277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com#endif
596277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    return points;
597277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com}
598277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com
59907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline double SkDInterp(double A, double B, double t) {
60007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return A + (B - A) * t;
60107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
60207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
60307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comdouble SkDCubeRoot(double x);
60407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
60507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com/* Returns -1 if negative, 0 if zero, 1 if positive
60607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com*/
60707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline int SkDSign(double x) {
60807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return (x > 0) - (x < 0);
60907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
61007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
61107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com/* Returns 0 if negative, 1 if zero, 2 if positive
61207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com*/
61307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline int SKDSide(double x) {
61407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return (x > 0) + (x >= 0);
61507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
61607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
61707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com/* Returns 1 if negative, 2 if zero, 4 if positive
61807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com*/
61907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline int SkDSideBit(double x) {
62007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return 1 << SKDSide(x);
62107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
62207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
623fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.cominline double SkPinT(double t) {
624fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com    return precisely_less_than_zero(t) ? 0 : precisely_greater_than_one(t) ? 1 : t;
625fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com}
626fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com
62707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#endif
628