summaryrefslogtreecommitdiffstats
path: root/libdimension/dimension
diff options
context:
space:
mode:
Diffstat (limited to 'libdimension/dimension')
-rw-r--r--libdimension/dimension/array.h117
-rw-r--r--libdimension/dimension/camera.h40
-rw-r--r--libdimension/dimension/cameras.h19
-rw-r--r--libdimension/dimension/canvas.h79
-rw-r--r--libdimension/dimension/color.h98
-rw-r--r--libdimension/dimension/csg.h31
-rw-r--r--libdimension/dimension/error.h79
-rw-r--r--libdimension/dimension/finishes.h38
-rw-r--r--libdimension/dimension/geometry.h171
-rw-r--r--libdimension/dimension/gl.h27
-rw-r--r--libdimension/dimension/inline.h16
-rw-r--r--libdimension/dimension/interior.h23
-rw-r--r--libdimension/dimension/light.h29
-rw-r--r--libdimension/dimension/lights.h11
-rw-r--r--libdimension/dimension/list.h166
-rw-r--r--libdimension/dimension/malloc.h36
-rw-r--r--libdimension/dimension/object.h101
-rw-r--r--libdimension/dimension/objects.h38
-rw-r--r--libdimension/dimension/pattern.h50
-rw-r--r--libdimension/dimension/patterns.h19
-rw-r--r--libdimension/dimension/pigments.h53
-rw-r--r--libdimension/dimension/png.h42
-rw-r--r--libdimension/dimension/polynomial.h35
-rw-r--r--libdimension/dimension/progress.h26
-rw-r--r--libdimension/dimension/raytrace.h16
-rw-r--r--libdimension/dimension/scene.h56
-rw-r--r--libdimension/dimension/texture.h140
-rw-r--r--libdimension/dimension/timer.h32
28 files changed, 1247 insertions, 341 deletions
diff --git a/libdimension/dimension/array.h b/libdimension/dimension/array.h
index 87af84a..514e13e 100644
--- a/libdimension/dimension/array.h
+++ b/libdimension/dimension/array.h
@@ -18,24 +18,30 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Simple generalized arrays, for returning variable-length arrays from
- * functions, and other fun stuff. All functions are inline for performance
- * reasons.
+/**
+ * @file
+ * Simple dynamic arrays.
*/
#ifndef DIMENSION_ARRAY_H
#define DIMENSION_ARRAY_H
-#include <stdlib.h> /* For size_t */
+#include <stddef.h> /* For size_t */
#include <string.h> /* For memcpy */
-typedef struct {
- void *ptr;
- size_t obj_size, length, capacity;
+/** Dynamic array type */
+typedef struct dmnsn_array {
+ void *ptr; /**< @internal The actual memory */
+ size_t obj_size; /**< @internal The size of each object */
+ size_t length; /**< @internal The current size of the array */
+ size_t capacity; /**< @internal The size of the allocated space */
} dmnsn_array;
-/* Array allocation */
+/**
+ * Allocate an array.
+ * @param[in] obj_size The size of the objects to store in the array.
+ * @return An empty array.
+ */
DMNSN_INLINE dmnsn_array *
dmnsn_new_array(size_t obj_size)
{
@@ -50,7 +56,10 @@ dmnsn_new_array(size_t obj_size)
return array;
}
-/* Delete an array */
+/**
+ * Delete an array.
+ * @param[in,out] array The array to delete.
+ */
DMNSN_INLINE void
dmnsn_delete_array(dmnsn_array *array)
{
@@ -60,14 +69,22 @@ dmnsn_delete_array(dmnsn_array *array)
}
}
-/* Get the size of the array */
+/**
+ * Get the size of the array.
+ * @param[in] array The array in question.
+ * @return The number of elements in the array.
+ */
DMNSN_INLINE size_t
dmnsn_array_size(const dmnsn_array *array)
{
return array->length;
}
-/* Set the size of the array */
+/**
+ * Set the size of the array.
+ * @param[in,out] array The array to resize.
+ * @param[in] length The new length of the array.
+ */
DMNSN_INLINE void
dmnsn_array_resize(dmnsn_array *array, size_t length)
{
@@ -80,7 +97,12 @@ dmnsn_array_resize(dmnsn_array *array, size_t length)
array->length = length;
}
-/* Get the i'th object, bailing out if i is out of range */
+/**
+ * Get the i'th element.
+ * @param[in] array The array to access.
+ * @param[in] i The index of the element to extract.
+ * @param[out] obj The location to store the extracted object.
+ */
DMNSN_INLINE void
dmnsn_array_get(const dmnsn_array *array, size_t i, void *obj)
{
@@ -89,7 +111,12 @@ dmnsn_array_get(const dmnsn_array *array, size_t i, void *obj)
}
-/* Set the i'th object, expanding the array if necessary */
+/**
+ * Set the i'th object, expanding the array if necessary.
+ * @param[in,out] array The array to modify.
+ * @param[in] i The index to update.
+ * @param[in] obj The location of the object to copy into the array.
+ */
DMNSN_INLINE void
dmnsn_array_set(dmnsn_array *array, size_t i, const void *obj)
{
@@ -100,21 +127,34 @@ dmnsn_array_set(dmnsn_array *array, size_t i, const void *obj)
memcpy((char *)array->ptr + array->obj_size*i, obj, array->obj_size);
}
-/* First element */
+/**
+ * First element.
+ * @param[in] array The array to index.
+ * @return The address of the first element of the array.
+ */
DMNSN_INLINE void *
dmnsn_array_first(const dmnsn_array *array)
{
return array->ptr;
}
-/* Last element */
+/**
+ * Last element.
+ * @param[in] array The array to index.
+ * @return The address of the last element of the array.
+ */
DMNSN_INLINE void *
dmnsn_array_last(const dmnsn_array *array)
{
return (char *)array->ptr + array->obj_size*(array->length - 1);
}
-/* Arbitrary element access */
+/**
+ * Arbitrary element access.
+ * @param[in] array The array to index.
+ * @param[in] i The index to access.
+ * @return The address of the i'th element of the array.
+ */
DMNSN_INLINE void *
dmnsn_array_at(const dmnsn_array *array, size_t i)
{
@@ -122,14 +162,22 @@ dmnsn_array_at(const dmnsn_array *array, size_t i)
return (char *)array->ptr + array->obj_size*i;
}
-/* Push obj to the end of the array */
+/**
+ * Push an object to the end of the array.
+ * @param[in,out] array The array to append to.
+ * @param[in] obj The location of the object to push.
+ */
DMNSN_INLINE void
dmnsn_array_push(dmnsn_array *array, const void *obj)
{
dmnsn_array_set(array, dmnsn_array_size(array), obj);
}
-/* Pop obj from the end of the array */
+/**
+ * Pop an object from the end of the array.
+ * @param[in,out] array The array to pop from.
+ * @param[out] obj The location to store the extracted object.
+ */
DMNSN_INLINE void
dmnsn_array_pop(dmnsn_array *array, void *obj)
{
@@ -139,7 +187,12 @@ dmnsn_array_pop(dmnsn_array *array, void *obj)
dmnsn_array_resize(array, size - 1); /* Shrink the array */
}
-/* Insert an item into the middle of the array */
+/**
+ * Insert an item into the middle of the array. This is O(n).
+ * @param[in,out] array The array to insert to.
+ * @param[in] i The index at which to insert.
+ * @param[in] obj The object to insert.
+ */
DMNSN_INLINE void
dmnsn_array_insert(dmnsn_array *array, size_t i, const void *obj)
{
@@ -156,7 +209,11 @@ dmnsn_array_insert(dmnsn_array *array, size_t i, const void *obj)
memcpy((char *)array->ptr + array->obj_size*i, obj, array->obj_size);
}
-/* Remove an item from the middle of the array */
+/**
+ * Remove an item from the middle of the array. This is O(n).
+ * @param[in,out] array The array to remove from.
+ * @param[in] i The index to remove.
+ */
DMNSN_INLINE void
dmnsn_array_remove(dmnsn_array *array, size_t i)
{
@@ -172,11 +229,29 @@ dmnsn_array_remove(dmnsn_array *array, size_t i)
/* Macros to shorten array iteration */
+/**
+ * Iterate over an array. For example,
+ * @code
+ * DMNSN_ARRAY_FOREACH (int *, i, array) {
+ * printf("%d\n", *i);
+ * }
+ * @endcode
+ *
+ * @param type The (pointer) type to use as an iterator.
+ * @param i The name of the iterator within the loop body.
+ * @param[in] array The array to loop over.
+ */
#define DMNSN_ARRAY_FOREACH(type, i, array) \
for (type i = dmnsn_array_first(array); \
i - (type)dmnsn_array_first(array) < dmnsn_array_size(array); \
++i)
+/**
+ * Iterate over an array, in reverse order.
+ * @param type The (pointer) type to use as an iterator.
+ * @param i The name of the iterator within the loop body.
+ * @param[in] array The array to loop over.
+ */
#define DMNSN_ARRAY_FOREACH_REVERSE(type, i, array) \
for (type i = dmnsn_array_last(array); \
i - (type)dmnsn_array_first(array) >= 0; \
diff --git a/libdimension/dimension/camera.h b/libdimension/dimension/camera.h
index e95ad18..e63cd80 100644
--- a/libdimension/dimension/camera.h
+++ b/libdimension/dimension/camera.h
@@ -18,8 +18,9 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * A camera.
+/**
+ * @file
+ * Cameras.
*/
#ifndef DIMENSION_CAMERA_H
@@ -28,20 +29,47 @@
/* Forward-declare dmnsn_camera */
typedef struct dmnsn_camera dmnsn_camera;
-/* Camera callback types */
+/**
+ * Camera ray callback.
+ * @param[in] camera The camera itself.
+ * @param[in] x The x coordinate of the pixel (in [0, 1]).
+ * @param[in] y The y coordinate of the pixel (in [0, 1]).
+ * @return The ray through (\p x, \p y).
+ */
typedef dmnsn_line dmnsn_camera_ray_fn(const dmnsn_camera *camera,
double x, double y);
+/** A camera. */
struct dmnsn_camera {
/* Callback functions */
- dmnsn_camera_ray_fn *ray_fn;
- dmnsn_free_fn *free_fn;
+ dmnsn_camera_ray_fn *ray_fn; /**< Camera ray callback. */
+ dmnsn_free_fn *free_fn; /**< Destructor callback. */
+
+ dmnsn_matrix trans; /**< Transformation matrix. */
- /* Generic pointer for camera info */
+ /** Generic pointer for camera info */
void *ptr;
};
+/**
+ * Create a dummy camera.
+ * @return The allocated camera.
+ */
dmnsn_camera *dmnsn_new_camera(void);
+
+/**
+ * Delete a camera.
+ * @param[in,out] camera The camera to delete.
+ */
void dmnsn_delete_camera(dmnsn_camera *camera);
+/**
+ * Invoke the camera ray callback, then correctly transform the ray.
+ * @param[in] camera The camera itself.
+ * @param[in] x The x coordinate of the pixel (in [0, 1]).
+ * @param[in] y The y coordinate of the pixel (in [0, 1]).
+ * @return The ray through (\p x, \p y).
+ */
+dmnsn_line dmnsn_camera_ray(const dmnsn_camera *camera, double x, double y);
+
#endif /* DIMENSION_CAMERA_H */
diff --git a/libdimension/dimension/cameras.h b/libdimension/dimension/cameras.h
index 7f4d549..077aebc 100644
--- a/libdimension/dimension/cameras.h
+++ b/libdimension/dimension/cameras.h
@@ -18,20 +18,21 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Types of cameras.
+/**
+ * @file
+ * Pre-defined camera types.
*/
#ifndef DIMENSION_CAMERAS_H
#define DIMENSION_CAMERAS_H
-/* A perspective camera, at the origin, looking at (0, 0, 1). The feild of view
- is the section of the plane z = 1 from (-0.5, -0.5) to (0.5, 0.5). Rays are
- transformed by the camera's transformation matrix. */
+/**
+ * A perspective camera. The camera is located at the origin, looking at
+ * (0, 0, 1). The feild of view is the section of the plane z = 1 from
+ * (-0.5, -0.5) to (0.5, 0.5). Rays are transformed by the camera's
+ * transformation matrix.
+ * @return A perspective camera.
+ */
dmnsn_camera *dmnsn_new_perspective_camera(void);
-/* Get or set the transformation matrix */
-dmnsn_matrix dmnsn_get_perspective_camera_trans(const dmnsn_camera *camera);
-void dmnsn_set_perspective_camera_trans(dmnsn_camera *camera, dmnsn_matrix T);
-
#endif /* DIMENSION_CAMERAS_H */
diff --git a/libdimension/dimension/canvas.h b/libdimension/dimension/canvas.h
index 018dcda..bc98e71 100644
--- a/libdimension/dimension/canvas.h
+++ b/libdimension/dimension/canvas.h
@@ -18,7 +18,8 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
+/**
+ * @file
* A canvas which is rendered to.
*/
@@ -27,16 +28,18 @@
#include <stddef.h>
+/** A canvas, or image. */
typedef struct {
- /* width, height */
- size_t x, y;
+ size_t width; /**< Canvas width */
+ size_t height; /**< Canvas height */
- /* An array of dmnsn_canvas_optimizer's */
+ /** An array of <tt>dmnsn_canvas_optimizer</tt>s */
dmnsn_array *optimizers;
- /*
+ /**
+ * @internal
* Stored in first-quadrant representation (origin is bottom-left). The pixel
- * at (a,b) is accessible as pixels[b*x + a].
+ * at (a,b) is accessible as pixels[b*width + a].
*/
dmnsn_color *pixels;
} dmnsn_canvas;
@@ -44,39 +47,79 @@ typedef struct {
/* Forward-declare dmnsn_canvas_optimizer */
typedef struct dmnsn_canvas_optimizer dmnsn_canvas_optimizer;
-/* Canvas optimizer callback types */
-typedef void dmnsn_canvas_optimizer_fn(dmnsn_canvas *canvas,
+/**
+ * Canvas optimizer callback type.
+ * @param[in] canvas The canvas that was just updated.
+ * @param[in] optimizer The canvas optimizer itself.
+ * @param[in] x The x-coordinate that was just updated.
+ * @param[in] y The y-coordinate that was just updated.
+ */
+typedef void dmnsn_canvas_optimizer_fn(const dmnsn_canvas *canvas,
dmnsn_canvas_optimizer optimizer,
size_t x, size_t y);
-/* Canvas optimizer */
+/** Canvas optimizer */
struct dmnsn_canvas_optimizer {
- /* Callback types */
- dmnsn_canvas_optimizer_fn *optimizer_fn;
- dmnsn_free_fn *free_fn;
+ dmnsn_canvas_optimizer_fn *optimizer_fn; /**< Optimizer callback */
+ dmnsn_free_fn *free_fn; /**< Destructor callback */
- /* Generic pointer */
- void *ptr;
+ void *ptr; /**< Generic pointer. */
};
-/* Allocate and free a canvas */
-dmnsn_canvas *dmnsn_new_canvas(size_t x, size_t y);
+/**
+ * Allocate a new canvas.
+ * @param[in] width The width of the canvas to allocate (in pixels).
+ * @param[in] height The height of the canvas to allocate (in pixels).
+ * @return The allocated canvas.
+ */
+dmnsn_canvas *dmnsn_new_canvas(size_t width, size_t height);
+
+/**
+ * Delete a canvas.
+ * @param[in,out] canvas The canvas to delete.
+ */
void dmnsn_delete_canvas(dmnsn_canvas *canvas);
-/* Set a canvas optimizer */
+/**
+ * Set a canvas optimizer
+ * @param[in,out] canvas The canvas to optimize.
+ * @param[in] optimizer The optimizer to use.
+ */
void dmnsn_optimize_canvas(dmnsn_canvas *canvas,
dmnsn_canvas_optimizer optimizer);
/* Pixel accessors */
+/**
+ * Get the color of a pixel.
+ * @param[in] canvas The canvas to access.
+ * @param[in] x The x coordinate.
+ * @param[in] y The y coordinate.
+ * @return The color of the canvas at (\p x, \p y).
+ */
DMNSN_INLINE dmnsn_color
dmnsn_get_pixel(const dmnsn_canvas *canvas, size_t x, size_t y)
{
- return canvas->pixels[y*canvas->x + x];
+ dmnsn_assert(x < canvas->width && y < canvas->height,
+ "Canvas access out of bounds.");
+ return canvas->pixels[y*canvas->width + x];
}
+/**
+ * Set the color of a pixel.
+ * @param[in,out] canvas The canvas to modify.
+ * @param[in] x The x coordinate of the pixel.
+ * @param[in] y The y coordinate of the pixel.
+ * @param[in] color The color to set the pixel at (\p x, \p y) to.
+ */
void dmnsn_set_pixel(dmnsn_canvas *canvas, size_t x, size_t y,
dmnsn_color color);
+
+/**
+ * Clear a canvas uniformly with a given color.
+ * @param[in,out] canvas The canvas to erase.
+ * @param[in] color The color to paint it with.
+ */
void dmnsn_clear_canvas(dmnsn_canvas *canvas, dmnsn_color color);
#endif /* DIMENSION_CANVAS_H */
diff --git a/libdimension/dimension/color.h b/libdimension/dimension/color.h
index 9e47282..393778d 100644
--- a/libdimension/dimension/color.h
+++ b/libdimension/dimension/color.h
@@ -18,8 +18,9 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Types to represent color.
+/**
+ * @file
+ * Color-related types and operations.
*/
#ifndef DIMENSION_COLOR_H
@@ -27,71 +28,110 @@
#include <stdbool.h>
-/* Internally, we use sRGB color. */
+/** A color value. */
typedef struct {
- double filter, trans; /* Filter transparancy only lets light of this color
- through; regular transparancy lets all colors
- through. filter + trans should be <= 1.0. */
- double R, G, B;
+ /** Filtered transparency. */
+ double filter;
+ /** Unfiltered transparency; <tt>filter + trans</tt> should be <= 1. */
+ double trans;
+
+ /* Internally we use sRGB color. */
+ double R; /**< @internal sRGB red value. */
+ double G; /**< @internal sRGB green value. */
+ double B; /**< @internal sRGB blue value. */
} dmnsn_color;
+/** sRGB color. */
typedef struct {
- double X, Y, Z; /* X, Y, and Z are tristimulus values, unbounded above zero.
- Diffuse white is (0.9505, 1, 1.089). */
+ double R; /**< sRGB red value. */
+ double G; /**< sRGB green value. */
+ double B; /**< sRGB blue value. */
+} dmnsn_sRGB;
+
+/** CIE XYZ color. */
+typedef struct {
+ double X; /**< X component. */
+ double Y; /**< Y (luminance) component. */
+ double Z; /**< Z component. */
} dmnsn_CIE_XYZ;
+/** CIE xyY color. */
typedef struct {
- double x, y, Y; /* x and y are chromaticity coordinates, and Y is luminance,
- in the CIE 1931 xyZ color space. We use an unlimited light
- model, so x,y in [0, 1] and Y >= 0, with 1 = diffuse
- white */
+ double x; /**< x chromaticity coordinate (in [0, 1]) */
+ double y; /**< y chromaticity coordinate (in [0, 1]) */
+ double Y; /**< Luminance, unbounded >= 0; 1 is diffuse white. */
} dmnsn_CIE_xyY;
+/** CIE 1976 (L*, a*, b*) color. */
typedef struct {
- double L, a, b; /* L is luminence (100 = diffuse white); a and b are color-
- opponent dimensions. This color space is used for color
- arithmetic. */
+ double L; /**< Luminance (100 is diffuse white). */
+ double a; /**< Red/greed color-opponent value. */
+ double b; /**< Yellow/blue color-opponent value. */
} dmnsn_CIE_Lab;
+/** CIE 1976 (L*, u*, v*) color. */
typedef struct {
- double L, u, v; /* L is luminence (100 = diffuse white); u and v are
- chromaticity coordinates. */
+ double L; /**< Luminance (same L* as CIE L*, a*, b*) */
+ double u; /**< u* coordinate. */
+ double v; /**< v* coordinate. */
} dmnsn_CIE_Luv;
-typedef struct {
- double R, G, B; /* sRGB R, G, and B values */
-} dmnsn_sRGB;
-
/* Standard colors */
-extern const dmnsn_color dmnsn_black, dmnsn_white, dmnsn_red, dmnsn_green,
- dmnsn_blue, dmnsn_magenta, dmnsn_orange, dmnsn_yellow, dmnsn_cyan;
-
-/* Standard whitepoint, determined by the conversion of sRGB white to CIE XYZ */
+extern const dmnsn_color dmnsn_black; /**< Black. */
+extern const dmnsn_color dmnsn_white; /**< White. */
+extern const dmnsn_color dmnsn_red; /**< Red. */
+extern const dmnsn_color dmnsn_green; /**< Green. */
+extern const dmnsn_color dmnsn_blue; /**< Blue. */
+extern const dmnsn_color dmnsn_magenta; /**< Magenta. */
+extern const dmnsn_color dmnsn_orange; /**< Orange. */
+extern const dmnsn_color dmnsn_yellow; /**< Yellow. */
+extern const dmnsn_color dmnsn_cyan; /**< Cyan. */
+
+/** Standard whitepoint, determined by the conversion of sRGB white to
+ CIE XYZ */
extern const dmnsn_CIE_XYZ dmnsn_whitepoint;
-/* Is this color black? */
+/** Is this color black? */
bool dmnsn_color_is_black(dmnsn_color color);
/* Color conversions */
+/** Convert an sRGB color to a Dimension color */
+dmnsn_color dmnsn_color_from_sRGB(dmnsn_sRGB sRGB);
+/** Convert a CIE XYZ color to a Dimension color */
dmnsn_color dmnsn_color_from_XYZ(dmnsn_CIE_XYZ XYZ);
+/** Convert a CIE xyY color to a Dimension color */
dmnsn_color dmnsn_color_from_xyY(dmnsn_CIE_xyY xyY);
+/** Convert a CIE L*, a*, b* color to a Dimension color */
dmnsn_color dmnsn_color_from_Lab(dmnsn_CIE_Lab Lab, dmnsn_CIE_XYZ white);
+/** Convert a CIE L*, u*, v* color to a Dimension color */
dmnsn_color dmnsn_color_from_Luv(dmnsn_CIE_Luv Luv, dmnsn_CIE_XYZ white);
-dmnsn_color dmnsn_color_from_sRGB(dmnsn_sRGB sRGB);
+/** Convert a Dimension color to sRGB */
+dmnsn_sRGB dmnsn_sRGB_from_color(dmnsn_color color);
+/** Convert a Dimension color to CIE XYZ */
dmnsn_CIE_XYZ dmnsn_XYZ_from_color(dmnsn_color color);
+/** Convert a Dimension color to CIE xyY */
dmnsn_CIE_xyY dmnsn_xyY_from_color(dmnsn_color color);
+/** Convert a Dimension color to CIE L*, a*, b* */
dmnsn_CIE_Lab dmnsn_Lab_from_color(dmnsn_color color, dmnsn_CIE_XYZ white);
+/** Convert a Dimension color to CIE L*, u*, v* */
dmnsn_CIE_Luv dmnsn_Luv_from_color(dmnsn_color color, dmnsn_CIE_XYZ white);
-dmnsn_sRGB dmnsn_sRGB_from_color(dmnsn_color color);
/* Perceptual color manipulation */
+
+/** Add two colors together */
dmnsn_color dmnsn_color_add(dmnsn_color color1, dmnsn_color color2);
+/** Multiply a color's intensity by \p n */
dmnsn_color dmnsn_color_mul(double n, dmnsn_color color);
+/** Return the color at \p n on a gradient from \p c1 at 0 to \p c2 at 1 */
dmnsn_color dmnsn_color_gradient(dmnsn_color c1, dmnsn_color c2, double n);
+/** Filter \p color through \p filter. */
dmnsn_color dmnsn_color_filter(dmnsn_color color, dmnsn_color filter);
+/** Illuminate \p color with \p light. */
dmnsn_color dmnsn_color_illuminate(dmnsn_color light, dmnsn_color color);
+
+/** Return the perceptual difference between two colors. */
double dmnsn_color_difference(dmnsn_color color1, dmnsn_color color2);
#endif /* DIMENSION_COLOR_H */
diff --git a/libdimension/dimension/csg.h b/libdimension/dimension/csg.h
index 176467a..5d923bf 100644
--- a/libdimension/dimension/csg.h
+++ b/libdimension/dimension/csg.h
@@ -18,16 +18,43 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
+/**
+ * @file
* Constructive solid geometry
*/
#ifndef DIMENSION_CSG_H
#define DIMENSION_CSG_H
-dmnsn_object *dmnsn_new_csg_union(dmnsn_array *objects);
+/**
+ * CSG union.
+ * @param[in] objects The objects from which to compose the union.
+ * @return A union of the objects in \p objects.
+ */
+dmnsn_object *dmnsn_new_csg_union(const dmnsn_array *objects);
+
+/**
+ * CSG intersection.
+ * @param[in,out] A The first object.
+ * @param[in,out] B The second object.
+ * @return The intersection of \p A and \p B.
+ */
dmnsn_object *dmnsn_new_csg_intersection(dmnsn_object *A, dmnsn_object *B);
+
+/**
+ * CSG intersection.
+ * @param[in,out] A The outer object.
+ * @param[in,out] B The inner object.
+ * @return The difference between \p A and \p B.
+ */
dmnsn_object *dmnsn_new_csg_difference(dmnsn_object *A, dmnsn_object *B);
+
+/**
+ * CSG Merge.
+ * @param[in,out] A The first object.
+ * @param[in,out] B The second object.
+ * @return The merge of \p A and \p B.
+ */
dmnsn_object *dmnsn_new_csg_merge(dmnsn_object *A, dmnsn_object *B);
#endif /* DIMENSION_CSG_H */
diff --git a/libdimension/dimension/error.h b/libdimension/dimension/error.h
index a0b3857..8482266 100644
--- a/libdimension/dimension/error.h
+++ b/libdimension/dimension/error.h
@@ -18,22 +18,29 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Error handling. Errors are reported at a given severity by the dmnsn_error()
- * macro at a given severity, which prints a warning if it is below the set
- * resilience, or prints an error and exits if it's at or above the set
- * resilience.
+/**
+ * @file
+ * Error reporting interface. Errors are reported at a given severity by the
+ * dmnsn_error() macro at a given severity, which prints a warning if it is
+ * below the set resilience, or prints an error and exits if it's at or above
+ * the set resilience.
*/
#ifndef DIMENSION_ERROR_H
#define DIMENSION_ERROR_H
-typedef enum {
- DMNSN_SEVERITY_LOW, /* Only die on low resilience */
- DMNSN_SEVERITY_MEDIUM, /* Die on low or medium resilience */
- DMNSN_SEVERITY_HIGH /* Always die */
+/** Error severity codes */
+typedef enum dmnsn_severity {
+ DMNSN_SEVERITY_LOW, /**< Only die on low resilience */
+ DMNSN_SEVERITY_MEDIUM, /**< Die on low or medium resilience */
+ DMNSN_SEVERITY_HIGH /**< Always die */
} dmnsn_severity;
+/**
+ * @internal
+ * @def DMNSN_FUNC
+ * @brief Expands to the name of the current function
+ */
#ifdef __GNUC__
#define DMNSN_FUNC __PRETTY_FUNCTION__
#elif __STDC_VERSION__ >= 199901L
@@ -42,13 +49,24 @@ typedef enum {
#define DMNSN_FUNC "<unknown function>"
#endif
-/* Use this macro to report an error */
+/**
+ * Report an error.
+ * @param[in] severity A @ref dmnsn_severity representing the severity of the
+ * error. DMNSN_SEVERITY_HIGH will always terminate the
+ * running thread.
+ * @param[in] str A string to print explaining the error.
+ */
#define dmnsn_error(severity, str) \
dmnsn_report_error((dmnsn_severity)(severity), \
DMNSN_FUNC, __FILE__, __LINE__, \
str)
-/* Make an assertion */
+/**
+ * @def dmnsn_assert
+ * Make an assertion.
+ * @param[in] expr The expression to assert.
+ * @param[in] str A string to print if the assertion fails.
+ */
#ifdef NDEBUG
#define dmnsn_assert(expr, str) ((void)0)
#else
@@ -60,21 +78,50 @@ typedef enum {
} while (0)
#endif
-/* Called by dmnsn_error() - don't call directly */
+/**
+ * @internal
+ * Called by dmnsn_error(); don't call directly.
+ * @param[in] severity The severity of the error.
+ * @param[in] func The name of the function where the error originated.
+ * @param[in] file The file where the error originated.
+ * @param[in] line The line number where the error originated.
+ * @param[in] str A string describing the error.
+ */
void dmnsn_report_error(dmnsn_severity severity,
const char *func, const char *file, unsigned int line,
const char *str);
-/* Get and set the library resilience, thread-safely */
+/**
+ * Get the library resilience, thread-safely.
+ * @return The error severity considered fatal.
+ */
dmnsn_severity dmnsn_get_resilience(void);
+
+/**
+ * Set the library resilience, thread-safely.
+ * @param[in] resilience The new minimum severity that will cause a fatal
+ * error.
+ */
void dmnsn_set_resilience(dmnsn_severity resilience);
-/* Fatal error callback type */
+/**
+ * Fatal error callback type. This function should never return.
+ */
typedef void dmnsn_fatal_error_fn(void);
-/* Get and set libdimension fatal error handling strategy - the default is
- exit(EXIT_FAILURE) */
+/**
+ * Get the libdimension fatal error handler, thread-safely. The default fatal
+ * error handler terminates the current thread, or the entire program if the
+ * current thread is the main thread.
+ * @return The current fatal error handler.
+ */
dmnsn_fatal_error_fn *dmnsn_get_fatal_error_fn(void);
+
+/**
+ * Set the libdimension fatal error handler, thread-safely.
+ * @param[in] fatal The new fatal error handler. This function must never
+ * return.
+ */
void dmnsn_set_fatal_error_fn(dmnsn_fatal_error_fn *fatal);
#endif /* DIMENSION_ERROR_H */
diff --git a/libdimension/dimension/finishes.h b/libdimension/dimension/finishes.h
index b84b5fb..bc07759 100644
--- a/libdimension/dimension/finishes.h
+++ b/libdimension/dimension/finishes.h
@@ -18,23 +18,51 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Custom finishes.
+/**
+ * @file
+ * Pre-defined finishes.
*/
#ifndef DIMENSION_FINISHES_H
#define DIMENSION_FINISHES_H
-/* Add two finishes */
+/**
+ * Add two finishes together.
+ * @param[in,out] f1 The first finish.
+ * @param[in,out] f2 The second finish.
+ * @return A finish that adds the values of two finishes together.
+ */
dmnsn_finish *dmnsn_new_finish_combination(dmnsn_finish *f1, dmnsn_finish *f2);
+/**
+ * Ambient finish.
+ * @param[in] ambient The color of the ambient light.
+ * @return A finish with ambient light.
+ */
dmnsn_finish *dmnsn_new_ambient_finish(dmnsn_color ambient);
+
+/**
+ * Diffuse finish.
+ * @param[in] diffuse The diffuse reflection coefficient.
+ * @return A finish with diffuse reflection.
+ */
dmnsn_finish *dmnsn_new_diffuse_finish(double diffuse);
-/* A phong specular highlight */
+/**
+ * A phong specular highlight.
+ * @param[in] specular The specular reflection coefficient.
+ * @param[in] exp The exponent (roughly the highlight size).
+ * @return A finish with phong specular highlight.
+ */
dmnsn_finish *dmnsn_new_phong_finish(double specular, double exp);
-/* Specular reflection */
+/**
+ * Specular (mirror) reflection.
+ * @param[in] min Reflection at paralell angles.
+ * @param[in] max Reflection at perpendicular angles (often == \p min).
+ * @param[in] falloff Degree of exponential falloff (usually 1).
+ * @return A finish with specular reflection.
+ */
dmnsn_finish *dmnsn_new_reflective_finish(dmnsn_color min, dmnsn_color max,
double falloff);
diff --git a/libdimension/dimension/geometry.h b/libdimension/dimension/geometry.h
index adf41dc..a62fb75 100644
--- a/libdimension/dimension/geometry.h
+++ b/libdimension/dimension/geometry.h
@@ -18,7 +18,8 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
+/**
+ * @file
* Core geometric types like vectors, matricies, and rays.
*/
@@ -28,74 +29,105 @@
#include <math.h>
#include <stdbool.h>
-/* Vector and matrix types */
+/** A vector in 3 dimensions. */
+typedef struct dmnsn_vector {
+ double x; /**< The x component. */
+ double y; /**< The y component. */
+ double z; /**< The z component. */
+} dmnsn_vector;
-typedef struct dmnsn_vector { double x, y, z; } dmnsn_vector;
+/** A standard format string for vectors. */
#define DMNSN_VECTOR_FORMAT "<%g, %g, %g>"
+/** The appropriate arguements to printf() a vector. */
#define DMNSN_VECTOR_PRINTF(v) (v).x, (v).y, (v).z
-typedef struct dmnsn_matrix { double n[4][4]; } dmnsn_matrix;
+/** A 4x4 affine transformation matrix. */
+typedef struct dmnsn_matrix {
+ double n[4][4]; /**< The matrix elements in row-major order. */
+} dmnsn_matrix;
+
+/** A standard format string for matricies. */
#define DMNSN_MATRIX_FORMAT \
"[%g\t%g\t%g\t%g]\n" \
"[%g\t%g\t%g\t%g]\n" \
"[%g\t%g\t%g\t%g]\n" \
"[%g\t%g\t%g\t%g]"
+/** The appropriate arguements to printf() a matrix. */
#define DMNSN_MATRIX_PRINTF(m) \
(m).n[0][0], (m).n[0][1], (m).n[0][2], (m).n[0][3], \
(m).n[1][0], (m).n[1][1], (m).n[1][2], (m).n[1][3], \
(m).n[2][0], (m).n[2][1], (m).n[2][2], (m).n[2][3], \
(m).n[3][0], (m).n[3][1], (m).n[3][2], (m).n[3][3]
-/* A line, or ray */
+/** A line, or ray. */
typedef struct dmnsn_line {
- dmnsn_vector x0; /* A point on the line */
- dmnsn_vector n; /* A normal vector; the direction of the line */
+ dmnsn_vector x0; /**< A point on the line. */
+ dmnsn_vector n; /**< A normal vector; the direction of the line. */
} dmnsn_line;
+
+/** A standard format string for lines. */
#define DMNSN_LINE_FORMAT "(<%g, %g, %g> + t*<%g, %g, %g>)"
+/** The appropriate arguements to printf() a line. */
#define DMNSN_LINE_PRINTF(l) \
DMNSN_VECTOR_PRINTF((l).x0), DMNSN_VECTOR_PRINTF((l).n)
-/* A bounding box */
-typedef struct dmnsn_bounding_box { dmnsn_vector min, max; } dmnsn_bounding_box;
+/** An axis-aligned bounding box (AABB). */
+typedef struct dmnsn_bounding_box {
+ dmnsn_vector min; /**< The coordinate-wise minimum extent of the box */
+ dmnsn_vector max; /**< The coordinate-wise maximum extent of the box */
+} dmnsn_bounding_box;
+
+/** A standard format string for bounding boxes. */
#define DMNSN_BOUNDING_BOX_FORMAT "(<%g, %g, %g> ==> <%g, %g, %g>)"
+/** The appropriate arguements to printf() a bounding box. */
#define DMNSN_BOUNDING_BOX_PRINTF(box) \
DMNSN_VECTOR_PRINTF((box).min), DMNSN_VECTOR_PRINTF((box).max)
/* Constants */
+/** The smallest value considered non-zero by some numerical algorithms */
#define dmnsn_epsilon 1.0e-10
+/** The zero vector */
static const dmnsn_vector dmnsn_zero = { 0.0, 0.0, 0.0 };
-static const dmnsn_vector dmnsn_x = { 1.0, 0.0, 0.0 };
-static const dmnsn_vector dmnsn_y = { 0.0, 1.0, 0.0 };
-static const dmnsn_vector dmnsn_z = { 0.0, 0.0, 1.0 };
+/** The x vector. */
+static const dmnsn_vector dmnsn_x = { 1.0, 0.0, 0.0 };
+/** The y vector. */
+static const dmnsn_vector dmnsn_y = { 0.0, 1.0, 0.0 };
+/** The z vector. */
+static const dmnsn_vector dmnsn_z = { 0.0, 0.0, 1.0 };
/* Scalar functions */
+/** Find the minimum of two scalars. */
DMNSN_INLINE double
dmnsn_min(double a, double b)
{
return a < b ? a : b;
}
+/** Find the maximum of two scalars. */
DMNSN_INLINE double
dmnsn_max(double a, double b)
{
return a > b ? a : b;
}
+/** Convert degrees to radians */
DMNSN_INLINE double
dmnsn_radians(double degrees)
{
return degrees*atan(1.0)/45.0;
}
+/** Convert radians to degrees */
DMNSN_INLINE double
dmnsn_degrees(double radians)
{
return radians*45.0/atan(1.0);
}
+/** Return the sign bit of a scalar. */
DMNSN_INLINE int
dmnsn_signbit(double n)
{
@@ -105,6 +137,7 @@ dmnsn_signbit(double n)
/* Shorthand for vector/matrix construction */
+/** Construct a new vector */
DMNSN_INLINE dmnsn_vector
dmnsn_new_vector(double x, double y, double z)
{
@@ -112,6 +145,7 @@ dmnsn_new_vector(double x, double y, double z)
return v;
}
+/** Construct a new matrix */
DMNSN_INLINE dmnsn_matrix
dmnsn_new_matrix(double a0, double a1, double a2, double a3,
double b0, double b1, double b2, double b3,
@@ -125,12 +159,37 @@ dmnsn_new_matrix(double a0, double a1, double a2, double a3,
return m;
}
+/** Return the identity matrix */
dmnsn_matrix dmnsn_identity_matrix(void);
+
+/**
+ * A scale transformation.
+ * @param[in] s A vector with components representing the scaling factor in
+ * each axis.
+ * @return The transformation matrix.
+ */
dmnsn_matrix dmnsn_scale_matrix(dmnsn_vector s);
+/**
+ * A translation.
+ * @param[in] d The vector to translate by.
+ * @return The transformation matrix.
+ */
dmnsn_matrix dmnsn_translation_matrix(dmnsn_vector d);
-/* Left-handed rotation; theta/|theta| = axis, |theta| = angle */
+/**
+ * A left-handed rotation.
+ * @param[in] theta A vector representing an axis and angle.
+ * @f$ axis = \vec{\theta}/|\vec{\theta}| @f$,
+ * @f$ angle = |\vec{\theta}| @f$
+ * @return The transformation matrix.
+ */
dmnsn_matrix dmnsn_rotation_matrix(dmnsn_vector theta);
+/**
+ * Construct a new line.
+ * @param[in] x0 A point on the line.
+ * @param[in] n The direction of the line.
+ * @return The new line.
+ */
DMNSN_INLINE dmnsn_line
dmnsn_new_line(dmnsn_vector x0, dmnsn_vector n)
{
@@ -138,6 +197,7 @@ dmnsn_new_line(dmnsn_vector x0, dmnsn_vector n)
return l;
}
+/** Return the bounding box which contains nothing. */
DMNSN_INLINE dmnsn_bounding_box
dmnsn_zero_bounding_box(void)
{
@@ -148,6 +208,7 @@ dmnsn_zero_bounding_box(void)
return box;
}
+/** Return the bounding box which contains everything. */
DMNSN_INLINE dmnsn_bounding_box
dmnsn_infinite_bounding_box(void)
{
@@ -160,12 +221,20 @@ dmnsn_infinite_bounding_box(void)
/* Vector element access */
+/** Constants for indexing a vector like an array. */
enum {
- DMNSN_X,
- DMNSN_Y,
- DMNSN_Z
+ DMNSN_X, /**< The x component. */
+ DMNSN_Y, /**< The y component. */
+ DMNSN_Z /**< The z component. */
};
+/**
+ * Index a vector like an array.
+ * @param[in] n The vector to index.
+ * @param[in] elem Which element to access; one of \ref DMNSN_X, \ref DMNSN_Y,
+ * or \ref DMNSN_Z.
+ * @return The requested element.
+ */
DMNSN_INLINE double
dmnsn_vector_element(dmnsn_vector n, int elem)
{
@@ -179,12 +248,13 @@ dmnsn_vector_element(dmnsn_vector n, int elem)
default:
dmnsn_assert(false, "Wrong vector element requested.");
- return 0.0; /* Shut up compiler */
+ return 0.0;
}
}
/* Vector and matrix arithmetic */
+/** Negate a vector */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_negate(dmnsn_vector rhs)
{
@@ -193,6 +263,7 @@ dmnsn_vector_negate(dmnsn_vector rhs)
return v;
}
+/** Add two vectors */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_add(dmnsn_vector lhs, dmnsn_vector rhs)
{
@@ -201,6 +272,7 @@ dmnsn_vector_add(dmnsn_vector lhs, dmnsn_vector rhs)
return v;
}
+/** Subtract two vectors */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_sub(dmnsn_vector lhs, dmnsn_vector rhs)
{
@@ -209,6 +281,7 @@ dmnsn_vector_sub(dmnsn_vector lhs, dmnsn_vector rhs)
return v;
}
+/** Multiply a vector by a scalar. */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_mul(double lhs, dmnsn_vector rhs)
{
@@ -217,6 +290,7 @@ dmnsn_vector_mul(double lhs, dmnsn_vector rhs)
return v;
}
+/** Divide a vector by a scalar. */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_div(dmnsn_vector lhs, double rhs)
{
@@ -225,6 +299,7 @@ dmnsn_vector_div(dmnsn_vector lhs, double rhs)
return v;
}
+/** Return the dot product of two vectors. */
DMNSN_INLINE double
dmnsn_vector_dot(dmnsn_vector lhs, dmnsn_vector rhs)
{
@@ -232,6 +307,7 @@ dmnsn_vector_dot(dmnsn_vector lhs, dmnsn_vector rhs)
return lhs.x*rhs.x + lhs.y*rhs.y + lhs.z*rhs.z;
}
+/** Return the cross product of two vectors. */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_cross(dmnsn_vector lhs, dmnsn_vector rhs)
{
@@ -242,6 +318,7 @@ dmnsn_vector_cross(dmnsn_vector lhs, dmnsn_vector rhs)
return v;
}
+/** Return the projection of \p u onto \p d. */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_proj(dmnsn_vector u, dmnsn_vector d)
{
@@ -249,6 +326,7 @@ dmnsn_vector_proj(dmnsn_vector u, dmnsn_vector d)
return dmnsn_vector_mul(dmnsn_vector_dot(u, d)/dmnsn_vector_dot(d, d), d);
}
+/** Return the magnitude of a vector. */
DMNSN_INLINE double
dmnsn_vector_norm(dmnsn_vector n)
{
@@ -256,6 +334,7 @@ dmnsn_vector_norm(dmnsn_vector n)
return sqrt(dmnsn_vector_dot(n, n));
}
+/** Return the direction of a vector. */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_normalize(dmnsn_vector n)
{
@@ -263,6 +342,7 @@ dmnsn_vector_normalize(dmnsn_vector n)
return dmnsn_vector_div(n, dmnsn_vector_norm(n));
}
+/** Return the component-wise minimum of two vectors. */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_min(dmnsn_vector a, dmnsn_vector b)
{
@@ -273,6 +353,7 @@ dmnsn_vector_min(dmnsn_vector a, dmnsn_vector b)
);
}
+/** Return the component-wise maximum of two vectors. */
DMNSN_INLINE dmnsn_vector
dmnsn_vector_max(dmnsn_vector a, dmnsn_vector b)
{
@@ -283,54 +364,65 @@ dmnsn_vector_max(dmnsn_vector a, dmnsn_vector b)
);
}
+/** Return the angle between two vectors with respect to an axis. */
double dmnsn_vector_axis_angle(dmnsn_vector v1, dmnsn_vector v2,
dmnsn_vector axis);
+/** Invert a matrix. */
dmnsn_matrix dmnsn_matrix_inverse(dmnsn_matrix A);
+
+/** Multiply two matricies. */
dmnsn_matrix dmnsn_matrix_mul(dmnsn_matrix lhs, dmnsn_matrix rhs);
-/* Affine transformation; lhs*(x,y,z,1), normalized so the fourth element is
- 1 */
+/** Transform a vector by a matrix. */
DMNSN_INLINE dmnsn_vector
-dmnsn_transform_vector(dmnsn_matrix lhs, dmnsn_vector rhs)
+dmnsn_transform_vector(dmnsn_matrix T, dmnsn_vector v)
{
/* 12 multiplications, 3 divisions, 12 additions */
dmnsn_vector r;
double w;
- r.x = lhs.n[0][0]*rhs.x + lhs.n[0][1]*rhs.y + lhs.n[0][2]*rhs.z + lhs.n[0][3];
- r.y = lhs.n[1][0]*rhs.x + lhs.n[1][1]*rhs.y + lhs.n[1][2]*rhs.z + lhs.n[1][3];
- r.z = lhs.n[2][0]*rhs.x + lhs.n[2][1]*rhs.y + lhs.n[2][2]*rhs.z + lhs.n[2][3];
- w = lhs.n[3][0]*rhs.x + lhs.n[3][1]*rhs.y + lhs.n[3][2]*rhs.z + lhs.n[3][3];
+ r.x = T.n[0][0]*v.x + T.n[0][1]*v.y + T.n[0][2]*v.z + T.n[0][3];
+ r.y = T.n[1][0]*v.x + T.n[1][1]*v.y + T.n[1][2]*v.z + T.n[1][3];
+ r.z = T.n[2][0]*v.x + T.n[2][1]*v.y + T.n[2][2]*v.z + T.n[2][3];
+ w = T.n[3][0]*v.x + T.n[3][1]*v.y + T.n[3][2]*v.z + T.n[3][3];
return dmnsn_vector_div(r, w);
}
-dmnsn_bounding_box dmnsn_transform_bounding_box(dmnsn_matrix lhs,
- dmnsn_bounding_box rhs);
+/** Transform a bounding box by a matrix. */
+dmnsn_bounding_box dmnsn_transform_bounding_box(dmnsn_matrix T,
+ dmnsn_bounding_box box);
-/* Affine line transformation; n = lhs*(x0 + n) - lhs*x0, x0 *= lhs */
+/**
+ * Transform a line by a matrix.
+ * \f$ n' = T(l.\vec{x_0} + l.\vec{n}) - T(l.\vec{x_0}) \f$,
+ * \f$ \vec{x_0}' = T(l.\vec{x_0}) \f$
+ */
DMNSN_INLINE dmnsn_line
-dmnsn_transform_line(dmnsn_matrix lhs, dmnsn_line rhs)
+dmnsn_transform_line(dmnsn_matrix T, dmnsn_line l)
{
/* 24 multiplications, 6 divisions, 30 additions */
- dmnsn_line l;
- l.x0 = dmnsn_transform_vector(lhs, rhs.x0);
- l.n = dmnsn_vector_sub(
- dmnsn_transform_vector(lhs, dmnsn_vector_add(rhs.x0, rhs.n)),
- l.x0
+ dmnsn_line ret;
+ ret.x0 = dmnsn_transform_vector(T, l.x0);
+ ret.n = dmnsn_vector_sub(
+ dmnsn_transform_vector(T, dmnsn_vector_add(l.x0, l.n)),
+ ret.x0
);
- return l;
+ return ret;
}
-/* A point on a line, defined by x0 + t*n */
+/**
+ * Return the point at \p t on a line.
+ * The point is defined by \f$ l.\vec{x_0} + t \cdot l.\vec{n} \f$
+ */
DMNSN_INLINE dmnsn_vector
dmnsn_line_point(dmnsn_line l, double t)
{
return dmnsn_vector_add(l.x0, dmnsn_vector_mul(t, l.n));
}
-/* Add epsilon*l.n to l.x0, to avoid self-intersections */
+/** Add epsilon*l.n to l.x0, to avoid self-intersections */
DMNSN_INLINE dmnsn_line
dmnsn_line_add_epsilon(dmnsn_line l)
{
@@ -343,10 +435,7 @@ dmnsn_line_add_epsilon(dmnsn_line l)
);
}
-/* Solve for the t value such that x0 + t*n = x */
-double dmnsn_line_index(dmnsn_line l, dmnsn_vector x);
-
-/* Return whether p is within the axis-aligned bounding box */
+/** Return whether \p p is within the axis-aligned bounding box */
DMNSN_INLINE bool
dmnsn_bounding_box_contains(dmnsn_bounding_box box, dmnsn_vector p)
{
@@ -354,7 +443,7 @@ dmnsn_bounding_box_contains(dmnsn_bounding_box box, dmnsn_vector p)
&& (p.x <= box.max.x && p.y <= box.max.y && p.z <= box.max.z);
}
-/* Return whether `box' is infinite */
+/** Return whether a bounding box is infinite */
DMNSN_INLINE bool
dmnsn_bounding_box_is_infinite(dmnsn_bounding_box box)
{
diff --git a/libdimension/dimension/gl.h b/libdimension/dimension/gl.h
index 3eb292c..25979c4 100644
--- a/libdimension/dimension/gl.h
+++ b/libdimension/dimension/gl.h
@@ -18,21 +18,36 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Draw a canvas to a GL framebuffer with glDrawPixels, or read one with
- * glReadPixels. Should be fast, so no _async() versions.
+/**
+ * @file
+ * OpenGL export/import of canvases.
*/
#ifndef DIMENSION_GL_H
#define DIMENSION_GL_H
-/* Optimize canvas for GL drawing */
+/**
+ * Optimize a canvas for GL drawing
+ * @param[in,out] canvas The canvas to optimize.
+ * @return Whether the canvas was successfully optimized.
+ */
int dmnsn_gl_optimize_canvas(dmnsn_canvas *canvas);
-/* Write canvas to GL framebuffer. Returns 0 on success, nonzero on failure. */
+/**
+ * Write canvas to GL framebuffer.
+ * @param[in] canvas The canvas to write.
+ * @return 0 on success, non-zero on failure.
+ */
int dmnsn_gl_write_canvas(const dmnsn_canvas *canvas);
-/* Read a canvas from a GL framebuffer. Returns NULL on failure. */
+/**
+ * Read a canvas from a GL framebuffer.
+ * @param[in] x0 The \a x screen coordinate to start copying from.
+ * @param[in] y0 The \a y screen coordinate to start copying from.
+ * @param[in] width The width of the read area.
+ * @param[in] height The height of the read area.
+ * @return The allocated canvas, or NULL on failure.
+ */
dmnsn_canvas *dmnsn_gl_read_canvas(size_t x0, size_t y0,
size_t width, size_t height);
diff --git a/libdimension/dimension/inline.h b/libdimension/dimension/inline.h
index edf92b1..4f12c28 100644
--- a/libdimension/dimension/inline.h
+++ b/libdimension/dimension/inline.h
@@ -18,16 +18,22 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Handle inlines nicely without cheating and making them static. The
- * DMNSN_INLINE macro is set appropriately for the version of C you're using,
- * and non-inline versions are emitted in exactly one translation unit when
- * necessary.
+/**
+ * @file
+ * Inline function support. Handle inlines nicely without cheating and making
+ * them static. The DMNSN_INLINE macro is set appropriately for the version of
+ * C you're using, and non-inline versions are emitted in exactly one
+ * translation unit when necessary.
*/
#ifndef DIMENSION_INLINE_H
#define DIMENSION_INLINE_H
+/**
+ * @def DMNSN_INLINE
+ * A portable inline specifier. Expands to the correct method of declaring
+ * inline functions for the version of C you are using.
+ */
#ifndef DMNSN_INLINE
#ifdef __cplusplus
/* C++ inline semantics */
diff --git a/libdimension/dimension/interior.h b/libdimension/dimension/interior.h
index 96168cf..7302426 100644
--- a/libdimension/dimension/interior.h
+++ b/libdimension/dimension/interior.h
@@ -18,28 +18,37 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
+/**
+ * @file
* Object interiors.
*/
#ifndef DIMENSION_INTERIOR_H
#define DIMENSION_INTERIOR_H
+/** An interior */
typedef struct dmnsn_interior {
- /* Refractive index */
- double ior;
+ double ior; /**< Refractive index. */
- /* Callbacks */
- dmnsn_free_fn *free_fn;
+ dmnsn_free_fn *free_fn; /**< Destructor callback. */
- /* Generic pointer */
+ /** Generic pointer. */
void *ptr;
- /* Reference count */
+ /** @internal Reference count. */
unsigned int *refcount;
} dmnsn_interior;
+/**
+ * Create an interior object.
+ * @return The new interior.
+ */
dmnsn_interior *dmnsn_new_interior(void);
+
+/**
+ * Delete an interior.
+ * @param[in,out] interior The interior to delete.
+ */
void dmnsn_delete_interior(dmnsn_interior *interior);
#endif /* DIMENSION_INTERIOR_H */
diff --git a/libdimension/dimension/light.h b/libdimension/dimension/light.h
index 69ed9e7..dfda157 100644
--- a/libdimension/dimension/light.h
+++ b/libdimension/dimension/light.h
@@ -18,30 +18,47 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
+/**
+ * @file
* Lights.
*/
#ifndef DIMENSION_LIGHT_H
#define DIMENSION_LIGHT_H
+/* Forward-declar dmnsn_light */
typedef struct dmnsn_light dmnsn_light;
+/**
+ * Light callback.
+ * @param[in] light The light itself.
+ * @param[in] v The point to illuminate.
+ * @return The color of the light at \p v.
+ */
typedef dmnsn_color dmnsn_light_fn(const dmnsn_light *light, dmnsn_vector v);
+/** A light. */
struct dmnsn_light {
- /* Origin of light rays */
- dmnsn_vector x0;
+ dmnsn_vector x0; /**< Origin of light rays */
/* Callbacks */
- dmnsn_light_fn *light_fn;
- dmnsn_free_fn *free_fn;
+ dmnsn_light_fn *light_fn; /**< Light callback. */
+ dmnsn_free_fn *free_fn; /**< Desctructor callback. */
- /* Generic pointer for light info */
+ /** Generic pointer for light info */
void *ptr;
};
+/**
+ * Create a dummy light.
+ * @return The allocated light.
+ */
dmnsn_light *dmnsn_new_light(void);
+
+/**
+ * Delete a light.
+ * @param[in,out] light The light to delete.
+ */
void dmnsn_delete_light(dmnsn_light *light);
#endif /* DIMENSION_LIGHT_H */
diff --git a/libdimension/dimension/lights.h b/libdimension/dimension/lights.h
index 7b7385e..7c0f140 100644
--- a/libdimension/dimension/lights.h
+++ b/libdimension/dimension/lights.h
@@ -18,13 +18,20 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Types of lights.
+/**
+ * @file
+ * Pre-defined light types.
*/
#ifndef DIMENSION_LIGHTS_H
#define DIMENSION_LIGHTS_H
+/**
+ * A point light.
+ * @param[in] x0 The origin of the light.
+ * @param[in] color The color of the light.
+ * @return A point light.
+ */
dmnsn_light *dmnsn_new_point_light(dmnsn_vector x0, dmnsn_color color);
#endif /* DIMENSION_LIGHTS_H */
diff --git a/libdimension/dimension/list.h b/libdimension/dimension/list.h
index dba18dc..9046583 100644
--- a/libdimension/dimension/list.h
+++ b/libdimension/dimension/list.h
@@ -18,8 +18,9 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Simple generalized doubly-linked lists.
+/**
+ * @file
+ * Simple doubly-linked lists.
*/
#ifndef DIMENSION_LIST_H
@@ -29,14 +30,22 @@
#include <stdlib.h>
#include <string.h>
+/**
+ * A list iterator.
+ */
typedef struct dmnsn_list_iterator {
- void *ptr;
- size_t obj_size;
- struct dmnsn_list_iterator *prev, *next;
+ void *ptr; /**< @internal The stored object */
+ size_t obj_size; /**< @internal The object size */
+ struct dmnsn_list_iterator *prev; /**< @internal The previous iterator */
+ struct dmnsn_list_iterator *next; /**< @internal The next iterator */
} dmnsn_list_iterator;
-/* Internal iterator allocation */
-
+/**
+ * @internal
+ * Iterator allocation.
+ * @param[in] obj The location of the object to store in the iterator.
+ * @param[in] obj_size The size of the object to store in the iterator.
+ */
DMNSN_INLINE dmnsn_list_iterator *
dmnsn_new_list_iterator(const void *obj, size_t obj_size)
{
@@ -50,6 +59,11 @@ dmnsn_new_list_iterator(const void *obj, size_t obj_size)
return i;
}
+/**
+ * @internal
+ * Iterator release.
+ * @param[in,out] i The iterator to free.
+ */
DMNSN_INLINE void
dmnsn_delete_list_iterator(dmnsn_list_iterator *i)
{
@@ -59,12 +73,19 @@ dmnsn_delete_list_iterator(dmnsn_list_iterator *i)
}
}
+/** A doubly-linked list. */
typedef struct dmnsn_list {
- dmnsn_list_iterator *first, *last;
- size_t obj_size, length;
+ dmnsn_list_iterator *first; /**< @internal The first iterator in the list */
+ dmnsn_list_iterator *last; /**< @internal The last iterator in the list */
+ size_t length; /**< @internal The size of the list */
+ size_t obj_size; /**< @internal The size of list objects */
} dmnsn_list;
-/* List allocation */
+/**
+ * Allocate a list.
+ * @param[in] obj_size The size of the objects to be stored.
+ * @return An empty list.
+ */
DMNSN_INLINE dmnsn_list *
dmnsn_new_list(size_t obj_size)
{
@@ -76,25 +97,53 @@ dmnsn_new_list(size_t obj_size)
return list;
}
-/* Construction to/from arrays */
+/**
+ * Delete a list.
+ * @param[in,out] list The list to delete.
+ */
+void dmnsn_delete_list(dmnsn_list *list);
+
+/**
+ * Construct a list from an array.
+ * @param[in] array The array to copy.
+ * @return A list with the same contents as \p array.
+ */
dmnsn_list *dmnsn_list_from_array(const dmnsn_array *array);
-dmnsn_array *dmnsn_array_from_list(const dmnsn_list *list);
-/* Delete a list */
-void dmnsn_delete_list(dmnsn_list *list);
+/**
+ * Construct an array from a list.
+ * @param[in] list The list to copy.
+ * @return An array with the same contents as \p list.
+ */
+dmnsn_array *dmnsn_array_from_list(const dmnsn_list *list);
+/**
+ * First element.
+ * @param[in] list The list to index.
+ * @return An iterator to the first list element, or NULL if the list is empty.
+ */
DMNSN_INLINE dmnsn_list_iterator *
dmnsn_list_first(const dmnsn_list *list)
{
return list->first;
}
+/**
+ * Last element.
+ * @param[in] list The list to index.
+ * @return An iterator to the last list element, or NULL if the list is empty.
+ */
DMNSN_INLINE dmnsn_list_iterator *
dmnsn_list_last(const dmnsn_list *list)
{
return list->last;
}
+/**
+ * Previous element.
+ * @param[in] i The iterator to follow.
+ * @return The iterator preceding \c i.
+ */
DMNSN_INLINE dmnsn_list_iterator *
dmnsn_list_prev(const dmnsn_list_iterator *i)
{
@@ -102,6 +151,11 @@ dmnsn_list_prev(const dmnsn_list_iterator *i)
return i->prev;
}
+/**
+ * Next element.
+ * @param[in] i The iterator to follow.
+ * @return The iterator following \c i.
+ */
DMNSN_INLINE dmnsn_list_iterator *
dmnsn_list_next(const dmnsn_list_iterator *i)
{
@@ -109,13 +163,22 @@ dmnsn_list_next(const dmnsn_list_iterator *i)
return i->next;
}
+/**
+ * Get the size of the list.
+ * @param[in] list The list in question.
+ * @return The number of elements in the list.
+ */
DMNSN_INLINE size_t
dmnsn_list_size(const dmnsn_list *list)
{
return list->length;
}
-/* Get the i'th object */
+/**
+ * Get the i'th object.
+ * @param[in] i The iterator to dereference.
+ * @param[out] obj The location to store the object.
+ */
DMNSN_INLINE void
dmnsn_list_get(const dmnsn_list_iterator *i, void *obj)
{
@@ -123,7 +186,11 @@ dmnsn_list_get(const dmnsn_list_iterator *i, void *obj)
memcpy(obj, i->ptr, i->obj_size);
}
-/* Get a pointer to the i'th object */
+/**
+ * Get a pointer to the i'th object.
+ * @param[in] i The iterator to dereference.
+ * @return A pointer to the object stored at \c i.
+ */
DMNSN_INLINE void *
dmnsn_list_at(const dmnsn_list_iterator *i)
{
@@ -131,7 +198,11 @@ dmnsn_list_at(const dmnsn_list_iterator *i)
return i->ptr;
}
-/* Set the i'th object, expanding the list if necessary */
+/**
+ * Set the i'th object.
+ * @param[in,out] i The iterator to dereference.
+ * @param[in] obj The object to store at \c i.
+ */
DMNSN_INLINE void
dmnsn_list_set(dmnsn_list_iterator *i, const void *obj)
{
@@ -139,7 +210,11 @@ dmnsn_list_set(dmnsn_list_iterator *i, const void *obj)
memcpy(i->ptr, obj, i->obj_size);
}
-/* Swap two iterators */
+/**
+ * Swap the objects in two iterators.
+ * @param[in,out] a The first iterator.
+ * @param[in,out] b The second iterator.
+ */
DMNSN_INLINE void
dmnsn_list_swap(dmnsn_list_iterator *a, dmnsn_list_iterator *b)
{
@@ -148,7 +223,13 @@ dmnsn_list_swap(dmnsn_list_iterator *a, dmnsn_list_iterator *b)
b->ptr = temp;
}
-/* Insert `j' before `i' */
+/**
+ * Insert a detached iterator into a list.
+ * @param[in,out] list The list to insert into.
+ * @param[in,out] i The detached iterator to insert.
+ * @param[in,out] j The iterator before which to insert, or NULL for the end
+ * of the list.
+ */
DMNSN_INLINE void
dmnsn_list_iterator_insert(dmnsn_list *list,
dmnsn_list_iterator *i, dmnsn_list_iterator *j)
@@ -170,7 +251,13 @@ dmnsn_list_iterator_insert(dmnsn_list *list,
++list->length;
}
-/* Insert an item before `i' (NULL means at the end) */
+/**
+ * Insert an object.
+ * @param[in,out] list The list to insert into.
+ * @param[in,out] i The iterator before which to insert, or NULL for the end
+ * of the list.
+ * @param[in] obj The location of the object to insert.
+ */
DMNSN_INLINE void
dmnsn_list_insert(dmnsn_list *list, dmnsn_list_iterator *i, const void *obj)
{
@@ -178,7 +265,11 @@ dmnsn_list_insert(dmnsn_list *list, dmnsn_list_iterator *i, const void *obj)
dmnsn_list_iterator_insert(list, i, j);
}
-/* Remove the given iterator */
+/**
+ * Detach an iterator from a list.
+ * @param[in,out] list The list to remove from.
+ * @param[in,out] i The iterator to detach.
+ */
DMNSN_INLINE void
dmnsn_list_iterator_remove(dmnsn_list *list, dmnsn_list_iterator *i)
{
@@ -197,7 +288,11 @@ dmnsn_list_iterator_remove(dmnsn_list *list, dmnsn_list_iterator *i)
--list->length;
}
-/* Remove the specified item */
+/**
+ * Remove the specified item from a list.
+ * @param[in,out] list The list to remove from.
+ * @param[in,out] i The iterator to delete.
+ */
DMNSN_INLINE void
dmnsn_list_remove(dmnsn_list *list, dmnsn_list_iterator *i)
{
@@ -205,14 +300,22 @@ dmnsn_list_remove(dmnsn_list *list, dmnsn_list_iterator *i)
dmnsn_delete_list_iterator(i);
}
-/* Push obj to the end of the list */
+/**
+ * Push an object to the end of the list.
+ * @param[in,out] list The list to append to.
+ * @param[in] obj The location of the object to push.
+ */
DMNSN_INLINE void
dmnsn_list_push(dmnsn_list *list, const void *obj)
{
dmnsn_list_insert(list, NULL, obj);
}
-/* Pop obj from the end of the list */
+/**
+ * Pop an object from the end of the list.
+ * @param[in,out] list The list to extract from.
+ * @param[out] obj The location to store the extracted object.
+ */
DMNSN_INLINE void
dmnsn_list_pop(dmnsn_list *list, void *obj)
{
@@ -221,11 +324,22 @@ dmnsn_list_pop(dmnsn_list *list, void *obj)
dmnsn_list_remove(list, list->last);
}
-/* Splits a list in half, and returns the second half */
+/**
+ * Split a list in half, and return the second half.
+ * @param[in,out] list The list to split.
+ * @return A the second half of the list.
+ */
dmnsn_list *dmnsn_list_split(dmnsn_list *list);
-/* Sort a list */
+
+/** List object comparator function type */
typedef bool dmnsn_list_comparator_fn(dmnsn_list_iterator *l,
dmnsn_list_iterator *r);
+
+/**
+ * Sort a list, with O(n*log(n)) comparisons.
+ * @param[in,out] list The list to sort.
+ * @param[in] comparator The comparator to use for comparisons.
+ */
void dmnsn_list_sort(dmnsn_list *list, dmnsn_list_comparator_fn *comparator);
#endif /* DIMENSION_LIST_H */
diff --git a/libdimension/dimension/malloc.h b/libdimension/dimension/malloc.h
index 3c9e84b..7a5295a 100644
--- a/libdimension/dimension/malloc.h
+++ b/libdimension/dimension/malloc.h
@@ -18,15 +18,41 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Seriously, how often does malloc fail? And how often can you do something
- * better than bail out when it does? dmnsn_malloc() is like malloc in every
- * way except it calls dmnsn_error() on failure.
+/**
+ * @file
+ * Dynamic memory. dmnsn_malloc() and friends behave like their
+ * non-dmnsn_-prefixed counterparts, but never return NULL. If allocation
+ * fails, they instead call dmnsn_error(DMNSN_SEVERITY_HIGH).
*/
#include <stddef.h> /* For size_t */
+/**
+ * Allocate some memory. Always use dmnsn_free() to free this memory, never
+ * free().
+ * @param[in] size The size of the memory block to allocate.
+ * @return The allocated memory area.
+ */
void *dmnsn_malloc(size_t size);
+
+/**
+ * Expand or shrink an allocation created by dmnsn_malloc().
+ * @param[in] ptr The block to resize.
+ * @param[in] size The new size.
+ * @return The resized memory area.
+ */
void *dmnsn_realloc(void *ptr, size_t size);
+
+/**
+ * Duplicate a string.
+ * @param[in] s The string to duplicate.
+ * @return A string with the same contents as \p s, suitable for release by
+ * dmnsn_free().
+ */
char *dmnsn_strdup(const char *s);
-void dmnsn_free(void *ptr);
+
+/**
+ * Free memory allocated by dmnsn_malloc() or dmnsn_strdup().
+ * @param[in] ptr The memory block to free, or NULL.
+ */
+void dmnsn_free(void *ptr);
diff --git a/libdimension/dimension/object.h b/libdimension/dimension/object.h
index 56cfacd..28682a2 100644
--- a/libdimension/dimension/object.h
+++ b/libdimension/dimension/object.h
@@ -18,7 +18,8 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
+/**
+ * @file
* Objects.
*/
@@ -27,70 +28,104 @@
#include <stdbool.h>
-/* A type to represent a ray-object intersection */
+/** A type to represent a ray-object intersection. */
typedef struct dmnsn_intersection {
- /* The ray and point which intersected */
- dmnsn_line ray;
- double t;
+ dmnsn_line ray; /**< The ray that intersected. */
+ double t; /**< The line index that intersected */
- /* The surface normal at the intersection point */
- dmnsn_vector normal;
+ dmnsn_vector normal; /**< The surface normal at the intersection point */
- /* The object properties at the intersection point */
- const dmnsn_texture *texture;
- const dmnsn_interior *interior;
+ const dmnsn_texture *texture; /**< The texture at the intersection point */
+ const dmnsn_interior *interior; /**< The interior at the intersection point */
} dmnsn_intersection;
/* Forward-declare dmnsn_object */
typedef struct dmnsn_object dmnsn_object;
-/* Object callback types */
-
+/**
+ * Object initialization callback.
+ * @param[in,out] object The object to initialize.
+ */
typedef void dmnsn_object_init_fn(dmnsn_object *object);
+
+/**
+ * Ray-object intersection callback.
+ * @param[in] object The object to test.
+ * @param[in] line The line to test.
+ * @param[out] intersection Where to store the intersection details of the
+ * closest (if any) intersection.
+ * @return Whether \p line intersected \p object.
+ */
typedef bool dmnsn_object_intersection_fn(const dmnsn_object *object,
dmnsn_line line,
dmnsn_intersection *intersection);
+
+/**
+ * Object inside callback.
+ * @param[in] object The object to test.
+ * @param[in] point The point to test.
+ * @return Whether \p point is inside \p object.
+ */
typedef bool dmnsn_object_inside_fn(const dmnsn_object *object,
dmnsn_vector point);
-/* dmnsn_object definition */
+/** An object. */
struct dmnsn_object {
- /* Surface properties */
- dmnsn_texture *texture;
-
- /* Interior properties */
- dmnsn_interior *interior;
+ dmnsn_texture *texture; /**< Surface properties */
+ dmnsn_interior *interior; /**< Interior properties */
- /* Transformation matrix */
- dmnsn_matrix trans, trans_inv;
+ dmnsn_matrix trans; /**< Transformation matrix */
+ dmnsn_matrix trans_inv; /**< Inverse of the transformation matrix */
- /* Bounding box */
- dmnsn_bounding_box bounding_box;
+ dmnsn_bounding_box bounding_box; /**< Object bounding box */
- /* Child objects */
+ /** Child objects. This array lists objects that can be split into
+ sub-objects for bounding purposes (for unions and meshes, for example). */
dmnsn_array *children;
- /* Callback functions */
- dmnsn_object_init_fn *init_fn;
- dmnsn_object_intersection_fn *intersection_fn;
- dmnsn_object_inside_fn *inside_fn;
- dmnsn_free_fn *free_fn;
+ dmnsn_object_init_fn *init_fn; /**< Initialization callback. */
+ dmnsn_object_intersection_fn *intersection_fn; /**< Intersection callback. */
+ dmnsn_object_inside_fn *inside_fn; /**< Inside callback. */
+ dmnsn_free_fn *free_fn; /**< Destruction callback. */
- /* Generic pointer for object info */
+ /** Generic pointer for object info */
void *ptr;
};
-/* Allocate a dummy object */
+/**
+ * Allocate a dummy object.
+ * @return The allocated object.
+ */
dmnsn_object *dmnsn_new_object(void);
-/* Free an object */
+
+/**
+ * Free an object
+ * @param[in,out] object The object to destroy.
+ */
void dmnsn_delete_object(dmnsn_object *object);
-/* Initialize an object and potentially its children */
+/**
+ * Initialize an object and potentially its children.
+ * @param[in,out] object The object to initialize.
+ */
void dmnsn_object_init(dmnsn_object *object);
-/* Helpers for invoking object callbacks with correct transformations */
+/**
+ * Appropriately transform a ray, then test for an intersection.
+ * @param[in] object The object to test.
+ * @param[in] line The ray to test.
+ * @param[out] intersection Where to store the intersection details.
+ * @return Whether there was an intersection.
+ */
bool dmnsn_object_intersection(const dmnsn_object *object, dmnsn_line line,
dmnsn_intersection *intersection);
+
+/**
+ * Appropriately transform a point, then test for containment.
+ * @param[in] object The object to test.
+ * @param[in] point The point to test.
+ * @return Whether \p point was inside \p object.
+ */
bool dmnsn_object_inside(const dmnsn_object *object, dmnsn_vector point);
#endif /* DIMENSION_OBJECT_H */
diff --git a/libdimension/dimension/objects.h b/libdimension/dimension/objects.h
index 41706a0..a98541b 100644
--- a/libdimension/dimension/objects.h
+++ b/libdimension/dimension/objects.h
@@ -18,8 +18,9 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Custom objects.
+/**
+ * @file
+ * Pre-defined objects.
*/
#ifndef DIMENSION_OBJECTS_H
@@ -27,19 +28,40 @@
#include <stdbool.h>
-/* A plane through the origin, with the given normal */
+/**
+ * A plane.
+ * @param[in] normal The normal vector of the plane.
+ * @return A plane through the origin, with the given normal.
+ */
dmnsn_object *dmnsn_new_plane(dmnsn_vector normal);
-/* A sphere object, of radius 1, centered at the origin. */
+/**
+ * A sphere.
+ * @return A sphere of radius 1, centered at the origin.
+ */
dmnsn_object *dmnsn_new_sphere(void);
-/* A cube, axis-aligned, from (-1, -1, -1) to (1, 1, 1) */
+/**
+ * A cube.
+ * @return An axis-aligned cube, from (-1, -1, -1) to (1, 1, 1).
+ */
dmnsn_object *dmnsn_new_cube(void);
-/* A cylinder/cone, from r = r1 at y = -1, to r = r2 at y = 1 */
-dmnsn_object *dmnsn_new_cylinder(double r1, double r2, bool open);
+/**
+ * A cylinder/cone.
+ * @param[in] r1 The bottom radius.
+ * @param[in] r2 The top radius.
+ * @param[in] open Whether to render caps.
+ * @return A cone slice, from r = \p r1 at y = -1, to r = \p r2 at y = 1
+ */
+dmnsn_object *dmnsn_new_cone(double r1, double r2, bool open);
-/* A torus, centered at the origin and lying in the x-z plane */
+/**
+ * A torus.
+ * @param[in] major The major radius.
+ * @param[in] minor The minor radius.
+ * @return A torus, centered at the origin and lying in the x-z plane.
+ */
dmnsn_object *dmnsn_new_torus(double major, double minor);
#endif /* DIMENSION_OBJECTS_H */
diff --git a/libdimension/dimension/pattern.h b/libdimension/dimension/pattern.h
index 6301372..9636155 100644
--- a/libdimension/dimension/pattern.h
+++ b/libdimension/dimension/pattern.h
@@ -18,8 +18,10 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Patterns
+/**
+ * @file
+ * Patterns. Patterns are functions which map vectors to scalars, which are
+ * used for pigments and normals.
*/
#ifndef DIMENSION_PATTERN_H
@@ -28,28 +30,52 @@
/* Forward-declare dmnsn_pattern */
typedef struct dmnsn_pattern dmnsn_pattern;
-/* Pattern callback */
+/**
+ * Pattern callback.
+ * @param[in] pattern The pattern itself.
+ * @param[in] v The point at which to evaluate the pattern.
+ * @return The value of the pattern at \p v.
+ */
typedef double dmnsn_pattern_fn(const dmnsn_pattern *pattern, dmnsn_vector v);
-/* Generic pattern */
+/** A pattern. */
struct dmnsn_pattern {
- /* Callbacks */
- dmnsn_pattern_fn *pattern_fn;
- dmnsn_free_fn *free_fn;
+ dmnsn_pattern_fn *pattern_fn; /**< The pattern callback. */
+ dmnsn_free_fn *free_fn; /**< The destructor callback. */
- /* Transformation matrix */
- dmnsn_matrix trans, trans_inv;
+ dmnsn_matrix trans; /**< The transformation matrix of the pattern */
+ dmnsn_matrix trans_inv; /**< The inverse of the transformation matrix */
- /* Generic pointer */
- void *ptr;
+ void *ptr; /**< Generic pointer */
};
+/**
+ * Allocate an dummy pattern.
+ * @return A pattern with no callbacks set.
+ */
dmnsn_pattern *dmnsn_new_pattern(void);
+
+/**
+ * Delete a pattern.
+ * @param[in,out] pattern The pattern to destroy.
+ */
void dmnsn_delete_pattern(dmnsn_pattern *pattern);
+/**
+ * Initialize a pattern. This precomputes some values that are used during
+ * ray-tracing; the pattern will not work until it has been initialized, but
+ * should not be modified after it has been initialized. Patterns are generally
+ * initialized for you.
+ * @param[in,out] pattern The pattern to initialize.
+ */
void dmnsn_pattern_init(dmnsn_pattern *pattern);
-/* Invoke the pattern callback with the right transformation */
+/**
+ * Invoke the pattern callback with the right transformation.
+ * @param[in] pattern The pattern to evaluate.
+ * @param[in] v The point to get the pattern value for.
+ * @return The value of the pattern at \p v.
+ */
double dmnsn_pattern_value(const dmnsn_pattern *pattern, dmnsn_vector v);
#endif /* DIMENSION_PATTERN_H */
diff --git a/libdimension/dimension/patterns.h b/libdimension/dimension/patterns.h
index cd4aa35..5dd44bf 100644
--- a/libdimension/dimension/patterns.h
+++ b/libdimension/dimension/patterns.h
@@ -18,14 +18,27 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Custom patterns
+/**
+ * @file
+ * Pre-defined patterns.
*/
#ifndef DIMENSION_PATTERNS_H
#define DIMENSION_PATTERNS_H
-dmnsn_pattern *dmnsn_new_checker_pattern();
+/**
+ * A checker pattern. The pattern is composed of tesselating unit cubes
+ * alternating between 0 and 1.
+ * @return A checker pattern.
+ */
+dmnsn_pattern *dmnsn_new_checker_pattern(void);
+
+/**
+ * A gradient. The value starts at 0 at the origin, and goes linearly to 1 in
+ * the direction of \p orientation, then repeats after a distance of 1.
+ * @param[in] orientation The direction of the gradient.
+ * @return A gradient pattern.
+ */
dmnsn_pattern *dmnsn_new_gradient_pattern(dmnsn_vector orientation);
#endif /* DIMENSION_PATTERNS_H */
diff --git a/libdimension/dimension/pigments.h b/libdimension/dimension/pigments.h
index 31c0598..68a9c66 100644
--- a/libdimension/dimension/pigments.h
+++ b/libdimension/dimension/pigments.h
@@ -18,28 +18,67 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Custom pigments.
+/**
+ * @file
+ * Pre-defined pigments.
*/
#ifndef DIMENSION_PIGMENTS_H
#define DIMENSION_PIGMENTS_H
-/* A solid color */
+/**
+ * A solid color.
+ * @param[in] color The color of the pigment.
+ * @return A pigment with the color \p color everywhere.
+ */
dmnsn_pigment *dmnsn_new_solid_pigment(dmnsn_color color);
-/* An image map */
+
+/**
+ * An image map. The image (regardless of its real dimensions) is projected
+ * on the x-y plane in tesselating unit squares.
+ * @param[in] canvas The canvas holding the image.
+ * @return An image-mapped pigment.
+ */
dmnsn_pigment *dmnsn_new_canvas_pigment(dmnsn_canvas *canvas);
-/* Color maps */
+/** Color map. */
typedef dmnsn_array dmnsn_color_map;
-dmnsn_color_map *dmnsn_new_color_map();
+/**
+ * Create an empty color map.
+ * @return A color map with no entries.
+ */
+dmnsn_color_map *dmnsn_new_color_map(void);
+
+/**
+ * Delete a color map.
+ * @param[in,out] map The color map to delete.
+ */
void dmnsn_delete_color_map(dmnsn_color_map *map);
+/**
+ * Add an entry (a scalar-color pair) to a color map.
+ * @param[in,out] map The color map to add to.
+ * @param[in] n The index of the entry.
+ * @param[in] c The value of the entry.
+ */
void dmnsn_add_color_map_entry(dmnsn_color_map *map, double n, dmnsn_color c);
+
+/**
+ * Evaluate a color map.
+ * @param[in] map The map to evaluate.
+ * @param[in] n The index to evaluate.
+ * @return The value of the gradient between the the two indicies closest to
+ * \p n.
+ */
dmnsn_color dmnsn_color_map_value(const dmnsn_color_map *map, double n);
-/* Color-mapped pigments */
+/**
+ * A color-mapped pigment.
+ * @param[in,out] pattern The pattern of the pigment.
+ * @param[in,out] map The color map to apply to the pattern.
+ * @return A pigment mapping the pattern to color values.
+ */
dmnsn_pigment *dmnsn_new_color_map_pigment(dmnsn_pattern *pattern,
dmnsn_color_map *map);
diff --git a/libdimension/dimension/png.h b/libdimension/dimension/png.h
index cf21116..296331a 100644
--- a/libdimension/dimension/png.h
+++ b/libdimension/dimension/png.h
@@ -18,8 +18,9 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Support for exporting/importing canvases to/from PNG files
+/**
+ * @file
+ * PNG import/export of canvases
*/
#ifndef DIMENSION_PNG_H
@@ -27,17 +28,46 @@
#include <stdio.h>
-/* Optimize canvas for PNG exporting */
+/**
+ * Optimize a canvas for PNG exporting
+ * @param[in,out] canvas The canvas to optimize.
+ * @return Whether the canvas was successfully optimized.
+ */
int dmnsn_png_optimize_canvas(dmnsn_canvas *canvas);
-/* Write canvas to file in PNG format. Returns 0 on success, nonzero on
- failure */
+/**
+ * Write a canvas to a file in PNG format.
+ * @param[in] canvas The canvas to write.
+ * @param[in,out] file The file to write to.
+ * @return 0 on success, non-zero on failure.
+ */
int dmnsn_png_write_canvas(const dmnsn_canvas *canvas, FILE *file);
+
+/**
+ * Write a canvas to a PNG file in the background.
+ * @param[in] canvas The canvas to write.
+ * @param[in,out] file The file to write to.
+ * @return A \ref dmnsn_progress object, or NULL on failure.
+ */
dmnsn_progress *dmnsn_png_write_canvas_async(const dmnsn_canvas *canvas,
FILE *file);
-/* Read a canvas from a PNG file. Returns NULL on failure. */
+/**
+ * Read a canvas from a PNG file.
+ * @param[in,out] file The PNG file to read.
+ * @return The new canvas, or NULL on failure.
+ */
dmnsn_canvas *dmnsn_png_read_canvas(FILE *file);
+
+/**
+ * Read a canvas from a PNG file in the background.
+ * @param[out] canvas The address of a non-allocated canvas object. The
+ * canvas object will be allocated and filled with the
+ * contents of \p file. Do not read from this object
+ * until the background task has finished.
+ * @param[in,out] file The PNG file to read.
+ * @return A \ref dmnsn_progress object, or NULL on failure.
+ */
dmnsn_progress *dmnsn_png_read_canvas_async(dmnsn_canvas **canvas, FILE *file);
#endif /* DIMENSION_PNG_H */
diff --git a/libdimension/dimension/polynomial.h b/libdimension/dimension/polynomial.h
index 56e3ac0..b0a9357 100644
--- a/libdimension/dimension/polynomial.h
+++ b/libdimension/dimension/polynomial.h
@@ -18,7 +18,8 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
+/**
+ * @file
* Utility functions for working with and numerically solving polynomials.
* Polynomials are represented as simple arrays where the ith element is the
* coefficient on x^i. In general, we are only interested in positive roots.
@@ -30,6 +31,14 @@
#include <stddef.h>
#include <stdio.h>
+/**
+ * Evaluate a polynomial at \p x.
+ * @param[in] poly The coefficients of the polynomial to evaluate, in order
+ * from lowest degree to highest degree. The array should
+ * have dimension <tt>degree + 1</tt>.
+ * @param[in] degree The degree of the polynomial.
+ * @param[in] x The value of the variable at which to evaluate.
+ */
DMNSN_INLINE double
dmnsn_evaluate_polynomial(const double poly[], size_t degree, double x)
{
@@ -41,6 +50,12 @@ dmnsn_evaluate_polynomial(const double poly[], size_t degree, double x)
return ret;
}
+/**
+ * Evaluate the derivative of a polynomial at \p x.
+ * @param[in] poly The coefficients of the polynomial to evaluate.
+ * @param[in] degree The degree of the polynomial.
+ * @param[in] x The value of the variable at which to evaluate.
+ */
DMNSN_INLINE double
dmnsn_evaluate_polynomial_derivative(const double poly[], size_t degree,
double x)
@@ -53,11 +68,23 @@ dmnsn_evaluate_polynomial_derivative(const double poly[], size_t degree,
return ret;
}
-/* Stores the positive roots of poly[] in x[], and returns the number of such
- roots that were stored */
+/**
+ * Find the positive roots of a polynomial.
+ * @param[in] poly The coefficients of the polynomial to solve.
+ * @param[in] degree The degree of the polynomial.
+ * @param[out] x An array in which to store the roots. It should have
+ * dimension \p degree.
+ * @return The number of positive roots stored in \c x[].
+ */
size_t dmnsn_solve_polynomial(const double poly[], size_t degree, double x[]);
-/* Helper function to print a polynomial */
+/**
+ * Output a polynomial. The polynomial is printed as a function of x suitable
+ * for input into a CAS, and without a trailing newline.
+ * @param[in,out] file The file to write to.
+ * @param[in] poly The coefficients of the polynomial to print.
+ * @param[in] degree The degree of the polynomial.
+ */
void dmnsn_print_polynomial(FILE *file, const double poly[], size_t degree);
#endif /* DIMENSION_POLYNOMIAL_H */
diff --git a/libdimension/dimension/progress.h b/libdimension/dimension/progress.h
index 043f014..89d0d25 100644
--- a/libdimension/dimension/progress.h
+++ b/libdimension/dimension/progress.h
@@ -18,7 +18,8 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
+/**
+ * @file
* An interface for asynchronous tasks. *_async() versions of functions
* return a dmnsn_progress* object which can indicate the progress of the
* background task, and wait for task completion. The task's return value
@@ -28,15 +29,30 @@
#ifndef DIMENSION_PROGRESS_H
#define DIMENSION_PROGRESS_H
+/** A progress object */
typedef struct dmnsn_progress dmnsn_progress;
-/* Join the worker thread and return it's integer return value in addition to
- deleting `progress' */
+/**
+ * Join the worker thread and return it's integer return value in addition to
+ * deleting \p progress.
+ * @param[in,out] progress The background task to finish.
+ * @return The return value of the background task.
+ */
int dmnsn_finish_progress(dmnsn_progress *progress);
-/* Get the progress of the background task, out of 1.0 */
+/**
+ * Get the progress of the background task.
+ * @param[in] progress The background task to examine.
+ * @return The progress of the background task, out of 1.0.
+ */
double dmnsn_get_progress(const dmnsn_progress *progress);
-/* Wait for the progress to be >= prog, in a better way than spinlocking */
+
+/**
+ * Wait for a certain amount of progress. Always use this rather than
+ * spinlocking.
+ * @param[in] progress The background task to monitor.
+ * @param[in] prog The progress value to wait for.
+ */
void dmnsn_wait_progress(const dmnsn_progress *progress, double prog);
#endif /* DIMENSION_PROGRESS_H */
diff --git a/libdimension/dimension/raytrace.h b/libdimension/dimension/raytrace.h
index f145d5f..2fee879 100644
--- a/libdimension/dimension/raytrace.h
+++ b/libdimension/dimension/raytrace.h
@@ -18,15 +18,25 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * Render a scene by raytracing
+/**
+ * @file
+ * Ray-trace a scene.
*/
#ifndef DIMENSION_RAYTRACE_H
#define DIMENSION_RAYTRACE_H
-/* Render a scene by raytracing */
+/**
+ * Render a scene by raytracing.
+ * @param[in,out] scene The scene to render.
+ */
void dmnsn_raytrace_scene(dmnsn_scene *scene);
+
+/**
+ * Render a scene in the background.
+ * @param[in,out] scene The scene to render.
+ * @return A \p dmnsn_progress object.
+ */
dmnsn_progress *dmnsn_raytrace_scene_async(dmnsn_scene *scene);
#endif /* DIMENSION_RAYTRACE_H */
diff --git a/libdimension/dimension/scene.h b/libdimension/dimension/scene.h
index 7e52859..36fe74e 100644
--- a/libdimension/dimension/scene.h
+++ b/libdimension/dimension/scene.h
@@ -18,60 +18,70 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * A scene.
+/**
+ * @file
+ * Entire scenes.
*/
#ifndef DIMENSION_SCENE_H
#define DIMENSION_SCENE_H
-#include <stdbool.h>
-
+/** Render quality flags. */
enum {
- DMNSN_RENDER_NONE = 0,
- DMNSN_RENDER_PIGMENT = 1 << 0,
- DMNSN_RENDER_LIGHTS = 1 << 1,
- DMNSN_RENDER_FINISH = 1 << 2,
- DMNSN_RENDER_TRANSLUCENCY = 1 << 3,
- DMNSN_RENDER_REFLECTION = 1 << 4,
- DMNSN_RENDER_FULL = ~DMNSN_RENDER_NONE
+ DMNSN_RENDER_NONE = 0, /**< Render nothing. */
+ DMNSN_RENDER_PIGMENT = 1 << 0, /**< Render pigments. */
+ DMNSN_RENDER_LIGHTS = 1 << 1, /**< Render lights and shadows. */
+ DMNSN_RENDER_FINISH = 1 << 2, /**< Render object finishes. */
+ DMNSN_RENDER_TRANSLUCENCY = 1 << 3, /**< Render translucency/refraction. */
+ DMNSN_RENDER_REFLECTION = 1 << 4, /**< Render specular reflection. */
+ DMNSN_RENDER_FULL = ~DMNSN_RENDER_NONE /**< Render everything. */
};
+/** Render quality. */
typedef unsigned int dmnsn_quality;
-typedef struct {
+/** An entire scene. */
+typedef struct dmnsn_scene {
/* World attributes */
- dmnsn_color background;
- dmnsn_texture *default_texture;
+ dmnsn_color background; /**< Background color. */
+ dmnsn_texture *default_texture; /**< Default object texture. */
- /* Camera */
+ /** Camera. */
dmnsn_camera *camera;
- /* Canvas */
+ /** Canvas. */
dmnsn_canvas *canvas;
- /* Objects */
+ /** Objects. */
dmnsn_array *objects;
- /* Lights */
+ /** Lights. */
dmnsn_array *lights;
- /* Rendering quality */
+ /** Render quality. */
dmnsn_quality quality;
- /* Recursion limit */
+ /** Recursion limit. */
unsigned int reclimit;
- /* Number of parallel threads */
+ /** Number of parallel threads. */
unsigned int nthreads;
- /* Timers */
+ /** Timers */
dmnsn_timer *bounding_timer;
dmnsn_timer *render_timer;
} dmnsn_scene;
-/* Create a scene */
+/**
+ * Create a scene.
+ * @return A new empty scene.
+ */
dmnsn_scene *dmnsn_new_scene(void);
+
+/**
+ * Delete a scene.
+ * @param[in,out] scene The scene to delete.
+ */
void dmnsn_delete_scene(dmnsn_scene *scene);
#endif /* DIMENSION_SCENE_H */
diff --git a/libdimension/dimension/texture.h b/libdimension/dimension/texture.h
index 5586e24..f582351 100644
--- a/libdimension/dimension/texture.h
+++ b/libdimension/dimension/texture.h
@@ -18,7 +18,8 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
+/**
+ * @file
* Object textures.
*/
@@ -32,31 +33,55 @@
/* Forward-declare dmnsn_pigment */
typedef struct dmnsn_pigment dmnsn_pigment;
-/* Pigment callbacks */
+/**
+ * Pigment callback.
+ * @param[in] pigment The pigment itself.
+ * @param[in] v The point to color.
+ * @return The color of the pigment at \p v.
+ */
typedef dmnsn_color dmnsn_pigment_fn(const dmnsn_pigment *pigment,
dmnsn_vector v);
+
+/**
+ * Pigment initializer callback.
+ * @param[in,out] pigment The pigment to initialize.
+ */
typedef void dmnsn_pigment_init_fn(dmnsn_pigment *pigment);
-/* dmnsn_pigment definition */
+/** A pigment */
struct dmnsn_pigment {
- /* Callbacks */
- dmnsn_pigment_fn *pigment_fn;
- dmnsn_pigment_init_fn *init_fn;
- dmnsn_free_fn *free_fn;
+ dmnsn_pigment_fn *pigment_fn; /**< The pigment callback. */
+ dmnsn_pigment_init_fn *init_fn; /**< The initializer callback. */
+ dmnsn_free_fn *free_fn; /**< The destructor callback. */
- /* Transformation matrix */
- dmnsn_matrix trans, trans_inv;
+ dmnsn_matrix trans; /**< Transformation matrix. */
+ dmnsn_matrix trans_inv; /**< The inverse of the transformation matrix. */
- /* Quick color */
+ /** Quick color -- used for low-quality renders. */
dmnsn_color quick_color;
- /* Generic pointer */
+ /** Generic pointer */
void *ptr;
};
+/**
+ * Allocate a new dummy pigment.
+ * @return The allocated pigment.
+ */
dmnsn_pigment *dmnsn_new_pigment(void);
+
+/**
+ * Delete a pigment.
+ * @param[in,out] pigment The pigment to delete.
+ */
void dmnsn_delete_pigment(dmnsn_pigment *pigment);
+/**
+ * Initialize a pigment. Pigments should not be used before being initialized,
+ * but should not be modified after being initialized. Pigments are generally
+ * initialized for you.
+ * @param[in,out] pigment The pigment to initialize.
+ */
void dmnsn_pigment_init(dmnsn_pigment *pigment);
/*
@@ -66,56 +91,111 @@ void dmnsn_pigment_init(dmnsn_pigment *pigment);
/* Forward-declare dmnsn_finish */
typedef struct dmnsn_finish dmnsn_finish;
-/* Finish callbacks */
+/**
+ * Diffuse reflection callback.
+ * @param[in] finish The finish itself.
+ * @param[in] light The color of the light illuminating the object.
+ * @param[in] color The pigment of the object.
+ * @param[in] ray The direction of the light source.
+ * @param[in] normal The normal vector of the surface.
+ * @return The diffuse reflection component of the object's color.
+ */
typedef dmnsn_color dmnsn_diffuse_fn(const dmnsn_finish *finish,
dmnsn_color light, dmnsn_color color,
dmnsn_vector ray, dmnsn_vector normal);
+/**
+ * Specular highlight callback.
+ * @param[in] finish The finish itself.
+ * @param[in] light The color of the light illuminating the object.
+ * @param[in] color The pigment of the object.
+ * @param[in] ray The direction of the light source.
+ * @param[in] normal The normal vector of the surface.
+ * @param[in] viewer The direction of the viewer.
+ * @return The specular reflection component of the object's color.
+ */
typedef dmnsn_color dmnsn_specular_fn(const dmnsn_finish *finish,
dmnsn_color light, dmnsn_color color,
dmnsn_vector ray, dmnsn_vector normal,
dmnsn_vector viewer);
+/**
+ * Ambient light callback.
+ * @param[in] finish The finish itself.
+ * @param[in] pigment The pigment of the object.
+ * @return The ambient contribution to the object's color.
+ */
typedef dmnsn_color dmnsn_ambient_fn(const dmnsn_finish *finish,
dmnsn_color pigment);
+/**
+ * Reflected light callback.
+ * @param[in] finish The finish itself.
+ * @param[in] reflect The color of the reflected ray.
+ * @param[in] color The pigment of the object.
+ * @param[in] ray The direction of the reflected ray.
+ * @param[in] normal The normal vector of the surface.
+ * @return The contribution of the reflected ray to the object's color.
+ */
typedef dmnsn_color dmnsn_reflection_fn(const dmnsn_finish *finish,
dmnsn_color reflect, dmnsn_color color,
dmnsn_vector ray, dmnsn_vector normal);
-/* dmnsn_finish definition */
+/** A finish. */
struct dmnsn_finish {
- /* Callbacks */
- dmnsn_diffuse_fn *diffuse_fn;
- dmnsn_specular_fn *specular_fn;
- dmnsn_ambient_fn *ambient_fn;
- dmnsn_reflection_fn *reflection_fn;
- dmnsn_free_fn *free_fn;
-
- /* Generic pointer */
+ dmnsn_diffuse_fn *diffuse_fn; /**< The diffuse callback. */
+ dmnsn_specular_fn *specular_fn; /**< The specular callback. */
+ dmnsn_ambient_fn *ambient_fn; /**< The ambient callback. */
+ dmnsn_reflection_fn *reflection_fn; /**< The reflection callback. */
+ dmnsn_free_fn *free_fn; /**< The destruction callback. */
+
+ /** Generic pointer */
void *ptr;
};
+/**
+ * Allocate a new dummy finish.
+ * @return The allocated finish.
+ */
dmnsn_finish *dmnsn_new_finish(void);
+
+/**
+ * Delete a finish.
+ * @param[in,out] finish The finish to delete.
+ */
void dmnsn_delete_finish(dmnsn_finish *finish);
/*
- * A complete texture
+ * Textures
*/
+/** A complete texture. */
typedef struct {
- /* Texture components */
- dmnsn_pigment *pigment;
- dmnsn_finish *finish;
+ dmnsn_pigment *pigment; /**< Pigment. */
+ dmnsn_finish *finish; /**< Finish. */
- /* Transformation matrix */
- dmnsn_matrix trans, trans_inv;
+ dmnsn_matrix trans; /**< Transformation matrix. */
+ dmnsn_matrix trans_inv; /**< The inverse of the transformation matrix. */
- /* Reference count */
- unsigned int *refcount;
- bool should_init;
+ unsigned int *refcount; /**< @internal Reference count. */
+ bool should_init; /**< @internal Whether to init the texture. */
} dmnsn_texture;
+/**
+ * Create a blank texture.
+ * @return The new texture.
+ */
dmnsn_texture *dmnsn_new_texture(void);
+
+/**
+ * Delete a texture.
+ * @param[in,out] texture The texture to delete.
+ */
void dmnsn_delete_texture(dmnsn_texture *texture);
+/**
+ * Initialize a texture. Textures should not be used before being initialized,
+ * but should not be modified after being initialized. Textures are generally
+ * initialized for you.
+ * @param[in,out] texture The texture to initialize.
+ */
void dmnsn_texture_init(dmnsn_texture *texture);
#endif /* DIMENSION_TEXTURE_H */
diff --git a/libdimension/dimension/timer.h b/libdimension/dimension/timer.h
index 0f3c61f..9e935c2 100644
--- a/libdimension/dimension/timer.h
+++ b/libdimension/dimension/timer.h
@@ -18,17 +18,43 @@
* <http://www.gnu.org/licenses/>. *
*************************************************************************/
-/*
- * A platform-agnostic timer abstraction
+/**
+ * @file
+ * A platform-agnostic timer abstraction.
*/
+/** A platform-agnotic timer. */
typedef struct dmnsn_timer {
- double real, user, system;
+ double real; /**< Wall-clock time. */
+ double user; /**< Time spent executing. */
+ double system; /**< Time spent waiting for the system. */
} dmnsn_timer;
+/** A standard format string for timers. */
#define DMNSN_TIMER_FORMAT "%.2fs (user: %.2fs; system: %.2fs)"
+/**
+ * The appropriate arguments to printf() a timer. For example:
+ * @code
+ * printf(DMNSN_TIMER_FORMAT "\n", DMNSN_TIMER_PRINTF(timer));
+ * @endcode
+ * will print something like "1.00s (user: 0.99s; system: 0.01s)".
+ */
#define DMNSN_TIMER_PRINTF(t) (t)->real, (t)->user, (t)->system
+/**
+ * Create a new timer. Timing starts right before this function returns.
+ * @return A new timer object.
+ */
dmnsn_timer *dmnsn_new_timer(void);
+
+/**
+ * Finish timing. The members of the timer struct will now contain timing data.
+ * @param[in,out] timer The timer to stop.
+ */
void dmnsn_complete_timer(dmnsn_timer *timer);
+
+/**
+ * Delete a timer.
+ * @param[in,out] timer The timer to delete.
+ */
void dmnsn_delete_timer(dmnsn_timer *timer);