00001
00002 #include "ContourExtractData.h"
00003
00004
00005
00006 ContourExtractData::ContourExtractData( bool okImagesResults)
00007 {
00008 this->imagedata = NULL;
00009 imagedataValueResult = NULL;
00010 imagedataMaskResult = NULL;
00011 this->okImagesResults = okImagesResults;
00012 _typeOperation = 0;
00013 }
00014
00015
00016
00017 ContourExtractData::~ContourExtractData()
00018 {
00019 }
00020
00021
00022
00023 void ContourExtractData::SetImage( vtkImageData* imagedata)
00024 {
00025 this->imagedata = imagedata;
00026
00027
00028 if (this->okImagesResults==true){ InitVtkImagesResult(); }
00029 }
00030
00031 void ContourExtractData::SetZtoBeAnalys( int z )
00032 {
00033 this->zImage = z;
00034 }
00035
00036
00037 void ContourExtractData::SetLstManualContourModel( std::vector<manualContourModel*> lstManConMod)
00038 {
00039 this->lstManConMod = lstManConMod;
00040 }
00041
00042
00043
00044 void ContourExtractData::GetMinMaxPoint(int *minPoint,
00045 int *maxPoint,
00046 manualContourModel *manualcontourmodel
00047 )
00048 {
00049 int i;
00050
00051
00052
00053
00054 int nps = manualcontourmodel->GetNumberOfPointsSpline();
00055
00056
00057
00058
00059 double x,y,z;
00060
00061 manualcontourmodel->UpdateSpline();
00062 for (i=0; i<nps; i++)
00063 {
00064
00065
00066 manualcontourmodel->GetSpline_i_Point(i,&x,&y,&z);
00067 if (x<minPoint[0]){ minPoint[0]=(int)x; }
00068 if (y<minPoint[1]){ minPoint[1]=(int)y; }
00069 if (x>maxPoint[0]){ maxPoint[0]=(int)x; }
00070 if (y>maxPoint[1]){ maxPoint[1]=(int)y; }
00071 }
00072 minPoint[0]--;
00073 minPoint[1]--;
00074 maxPoint[0]++;
00075 maxPoint[1]++;
00076
00077 }
00078
00079
00080 void ContourExtractData::GetMinMaxPoint_Of_LstManConMod( int *minPoint,
00081 int *maxPoint
00082 )
00083
00084 {
00085 int i,size = lstManConMod.size();
00086 for(i=0 ; i<size ; i++)
00087 {
00088 GetMinMaxPoint(minPoint,maxPoint,lstManConMod[i]);
00089 }
00090 }
00091
00092
00093
00094 int ContourExtractData::AnalisisContourInsideV2(int x, int y, int iContour )
00095 {
00096 bool inBorder=false;
00097 int result = 0;
00098 int i;
00099
00100 int nps=_lstlstlstVecX1[iContour][y].size();
00101
00102 double x1,y1,x2,y2;
00103 double borderX, borderY;
00104 double xx1, yy1,xx2, yy2;
00105 double xx=x, yy=y;
00106 double d;
00107
00108 for (i=0; i<nps; i++)
00109 {
00110 x1=_lstlstlstVecX1[iContour][y][i];
00111 y1=_lstlstlstVecY1[iContour][y][i];
00112 x2=_lstlstlstVecX2[iContour][y][i];
00113 y2=_lstlstlstVecY2[iContour][y][i];
00114
00115 borderX=x1;
00116 borderY=y1;
00117
00118 if (y1<y2)
00119 {
00120 xx1=x1; yy1=y1; xx2=x2; yy2=y2;
00121 } else {
00122 xx1=x2; yy1=y2; xx2=x1; yy2=y1;
00123 }
00124
00125 double difxx2xx1=fabs(xx2-xx1);
00126 if (difxx2xx1==0) difxx2xx1=0.0000000001;
00127
00128
00129 if ( (yy>=yy1)&&(yy<=yy2) )
00130 {
00131
00132 d = ( fabs(xx2-xx1)*(yy-yy1) ) / (yy2-yy1) ;
00133 if ( (xx1<=xx2)&&(x<(xx1+d)) ) { result++; }
00134 if ( (xx1>xx2)&&(x<(xx1-d)) ) { result++; }
00135
00136 if ( (yy2-yy1)/difxx2xx1 >= 1.0)
00137 {
00138 if (xx1<=xx2)
00139 {
00140 borderX = xx1+d;
00141 borderY = y;
00142 } else {
00143 borderX = xx1-d;
00144 borderY = y;
00145 }
00146 }
00147 }
00148
00149
00150
00151 if ( ((xx1<=xx2)&&(xx>=xx1)&&(xx<xx2)) || ((xx1>xx2)&&(xx>=xx2)&&(xx<xx1)) )
00152 {
00153 if ( (yy2-yy1)/difxx2xx1 <= 1.0)
00154 {
00155
00156 d = ( fabs(xx1-xx)*(yy2-yy1) ) / difxx2xx1;
00157 if (yy1+d<=yy2) {
00158 borderX=x;
00159 borderY=yy1+d;
00160 }
00161 }
00162 }
00163
00164
00165
00166 if ( (x==(int)borderX) && (y==(int)borderY) ) { inBorder=true; }
00167
00168
00169 if ( ((int)y1==(int)y2) && ((int)y1==y) && (x1<x2) && (x>=x1) && (x<=x2)) { inBorder=true; }
00170 if ( ((int)y1==(int)y2) && ((int)y1==y) && (x2<x1) && (x>=x2) && (x<=x1)) { inBorder=true; }
00171
00172 if (inBorder==true){ i=nps; }
00173 }
00174
00175 if (inBorder==true) { result=1; }
00176
00177 return result;
00178 }
00179
00180
00181
00182
00183 bool ContourExtractData::isInside(int x, int y, int typeOperation)
00184 {
00185 bool result = false;
00186 int numberLeft = 0;
00187 int i,size = this->lstManConMod.size();
00188 int numberInside = 0;
00189
00190 int ext[6];
00191 imagedata->GetExtent(ext);
00192
00193 if ((x>=0) && (x<=ext[1]) && (y>=0) && (y<=ext[3]))
00194 {
00195
00196 if (typeOperation==0)
00197 {
00198 for (i=0;i<size;i++)
00199 {
00200 numberLeft = AnalisisContourInsideV2(x,y, i );
00201 if ( (numberLeft % 2) ==1){ numberInside++; }
00202 }
00203 if ( numberInside == (size) ){ result=true; }
00204 }
00205
00206
00207 if (typeOperation==1)
00208 {
00209 for (i=0;i<size;i++)
00210 {
00211 numberLeft = AnalisisContourInsideV2(x,y, i );
00212 if ( (numberLeft % 2) ==1){ result=true; }
00213 }
00214 }
00215
00216 if (typeOperation==2)
00217 {
00218 for (i=0;i<size;i++)
00219 {
00220 numberLeft = numberLeft + AnalisisContourInsideV2(x,y, i );
00221 }
00222 if ( numberLeft % 2 ==1){ result = true; }
00223 }
00224
00225
00226
00227 }
00228
00229 return result;
00230 }
00231
00232
00233
00234 double ContourExtractData::GetDataValue(int x, int y, int z)
00235 {
00236
00237
00238
00239
00240
00241 double result;
00242 void *p;
00243 p = imagedata->GetScalarPointer(x,y,z);
00244
00245 if (imagedata->GetScalarType()==VTK_CHAR)
00246 {
00247 char *pp = (char*)p;
00248 result = (double)(*pp);
00249 }
00250 else if (imagedata->GetScalarType()==VTK_SIGNED_CHAR)
00251 {
00252 signed char *pp = (signed char*)p;
00253 result = (double)(*pp);
00254 }
00255 else if (imagedata->GetScalarType()==VTK_UNSIGNED_CHAR)
00256 {
00257 unsigned char *pp = (unsigned char*)p;
00258 result = (double)(*pp);
00259 }
00260 else if (imagedata->GetScalarType()==VTK_SHORT)
00261 {
00262 short *pp = (short*)p;
00263 result = (double)(*pp);
00264 }
00265 else if (imagedata->GetScalarType()==VTK_UNSIGNED_SHORT)
00266 {
00267 unsigned short *pp = (unsigned short*)p;
00268 result = (double)(*pp);
00269 }
00270 else if (imagedata->GetScalarType()==VTK_INT)
00271 {
00272 int *pp = (int*)p;
00273 result = (double)(*pp);
00274 }
00275 else if (imagedata->GetScalarType()==VTK_UNSIGNED_INT)
00276 {
00277 unsigned int *pp = (unsigned int*)p;
00278 result = (double)(*pp);
00279 }
00280 else if (imagedata->GetScalarType()==VTK_LONG)
00281 {
00282 long *pp = (long*)p;
00283 result = (double)(*pp);
00284 }
00285 else if (imagedata->GetScalarType()==VTK_UNSIGNED_LONG)
00286 {
00287 unsigned long *pp = (unsigned long*)p;
00288 result = (double)(*pp);
00289 }
00290 else if (imagedata->GetScalarType()==VTK_FLOAT)
00291 {
00292 float *pp = (float*)p;
00293 result = (double)(*pp);
00294 }
00295 else if (imagedata->GetScalarType()==VTK_DOUBLE)
00296 {
00297 double *pp = (double*)p;
00298 result = (double)(*pp);
00299 }
00300
00301 return result;
00302 }
00303
00304
00305
00306 void ContourExtractData::PutVtkImageDataResultValue( int x, int y, int z, double value )
00307 {
00308 unsigned short *pValue;
00309 unsigned short *pMask;
00310 pValue = (unsigned short *)imagedataValueResult->GetScalarPointer(x,y,z);
00311 pMask = (unsigned short *)imagedataMaskResult->GetScalarPointer(x,y,z);
00312 *pMask = 255;
00313 *pValue = (unsigned short)value;
00314 }
00315
00316
00317 void ContourExtractData::ResetImageResult(int z)
00318 {
00319 if (okImagesResults==true)
00320 {
00321 unsigned short *pValue;
00322 unsigned short *pMask;
00323 pValue = (unsigned short *)imagedataValueResult->GetScalarPointer(0,0,z);
00324 pMask = (unsigned short *)imagedataMaskResult->GetScalarPointer(0,0,z);
00325
00326 int ext[6];
00327 imagedataValueResult->GetExtent(ext);
00328
00329 int size = (ext[1]-ext[0]+1) * (ext[3]-ext[2]+1);
00330 memset(pValue,0,size*2);
00331 memset(pMask,0,size*2);
00332 }
00333 }
00334
00335
00336
00337 void ContourExtractData::CalculateImageResult()
00338 {
00339 if (okImagesResults==true)
00340 {
00341 ResetImageResult(zImage);
00342
00343 int minPoint[2];
00344 int maxPoint[2];
00345 int i,j;
00346 double value;
00347
00348 minPoint[0] = 999999;
00349 minPoint[1] = 999999;
00350 maxPoint[0] = -999999;
00351 maxPoint[1] = -999999;
00352
00353 GetMinMaxPoint_Of_LstManConMod(minPoint,maxPoint);
00354 InitLstContoursLinesYPoints();
00355
00356 for (j=minPoint[1]; j<=maxPoint[1]; j++)
00357 {
00358 for (i=minPoint[0]; i<=maxPoint[0]; i++)
00359 {
00360 if (isInside(i,j,_typeOperation)==true)
00361 {
00362 value = GetDataValue(i,j,zImage);
00363 PutVtkImageDataResultValue(i,j,zImage, value );
00364 }
00365 }
00366 }
00367
00368
00369 imagedataValueResult->Modified();
00370 imagedataMaskResult->Modified();
00371 imagedataValueResult->Update();
00372 imagedataMaskResult->Update();
00373 }
00374
00375 }
00376
00377
00378 void ContourExtractData::GetValuesInsideCrown(std::vector<double> *pLstValue,
00379 std::vector<double> *pLstValuePosX,
00380 std::vector<double> *pLstValuePosY,
00381 std::vector<double> *pLstValuePosZ)
00382 {
00383 pLstValue->clear();
00384 pLstValuePosX->clear();
00385 pLstValuePosY->clear();
00386 pLstValuePosZ->clear();
00387
00388
00389
00390
00391
00392
00393 int minPoint[2];
00394 int maxPoint[2];
00395 int i,j;
00396 double value;
00397
00398
00399 minPoint[0] = 999999;
00400 minPoint[1] = 999999;
00401 maxPoint[0] = -999999;
00402 maxPoint[1] = -999999;
00403
00404 GetMinMaxPoint_Of_LstManConMod(minPoint,maxPoint);
00405 InitLstContoursLinesYPoints();
00406
00407 for (j=minPoint[1]; j<=maxPoint[1]; j++)
00408 {
00409 for (i=minPoint[0]; i<=maxPoint[0]; i++)
00410 {
00411 if (isInside(i,j,_typeOperation)==true)
00412 {
00413 value = GetDataValue(i,j,zImage);
00414
00415
00416
00417
00418
00419
00420 pLstValue -> push_back( value );
00421 pLstValuePosX -> push_back( i );
00422 pLstValuePosY -> push_back( j );
00423 pLstValuePosZ -> push_back( -1 );
00424 }
00425 }
00426 }
00427
00428
00429
00430
00431
00432
00433
00434
00435
00436 }
00437
00438
00439
00440 vtkImageData *ContourExtractData::GetVtkImageValueResult()
00441 {
00442 return imagedataValueResult;
00443 }
00444
00445 vtkImageData *ContourExtractData::GetVtkImageMaskResult()
00446 {
00447 return imagedataMaskResult;
00448 }
00449
00450 void ContourExtractData::InitVtkImagesResult()
00451 {
00452 int ext[6];
00453 int newDim[3];
00454 double spc[3];
00455 int scalartype;
00456
00457 imagedata->GetSpacing(spc);
00458 imagedata->GetExtent(ext);
00459 newDim[0]=ext[1]-ext[0]+1;
00460 newDim[1]=ext[3]-ext[2]+1;
00461 newDim[2]=ext[5]-ext[4]+1;
00462 scalartype = imagedata->GetScalarType();
00463
00464 if (imagedataValueResult!=NULL)
00465 {
00466 imagedataValueResult->Delete();
00467 }
00468 imagedataValueResult = vtkImageData::New();
00469
00470 imagedataValueResult->SetScalarTypeToUnsignedShort();
00471 imagedataValueResult->SetSpacing(spc);
00472 imagedataValueResult->SetDimensions( newDim );
00473 imagedataValueResult->AllocateScalars();
00474
00475 if (imagedataMaskResult!=NULL)
00476 {
00477 imagedataMaskResult->Delete();
00478 }
00479 imagedataMaskResult = vtkImageData::New();
00480
00481 imagedataMaskResult->SetScalarTypeToUnsignedShort();
00482 imagedataMaskResult->SetSpacing(spc);
00483 imagedataMaskResult->SetDimensions( newDim );
00484 imagedataMaskResult->AllocateScalars();
00485 }
00486
00487
00488
00489 void ContourExtractData::InitVolumeStatistics()
00490 {
00491 vol_rCountRange = 0;
00492 vol_rsize = 0;
00493 vol_minValue = 9999999;
00494 vol_maxValue =-9999999;
00495 vol_acum_average = 0;
00496 vol_acum_standardeviation = 0;
00497 }
00498
00499
00500 void ContourExtractData::SetVolumeStatistics(int rCountRange,
00501 int rsize,
00502 double minValue,
00503 double maxValue,
00504 double acum_average,
00505 double acum_standardeviation)
00506 {
00507 vol_rCountRange = vol_rCountRange + rCountRange;
00508 vol_rsize = vol_rsize + rsize;
00509
00510 if (minValue<vol_minValue){ vol_minValue = minValue; }
00511 if (maxValue>vol_maxValue){ vol_maxValue = maxValue; }
00512
00513 vol_acum_average = vol_acum_average + acum_average;
00514 vol_acum_standardeviation = vol_acum_standardeviation + acum_standardeviation;
00515 }
00516
00517
00518 void ContourExtractData::GetVolumeStatistics(int *vol_rCountRange,
00519 int *vol_rsize,
00520 double *vol_minValue,
00521 double *vol_maxValue,
00522 double *vol_average,
00523 double *vol_standardeviation)
00524 {
00525 *vol_rCountRange = this->vol_rCountRange;
00526 *vol_rsize = this->vol_rsize;
00527 *vol_minValue = this->vol_minValue;
00528 *vol_maxValue = this->vol_maxValue;
00529 *vol_average = this->vol_acum_average / this->vol_rsize;
00530 *vol_standardeviation = sqrt(this->vol_acum_standardeviation / this->vol_rsize);
00531 }
00532
00533
00534
00535 void ContourExtractData::Statistics( std::vector<double> *inputLstValue,
00536 int grayRangeMin,
00537 int grayRangeMax,
00538 int *rCountRange,
00539 int *rsize,
00540 double *rmin,
00541 double *rmax,
00542 double *raverage,
00543 double *rstandardeviation
00544 )
00545 {
00546 double min = 0;
00547 double max = 0;
00548 double average = 0;
00549 double standardeviation = 0;
00550 double acum_average = 0;
00551 double acum_standardeviation = 0;
00552 int size = 0;
00553 int countRange = 0;
00554 double ng;
00555
00556 if (inputLstValue!=NULL)
00557 {
00558 size=inputLstValue->size();
00559 if (size>0){
00560 max=(*inputLstValue)[0];
00561 min=(*inputLstValue)[0];
00562
00563 int i;
00564 for ( i=0; i<size; i++ )
00565 {
00566 ng=(*inputLstValue)[i];
00567 acum_average = acum_average + ng;
00568 if (max<ng) max=ng;
00569 if (min>ng) min=ng;
00570 if ((ng>=grayRangeMin) && (ng<=grayRangeMax)) countRange++;
00571 }
00572 average = acum_average / size;
00573
00574
00575 acum_standardeviation=0;
00576 double tmp;
00577 for ( i=0; i<size; i++ )
00578 {
00579 tmp = (*inputLstValue)[i] - average;
00580 acum_standardeviation = acum_standardeviation + tmp*tmp;
00581 }
00582 standardeviation = sqrt(acum_standardeviation/size);
00583 SetVolumeStatistics(countRange, size,
00584 min,max,
00585 acum_average,acum_standardeviation);
00586 }
00587 }
00588
00589
00590 *rsize = size;
00591 *rCountRange = countRange;
00592 *rmin = min;
00593 *rmax = max;
00594 *raverage = average;
00595 *rstandardeviation = standardeviation;
00596 }
00597
00598
00599 void ContourExtractData::SetTypeOperation(int type)
00600 {
00601 _typeOperation=type;
00602 }
00603
00604
00605 void ContourExtractData::Fill_lstlstlstVecXY(int iContour, int sizeY)
00606 {
00607 int i,y;
00608 double x1,y1,z1,x2,y2,z2;
00609 manualContourModel *manualcontourmodel= lstManConMod[iContour];
00610 int nps = manualcontourmodel->GetNumberOfPointsSpline();
00611 manualcontourmodel->UpdateSpline();
00612
00613
00614 for (y=0;y<sizeY;y++)
00615 {
00616 manualcontourmodel->GetSpline_i_Point(0,&x1,&y1,&z1);
00617 x1=x1+0.5; y1=y1+0.5;
00618 for (i=1; i<nps; i++)
00619 {
00620 manualcontourmodel->GetSpline_i_Point(i,&x2,&y2,&z2);
00621 x2=x2+0.5; y2=y2+0.5;
00622 if ( ((y1<y2)&&(y>=y1)&&(y<=y2)) || ((y1>y2)&&(y>=y2)&&(y<=y1)) || ((int)y1==y) || ((int)y2==y) )
00623 {
00624 _lstlstlstVecX1[iContour][y].push_back(x1);
00625 _lstlstlstVecY1[iContour][y].push_back(y1);
00626 _lstlstlstVecX2[iContour][y].push_back(x2);
00627 _lstlstlstVecY2[iContour][y].push_back(y2);
00628 }
00629 x1=x2; y1=y2; z1=z2;
00630 }
00631 }
00632
00633 }
00634
00635 void ContourExtractData::InitLstContoursLinesYPoints()
00636 {
00637
00638 int i;
00639
00640 _lstlstlstVecX1.clear();
00641 _lstlstlstVecY1.clear();
00642 _lstlstlstVecX2.clear();
00643 _lstlstlstVecY2.clear();
00644
00645 int ext[6];
00646 this->imagedata->GetWholeExtent(ext);
00647 int sizeY = ext[3]-ext[2]+1;
00648 std::vector<double> vecDouble;
00649 std::vector< std::vector<double> > vecVecDouble;
00650 for ( i=0 ; i<sizeY ; i++ )
00651 {
00652 vecVecDouble.push_back( vecDouble );
00653 }
00654
00655
00656 int sizeContours = lstManConMod.size();
00657 for( i=0 ; i<sizeContours ; i++ )
00658 {
00659 _lstlstlstVecX1.push_back( vecVecDouble );
00660 _lstlstlstVecY1.push_back( vecVecDouble );
00661 _lstlstlstVecX2.push_back( vecVecDouble );
00662 _lstlstlstVecY2.push_back( vecVecDouble );
00663 Fill_lstlstlstVecXY(i,sizeY);
00664 }
00665
00666 }
00667
00668