Main Page | Modules | Data Structures | File List | Data Fields | Globals | Related Pages

clip_3d.c

Go to the documentation of this file.
00001 #include <volume_io/internal_volume_io.h> 00002 #include <bicpl/geom.h> 00003 00004 #define STATIC_STORAGE 1000 00005 00006 public int clip_polygon_against_box( 00007 int n_points, 00008 Point points[], 00009 Real x_min, 00010 Real x_max, 00011 Real y_min, 00012 Real y_max, 00013 Real z_min, 00014 Real z_max, 00015 int n_output_points, 00016 Point output_points[] ) 00017 { 00018 int p, n_planes, n_out, n, i; 00019 int n_input[7], dim, which; 00020 BOOLEAN last[7][2], first_flags[6], last_flag; 00021 Point prev[6], input[7][2], point, first_points[6]; 00022 Real box[2][N_DIMENSIONS], prev_dist[6], first_dist[6], dist, ratio; 00023 00024 box[0][X] = x_min; 00025 box[1][X] = x_max; 00026 box[0][Y] = y_min; 00027 box[1][Y] = y_max; 00028 box[0][Z] = z_min; 00029 box[1][Z] = z_max; 00030 n_planes = 6; 00031 00032 for_less( p, 0, n_planes ) 00033 { 00034 first_flags[p] = TRUE; 00035 n_input[p] = 0; 00036 } 00037 n_input[n_planes] = 0; 00038 00039 n_out = 0; 00040 00041 for_less( i, 0, n_points+1 ) 00042 { 00043 input[0][0] = points[i%n_points]; 00044 last[0][0] = (i == n_points); 00045 n_input[0] = 1; 00046 p = 0; 00047 00048 while( p >= 0 ) 00049 { 00050 --n_input[p]; 00051 point = input[p][n_input[p]]; 00052 last_flag = last[p][n_input[p]]; 00053 00054 if( !last_flag ) 00055 { 00056 dim = p / 2; 00057 which = p % 2; 00058 if( which == 0 ) 00059 dist = RPoint_coord(point,dim) - box[0][dim]; 00060 else 00061 dist = box[1][dim] - RPoint_coord(point,dim); 00062 00063 if( dist >= 0.0 ) 00064 { 00065 input[p+1][0] = point; 00066 last[p+1][0] = FALSE; 00067 n_input[p+1] = 1; 00068 } 00069 } 00070 else 00071 { 00072 dist = first_dist[p]; 00073 point = first_points[p]; 00074 00075 if( !first_flags[p] && p < n_planes - 1 ) 00076 { 00077 last[p+1][0] = TRUE; 00078 n_input[p+1] = 1; 00079 } 00080 } 00081 00082 if( first_flags[p] ) 00083 { 00084 first_points[p] = point; 00085 first_flags[p] = FALSE; 00086 first_dist[p] = dist; 00087 } 00088 else if( prev_dist[p] * dist < 0.0 ) 00089 { 00090 ratio = prev_dist[p] / (prev_dist[p] - dist); 00091 n = n_input[p+1]; 00092 INTERPOLATE_POINTS( input[p+1][n], prev[p], point, ratio ); 00093 last[p+1][n] = FALSE; 00094 ++n_input[p+1]; 00095 } 00096 00097 prev[p] = point; 00098 prev_dist[p] = dist; 00099 00100 ++p; 00101 00102 if( p == n_planes && n_input[p] > 0 ) 00103 { 00104 n = n_input[p]; 00105 for_down( n, n_input[p]-1, 0 ) 00106 { 00107 if ( n_out >= n_output_points ) 00108 { 00109 handle_internal_error( "too many points generated in clip_polygon_against_box()" ); 00110 return( n_out ); 00111 } 00112 output_points[n_out] = input[p][n]; 00113 ++n_out; 00114 } 00115 n_input[p] = 0; 00116 --p; 00117 } 00118 00119 while( p >= 0 && n_input[p] == 0 ) 00120 --p; 00121 } 00122 } 00123 00124 return( n_out ); 00125 } 00126 00127 public int clip_polygon_against_plane( 00128 int n_points, 00129 Point points[], 00130 Real plane_constant, 00131 Vector *normal, 00132 Point output_points[] ) 00133 { 00134 int p, n_output; 00135 Real next_dist, dist, ratio; 00136 Point point, next_point; 00137 00138 n_output = 0; 00139 dist = 0.0; 00140 00141 next_dist = DOT_POINT_VECTOR( *normal, points[0] ) + plane_constant; 00142 next_point = points[0]; 00143 00144 for_less( p, 0, n_points ) 00145 { 00146 dist = next_dist; 00147 point = next_point; 00148 next_point = points[(p+1) % n_points]; 00149 next_dist = DOT_POINT_VECTOR( *normal, next_point ) + plane_constant; 00150 00151 if( dist >= 0.0 ) 00152 { 00153 output_points[n_output] = point; 00154 ++n_output; 00155 } 00156 00157 if( (n_points > 2 || (p == 0 && n_points == 2)) 00158 && dist * next_dist < 0.0 ) 00159 { 00160 ratio = dist / (dist - next_dist); 00161 INTERPOLATE_POINTS( output_points[n_output], 00162 point, next_point, ratio ); 00163 ++n_output; 00164 } 00165 } 00166 00167 return( n_output ); 00168 } 00169 00170 public void split_polygon_with_plane( 00171 int n_points, 00172 Point points[], 00173 Real plane_constant, 00174 Vector *normal, 00175 int *n_in, 00176 Point in_points[], 00177 int *n_out, 00178 Point out_points[] ) 00179 { 00180 int p; 00181 Real next_dist, dist, ratio; 00182 Point point, next_point, interp; 00183 00184 *n_in = 0; 00185 *n_out = 0; 00186 dist = 0.0; 00187 00188 next_dist = DOT_POINT_VECTOR( *normal, points[0] ) + plane_constant; 00189 next_point = points[0]; 00190 00191 for_less( p, 0, n_points ) 00192 { 00193 dist = next_dist; 00194 point = next_point; 00195 next_point = points[(p+1) % n_points]; 00196 next_dist = DOT_POINT_VECTOR( *normal, next_point ) + plane_constant; 00197 00198 if( dist >= 0.0 ) 00199 { 00200 in_points[*n_in] = point; 00201 ++(*n_in); 00202 } 00203 00204 if( dist <= 0.0 ) 00205 { 00206 out_points[*n_out] = point; 00207 ++(*n_out); 00208 } 00209 00210 if( (n_points > 2 || (p == 0 && n_points == 2)) 00211 && dist * next_dist < 0.0 ) 00212 { 00213 ratio = dist / (dist - next_dist); 00214 INTERPOLATE_POINTS( interp, point, next_point, ratio ); 00215 in_points[*n_in] = interp; 00216 ++(*n_in); 00217 out_points[*n_out] = interp; 00218 ++(*n_out); 00219 } 00220 } 00221 }

Generated on Wed Jul 28 09:10:56 2004 for BICPL by doxygen 1.3.7