/********************\
|  Copyright 2024,   |
|       Ulysse Cura  |
\********************/

/////////////////////////////////////////
//                                     //
//   Definition de la classe Vector2D. //
//                                     //
/////////////////////////////////////////

template<typename T>
Vector2D<T>::Vector2D() : x(static_cast<T>(0)), y(static_cast<T>(0))
{}

template<typename T>
Vector2D<T>::Vector2D(T xInit, T yInit) : x(xInit), y(yInit)
{}

template <typename T> template<typename U>
Vector2D<T>::Vector2D(const Vector2D<U>& vec) : x(static_cast<T>(vec.x)), y(static_cast<T>(vec.y))
{}

template<typename T>
Vector2D<T> &Vector2D<T>::operator+=(const Vector2D<T> &vec) noexcept
{
    x += vec.x;
    y += vec.y;

    return *this;
}

template<typename T>
Vector2D<T> &Vector2D<T>::operator-=(const Vector2D<T> &vec) noexcept
{
    x -= vec.x;
    y -= vec.y;

    return *this;
}

template<typename T>
Vector2D<T> &Vector2D<T>::operator*=(const Vector2D<T> &vec) noexcept
{
    x *= vec.x;
    y *= vec.y;

    return *this;
}

template<typename T>
Vector2D<T> &Vector2D<T>::operator/=(const Vector2D<T> &vec) noexcept
{
    x /= vec.x;
    y /= vec.y;

    return *this;
}

template<typename T>
Vector2D<T> Vector2D<T>::operator*(const T &i) noexcept
{
    return Vector2D<T>(x * i, y * i);
}

template<typename T>
Vector2D<T> Vector2D<T>::operator/(const T &i) noexcept
{
    return Vector2D<T>(x / i, y / i);
}

template<typename T>
Vector2D<T> &Vector2D<T>::zero() noexcept
{
    x = static_cast<T>(0);
    y = static_cast<T>(0);

    return *this;
}

template<typename T>
Vector2D<T> operator+(const Vector2D<T> &v1, const Vector2D<T> &v2)
{
    return Vector2D<T>(v1.x + v2.x, v1.y + v2.y);
}

template<typename T>
Vector2D<T> operator-(const Vector2D<T> &v1, const Vector2D<T> &v2)
{
    return Vector2D<T>(v1.x - v2.x, v1.y - v2.y);
}

template<typename T>
Vector2D<T> operator*(const Vector2D<T> &v1, const Vector2D<T> &v2)
{
    return Vector2D<T>(v1.x * v2.x, v1.y * v2.y);
}

template<typename T>
Vector2D<T> operator/(const Vector2D<T> &v1, const Vector2D<T> &v2)
{
    return Vector2D<T>(v1.x / v2.x, v1.y / v2.y);
}
