00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
#include <volume_io/internal_volume_io.h>
00016
#include <bicpl/geom.h>
00017
00018
#ifndef lint
00019
static char rcsid[] =
"$Header: /software/source//libraries/bicpl/Geometry/tetrahedrons.c,v 1.14 2002/04/29 18:31:05 stever Exp $";
00020
#endif
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038 public BOOLEAN
is_this_tetrahedral_topology(
00039
polygons_struct *polygons )
00040 {
00041
int n_polygons;
00042
00043 n_polygons = polygons->
n_items;
00044
00045
while( n_polygons != 20 && n_polygons > 8 && n_polygons % 4 == 0 )
00046 n_polygons /= 4;
00047
00048
return( n_polygons == 4 || n_polygons == 6 || n_polygons == 8 ||
00049 n_polygons == 20 );
00050 }
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066 public int get_tetra_tessellation_with_n_points(
00067
int n_points )
00068 {
00069
int n_polygons;
00070
00071 n_polygons = 2 * (n_points - 2);
00072
00073
return( n_polygons );
00074 }
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101 public void create_tetrahedral_sphere(
00102 Point *centre,
00103 Real rx,
00104 Real ry,
00105 Real rz,
00106
int n_triangles,
00107
polygons_struct *polygons )
00108 {
00109
static int possible_sizes[] = { 4, 6, 8, 20 };
00110
int p, start_size, s, size, best_size, prev_size;
00111 Real cx, cy, cz, dx, dy, dz, scale;
00112 Real x,
y, z;
00113 Point origin;
00114
00115
00116
00117 start_size = 4;
00118 best_size = 0;
00119 for_less( s, 0, SIZEOF_STATIC_ARRAY( possible_sizes ) )
00120 {
00121 size = possible_sizes[s];
00122 prev_size = size;
00123
while( size < n_triangles )
00124 {
00125 prev_size = size;
00126 size *= 4;
00127 }
00128
00129
if( ABS( n_triangles - prev_size ) < ABS( n_triangles - best_size ) )
00130 {
00131 best_size = prev_size;
00132 start_size = possible_sizes[s];
00133 }
00134
00135
if( ABS( n_triangles - size ) < ABS( n_triangles - best_size ) )
00136 {
00137 best_size = size;
00138 start_size = possible_sizes[s];
00139 }
00140 }
00141
00142 fill_Point( origin, 0.0, 0.0, 0.0 );
00143
00144
if( start_size == 6 )
00145 {
00146
create_polygons_sphere( &origin, 1.0, 1.0, 1.0, 2, 3,
FALSE, polygons );
00147 }
00148
else if( start_size == 8 )
00149 {
00150
create_polygons_sphere( &origin, 1.0, 1.0, 1.0, 2, 4,
FALSE, polygons );
00151 }
00152
else if( start_size == 20 )
00153 {
00154
create_unit_icosahedron( polygons );
00155 }
00156
else
00157 {
00158
create_unit_tetrahedron( polygons );
00159 }
00160
00161 cx = (Real) Point_x( *centre );
00162 cy = (Real) Point_y( *centre );
00163 cz = (Real) Point_z( *centre );
00164
00165 for_less( p, 0, polygons->
n_points )
00166 {
00167 x = cx + rx * (Real) Point_x(polygons->
points[p]);
00168
y = cy + ry * (Real) Point_y(polygons->
points[p]);
00169 z = cz + rz * (Real) Point_z(polygons->
points[p]);
00170 fill_Point( polygons->
points[p], x,
y, z );
00171 }
00172
00173
00174
00175
00176
while( polygons->
n_items < n_triangles )
00177 {
00178
subdivide_polygons( polygons );
00179
00180
00181
00182 for_less( p, 0, polygons->
n_points )
00183 {
00184 dx = (Real) Point_x(polygons->
points[p]) - cx;
00185 dy = (Real) Point_y(polygons->
points[p]) - cy;
00186 dz = (Real) Point_z(polygons->
points[p]) - cz;
00187 scale = dx * dx / rx / rx + dy * dy / ry / ry + dz * dz / rz / rz;
00188 scale = 1.0 / sqrt( scale );
00189 dx *= scale;
00190 dy *= scale;
00191 dz *= scale;
00192 fill_Point( polygons->
points[p], cx + dx, cy + dy, cz + dz );
00193 }
00194 }
00195
00196
compute_polygon_normals( polygons );
00197 }
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211
00212
00213 public void half_sample_tetrahedral_tessellation(
00214
polygons_struct *polygons,
00215
polygons_struct *half )
00216 {
00217
int i, quarter_n_polygons;
00218
static Point dummy_centre = { 0.0f, 0.0f, 0.0f };
00219
00220 quarter_n_polygons = polygons->
n_items / 4;
00221
00222
create_tetrahedral_sphere( &dummy_centre, 1.0, 1.0, 1.0,
00223 quarter_n_polygons, half );
00224
00225 for_less( i, 0, half->
n_points )
00226 {
00227 half->
points[i] = polygons->
points[i];
00228 half->
normals[i] = polygons->
normals[i];
00229 }
00230
00231
if( polygons->
colour_flag ==
PER_VERTEX_COLOURS )
00232 {
00233 half->
colour_flag =
PER_VERTEX_COLOURS;
00234 REALLOC( half->
colours, half->
n_points );
00235 for_less( i, 0, half->
n_points )
00236 half->
colours[i] = polygons->
colours[i];
00237 }
00238 }