Index: Core/Code/DataManagement/mitkGeometry3D.cpp =================================================================== --- Core/Code/DataManagement/mitkGeometry3D.cpp (revision 26530) +++ Core/Code/DataManagement/mitkGeometry3D.cpp (working copy) @@ -623,3 +623,39 @@ mitk::Geometry3D::ResetSubTransforms() { } + +void +mitk::Geometry3D::ChangeImageGeometryConsideringOriginOffset( const bool isAnImageGeometry ) +{ + // If Geometry is switched to ImageGeometry, you have to put an offset to the origin, because + // imageGeometries origins are pixel-center-based + // ... and remove the offset, if you switch an imageGeometry back to a normal geometry + + if(m_ImageGeometry == isAnImageGeometry) + return; + + const BoundingBox::BoundsArrayType& boundsarray = + this->GetBoundingBox()->GetBounds(); + + Point3D originIndex; + FillVector3D(originIndex, boundsarray[0], boundsarray[2], boundsarray[4]); + + if(isAnImageGeometry == true) + FillVector3D( originIndex, + originIndex[0] + 0.5, + originIndex[1] + 0.5, + originIndex[2] + 0.5 ); + else + FillVector3D( originIndex, + originIndex[0] - 0.5, + originIndex[1] - 0.5, + originIndex[2] - 0.5 ); + + Point3D originWorld; + originWorld = GetIndexToWorldTransform() + ->TransformPoint( originIndex ); + + SetOrigin(originWorld); + + this->SetImageGeometry(isAnImageGeometry); +} \ No newline at end of file Index: Core/Code/DataManagement/mitkGeometry3D.h =================================================================== --- Core/Code/DataManagement/mitkGeometry3D.h (revision 26530) +++ Core/Code/DataManagement/mitkGeometry3D.h (working copy) @@ -145,6 +145,11 @@ //## @brief Set the bounding box (in index/unit coordinates) via a double array virtual void SetFloatBounds(const double bounds[6]); + + /// Changes Geometry Origin, if switching from imageGeometry to normal Geometry (and the other way around) + virtual void ChangeImageGeometryConsideringOriginOffset( const bool isAnImageGeometry ); + + //##Documentation //## @brief Get the time bounds (in ms) itkGetConstReferenceMacro(TimeBounds, TimeBounds); @@ -279,7 +284,7 @@ virtual void Compose( const vtkMatrix4x4 * vtkmatrix, bool pre = 0 ); //##Documentation - //## @brief Get the origin, i.e. the upper-left corner of the plane + //## @brief Get the origin, e.g. the upper-left corner of the plane const Point3D& GetOrigin() const { return m_Origin; Index: Core/Code/DataManagement/mitkImage.cpp =================================================================== --- Core/Code/DataManagement/mitkImage.cpp (revision 26530) +++ Core/Code/DataManagement/mitkImage.cpp (working copy) @@ -765,6 +765,7 @@ TimeSlicedGeometry::Pointer timeSliceGeometry = TimeSlicedGeometry::New(); timeSliceGeometry->InitializeEvenlyTimed(slicedGeometry, m_Dimensions[3]); + timeSliceGeometry->ImageGeometryOn(); SetGeometry(timeSliceGeometry); @@ -997,6 +998,7 @@ TimeSlicedGeometry::Pointer timeSliceGeometry = TimeSlicedGeometry::New(); timeSliceGeometry->InitializeEvenlyTimed(slicedGeometry, m_Dimensions[3]); + timeSliceGeometry->ImageGeometryOn(); SetGeometry(timeSliceGeometry); @@ -1168,6 +1170,21 @@ void mitk::Image::SetGeometry(Geometry3D* aGeometry3D) { + // ATTENTION!!! Please be aware of the 0.5 offset/pixel-center issue! + // The geometry of an image should have the bool value "ImageGeometry" as true, to indicate it belongs to an image. + // While "normal" geometries have their origin usually on a corner (e.g. 0,0,0), image geometries are pixel-center based. + // That means, they have their origin in the middle of the first pixel (e.g. 0.5,0.5,0.5). + // When you call mitk::Image::SetGeometry(..) please be sure, that the geometry + // a) is center-based + // b) has the bool flag "ImageGeometry" on true + // + // If ImageGeometry==false, you can call "Geometry3D::ChangeImageGeometryConsideringOriginOffset(true)" to make it centerbased and turn on the flag. + // If ImageGeometry==true, you can call "Geometry3D::ChangeImageGeometryConsideringOriginOffset(false)" to make it cornerbased again and turn off the flag. + + if(aGeometry3D->GetImageGeometry()==false) + { + MITK_INFO << "WARNING: Applied a non-image geometry onto an image. If you are SURE that this this geometry is pixel-center-based, please turn the imageGeometry flag on by calling 'ImageGeometryOn()'. If the geometry is not center-based yet, please call 'ChangeImageGeometryConsideringOriginOffset(true)' to make it center-based and flag it.\n"; + } Superclass::SetGeometry(aGeometry3D); GetTimeSlicedGeometry()->ImageGeometryOn(); } Index: Core/Code/DataManagement/mitkSlicedGeometry3D.cpp =================================================================== --- Core/Code/DataManagement/mitkSlicedGeometry3D.cpp (revision 26530) +++ Core/Code/DataManagement/mitkSlicedGeometry3D.cpp (working copy) @@ -459,6 +459,25 @@ } } +void +mitk::SlicedGeometry3D::ChangeImageGeometryConsideringOriginOffset( const bool isAnImageGeometry ) +{ + mitk::Geometry3D* geometry; + + unsigned int s; + for ( s = 0; s < m_Slices; ++s ) + { + geometry = m_Geometry2Ds[s]; + if ( geometry!=NULL ) + { + geometry->ChangeImageGeometryConsideringOriginOffset( isAnImageGeometry ); + } + } + + Superclass::ChangeImageGeometryConsideringOriginOffset( isAnImageGeometry ); +} + + bool mitk::SlicedGeometry3D::IsValidSlice( int s ) const { Index: Core/Code/DataManagement/mitkSlicedGeometry3D.h =================================================================== --- Core/Code/DataManagement/mitkSlicedGeometry3D.h (revision 26530) +++ Core/Code/DataManagement/mitkSlicedGeometry3D.h (working copy) @@ -112,6 +112,9 @@ */ virtual bool SetGeometry2D( mitk::Geometry2D *geometry2D, int s ); + /// Changes Geometry Origin, if switching from imageGeometry to normal Geometry (and the other way around) + virtual void ChangeImageGeometryConsideringOriginOffset( const bool isAnImageGeometry ); + virtual void SetTimeBounds( const mitk::TimeBounds& timebounds ); Index: Core/Code/DataManagement/mitkTimeSlicedGeometry.cpp =================================================================== --- Core/Code/DataManagement/mitkTimeSlicedGeometry.cpp (revision 26530) +++ Core/Code/DataManagement/mitkTimeSlicedGeometry.cpp (working copy) @@ -313,6 +313,22 @@ } } + +void mitk::TimeSlicedGeometry::ChangeImageGeometryConsideringOriginOffset(const bool isAnImageGeometry) +{ + mitk::Geometry3D* geometry3d; + unsigned int t; + for(t=0; tChangeImageGeometryConsideringOriginOffset(isAnImageGeometry); + } + + Superclass::ChangeImageGeometryConsideringOriginOffset(isAnImageGeometry); +} + + void mitk::TimeSlicedGeometry::SetEvenlyTimed(bool on) { m_EvenlyTimed = on; Index: Core/Code/DataManagement/mitkTimeSlicedGeometry.h =================================================================== --- Core/Code/DataManagement/mitkTimeSlicedGeometry.h (revision 26530) +++ Core/Code/DataManagement/mitkTimeSlicedGeometry.h (working copy) @@ -78,6 +78,9 @@ //## @brief Set the Geometry3D for time @a t virtual bool SetGeometry3D(mitk::Geometry3D* geometry3D, int t); + /// Changes Geometry Origin, if switching from imageGeometry to normal Geometry (and the other way around) + virtual void ChangeImageGeometryConsideringOriginOffset( const bool isAnImageGeometry ); + //##Documentation //## @brief Get the Geometry3D at time @a t virtual mitk::Geometry3D* GetGeometry3D(int t) const; Index: Core/Code/Testing/mitkSlicedGeometry3DTest.cpp =================================================================== --- Core/Code/Testing/mitkSlicedGeometry3DTest.cpp (revision 26530) +++ Core/Code/Testing/mitkSlicedGeometry3DTest.cpp (working copy) @@ -142,7 +142,34 @@ } std::cout<<"[PASSED]"<GetImageGeometry() is false by default"); + //MITK_TEST_CONDITION_REQUIRED( slicedWorldGeometry->GetImageGeometry()==false, ""); + //MITK_TEST_OUTPUT(<< "Testing whether first geometry in the SlicedGeometry3D has GetImageGeometry()==false by default"); + //MITK_TEST_CONDITION_REQUIRED( accessedplanegeometry3->GetImageGeometry()==false, ""); + //MITK_TEST_OUTPUT(<< "Testing whether last geometry in the SlicedGeometry3D has GetImageGeometry()==false by default"); + //MITK_TEST_CONDITION_REQUIRED( accessedplanegeometry3last->GetImageGeometry()==false, ""); + //slicedWorldGeometry->GetCornerPoint(0) + // accessedplanegeometry3->GetCornerPoint(0) + // accessedplanegeometry3last->GetCornerPoint(0) + + //MITK_TEST_OUTPUT(<< "Calling slicedWorldGeometry->ChangeImageGeometry(true)"); + //slicedWorldGeometry->ChangeImageGeometry(true); + + //accessedplanegeometry3 = dynamic_cast(slicedWorldGeometry->GetGeometry2D(0)); + //accessedplanegeometry3last = dynamic_cast(slicedWorldGeometry->GetGeometry2D(numSlices-1)); + + //MITK_TEST_OUTPUT(<< "Testing whether slicedWorldGeometry->GetImageGeometry() is now true"); + //MITK_TEST_CONDITION_REQUIRED( slicedWorldGeometry->GetImageGeometry()==true, ""); + //MITK_TEST_OUTPUT(<< "Testing whether first geometry in the SlicedGeometry3D has GetImageGeometry()==true"); + //MITK_TEST_CONDITION_REQUIRED( accessedplanegeometry3->GetImageGeometry()==true, ""); + //MITK_TEST_OUTPUT(<< "Testing whether last geometry in the SlicedGeometry3D has GetImageGeometry()==true"); + //MITK_TEST_CONDITION_REQUIRED( accessedplanegeometry3last->GetImageGeometry()==true, ""); + + //slicedWorldGeometry->GetOrigin() + + std::cout<<"[TEST DONE]"<WorldToIndex( currentPointIn3D, projectedPointIn2D ); - MITK_DEBUG << "world point " << currentPointIn3D << " in index is " << projectedPointIn2D; + MITK_INFO << "world point " << currentPointIn3D << " in index is " << projectedPointIn2D; if ( !sliceGeometry->IsIndexInside( projectedPointIn2D ) && constrainToInside ) { @@ -81,7 +81,7 @@ Point3D worldPointIn3D; worldPointIn3D.Fill(0.0); sliceGeometry->IndexToWorld( currentPointIn2D, worldPointIn3D ); - MITK_DEBUG << "index " << currentPointIn2D << " world " << worldPointIn3D << std::endl; + MITK_INFO << "index " << currentPointIn2D << " world " << worldPointIn3D << std::endl; worldContour->AddVertex( worldPointIn3D ); } @@ -104,9 +104,9 @@ iter != pointsIn2D->end(); ++iter, ++index ) { - picContour[ 2 * index + 0 ] = static_cast( (*iter)[0] + 0.5); - picContour[ 2 * index + 1 ] = static_cast( (*iter)[1] + 0.5); - MITK_DEBUG << "mitk 2d [" << (*iter)[0] << ", " << (*iter)[1] << "] pic [" << picContour[ 2*index+0] << ", " << picContour[ 2*index+1] << "]"; + picContour[ 2 * index + 0 ] = static_cast( (*iter)[0] + 1.0 ); // +0.5 wahrscheinlich richtiger + picContour[ 2 * index + 1 ] = static_cast( (*iter)[1] + 1.0 ); + MITK_INFO << "mitk 2d [" << (*iter)[0] << ", " << (*iter)[1] << "] pic [" << picContour[ 2*index+0] << ", " << picContour[ 2*index+1] << "]"; } assert( sliceImage->GetSliceData() ); Index: Modules/MitkExt/Algorithms/mitkCorrectorAlgorithm.cpp =================================================================== --- Modules/MitkExt/Algorithms/mitkCorrectorAlgorithm.cpp (revision 26530) +++ Modules/MitkExt/Algorithms/mitkCorrectorAlgorithm.cpp (working copy) @@ -154,8 +154,8 @@ iter != pointsIn2D->end(); ++iter, ++index ) { - _points[ 2 * index + 0 ] = static_cast( (*iter)[0] + 1.0 ); - _points[ 2 * index + 1 ] = static_cast( (*iter)[1] + 1.0 ); + _points[ 2 * index + 0 ] = static_cast( (*iter)[0] + 0.5 ); + _points[ 2 * index + 1 ] = static_cast( (*iter)[1] + 0.5 ); } // store ofsets of the drawn line in array Index: Modules/MitkExt/Algorithms/mitkExtractImageFilter.cpp =================================================================== --- Modules/MitkExt/Algorithms/mitkExtractImageFilter.cpp (revision 26530) +++ Modules/MitkExt/Algorithms/mitkExtractImageFilter.cpp (working copy) @@ -96,6 +96,7 @@ PlaneGeometry::Pointer planeGeometry = PlaneGeometry::New(); planeGeometry->InitializeStandardPlane( inputImageGeometry, orientation, (ScalarType)m_SliceIndex + 0.5 , true, false ); Image::Pointer resultImage = ImageToImageFilter::GetOutput(); + planeGeometry->ChangeImageGeometryConsideringOriginOffset(true); resultImage->SetGeometry( planeGeometry ); } Index: Modules/MitkExt/Interactions/mitkPaintbrushTool.cpp =================================================================== --- Modules/MitkExt/Interactions/mitkPaintbrushTool.cpp (revision 26530) +++ Modules/MitkExt/Interactions/mitkPaintbrushTool.cpp (working copy) @@ -237,13 +237,13 @@ // round to nearest voxel center (abort if this hasn't changed) if ( m_Size % 2 == 0 ) // even { - indexCoordinates[firstDimension] = ROUND( indexCoordinates[firstDimension] + 0.5 ); + indexCoordinates[firstDimension] = ROUND( indexCoordinates[firstDimension] + 0.5); indexCoordinates[secondDimension] = ROUND( indexCoordinates[secondDimension] + 0.5 ); } else // odd { - indexCoordinates[firstDimension] = ROUND( indexCoordinates[firstDimension] ) ;//+ 0.5; - indexCoordinates[secondDimension] = ROUND( indexCoordinates[secondDimension] );// + 0.5; + indexCoordinates[firstDimension] = ROUND( indexCoordinates[firstDimension] ) ; + indexCoordinates[secondDimension] = ROUND( indexCoordinates[secondDimension] ) ; } static Point3D lastPos; // uninitialized: if somebody finds out how this can be initialized in a one-liner, tell me @@ -300,11 +300,11 @@ for (unsigned int index = 0; index < contour->GetNumberOfPoints(); ++index) { Point3D point = contour->GetPoints()->ElementAt(index); - if ( m_Size % 2 != 0 ) // even + /*if ( m_Size % 2 != 0 ) // even { point[0] += 0.5; point[1] += 0.5; - } + }*/ displayContour->AddVertex( point ); } Index: Modules/MitkExt/Interactions/mitkRegionGrowingTool.cpp =================================================================== --- Modules/MitkExt/Interactions/mitkRegionGrowingTool.cpp (revision 26530) +++ Modules/MitkExt/Interactions/mitkRegionGrowingTool.cpp (working copy) @@ -524,7 +524,7 @@ newPoint[1] = contourPoints[ 2 * index + 1]; newPoint[2] = 0; - contourInImageIndexCoordinates->AddVertex( newPoint ); + contourInImageIndexCoordinates->AddVertex( newPoint + 0.5); } free(contourPoints); Index: Modules/MitkExt/Interactions/mitkSetRegionTool.cpp =================================================================== --- Modules/MitkExt/Interactions/mitkSetRegionTool.cpp (revision 26530) +++ Modules/MitkExt/Interactions/mitkSetRegionTool.cpp (working copy) @@ -188,7 +188,7 @@ newPoint[1] = contourPoints[ 2 * index + 1]; newPoint[2] = 0; - contourInImageIndexCoordinates->AddVertex( newPoint ); + contourInImageIndexCoordinates->AddVertex( newPoint - 0.5 ); } m_SegmentationContourInWorldCoordinates = FeedbackContourTool::BackProjectContourFrom2DSlice( workingSlice, contourInImageIndexCoordinates, true ); // true, correct the result from ipMITKSegmentationGetContour8N