Mercurial > hg > pub > prymula > com
diff DPF-Prymula-audioplugins/dpf/dgl/src/Geometry.cpp @ 3:84e66ea83026
DPF-Prymula-audioplugins-0.231015-2
author | prymula <prymula76@outlook.com> |
---|---|
date | Mon, 16 Oct 2023 21:53:34 +0200 |
parents | |
children |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/DPF-Prymula-audioplugins/dpf/dgl/src/Geometry.cpp Mon Oct 16 21:53:34 2023 +0200 @@ -0,0 +1,1053 @@ +/* + * DISTRHO Plugin Framework (DPF) + * Copyright (C) 2012-2021 Filipe Coelho <falktx@falktx.com> + * + * Permission to use, copy, modify, and/or distribute this software for any purpose with + * or without fee is hereby granted, provided that the above copyright notice and this + * permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD + * TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN + * NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL + * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER + * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN + * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +#ifdef _MSC_VER +# pragma warning(disable:4661) /* instantiated template classes whose methods are defined elsewhere */ +#elif defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6)) +# pragma GCC diagnostic push +# pragma GCC diagnostic ignored "-Wconversion" +#endif + +#include "../Geometry.hpp" + +#include <cmath> + +START_NAMESPACE_DGL + +static const float M_2PIf = 3.14159265358979323846f*2.0f; + +// ----------------------------------------------------------------------- +// Point + +template<typename T> +Point<T>::Point() noexcept + : x(0), + y(0) {} + +template<typename T> +Point<T>::Point(const T& x2, const T& y2) noexcept + : x(x2), + y(y2) {} + +template<typename T> +Point<T>::Point(const Point<T>& pos) noexcept + : x(pos.x), + y(pos.y) {} + +template<typename T> +const T& Point<T>::getX() const noexcept +{ + return x; +} + +template<typename T> +const T& Point<T>::getY() const noexcept +{ + return y; +} + +template<typename T> +void Point<T>::setX(const T& x2) noexcept +{ + x = x2; +} + +template<typename T> +void Point<T>::setY(const T& y2) noexcept +{ + y = y2; +} + +template<typename T> +void Point<T>::setPos(const T& x2, const T& y2) noexcept +{ + x = x2; + y = y2; +} + +template<typename T> +void Point<T>::setPos(const Point<T>& pos) noexcept +{ + x = pos.x; + y = pos.y; +} + +template<typename T> +void Point<T>::moveBy(const T& x2, const T& y2) noexcept +{ + x = static_cast<T>(x+x2); + y = static_cast<T>(y+y2); +} + +template<typename T> +void Point<T>::moveBy(const Point<T>& pos) noexcept +{ + x = static_cast<T>(x+pos.x); + y = static_cast<T>(y+pos.y); +} + +template<typename T> +bool Point<T>::isZero() const noexcept +{ + return x == 0 && y == 0; +} + +template<typename T> +bool Point<T>::isNotZero() const noexcept +{ + return x != 0 || y != 0; +} + +template<typename T> +Point<T> Point<T>::operator+(const Point<T>& pos) noexcept +{ + return Point<T>(x+pos.x, y+pos.y); +} + +template<typename T> +Point<T> Point<T>::operator-(const Point<T>& pos) noexcept +{ + return Point<T>(x-pos.x, y-pos.y); +} + +template<typename T> +Point<T>& Point<T>::operator=(const Point<T>& pos) noexcept +{ + x = pos.x; + y = pos.y; + return *this; +} + +template<typename T> +Point<T>& Point<T>::operator+=(const Point<T>& pos) noexcept +{ + x = static_cast<T>(x+pos.x); + y = static_cast<T>(y+pos.y); + return *this; +} + +template<typename T> +Point<T>& Point<T>::operator-=(const Point<T>& pos) noexcept +{ + x = static_cast<T>(x-pos.x); + y = static_cast<T>(y-pos.y); + return *this; +} + +template<typename T> +bool Point<T>::operator==(const Point<T>& pos) const noexcept +{ + return (x == pos.x && y == pos.y); +} + +template<typename T> +bool Point<T>::operator!=(const Point<T>& pos) const noexcept +{ + return (x != pos.x || y != pos.y); +} + +// ----------------------------------------------------------------------- +// Size + +template<typename T> +Size<T>::Size() noexcept + : fWidth(0), + fHeight(0) {} + +template<typename T> +Size<T>::Size(const T& width, const T& height) noexcept + : fWidth(width), + fHeight(height) {} + +template<typename T> +Size<T>::Size(const Size<T>& size) noexcept + : fWidth(size.fWidth), + fHeight(size.fHeight) {} + +template<typename T> +const T& Size<T>::getWidth() const noexcept +{ + return fWidth; +} + +template<typename T> +const T& Size<T>::getHeight() const noexcept +{ + return fHeight; +} + +template<typename T> +void Size<T>::setWidth(const T& width) noexcept +{ + fWidth = width; +} + +template<typename T> +void Size<T>::setHeight(const T& height) noexcept +{ + fHeight = height; +} + +template<typename T> +void Size<T>::setSize(const T& width, const T& height) noexcept +{ + fWidth = width; + fHeight = height; +} + +template<typename T> +void Size<T>::setSize(const Size<T>& size) noexcept +{ + fWidth = size.fWidth; + fHeight = size.fHeight; +} + +template<typename T> +void Size<T>::growBy(double multiplier) noexcept +{ + fWidth = static_cast<T>(static_cast<double>(fWidth)*multiplier); + fHeight = static_cast<T>(static_cast<double>(fHeight)*multiplier); +} + +template<typename T> +void Size<T>::shrinkBy(double divider) noexcept +{ + fWidth = static_cast<T>(static_cast<double>(fWidth)/divider); + fHeight = static_cast<T>(static_cast<double>(fHeight)/divider); +} + +template<typename T> +bool Size<T>::isNull() const noexcept +{ + return fWidth == 0 && fHeight == 0; +} + +template<typename T> +bool Size<T>::isNotNull() const noexcept +{ + return fWidth != 0 || fHeight != 0; +} + +template<typename T> +bool Size<T>::isValid() const noexcept +{ + return fWidth > 0 && fHeight > 0; +} + +template<typename T> +bool Size<T>::isInvalid() const noexcept +{ + return fWidth <= 0 || fHeight <= 0; +} + +template<typename T> +Size<int> Size<T>::toInt() const noexcept +{ + return Size<int>(static_cast<int>(fWidth), + static_cast<int>(fHeight)); +} + +template<> +Size<int> Size<double>::toInt() const noexcept +{ + return Size<int>(static_cast<int>(fWidth + 0.5), + static_cast<int>(fHeight + 0.5)); +} + +template<> +Size<int> Size<float>::toInt() const noexcept +{ + return Size<int>(static_cast<int>(fWidth + 0.5f), + static_cast<int>(fHeight + 0.5f)); +} + +template<typename T> +Size<T> Size<T>::operator+(const Size<T>& size) noexcept +{ + return Size<T>(fWidth+size.fWidth, fHeight+size.fHeight); +} + +template<typename T> +Size<T> Size<T>::operator-(const Size<T>& size) noexcept +{ + return Size<T>(fWidth-size.fWidth, fHeight-size.fHeight); +} + +template<typename T> +Size<T>& Size<T>::operator=(const Size<T>& size) noexcept +{ + fWidth = size.fWidth; + fHeight = size.fHeight; + return *this; +} + +template<typename T> +Size<T>& Size<T>::operator+=(const Size<T>& size) noexcept +{ + fWidth = static_cast<T>(fWidth+size.fWidth); + fHeight = static_cast<T>(fHeight+size.fHeight); + return *this; +} + +template<typename T> +Size<T>& Size<T>::operator-=(const Size<T>& size) noexcept +{ + fWidth = static_cast<T>(fWidth-size.fWidth); + fHeight = static_cast<T>(fHeight-size.fHeight); + return *this; +} + +template<typename T> +Size<T>& Size<T>::operator*=(double m) noexcept +{ + fWidth = static_cast<T>(static_cast<double>(fWidth)*m); + fHeight = static_cast<T>(static_cast<double>(fHeight)*m); + return *this; +} + +template<typename T> +Size<T>& Size<T>::operator/=(double d) noexcept +{ + fWidth = static_cast<T>(static_cast<double>(fWidth)/d); + fHeight = static_cast<T>(static_cast<double>(fHeight)/d); + return *this; +} + +template<typename T> +Size<T> Size<T>::operator*(const double m) const noexcept +{ + Size<T> size(fWidth, fHeight); + size *= m; + return size; +} + +template<typename T> +Size<T> Size<T>::operator/(const double m) const noexcept +{ + Size<T> size(fWidth, fHeight); + size /= m; + return size; +} + +template<typename T> +bool Size<T>::operator==(const Size<T>& size) const noexcept +{ + return (fWidth == size.fWidth && fHeight == size.fHeight); +} + +template<typename T> +bool Size<T>::operator!=(const Size<T>& size) const noexcept +{ + return (fWidth != size.fWidth || fHeight != size.fHeight); +} + +// ----------------------------------------------------------------------- +// Line + +template<typename T> +Line<T>::Line() noexcept + : posStart(0, 0), + posEnd(0, 0) {} + +template<typename T> +Line<T>::Line(const T& startX, const T& startY, const T& endX, const T& endY) noexcept + : posStart(startX, startY), + posEnd(endX, endY) {} + +template<typename T> +Line<T>::Line(const T& startX, const T& startY, const Point<T>& endPos) noexcept + : posStart(startX, startY), + posEnd(endPos) {} + +template<typename T> +Line<T>::Line(const Point<T>& startPos, const T& endX, const T& endY) noexcept + : posStart(startPos), + posEnd(endX, endY) {} + +template<typename T> +Line<T>::Line(const Point<T>& startPos, const Point<T>& endPos) noexcept + : posStart(startPos), + posEnd(endPos) {} + +template<typename T> +Line<T>::Line(const Line<T>& line) noexcept + : posStart(line.posStart), + posEnd(line.posEnd) {} + +template<typename T> +const T& Line<T>::getStartX() const noexcept +{ + return posStart.x; +} + +template<typename T> +const T& Line<T>::getStartY() const noexcept +{ + return posStart.y; +} + +template<typename T> +const T& Line<T>::getEndX() const noexcept +{ + return posEnd.x; +} + +template<typename T> +const T& Line<T>::getEndY() const noexcept +{ + return posEnd.y; +} + +template<typename T> +const Point<T>& Line<T>::getStartPos() const noexcept +{ + return posStart; +} + +template<typename T> +const Point<T>& Line<T>::getEndPos() const noexcept +{ + return posEnd; +} + +template<typename T> +void Line<T>::setStartX(const T& x) noexcept +{ + posStart.x = x; +} + +template<typename T> +void Line<T>::setStartY(const T& y) noexcept +{ + posStart.y = y; +} + +template<typename T> +void Line<T>::setStartPos(const T& x, const T& y) noexcept +{ + posStart = Point<T>(x, y); +} + +template<typename T> +void Line<T>::setStartPos(const Point<T>& pos) noexcept +{ + posStart = pos; +} + +template<typename T> +void Line<T>::setEndX(const T& x) noexcept +{ + posEnd.x = x; +} + +template<typename T> +void Line<T>::setEndY(const T& y) noexcept +{ + posEnd.y = y; +} + +template<typename T> +void Line<T>::setEndPos(const T& x, const T& y) noexcept +{ + posEnd = Point<T>(x, y); +} + +template<typename T> +void Line<T>::setEndPos(const Point<T>& pos) noexcept +{ + posEnd = pos; +} + +template<typename T> +void Line<T>::moveBy(const T& x, const T& y) noexcept +{ + posStart.moveBy(x, y); + posEnd.moveBy(x, y); +} + +template<typename T> +void Line<T>::moveBy(const Point<T>& pos) noexcept +{ + posStart.moveBy(pos); + posEnd.moveBy(pos); +} + +template<typename T> +bool Line<T>::isNull() const noexcept +{ + return posStart == posEnd; +} + +template<typename T> +bool Line<T>::isNotNull() const noexcept +{ + return posStart != posEnd; +} + +template<typename T> +Line<T>& Line<T>::operator=(const Line<T>& line) noexcept +{ + posStart = line.posStart; + posEnd = line.posEnd; + return *this; +} + +template<typename T> +bool Line<T>::operator==(const Line<T>& line) const noexcept +{ + return (posStart == line.posStart && posEnd == line.posEnd); +} + +template<typename T> +bool Line<T>::operator!=(const Line<T>& line) const noexcept +{ + return (posStart != line.posStart || posEnd != line.posEnd); +} + +// ----------------------------------------------------------------------- +// Circle + +template<typename T> +Circle<T>::Circle() noexcept + : fPos(0, 0), + fSize(0.0f), + fNumSegments(0), + fTheta(0.0f), + fCos(0.0f), + fSin(0.0f) {} + +template<typename T> +Circle<T>::Circle(const T& x, const T& y, const float size, const uint numSegments) + : fPos(x, y), + fSize(size), + fNumSegments(numSegments >= 3 ? numSegments : 3), + fTheta(M_2PIf / static_cast<float>(fNumSegments)), + fCos(std::cos(fTheta)), + fSin(std::sin(fTheta)) +{ + DISTRHO_SAFE_ASSERT(fSize > 0.0f); +} + +template<typename T> +Circle<T>::Circle(const Point<T>& pos, const float size, const uint numSegments) + : fPos(pos), + fSize(size), + fNumSegments(numSegments >= 3 ? numSegments : 3), + fTheta(M_2PIf / static_cast<float>(fNumSegments)), + fCos(std::cos(fTheta)), + fSin(std::sin(fTheta)) +{ + DISTRHO_SAFE_ASSERT(fSize > 0.0f); +} + +template<typename T> +Circle<T>::Circle(const Circle<T>& cir) noexcept + : fPos(cir.fPos), + fSize(cir.fSize), + fNumSegments(cir.fNumSegments), + fTheta(cir.fTheta), + fCos(cir.fCos), + fSin(cir.fSin) +{ + DISTRHO_SAFE_ASSERT(fSize > 0.0f); +} + +template<typename T> +const T& Circle<T>::getX() const noexcept +{ + return fPos.x; +} + +template<typename T> +const T& Circle<T>::getY() const noexcept +{ + return fPos.y; +} + +template<typename T> +const Point<T>& Circle<T>::getPos() const noexcept +{ + return fPos; +} + +template<typename T> +void Circle<T>::setX(const T& x) noexcept +{ + fPos.x = x; +} + +template<typename T> +void Circle<T>::setY(const T& y) noexcept +{ + fPos.y = y; +} + +template<typename T> +void Circle<T>::setPos(const T& x, const T& y) noexcept +{ + fPos.x = x; + fPos.y = y; +} + +template<typename T> +void Circle<T>::setPos(const Point<T>& pos) noexcept +{ + fPos = pos; +} + +template<typename T> +float Circle<T>::getSize() const noexcept +{ + return fSize; +} + +template<typename T> +void Circle<T>::setSize(const float size) noexcept +{ + DISTRHO_SAFE_ASSERT_RETURN(size > 0.0f,); + + fSize = size; +} + +template<typename T> +uint Circle<T>::getNumSegments() const noexcept +{ + return fNumSegments; +} + +template<typename T> +void Circle<T>::setNumSegments(const uint num) +{ + DISTRHO_SAFE_ASSERT_RETURN(num >= 3,); + + if (fNumSegments == num) + return; + + fNumSegments = num; + + fTheta = M_2PIf / static_cast<float>(fNumSegments); + fCos = std::cos(fTheta); + fSin = std::sin(fTheta); +} + +template<typename T> +Circle<T>& Circle<T>::operator=(const Circle<T>& cir) noexcept +{ + fPos = cir.fPos; + fSize = cir.fSize; + fTheta = cir.fTheta; + fCos = cir.fCos; + fSin = cir.fSin; + fNumSegments = cir.fNumSegments; + return *this; +} + +template<typename T> +bool Circle<T>::operator==(const Circle<T>& cir) const noexcept +{ + return (fPos == cir.fPos && d_isEqual(fSize, cir.fSize) && fNumSegments == cir.fNumSegments); +} + +template<typename T> +bool Circle<T>::operator!=(const Circle<T>& cir) const noexcept +{ + return (fPos != cir.fPos || d_isNotEqual(fSize, cir.fSize) || fNumSegments != cir.fNumSegments); +} + +// ----------------------------------------------------------------------- +// Triangle + +template<typename T> +Triangle<T>::Triangle() noexcept + : pos1(0, 0), + pos2(0, 0), + pos3(0, 0) {} + +template<typename T> +Triangle<T>::Triangle(const T& x1, const T& y1, const T& x2, const T& y2, const T& x3, const T& y3) noexcept + : pos1(x1, y1), + pos2(x2, y2), + pos3(x3, y3) {} + +template<typename T> +Triangle<T>::Triangle(const Point<T>& p1, const Point<T>& p2, const Point<T>& p3) noexcept + : pos1(p1), + pos2(p2), + pos3(p3) {} + +template<typename T> +Triangle<T>::Triangle(const Triangle<T>& tri) noexcept + : pos1(tri.pos1), + pos2(tri.pos2), + pos3(tri.pos3) {} + +template<typename T> +bool Triangle<T>::isNull() const noexcept +{ + return pos1 == pos2 && pos1 == pos3; +} + +template<typename T> +bool Triangle<T>::isNotNull() const noexcept +{ + return pos1 != pos2 || pos1 != pos3; +} + +template<typename T> +bool Triangle<T>::isValid() const noexcept +{ + return pos1 != pos2 && pos1 != pos3; +} + +template<typename T> +bool Triangle<T>::isInvalid() const noexcept +{ + return pos1 == pos2 || pos1 == pos3; +} + +template<typename T> +Triangle<T>& Triangle<T>::operator=(const Triangle<T>& tri) noexcept +{ + pos1 = tri.pos1; + pos2 = tri.pos2; + pos3 = tri.pos3; + return *this; +} + +template<typename T> +bool Triangle<T>::operator==(const Triangle<T>& tri) const noexcept +{ + return (pos1 == tri.pos1 && pos2 == tri.pos2 && pos3 == tri.pos3); +} + +template<typename T> +bool Triangle<T>::operator!=(const Triangle<T>& tri) const noexcept +{ + return (pos1 != tri.pos1 || pos2 != tri.pos2 || pos3 != tri.pos3); +} + +// ----------------------------------------------------------------------- +// Rectangle + +template<typename T> +Rectangle<T>::Rectangle() noexcept + : pos(0, 0), + size(0, 0) {} + +template<typename T> +Rectangle<T>::Rectangle(const T& x, const T& y, const T& w, const T& h) noexcept + : pos(x, y), + size(w, h) {} + +template<typename T> +Rectangle<T>::Rectangle(const T& x, const T& y, const Size<T>& s) noexcept + : pos(x, y), + size(s) {} + +template<typename T> +Rectangle<T>::Rectangle(const Point<T>& p, const T& w, const T& h) noexcept + : pos(p), + size(w, h) {} + +template<typename T> +Rectangle<T>::Rectangle(const Point<T>& p, const Size<T>& s) noexcept + : pos(p), + size(s) {} + +template<typename T> +Rectangle<T>::Rectangle(const Rectangle<T>& rect) noexcept + : pos(rect.pos), + size(rect.size) {} + +template<typename T> +const T& Rectangle<T>::getX() const noexcept +{ + return pos.x; +} + +template<typename T> +const T& Rectangle<T>::getY() const noexcept +{ + return pos.y; +} + +template<typename T> +const T& Rectangle<T>::getWidth() const noexcept +{ + return size.fWidth; +} + +template<typename T> +const T& Rectangle<T>::getHeight() const noexcept +{ + return size.fHeight; +} + +template<typename T> +const Point<T>& Rectangle<T>::getPos() const noexcept +{ + return pos; +} + +template<typename T> +const Size<T>& Rectangle<T>::getSize() const noexcept +{ + return size; +} + +template<typename T> +void Rectangle<T>::setX(const T& x) noexcept +{ + pos.x = x; +} + +template<typename T> +void Rectangle<T>::setY(const T& y) noexcept +{ + pos.y = y; +} + +template<typename T> +void Rectangle<T>::setPos(const T& x, const T& y) noexcept +{ + pos.x = x; + pos.y = y; +} + +template<typename T> +void Rectangle<T>::setPos(const Point<T>& pos2) noexcept +{ + pos = pos2; +} + +template<typename T> +void Rectangle<T>::moveBy(const T& x, const T& y) noexcept +{ + pos.moveBy(x, y); +} + +template<typename T> +void Rectangle<T>::moveBy(const Point<T>& pos2) noexcept +{ + pos.moveBy(pos2); +} + +template<typename T> +void Rectangle<T>::setWidth(const T& width) noexcept +{ + size.fWidth = width; +} + +template<typename T> +void Rectangle<T>::setHeight(const T& height) noexcept +{ + size.fHeight = height; +} + +template<typename T> +void Rectangle<T>::setSize(const T& width, const T& height) noexcept +{ + size.fWidth = width; + size.fHeight = height; +} + +template<typename T> +void Rectangle<T>::setSize(const Size<T>& size2) noexcept +{ + size = size2; +} + +template<typename T> +void Rectangle<T>::growBy(double multiplier) noexcept +{ + size.growBy(multiplier); +} + +template<typename T> +void Rectangle<T>::shrinkBy(double divider) noexcept +{ + size.shrinkBy(divider); +} + +template<typename T> +void Rectangle<T>::setRectangle(const Point<T>& pos2, const Size<T>& size2) noexcept +{ + pos = pos2; + size = size2; +} + +template<typename T> +void Rectangle<T>::setRectangle(const Rectangle<T>& rect) noexcept +{ + pos = rect.pos; + size = rect.size; +} + +template<typename T> +bool Rectangle<T>::contains(const T& x, const T& y) const noexcept +{ + return (x >= pos.x && y >= pos.y && x <= pos.x+size.fWidth && y <= pos.y+size.fHeight); +} + +template<typename T> +bool Rectangle<T>::contains(const Point<T>& p) const noexcept +{ + return contains(p.x, p.y); +} + +template<typename T> +template<typename T2> +bool Rectangle<T>::contains(const Point<T2>& p) const noexcept +{ + return (p.x >= pos.x && p.y >= pos.y && p.x <= pos.x+size.fWidth && p.y <= pos.y+size.fHeight); +} + +template<> template<> +bool Rectangle<int>::contains(const Point<double>& p) const noexcept +{ + return (p.x >= pos.x && p.y >= pos.y && p.x <= pos.x+size.fWidth && p.y <= pos.y+size.fHeight); +} + +template<> template<> +bool Rectangle<uint>::contains(const Point<double>& p) const noexcept +{ + return (p.x >= pos.x && p.y >= pos.y && p.x <= pos.x+size.fWidth && p.y <= pos.y+size.fHeight); +} + +template<typename T> +bool Rectangle<T>::containsAfterScaling(const Point<T>& p, const double scaling) const noexcept +{ + return (p.x >= pos.x && p.y >= pos.y && p.x/scaling <= pos.x+size.fWidth && p.y/scaling <= pos.y+size.fHeight); +} + +template<typename T> +bool Rectangle<T>::containsX(const T& x) const noexcept +{ + return (x >= pos.x && x <= pos.x + size.fWidth); +} + +template<typename T> +bool Rectangle<T>::containsY(const T& y) const noexcept +{ + return (y >= pos.y && y <= pos.y + size.fHeight); +} + +template<typename T> +bool Rectangle<T>::isNull() const noexcept +{ + return size.isNull(); +} + +template<typename T> +bool Rectangle<T>::isNotNull() const noexcept +{ + return size.isNotNull(); +} + +template<typename T> +bool Rectangle<T>::isValid() const noexcept +{ + return size.isValid(); +} + +template<typename T> +bool Rectangle<T>::isInvalid() const noexcept +{ + return size.isInvalid(); +} + +template<typename T> +Rectangle<T>& Rectangle<T>::operator=(const Rectangle<T>& rect) noexcept +{ + pos = rect.pos; + size = rect.size; + return *this; +} + +template<typename T> +Rectangle<T>& Rectangle<T>::operator*=(double m) noexcept +{ + size *= m; + return *this; +} + +template<typename T> +Rectangle<T>& Rectangle<T>::operator/=(double d) noexcept +{ + size /= d; + return *this; +} + +template<typename T> +bool Rectangle<T>::operator==(const Rectangle<T>& rect) const noexcept +{ + return (pos == rect.pos && size == rect.size); +} + +template<typename T> +bool Rectangle<T>::operator!=(const Rectangle<T>& rect) const noexcept +{ + return (pos != rect.pos || size != rect.size); +} + +// ----------------------------------------------------------------------- +// Possible template data types + +template class Point<double>; +template class Point<float>; +template class Point<int>; +template class Point<uint>; +template class Point<short>; +template class Point<ushort>; + +template class Size<double>; +template class Size<float>; +template class Size<int>; +template class Size<uint>; +template class Size<short>; +template class Size<ushort>; + +template class Line<double>; +template class Line<float>; +template class Line<int>; +template class Line<uint>; +template class Line<short>; +template class Line<ushort>; + +template class Circle<double>; +template class Circle<float>; +template class Circle<int>; +template class Circle<uint>; +template class Circle<short>; +template class Circle<ushort>; + +template class Triangle<double>; +template class Triangle<float>; +template class Triangle<int>; +template class Triangle<uint>; +template class Triangle<short>; +template class Triangle<ushort>; + +template class Rectangle<double>; +template class Rectangle<float>; +template class Rectangle<int>; +template class Rectangle<uint>; +template class Rectangle<short>; +template class Rectangle<ushort>; + +// ----------------------------------------------------------------------- + +END_NAMESPACE_DGL