star-3d

Surface structuring for efficient 3D geometric queries
git clone git://git.meso-star.fr/star-3d.git
Log | Files | Refs | README | LICENSE

commit 3289952fd733c2de94b1e5735ca15637b7a01254
parent dafd321577b8fd0b578582467c73357c90719f06
Author: Vincent Forest <vincent.forest@meso-star.com>
Date:   Wed,  4 Nov 2015 14:48:38 +0100

Add and test mesh data getters

Implement the s3d_mesh_get_<triangles|vertices>_count and
s3d_mesh_get_<vertex_attrib|triangle_indices> functions.

Diffstat:
Msrc/s3d.h | 23+++++++++++++++++++++++
Msrc/s3d_shape.c | 63+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Msrc/test_s3d_shape.c | 64+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-
3 files changed, 149 insertions(+), 1 deletion(-)

diff --git a/src/s3d.h b/src/s3d.h @@ -439,6 +439,29 @@ s3d_mesh_copy (const struct s3d_shape* src, struct s3d_shape* dst); +S3D_API res_T +s3d_mesh_get_vertices_count + (const struct s3d_shape* shape, + unsigned* nverts); + +S3D_API res_T +s3d_mesh_get_vertex_attrib + (const struct s3d_shape* shape, + const unsigned ivert, + const enum s3d_attrib_usage usage, + struct s3d_attrib* attrib); + +S3D_API res_T +s3d_mesh_get_triangles_count + (const struct s3d_shape* shape, + unsigned* ntris); + +S3D_API res_T +s3d_mesh_get_triangle_indices + (const struct s3d_shape* shape, + const unsigned itri, + unsigned ids[3]); + /******************************************************************************* * Instance API - An instance is a shape that encapsulates a scene and that * supports a local to world transformation. Since the scene geometry is stored diff --git a/src/s3d_shape.c b/src/s3d_shape.c @@ -31,6 +31,7 @@ * knowledge of the CeCILL license and that you accept its terms. */ #include "s3d.h" +#include "s3d_c.h" #include "s3d_device_c.h" #include "s3d_scene_c.h" #include "s3d_shape_c.h" @@ -275,3 +276,65 @@ s3d_mesh_copy return RES_OK; } +res_T +s3d_mesh_get_vertices_count(const struct s3d_shape* shape, unsigned* nverts) +{ + if(!shape || !nverts || shape->type != GEOM_MESH) return RES_BAD_ARG; + *nverts = (unsigned)mesh_get_nverts(shape->data.mesh); + return RES_OK; +} + +res_T +s3d_mesh_get_vertex_attrib + (const struct s3d_shape* shape, + const unsigned ivert, + const enum s3d_attrib_usage usage, + struct s3d_attrib* attrib) +{ + const float* data; + unsigned i, dim; + if(!shape + || shape->type != GEOM_MESH + || (unsigned)usage >= S3D_ATTRIBS_COUNT__ + || !shape->data.mesh->attribs[usage] + || !attrib + || ivert >= (unsigned)mesh_get_nverts(shape->data.mesh)) + return RES_BAD_ARG; + + attrib->usage = usage; + attrib->type = shape->data.mesh->attribs_type[usage]; + + dim = s3d_type_get_dimension(attrib->type); + data = mesh_get_attr(shape->data.mesh, usage) + ivert * dim; + FOR_EACH(i, 0, dim) attrib->value[i] = data[i]; + return RES_OK; +} + +res_T +s3d_mesh_get_triangles_count(const struct s3d_shape* shape, unsigned* ntris) +{ + if(!shape || !ntris || shape->type != GEOM_MESH) return RES_BAD_ARG; + *ntris = (unsigned)mesh_get_ntris(shape->data.mesh); + return RES_OK; +} + +res_T +s3d_mesh_get_triangle_indices + (const struct s3d_shape* shape, + const unsigned itri, + unsigned ids[3]) +{ + const unsigned* data; + if(!shape + || shape->type != GEOM_MESH + || !ids + || itri >= (unsigned)mesh_get_ntris(shape->data.mesh)) + return RES_BAD_ARG; + + data = mesh_get_ids(shape->data.mesh) + itri * 3; + ids[0] = data[0]; + ids[1] = data[1]; + ids[2] = data[2]; + return RES_OK; +} + diff --git a/src/test_s3d_shape.c b/src/test_s3d_shape.c @@ -34,6 +34,7 @@ #include "test_s3d_cbox.h" #include "test_s3d_utils.h" +#include <rsys/float3.h> #include <rsys/math.h> int @@ -46,6 +47,9 @@ main(int argc, char** argv) struct s3d_shape* inst; struct s3d_scene* scn; struct s3d_vertex_data attribs[4]; + struct s3d_attrib attr; + unsigned nverts, ntris; + unsigned ids[3]; float pos[3]; const unsigned cbox_ntris = sizeof(cbox_walls_ids) / sizeof(unsigned[3]); const unsigned cbox_nverts = sizeof(cbox_walls) / sizeof(float[3]); @@ -189,7 +193,6 @@ main(int argc, char** argv) attribs[2].type = S3D_FLOAT2; attribs[2].usage = S3D_ATTRIB_2; attribs[2].get = cbox_get_uv; - attribs[3] = S3D_VERTEX_DATA_NULL; CHECK(s3d_mesh_setup_indexed_vertices (shape, cbox_ntris, S3D_KEEP, cbox_nverts, attribs, 3, data), RES_OK); @@ -211,6 +214,65 @@ main(int argc, char** argv) CHECK(s3d_mesh_setup_indexed_vertices (shape, cbox_ntris, S3D_KEEP, cbox_nverts, attribs, 2, data), RES_OK); + CHECK(s3d_mesh_get_vertices_count(NULL, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertices_count(shape, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertices_count(NULL, &nverts), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertices_count(shape, &nverts), RES_OK); + CHECK(nverts, cbox_nverts); + + CHECK(s3d_mesh_get_vertex_attrib(NULL, nverts, S3D_ATTRIBS_COUNT__, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(shape, nverts, S3D_ATTRIBS_COUNT__, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(NULL, 0, S3D_ATTRIBS_COUNT__, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(shape, 0, S3D_ATTRIBS_COUNT__, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(NULL, nverts, S3D_POSITION, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(shape, nverts, S3D_POSITION, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(NULL, 0, S3D_POSITION, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(shape, 0, S3D_POSITION, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(NULL, nverts, S3D_ATTRIBS_COUNT__, &attr), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(shape, nverts, S3D_ATTRIBS_COUNT__, &attr), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(NULL, 0, S3D_ATTRIBS_COUNT__, &attr), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(shape, 0, S3D_ATTRIBS_COUNT__, &attr), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(NULL, nverts, S3D_POSITION, &attr), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(shape, nverts, S3D_POSITION, &attr), RES_BAD_ARG); + CHECK(s3d_mesh_get_vertex_attrib(NULL, 0, S3D_POSITION, &attr), RES_BAD_ARG); + FOR_EACH(id, 0, nverts) { + cbox_get_position(id, pos, data); + + CHECK(s3d_mesh_get_vertex_attrib(shape, id, S3D_POSITION, &attr), RES_OK); + CHECK(attr.type, S3D_FLOAT3); + CHECK(attr.usage, S3D_POSITION); + CHECK(f3_eq_eps(attr.value, pos, 1.e-6f), 1); + + CHECK(s3d_mesh_get_vertex_attrib(shape, id, S3D_ATTRIB_0, &attr), RES_OK); + CHECK(attr.type, S3D_FLOAT3); + CHECK(attr.usage, S3D_ATTRIB_0); + CHECK(f3_eq_eps(attr.value, pos, 1.e-6f), 1); + } + CHECK(s3d_mesh_get_vertex_attrib(shape, id, S3D_ATTRIB_1, &attr), RES_BAD_ARG); + + CHECK(s3d_mesh_get_triangles_count(NULL, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_triangles_count(shape, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_triangles_count(NULL, &ntris), RES_BAD_ARG); + CHECK(s3d_mesh_get_triangles_count(shape, &ntris), RES_OK); + CHECK(ntris, cbox_ntris); + + CHECK(s3d_mesh_get_triangle_indices(NULL, ntris, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_triangle_indices(shape, ntris, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_triangle_indices(NULL, 0, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_triangle_indices(shape, 0, NULL), RES_BAD_ARG); + CHECK(s3d_mesh_get_triangle_indices(NULL, ntris, ids), RES_BAD_ARG); + CHECK(s3d_mesh_get_triangle_indices(shape, ntris, ids), RES_BAD_ARG); + CHECK(s3d_mesh_get_triangle_indices(NULL, 0, ids), RES_BAD_ARG); + + FOR_EACH(id, 0, ntris) { + unsigned indices[3]; + CHECK(s3d_mesh_get_triangle_indices(shape, id, ids), RES_OK); + cbox_get_ids(id, indices, data); + CHECK(ids[0], indices[0]); + CHECK(ids[1], indices[1]); + CHECK(ids[2], indices[2]); + } + CHECK(s3d_shape_is_enabled(NULL, NULL), RES_BAD_ARG); CHECK(s3d_shape_is_enabled(shape, NULL), RES_BAD_ARG); CHECK(s3d_shape_is_enabled(NULL, &c), RES_BAD_ARG);