diff options
author | Simponic <loganthebean222@gmail.com> | 2020-08-04 23:36:21 -0600 |
---|---|---|
committer | Simponic <loganthebean222@gmail.com> | 2020-08-04 23:36:21 -0600 |
commit | ebd81999b71ada201a316060fa47a7a66a277935 (patch) | |
tree | 930be8337e1144ba227bedb3e72e4473309c28e8 /src/vertex.h | |
parent | b323ae0ca067deb0a48e3d9088160383d698a28f (diff) | |
download | simple3dengine-ebd81999b71ada201a316060fa47a7a66a277935.tar.gz simple3dengine-ebd81999b71ada201a316060fa47a7a66a277935.zip |
Added files
Diffstat (limited to 'src/vertex.h')
-rw-r--r-- | src/vertex.h | 112 |
1 files changed, 112 insertions, 0 deletions
diff --git a/src/vertex.h b/src/vertex.h new file mode 100644 index 0000000..7880495 --- /dev/null +++ b/src/vertex.h @@ -0,0 +1,112 @@ +#include "defs.h" +#include "fixed.h" +#include "pt.h" +#include <math.h> + +#ifndef VERTEX_H +#define VERTEX_H + +typedef struct VERTEX { + FIXED x; + FIXED y; + FIXED z; +} VERTEX; + +static inline POINT viewportToScreen (POINT *point) { + // Convert a viewport coordinate to screen x, y + return createPoint(fixed_multiply(point->x, fixed_divide(WINDOW_WIDTH << FIX_SHIFT, viewport_width << FIX_SHIFT)), + fixed_multiply(point->y, fixed_divide(WINDOW_HEIGHT << FIX_SHIFT, viewport_height << FIX_SHIFT)) + ); +} + +static inline POINT projectVertex(VERTEX *vertex) { + // Project a vertex to a point + POINT temp; + if (vertex->z != 0) { + // Make sure we don't divide by zero + temp = createPoint(fixed_multiply(vertex->x, fixed_divide(ZPlane << FIX_SHIFT, vertex->z)), + fixed_multiply(vertex->y, fixed_divide(ZPlane << FIX_SHIFT, vertex->z)) + ); + } + else { + temp = createPoint(0, 0); + } + temp = viewportToScreen(&temp); + return temp; +} + +static inline VERTEX createVertex(FIXED x, FIXED y, FIXED z) { + // Create a vertex from data + VERTEX temp; + temp.x = x; + temp.y = y; + temp.z = z; + return temp; +} + +static inline VERTEX addVertices(VERTEX *a, VERTEX *b) { + // Add two vertices together + VERTEX temp = createVertex(a->x + b->x, a->y + b->y, a->z + b->z); + return temp; +} + +static inline void applyXRotation(VERTEX *vertex, FIXED xRotation) { + // Apply rotation to vertex on x-axis + FIXED sinTheta = float_to_fixed(sin(fixed_to_float(xRotation) * (3.14159 / 180))); + FIXED cosTheta = float_to_fixed(cos(fixed_to_float(xRotation) * (3.14159 / 180))); + FIXED y = vertex->y; + FIXED z = vertex->z; + vertex->y = fixed_multiply(y, cosTheta) - fixed_multiply(z, sinTheta); + vertex->z = fixed_multiply(z, cosTheta) + fixed_multiply(y, sinTheta); +} + +static inline void applyYRotation(VERTEX *vertex, FIXED yRotation) { + // Apply rotation to vertex on y-axis + FIXED sinTheta = float_to_fixed(sin(fixed_to_float(yRotation) * (3.14159 / 180))); + FIXED cosTheta = float_to_fixed(cos(fixed_to_float(yRotation) * (3.14159 / 180))); + FIXED x = vertex->x; + FIXED z = vertex->z; + vertex->x = fixed_multiply(x, cosTheta) + fixed_multiply(z, sinTheta); + vertex->z = fixed_multiply(z, cosTheta) - fixed_multiply(x, sinTheta); +} + +static inline void applyZRotation(VERTEX *vertex, FIXED zRotation) { + // Apply rotation to vertex on z-axis + FIXED sinTheta = float_to_fixed(sin(fixed_to_float(zRotation) * (3.14159 / 180))); + FIXED cosTheta = float_to_fixed(cos(fixed_to_float(zRotation) * (3.14159 / 180))); + FIXED x = vertex->x; + FIXED y = vertex->y; + vertex->x = fixed_multiply(x, cosTheta) - fixed_multiply(y, sinTheta); + vertex->y = fixed_multiply(y, cosTheta) + fixed_multiply(x, sinTheta); +} + +static inline VERTEX crossProduct(VERTEX *a, VERTEX *b) { + // Calculate the cross product of two vertices + return createVertex( + fixed_multiply(a->y, b->z) - fixed_multiply(a->z, b->y), + fixed_multiply(a->z, b->x) - fixed_multiply(a->x, b->z), + fixed_multiply(a->x, b->y) - fixed_multiply(a->y, b->x) + ); +} + +static inline FIXED dotProduct(VERTEX *a, VERTEX *b) { + // Dot two vertices + FIXED product = fixed_multiply(a->x, b->x) + + fixed_multiply(a->y, b->y) + + fixed_multiply(a->z, b->z); + return product; +} + +static inline void normalizeVertex(VERTEX *vertex) { + // Normalize (magnitude = 1) a vertex + float x = fixed_to_float(vertex->x); + float y = fixed_to_float(vertex->y); + float z = fixed_to_float(vertex->z); + float d = sqrtf(x*x + y*y + z*z); + + vertex->x = float_to_fixed(fixed_to_float(vertex->x) / d); + vertex->y = float_to_fixed(fixed_to_float(vertex->y) / d); + vertex->z = float_to_fixed(fixed_to_float(vertex->z) / d); +} + +#endif // VERTEX_H |