- Main Page
- Namespaces
- Classes
- Files

- File List
- File Members

# C:/AngioLocalizeNoAuto/MevisLabNoAutoReg/STUMevisApp/Angiolocalize/Modules/Macros/STURegistration2D3D/Registration2D3D.py

    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 #----------------------------------------------------------------------------------
    00036 #! Macro module Registration2D3D
    00037 #/*!
    00038 # \file    Registration2D3D.py
    00039 # \author  Lina Liu and Dimitre Hristov
    00040 # \date    2009-12-10
    00041 #
    00042 #
    00043 #*/
    00044 #----------------------------------------------------------------------------------
    00045
    00046 from mevis import *
    00047 from linear import *
    00048 from math import *
    00049
    00050
    00051 ## Global varibles
    00052 source = None
    00053 dest = None
    00054 srcID = 0
    00055 targetID = 0
    00056 perspectM = ""
    00057 affineM = ""
    00058 postAffineM = ""
    00059
    00060 ## initialize some varibles when window pops up
    00061 def initWindow():
    00062   ctx.field("PatientID").setValue(ctx.parent().field("PatientID").value);
    00063   ctx.field("PatientsName").setValue(ctx.parent().field("PatientsName").value);
    00064   ctx.field("PatientsBirthDate").setValue(ctx.parent().field("PatientsBirthDate").value);
    00065   ctx.field("PatientsSex").setValue(ctx.parent().field("PatientsSex").value);
    00066   ctx.field("ImgLoad2D.autoLoad").touch();
    00067   ctx.field("ImgLoad3D.autoLoad").touch();
    00068   ctx.field("Registration_3D_2D.View2D.ext.annotation.annotationMode").setValue("ANNO_MODE_USER");
    00069   ctx.field("Registration_3D_2D.View2D.ext.annotation.annotationUserBottomLeft").setValue("Timepoint: $(slice) \n$(sizex),$(sizey),$(sizec) \n$(voxelx),$(voxely) \n$(SeriesDescription)");
    00070   ctx.field("Registration_3D_2D.View2D.ext.annotation.showOrientation").setValue("ANNO_ORIENTATION_OFF");
    00071   patientID = getPatientRecordID();
    00072   if (patientID != "0"):
    00073     loadGUILists(patientID);
    00074
    00075 ## cleanUp when windows are closed
    00076 def cleanUp():
    00077   ctx.disconnectField("Registration_3D_2D.Image2D");
    00078   ctx.disconnectField("Registration_3D_2D.Image3D");
    00079   ctx.field("ImgLoad2D.close").touch();
    00080   ctx.field("ImgLoad3D.close").touch();
    00081
    00082 ## send a query to the Database and return the result set
    00083 def sendQuery(query):
    00084   ctx.field("DBConn.Statement").setValue(query);
    00085   dbModule = ctx.module("DBConn");
    00086   result = dbModule.call("sendQuery");
    00087   if (result == -1):
    00088     MLAB.logError("The following query to database failed. \n" + query + "\n.");
    00089   dbModule.call("close");
    00090   return result;
    00091
    00092 ## get the DB record ID for a patient given MRO number
    00093 def getPatientRecordID():
    00094   patientID = 0;
    00095   if (ctx.field("PatientID").value == ""):
    00096     return str(patientID);
    00097   queryString = "SELECT PatientID FROM Patients WHERE MRO = " + "'" + ctx.field("PatientID").value + "'";
    00098   result = sendQuery(queryString);
    00099   if (str(result) != "()"):
    00100     for item in result:
    00101       patientID = item["patientid"];
    00102   return str(patientID);
    00103
    00104 ## load GUI Lists (2D, 3D and registration lists)
    00105 def loadGUILists(patientID):
    00106     load3DImageList(patientID);
    00107     load2DImageList(patientID);
    00108     loadRegItem();
    00109
    00110 ## load 3D image List in GUI
    00111 def load3DImageList(patientID):
    00112     imgList = ctx.controlDebug("list3D");
    00113     imgList.clearItems();
    00114     #init DB
    00115     queryString = "select imageID, modality, seriesDescr from images where imagetype = 2 and patientID = " + patientID + ";";
    00116     result = sendQuery(queryString);
    00117     for item in result:
    00118       imgName = item["imageid"];
    00119       imgM = item["modality"];
    00120       series = item["seriesdescr"];
    00121       imgList.insertItem([str(imgName), imgM, series]);
    00122
    00123 ## load 2D image List in GUI
    00124 def load2DImageList(patientID):
    00125     imgList = ctx.controlDebug("list2D");
    00126     imgList.clearItems();
    00127     #init DB
    00128     queryString = "select imageID, modality, seriesDescr from images where imagetype = 1 and patientID = " + patientID + ";";
    00129     result = sendQuery(queryString);
    00130     for item in result:
    00131       imgName = item["imageid"];
    00132       imgM = item["modality"];
    00133       series = item["seriesdescr"];
    00134       imgList.insertItem([str(imgName), imgM, series]);
    00135
    00136 ## pop up the registration context menu
    00137 def selectRegImg():
    00138    ctx.control("imgRegOp").popup();
    00139
    00140 ## pop up the 3D context menu
    00141 def selectChanged3D():
    00142    ctx.control("popupTgt").popup();
    00143
    00144 ## pop up the 2D context menu
    00145 def selectChanged2D():
    00146    ctx.control("popupSrc").popup();
    00147
    00148 ## select 2D image as source
    00149 def selectAsSource():
    00150   list2D = ctx.control("list2D");
    00151   srcItem = list2D.selectedItem();
    00152   loadImage(srcItem.text(0), 1);
    00153
    00154 ## select 3D image as target
    00155 def selectAsDest():
    00156   list3D = ctx.control("list3D");
    00157   targetItem = list3D.selectedItem();
    00158   loadImage(targetItem.text(0), 2);
    00159
    00160   global targetID;
    00161   global srcID;
    00162   redoOp = False;
    00163
    00164   if (regExist(srcID, targetID)):
    00165     answer = MLAB.showQuestion("The Registration already exists. Do you want to redo or delete?", "", "MeVisLab", ["Redo", "Delete", "Cancel"], 0);
    00166     if (answer== 2):
    00167       return;
    00168     elif (answer == 1):
    00169      deleteReg(srcID, targetID);
    00170      return;
    00171     else:
    00172       redoOp = True;
    00173   if (redoOp == False):
    00174     getInitialRegMatrix();
    00175   global affineM;
    00176   global perspectM;
    00177   global postAffineM;
    00178   register(affineM, perspectM, postAffineM);
    00179
    00180 ## do registration with given AffineMatrix, perspectiveMatrix and postAffine Matrix
    00181 def register(affineM, perspectM, postAffineM):
    00182   ctx.field("ImgLoad3D.load").touch();
    00183   ctx.field("ImgLoad2D.load").touch();
    00184   ctx.connectField("Registration_3D_2D.Image2D", "ImgLoad2D.output0");
    00185   ctx.connectField("Registration_3D_2D.Image3D", "ImgLoad3D.output0");
    00186   wind = ctx.showWindow("Reg2D3DW");
    00187   wind.showMaximized();
    00188   loadMatrices(affineM, perspectM, postAffineM);
    00189
    00190 ## redo the registration
    00191 def redoRegFromPopup():
    00192   regList = ctx.control("registeredImg");
    00193   item = regList.selectedItem();
    00194   global targetID;
    00195   global srcID;
    00196   srcID = item.text(0);
    00197   targetID = item.text(3);
    00198   loadImage(item.text(0),1);
    00199   loadImage(item.text(3),2);
    00200   register(item.text(8),item.text(9),item.text(10));
    00201
    00202 ## load Image as target or source from a given fileName
    00203 def loadImage(imageID, srcOrTgt):
    00204   srcF = getImageFileName(imageID);
    00205   src = os.path.normpath(srcF + ".dcm");
    00206   source = os.path.normpath(src);
    00207   if (srcOrTgt == 1):
    00208     global srcID;
    00209     srcID = imageID;
    00210     if source != None:
    00211       ctx.field("ImgLoad2D.filename").setValue(source);
    00212       ctx.field("ImgLoad2D.load").touch();
    00213     ctx.control("srcLabel").setTitle("Source:" + source);
    00214   else:
    00215     global targetID;
    00216     targetID = imageID;
    00217     if source != None:
    00218       ctx.field("ImgLoad3D.filename").setValue(source);
    00219       ctx.field("ImgLoad2D.load").touch();
    00220     ctx.control("targetLabel").setTitle("Target:" + source);
    00221
    00222 ## check if registration exists
    00223 def regExist(srcID, targetID):
    00224   queryString = "SELECT matrixID as Num, affineM, perspectM, postAffineM FROM REGMATRICES WHERE srcImage = " + str(srcID) + " AND type = 1 AND targetImage = " + str(targetID) + ";";
    00225   result = sendQuery(queryString);
    00226   if (str(result) == "()"):
    00227     return 0;
    00228   number = 0;
    00229   number = result[0]["num"];
    00230   global affineM;
    00231   global postAffineM;
    00232   global perspectM;
    00233   affineM = result[0]["affinem"];
    00234   postAffineM = result[0]["postaffinem"];
    00235   perspectM = result[0]["perspectm"];
    00236   return number;
    00237
    00238 ## generate the initial registration matrix based on Dicom tags
    00239 ## code tested only for the Siemens Artis System and the dynaCT mode.
    00240 ## if different system is used it may have to be rewritten to generate the global matrices
    00241 def getInitialRegMatrix():
    00242   global perspectM;
    00243   global postAffineM;
    00244   global affineM;
    00245
    00246   #image2D=ctx.field("Registration_3D_2D.Image2D");
    00247   dist_source_detector = float((ctx.field("ImgLoad2D.output0").getDicomTagValueByName("DistanceSourceToDetector")));
    00248   dist_source_patient = float(ctx.field("ImgLoad2D.output0").getDicomTagValueByName("DistanceSourceToPatient"));
    00249   rows = float(ctx.field("ImgLoad2D.output0").getDicomTagValueByName("Rows"));
    00250   columns = float(ctx.field("ImgLoad2D.output0").getDicomTagValueByName("Columns"));
    00251
    00252   #get the pixel spacing in x and y directions
    00253   pixel_spacing_string = []
    00254   temp = str(ctx.field("ImgLoad2D.output0").getDicomTagValueByName("PixelSpacing"))
    00255   resume = True
    00256   count = 0
    00257   pixel_spacing_string = ''
    00258   while (resume):
    00259     if (temp[count] == '\\'):
    00260       resume = False
    00261       count = count + 1
    00262     else:
    00263       pixel_spacing_string = pixel_spacing_string + temp[count]
    00264       count = count + 1
    00265   pixel_spacing_x = float(pixel_spacing_string);
    00266
    00267   pixel_spacing_string = ''
    00268   while (count<len(temp)):
    00269     pixel_spacing_string = pixel_spacing_string + temp[count]
    00270     count = count + 1
    00271   pixel_spacing_y = float(pixel_spacing_string);
    00272
    00273   #get the primary and secondary angles
    00274   pAngle = float(ctx.field("ImgLoad2D.output0").getDicomTagValueByName("PositionerPrimaryAngle"));
    00275   sAngle = float(ctx.field("ImgLoad2D.output0").getDicomTagValueByName("PositionerSecondaryAngle"));
    00276
    00277   #assign rotation angles: theta_x, theta_y, theta_z
    00278
    00279   theta_x = -sAngle;
    00280   theta_z =  pAngle;
    00281
    00282   #assign translations
    00283   t_x = 0;
    00284   t_y = 0;
    00285   t_z = dist_source_patient;
    00286
    00287   #find the rotation matrices: R_x, R_table_camera, R_z
    00288   #R_table_camera is used to transform from the table/supine patient coordinate system
    00289   #to one linked with the x-ray source (camera)
    00290   R_x = matrix();
    00291   R_table_camera = matrix();
    00292   R_z = matrix();
    00293   R_x = matrix.fromSeq(R_x,[[1,0,0,0],[0,cos(deg2rad(theta_x)),sin(deg2rad(theta_x)),0],[0,-sin(deg2rad(theta_x)),cos(deg2rad(theta_x)),0],[0,0,0,1]]);
    00294   R_table_camera = matrix.fromSeq(R_table_camera,[[-1,0,0,0],[0,0,-1,0],[0,-1,0,0],[0,0,0,1]]);
    00295   R_z = matrix.fromSeq(R_z,[[cos(deg2rad(theta_z)),sin(deg2rad(theta_z)),0,0],[-sin(deg2rad(theta_z)),cos(deg2rad(theta_z)),0,0],[0,0,1,0],[0,0,0,1]]);
    00296
    00297   #multiply them in the order R_x*R_table_camera*R_z to get the Rotation matrix
    00298   affineM = R_z.multMatrixFromLeft(R_x)
    00299   affineM = affineM.multMatrixFromLeft(R_table_camera)
    00300
    00301   #find the K matrix
    00302   perspectM = matrix();
    00303   perspectM.setElement(0,0,dist_source_detector);
    00304   perspectM.setElement(1,1,dist_source_detector);
    00305   perspectM.setElement(2,2,1);
    00306   perspectM.setElement(3,3,1);
    00307   # Not sure whether x corresponds to columns and y to rows
    00308   perspectM.setElement(0,2,columns*pixel_spacing_x/2);
    00309   perspectM.setElement(1,2,rows*pixel_spacing_y/2);
    00310
    00311   postAffineM=matrix();
    00312   postAffineM.setElement(0,0,-1);
    00313   postAffineM.setElement(0,3,columns*pixel_spacing_x);
    00314
    00315   #find the A matrix
    00316   affineM.setElement(2,3,dist_source_patient);
    00317
    00318 ## load the Affine Matrix, perspective Matrix and post AffineMatrix into Registration_3D_2D module
    00319 def loadMatrices(affineM, perspectM, postAffineM):
    00320   ctx.field("Registration_3D_2D.AffineMatrix").setStringValue(affineM);
    00321   ctx.field("Registration_3D_2D.AffinePostMatrix").setStringValue(postAffineM);
    00322   ctx.field("Registration_3D_2D.PerspectiveMatrix").setStringValue(perspectM);
    00323
    00324 ## delete a registration from registered Image list
    00325 def deleteRegFromPopup():
    00326   regList = ctx.control("registeredImg");
    00327   item = regList.selectedItem();
    00328   deleteReg(item.text(0), item.text(3));
    00329
    00330 ## delete a registration from a database record
    00331 def deleteReg(srcid, targetid):
    00332   query = "select matrixID from regmatrices where srcImage = " + str(srcid) + " AND targetImage = " + str(targetid) + ";";
    00333   result = sendQuery(query);
    00334   regToDel = result[0]["matrixid"];
    00335
    00336   query = "DELETE FROM REGMATRICES WHERE srcImage = " + str(srcid) + " AND targetImage = " + str(targetid);
    00337   result = sendQuery(query);
    00338
    00339   query = "DELETE FROM APPROVALS WHERE objType = 0 and objID = " + str(regToDel) + ";";
    00340   result = sendQuery(query);
    00341   delete2D3DReg(ctx.parent().field("PatientID").value, srcid, targetid);
    00342   loadRegItem();
    00343
    00344 ## retrieve the image file name from a database record ID
    00345 def getImageFileName(imgID):
    00346   queryString = "select imageName, imageDir from images where imageID = " + str(imgID);
    00347   result = sendQuery(queryString);
    00348   imgName = None;
    00349   for item in result:
    00350     imgName = item["imagename"];
    00351   return imgName;
    00352
    00353 ## load registration into the GUI registered image list
    00354 def loadRegItem():
    00355     regImage = ctx.controlDebug("registeredImg");
    00356     regImage.clearItems();
    00357     patientID = getPatientRecordID();
    00358     if (patientID == "0"):
    00359       return;
    00360     queryString = "select b.affineM as matrixA, b.perspectM as matrixB, b.postAffineM as matrixC, b.srcImage as src, a.modality as srcM, a.seriesDescr as srcDesc, c.modality as trgM, c.seriesDescr as tgtDesc, b.targetImage as target , d.approvalStatus as status, to_char(d.approvaldate,'YYYY-MM-DD HH12:MI:SS') as savedTime, b.status as genre from images a, regmatrices b, images c, approvals d where a.imagetype = 1 and c.imagetype = 2 and b.srcImage = a.imageID and b.targetImage = c.imageID and d.objID = b.matrixID and b.type = 1 and a.patientID = " + patientID + ";"
    00361     result = sendQuery(queryString);
    00362     for item in result:
    00363       matrixReg = item["matrixa"];
    00364       perspectiveM = item["matrixb"];
    00365       postAffineM = item["matrixc"];
    00366       srcImg = item["src"];
    00367       tgtImg = item["target"];
    00368       srcMod = item["srcm"];
    00369       srcDesc = item["srcdesc"];
    00370       targetMod = item["trgm"];
    00371       targetDesc = item["tgtdesc"];
    00372       statusNum = item["status"];
    00373       approvalDate = item["savedtime"];
    00374       genreNum = item["genre"];
    00375       status = None;
    00376       genre = None;
    00377       if (statusNum == 0):
    00378         status = "false";
    00379       else:
    00380         status = "true";
    00381       if (genreNum == 0):
    00382         genre = "direct";
    00383       else:
    00384         genre = "inferred";
    00385       regImage.insertItem([str(srcImg), srcMod, srcDesc, str(tgtImg), targetMod, targetDesc,status, genre, approvalDate, matrixReg, perspectiveM, postAffineM]);
    00386
    00387 ## This function is to check if the registration exists and is direct
    00388 def directRegExist(srcID, targetID):
    00389   query = "SELECT matrixID from RegMatrices where srcImage = " + str(srcID) + " and targetImage = " + str(targetID) + " and status = 0;"
    00390   result = sendQuery(query);
    00391   if (str(result) != "()"):
    00392     return True;
    00393   return False;
    00394
    00395 ## propagate the registration to 3D and 3D registration
    00396 ##For example if registration for 3D image 1 and 2 exist, 2 and 3 exist,
    00397 ## we need to infer registration for 1 and 3 and save it into database
    00398 ## the propagation rule is that if the infered pair's registration exists and the status is direct,
    00399 ## we will not overwrite it.
    00400 def propagate(targetID, srcID, approvalStatus, regMatrix):
    00401   queryString = "SELECT targetImage, affineM, approvalStatus, status FROM REGMATRICES, approvals WHERE objID = matrixID and srcImage = " + str(targetID) + " AND type = 0 " + ";";
    00402   result = sendQuery(queryString);
    00403   newTarget = 0;
    00404   for item in result:
    00405      newTarget = item["targetimage"];
    00406      oldApprovalS = item["approvalstatus"];
    00407      Affine = item["affinem"];
    00408      if (directRegExist(srcID, newTarget)):
    00409          continue;
    00410      insertOp = 0;
    00411      status = 1; # status is inferred
    00412      newAffine = regMultiply(regMatrix, Affine);
    00413      regS = newAffine.replace("\n", " ");
    00414      ret = regExist(srcID, newTarget);
    00415      if (ret == 0):
    00416          insertOp = 1;
    00417      newApprovalS = approvalStatus & oldApprovalS;
    00418      regID = saveReg(insertOp, srcID, newTarget, status, regS);
    00419      saveApprovalStatus(regID, newApprovalS, insertOp);
    00420
    00421 ## save or update registration into database
    00422 def saveReg(insertOp, srcID, targetID, status, regS):
    00423  perspectiveMatrix = ctx.field("Registration_3D_2D.PerspectiveMatrix").stringValue();
    00424  perspectS = perspectiveMatrix.replace("\n", " ");
    00425  affineS = regS;
    00426  postAffineMatrix = ctx.field("Registration_3D_2D.AffinePostMatrix").stringValue();
    00427  postAffineS = postAffineMatrix.replace("\n", " ");
    00428  saveProjRegToFile(perspectS,affineS, postAffineS, srcID, targetID, ctx.parent().field("PatientID").value);
    00429  ## affineTransformation regType : 0
    00430  ## perspectiveTransformation regType: 1
    00431  if (insertOp == 1):
    00432    queryS = "INSERT INTO REGMATRICES(srcImage, targetImage, affineM, perspectM, postAffineM, status, type)values(" + str(srcID) + "," + str(targetID) + ",'" + affineS + "'" + ",'" + perspectS + "','"+ postAffineS + "'," + str(status) + ", 1" + ");";
    00433  else:
    00434    queryS = "UPDATE REGMATRICES set status = " + str(status) + "," + "perspectM = " + "'" + perspectS + "'" + " , affineM = '" + affineS + "' , postAffineM = '" + postAffineS + "' where srcImage = " + str(srcID) + " AND targetImage = " + str(targetID) + ";";
    00435  result = sendQuery(queryS);
    00436
    00437  query = "select matrixID from regmatrices where type = 1 and srcImage = " + str(srcID) + " and targetImage = " + str(targetID) + ";";
    00438  result = sendQuery(query);
    00439  imgID = None;
    00440  for item in result:
    00441     imgID = item["matrixid"];
    00442
    00443  return imgID;
    00444
    00445 ## multiply registration matrices of affine Matrix and registration modification
    00446 def regMultiply(regMatrix, Affine):
    00447   ctx.field("Registration_3D_2D.regMultiply.matrixA").setStringValue(regMatrix);
    00448   ctx.field("Registration_3D_2D.regMultiply.matrixB").setStringValue(Affine);
    00449   ctx.field("Registration_3D_2D.regMultiply.operation").setStringValue("Multiply");
    00450   return ctx.field("Registration_3D_2D.regMultiply.outputMatrixC").stringValue();
    00451
    00452 ## save the approval status
    00453 def saveApprovalStatus(imgID, status, insertOp):
    00454  if (insertOp == 0):
    00455    queryS = "Update APPROVALS SET approvalStatus = " + str(status) + " where UserID = 1 AND objType = 0 AND objID = " + str(imgID) + ";";
    00456  else:
    00457    queryS = "INSERT INTO APPROVALS(userID, objID, objType, patientID, approvalStatus)VALUES(1," + str(imgID) + ", 0 , " + getPatientRecordID() + " , " + str(status) + ");";
    00458  result = sendQuery(queryS);
    00459
    00460 ## the function is called when user clicks "save" button
    00461 ## it saves the registration and approval status
    00462 def saveOnRegManual():
    00463   saveRegAndApprovalStatus(0);
    00464
    00465 ## the function is called when user clicks "save and approve" button
    00466 ## it saves the registration and approval status
    00467 def approveOnRegManual():
    00468   saveRegAndApprovalStatus(1);
    00469
    00470 ## save the registration and approval status
    00471 def saveRegAndApprovalStatus(approvalS):
    00472   global srcID;
    00473   global targetID;
    00474   insertOp = 0;
    00475   status = 0;
    00476   if (regExist(srcID, targetID) == 0):
    00477    insertOp = 1;
    00478   affineMatrix = ctx.field("Registration_3D_2D.AffineMatrix").stringValue();
    00479   affineS = affineMatrix.replace("\n", " ");
    00480   imgID = saveReg(insertOp, srcID, targetID, status, affineS);
    00481   saveApprovalStatus(imgID, str(approvalS), insertOp);
    00482   propagate(targetID, srcID, approvalS, affineS);
    00483   ctx.module("Registration_3D_2D").closeWindow();
    00484   loadRegItem();
    00485
    00486
    00487 ## show Help
    00488 def help():
    00489   ctx.showHtmlHelp();
    00490
    00491 ## the function is called when user clicks "cancel" button
    00492 def cancelonRegManual():
    00493   MLAB.log("The user reviewed the image and canceled.");
    00494   ctx.disconnectField("Registration_3D_2D.Image2D");
    00495   ctx.disconnectField("Registration_3D_2D.Image3D");
    00496   ctx.module("Registration_3D_2D").closeWindow();

All Classes Namespaces Files Functions Variables Enumerator Friends