1
0
Fork 0
mirror of https://git.coom.tech/drummyfish/small3dlib.git synced 2024-11-21 20:39:57 +01:00
This commit is contained in:
Miloslav Číž 2019-06-04 22:59:38 +02:00
parent d0f504bc5d
commit f4a4ca06b4
2 changed files with 102 additions and 106 deletions

View file

@ -1,5 +1,5 @@
#ifndef S3L_H #ifndef SMALL3DLIB_H
#define S3L_H #define SMALL3DLIB_H
/* /*
WIP WIP
@ -126,30 +126,44 @@
// --------------- // ---------------
#ifndef S3L_RESOLUTION_X #ifndef S3L_RESOLUTION_X
#define S3L_RESOLUTION_X 640 ///< Redefine to your screen x resolution. #define S3L_RESOLUTION_X 640 ///< Redefine to screen x resolution.
#endif #endif
#ifndef S3L_RESOLUTION_Y #ifndef S3L_RESOLUTION_Y
#define S3L_RESOLUTION_Y 480 ///< Redefine to your screen y resolution. #define S3L_RESOLUTION_Y 480 ///< Redefine to screen y resolution.
#endif #endif
/** Units of measurement in 3D space. There is S3L_FRACTIONS_PER_UNIT in one
spatial unit. By dividing the unit into fractions we effectively achieve a
fixed point arithmetic. The number of fractions is a constant that serves as
1.0 in floating point arithmetic (normalization etc.). */
typedef int32_t S3L_Unit;
/** How many fractions a spatial unit is split into. This is NOT SUPPOSED TO
BE REDEFINED, so rather don't do it (otherwise things may overflow etc.). */
#define S3L_FRACTIONS_PER_UNIT 512
typedef int16_t S3L_ScreenCoord;
typedef uint16_t S3L_Index;
#ifndef S3L_STRICT_NEAR_CULLING #ifndef S3L_STRICT_NEAR_CULLING
#define S3L_STRICT_NEAR_CULLING 1 /**< If on, any triangle that only partially /** If on, any triangle that only partially intersects the near plane will be
intersects the near plane will be culled. culled. This can prevent errorneous rendering and artifacts, but also makes
This can prevent errorneous rendering and triangles close to the camera disappear. */
artifacts, but also makes triangles close to
the camera disappear. */ #define S3L_STRICT_NEAR_CULLING 1
#endif #endif
#ifndef S3L_FLAT #ifndef S3L_FLAT
#define S3L_FLAT 0 /**< If on, disables computation of per-pixel /** If on, disables computation of per-pixel values such as barycentric
values such as barycentric coordinates and coordinates and depth -- these will still be available but will be the same
depth -- these will still be available but for the whole triangle. This can be used to create flat-shaded renders and
will be the same for the whole triangle. This will be a lot faster. With this option on you will probably want to use
can be used to create flat-shaded renders and sorting instead of z-buffer. */
will be a lot faster. With this option on you
will probably want to use sorting instead of #define S3L_FLAT 0
z-buffer. */
#endif #endif
#if S3L_FLAT #if S3L_FLAT
@ -159,15 +173,13 @@
#endif #endif
#ifndef S3L_PERSPECTIVE_CORRECTION #ifndef S3L_PERSPECTIVE_CORRECTION
#define S3L_PERSPECTIVE_CORRECTION 0 /**< Specifies what type of perspective /** Specifies what type of perspective correction (PC) to use. Remember this
correction (PC) to use. Remember this is an expensive is an expensive operation! Possible values:
operation! Possible values:
- 0 No perspective correction. Fastest, ugly. - 0: No perspective correction. Fastest, ugly.
- 1 Per-pixel perspective correction, nice but very - 1: Per-pixel perspective correction, nice but very expensive.*/
expensive.
- 2 Partial perspecive correction by subdividing #define S3L_PERSPECTIVE_CORRECTION 0
triangles. */
#endif #endif
#if S3L_PERSPECTIVE_CORRECTION #if S3L_PERSPECTIVE_CORRECTION
@ -175,104 +187,83 @@
#endif #endif
#ifndef S3L_COMPUTE_DEPTH #ifndef S3L_COMPUTE_DEPTH
#define S3L_COMPUTE_DEPTH 1 /**< Whether to compute depth for each pixel /** Whether to compute depth for each pixel (fragment). Some other options
(fragment). Some other options may turn this may turn this on automatically. */
on. */ #define S3L_COMPUTE_DEPTH 1
#endif #endif
typedef int32_t S3L_Unit; /**< Units of measurement in 3D space. There is
S3L_FRACTIONS_PER_UNIT in one spatial unit.
By dividing the unit into fractions we
effectively achieve fixed point arithmetic.
The number of fractions is a constant that
serves as 1.0 in floating point arithmetic
(normalization etc.). */
#define S3L_FRACTIONS_PER_UNIT 512 /**< How many fractions a spatial unit is
split into. WARNING: if setting higher than
1024, you'll probably have to modify a sin
table otherwise it will overflow. Also other
things may overflow, so rather don't do
it. */
typedef int16_t S3L_ScreenCoord;
typedef uint16_t S3L_Index;
#ifndef S3L_Z_BUFFER #ifndef S3L_Z_BUFFER
#define S3L_Z_BUFFER 0 /**< What type of z-buffer (depth buffer) to use /** What type of z-buffer (depth buffer) to use for visibility determination.
for visibility determination. possible values: Possible values:
- 0 Don't use z-buffer. This saves a lot of memory, but - 0: Don't use z-buffer. This saves a lot of memory, but visibility checking
visibility checking won't be pixel-accurate and has won't be pixel-accurate and has to mostly be done by other means
to mostly be done by other means (typically (typically sorting).
sorting). - 1: Use full z-buffer (of S3L_Units) for visibiltiy determination. This is
- 1 Use full z-buffer (of S3L_Units) for visibiltiy the most accurate option (and also a fast one), but requires a big
determination. This is the most accurate option amount of memory.
(and also a fast one), but requires a big amount - 2: Use reduced-size z-buffer (of bytes). This is fast and somewhat
of memory. accurate, but inaccuracies can occur and a considerable amount of memory
- 2 Use reduced-size z-buffer (of bytes). This is fast is needed. */
and somewhat accurate, but inaccuracies can occur
and a considerable amount of memory is needed. */ #define S3L_Z_BUFFER 0
#endif #endif
#ifndef S3L_STENCIL_BUFFER #ifndef S3L_STENCIL_BUFFER
#define S3L_STENCIL_BUFFER 0 /**< Whether to use stencil buffer for drawing -- /** Whether to use stencil buffer for drawing -- with this a pixel that would
with this pixels that have already been be resterized over an already rasterized pixel will be discarded. This is
rasterized will be discarded. This is mostly mostly for front-to-back sorted drawing. */
for front-to-back sorted drawing. */
#define S3L_STENCIL_BUFFER 0
#endif #endif
#ifndef S3L_SORT #ifndef S3L_SORT
#define S3L_SORT 0 /**< Defines how to sort triangles before /** Defines how to sort triangles before drawing a frame. This can be used to
drawing a frame. This can be used to solve visibility solve visibility in case z-buffer is not used, to prevent overwrting already
in case z-buffer is not used, to prevent overwrting rasterized pixels, implement transparency etc. Note that for simplicity and
already rasterized pixels, implement transparency etc. performance a relatively simple sorting is used which doesn't work completely
Note that for simplicity and performance a relatively correctly, so mistakes can occur (even the best sorting wouldn't be able to
simple sorting is used which doesn't work completely solve e.g. intersecting triangles). Possible values:
correctly, so mistakes can occur (even the best sorting
wouldn't be able to solve e.g. intersecting triangles).
Possible values:
- 0 Don't sort triangles. This is fastest. - 0: Don't sort triangles. This is fastest.
- 1 Sort triangles from back to front. This can in most - 1: Sort triangles from back to front. This can in most cases solve
cases solve visibility without requiring almost any visibility without requiring almost any extra memory compared to
extra memory compared to z-buffer. z-buffer.
- 2 Sort triangles from front to back. This can be - 2: Sort triangles from front to back. This can be faster than back to
faster than back to front, because we prevent front, because we prevent computing pixels that will be overwritten by
computing pixels that will be overwritten by nearer nearer ones, but we need a 1b stencil buffer for this (enable
ones, but we need a 1b stencil buffer for this S3L_STENCIL_BUFFER), so a bit more memory is needed. */
(enable S3L_STENCIL_BUFFER), so a bit more memory
is needed. */ #define S3L_SORT 0
#endif #endif
#ifndef S3L_MAX_TRIANGES_DRAWN #ifndef S3L_MAX_TRIANGES_DRAWN
#define S3L_MAX_TRIANGES_DRAWN 128 /**< Maximum number of triangles that can be /** Maximum number of triangles that can be drawn in sorted modes. This
drawn in sorted modes. This affects the size affects the size of the cache used for triangle sorting. */
of a cache used for triangle sorting. */
#define S3L_MAX_TRIANGES_DRAWN 128
#endif #endif
#ifndef S3L_NEAR #ifndef S3L_NEAR
#define S3L_NEAR (S3L_FRACTIONS_PER_UNIT / 4) /**< Distance of the near /** Distance of the near clipping plane. Points in front or EXATLY ON this
clipping plane. Points in front or EXATLY ON plane are considered outside the frustum. This must be >= 0. */
this plane are considered outside the
frustum. This must be >= 0. */ #define S3L_NEAR (S3L_FRACTIONS_PER_UNIT / 4)
#endif #endif
#if S3L_NEAR <= 0 #if S3L_NEAR <= 0
#define S3L_NEAR 1 // Can't be <= 0. #define S3L_NEAR 1 // Can't be <= 0.
#endif #endif
#ifndef S3L_FAST_LERP_QUALITY #ifndef S3L_FAST_LERP_QUALITY
#define S3L_FAST_LERP_QUALITY 8 /**< Quality (scaling) of SOME linear /** Quality (scaling) of SOME (stepped) linear interpolations. 0 will most
interpolations. 0 will most likely be faster, likely be a tiny bit faster, but artifacts can occur for bigger tris, while
but artifacts can occur for bigger tris, higher values can fix this -- in theory all higher values will have the same
while higher values can fix this -- in speed (it is a shift value), but it mustn't be too high to prevent
theory all higher values will have the same overflow. */
speed (it is a shift value), but it mustn't
be too high to prevent overflow. */
#endif
#define S3L_HALF_RESOLUTION_X (S3L_RESOLUTION_X >> 1) #define S3L_FAST_LERP_QUALITY 8
#define S3L_HALF_RESOLUTION_Y (S3L_RESOLUTION_Y >> 1) #endif
/** Vector that consists of four scalars and can represent homogenous /** Vector that consists of four scalars and can represent homogenous
coordinates, but is generally also used as Vec3 and Vec2. */ coordinates, but is generally also used as Vec3 and Vec2. */
@ -289,7 +280,7 @@ static inline void S3L_initVec4(S3L_Vec4 *v);
static inline void S3L_vec3Add(S3L_Vec4 *result, S3L_Vec4 added); static inline void S3L_vec3Add(S3L_Vec4 *result, S3L_Vec4 added);
static inline void S3L_vec3Sub(S3L_Vec4 *result, S3L_Vec4 substracted); static inline void S3L_vec3Sub(S3L_Vec4 *result, S3L_Vec4 substracted);
#define S3L_writeVec4(v)\ #define S3L_logVec4(v)\
printf("Vec4: %d %d %d %d\n",((v).x),((v).y),((v).z),((v).w)) printf("Vec4: %d %d %d %d\n",((v).x),((v).y),((v).z),((v).w))
typedef struct typedef struct
@ -302,7 +293,7 @@ typedef struct
S3L_Vec4 scale; S3L_Vec4 scale;
} S3L_Transform3D; } S3L_Transform3D;
#define S3L_writeTransform3D(t)\ #define S3L_logTransform3D(t)\
printf("Transform3D: T = [%d %d %d], R = [%d %d %d], S = [%d %d %d]\n",\ printf("Transform3D: T = [%d %d %d], R = [%d %d %d], S = [%d %d %d]\n",\
(t).translation.x,(t).translation.y,(t).translation.z,\ (t).translation.x,(t).translation.y,(t).translation.z,\
(t).rotation.x,(t).rotation.y,(t).rotation.z,\ (t).rotation.x,(t).rotation.y,(t).rotation.z,\
@ -331,10 +322,12 @@ void S3L_rotationToDirections(
S3L_Vec4 *right, S3L_Vec4 *right,
S3L_Vec4 *up); S3L_Vec4 *up);
typedef S3L_Unit S3L_Mat4[4][4]; /**< 4x4 matrix, used mostly for 3D
transforms. The indexing is this: /** 4x4 matrix, used mostly for 3D transforms. The indexing is this:
matrix[column][row]. */ matrix[column][row]. */
#define S3L_writeMat4(m)\ typedef S3L_Unit S3L_Mat4[4][4];
#define S3L_logMat4(m)\
printf("Mat4:\n %d %d %d %d\n %d %d %d %d\n %d %d %d %d\n %d %d %d %d\n"\ printf("Mat4:\n %d %d %d %d\n %d %d %d %d\n %d %d %d %d\n %d %d %d %d\n"\
,(m)[0][0],(m)[1][0],(m)[2][0],(m)[3][0],\ ,(m)[0][0],(m)[1][0],(m)[2][0],(m)[3][0],\
(m)[0][1],(m)[1][1],(m)[2][1],(m)[3][1],\ (m)[0][1],(m)[1][1],(m)[2][1],(m)[3][1],\
@ -576,6 +569,9 @@ static inline void S3L_rotate2DPoint(S3L_Unit *x, S3L_Unit *y, S3L_Unit angle);
//============================================================================= //=============================================================================
// privates // privates
#define S3L_HALF_RESOLUTION_X (S3L_RESOLUTION_X >> 1)
#define S3L_HALF_RESOLUTION_Y (S3L_RESOLUTION_Y >> 1)
#define S3L_PROJECTION_PLANE_HEIGHT\ #define S3L_PROJECTION_PLANE_HEIGHT\
((S3L_RESOLUTION_Y * S3L_FRACTIONS_PER_UNIT * 2) / S3L_RESOLUTION_X) ((S3L_RESOLUTION_Y * S3L_FRACTIONS_PER_UNIT * 2) / S3L_RESOLUTION_X)

View file

@ -322,7 +322,7 @@ void draw()
printf("FPS: %d\n",fps); printf("FPS: %d\n",fps);
printf("camera: "); printf("camera: ");
S3L_writeTransform3D(scene.camera.transform); S3L_logTransform3D(scene.camera.transform);
fps = 0; fps = 0;
} }
} }