From f7f5b2cc2a2bd636607fddb45a02dfa855b7d12e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lo=C3=AFc=20GUEZO?= Date: Sun, 9 Mar 2025 16:06:27 +0100 Subject: [PATCH] feat(vector): add all basic functions --- include/math/vector3.h | 24 +++++++-- src/math/vector3.c | 109 +++++++++++++++++++++++++++++++++++++++++ 2 files changed, 130 insertions(+), 3 deletions(-) diff --git a/include/math/vector3.h b/include/math/vector3.h index 8ad1d03..fd88e97 100644 --- a/include/math/vector3.h +++ b/include/math/vector3.h @@ -1,5 +1,5 @@ -#ifndef VECTOR3_H -#define VECTOR3_H +#ifndef VEC3_H +#define VEC3_H typedef struct { float x, y, z; @@ -7,4 +7,22 @@ typedef struct { Vec3* vec3(float x, float y, float z); -#endif // VECTOR3_H \ No newline at end of file +Vec3* vec3Add(Vec3* v1, Vec3* v2); +Vec3* vec3Sub(Vec3* v1, Vec3* v2); +Vec3* vec3Scale(Vec3* v, float scalar); + +float vec3Dot(Vec3* a, Vec3* b); +float vec3Len(Vec3* v); + +Vec3* vec3Norm(Vec3* v); +Vec3* vec3Lerp(Vec3* a, Vec3* b, float t); +Vec3* vec3Cross(Vec3* a, Vec3* b); +float vec3Angle(Vec3* a, Vec3* b); +Vec3* vec3Proj(Vec3* a, Vec3* b); +Vec3* vec3Refl(Vec3* v, Vec3* normal); +float vec3Dist(Vec3* a, Vec3* b); +Vec3* vec3Rotate(Vec3* v, Vec3* axis, float angle); + +void vec3Free(Vec3* v); + +#endif // VEC3_H \ No newline at end of file diff --git a/src/math/vector3.c b/src/math/vector3.c index e469dd4..004d57f 100644 --- a/src/math/vector3.c +++ b/src/math/vector3.c @@ -11,4 +11,113 @@ Vec3* vec3(float x, float y, float z) vec->z = z; return vec; +} + +Vec3* vec3Add(Vec3* v1, Vec3* v2) +{ + if (!v1 || !v2) return NULL; + return vec3(v1->x + v2->x, v1->y + v2->y, v1->z + v2->z); +} + +Vec3* vec3Sub(Vec3* v1, Vec3* v2) +{ + if (!v1 || !v2) return NULL; + return vec3(v1->x - v2->x, v1->y - v2->y, v1->z - v2->z); +} + +Vec3* vec3Scale(Vec3* v, float scalar) +{ + if (!v) return NULL; + return vec3(v->x * scalar, v->y * scalar, v->z * scalar); +} + +float vec3Dot(Vec3* a, Vec3* b) +{ + if (!a || !b) return 0; + return a->x * b->x + a->y * b->y + a->z * b->z; +} + +float vec3Len(Vec3* v) +{ + if (!v) return 0; + return sqrtf(vec3Dot(v, v)); +} + +Vec3* vec3Norm(Vec3* v) +{ + if (!v) return NULL; + + float length = vec3Len(v); + if (length == 0.f) return vec3(0, 0, 0); + + float invLength = 1.f / length; + return vec3(v->x * invLength, v->y * invLength, v->z * invLength); +} + +Vec3* vec3Lerp(Vec3* a, Vec3* b, float t) +{ + if (t < 0.f) t = 0.f; + if (t > 1.f) t = 1.f; + + return vec3( + a->x + t * (b->x - a->x), + a->y + t * (b->y - a->y), + a->z + t * (b->z - a->z) + ); +} + +Vec3* vec3Cross(Vec3* a, Vec3* b) +{ + return vec3( + a->y * b->z - a->z * b->y, + a->z * b->x - a->x * b->z, + a->x * b->y - a->y * b->x + ); +} + +float vec3Angle(Vec3* a, Vec3* b) +{ + float dot = vec3Dot(a, b); + float lenA = vec3Len(a); + float lenB = vec3Len(b); + return acosf(dot / (lenA * lenB)); +} + +Vec3* vec3Proj(Vec3* a, Vec3* b) +{ + float dotAB = vec3Dot(a, b); + float lenB2 = vec3Dot(b, b); + float scale = dotAB / lenB2; + return vec3(b->x * scale, b->y * scale, b->z * scale); +} + +Vec3* vec3Refl(Vec3* v, Vec3* normal) +{ + Vec3* proj = vec3Proj(v, normal); + return vec3Sub(v, vec3Scale(proj, 2.f)); +} + +float vec3Dist(Vec3* a, Vec3* b) +{ + return vec3Len(vec3Sub(a, b)); +} + +Vec3* vec3Rotate(Vec3* v, Vec3* axis, float angle) +{ + axis = vec3Norm(axis); + float dot = vec3Dot(axis, v); + Vec3* cross = vec3Cross(axis, v); + + return vec3Add( + vec3Add( + vec3Scale(v, cosf(angle)), + vec3Scale(cross, sinf(angle)) + ), + vec3Scale(axis, dot * (1 - cosf(angle))) + ); +} + +void vec3Free(Vec3* v) +{ + if (v) free(v); } \ No newline at end of file