sgs_geometry_box.c (5884B)
1 /* Copyright (C) 2021-2023 Centre National de la Recherche Scientifique 2 * Copyright (C) 2021-2023 INSA Lyon 3 * Copyright (C) 2021-2023 Institut Mines Télécom Albi-Carmaux 4 * Copyright (C) 2021-2023 |Méso|Star> (contact@meso-star.com) 5 * Copyright (C) 2021-2023 Institut Pascal 6 * Copyright (C) 2021-2023 PhotonLyX (info@photonlyx.com) 7 * Copyright (C) 2021-2023 Université de Lorraine 8 * Copyright (C) 2021-2023 Université Paul Sabatier 9 * Copyright (C) 2021-2023 Université Toulouse - Jean Jaurès 10 * 11 * This program is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU General Public License as published by 13 * the Free Software Foundation, either version 3 of the License, or 14 * (at your option) any later version. 15 * 16 * This program is distributed in the hope that it will be useful, 17 * but WITHOUT ANY WARRANTY; without even the implied warranty of 18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 19 * GNU General Public License for more details. 20 * 21 * You should have received a copy of the GNU General Public License 22 * along with this program. If not, see <http://www.gnu.org/licenses/>. */ 23 24 #include "sgs_geometry.h" 25 #include "sgs_geometry_c.h" 26 #include "sgs_log.h" 27 28 /******************************************************************************* 29 * Helper functions 30 ******************************************************************************/ 31 static res_T 32 check_box_args(struct sgs* sgs, const struct sgs_geometry_box_args* args) 33 { 34 ASSERT(args); 35 if(args->lower[0] >= args->upper[0] 36 || args->lower[1] >= args->upper[1] 37 || args->lower[2] >= args->upper[2]) { 38 sgs_log_err(sgs, 39 "Invalid box definition (lower: %g,%g,%g; upper: %g,%g,%g)\n", 40 SPLIT3(args->lower), 41 SPLIT3(args->upper)); 42 return RES_BAD_ARG; 43 } 44 45 if(args->pi < 0) { 46 sgs_log_err(sgs, 47 "Invalid box opening (pi = %g)\n", args->pi); 48 return RES_BAD_ARG; 49 } 50 51 return RES_OK; 52 } 53 54 static res_T 55 setup_box_mesh 56 (struct sgs_geometry* geom, 57 const struct sgs_geometry_box_args* args) 58 { 59 const double* low = NULL; 60 const double* upp = NULL; 61 double* vtx = NULL; 62 size_t* ids = NULL; 63 int* types = NULL; 64 res_T res = RES_OK; 65 ASSERT(geom && args); 66 67 /* Allocate memory space */ 68 res = darray_double_resize(&geom->verts, 12/*#vertices*/*3/*#coords per vertex*/); 69 if(res != RES_OK) goto error; 70 res = darray_size_t_resize(&geom->tris, 12/*#triangles*/*3/*#ids per triangle*/); 71 if(res != RES_OK) goto error; 72 res = darray_int_resize(&geom->tris_rt_type, 12/*#triangles*/); 73 if(res != RES_OK) goto error; 74 75 /* Fetch allocated memory space */ 76 vtx = darray_double_data_get(&geom->verts); 77 ids = darray_size_t_data_get(&geom->tris); 78 types = darray_int_data_get(&geom->tris_rt_type); 79 80 /* Fetch input args */ 81 low = args->lower; 82 upp = args->upper; 83 84 /* Setup the vertices */ 85 vtx[0*3+0] = low[0]; vtx[0*3+1] = low[1]; vtx[0*3+2] = low[2]; 86 vtx[1*3+0] = upp[0]; vtx[1*3+1] = low[1]; vtx[1*3+2] = low[2]; 87 vtx[2*3+0] = low[0]; vtx[2*3+1] = upp[1]; vtx[2*3+2] = low[2]; 88 vtx[3*3+0] = upp[0]; vtx[3*3+1] = upp[1]; vtx[3*3+2] = low[2]; 89 90 vtx[4*3+0] = low[0]; vtx[4*3+1] = low[1]; vtx[4*3+2] = upp[2]; 91 vtx[5*3+0] = upp[0]; vtx[5*3+1] = low[1]; vtx[5*3+2] = upp[2]; 92 vtx[6*3+0] = low[0]; vtx[6*3+1] = upp[1]; vtx[6*3+2] = upp[2]; 93 vtx[7*3+0] = upp[0]; vtx[7*3+1] = upp[1]; vtx[7*3+2] = upp[2]; 94 95 vtx[8*3 +0] = low[0]; vtx[8*3+1] = low[1]; vtx[8*3+2] = upp[2]+args->pi; 96 vtx[9*3 +0] = upp[0]; vtx[9*3+1] = low[1]; vtx[9*3+2] = upp[2]+args->pi; 97 vtx[10*3+0] = low[0]; vtx[10*3+1] = upp[1]; vtx[10*3+2] = upp[2]+args->pi; 98 vtx[11*3+0] = upp[0]; vtx[11*3+1] = upp[1]; vtx[11*3+2] = upp[2]+args->pi; 99 100 /* Setup the triangles */ 101 ids[0*3+0] = 0; ids[0*3+1] = 4; ids[0*3+2] = 2; /* min X */ 102 ids[1*3+0] = 2; ids[1*3+1] = 4; ids[1*3+2] = 6; /* min X */ 103 ids[2*3+0] = 3; ids[2*3+1] = 7; ids[2*3+2] = 5; /* max X */ 104 ids[3*3+0] = 5; ids[3*3+1] = 1; ids[3*3+2] = 3; /* max X */ 105 ids[4*3+0] = 0; ids[4*3+1] = 1; ids[4*3+2] = 5; /* min Y */ 106 ids[5*3+0] = 5; ids[5*3+1] = 4; ids[5*3+2] = 0; /* min Y */ 107 ids[6*3+0] = 2; ids[6*3+1] = 6; ids[6*3+2] = 7; /* max Y */ 108 ids[7*3+0] = 7; ids[7*3+1] = 3; ids[7*3+2] = 2; /* max Y */ 109 ids[8*3+0] = 0; ids[8*3+1] = 2; ids[8*3+2] = 1; /* min Z */ 110 ids[9*3+0] = 1; ids[9*3+1] = 2; ids[9*3+2] = 3; /* min Z */ 111 ids[10*3+0] = 8; ids[10*3+1] = 9; ids[10*3+2] = 10; /* max Z */ 112 ids[11*3+0] = 10; ids[11*3+1] = 9; ids[11*3+2] = 11; /* max Z */ 113 114 /* Setup the type of the triangles */ 115 types[0] = types[1] = SGS_SURFACE_X_MIN; 116 types[2] = types[3] = SGS_SURFACE_X_MAX; 117 types[4] = types[5] = SGS_SURFACE_Y_MIN; 118 types[6] = types[7] = SGS_SURFACE_Y_MAX; 119 types[8] = types[9] = SGS_SURFACE_Z_MIN; 120 types[10] = types[11] = SGS_SURFACE_Z_MAX; 121 122 exit: 123 return res; 124 error: 125 darray_double_clear(&geom->verts); 126 darray_size_t_clear(&geom->tris); 127 darray_int_clear(&geom->tris_rt_type); 128 goto exit; 129 } 130 131 /******************************************************************************* 132 * API function 133 ******************************************************************************/ 134 res_T 135 sgs_geometry_box_create 136 (struct sgs* sgs, 137 const struct sgs_geometry_box_args* args, 138 struct sgs_geometry** out_geom) 139 { 140 struct sgs_geometry* geom = NULL; 141 res_T res = RES_OK; 142 ASSERT(sgs && args && out_geom); 143 144 res = check_box_args(sgs, args); 145 if(res != RES_OK) goto error; 146 res = geometry_create(sgs, args->sampling_mask, &geom); 147 if(res != RES_OK) goto error; 148 res = setup_box_mesh(geom, args); 149 if(res != RES_OK) goto error; 150 res = geometry_setup_view_rt(geom); 151 if(res != RES_OK) goto error; 152 res = geometry_setup_view_sp(geom, args->sampling_mask); 153 if(res != RES_OK) goto error; 154 155 geometry_compute_aabb(geom); 156 157 exit: 158 *out_geom = geom; 159 return res; 160 error: 161 if(geom) { 162 sgs_geometry_ref_put(geom); 163 geom = NULL; 164 } 165 goto exit; 166 } 167