commit ef81091ebbdf981c7623b61d14cc8f579a6ed2e1
parent 7a8aa9db22e7cc8a63f72ca10143302a9854a4fb
Author: Eduardo Fontana Lazzari <edufonlaz@gmail.com>
Date: Thu, 27 Nov 2025 20:45:21 +0100
Add new geometry-based functions to sphin API
sphin_config_get_total_power_surface, which computes the total power of
all surface sources in the configuration.
sphin_volume_compute_total_volume, which computes the volume (as
the extent, or more formally, the integral of 1 over the region) defined
by the sphin_volume.
Their counterparts (sphin_surface_compute_total_area and
sphin_config_get_total_power_volume) are yet to be implemented.
Diffstat:
5 files changed, 134 insertions(+), 18 deletions(-)
diff --git a/src/sphin.h b/src/sphin.h
@@ -295,6 +295,11 @@ sphin_config_get_surface
size_t isurface,
struct sphin_surface** surface);
+SPHIN_API res_T
+sphin_config_get_total_surface_power
+ (struct sphin_config* config,
+ double* total_power);
+
/*******************************************************************************
* API of the volume
******************************************************************************/
@@ -312,6 +317,11 @@ sphin_volume_get_name
char** name);
SPHIN_API res_T
+sphin_volume_compute_total_volume
+ (struct sphin_volume* volume,
+ double* total_volume);
+
+SPHIN_API res_T
sphin_volume_get_ka
(struct sphin_volume* volume,
double* ka);
@@ -459,7 +469,7 @@ sphin_surface_source_get_power
double* power);
/*******************************************************************************
- * API of the surface source
+ * API of the source surface
******************************************************************************/
SPHIN_API res_T
sphin_source_surface_ref_get
diff --git a/src/sphin_config.c b/src/sphin_config.c
@@ -415,3 +415,42 @@ sphin_config_get_surface
*surface = darray_sphin_surface_ptr_data_get(&config->surfaces)[isurface];
return res;
}
+
+res_T
+sphin_config_get_total_surface_power
+ (struct sphin_config* config,
+ double* total_power)
+{
+ double source_pow = 0;
+ struct sphin_surface* surface = NULL;
+ struct sphin_source_surface* source = NULL;
+ size_t surface_count = 0;
+ size_t i = 0;
+ res_T res = RES_OK;
+
+ if (NULL == config) { res = RES_BAD_ARG; goto error; }
+ if (NULL == total_power) { res = RES_BAD_ARG; goto error; }
+
+ res = sphin_config_get_surface_count(config, &surface_count);
+ if (RES_OK != res) { goto error; }
+
+ FOR_EACH(i, 0, surface_count) {
+ res = sphin_config_get_surface(config, i, &surface);
+ if (RES_OK != res) { goto error; }
+
+ res = sphin_surface_get_source(surface, &source);
+ if (RES_OK != res) { goto error; }
+
+ if (NULL != source) {
+ res = sphin_surface_source_get_power(surface, &source_pow);
+ if (RES_OK != res) { goto error; }
+
+ *total_power += source_pow;
+ }
+ }
+
+exit:
+ return res;
+error:
+ goto exit;
+}
diff --git a/src/sphin_geometry.c b/src/sphin_geometry.c
@@ -95,33 +95,29 @@ error:
******************************************************************************/
double
geometry_compute_area
- (struct sphin_geometry* geom)
+ (const struct sphin_geometry* geom)
{
const double* pos = NULL;
- const double* v0 = NULL;
- const double* v1 = NULL;
- const double* v2 = NULL;
const size_t* ids = NULL;
double area = 0.0;
- double E0[3], E1[3], N[3];
size_t id, itri, tri_count;
- ASSERT(geom);
+ ASSERT(NULL != geom);
- pos = darray_double_data_get(&geom->coords);
- ids = darray_size_t_data_get(&geom->indices);
+ pos = darray_double_cdata_get(&geom->coords);
+ ids = darray_size_t_cdata_get(&geom->indices);
tri_count = darray_size_t_size_get(&geom->indices)/3;
- if(0 == tri_count) return 0.f;
-
- for (itri = 0; itri < tri_count; itri++) {
- id = itri * 3; /*#ids per vertex*/
+ if(0 == tri_count) return 0.;
+ FOR_EACH(itri, 0, tri_count) {
/* Retrieve vertex coordinates */
- v0 = pos + ids[id+0]*3;
- v1 = pos + ids[id+1]*3;
- v2 = pos + ids[id+2]*3;
+ id = itri * 3; /*#ids per vertex*/
+ const double* v0 = pos + ids[id+0]*3;
+ const double* v1 = pos + ids[id+1]*3;
+ const double* v2 = pos + ids[id+2]*3;
+ double E0[3], E1[3], N[3];
- /* Construct vectors defining the triangle */
+ /* Construct vectors defining the triangle vertices */
d3_sub(E0, v1, v0);
d3_sub(E1, v2, v0);
@@ -131,6 +127,49 @@ geometry_compute_area
return area * 0.5f;
}
+double
+geometry_compute_volume
+ (const struct sphin_geometry* geom,
+ const enum sphin_side side)
+{
+ const double* pos = NULL;
+ const size_t* ids = NULL;
+ double volume = 0.0;
+ size_t id, itri, tri_count;
+
+ pos = darray_double_cdata_get(&geom->coords);
+ ids = darray_size_t_cdata_get(&geom->indices);
+ tri_count = darray_size_t_size_get(&geom->indices)/3;
+ if(0 == tri_count) return 0.;
+
+ FOR_EACH(itri, 0, tri_count) {
+ /* Retrieve vertex coordinates */
+ id = itri * 3; /*#ids per vertex*/
+ const double* v0 = pos + ids[id+0]*3;
+ const double* v1 = pos + ids[id+1]*3;
+ const double* v2 = pos + ids[id+2]*3;
+ double E0[3], E1[3], N[3];
+ double b, h;
+
+ /* Construct vectors defining the triangle vertices */
+ d3_sub(E0, v1, v0);
+ d3_sub(E1, v2, v0);
+
+ /* Compute triangle normal */
+ if (SPHIN_SIDE_BACK == side) {
+ d3_cross(N, E1, E0);
+ } else {
+ d3_cross(N, E0, E1);
+ }
+ b = d3_normalize(N, N); /* Base area */
+ h = -d3_dot(N, v0); /* Height from the base to the apex */
+
+ volume += (h*b);
+ }
+ return volume / 3.0;
+
+
+}
res_T
geometry_parse
diff --git a/src/sphin_geometry.h b/src/sphin_geometry.h
@@ -55,7 +55,12 @@ geometry_parse
extern LOCAL_SYM double
geometry_compute_area
- (struct sphin_geometry* geom);
+ (const struct sphin_geometry* geom);
+
+extern LOCAL_SYM double
+geometry_compute_volume
+ (const struct sphin_geometry* geom,
+ const enum sphin_side side);
/* Generate a dynamic array for storing sphin_geometry* elements and its API
* using the API provided by rsys/dynamic_array.h
diff --git a/src/sphin_volume.c b/src/sphin_volume.c
@@ -348,6 +348,29 @@ sphin_volume_get_name
}
res_T
+sphin_volume_compute_total_volume
+ (struct sphin_volume* volume,
+ double* total_volume)
+{
+ double total_vol = 0.;
+ size_t geometry_count = 0;
+ size_t i = 0;
+ struct sphin_geometry* geometry = NULL;
+
+ if (NULL == volume) { return RES_BAD_ARG; }
+ if (NULL == total_volume ) { return RES_BAD_ARG; }
+
+ geometry_count = darray_sphin_geometry_ptr_size_get(&volume->geometries);
+
+ FOR_EACH(i, 0, geometry_count) {
+ geometry = darray_sphin_geometry_ptr_data_get(&volume->geometries)[i];
+ total_vol += geometry_compute_volume(geometry, geometry->side);
+ }
+ *total_volume = total_vol;
+ return RES_OK;
+}
+
+res_T
sphin_volume_get_ka
(struct sphin_volume* volume,
double* ka)