00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00021 #include<ImLib3D/TestPatterns.hpp>
00022 #include<ImLib3D/MorphologicalOperators.hpp>
00023
00024
00025
00026 void
00027 IP3D::Explode(const Size3D &size,const Vect3Df &C,Field3Df &ima)
00028 {
00029 ima.Resize(size);
00030 Field3Df::iteratorXYZ p;
00031 for(p=ima.begin();p!=ima.end();++p)
00032 {
00033 *p=Vect3Df(p.x,p.y,p.z)-C;
00034 }
00035 }
00036
00037 void
00038 IP3D::Sphere(const Size3D &size,const Vect3Df &C,float r,Image3Df &ima)
00039 {
00040 ima.Resize(size);
00041 Image3Df::iteratorXYZ p;
00042 for(p=ima.begin();p!=ima.end();++p)
00043 {
00044 if(C.Dist2(Vect3Df(p.x,p.y,p.z))<r*r){*p=1;}
00045 else{*p=0;}
00046 }
00047 }
00048
00049 namespace IP3D
00050 {
00051 namespace ConeHelpers
00052 {
00053 void
00054 NoAA(Image3Df &ima,const Vect3Df &P0,const Vect3Df &P1,float r)
00055 {
00056 Image3Df::iteratorXYZ p;
00057 Vect3Df P0P1=P1-P0;
00058 Vect3Df Uz=P0P1;Uz.Unit();
00059 float l=P0P1.Norme();
00060 for(p=ima.begin();p!=ima.end();++p)
00061 {
00062 Vect3Df P=Vect3Df(p.x,p.y,p.z);
00063
00064 float cz=(P-P0)*Uz;
00065 Vect3Df N=(P-P0)-cz*Uz;
00066 float cr=N.Norme();
00067 if(cz<l && cz>0 && cr<(r*(1-cz/l)) ){*p=1;}
00068 else{*p=0;}
00069 }
00070 }
00071 }
00072 }
00073 void
00074 IP3D::Cone(const Size3D &size,const Vect3Df &P0,const Vect3Df &P1,float r,Image3Df &ima,float ar)
00075 {
00076 ima.Resize(size);
00077 if(ar==0){ConeHelpers::NoAA(ima,P0,P1,r);return;}
00078 Image3Df::iteratorXYZ p;
00079 Vect3Df P0P1=P1-P0;
00080 Vect3Df Uz=P0P1;Uz.Unit();
00081 float l=P0P1.Norme();
00082 float M=M_PI/2.0;
00083 for(p=ima.begin();p!=ima.end();++p)
00084 {
00085 Vect3Df P=Vect3Df(p.x,p.y,p.z);
00086
00087 float cz=(P-P0)*Uz;
00088 if(cz>l){*p=0;continue;}
00089
00090 Vect3Df N=(P-P0)-cz*Uz;
00091 float cr=N.Norme();
00092 float r1=r*(1-cz/l);
00093 float dr=-(cr-r1)/ar;
00094 float dz= (cz-0 )/ar;
00095 bool isBorder=fabs(dz)<1 || fabs(dr)<1;
00096
00097 if(!isBorder)
00098 {
00099 if(cz<l && cz>0 && cr<(r*(1-cz/l)) ){*p=1;}
00100 else{*p=0;}
00101 }
00102 else
00103 {
00104 float fz=(dz>0 ? 1 : 0);
00105 if(fabs(dz)<=1){fz=.5+.5*sin(M*dz);}
00106 float fr=(dr>0 ? 1 : 0);
00107 if(fabs(dr)<=1){fr=.5+.5*sin(M*dr);}
00108 *p=fz*fr;
00109 }
00110 }
00111 }
00112 void
00113 IP3D::NoiseUniform(const Size3D &size,Image3Df &ima,float v0,float v1)
00114 {
00115 ima.Resize(size);
00116 Image3Df::iteratorXYZ p;
00117 for(p=ima.begin();p!=ima.end();++p)
00118 {
00119 *p=RandomDouble(v0,v1);
00120 }
00121 }
00122
00123 void
00124 IP3D::NoiseGaussian(const Size3D &size,Image3Df &ima,float average,float variance)
00125 {
00126 ima.Resize(size);
00127 Image3Df::iteratorXYZ p;
00128 double et=sqrt(variance);
00129 for(p=ima.begin();p!=ima.end();++p)
00130 {
00131 double randVal=RandomDouble();
00132 double r=sqrt(-2 * log(randVal) );
00133 double angle=RandomDouble(0,2*M_PI);
00134 *p=average+et*r*cos(angle);
00135 }
00136 }
00137
00138 void
00139 IP3D::Target(const Size3D &size,Image3Df &ima)
00140 {
00141 ima.Resize(size);
00142 Image3Df::iteratorXYZ p;
00143 for(p=ima.begin();p!=ima.end();++p)
00144 {
00145 Vect3Df P(p.x/(float)ima.Width(),p.y/(float)ima.Height(),p.z/(float)ima.Depth());
00146 double d=(P-Vect3Df(.5,.5,.5)).Norme();
00147 d=d/.5;
00148 float cx=.8;
00149 float a=((d-cx)/(1-cx))*M_PI/2.0;
00150 float f=1;
00151 if(d>cx && d<1){f=cos(a);f=f*f;}
00152 if(d>1){f=0;}
00153 *p=f*sin((.7*128.0)*d*d);
00154 }
00155 }
00156
00157 void
00158 IP3D::Bump(const Size3D &size,const Vect3Df ¢er,float height,float gsize,Image3Df &ima)
00159 {
00160 ima.Resize(size);
00161 Image3Df::iteratorXYZ p;
00162 for(p=ima.begin();p!=ima.end();++p)
00163 {
00164 Vect3Df pos=p.Pos();
00165 double r2=pos.Dist2(center);
00166 *p=height*exp(-r2/(2*gsize*gsize));
00167 }
00168 }
00169
00170 void
00171 IP3D::Ramp(const Size3D &size,int direction,float v0,float v1,Image3Df &res,int pos0,int pos1)
00172 {
00173 res.Resize(size);
00174
00175 if(direction<0 || direction>2){ThrowError("IP3D::Ramp bad direction 0=X 1=Y 2=Z");}
00176 if(pos0<0){pos0=0;}
00177 if(pos1<0){pos1=res.SizeV()(direction)-1;}
00178 for(Image3Df::iteratorXYZ p=res.begin();p!=res.end();++p)
00179 {
00180 int pos=p.Pos()(direction);
00181 if(pos<pos0){*p=v0;}
00182 else
00183 if(pos>pos1){*p=v1;}
00184 else
00185 {
00186 *p=v0+(v1-v0)*((pos-pos0)/(float)(pos1-pos0));
00187 }
00188 }
00189 }
00190
00191 void
00192 IP3D::Parallellogram(const Size3D &size, const RectZone3Di & rect,Image3Df &ima)
00193 {
00194 ima.Resize(size);
00195 Image3Df::iteratorXYZ p;
00196
00197 for (p=ima.begin(); p!=ima.end(); p++)
00198 {
00199 if (rect.IsInside(p.x, p.y, p.z)){*p = 1;}
00200 else{*p = 0;}
00201 }
00202 }
00203
00204 void
00205 IP3D::RectangularGrid(const Size3D &size, const Size3D& masksize,Image3Df &ima, const Vect3Di* pP0)
00206 {
00207 ima.Resize(size);
00208 Vect3Di defP0(0,0,0);
00209 const Vect3Di &P0=(pP0 ? *pP0 : defP0);
00210
00211 Vect3Di P = Vect3Di(P0.x%masksize.width, P0.y%masksize.height, P0.z%masksize.depth);
00212
00213 int x, y, z;
00214 for (x=0;x<ima.Width();x++)
00215 {
00216 for (y=0;y<ima.Height();y++)
00217 {
00218 for (z=0;z<ima.Depth();z++)
00219 {
00220 if (!((P.z+z)%masksize.depth || (P.y+y)%masksize.height))
00221 ima(x, y, z)=1;
00222 else if(!((P.x+x)%masksize.width || (P.y+y)%masksize.height))
00223 ima(x, y, z)=1;
00224 else if(!((P.x+x)%masksize.width || (P.z+z)%masksize.depth))
00225 ima(x, y, z)=1;
00226 else
00227 ima(x, y, z)=0;
00228 }
00229 }
00230 }
00231 }
00232
00233 void
00234 IP3D::ColoredGrid(const Size3D &size, const Size3D& masksize, Mask3D &ima,StructureElementType structure)
00235 {
00236 ima.Resize(size);
00237
00238 int x,y,z;
00239 if (structure == MORPHO_Cross7)
00240 {
00241 int lastx = 2;
00242 int xcount = 0;
00243 for (x=0;x<ima.Depth();x++, xcount++)
00244 {
00245 int lasty = lastx;
00246 int ycount = 0;
00247 for (y=0;y<ima.Height();y++, ycount++)
00248 {
00249 int lastz = lasty;
00250 int zcount = 0;
00251 for (z=0;z<ima.Width();z++, zcount++)
00252 {
00253 if (zcount==masksize.width)
00254 {
00255 lastz = ima(z,y,x) = (byte) ((lastz==1) ? 2 : 1);
00256 zcount = 0;
00257 }
00258 else
00259 ima(z,y,x)=lastz;
00260 }
00261 if (ycount == masksize.height)
00262 {
00263 lasty = (lasty==1) ? 2 : 1;
00264 ycount = 0;
00265 }
00266 }
00267 if (xcount == masksize.depth)
00268 {
00269 lastx = (lastx==1) ? 2 : 1;
00270 xcount = 0;
00271 }
00272 }
00273 }
00274 else if (structure == MORPHO_Planar19)
00275 {
00276 int actx = 1;
00277 int xcount = 0;
00278 for (x=0;x<ima.Depth();x++, xcount++)
00279 {
00280 int acty = actx;
00281 int ycount = 0;
00282 for (y=0;y<ima.Height();y++, ycount++)
00283 {
00284 int actz=acty;
00285 int zcount = 0;
00286 for (z=0;z<ima.Width();z++, zcount++)
00287 {
00288 if (zcount==masksize.width)
00289 {
00290 if (actz==3)
00291 actz=4;
00292 else if (actz==4)
00293 actz=3;
00294 else if (actz==1)
00295 actz=2;
00296 else if (actz==2)
00297 actz=1;
00298 ima(z, y, x) = (byte)actz;
00299 zcount = 0;
00300 }
00301 else
00302 ima(z,y,x)=(byte)actz;
00303 }
00304 if (ycount == masksize.height)
00305 {
00306 acty+=2;
00307 acty%=4;
00308 if (acty==0) acty=4;
00309 ycount = 0;
00310 }
00311 }
00312 if (xcount == masksize.depth)
00313 {
00314 actx = (actx==1) ? 4 : 1;
00315 xcount = 0;
00316 }
00317 }
00318 }
00319 else if (structure == MORPHO_Cubic27)
00320 {
00321 int actx = 1;
00322 int xcount = 0;
00323 for (x=0;x<ima.Depth();x++, xcount++)
00324 {
00325 int acty = actx;
00326 int ycount = 0;
00327 for (y=0;y<ima.Height();y++, ycount++)
00328 {
00329 int actz=acty;
00330 int zcount = 0;
00331 for (z=0;z<ima.Width();z++, zcount++)
00332 {
00333 if (zcount==masksize.width)
00334 {
00335 if (actz==1||actz==3)
00336 actz=(actz==1)?3:1;
00337 if (actz==2||actz==6)
00338 actz=(actz==2)?6:2;
00339 if (actz==4||actz==5)
00340 actz=(actz==4)?5:4;
00341 if (actz==7||actz==8)
00342 actz=(actz==7)?8:7;
00343 ima(z, y, x) = (byte)actz;
00344 zcount = 0;
00345 }
00346 else
00347 ima(z,y,x)=(byte)actz;
00348 }
00349 if (ycount == masksize.height)
00350 {
00351 if (acty==1 || acty==4)
00352 acty=(acty==1)?4:1;
00353 else if (acty==2 || acty==7)
00354 acty=(acty==2)?7:2;
00355 ycount = 0;
00356 }
00357 }
00358 if (xcount == masksize.depth)
00359 {
00360 actx = (actx==1) ? 2 : 1;
00361 xcount = 0;
00362 }
00363 }
00364 }
00365 else
00366 {
00367 ThrowError("TestPatterns::ColoredGrid ERROR No Colored grid for such a structure element implemented!");
00368 }
00369 }