Пример #1
0
void
PlaneGeometry::InitializeStandardPlane( const Vector3D &rightVector,
  const Vector3D &downVector, const Vector3D *spacing )
{
  InitializeStandardPlane( rightVector.GetVnlVector(),
    downVector.GetVnlVector(), spacing );
}
Пример #2
0
bool mitk::SegTool2D::DetermineAffectedImageSlice( const Image* image, const PlaneGeometry* plane, int& affectedDimension, int& affectedSlice )
{
  assert(image);
  assert(plane);

  // compare normal of plane to the three axis vectors of the image
  Vector3D normal       = plane->GetNormal();
  Vector3D imageNormal0 = image->GetSlicedGeometry()->GetAxisVector(0);
  Vector3D imageNormal1 = image->GetSlicedGeometry()->GetAxisVector(1);
  Vector3D imageNormal2 = image->GetSlicedGeometry()->GetAxisVector(2);

  normal.Normalize();
  imageNormal0.Normalize();
  imageNormal1.Normalize();
  imageNormal2.Normalize();

  imageNormal0.SetVnlVector( vnl_cross_3d<ScalarType>(normal.GetVnlVector(),imageNormal0.GetVnlVector()) );
  imageNormal1.SetVnlVector( vnl_cross_3d<ScalarType>(normal.GetVnlVector(),imageNormal1.GetVnlVector()) );
  imageNormal2.SetVnlVector( vnl_cross_3d<ScalarType>(normal.GetVnlVector(),imageNormal2.GetVnlVector()) );

  double eps( 0.00001 );
  // axial
  if ( imageNormal2.GetNorm() <= eps )
  {
    affectedDimension = 2;
  }
  // sagittal
  else if ( imageNormal1.GetNorm() <= eps )
  {
    affectedDimension = 1;
  }
  // frontal
  else if ( imageNormal0.GetNorm() <= eps )
  {
    affectedDimension = 0;
  }
  else
  {
    affectedDimension = -1; // no idea
    return false;
  }

  // determine slice number in image
  BaseGeometry* imageGeometry = image->GetGeometry(0);
  Point3D testPoint = imageGeometry->GetCenter();
  Point3D projectedPoint;
  plane->Project( testPoint, projectedPoint );

  Point3D indexPoint;

  imageGeometry->WorldToIndex( projectedPoint, indexPoint );
  affectedSlice = ROUND( indexPoint[affectedDimension] );
  MITK_DEBUG << "indexPoint " << indexPoint << " affectedDimension " << affectedDimension << " affectedSlice " << affectedSlice;

  // check if this index is still within the image
  if ( affectedSlice < 0 || affectedSlice >= static_cast<int>(image->GetDimension(affectedDimension)) ) return false;

  return true;
}
Пример #3
0
void
PlaneGeometry::InitializeStandardPlane( mitk::ScalarType width,
  ScalarType height, const Vector3D &rightVector, const Vector3D &downVector,
  const Vector3D *spacing )
{
  InitializeStandardPlane(
    width, height,
    rightVector.GetVnlVector(), downVector.GetVnlVector(),
    spacing );
}
Пример #4
0
bool
PlaneGeometry::IntersectionLine(
  const PlaneGeometry* plane, Line3D& crossline ) const
{
  Vector3D normal = this->GetNormal();
  normal.Normalize();

  Vector3D planeNormal = plane->GetNormal();
  planeNormal.Normalize();

  Vector3D direction = itk::CrossProduct( normal, planeNormal );

  if ( direction.GetSquaredNorm() < eps )
    return false;

  crossline.SetDirection( direction );

  double N1dN2 = normal * planeNormal;
  double determinant = 1.0 - N1dN2 * N1dN2;

  Vector3D origin = this->GetOrigin().GetVectorFromOrigin();
  Vector3D planeOrigin = plane->GetOrigin().GetVectorFromOrigin();

  double d1 = normal * origin;
  double d2 = planeNormal * planeOrigin;

  double c1 = ( d1 - d2 * N1dN2 ) / determinant;
  double c2 = ( d2 - d1 * N1dN2 ) / determinant;

  Vector3D p = normal * c1 + planeNormal * c2;
  crossline.GetPoint().GetVnlVector() = p.GetVnlVector();

  return true;
}
Пример #5
0
void
PlaneGeometry::InitializePlane( const Point3D &origin,
  const Vector3D &normal )
{
  VnlVector rightVectorVnl(3), downVectorVnl;

  if( Equal( normal[1], 0.0f ) == false )
  {
    FillVector3D( rightVectorVnl, 1.0f, -normal[0]/normal[1], 0.0f );
    rightVectorVnl.normalize();
  }
  else
  {
    FillVector3D( rightVectorVnl, 0.0f, 1.0f, 0.0f );
  }
  downVectorVnl = vnl_cross_3d( normal.GetVnlVector(), rightVectorVnl );
  downVectorVnl.normalize();

  InitializeStandardPlane( rightVectorVnl, downVectorVnl );

  SetOrigin(origin);
}
Пример #6
0
void mitk::VectorImageMapper2D::Paint( mitk::BaseRenderer * renderer )
{
  //std::cout << "2d vector mapping..." << std::endl;

  bool visible = true;
  GetDataNode()->GetVisibility(visible, renderer, "visible");

  if ( !visible )
    return ;

  mitk::Image::Pointer input = const_cast<mitk::Image*>( this->GetInput() );

  if ( input.IsNull() )
    return ;


  mitk::PlaneGeometry::Pointer worldPlaneGeometry2D = dynamic_cast< mitk::PlaneGeometry*>( const_cast<mitk::Geometry2D*>( renderer->GetCurrentWorldGeometry2D() ) );
  assert( worldPlaneGeometry2D.IsNotNull() );

  vtkImageData* vtkImage = input->GetVtkImageData( this->GetCurrentTimeStep( input, renderer ) );

  //
  // set up the cutter orientation according to the current geometry of
  // the renderers plane
  //
  Point3D point;
  Vector3D normal;
  Geometry2D::ConstPointer worldGeometry = renderer->GetCurrentWorldGeometry2D();
  PlaneGeometry::ConstPointer worldPlaneGeometry = dynamic_cast<const PlaneGeometry*>( worldGeometry.GetPointer() );

  if ( worldPlaneGeometry.IsNotNull() )
  {
    // set up vtkPlane according to worldGeometry
    point = worldPlaneGeometry->GetOrigin();
    normal = worldPlaneGeometry->GetNormal(); normal.Normalize();
    m_Plane->SetTransform( (vtkAbstractTransform*)NULL );
  }
  else
  {
    itkWarningMacro( << "worldPlaneGeometry is NULL!" );
    return ;
  }

  double vp[ 3 ], vp_slice[ 3 ], vnormal[ 3 ];
  vnl2vtk( point.GetVnlVector(), vp );
  vnl2vtk( normal.GetVnlVector(), vnormal );
  //std::cout << "Origin: " << vp[0] <<" "<< vp[1] <<" "<< vp[2] << std::endl;
  //std::cout << "Normal: " << vnormal[0] <<" "<< vnormal[1] <<" "<< vnormal[2] << std::endl;

  //normally, we would need to transform the surface and cut the transformed surface with the cutter.
  //This might be quite slow. Thus, the idea is, to perform an inverse transform of the plane instead.
  //@todo It probably does not work for scaling operations yet:scaling operations have to be
  //dealed with after the cut is performed by scaling the contour.
  vtkLinearTransform * vtktransform = GetDataNode() ->GetVtkTransform();

  vtkTransform* world2vtk = vtkTransform::New();
  world2vtk->Identity();
  world2vtk->Concatenate(vtktransform->GetLinearInverse());
  double myscale[3];
  world2vtk->GetScale(myscale);
  world2vtk->PostMultiply();
  world2vtk->Scale(1/myscale[0],1/myscale[1],1/myscale[2]);
  world2vtk->TransformPoint( vp, vp );
  world2vtk->TransformNormalAtPoint( vp, vnormal, vnormal );
  world2vtk->Delete();

    // vtk works in axis align coords
  // thus the normal also must be axis align, since
  // we do not allow arbitrary cutting through volume
  //
  // vnormal should already be axis align, but in order
  // to get rid of precision effects, we set the two smaller
  // components to zero here
  int dims[3];
  vtkImage->GetDimensions(dims);
  double spac[3];
  vtkImage->GetSpacing(spac);
  vp_slice[0] = vp[0];
  vp_slice[1] = vp[1];
  vp_slice[2] = vp[2];
  if(fabs(vnormal[0]) > fabs(vnormal[1]) && fabs(vnormal[0]) > fabs(vnormal[2]) )
  {
    if(fabs(vp_slice[0]/spac[0]) < 0.4)
      vp_slice[0] = 0.4*spac[0];
    if(fabs(vp_slice[0]/spac[0]) > (dims[0]-1)-0.4)
      vp_slice[0] = ((dims[0]-1)-0.4)*spac[0];
    vnormal[1] = 0;
    vnormal[2] = 0;
  }

  if(fabs(vnormal[1]) > fabs(vnormal[0]) && fabs(vnormal[1]) > fabs(vnormal[2]) )
  {
    if(fabs(vp_slice[1]/spac[1]) < 0.4)
      vp_slice[1] = 0.4*spac[1];
    if(fabs(vp_slice[1]/spac[1]) > (dims[1]-1)-0.4)
      vp_slice[1] = ((dims[1]-1)-0.4)*spac[1];
    vnormal[0] = 0;
    vnormal[2] = 0;
  }

  if(fabs(vnormal[2]) > fabs(vnormal[1]) && fabs(vnormal[2]) > fabs(vnormal[0]) )
  {
    if(fabs(vp_slice[2]/spac[2]) < 0.4)
      vp_slice[2] = 0.4*spac[2];
    if(fabs(vp_slice[2]/spac[2]) > (dims[2]-1)-0.4)
      vp_slice[2] = ((dims[2]-1)-0.4)*spac[2];
    vnormal[0] = 0;
    vnormal[1] = 0;
  }


  m_Plane->SetOrigin( vp_slice );
  m_Plane->SetNormal( vnormal );

  vtkPolyData* cuttedPlane;
  if(!( (dims[0] == 1 && vnormal[0] != 0) ||
        (dims[1] == 1 && vnormal[1] != 0) ||
        (dims[2] == 1 && vnormal[2] != 0) ))
  {
    m_Cutter->SetCutFunction( m_Plane );
    m_Cutter->SetInputData( vtkImage );
    m_Cutter->GenerateCutScalarsOff();//!
    m_Cutter->Update();
    cuttedPlane = m_Cutter->GetOutput();
  }
  else
  {
    // cutting of a 2D-Volume does not work,
    // so we have to build up our own polydata object
    cuttedPlane = vtkPolyData::New();
    vtkPoints* points = vtkPoints::New();
    points->SetNumberOfPoints(vtkImage->GetNumberOfPoints());
    for(int i=0; i<vtkImage->GetNumberOfPoints(); i++)
      points->SetPoint(i, vtkImage->GetPoint(i));
    cuttedPlane->SetPoints(points);
    vtkFloatArray* pointdata = vtkFloatArray::New();
    int comps  = vtkImage->GetPointData()->GetScalars()->GetNumberOfComponents();
    pointdata->SetNumberOfComponents(comps);
    int tuples = vtkImage->GetPointData()->GetScalars()->GetNumberOfTuples();
    pointdata->SetNumberOfTuples(tuples);
    for(int i=0; i<tuples; i++)
      pointdata->SetTuple(i,vtkImage->GetPointData()->GetScalars()->GetTuple(i));
    pointdata->SetName( "vector" );
    cuttedPlane->GetPointData()->AddArray(pointdata);
  }

  if ( cuttedPlane->GetNumberOfPoints() != 0)
  {
    //
    // make sure, that we have point data with more than 1 component (as vectors)
    //
    vtkPointData * pointData = cuttedPlane->GetPointData();
    if ( pointData == NULL )
    {
      itkWarningMacro( << "no point data associated with cutters result!" );
      return ;
    }
Пример #7
0
void mitk::SurfaceGLMapper2D::Paint(mitk::BaseRenderer * renderer)
{
  bool visible = true;
  GetDataNode()->GetVisibility(visible, renderer, "visible");
  if(!visible) return;

  Surface::Pointer input  = const_cast<Surface*>(this->GetInput());

  if(input.IsNull())
    return;

  //
  // get the TimeGeometry of the input object
  //
  const TimeGeometry* inputTimeGeometry = input->GetTimeGeometry();
  if(( inputTimeGeometry == NULL ) || ( inputTimeGeometry->CountTimeSteps() == 0 ) )
    return;

  m_LineWidth = 1;
  GetDataNode()->GetIntProperty("line width", m_LineWidth, renderer);

  //
  // get the world time
  //
  ScalarType time =renderer->GetTime();
  int timestep=0;

  if( time > itk::NumericTraits<mitk::ScalarType>::NonpositiveMin() )
    timestep = inputTimeGeometry->TimePointToTimeStep( time );

 // int timestep = this->GetTimestep();

  if( inputTimeGeometry->IsValidTimeStep( timestep ) == false )
    return;

  vtkPolyData * vtkpolydata = input->GetVtkPolyData( timestep );
  if((vtkpolydata==NULL) || (vtkpolydata->GetNumberOfPoints() < 1 ))
    return;

  //apply color and opacity read from the PropertyList
  this->ApplyAllProperties(renderer);

  if (m_DrawNormals)
  {
    m_PointLocator->SetDataSet( vtkpolydata );
    m_PointLocator->BuildLocatorFromPoints( vtkpolydata->GetPoints() );
  }

  if(vtkpolydata!=NULL)
  {
    Point3D point;
    Vector3D normal;

    //Check if Lookup-Table is already given, else use standard one.
    double* scalarLimits = m_LUT->GetTableRange();
    double scalarsMin = scalarLimits[0], scalarsMax = scalarLimits[1];

    vtkLookupTable *lut;

    LookupTableProperty::Pointer lookupTableProp;
    this->GetDataNode()->GetProperty(lookupTableProp, "LookupTable", renderer);
    if (lookupTableProp.IsNotNull() )
    {
      lut = lookupTableProp->GetLookupTable()->GetVtkLookupTable();

      GetDataNode()->GetDoubleProperty("ScalarsRangeMinimum", scalarsMin, renderer);
      GetDataNode()->GetDoubleProperty("ScalarsRangeMaximum", scalarsMax, renderer);

      // check if the scalar range has been changed, e.g. manually, for the data tree node, and rebuild the LUT if necessary.
      double* oldRange = lut->GetTableRange();
      if( oldRange[0] != scalarsMin || oldRange[1] != scalarsMax )
      {
        lut->SetTableRange(scalarsMin, scalarsMax);
        lut->Build();
      }
    }
    else
    {
      lut = m_LUT;
    }

    vtkLinearTransform * vtktransform = GetDataNode()->GetVtkTransform(timestep);
    PlaneGeometry::ConstPointer worldGeometry = renderer->GetCurrentWorldPlaneGeometry();
    assert( worldGeometry.IsNotNull() );
    if (worldGeometry.IsNotNull())
    {
      // set up vtkPlane according to worldGeometry
      point=worldGeometry->GetOrigin();
      normal=worldGeometry->GetNormal(); normal.Normalize();
      m_Plane->SetTransform((vtkAbstractTransform*)NULL);
    }
    else
    {
      AbstractTransformGeometry::ConstPointer worldAbstractGeometry = dynamic_cast<const AbstractTransformGeometry*>(renderer->GetCurrentWorldPlaneGeometry());
      if(worldAbstractGeometry.IsNotNull())
      {
        AbstractTransformGeometry::ConstPointer surfaceAbstractGeometry = dynamic_cast<const AbstractTransformGeometry*>(input->GetTimeGeometry()->GetGeometryForTimeStep(0).GetPointer());
        if(surfaceAbstractGeometry.IsNotNull()) //@todo substitude by operator== after implementation, see bug id 28
        {
          PaintCells(renderer, vtkpolydata, worldGeometry, renderer->GetDisplayGeometry(), vtktransform, lut);
          return;
        }
        else
        {
          //@FIXME: does not work correctly. Does m_Plane->SetTransform really transforms a "flat plane" into a "curved plane"?
          return;
          // set up vtkPlane according to worldGeometry
          point=const_cast<BoundingBox*>(worldAbstractGeometry->GetParametricBoundingBox())->GetMinimum();
          FillVector3D(normal, 0, 0, 1);
          m_Plane->SetTransform(worldAbstractGeometry->GetVtkAbstractTransform()->GetInverse());
        }
      }
      else
        return;
    }

    double vp[3], vnormal[3];

    vnl2vtk(point.GetVnlVector(), vp);
    vnl2vtk(normal.GetVnlVector(), vnormal);

    //normally, we would need to transform the surface and cut the transformed surface with the cutter.
    //This might be quite slow. Thus, the idea is, to perform an inverse transform of the plane instead.
    //@todo It probably does not work for scaling operations yet:scaling operations have to be
    //dealed with after the cut is performed by scaling the contour.
    vtkLinearTransform * inversetransform = vtktransform->GetLinearInverse();
    inversetransform->TransformPoint(vp, vp);
    inversetransform->TransformNormalAtPoint(vp, vnormal, vnormal);

    m_Plane->SetOrigin(vp);
    m_Plane->SetNormal(vnormal);

    //set data into cutter
    m_Cutter->SetInputData(vtkpolydata);
    m_Cutter->Update();
    //    m_Cutter->GenerateCutScalarsOff();
    //    m_Cutter->SetSortByToSortByCell();

    if (m_DrawNormals)
    {
      m_Stripper->SetInputData( m_Cutter->GetOutput() );
      // calculate the cut
      m_Stripper->Update();
      PaintCells(renderer, m_Stripper->GetOutput(), worldGeometry, renderer->GetDisplayGeometry(), vtktransform, lut, vtkpolydata);
    }
    else
    {
      PaintCells(renderer, m_Cutter->GetOutput(), worldGeometry, renderer->GetDisplayGeometry(), vtktransform, lut, vtkpolydata);
    }
  }
}
void mitk::UnstructuredGridMapper2D::Paint( mitk::BaseRenderer* renderer )
{
  bool visible = true;
  GetDataNode()->GetVisibility(visible, renderer, "visible");
  if(!visible) return;

  vtkLinearTransform * vtktransform = GetDataNode()->GetVtkTransform();
  vtkLinearTransform * inversetransform = vtktransform->GetLinearInverse();

  PlaneGeometry::ConstPointer worldGeometry = renderer->GetCurrentWorldPlaneGeometry();
  PlaneGeometry::ConstPointer worldPlaneGeometry = dynamic_cast<const PlaneGeometry*>( worldGeometry.GetPointer() );

  Point3D point;
  Vector3D normal;

  if(worldPlaneGeometry.IsNotNull())
  {
    // set up vtkPlane according to worldGeometry
    point=worldPlaneGeometry->GetOrigin();
    normal=worldPlaneGeometry->GetNormal(); normal.Normalize();
    m_Plane->SetTransform((vtkAbstractTransform*)NULL);
  }
  else
  {
    //@FIXME: does not work correctly. Does m_Plane->SetTransform really transforms a "plane plane" into a "curved plane"?
    return;
    AbstractTransformGeometry::ConstPointer worldAbstractGeometry = dynamic_cast<const AbstractTransformGeometry*>(renderer->GetCurrentWorldPlaneGeometry());
    if(worldAbstractGeometry.IsNotNull())
    {
      // set up vtkPlane according to worldGeometry
      point=const_cast<mitk::BoundingBox*>(worldAbstractGeometry->GetParametricBoundingBox())->GetMinimum();
      FillVector3D(normal, 0, 0, 1);
      m_Plane->SetTransform(worldAbstractGeometry->GetVtkAbstractTransform()->GetInverse());
    }
    else
      return;
  }

  double vp[ 3 ], vnormal[ 3 ];

  vnl2vtk(point.GetVnlVector(), vp);
  vnl2vtk(normal.GetVnlVector(), vnormal);

  //normally, we would need to transform the surface and cut the transformed surface with the cutter.
  //This might be quite slow. Thus, the idea is, to perform an inverse transform of the plane instead.
  //@todo It probably does not work for scaling operations yet:scaling operations have to be
  //dealed with after the cut is performed by scaling the contour.
  inversetransform->TransformPoint( vp, vp );
  inversetransform->TransformNormalAtPoint( vp, vnormal, vnormal );

  m_Plane->SetOrigin( vp );
  m_Plane->SetNormal( vnormal );

  // set data into cutter
  m_Slicer->SetInputData( m_VtkPointSet );
  //    m_Cutter->GenerateCutScalarsOff();
  //    m_Cutter->SetSortByToSortByCell();

  // calculate the cut
  m_Slicer->Update();

  //apply color and opacity read from the PropertyList
  ApplyColorAndOpacityProperties( renderer );

  // traverse the cut contour
  vtkPolyData * contour = m_Slicer->GetOutput();

  vtkPoints *vpoints = contour->GetPoints();
  vtkCellArray *vlines = contour->GetLines();
  vtkCellArray *vpolys = contour->GetPolys();
  vtkPointData *vpointdata = contour->GetPointData();
  vtkDataArray* vscalars = vpointdata->GetScalars();

  vtkCellData *vcelldata = contour->GetCellData();
  vtkDataArray* vcellscalars = vcelldata->GetScalars();

  const int numberOfLines = contour->GetNumberOfLines();
  const int numberOfPolys = contour->GetNumberOfPolys();

  const bool useCellData = m_ScalarMode->GetVtkScalarMode() == VTK_SCALAR_MODE_DEFAULT ||
      m_ScalarMode->GetVtkScalarMode() == VTK_SCALAR_MODE_USE_CELL_DATA;
  const bool usePointData = m_ScalarMode->GetVtkScalarMode() == VTK_SCALAR_MODE_USE_POINT_DATA;

  Point3D p;
  Point2D p2d;

  vlines->InitTraversal();
  vpolys->InitTraversal();

  mitk::Color outlineColor = m_Color->GetColor();

  glLineWidth((float)m_LineWidth->GetValue());

  for (int i = 0;i < numberOfLines;++i )
  {
    vtkIdType *cell(0);
    vtkIdType cellSize(0);

    vlines->GetNextCell( cellSize, cell );

    float rgba[4] = {outlineColor[0], outlineColor[1], outlineColor[2], 1.0f};
    if (m_ScalarVisibility->GetValue() && vcellscalars)
    {
      if ( useCellData )
      {  // color each cell according to cell data
        double scalar = vcellscalars->GetComponent( i, 0 );
        double rgb[3] = { 1.0f, 1.0f, 1.0f };
        m_ScalarsToColors->GetColor(scalar, rgb);
        rgba[0] = (float)rgb[0];
        rgba[1] = (float)rgb[1];
        rgba[2] = (float)rgb[2];
        rgba[3] = (float)m_ScalarsToOpacity->GetValue(scalar);
      }
      else if ( usePointData )
      {
        double scalar = vscalars->GetComponent( i, 0 );
        double rgb[3] = { 1.0f, 1.0f, 1.0f };
        m_ScalarsToColors->GetColor(scalar, rgb);
        rgba[0] = (float)rgb[0];
        rgba[1] = (float)rgb[1];
        rgba[2] = (float)rgb[2];
        rgba[3] = (float)m_ScalarsToOpacity->GetValue(scalar);
      }
    }

    glColor4fv( rgba );

    glBegin ( GL_LINE_LOOP );
    for ( int j = 0;j < cellSize;++j )
    {
      vpoints->GetPoint( cell[ j ], vp );
      //take transformation via vtktransform into account
      vtktransform->TransformPoint( vp, vp );

      vtk2itk( vp, p );

      //convert 3D point (in mm) to display coordinates (units )
      renderer->WorldToDisplay( p, p2d );

      //convert display coordinates ( (0,0) is top-left ) in GL coordinates ( (0,0) is bottom-left )
      //p2d[1]=toGL-p2d[1];

      //add the current vertex to the line
      glVertex2f( p2d[0], p2d[1] );
    }
    glEnd ();

  }

  bool polyOutline = m_Outline->GetValue();
  bool scalarVisibility = m_ScalarVisibility->GetValue();

  // cache the transformed points
  // a fixed size array is way faster than 'new'
  // slices through 3d cells usually do not generated
  // polygons with more than 6 vertices
  const int maxPolySize = 10;
  Point2D* cachedPoints = new Point2D[maxPolySize*numberOfPolys];

  glEnable(GL_BLEND);
  glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);

  // only draw polygons if there are cell scalars
  // or the outline property is set to true
  if (scalarVisibility && vcellscalars)
  {
    glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);

    for (int i = 0;i < numberOfPolys;++i )
    {
      vtkIdType *cell(0);
      vtkIdType cellSize(0);

      vpolys->GetNextCell( cellSize, cell );

      float rgba[4] = {1.0f, 1.0f, 1.0f, 0};
      if (scalarVisibility && vcellscalars)
      {
        if ( useCellData )
        {  // color each cell according to cell data
          double scalar = vcellscalars->GetComponent( i+numberOfLines, 0 );
          double rgb[3] = { 1.0f, 1.0f, 1.0f };
          m_ScalarsToColors->GetColor(scalar, rgb);
          rgba[0] = (float)rgb[0];
          rgba[1] = (float)rgb[1];
          rgba[2] = (float)rgb[2];
          rgba[3] = (float)m_ScalarsToOpacity->GetValue(scalar);
        }
        else if ( usePointData )
        {
          double scalar = vscalars->GetComponent( i, 0 );
          double rgb[3] = { 1.0f, 1.0f, 1.0f };
          m_ScalarsToColors->GetColor(scalar, rgb);
          rgba[0] = (float)rgb[0];
          rgba[1] = (float)rgb[1];
          rgba[2] = (float)rgb[2];
          rgba[3] = (float)m_ScalarsToOpacity->GetValue(scalar);
        }
      }
      glColor4fv( rgba );

      glBegin( GL_POLYGON );
      for (int j = 0; j < cellSize; ++j)
      {
        vpoints->GetPoint( cell[ j ], vp );
        //take transformation via vtktransform into account
        vtktransform->TransformPoint( vp, vp );

        vtk2itk( vp, p );

        //convert 3D point (in mm) to display coordinates (units )
        renderer->WorldToDisplay( p, p2d );

        //convert display coordinates ( (0,0) is top-left ) in GL coordinates ( (0,0) is bottom-left )
        //p2d[1]=toGL-p2d[1];

        cachedPoints[i*10+j][0] = p2d[0];
        cachedPoints[i*10+j][1] = p2d[1];

        //add the current vertex to the line
        glVertex2f( p2d[0], p2d[1] );
      }
      glEnd();
    }

    if (polyOutline)
    {
      vpolys->InitTraversal();

      glColor4f(outlineColor[0], outlineColor[1], outlineColor[2], 1.0f);
      glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
      for (int i = 0;i < numberOfPolys;++i)
      {
        vtkIdType *cell(0);
        vtkIdType cellSize(0);

        vpolys->GetNextCell( cellSize, cell );

        glBegin( GL_POLYGON );
        //glPolygonOffset(1.0, 1.0);
        for (int j = 0; j < cellSize; ++j)
        {
          //add the current vertex to the line
          glVertex2f( cachedPoints[i*10+j][0], cachedPoints[i*10+j][1] );
        }
        glEnd();
      }
    }
  }
  glDisable(GL_BLEND);
  delete[] cachedPoints;
}
Пример #9
0
void SlicesRotator::RotateToPoint( SliceNavigationController *rotationPlaneSNC,
                                   SliceNavigationController *rotatedPlaneSNC,
                                   const Point3D &point, bool linked )
{
    MITK_WARN << "Deprecated function! Use SliceNavigationController::ReorientSlices() instead";

    SliceNavigationController *thirdSNC = NULL;

    SNCVector::iterator iter;
    for ( iter = m_RotatableSNCs.begin(); iter != m_RotatableSNCs.end(); ++iter )
    {
        if ( ((*iter) != rotationPlaneSNC)
                && ((*iter) != rotatedPlaneSNC) )
        {
            thirdSNC = *iter;
            break;
        }
    }

    if ( thirdSNC == NULL )
    {
        return;
    }

    const PlaneGeometry *rotationPlane = rotationPlaneSNC->GetCurrentPlaneGeometry();
    const PlaneGeometry *rotatedPlane = rotatedPlaneSNC->GetCurrentPlaneGeometry();
    const PlaneGeometry *thirdPlane = thirdSNC->GetCurrentPlaneGeometry();

    if ( (rotationPlane == NULL) || (rotatedPlane == NULL)
            || (thirdPlane == NULL) )
    {
        return;
    }

    if ( rotatedPlane->DistanceFromPlane( point ) < 0.001 )
    {
        // Skip irrelevant rotations
        return;
    }

    Point3D projectedPoint;
    Line3D intersection;
    Point3D rotationCenter;

    if ( !rotationPlane->Project( point, projectedPoint )
            || !rotationPlane->IntersectionLine( rotatedPlane, intersection )
            || !thirdPlane->IntersectionPoint( intersection, rotationCenter ) )
    {
        return;
    }

    // All pre-requirements are met; execute the rotation

    Point3D referencePoint = intersection.Project( projectedPoint );

    Vector3D toProjected = referencePoint - rotationCenter;
    Vector3D toCursor    = projectedPoint - rotationCenter;

    // cross product: | A x B | = |A| * |B| * sin(angle)
    Vector3D axisOfRotation;
    vnl_vector_fixed< ScalarType, 3 > vnlDirection =
        vnl_cross_3d( toCursor.GetVnlVector(), toProjected.GetVnlVector() );
    axisOfRotation.SetVnlVector( vnlDirection );

    // scalar product: A * B = |A| * |B| * cos(angle)
    // tan = sin / cos
    ScalarType angle = - atan2(
                           (double)(axisOfRotation.GetNorm()),
                           (double)(toCursor * toProjected) );
    angle *= 180.0 / vnl_math::pi;

    // create RotationOperation and apply to all SNCs that should be rotated
    RotationOperation op(OpROTATE, rotationCenter, axisOfRotation, angle);

    if ( !linked )
    {
        BaseRenderer *renderer = rotatedPlaneSNC->GetRenderer();
        if ( renderer == NULL )
        {
            return;
        }

        DisplayGeometry *displayGeometry = renderer->GetDisplayGeometry();

        Point2D point2DWorld, point2DDisplayPre, point2DDisplayPost;
        displayGeometry->Map( rotationCenter, point2DWorld );
        displayGeometry->WorldToDisplay( point2DWorld, point2DDisplayPre );

        TimeGeometry *timeGeometry= rotatedPlaneSNC->GetCreatedWorldGeometry();
        if ( !timeGeometry )
        {
            return;
        }

        timeGeometry->ExecuteOperation( &op );

        displayGeometry->Map( rotationCenter, point2DWorld );
        displayGeometry->WorldToDisplay( point2DWorld, point2DDisplayPost );
        Vector2D vector2DDisplayDiff = point2DDisplayPost - point2DDisplayPre;

        //Vector2D origin = displayGeometry->GetOriginInMM();

        displayGeometry->MoveBy( vector2DDisplayDiff );

        rotatedPlaneSNC->SendCreatedWorldGeometryUpdate();
    }
    else
    {
        SNCVector::iterator iter;
        for ( iter = m_RotatableSNCs.begin(); iter != m_RotatableSNCs.end(); ++iter )
        {
            BaseRenderer *renderer = (*iter)->GetRenderer();
            if ( renderer == NULL )
            {
                continue;
            }

            DisplayGeometry *displayGeometry = renderer->GetDisplayGeometry();

            Point2D point2DWorld, point2DDisplayPre, point2DDisplayPost;
            displayGeometry->Map( rotationCenter, point2DWorld );
            displayGeometry->WorldToDisplay( point2DWorld, point2DDisplayPre );

            TimeGeometry* timeGeometry = (*iter)->GetCreatedWorldGeometry();
            if ( !timeGeometry )
            {
                continue;
            }

            timeGeometry->ExecuteOperation( &op );

            displayGeometry->Map( rotationCenter, point2DWorld );
            displayGeometry->WorldToDisplay( point2DWorld, point2DDisplayPost );
            Vector2D vector2DDisplayDiff = point2DDisplayPost - point2DDisplayPre;

            //Vector2D origin = displayGeometry->GetOriginInMM();

            displayGeometry->MoveBy( vector2DDisplayDiff );

            (*iter)->SendCreatedWorldGeometryUpdate();
        }
    }
} // end RotateToPoint
Пример #10
0
bool SlicesRotator::DoRotationStep(Action*, const StateEvent* e)
{
    const DisplayPositionEvent* posEvent = dynamic_cast<const DisplayPositionEvent*>(e->GetEvent());
    if (!posEvent) return false;

    Point3D cursor = posEvent->GetWorldPosition();

    Vector3D toProjected = m_LastCursorPosition - m_CenterOfRotation;
    Vector3D toCursor    = cursor - m_CenterOfRotation;

    // cross product: | A x B | = |A| * |B| * sin(angle)
    Vector3D axisOfRotation;
    vnl_vector_fixed< ScalarType, 3 > vnlDirection = vnl_cross_3d( toCursor.GetVnlVector(), toProjected.GetVnlVector() );
    axisOfRotation.SetVnlVector(vnlDirection);

    // scalar product: A * B = |A| * |B| * cos(angle)
    // tan = sin / cos
    ScalarType angle = - atan2( (double)(axisOfRotation.GetNorm()), (double)(toCursor * toProjected) );
    angle *= 180.0 / vnl_math::pi;
    m_LastCursorPosition = cursor;

    // create RotationOperation and apply to all SNCs that should be rotated
    RotationOperation rotationOperation(OpROTATE, m_CenterOfRotation, axisOfRotation, angle);

    // iterate the OTHER slice navigation controllers: these are filled in DoDecideBetweenRotationAndSliceSelection
    for (SNCVector::iterator iter = m_SNCsToBeRotated.begin(); iter != m_SNCsToBeRotated.end(); ++iter)
    {
        //  - remember the center of rotation on the 2D display BEFORE rotation
        //  - execute rotation
        //  - calculate new center of rotation on 2D display
        //  - move display IF the center of rotation has moved slightly before and after rotation

        // DM 2012-10: this must probably be due to rounding errors only, right?
        //             We don't have documentation on if/why this code is needed
        BaseRenderer *renderer = (*iter)->GetRenderer();
        if ( !renderer ) continue;

        DisplayGeometry *displayGeometry = renderer->GetDisplayGeometry();

        Point2D rotationCenter2DWorld, point2DDisplayPreRotation, point2DDisplayPostRotation;
        displayGeometry->Map( m_CenterOfRotation, rotationCenter2DWorld );
        displayGeometry->WorldToDisplay( rotationCenter2DWorld, point2DDisplayPreRotation );

        TimeGeometry* timeGeometry = (*iter)->GetCreatedWorldGeometry();
        if (!timeGeometry) continue;

        timeGeometry->ExecuteOperation(&rotationOperation);

        displayGeometry->Map( m_CenterOfRotation, rotationCenter2DWorld );
        displayGeometry->WorldToDisplay( rotationCenter2DWorld, point2DDisplayPostRotation );
        Vector2D vector2DDisplayDiff = point2DDisplayPostRotation - point2DDisplayPreRotation;

        displayGeometry->MoveBy( vector2DDisplayDiff );

        (*iter)->SendCreatedWorldGeometryUpdate();
    }

    RenderingManager::GetInstance()->RequestUpdateAll();

    this->InvokeEvent( SliceRotationEvent() ); // notify listeners

    return true;
}