/*
 * Copyright 2006 The Android Open Source Project
 *
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */

/* Generated by tools/bookmaker from include/core/SkPoint.h and docs/SkPoint_Reference.bmh
   on 2018-07-13 08:15:11. Additional documentation and examples can be found at:
   https://skia.org/user/api/SkPoint_Reference

   You may edit either file directly. Structural changes to public interfaces require
   editing both files. After editing docs/SkPoint_Reference.bmh, run:
       bookmaker -b docs -i include/core/SkPoint.h -p
   to create an updated version of this file.
 */

#ifndef SkPoint_DEFINED
#define SkPoint_DEFINED

#include "SkMath.h"
#include "SkScalar.h"
#include "../private/SkSafe32.h"

struct SkIPoint;

/** SkIVector provides an alternative name for SkIPoint. SkIVector and SkIPoint
    can be used interchangeably for all purposes.
*/
typedef SkIPoint SkIVector;

/** \struct SkIPoint
    SkIPoint holds two 32-bit integer coordinates.
*/
struct SkIPoint {
    int32_t fX; //!< x-axis value
    int32_t fY; //!< y-axis value

    /** Sets fX to x, fY to y.

        @param x  integer x-axis value of constructed SkIPoint
        @param y  integer y-axis value of constructed SkIPoint
        @return   SkIPoint (x, y)
    */
    static constexpr SkIPoint Make(int32_t x, int32_t y) {
        return {x, y};
    }

    /** Returns x-axis value of SkIPoint.

        @return  fX
    */
    int32_t x() const { return fX; }

    /** Returns y-axis value of SkIPoint.

        @return  fY
    */
    int32_t y() const { return fY; }

    /** Returns true if fX and fY are both zero.

        @return  true if fX is zero and fY is zero
    */
    bool isZero() const { return (fX | fY) == 0; }

    /** Sets fX to x and fY to y.

        @param x  new value for fX
        @param y  new value for fY
    */
    void set(int32_t x, int32_t y) {
        fX = x;
        fY = y;
    }

    /** Returns SkIPoint changing the signs of fX and fY.

        @return  SkIPoint as (-fX, -fY)
    */
    SkIPoint operator-() const {
        return {-fX, -fY};
    }

    /** Offsets SkIPoint by ivector v. Sets SkIPoint to (fX + v.fX, fY + v.fY).

        @param v  ivector to add
    */
    void operator+=(const SkIVector& v) {
        fX = Sk32_sat_add(fX, v.fX);
        fY = Sk32_sat_add(fY, v.fY);
    }

    /** Subtracts ivector v from SkIPoint. Sets SkIPoint to: (fX - v.fX, fY - v.fY).

        @param v  ivector to subtract
    */
    void operator-=(const SkIVector& v) {
        fX = Sk32_sat_sub(fX, v.fX);
        fY = Sk32_sat_sub(fY, v.fY);
    }

    /** Returns true if SkIPoint is equivalent to SkIPoint constructed from (x, y).

        @param x  value compared with fX
        @param y  value compared with fY
        @return   true if SkIPoint equals (x, y)
    */
    bool equals(int32_t x, int32_t y) const {
        return fX == x && fY == y;
    }

    /** Returns true if a is equivalent to b.

        @param a  SkIPoint to compare
        @param b  SkIPoint to compare
        @return   true if a.fX == b.fX and a.fY == b.fY
    */
    friend bool operator==(const SkIPoint& a, const SkIPoint& b) {
        return a.fX == b.fX && a.fY == b.fY;
    }

    /** Returns true if a is not equivalent to b.

        @param a  SkIPoint to compare
        @param b  SkIPoint to compare
        @return   true if a.fX != b.fX or a.fY != b.fY
    */
    friend bool operator!=(const SkIPoint& a, const SkIPoint& b) {
        return a.fX != b.fX || a.fY != b.fY;
    }

    /** Returns ivector from b to a; computed as (a.fX - b.fX, a.fY - b.fY).

        Can also be used to subtract ivector from ivector, returning ivector.

        @param a  SkIPoint or ivector to subtract from
        @param b  ivector to subtract
        @return   ivector from b to a
    */
    friend SkIVector operator-(const SkIPoint& a, const SkIPoint& b) {
        return { Sk32_sat_sub(a.fX, b.fX), Sk32_sat_sub(a.fY, b.fY) };
    }

    /** Returns SkIPoint resulting from SkIPoint a offset by ivector b, computed as: (a.fX + b.fX, a.fY + b.fY).

        Can also be used to offset SkIPoint b by ivector a, returning SkIPoint.
        Can also be used to add ivector to ivector, returning ivector.

        @param a  SkIPoint or ivector to add to
        @param b  SkIPoint or ivector to add
        @return   SkIPoint equal to a offset by b
    */
    friend SkIPoint operator+(const SkIPoint& a, const SkIVector& b) {
        return { Sk32_sat_add(a.fX, b.fX), Sk32_sat_add(a.fY, b.fY) };
    }
};

struct SkPoint;

/** SkVector provides an alternative name for SkPoint. SkVector and SkPoint can
    be used interchangeably for all purposes.
*/
typedef SkPoint SkVector;

/** \struct SkPoint
    SkPoint holds two 32-bit floating point coordinates.
*/
struct SK_API SkPoint {
    SkScalar fX; //!< x-axis value
    SkScalar fY; //!< y-axis value

    /** Sets fX to x, fY to y. Used both to set SkPoint and vector.

        @param x  SkScalar x-axis value of constructed SkPoint or vector
        @param y  SkScalar y-axis value of constructed SkPoint or vector
        @return   SkPoint (x, y)
    */
    static constexpr SkPoint Make(SkScalar x, SkScalar y) {
        return {x, y};
    }

    /** Returns x-axis value of SkPoint or vector.

        @return  fX
    */
    SkScalar x() const { return fX; }

    /** Returns y-axis value of SkPoint or vector.

        @return  fY
    */
    SkScalar y() const { return fY; }

    /** Returns true if fX and fY are both zero.

        @return  true if fX is zero and fY is zero
    */
    bool isZero() const { return (0 == fX) & (0 == fY); }

    /** Sets fX to x and fY to y.

        @param x  new value for fX
        @param y  new value for fY
    */
    void set(SkScalar x, SkScalar y) {
        fX = x;
        fY = y;
    }

    /** Sets fX to x and fY to y, promoting integers to SkScalar values.

        Assigning a large integer value directly to fX or fY may cause a compiler
        error, triggered by narrowing conversion of int to SkScalar. This safely
        casts x and y to avoid the error.

        @param x  new value for fX
        @param y  new value for fY
    */
    void iset(int32_t x, int32_t y) {
        fX = SkIntToScalar(x);
        fY = SkIntToScalar(y);
    }

    /** Sets fX to p.fX and fY to p.fY, promoting integers to SkScalar values.

        Assigning an SkIPoint containing a large integer value directly to fX or fY may
        cause a compiler error, triggered by narrowing conversion of int to SkScalar.
        This safely casts p.fX and p.fY to avoid the error.

        @param p  SkIPoint members promoted to SkScalar
    */
    void iset(const SkIPoint& p) {
        fX = SkIntToScalar(p.fX);
        fY = SkIntToScalar(p.fY);
    }

    /** Sets fX to absolute value of pt.fX; and fY to absolute value of pt.fY.

        @param pt  members providing magnitude for fX and fY
    */
    void setAbs(const SkPoint& pt) {
        fX = SkScalarAbs(pt.fX);
        fY = SkScalarAbs(pt.fY);
    }

    /** Adds offset to each SkPoint in points array with count entries.

        @param points  SkPoint array
        @param count   entries in array
        @param offset  vector added to points
    */
    static void Offset(SkPoint points[], int count, const SkVector& offset) {
        Offset(points, count, offset.fX, offset.fY);
    }

    /** Adds offset (dx, dy) to each SkPoint in points array of length count.

        @param points  SkPoint array
        @param count   entries in array
        @param dx      added to fX in points
        @param dy      added to fY in points
    */
    static void Offset(SkPoint points[], int count, SkScalar dx, SkScalar dy) {
        for (int i = 0; i < count; ++i) {
            points[i].offset(dx, dy);
        }
    }

    /** Adds offset (dx, dy) to SkPoint.

        @param dx  added to fX
        @param dy  added to fY
    */
    void offset(SkScalar dx, SkScalar dy) {
        fX += dx;
        fY += dy;
    }

    /** Returns the Euclidean distance from origin, computed as:

            sqrt(fX * fX + fY * fY)

        .

        @return  straight-line distance to origin
    */
    SkScalar length() const { return SkPoint::Length(fX, fY); }

    /** Returns the Euclidean distance from origin, computed as:

            sqrt(fX * fX + fY * fY)

        .

        @return  straight-line distance to origin
    */
    SkScalar distanceToOrigin() const { return this->length(); }

    /** Scales (fX, fY) so that length() returns one, while preserving ratio of fX to fY,
        if possible. If prior length is nearly zero, sets vector to (0, 0) and returns
        false; otherwise returns true.

        @return  true if former length is not zero or nearly zero
    */
    bool normalize();

    /** Sets vector to (x, y) scaled so length() returns one, and so that
        (fX, fY) is proportional to (x, y).  If (x, y) length is nearly zero,
        sets vector to (0, 0) and returns false; otherwise returns true.

        @param x  proportional value for fX
        @param y  proportional value for fY
        @return   true if (x, y) length is not zero or nearly zero
    */
    bool setNormalize(SkScalar x, SkScalar y);

    /** Scales vector so that distanceToOrigin() returns length, if possible. If former
        length is nearly zero, sets vector to (0, 0) and return false; otherwise returns
        true.

        @param length  straight-line distance to origin
        @return        true if former length is not zero or nearly zero
    */
    bool setLength(SkScalar length);

    /** Sets vector to (x, y) scaled to length, if possible. If former
        length is nearly zero, sets vector to (0, 0) and return false; otherwise returns
        true.

        @param x       proportional value for fX
        @param y       proportional value for fY
        @param length  straight-line distance to origin
        @return        true if (x, y) length is not zero or nearly zero
    */
    bool setLength(SkScalar x, SkScalar y, SkScalar length);

    /** Sets dst to SkPoint times scale. dst may be SkPoint to modify SkPoint in place.

        @param scale  factor to multiply SkPoint by
        @param dst    storage for scaled SkPoint
    */
    void scale(SkScalar scale, SkPoint* dst) const;

    /** Scales SkPoint in place by scale.

        @param value  factor to multiply SkPoint by
    */
    void scale(SkScalar value) { this->scale(value, this); }

    /** Changes the sign of fX and fY.
    */
    void negate() {
        fX = -fX;
        fY = -fY;
    }

    /** Returns SkPoint changing the signs of fX and fY.

        @return  SkPoint as (-fX, -fY)
    */
    SkPoint operator-() const {
        return {-fX, -fY};
    }

    /** Adds vector v to SkPoint. Sets SkPoint to: (fX + v.fX, fY + v.fY).

        @param v  vector to add
    */
    void operator+=(const SkVector& v) {
        fX += v.fX;
        fY += v.fY;
    }

    /** Subtracts vector v from SkPoint. Sets SkPoint to: (fX - v.fX, fY - v.fY).

        @param v  vector to subtract
    */
    void operator-=(const SkVector& v) {
        fX -= v.fX;
        fY -= v.fY;
    }

    /** Returns SkPoint multiplied by scale.

        @param scale  scalar to multiply by
        @return       SkPoint as (fX * scale, fY * scale)
    */
    SkPoint operator*(SkScalar scale) const {
        return {fX * scale, fY * scale};
    }

    /** Multiplies SkPoint by scale. Sets SkPoint to: (fX * scale, fY * scale).

        @param scale  scalar to multiply by
        @return       reference to SkPoint
    */
    SkPoint& operator*=(SkScalar scale) {
        fX *= scale;
        fY *= scale;
        return *this;
    }

    /** Returns true if both fX and fY are measurable values.

        @return  true for values other than infinities and NaN
    */
    bool isFinite() const {
        SkScalar accum = 0;
        accum *= fX;
        accum *= fY;

        // accum is either NaN or it is finite (zero).
        SkASSERT(0 == accum || SkScalarIsNaN(accum));

        // value==value will be true iff value is not NaN
        // TODO: is it faster to say !accum or accum==accum?
        return !SkScalarIsNaN(accum);
    }

    /** Returns true if SkPoint is equivalent to SkPoint constructed from (x, y).

        @param x  value compared with fX
        @param y  value compared with fY
        @return   true if SkPoint equals (x, y)
    */
    bool equals(SkScalar x, SkScalar y) const {
        return fX == x && fY == y;
    }

    /** Returns true if a is equivalent to b.

        @param a  SkPoint to compare
        @param b  SkPoint to compare
        @return   true if a.fX == b.fX and a.fY == b.fY
    */
    friend bool operator==(const SkPoint& a, const SkPoint& b) {
        return a.fX == b.fX && a.fY == b.fY;
    }

    /** Returns true if a is not equivalent to b.

        @param a  SkPoint to compare
        @param b  SkPoint to compare
        @return   true if a.fX != b.fX or a.fY != b.fY
    */
    friend bool operator!=(const SkPoint& a, const SkPoint& b) {
        return a.fX != b.fX || a.fY != b.fY;
    }

    /** Returns vector from b to a, computed as (a.fX - b.fX, a.fY - b.fY).

        Can also be used to subtract vector from SkPoint, returning SkPoint.
        Can also be used to subtract vector from vector, returning vector.

        @param a  SkPoint to subtract from
        @param b  SkPoint to subtract
        @return   vector from b to a
    */
    friend SkVector operator-(const SkPoint& a, const SkPoint& b) {
        return {a.fX - b.fX, a.fY - b.fY};
    }

    /** Returns SkPoint resulting from SkPoint a offset by vector b, computed as: (a.fX + b.fX, a.fY + b.fY).

        Can also be used to offset SkPoint b by vector a, returning SkPoint.
        Can also be used to add vector to vector, returning vector.

        @param a  SkPoint or vector to add to
        @param b  SkPoint or vector to add
        @return   SkPoint equal to a offset by b
    */
    friend SkPoint operator+(const SkPoint& a, const SkVector& b) {
        return {a.fX + b.fX, a.fY + b.fY};
    }

    /** Returns the Euclidean distance from origin, computed as:

            sqrt(x * x + y * y)

        .

        @param x  component of length
        @param y  component of length
        @return   straight-line distance to origin
    */
    static SkScalar Length(SkScalar x, SkScalar y);

    /** Scales (vec->fX, vec->fY) so that length() returns one, while preserving ratio of vec->fX to vec->fY,
        if possible. If original length is nearly zero, sets vec to (0, 0) and returns zero;
        otherwise, returns length of vec before vec is scaled.

        Returned prior length may be SK_ScalarInfinity if it can not be represented by SkScalar.

        Note that normalize() is faster if prior length is not required.

        @param vec  normalized to unit length
        @return     original vec length
    */
    static SkScalar Normalize(SkVector* vec);

    /** Returns the Euclidean distance between a and b.

        @param a  line end point
        @param b  line end point
        @return   straight-line distance from a to b
    */
    static SkScalar Distance(const SkPoint& a, const SkPoint& b) {
        return Length(a.fX - b.fX, a.fY - b.fY);
    }

    /** Returns the dot product of vector a and vector b.

        @param a  left side of dot product
        @param b  right side of dot product
        @return   product of input magnitudes and cosine of the angle between them
    */
    static SkScalar DotProduct(const SkVector& a, const SkVector& b) {
        return a.fX * b.fX + a.fY * b.fY;
    }

    /** Returns the cross product of vector a and vector b.

        a and b form three-dimensional vectors with z-axis value equal to zero. The
        cross product is a three-dimensional vector with x-axis and y-axis values equal
        to zero. The cross product z-axis component is returned.

        @param a  left side of cross product
        @param b  right side of cross product
        @return   area spanned by vectors signed by angle direction
    */
    static SkScalar CrossProduct(const SkVector& a, const SkVector& b) {
        return a.fX * b.fY - a.fY * b.fX;
    }

    /** Returns the cross product of vector and vec.

        Vector and vec form three-dimensional vectors with z-axis value equal to zero.
        The cross product is a three-dimensional vector with x-axis and y-axis values
        equal to zero. The cross product z-axis component is returned.

        @param vec  right side of cross product
        @return     area spanned by vectors signed by angle direction
    */
    SkScalar cross(const SkVector& vec) const {
        return CrossProduct(*this, vec);
    }

    /** Returns the dot product of vector and vector vec.

        @param vec  right side of dot product
        @return     product of input magnitudes and cosine of the angle between them
    */
    SkScalar dot(const SkVector& vec) const {
        return DotProduct(*this, vec);
    }

};

#endif
