00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #include "mitkPointInteractor.h"
00020 #include <mitkPointOperation.h>
00021 #include <mitkPositionEvent.h>
00022 #include <mitkOperationEvent.h>
00023
00024 #include <mitkDataNode.h>
00025 #include <mitkPointSet.h>
00026 #include <mitkInteractionConst.h>
00027 #include <mitkAction.h>
00028 #include <mitkProperties.h>
00029 #include <vtkLinearTransform.h>
00030 #include <mitkUndoController.h>
00031 #include <mitkStateEvent.h>
00032 #include <mitkState.h>
00033
00034
00035 mitk::PointInteractor::PointInteractor(const char * type, DataNode* dataNode)
00036 : Interactor(type, dataNode), m_LastPosition(0)
00037 {
00038 m_LastPoint.Fill(0);
00039 }
00040
00041 mitk::PointInteractor::~PointInteractor()
00042 {}
00043
00044 void mitk::PointInteractor::SelectPoint(int position)
00045 {
00046 mitk::PointSet* pointSet = dynamic_cast<mitk::PointSet*>(m_DataNode->GetData());
00047 if (pointSet == NULL)
00048 return;
00049 if (pointSet->GetSize()<=0)
00050 return;
00051
00052 mitk::Point3D noPoint;
00053 noPoint.Fill(0);
00054 mitk::PointOperation* doOp = new mitk::PointOperation(OpSELECTPOINT, noPoint, position);
00055 if (m_UndoEnabled)
00056 {
00057 mitk::PointOperation* undoOp = new mitk::PointOperation(OpDESELECTPOINT, noPoint, position);
00058 OperationEvent *operationEvent = new OperationEvent(pointSet, doOp, undoOp);
00059 m_UndoController->SetOperationEvent(operationEvent);
00060 }
00061 pointSet->ExecuteOperation(doOp);
00062 }
00063
00064 void mitk::PointInteractor::DeselectAllPoints()
00065 {
00066 mitk::PointSet* pointSet = dynamic_cast<mitk::PointSet*>(m_DataNode->GetData());
00067 if (pointSet == NULL)
00068 return;
00069
00070 mitk::PointSet::DataType *itkPointSet = pointSet->GetPointSet();
00071 mitk::PointSet::PointsContainer::Iterator it, end;
00072 end = itkPointSet->GetPoints()->End();
00073
00074 for (it = itkPointSet->GetPoints()->Begin(); it != end; it++)
00075 {
00076 int position = it->Index();
00077 PointSet::PointDataType pointData = {0, false, PTUNDEFINED};
00078 itkPointSet->GetPointData(position, &pointData);
00079 if ( pointData.selected )
00080 {
00081 mitk::Point3D noPoint;
00082 noPoint.Fill(0);
00083
00084 mitk::PointOperation* doOp = new mitk::PointOperation(OpDESELECTPOINT, noPoint, position);
00085 if (m_UndoEnabled)
00086 {
00087 mitk::PointOperation* undoOp = new mitk::PointOperation(OpSELECTPOINT, noPoint, position);
00088 OperationEvent *operationEvent = new OperationEvent(pointSet, doOp, undoOp);
00089 m_UndoController->SetOperationEvent(operationEvent);
00090 }
00091 pointSet->ExecuteOperation(doOp);
00092 }
00093 }
00094 }
00095
00096 float mitk::PointInteractor::CanHandleEvent(StateEvent const* stateEvent) const
00097
00098 {
00099 float returnValue = 0;
00100
00101 mitk::PositionEvent const *posEvent = dynamic_cast <const mitk::PositionEvent *> (stateEvent->GetEvent());
00102
00103 if (posEvent == NULL)
00104 {
00105
00106 if (this->GetCurrentState()->GetTransition(stateEvent->GetId())!=NULL)
00107 {
00108 return 0.5;
00109 }
00110 else
00111 {
00112 return 0;
00113 }
00114 }
00115
00116
00117
00118 if (stateEvent->GetEvent()->GetType() == mitk::Type_MouseMove)
00119 {
00120 return 0;
00121 }
00122
00123
00124 if (this->GetCurrentState()->GetTransition(stateEvent->GetId())!=NULL)
00125 {
00126 returnValue = 0.5;
00127 }
00128
00129
00130 mitk::PointSet* pointSet = dynamic_cast<mitk::PointSet*>(m_DataNode->GetData());
00131 if (pointSet == NULL)
00132 return 0;
00133
00134
00135
00136
00137 mitk::Point3D worldPoint = posEvent->GetWorldPosition();
00138 float p[3];
00139 itk2vtk(worldPoint, p);
00140
00141 m_DataNode->GetData()->GetGeometry()->GetVtkTransform()->GetInverse()->TransformPoint(p, p);
00142 vtk2itk(p, worldPoint);
00143
00144 float distance = 5;
00145 int index = pointSet->SearchPoint(worldPoint, distance);
00146 if (index>-1)
00147
00148 {
00149
00150 mitk::PointSet::PointType point;
00151 pointSet->GetPointSet()->GetPoint(index, &point);
00152 returnValue = point.EuclideanDistanceTo(worldPoint);
00153
00154
00155 returnValue = 1 - ( returnValue / distance );
00156 if (returnValue<0 || returnValue>1)
00157 {
00158 itkWarningMacro("Difficulties in calculating Jurisdiction. Check PointInteractor");
00159 return 0;
00160 }
00161
00162
00163 returnValue = 0.5 + (returnValue / 2);
00164
00165 return returnValue;
00166 }
00167 else
00168 {
00169 return returnValue;
00170 }
00171
00172 }
00173
00174
00175 bool mitk::PointInteractor::ExecuteAction( Action* action, mitk::StateEvent const* stateEvent )
00176 {
00177 bool ok = false;
00178
00179
00180 mitk::PointSet* pointSet = dynamic_cast<mitk::PointSet*>(m_DataNode->GetData());
00181 if (pointSet == NULL)
00182 return false;
00183
00184
00185 mitk::PointSet::DataType *itkPointSet = pointSet->GetPointSet();
00186 mitk::PointSet::PointsContainer *itkPoints = itkPointSet->GetPoints();
00187
00188
00189 switch (action->GetActionId())
00190 {
00191 case AcADDPOINT:
00192 {
00193 mitk::PositionEvent const *posEvent = dynamic_cast <const mitk::PositionEvent *> (stateEvent->GetEvent());
00194 if (posEvent == NULL)
00195 return false;
00196
00197 mitk::Point3D itkPoint;
00198 itkPoint = posEvent->GetWorldPosition();
00199
00200
00201
00202 int lastPosition = 0;
00203 if (!itkPoints->empty())
00204 {
00205 mitk::PointSet::PointsIterator it, end;
00206 it = itkPoints->Begin();
00207 end = itkPoints->End();
00208 while( it != end )
00209 {
00210 if (!itkPoints->IndexExists(lastPosition))
00211 break;
00212 ++it;
00213 ++lastPosition;
00214 }
00215 }
00216
00217 PointOperation* doOp = new mitk::PointOperation(OpINSERT, itkPoint, lastPosition);
00218 if (m_UndoEnabled)
00219 {
00220 PointOperation* undoOp = new mitk::PointOperation(OpREMOVE, itkPoint, lastPosition);
00221 OperationEvent *operationEvent = new OperationEvent(pointSet, doOp, undoOp, "Add point");
00222 m_UndoController->SetOperationEvent(operationEvent);
00223 }
00224 pointSet->ExecuteOperation(doOp);
00225 ok = true;
00226 break;
00227 }
00228 case AcDESELECTALL:
00229 this->DeselectAllPoints();
00230 ok = true;
00231 break;
00232 case AcCHECKELEMENT :
00233
00234 {
00235 mitk::PositionEvent const *posEvent = dynamic_cast <const mitk::PositionEvent *> (stateEvent->GetEvent());
00236 if (posEvent != NULL)
00237 {
00238 mitk::Point3D worldPoint = posEvent->GetWorldPosition();
00239
00240 int PRECISION = 4;
00241 mitk::IntProperty *precision = dynamic_cast<IntProperty*>(action->GetProperty("PRECISION"));
00242 if (precision != NULL)
00243 {
00244 PRECISION = precision->GetValue();
00245 }
00246
00247 int position = pointSet->SearchPoint(worldPoint, PRECISION);
00248 if (position>=0)
00249 {
00250 m_LastPosition = position;
00251 worldPoint = pointSet->GetPoint(position);
00252 mitk::Point2D displPoint;
00253 displPoint[0] = worldPoint[0];
00254 displPoint[1] = worldPoint[1];
00255
00256
00257 mitk::PositionEvent const* newPosEvent = new mitk::PositionEvent(posEvent->GetSender(), posEvent->GetType(),
00258 posEvent->GetButton(), posEvent->GetButtonState(), posEvent->GetKey(),
00259 displPoint, worldPoint);
00260 mitk::StateEvent* newStateEvent = new mitk::StateEvent(EIDYES, newPosEvent);
00261
00262 this->HandleEvent( newStateEvent );
00263 ok = true;
00264 }
00265 else
00266 {
00267
00268 mitk::StateEvent* newStateEvent = new mitk::StateEvent(EIDNO, posEvent);
00269 this->HandleEvent( newStateEvent );
00270 ok = true;
00271 }
00272 }
00273 else
00274 {
00275 mitk::DisplayPositionEvent const *disPosEvent = dynamic_cast <const mitk::DisplayPositionEvent *> (stateEvent->GetEvent());
00276 if (disPosEvent != NULL)
00277 {
00278 mitk::StateEvent* newStateEvent = new mitk::StateEvent(EIDNO, posEvent);
00279 this->HandleEvent( newStateEvent );
00280 ok = true;
00281 }
00282 }
00283 }
00284 break;
00285 case AcCHECKSELECTED:
00286
00287 {
00288 mitk::PositionEvent const *posEvent = dynamic_cast <const mitk::PositionEvent *> (stateEvent->GetEvent());
00289 if (posEvent != NULL)
00290 {
00291 mitk::Point3D worldPoint = posEvent->GetWorldPosition();
00292
00293 int PRECISION = 4;
00294 mitk::IntProperty *precision = dynamic_cast<IntProperty*>(action->GetProperty("precision"));
00295 if (precision != NULL)
00296 {
00297 PRECISION = precision->GetValue();
00298 }
00299
00300 int position = pointSet->SearchPoint(worldPoint, PRECISION);
00301 if (position <0)
00302 {
00303
00304 mitk::StateEvent* newStateEvent = new mitk::StateEvent(EIDNO, posEvent);
00305 this->HandleEvent( newStateEvent );
00306 ok = true;
00307 break;
00308 }
00309
00310
00311 unsigned int upos = (unsigned int) position;
00312 if (upos == m_LastPosition)
00313 {
00314 mitk::StateEvent* newStateEvent = new mitk::StateEvent(EIDYES, posEvent);
00315
00316 this->HandleEvent( newStateEvent );
00317 ok = true;
00318 }
00319 else
00320 {
00321
00322 mitk::StateEvent* newStateEvent = new mitk::StateEvent(EIDNO, posEvent);
00323 this->HandleEvent( newStateEvent );
00324 ok = true;
00325 }
00326 }
00327 else
00328 {
00329 mitk::DisplayPositionEvent const *disPosEvent = dynamic_cast <const mitk::DisplayPositionEvent *> (stateEvent->GetEvent());
00330 if (disPosEvent != NULL)
00331 {
00332 mitk::StateEvent* newStateEvent = new mitk::StateEvent(EIDNO, posEvent);
00333 this->HandleEvent( newStateEvent );
00334 ok = true;
00335 }
00336 }
00337 }
00338 break;
00339 case AcINITMOVEMENT:
00340 {
00341 mitk::PositionEvent const *posEvent = dynamic_cast <const mitk::PositionEvent *> (stateEvent->GetEvent());
00342 if (posEvent == NULL)
00343 return false;
00344
00345
00346 m_LastPoint = posEvent->GetWorldPosition();
00347
00348 ok = true;
00349 break;
00350 }
00351
00352 case AcMOVESELECTED:
00353 {
00354 mitk::PositionEvent const *posEvent = dynamic_cast <const mitk::PositionEvent *> (stateEvent->GetEvent());
00355 if (posEvent == NULL)
00356 return false;
00357
00358 mitk::Point3D newPoint;
00359 newPoint = posEvent->GetWorldPosition();
00360
00361 PointOperation* doOp = new mitk::PointOperation(OpMOVE, newPoint, m_LastPosition);
00362
00363
00364 m_DataNode->GetData()->ExecuteOperation(doOp);
00365 ok = true;
00366 break;
00367 }
00368
00369 case AcFINISHMOVEMENT:
00370 {
00371 mitk::PositionEvent const *posEvent = dynamic_cast <const mitk::PositionEvent *> (stateEvent->GetEvent());
00372 if (posEvent == NULL)
00373 return false;
00374
00375
00376
00377 mitk::Point3D newPoint;
00378 newPoint = posEvent->GetWorldPosition();
00379
00380 PointOperation* doOp = new mitk::PointOperation(OpMOVE, newPoint, m_LastPosition);
00381 if ( m_UndoEnabled )
00382 {
00383 PointOperation* undoOp = new mitk::PointOperation(OpMOVE, m_LastPoint, m_LastPosition);
00384 OperationEvent *operationEvent = new OperationEvent( m_DataNode->GetData(), doOp, undoOp, "Move point");
00385 m_UndoController->SetOperationEvent(operationEvent);
00386 }
00387
00388 m_DataNode->GetData()->ExecuteOperation(doOp);
00389
00390
00391
00392 ok = true;
00393 }
00394 break;
00395 case AcCHECKGREATERONE:
00396
00397 {
00398 if (pointSet->GetSize()>1)
00399 {
00400 mitk::StateEvent* newStateEvent = new mitk::StateEvent(EIDYES, stateEvent->GetEvent());
00401 this->HandleEvent( newStateEvent );
00402 ok = true;
00403 }
00404 else
00405 {
00406 mitk::StateEvent* newStateEvent = new mitk::StateEvent(EIDNO, stateEvent->GetEvent());
00407 this->HandleEvent( newStateEvent );
00408 ok = true;
00409 }
00410 }
00411 break;
00412 case AcSELECTANOTHEROBJECT:
00413
00414 {
00415
00416
00417
00418 if (pointSet->GetSize()>0)
00419 {
00420 if (m_LastPosition > 0)
00421 {
00422 this->SelectPoint( m_LastPosition-1 );
00423 }
00424 else
00425 {
00426 m_LastPosition = pointSet->GetSize()-1;
00427 SelectPoint( m_LastPosition );
00428 }
00429 }
00430 ok = true;
00431 }
00432 break;
00433 case AcREMOVEPOINT:
00434 {
00435
00436
00437
00438 m_LastPosition = pointSet->SearchSelectedPoint();
00439
00440 Operation* doOp = new mitk::Operation(OpREMOVEPOINT);
00441 if (m_UndoEnabled)
00442 {
00443 Operation* undoOp = new mitk::Operation(OpINSERTPOINT);
00444 OperationEvent *operationEvent = new OperationEvent(pointSet, doOp, undoOp, "Remove point");
00445 m_UndoController->SetOperationEvent(operationEvent);
00446 }
00447 pointSet->ExecuteOperation(doOp);
00448 ok = true;
00449 }
00450 break;
00451 case AcSELECT:
00452
00453 {
00454 mitk::PositionEvent const *posEvent = dynamic_cast <const mitk::PositionEvent *> (stateEvent->GetEvent());
00455 if (posEvent == NULL)
00456 return false;
00457
00458 mitk::Point3D worldPoint = posEvent->GetWorldPosition();
00459
00460
00461
00462
00463 int position = pointSet->SearchPoint(worldPoint, 0);
00464
00465 if (position>=0)
00466 {
00467 PointOperation* doOp = new mitk::PointOperation(OpSELECTPOINT, worldPoint, position);
00468
00469
00470 if (m_UndoEnabled)
00471 {
00472 PointOperation* undoOp = new mitk::PointOperation(OpDESELECTPOINT, worldPoint, position);
00473 OperationEvent *operationEvent = new OperationEvent(pointSet, doOp, undoOp);
00474 m_UndoController->SetOperationEvent(operationEvent);
00475 }
00476
00477
00478 pointSet->ExecuteOperation(doOp);
00479 ok = true;
00480 }
00481 }
00482 break;
00483 case AcDESELECT:
00484 {
00485 mitk::PositionEvent const *posEvent = dynamic_cast <const mitk::PositionEvent *> (stateEvent->GetEvent());
00486 if (posEvent == NULL)
00487 return false;
00488
00489 mitk::Point3D worldPoint = posEvent->GetWorldPosition();
00490
00491
00492
00493
00494 int position = pointSet->SearchPoint(worldPoint, 0);
00495
00496 if (position>=0)
00497 {
00498 PointOperation* doOp = new mitk::PointOperation(OpDESELECTPOINT, worldPoint, position);
00499
00500
00501 if (m_UndoEnabled)
00502 {
00503 PointOperation* undoOp = new mitk::PointOperation(OpSELECTPOINT, worldPoint, position);
00504 OperationEvent *operationEvent = new OperationEvent(pointSet, doOp, undoOp);
00505 m_UndoController->SetOperationEvent(operationEvent);
00506 }
00507
00508
00509 pointSet->ExecuteOperation(doOp);
00510 ok = true;
00511 }
00512 }
00513 break;
00514 case AcSETSTARTPOINT:
00515 {
00516
00517 Point3D point;
00518 point.Fill(0);
00519 int position = pointSet->SearchSelectedPoint();
00520 if (position >-1)
00521 {
00522 PointOperation* doOp = new mitk::PointOperation(OpSETPOINTTYPE, point, position, true, PTSTART);
00523
00524
00525 if (m_UndoEnabled)
00526 {
00527 PointOperation* undoOp = new mitk::PointOperation(OpSETPOINTTYPE, point, position, true, PTUNDEFINED);
00528 OperationEvent *operationEvent = new OperationEvent(pointSet, doOp, undoOp);
00529 m_UndoController->SetOperationEvent(operationEvent);
00530 }
00531
00532
00533 pointSet->ExecuteOperation(doOp);
00534 ok = true;
00535 }
00536 }
00537 break;
00538 default:
00539 return Superclass::ExecuteAction( action, stateEvent );
00540 }
00541
00542 return ok;
00543
00544 }
00545