- Main Page
- Namespaces
- Classes
- Files

- File List
- File Members

# C:/AngioLocalizeNoAuto/MevisLabNoAutoReg/STUMevisApp/Angiolocalize/Sources/ML/STUChamferMatching/mlChamferMatching.cpp

Go to the documentation of this file.

    00001 /*
    00002 * Copyright (c) 2009 Stanford University, School of Medicine All rights reserved.
    00003 *
    00004 * STANFORD ACADEMIC SOFTWARE LICENSE AGREEMENT
    00005 * FOR AngioLocalize SOURCE CODE:
    00006 *
    00007 * 1.  This is a legal agreement between you, RECIPIENT, and STANFORD UNIVERSITY.
    00008 *       By accepting, receiving, and using AngioLocalize.including any accompanying information, materials or
    00009 *       manuals (Program), you are agreeing to be bound by the terms of this Agreement.
    00010 *       If you do not agree to the terms of this Agreement, promptly return the Program to the STANFORD.
    00011
    00012 * 2.  STANFORD grants to RECIPIENT a royalty-free, nonexclusive, and nontransferable license to use the Program
    00013 *       and accompanying source code furnished hereunder, upon the terms and conditions set out below.
    00014 *       documentation and/or other materials provided with the distribution.
    00015 * 3.  RECIPIENT acknowledges that the Program is a research tool still in the development stage and that
    00016 *       it is being supplied as is, without any accompanying services, support or improvements from STANFORD.
    00017 * 4.  RECIPIENT agrees to use the Program solely for internal non-commercial purposes.
    00018 * 5.  RECIPIENT may create derivatives and further transfer the Program under the following terms and conditions:
    00019 *        A) Recipient agrees to not commercially exploit the Program and agrees all uses will be for non-commercial purposes; and,
    00020 *        B) Recipient may not mark any derivatives with the title of Program and may not to use iPad mark for any derivatives; and,
    00021 *        C) Recipient agrees to mark and acknowledge all derivatives as follows: "This is a derivative work based on AngioLocalize:
    00022 *           Frameless AVM localization with 2D Digital Subtraction Angiography (DSA) and 3D Rotational Angiography (DRA) Images developed
    00023 *           by Dimitre Hristov, Lina Liu.
    00024 *        D) Recipient agrees to make all improvements, enhancements and derivatives available under
    00025 *           similar terms and conditions to the research community.
    00026 * 6.   RECIPIENT warrants that RECIPIENT will not remove or export any part of the software or Program from the United
    00027 *       States except in full compliance with all United States and other applicable laws and regulations.
    00028 * 7.  RECIPIENT will use the Program in compliance with all applicable laws, policies and regulations including, but not
    00029 *       limited to, any approvals, informed consent and patient confidentiality principles.
    00030 * 8.   RECIPIENT will indemnify, hold harmless, and defend Stanford against any claim of any kind arising out of or
    00031 *       related to the exercise of any rights granted under this Agreement or the breach of this Agreement by RECIPIENT.
    00032 * 9.  Title and copyright to the Program and any associated documentation shall at all times remain with STANFORD,
    00033 *       and RECIPIENT agrees to preserve same.
    00034 */
    00035 //----------------------------------------------------------------------------------
    00037
    00045 //----------------------------------------------------------------------------------
    00046
    00047 // Local includes
    00048 #include "mlChamferMatching.h"
    00049
    00050 ML_START_NAMESPACE
    00051
    00052
    00054 ML_BASEOP_CLASS_SOURCE(ChamferMatching, BaseOp);
    00055
    00056 //----------------------------------------------------------------------------------
    00058 //----------------------------------------------------------------------------------
    00059 ChamferMatching::ChamferMatching ()
    00060   : BaseOp(2, 0)
    00061 {
    00062   ML_TRACE_IN("ChamferMatching::ChamferMatching ()");
    00063
    00064   // Suppress calls of handleNotification on field changes to
    00065   // avoid side effects during initialization phase.
    00066   handleNotificationOff();
    00067
    00068    const char * funcNames[] = {
    00069       "Amoeba",                //0
    00070           "Amebsa"
    00071    };
    00072
    00073
    00075   FieldContainer &fields = *getFieldContainer();
    00076
    00077   ML_CHECK(&fields);
    00078
    00079
    00080   _modeFld = fields.addEnum ("algorithms", funcNames, numAlgorithms);
    00081   _modeFld->setEnumValue(amoeba);
    00082
    00083   // Initializes loaded image buffer.
    00084   _inputImage.setData(NULL);
    00085   _inputImage.setBox(SubImgBox());
    00086
    00087   // add all the fields in UI
    00088   _matrix1Fld = fields.addMatrix("matrix1");
    00089   _matrix2Fld = fields.addMatrix("matrix2");
    00090   _matrix3Fld = fields.addMatrix("matrix3");
    00091
    00093   float mat[16];
    00094   for (int i = 0; i< 16; i++) {
    00095           mat[i] = (i%5 == 0)? 1 : 0;
    00096   }
    00097
    00098   _matrixToUse.setValues(mat);
    00099
    00100   _apply1Fld = fields.addBool("apply1");
    00101   _apply1Fld->setBoolValue(true);
    00102   _apply2Fld = fields.addBool("apply2");
    00103   _apply2Fld->setBoolValue(true);
    00104   _apply3Fld = fields.addBool("apply3");
    00105   _apply3Fld->setBoolValue(true);
    00106
    00107   _startFld = fields.addNotify("start");
    00108   _stopFld = fields.addNotify("stop");
    00109   _continueFld = fields.addNotify("continue");
    00110
    00111   _updateFreqFld = fields.addInt("updateFreq");
    00112   _accuracyFld = fields.addFloat("accuracy");
    00113   _iterationsFld = fields.addInt("iterations");
    00114   _temperatureFld = fields.addFloat("Temperature");
    00115   _annealingFld = fields.addFloat("AnnealingConstant");
    00116   _finalCostFld = fields.addFloat("finalCost");
    00117   _numMarkersFld = fields.addInt("numMarkers");
    00118
    00119   (_inMarkerListFld = fields.addBase("inMarkerList"))->setBaseValue(NULL);
    00120
    00121   _inMarkerList = NULL;
    00122   _outMarkerList = NULL;
    00123   _filteredMarkerList = NULL;
    00124   _hasMaskImage = false;
    00125   _input1Img = NULL;
    00126   _maskImg = NULL;
    00127
    00128   // Connect input fields with output field to update connected
    00129   // modules if input images change.
    00130   for (int inIdx=0; inIdx < 0; ++inIdx){
    00131     for (int outIdx=0; outIdx < 0; ++outIdx){
    00132       getInField(inIdx)->attachField(getOutField(outIdx));
    00133     }
    00134   }
    00135
    00136   handleNotificationOn();
    00137 }
    00138
    00139
    00140 //----------------------------------------------------------------------------------
    00144 //----------------------------------------------------------------------------------
    00145 /*double func(VecDoub &x, void *obj)
    00146 {
    00147         ChamferMatching *myObj = (ChamferMatching *)obj;
    00148     return SQR(x[0]) + SQR(x[1]);
    00149 }*/
    00150
    00151
    00152
    00153 //----------------------------------------------------------------------------------
    00155 //----------------------------------------------------------------------------------
    00156 void updateFunc(void *obj)
    00157 {
    00158   ML_TRACE_IN("updateFunc")
    00159   //get the projected XMarkerList
    00160
    00161   ChamferMatching* curr = (ChamferMatching*) obj;
    00162   curr->updateMatrix1Fld();
    00163   curr->updateMatrix2Fld();
    00164  // curr->updateMatrix3Fld();
    00165
    00166 }
    00167
    00168
    00169
    00170 //----------------------------------------------------------------------------------
    00172 //----------------------------------------------------------------------------------
    00173 double cost(VecDoub &x, void *obj)
    00174 {
    00175   ML_TRACE_IN("cost")
    00176
    00177   ChamferMatching* curr = (ChamferMatching*) obj;
    00178
    00179   curr->generateMatrices(x);
    00180   curr->doTransform();
    00181
    00182   XMarkerList *outMarkerList = curr->_outMarkerList;
    00183
    00184   double sum = 0.0;
    00185   int IntMarkerListSize=outMarkerList->getSize();
    00186           for(size_t i = 0; i<IntMarkerListSize; i++) {
    00187                    XMarker *marker = (XMarker*)outMarkerList->getItemAt(i);
    00188                    double *voxelVal = NULL;
    00189                    if (curr->getVoxelValue(0,marker, curr->_input1Img, &voxelVal))
    00190                            sum += *voxelVal;
    00191                    else sum+=(curr->_input1Img)->getMaxVoxelValue(); //
    00192           }
    00193           return sum/IntMarkerListSize;
    00194 }
    00195
    00196 //----------------------------------------------------------------------------------
    00198 //----------------------------------------------------------------------------------
    00199
    00200 Doub test(VecDoub &x)
    00201 {
    00202         return SQR(x[0]) + SQR(x[1]);
    00203 }
    00204
    00205 bool isStopButtonPressed(void *obj)
    00206 {
    00207   Field *field = NULL;
    00208   ChamferMatching* curr = (ChamferMatching*) obj;
    00209
    00210  /* do {
    00211           field = curr->getPressedNotifyField();
    00212          // if (curr->getStopFld() == *field)
    00213           {
    00214             return true;
    00215           }
    00216   } while (field);
    00217
    00218   return false; */
    00219   return true;
    00220 }
    00221
    00222
    00223 //----------------------------------------------------------------------------------
    00225 //----------------------------------------------------------------------------------
    00226 bool ChamferMatching::getVoxelValue(MLint OutIndex, XMarker  *marker, PagedImg *inImg, double ** voxelValue) {
    00227
    00228         vec6 pos = marker->pos;
    00229         float x = pos[0];
    00230         float y = pos[1];
    00231         float z = pos[2];
    00232
    00233         inImg->transformToVoxelCoord(&x, &y, &z);
    00234         Vector imgExt = inImg->getImgExt();
    00235         if (imgExt.x <= x
    00236          || x < 0
    00237          || imgExt.y <= y
    00238          || y < 0
    00239          || imgExt.z <= z
    00240          || z < 0
    00241          || imgExt.c <= pos[3]
    00242          || pos[3] < 0
    00243          || imgExt.t <= pos[4]
    00244          || pos[4] < 0
    00245          || imgExt.u <= pos[5]
    00246          || pos[5] < 0
    00247          )
    00248       {
    00249                   // image out of boundary
    00250                   return false;
    00251                  }
    00252                 // create subimage box consisting only of the voxel
    00253     SubImgBox voxelBox = SubImgBox(Vector((MLint)x, (MLint)y, (MLint)z,
    00254                                               (MLint)(pos[3]),
    00255                                               (MLint)(pos[4]),
    00256                                               (MLint)(pos[5])),
    00257                                        Vector((MLint)x, (MLint)y, (MLint)z,
    00258                                               (MLint)(pos[3]),
    00259                                               (MLint)(pos[4]),
    00260                                               (MLint)(pos[5])));
    00261
    00262         // get voxel value
    00263     getTile(getInOp(OutIndex), getInOpIndex(OutIndex),voxelBox, MLdoubleType, (void **)(voxelValue));
    00264     return true;
    00265 }
    00266
    00267
    00268
    00269 //----------------------------------------------------------------------------------
    00271 //----------------------------------------------------------------------------------
    00272 void ChamferMatching::handleNotification (Field *field)
    00273 {
    00274   ML_TRACE_IN("ChamferMatching::handleNotification ()");
    00275
    00276
    00277   if (field == _inMarkerListFld) {
    00278
    00279       if (ML_BASE_IS_A((static_cast<Base*>(_inMarkerListFld->getBaseValue())), XMarkerList)){
    00280
    00281                   _inMarkerList = static_cast<XMarkerList*>(_inMarkerListFld->getBaseValue());
    00282
    00283                   if (_inMarkerList != NULL){
    00284                         /*if (!_isInNotificationCB) {
    00285                                 _inputList->addNotificationObserver(_csoListNotificationCB, this);
    00286                         }*/
    00287                   }
    00288                 } else {
    00289                   _inMarkerList = NULL;
    00290                 }
    00291   }
    00292
    00293   if (field == _modeFld) {
    00294       if (_modeFld->getEnumValue() < 0 || _modeFld->getEnumValue() >= numAlgorithms) {
    00295                   ML_PRINT_ERROR("ChamferMatching:getAlgorithms", ML_BAD_PARAMETER,
    00296                        "Invalid alogithm parameter passed, using 'Ameoba' instead.");
    00297       }
    00298
    00299   }
    00300
    00301   int mode = _modeFld->getEnumValue();
    00302   if (mode < 0 || mode >= numAlgorithms) {
    00303       mode = amoeba;
    00304     }
    00305
    00306   if (getUpdatedInImg(0) == NULL) {
    00307       // input image is invalid
    00308       return;
    00309   } else {
    00310           _input1Img = getInImg(0);
    00311   }
    00312
    00313   if (getUpdatedInImg(1)) {
    00314           _maskImg = getInImg(1);
    00315           _hasMaskImage = true;
    00316   } else {
    00317           _hasMaskImage = false;
    00318   }
    00319
    00320
    00321
    00322   if (field == _startFld) {
    00323           if (_inMarkerList == NULL){
    00324                   return;
    00325           }
    00326           if (_filteredMarkerList) delete _filteredMarkerList;
    00327           if (_outMarkerList) delete _outMarkerList;
    00328
    00329           getValuesFromUI();
    00330           filter();
    00331           int numOfIter = 0;
    00332           VecDoub x_initial(_elementNum,0.0); // initialize the transformation vector
    00333           VecDoub x(_elementNum,0.0); // initialize the transformation vector
    00334
    00335           if (mode == amoeba ) {
    00337
    00338                 //minimum = am.minimize(x, accuracy, cost, updateFunc, isStopButtonPressed, this);
    00339                 Amoeba am(_accuracy, _iterations, _updateFreq); //initialize the minimization
    00340                 x=am.minimize(x_initial, _DEL, cost, updateFunc, isStopButtonPressed, this);
    00341                 numOfIter = am.nfunc;
    00342
    00343            } else {
    00344
    00346
    00347                 Amebsa<Doub(VecDoub &, void*)> am(x_initial, _DEL, cost, _accuracy, this);
    00348
    00349                 int iter = _iterations/_updateFreq; //initial number of iterations
    00350                 double temp=_temperature; // initial temperature
    00351                 int total_iterations = 0; // cummulative number of iteartions
    00352                 Bool converged = false;
    00353                 while ((temp >= 0)&& (total_iterations < _iterations)&& (!converged)){
    00354                         // try different annealing schedules
    00355                         total_iterations+=iter;
    00356                         converged= am.anneal(iter, temp, this);
    00357                         if (!converged) {
    00358                         temp = _annealing*temp; // cool off
    00359                                 iter = _iterations/_updateFreq; // search more elaborately
    00360                         }
    00361                 }
    00362                 x = am.pb;
    00363           }
    00364           //   update the matrices and the number of iterations taken
    00365           generateMatrices(x);
    00366           updateMatrix1Fld();
    00367           updateMatrix2Fld();
    00368           //float finalobjective = cost(x,this);
    00369           _finalCostFld->setFloatValue(cost(x,this));
    00370           _numMarkersFld->setIntValue(_filteredMarkerList->getSize()); //field capturing how many markers were used for cost calculation
    00371           _finalCostFld->notifyAttachments();
    00372           _numMarkersFld->notifyAttachments();
    00373
    00374
    00375   } // end start action
    00376
    00377
    00378
    00379
    00380   // Handle changes of module parameters and connectors here.
    00381   // For example:
    00382   // if (getInField(0) == field){ /* Handle changes of input 0. */ }
    00383   // if (fieldPtr == field){      /* Handle changes of a field added in constructor .*/ }
    00384   // See section "Implementing handleNotification()" in ML Programming Guide for details.
    00385         BaseOp::handleNotification(field);
    00386 }
    00387
    00388 void ChamferMatching::getValuesFromUI()
    00389 {
    00390
    00391   _affine1TempM =  _matrix1Fld->getMatrixValue();
    00392   _perspectTempM = _matrix2Fld->getMatrixValue();
    00393   _affine2TempM =  _matrix3Fld->getMatrixValue();
    00394   _matrixToUse = _perspectTempM * _affine1TempM;
    00395
    00396   _updateFreq = _updateFreqFld->getIntValue();
    00397   _iterations = _iterationsFld->getIntValue();
    00398   _accuracy = _accuracyFld->getFloatValue();
    00399   _temperature = _temperatureFld->getFloatValue();
    00400   _annealing = _annealingFld->getFloatValue();
    00401
    00402   if (_apply1Fld->getBoolValue() == true){
    00403   // Number of independent transformation variables for projection adjustment only.
    00404         _elementNum = _NUM_AFFINE_PARAMETERS;
    00405
    00406   }
    00407   if (_apply2Fld->getBoolValue() == true){
    00408   // Number of independent transformation variables for rigid body adjustment only.
    00409         _elementNum = _NUM_PROJECTION_PARAMETERS;
    00410   }
    00411   if ((_apply1Fld->getBoolValue() == true)&&(_apply2Fld->getBoolValue() == true)) {
    00412         _elementNum = _NUM_AFFINE_PARAMETERS+ _NUM_PROJECTION_PARAMETERS;
    00413   }
    00414 }
    00415
    00416 //----------------------------------------------------------------------------------
    00418 //----------------------------------------------------------------------------------
    00419 void ChamferMatching::activateAttachments ()
    00420 {
    00421   ML_TRACE_IN("ChamferMatching::activateAttachments ()");
    00422
    00423   // Update members to new field state here.
    00424   // Call super class functionality to enable notification handling again.
    00425   BaseOp::activateAttachments ();
    00426 }
    00427
    00428 //----------------------------------------------------------------------------------
    00430 //----------------------------------------------------------------------------------
    00431 BaseOp::INPUT_HANDLE ChamferMatching::handleInput(int /*inIndex*/, INPUT_STATE /*state*/) const
    00432 {
    00433   ML_TRACE_IN("ChamferMatching::handleInput ()")
    00434
    00435   return INVALIDATE;
    00436 }
    00437
    00438
    00439
    00440 //----------------------------------------------------------------------------------
    00442 //----------------------------------------------------------------------------------
    00443 void ChamferMatching::generateMatrices(NRvector<Doub> x)
    00444 // This method generates pertutbations to the input affine and perspective transforms
    00445 {
    00446         if (x.size() == _NUM_AFFINE_PARAMETERS){
    00447 // Generate affine transformation
    00448
    00449 // Generate perturbations in translations
    00450         mat4 Translations(1,0,0,x[0], 0,1,0,x[1], 0,0,1,x[2], 0, 0, 0,1);
    00451         //_affine1TempM = (_matrix1Fld->getMatrixValue()) * Translations;
    00452
    00453 // Generate 3 rotations corresponding to x[3], x[4] and x[5]
    00454         // x[3] is the rotation angle in radians around the x-axis
    00455         // x[4] is the rotation angle in radians around the y-axis
    00456         // x[5] is the rotation angle in radians around the z-axis
    00457
    00458         // First scale the rotation variables so that they resut in shifts
    00459         // comprable to the translations
    00460
    00461         Vector ImgExt=getInImg(0)->getImgExt();
    00462         MLfloat xscale = ImgExt.x/2.;
    00463         MLfloat yscale = ImgExt.y/2.;
    00464         MLfloat zscale = ImgExt.z/2.;
    00465         getInImg(0)->transformToWorldCoord(&xscale, &yscale, &zscale);
    00466         MLfloat scale = 4.*_DEL /(fabs (xscale) + fabs (yscale));
    00467         // Initiate rotations around the x, y, z, axis
    00468         vec3 axis(1, 0, 0); // x axis
    00469         Rotation RotTemp(axis, x[3] * scale);
    00470         axis.assign(0,1,0); // y axis
    00471         Rotation rot(axis, x[4] * scale); //y axis
    00472         rot *= RotTemp;
    00473         axis.assign(0,0,1); // z axis
    00474         RotTemp.setRotation(axis, x[5]*scale);
    00475         rot *= RotTemp;
    00476         mat4 RotMatrix = rot.getMatrix();
    00477         //_affine1TempM=RotMatrix * _affine1TempM;
    00478         _affine1TempM= (_matrix1Fld->getMatrixValue())*RotMatrix *Translations;
    00479         }
    00480
    00481         if (x.size() == _NUM_AFFINE_PARAMETERS + _NUM_PROJECTION_PARAMETERS){
    00482                 // x[6] is a ux shift in the detector plane
    00483                 // x[7] is a vx shift in the detector plane  (piercing point)
    00484                 _perspectTempM = _matrix2Fld->getMatrixValue();
    00485                 _perspectTempM[0][2]=_perspectTempM[0][2]+x[6]*_perspectTempM[2][2];
    00486                 _perspectTempM[1][2]=_perspectTempM[1][2]+x[7]*_perspectTempM[2][2];
    00487
    00488         } else if (x.size() == _NUM_PROJECTION_PARAMETERS) {
    00489                 _perspectTempM = _matrix2Fld->getMatrixValue();
    00490                 _perspectTempM[0][2]=_perspectTempM[0][2]+x[0]*_perspectTempM[2][2];
    00491                 _perspectTempM[1][2]=_perspectTempM[1][2]+x[1]*_perspectTempM[2][2];
    00492
    00493         }
    00494
    00495 }
    00496
    00497
    00498
    00499 //----------------------------------------------------------------------------------
    00501 //----------------------------------------------------------------------------------
    00502 void   ChamferMatching::doTransform()
    00503 {
    00504     ML_TRACE_IN("ChamferMatching::doTransform")
    00505
    00506         _matrixToUse = _perspectTempM * _affine1TempM;
    00507
    00508         if (_outMarkerList == NULL || _outMarkerList->size() == 0)
    00509                 return;
    00510
    00511         for (size_t i = 0; i < _outMarkerList->getSize(); i ++) {
    00512                 XMarker *marker3D = (XMarker*)_filteredMarkerList->getItemAt(i);
    00513                 XMarker *marker = (XMarker*)_outMarkerList->getItemAt(i);
    00514                 Tvec3<double> markerPos(marker3D->x(), marker3D->y(), marker3D->z());
    00515                 markerPos = (Tvec3<double>(_matrixToUse * markerPos.affinePoint(), true));
    00516                 if (markerPos[2]) {
    00517                         markerPos = markerPos.divideByLastComp();
    00518                         markerPos[2]=0; //set up the z-coordinate to zero. The actual z coordinate is to be picked up
    00519                 }
    00520                 // from the original image via the _affine2Temp matrix
    00521                 markerPos = (Tvec3<double>(_affine2TempM * markerPos.affinePoint(), true));
    00522                 marker->x() = markerPos[0];
    00523                 marker->y() = markerPos[1];
    00524                 marker->z() = markerPos[2];
    00525                 _outMarkerList->modifyItemAt(i, marker);
    00526         }
    00527
    00528 }
    00529
    00530
    00531 //----------------------------------------------------------------------------------
    00533 //----------------------------------------------------------------------------------
    00534 void ChamferMatching::updateMatrix1Fld() {
    00535          ML_TRACE_IN("ChamferMatching::updateMatrix1Fld")
    00536
    00537          _matrix1Fld->setMatrixValue(_affine1TempM);
    00538          _matrix1Fld->notifyAttachments();
    00539 }
    00540
    00541 void ChamferMatching::updateMatrix2Fld() {
    00542          ML_TRACE_IN("ChamferMatching::updateMatrix2Fld")
    00543
    00544          _matrix2Fld->setMatrixValue(_perspectTempM);
    00545          _matrix2Fld->notifyAttachments();
    00546 }
    00547
    00548 void ChamferMatching::updateMatrix3Fld() {
    00549          ML_TRACE_IN("ChamferMatching::updateMatrix3Fld")
    00550
    00551          _matrix3Fld->setMatrixValue(_affine2TempM);
    00552          _matrix3Fld->notifyAttachments();
    00553 }
    00554
    00555
    00556 void ChamferMatching::filter()
    00557 {
    00558         _filteredMarkerList = new XMarkerList();
    00559
    00560         for (size_t i = 0; i < _inMarkerList->getSize(); i ++) {
    00561                 XMarker *tmarker = (XMarker*)_inMarkerList->getItemAt(i);
    00562                 Tvec3<double> markerPos(tmarker->x(), tmarker->y(), tmarker->z());
    00563                 XMarker *marker3D=new XMarker(markerPos);
    00564                 XMarker *marker=new XMarker(markerPos);
    00565                 if (!_hasMaskImage) {
    00566                         _filteredMarkerList->appendItem(*marker3D);
    00567                         }
    00568                 else {
    00569                         markerPos = (Tvec3<double>(_matrixToUse * markerPos.affinePoint(), true));
    00570                         if(markerPos[2]) {
    00571                                 markerPos = markerPos.divideByLastComp();
    00572                                 markerPos[2]=0; //set up the z-coordinate to zero. The actual z coordinate is to be picked up
    00573                                 // from the original image via the _affine2Temp matrix
    00574                         }
    00575                         markerPos = (Tvec3<double>(_affine2TempM * markerPos.affinePoint(), true));
    00576                         marker->x() = markerPos[0];
    00577                         marker->y() = markerPos[1];
    00578                         marker->z() = markerPos[2];
    00579                         double *voxelValue = NULL;
    00580
    00581                         if (getVoxelValue(1,marker, _maskImg, &voxelValue)) {
    00582                                 if (*voxelValue==0) {
    00583                                         // we need to keep this marker from original list
    00584                                         _filteredMarkerList->appendItem(*marker3D);
    00585                                 }
    00586                         }
    00587                         delete marker3D;
    00588                         delete marker;
    00589
    00590                 }
    00591         }
    00592         _outMarkerList = new XMarkerList();
    00593         for (size_t i = 0; i < _filteredMarkerList->getSize(); i ++) {
    00594                 XMarker *marker1=new XMarker();
    00595                 _outMarkerList->appendItem(*marker1);
    00596                 delete marker1;
    00597                 }
    00598 }
    00599 ML_END_NAMESPACE
    00600

All Classes Namespaces Files Functions Variables Enumerator Friends