00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047 #ifndef lint
00048 static const char RCSmater[] = "@(#)$Header: /cvsroot/brlcad/brlcad/src/librt/mater.c,v 14.10 2006/09/16 02:04:25 lbutler Exp $ (BRL)";
00049 #endif
00050
00051 #include "common.h"
00052
00053
00054
00055 #include <stdio.h>
00056 #include "machine.h"
00057 #include "vmath.h"
00058 #include "mater.h"
00059 #include "raytrace.h"
00060 #include "./debug.h"
00061
00062
00063
00064
00065
00066
00067 struct mater *rt_material_head = MATER_NULL;
00068
00069 void rt_insert_color(struct mater *newp);
00070
00071
00072
00073
00074 void
00075 rt_pr_mater(register struct mater *mp)
00076 {
00077 (void)bu_log( "%5d..%d\t", mp->mt_low, mp->mt_high );
00078 (void)bu_log( "%d,%d,%d\t", mp->mt_r, mp->mt_g, mp->mt_b);
00079 }
00080
00081
00082
00083
00084
00085
00086 void
00087 rt_color_addrec( int low, int hi, int r, int g, int b, long addr )
00088 {
00089 register struct mater *mp;
00090
00091 BU_GETSTRUCT( mp, mater );
00092 mp->mt_low = low;
00093 mp->mt_high = hi;
00094 mp->mt_r = r;
00095 mp->mt_g = g;
00096 mp->mt_b = b;
00097
00098 mp->mt_daddr = addr;
00099 rt_insert_color( mp );
00100 }
00101
00102
00103
00104
00105
00106
00107
00108 void
00109 rt_insert_color( struct mater *newp )
00110 {
00111 register struct mater *mp;
00112 register struct mater *zot;
00113
00114 if( rt_material_head == MATER_NULL || newp->mt_high < rt_material_head->mt_low ) {
00115
00116 newp->mt_forw = rt_material_head;
00117 rt_material_head = newp;
00118 return;
00119 }
00120 if( newp->mt_low < rt_material_head->mt_low ) {
00121
00122 newp->mt_forw = rt_material_head;
00123 rt_material_head = newp;
00124 goto check_overlap;
00125 }
00126 for( mp = rt_material_head; mp != MATER_NULL; mp = mp->mt_forw ) {
00127 if( mp->mt_low == newp->mt_low &&
00128 mp->mt_high <= newp->mt_high ) {
00129 bu_log("dropping overwritten region-id based material property entry:\n");
00130 newp->mt_forw = mp->mt_forw;
00131 rt_pr_mater( mp );
00132 *mp = *newp;
00133 bu_free( (char *)newp, "getstruct mater" );
00134 newp = mp;
00135 goto check_overlap;
00136 }
00137 if( mp->mt_low < newp->mt_low &&
00138 mp->mt_high > newp->mt_high ) {
00139
00140 bu_log("Splitting region-id based material property entry into 3 ranges\n");
00141 BU_GETSTRUCT( zot, mater );
00142 *zot = *mp;
00143 zot->mt_daddr = MATER_NO_ADDR;
00144
00145 zot->mt_low = newp->mt_high+1;
00146 mp->mt_high = newp->mt_low-1;
00147
00148
00149 newp->mt_forw = zot;
00150 mp->mt_forw = newp;
00151 rt_pr_mater( mp );
00152 rt_pr_mater( newp );
00153 rt_pr_mater( zot );
00154 return;
00155 }
00156 if( mp->mt_high > newp->mt_low ) {
00157
00158 bu_log("Shortening region-id based material property entry lhs range, from:\n");
00159 rt_pr_mater( mp );
00160 bu_log("to:\n");
00161 mp->mt_high = newp->mt_low-1;
00162 rt_pr_mater( mp );
00163
00164 newp->mt_forw = mp->mt_forw;
00165 mp->mt_forw = newp;
00166 goto check_overlap;
00167 }
00168 if( mp->mt_forw == MATER_NULL ||
00169 newp->mt_low < mp->mt_forw->mt_low ) {
00170
00171 newp->mt_forw = mp->mt_forw;
00172 mp->mt_forw = newp;
00173 goto check_overlap;
00174 }
00175 }
00176 bu_log("fell out of rt_insert_color loop, append region-id based material property entry to end of list\n");
00177
00178 newp->mt_forw = MATER_NULL;
00179 mp->mt_forw = newp;
00180 return;
00181
00182
00183 check_overlap:
00184 while( newp->mt_forw != MATER_NULL &&
00185 newp->mt_high >= newp->mt_forw->mt_low ) {
00186 if( newp->mt_high >= newp->mt_forw->mt_high ) {
00187
00188 zot = newp->mt_forw;
00189 newp->mt_forw = zot->mt_forw;
00190 bu_log("dropping overlaping region-id based material property entry:\n");
00191 rt_pr_mater( zot );
00192 bu_free( (char *)zot, "getstruct mater" );
00193 continue;
00194 }
00195 if( newp->mt_high >= newp->mt_forw->mt_low ) {
00196
00197 bu_log("Shortening region-id based material property entry rhs range, from:\n");
00198 rt_pr_mater( newp->mt_forw );
00199 bu_log("to:\n");
00200 newp->mt_forw->mt_low = newp->mt_high+1;
00201 rt_pr_mater( newp->mt_forw );
00202 continue;
00203 }
00204 }
00205 }
00206
00207
00208
00209
00210
00211
00212
00213 void
00214 rt_region_color_map(register struct region *regp)
00215 {
00216 register struct mater *mp;
00217
00218 if( regp == REGION_NULL ) {
00219 bu_log("color_map(NULL)\n");
00220 return;
00221 }
00222 for( mp = rt_material_head; mp != MATER_NULL; mp = mp->mt_forw ) {
00223 if( regp->reg_regionid <= mp->mt_high &&
00224 regp->reg_regionid >= mp->mt_low ) {
00225 regp->reg_mater.ma_color_valid = 1;
00226 regp->reg_mater.ma_color[0] =
00227 (((double)mp->mt_r)+0.5)*bn_inv255;
00228 regp->reg_mater.ma_color[1] =
00229 (((double)mp->mt_g)+0.5)*bn_inv255;
00230 regp->reg_mater.ma_color[2] =
00231 (((double)mp->mt_b)+0.5)*bn_inv255;
00232 return;
00233 }
00234 }
00235 }
00236
00237
00238
00239
00240
00241
00242
00243 void
00244 rt_color_free(void)
00245 {
00246 register struct mater *mp;
00247
00248 while( (mp = rt_material_head) != MATER_NULL ) {
00249 rt_material_head = mp->mt_forw;
00250
00251 bu_free( (char *)mp, "getstruct mater" );
00252 }
00253 }
00254
00255
00256
00257
00258
00259
00260
00261
00262
00263