rngrd

Describe a surface and its physical properties
git clone git://git.meso-star.com/rngrd.git
Log | Files | Refs | README | LICENSE

commit 496e9c717254aff60263404becb78ce4e1b8ca1c
parent 1279c611af4b8bfc8a0b75d097c8f39e7d23fc9e
Author: Vincent Forest <vincent.forest@meso-star.com>
Date:   Fri, 22 May 2026 14:21:15 +0200

Add the API function for finding the closest point

Like the ray-tracing function, it serves as an interface to the Star-3D
library used to partition the ground geometry.

Diffstat:
Mconfig.mk | 2+-
Msrc/rngrd.h | 23+++++++++++++++++++++++
Msrc/rngrd_mesh.c | 65++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-------
3 files changed, 82 insertions(+), 8 deletions(-)

diff --git a/config.mk b/config.mk @@ -1,4 +1,4 @@ -VERSION = 0.1.1 +VERSION = 0.2.0 PREFIX = /usr/local LIB_TYPE = SHARED diff --git a/src/rngrd.h b/src/rngrd.h @@ -97,6 +97,23 @@ struct rngrd_trace_ray_args { static const struct rngrd_trace_ray_args RNGRD_TRACE_RAY_ARGS_DEFAULT = RNGRD_TRACE_RAY_ARGS_DEFAULT__; +struct rngrd_closest_point_args { + double position[3]; + double radius; /* Search radius around the position */ + + s3d_hit_filter_function_T filter; /* NULL <=> Return closest triangle */ + void* filter_data; /* User data send to the filter function */ +}; +#define RNGRD_CLOSEST_POINT_ARGS_DEFAULT__ { \ + {0,0,0}, /* Position */ \ + DBL_MAX, /* Radius */ \ + \ + NULL, /* Filter function */ \ + NULL /* Filter data */ \ +} +static const struct rngrd_closest_point_args +RNGRD_CLOSEST_POINT_ARGS_DEFAULT = RNGRD_CLOSEST_POINT_ARGS_DEFAULT__; + struct rngrd_create_bsdf_args { struct s3d_primitive prim; /* Surface primitive to query */ double barycentric_coords[3]; /* Position into and relative to `prim' */ @@ -151,6 +168,12 @@ rngrd_trace_ray struct s3d_hit* hit); RNGRD_API res_T +rngrd_closest_point + (const struct rngrd* ground, + struct rngrd_closest_point_args* args, + struct s3d_hit* hit); + +RNGRD_API res_T rngrd_create_bsdf (struct rngrd* ground, const struct rngrd_create_bsdf_args* args, diff --git a/src/rngrd_mesh.c b/src/rngrd_mesh.c @@ -31,6 +31,14 @@ #include <rsys/float2.h> #include <rsys/float3.h> +struct filter_args { + struct s3d_hit hit; + + s3d_hit_filter_function_T func; /* NULL <=> Stop RT at 1st hit triangle */ + void* context; /* User data send to the filter function */ +}; +static const struct filter_args FILTER_ARGS_NULL = {S3D_HIT_NULL, NULL, NULL}; + /******************************************************************************* * Helper functions ******************************************************************************/ @@ -129,7 +137,7 @@ mesh_filter void* ray_data, void* filter_data) { - const struct rngrd_trace_ray_args* ray_args = ray_data; + const struct filter_args* filter = ray_data; (void)filter_data; /* Internally, Star-3D relies on Embree which, due to numerical imprecision, @@ -138,18 +146,18 @@ mesh_filter if(hit->distance <= ray_range[0] || hit->distance >= ray_range[1]) return 1; - if(!ray_args) /* Nothing more to do */ + if(!filter) /* Nothing more to do */ return 0; /* Discard this intersection */ - if(self_hit(hit, ray_org, ray_dir, ray_range, &ray_args->hit_from)) + if(self_hit(hit, ray_org, ray_dir, ray_range, &filter->hit)) return 1; - if(!ray_args->filter) /* No user-defined filter functions */ + if(!filter->func) /* No user-defined filter functions */ return 0; - return ray_args->filter /* Invoke user-defined filtering */ - (hit, ray_org, ray_dir, ray_range, ray_args->filter_data, filter_data); + return filter->func /* Invoke user-defined filtering */ + (hit, ray_org, ray_dir, ray_range, filter->context, filter_data); } static void @@ -269,6 +277,7 @@ rngrd_trace_ray struct rngrd_trace_ray_args* args, struct s3d_hit* hit) { + struct filter_args filter = FILTER_ARGS_NULL; float org[3]; float dir[3]; float range[2]; @@ -283,9 +292,13 @@ rngrd_trace_ray f3_set_d3(dir, args->ray_dir); f2_set_d2(range, args->ray_range); + filter.hit = args->hit_from; + filter.func = args->filter; + filter.context = args->filter_data; + *hit = S3D_HIT_NULL; - res = s3d_scene_view_trace_ray(ground->s3d_view, org, dir, range, args, hit); + res = s3d_scene_view_trace_ray(ground->s3d_view, org, dir, range, &filter, hit); if(res != RES_OK) { log_err(ground, "%s: error tracing ray " @@ -300,6 +313,44 @@ error: goto exit; } +res_T +rngrd_closest_point + (const struct rngrd* ground, + struct rngrd_closest_point_args* args, + struct s3d_hit* hit) +{ + struct filter_args filter = FILTER_ARGS_NULL; + float pos[3]; + float radius; + res_T res = RES_OK; + + if(!ground || !args || !hit) { + res = RES_BAD_ARG; + goto error; + } + + f3_set_d3(pos, args->position); + radius = (float)args->radius; + filter.func = args->filter; + filter.context = args->filter_data; + + *hit = S3D_HIT_NULL; + + res = s3d_scene_view_closest_point(ground->s3d_view, pos, radius, &filter, hit); + if(res != RES_OK) { + log_err(ground, + "%s: error finding the closest point " + "(position = %g, %g, %g; radius = %g)\n", + FUNC_NAME, SPLIT3(pos), radius); + goto error; + } + +exit: + return res; +error: + goto exit; +} + /******************************************************************************* * Local function ******************************************************************************/