#ifndef CORE_VECTOR_H #define CORE_VECTOR_H #include "core/Types.h" #define VECTOR_OP2(name) name *r, const name *a #define VECTOR_OP3(name) VECTOR_OP2(name), const name* b #define VECTOR_TYPE(type, Type) \ typedef union { \ type data[2]; \ struct { \ type x, y; \ }; \ } Type##2; \ typedef union { \ type data[3]; \ struct { \ type x, y, z; \ }; \ Type##2 xy; \ } Type##3; \ typedef union { \ type data[4]; \ struct { \ type x, y, z, w; \ }; \ struct { \ Type##2 xy, zw; \ }; \ Type##3 xyz; \ } Type##4 VECTOR_TYPE(float, Vector); VECTOR_TYPE(int, IntVector); #define DEFINE_VECTOR(N, name, sname, type) \ name* addSet##sname(VECTOR_OP2(name)); \ name* add##sname(VECTOR_OP3(name)); \ name* subSet##sname(VECTOR_OP2(name)); \ name* sub##sname(VECTOR_OP3(name)); \ name* mulSet##sname(VECTOR_OP2(name)); \ name* mul##sname(VECTOR_OP3(name)); \ name* divSet##sname(VECTOR_OP2(name)); \ name* div##sname(VECTOR_OP3(name)); \ name* mulSet##sname##F(name* r, type f); \ name* mul##sname##F(name* r, const name* a, type f); \ name* divSet##sname##F(name* r, type f); \ name* div##sname##F(name* r, const name* a, type f); \ name* invertSet##sname(name* r); \ name* invert##sname(name* r, const name* a); \ size_t toString##sname(const name* a, char* buffer, size_t n); #define DEFINE_FVECTOR(N, name) \ float dotV##N(const name* a, const name* b); \ float squareLengthV##N(const name* a); \ float lengthV##N(const name* a); \ name* normalizeV##N(name* r); DEFINE_VECTOR(2, Vector2, V2, float) DEFINE_VECTOR(3, Vector3, V3, float) DEFINE_VECTOR(4, Vector4, V4, float) DEFINE_FVECTOR(2, Vector2) DEFINE_FVECTOR(3, Vector3) DEFINE_FVECTOR(4, Vector4) DEFINE_VECTOR(2, IntVector2, IV2, int) DEFINE_VECTOR(3, IntVector3, IV3, int) DEFINE_VECTOR(4, IntVector4, IV4, int) Vector3* angles(Vector3* r, float lengthAngle, float widthAngle); Vector3* cross(VECTOR_OP3(Vector3)); #define DEFINE_VECTOR_CONVERSION(a, nameA, b, nameB) \ a* convert##nameB(a* r, const b* c); \ b* convert##nameA(b* r, const a* c) DEFINE_VECTOR_CONVERSION(Vector2, V2, IntVector2, IV2); DEFINE_VECTOR_CONVERSION(Vector3, V3, IntVector3, IV3); DEFINE_VECTOR_CONVERSION(Vector4, V4, IntVector4, IV4); #define VECTOR2 ((Vector2){0}) #define VECTOR3 ((Vector3){0}) #define VECTOR4 ((Vector4){0}) #define INT_VECTOR2 ((IntVector2){0}) #define INT_VECTOR3 ((IntVector3){0}) #define INT_VECTOR4 ((IntVector4){0}) #define SELECT_VECTOR(_1, _2, _3, _4, name, ...) name #define V(...) \ ((SELECT_VECTOR(__VA_ARGS__, Vector4, Vector3, Vector2, 0)){{__VA_ARGS__}}) #define IV(...) \ ((SELECT_VECTOR(__VA_ARGS__, IntVector4, IntVector3, IntVector2, 0)){ \ {__VA_ARGS__}}) #endif