SkPathOpsTypes.h revision dac1d17027dcaa5596885a9f333979418b35001c
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
25c3f63570c35a1e2bc84b33906c6401d6f3062bf2caryclark@google.com// Use Almost Equal when comparing coordinates. Use epsilon to compare T values.
264fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.combool AlmostEqualUlps(float a, float b);
274fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.cominline bool AlmostEqualUlps(double a, double b) {
284fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com    return AlmostEqualUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
2907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
3007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
317eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com// Use Almost Dequal when comparing should not special case denormalized values.
327eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.combool AlmostDequalUlps(float a, float b);
332db7fe7d3b7ee875e1099a22f0af17520696f5d7commit-bot@chromium.orgbool AlmostDequalUlps(double a, double b);
347eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com
35570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.combool NotAlmostEqualUlps(float a, float b);
36570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.cominline bool NotAlmostEqualUlps(double a, double b) {
37570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com    return NotAlmostEqualUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
38570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com}
39570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com
407eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.combool NotAlmostDequalUlps(float a, float b);
417eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.cominline bool NotAlmostDequalUlps(double a, double b) {
427eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com    return NotAlmostDequalUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
437eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com}
447eaa53d8f7e48fd17d02b5e3bd91f90e9c1899efcaryclark@google.com
45570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com// Use Almost Bequal when comparing coordinates in conjunction with between.
46570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.combool AlmostBequalUlps(float a, float b);
47570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.cominline bool AlmostBequalUlps(double a, double b) {
48570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com    return AlmostBequalUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
49570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com}
50570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com
51a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.combool AlmostPequalUlps(float a, float b);
52a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.cominline bool AlmostPequalUlps(double a, double b) {
53a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.com    return AlmostPequalUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
54a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.com}
55a2bbc6e19d5332e81784e582c290cc060f40c4c7caryclark@google.com
564fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.combool RoughlyEqualUlps(float a, float b);
574fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.cominline bool RoughlyEqualUlps(double a, double b) {
584fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com    return RoughlyEqualUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
5907e97fccd2d85076cd22ef411b0773ab92a18abecaryclark@google.com}
6007e97fccd2d85076cd22ef411b0773ab92a18abecaryclark@google.com
61570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.combool AlmostLessUlps(float a, float b);
62570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.cominline bool AlmostLessUlps(double a, double b) {
63570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com    return AlmostLessUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
64570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com}
65570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com
66570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.combool AlmostLessOrEqualUlps(float a, float b);
67570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.cominline bool AlmostLessOrEqualUlps(double a, double b) {
68570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com    return AlmostLessOrEqualUlps(SkDoubleToScalar(a), SkDoubleToScalar(b));
69570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com}
70570863f2e22b8ea7d7c504bd15e4f766af097df2caryclark@google.com
71fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.combool AlmostBetweenUlps(float a, float b, float c);
724fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.cominline bool AlmostBetweenUlps(double a, double b, double c) {
734fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com    return AlmostBetweenUlps(SkDoubleToScalar(a), SkDoubleToScalar(b), SkDoubleToScalar(c));
744fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com}
754fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com
764fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.comint UlpsDistance(float a, float b);
774fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.cominline int UlpsDistance(double a, double b) {
784fdbb229649caf74e5c1b55a1823926df903af34caryclark@google.com    return UlpsDistance(SkDoubleToScalar(a), SkDoubleToScalar(b));
79fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com}
80fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com
8107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// FLT_EPSILON == 1.19209290E-07 == 1 / (2 ^ 23)
8207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// DBL_EPSILON == 2.22045e-16
8307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_CUBED = FLT_EPSILON * FLT_EPSILON * FLT_EPSILON;
8407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_HALF = FLT_EPSILON / 2;
85cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.comconst double FLT_EPSILON_DOUBLE = FLT_EPSILON * 2;
864431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orgconst double FLT_EPSILON_ORDERABLE_ERR = FLT_EPSILON * 16;
8707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_SQUARED = FLT_EPSILON * FLT_EPSILON;
8807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_SQRT = sqrt(FLT_EPSILON);
8907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double FLT_EPSILON_INVERSE = 1 / FLT_EPSILON;
9007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double DBL_EPSILON_ERR = DBL_EPSILON * 4;  // FIXME: tune -- allow a few bits of error
91cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.comconst double DBL_EPSILON_SUBDIVIDE_ERR = DBL_EPSILON * 16;
9207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double ROUGH_EPSILON = FLT_EPSILON * 64;
9307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comconst double MORE_ROUGH_EPSILON = FLT_EPSILON * 256;
94dac1d17027dcaa5596885a9f333979418b35001ccaryclarkconst double WAY_ROUGH_EPSILON = FLT_EPSILON * 2048;
95dac1d17027dcaa5596885a9f333979418b35001ccaryclark
96dac1d17027dcaa5596885a9f333979418b35001ccaryclarkinline bool zero_or_one(double x) {
97dac1d17027dcaa5596885a9f333979418b35001ccaryclark    return x == 0 || x == 1;
98dac1d17027dcaa5596885a9f333979418b35001ccaryclark}
9907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
10007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero(double x) {
10107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON;
10207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
10307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
10407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_zero(double x) {
10507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < DBL_EPSILON_ERR;
10607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
10707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
108cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool precisely_subdivide_zero(double x) {
109cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return fabs(x) < DBL_EPSILON_SUBDIVIDE_ERR;
110cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
111cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
11207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero(float x) {
11307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON;
11407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
11507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
11607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_cubed(double x) {
11707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON_CUBED;
11807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
11907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
12007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_half(double x) {
12107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON_HALF;
12207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
12307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
124cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool approximately_zero_double(double x) {
125cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return fabs(x) < FLT_EPSILON_DOUBLE;
126cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
127cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
1284431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_zero_orderable(double x) {
1294431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return fabs(x) < FLT_EPSILON_ORDERABLE_ERR;
1304431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
1314431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
13207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_squared(double x) {
13307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON_SQUARED;
13407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
13507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
13607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_sqrt(double x) {
13707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) < FLT_EPSILON_SQRT;
13807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
13907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
140cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool roughly_zero(double x) {
141cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return fabs(x) < ROUGH_EPSILON;
142cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
143cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
14407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_inverse(double x) {
14507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x) > FLT_EPSILON_INVERSE;
14607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
14707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
14807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// OPTIMIZATION: if called multiple times with the same denom, we want to pass 1/y instead
14907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_when_compared_to(double x, double y) {
1504431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x == 0 || fabs(x) < fabs(y * FLT_EPSILON);
15107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
15207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
15307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// Use this for comparing Ts in the range of 0 to 1. For general numbers (larger and smaller) use
15407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// AlmostEqualUlps instead.
15507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_equal(double x, double y) {
15607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return approximately_zero(x - y);
15707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
15807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
15907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_equal(double x, double y) {
16007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return precisely_zero(x - y);
16107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
16207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
163cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool precisely_subdivide_equal(double x, double y) {
164cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return precisely_subdivide_zero(x - y);
165cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
166cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
16707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_equal_half(double x, double y) {
16807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return approximately_zero_half(x - y);
16907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
17007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
171cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.cominline bool approximately_equal_double(double x, double y) {
172cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com    return approximately_zero_double(x - y);
173cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com}
174cffbcc3b9665f2c928544b6fc6b8a0e22a4210fbcaryclark@google.com
1754431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_equal_orderable(double x, double y) {
1764431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return approximately_zero_orderable(x - y);
1774431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
1784431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
17907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_equal_squared(double x, double y) {
18007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return approximately_equal(x, y);
18107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
18207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
18307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_greater(double x, double y) {
18407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x - FLT_EPSILON >= y;
18507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
18607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
1874431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_greater_double(double x, double y) {
1884431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x - FLT_EPSILON_DOUBLE >= y;
1894431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
1904431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
1914431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_greater_orderable(double x, double y) {
1924431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x - FLT_EPSILON_ORDERABLE_ERR >= y;
1934431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
1944431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
19507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_greater_or_equal(double x, double y) {
19607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x + FLT_EPSILON > y;
19707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
19807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
1994431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_greater_or_equal_double(double x, double y) {
2004431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x + FLT_EPSILON_DOUBLE > y;
2014431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2024431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
2034431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_greater_or_equal_orderable(double x, double y) {
2044431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x + FLT_EPSILON_ORDERABLE_ERR > y;
2054431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2064431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
20707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_lesser(double x, double y) {
20807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x + FLT_EPSILON <= y;
20907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
21007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
2114431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_lesser_double(double x, double y) {
2124431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x + FLT_EPSILON_DOUBLE <= y;
2134431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2144431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
2154431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_lesser_orderable(double x, double y) {
2164431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x + FLT_EPSILON_ORDERABLE_ERR <= y;
2174431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2184431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
21907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_lesser_or_equal(double x, double y) {
22007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x - FLT_EPSILON < y;
22107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
22207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
2234431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_lesser_or_equal_double(double x, double y) {
2244431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x - FLT_EPSILON_DOUBLE < y;
2254431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2264431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
2274431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_lesser_or_equal_orderable(double x, double y) {
2284431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x - FLT_EPSILON_ORDERABLE_ERR < y;
2294431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2304431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
23107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_greater_than_one(double x) {
23207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > 1 - FLT_EPSILON;
23307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
23407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
23507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_greater_than_one(double x) {
23607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > 1 - DBL_EPSILON_ERR;
23707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
23807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
23907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_less_than_zero(double x) {
24007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < FLT_EPSILON;
24107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
24207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
24307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_less_than_zero(double x) {
24407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < DBL_EPSILON_ERR;
24507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
24607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
24707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_negative(double x) {
24807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < FLT_EPSILON;
24907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
25007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
2514431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_negative_orderable(double x) {
2524431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x < FLT_EPSILON_ORDERABLE_ERR;
2534431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2544431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
25507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool precisely_negative(double x) {
25607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < DBL_EPSILON_ERR;
25707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
25807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
25907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_one_or_less(double x) {
26007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x < 1 + FLT_EPSILON;
26107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
26207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
2634431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_one_or_less_double(double x) {
2644431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x < 1 + FLT_EPSILON_DOUBLE;
2654431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2664431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
26707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_positive(double x) {
26807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > -FLT_EPSILON;
26907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
27007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
27107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_positive_squared(double x) {
27207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > -(FLT_EPSILON_SQUARED);
27307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
27407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
27507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_zero_or_more(double x) {
27607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return x > -FLT_EPSILON;
27707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
27807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
2794431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_zero_or_more_double(double x) {
2804431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return x > -FLT_EPSILON_DOUBLE;
2814431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2824431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
2834431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.orginline bool approximately_between_orderable(double a, double b, double c) {
2844431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org    return a <= c
2854431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org            ? approximately_negative_orderable(a - b) && approximately_negative_orderable(b - c)
2864431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org            : approximately_negative_orderable(b - a) && approximately_negative_orderable(c - b);
2874431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org}
2884431e7757cfcb8cfa99535eed0e9f156dabf95c2commit-bot@chromium.org
28907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool approximately_between(double a, double b, double c) {
29007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return a <= c ? approximately_negative(a - b) && approximately_negative(b - c)
29107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com            : approximately_negative(b - a) && approximately_negative(c - b);
29207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
2930361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.com
2940361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.cominline bool precisely_between(double a, double b, double c) {
2950361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.com    return a <= c ? precisely_negative(a - b) && precisely_negative(b - c)
2960361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.com            : precisely_negative(b - a) && precisely_negative(c - b);
2970361032c0b53401030a720bc8b4930c3ec59f19ecaryclark@google.com}
29807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
29907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com// returns true if (a <= b <= c) || (a >= b >= c)
30007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool between(double a, double b, double c) {
30107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    SkASSERT(((a <= b && b <= c) || (a >= b && b >= c)) == ((a - b) * (c - b) <= 0));
30207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return (a - b) * (c - b) <= 0;
30307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
30407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
305dac1d17027dcaa5596885a9f333979418b35001ccaryclarkinline bool roughly_equal(double x, double y) {
306dac1d17027dcaa5596885a9f333979418b35001ccaryclark    return fabs(x - y) < ROUGH_EPSILON;
307dac1d17027dcaa5596885a9f333979418b35001ccaryclark}
308dac1d17027dcaa5596885a9f333979418b35001ccaryclark
30907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline bool more_roughly_equal(double x, double y) {
31007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return fabs(x - y) < MORE_ROUGH_EPSILON;
31107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
31207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
313dac1d17027dcaa5596885a9f333979418b35001ccaryclarkinline bool way_roughly_equal(double x, double y) {
314dac1d17027dcaa5596885a9f333979418b35001ccaryclark    return fabs(x - y) < WAY_ROUGH_EPSILON;
31507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
31607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
31707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDPoint;
31807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDVector;
31907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDLine;
32007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDQuad;
32107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDTriangle;
32207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDCubic;
32307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comstruct SkDRect;
32407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
325277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.cominline SkPath::Verb SkPathOpsPointsToVerb(int points) {
326277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    int verb = (1 << points) >> 1;
327277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com#ifdef SK_DEBUG
328277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    switch (points) {
329277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case 0: SkASSERT(SkPath::kMove_Verb == verb); break;
330277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case 1: SkASSERT(SkPath::kLine_Verb == verb); break;
331277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case 2: SkASSERT(SkPath::kQuad_Verb == verb); break;
332277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case 3: SkASSERT(SkPath::kCubic_Verb == verb); break;
333330313a8a8343876ee596da39da06a5d69badd9cmtklein@google.com        default: SkDEBUGFAIL("should not be here");
334277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    }
335277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com#endif
336277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    return (SkPath::Verb)verb;
337277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com}
338277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com
339277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.cominline int SkPathOpsVerbToPoints(SkPath::Verb verb) {
340277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    int points = (int) verb - ((int) verb >> 2);
341277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com#ifdef SK_DEBUG
342277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    switch (verb) {
343277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case SkPath::kLine_Verb: SkASSERT(1 == points); break;
344277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case SkPath::kQuad_Verb: SkASSERT(2 == points); break;
345277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com        case SkPath::kCubic_Verb: SkASSERT(3 == points); break;
346330313a8a8343876ee596da39da06a5d69badd9cmtklein@google.com        default: SkDEBUGFAIL("should not get here");
347277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    }
348277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com#endif
349277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com    return points;
350277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com}
351277c3f87656c44e0a651ed0dd56efa16c0ab07b4reed@google.com
35207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline double SkDInterp(double A, double B, double t) {
35307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return A + (B - A) * t;
35407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
35507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
35607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.comdouble SkDCubeRoot(double x);
35707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
35807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com/* Returns -1 if negative, 0 if zero, 1 if positive
35907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com*/
36007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline int SkDSign(double x) {
36107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return (x > 0) - (x < 0);
36207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
36307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
36407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com/* Returns 0 if negative, 1 if zero, 2 if positive
36507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com*/
36607393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline int SKDSide(double x) {
36707393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return (x > 0) + (x >= 0);
36807393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
36907393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
37007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com/* Returns 1 if negative, 2 if zero, 4 if positive
37107393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com*/
37207393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.cominline int SkDSideBit(double x) {
37307393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com    return 1 << SKDSide(x);
37407393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com}
37507393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com
376fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.cominline double SkPinT(double t) {
377fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com    return precisely_less_than_zero(t) ? 0 : precisely_greater_than_one(t) ? 1 : t;
378fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com}
379fa2aeee27af27f2934ee52a9732148f66481fb03caryclark@google.com
38007393cab57ce74a4aae89a31fae9aaa9780fc19dcaryclark@google.com#endif
381