[Insight-users] PGM from NII with ITK

Dženan Zukić dzenanz at gmail.com
Fri Feb 28 05:03:38 EST 2014


I needed to compare results of my segmentation method with power
watersheds, so I modified one of ITK's image reading files to enable
natural support for PGM format.

#include "itkPGMImageIOFactory.h" //include it in the beginning of the main
file

//call in the main() function before any ITK-related read/write operations
take place
itk::ObjectFactoryBase::RegisterFactory( itk::PGMImageIOFactory::New() );

This makes .pgm supported just as well as .png or .mha. You can make your
own project "natively" support it. If you only want to convert a few
images, you can modify ITK's ImageReadWrite example.


On Thu, Feb 27, 2014 at 9:19 PM, Richard Beare <richard.beare at gmail.com>wrote:

> Hi,
> I'm assuming you really want a 3d watershed, since you are starting with
> nifti, rather than a series of 2D versions. If you are interested in a
> series of 2d versions, then you might try nifti to tiff with convert3d,
> then extract the tiff slices with tiffsplit, then tifftopgm with the image
> magick tools.
>
> The README with the power watershed code  says that the 3d format is a
> very simple header followed by the data, so your best bet is to probably do
> it manually. Use convert3d, or equivalent tool to change the nii to a
> format that has separate data and header sections (or strip the nii header
> off), making sure that you have unsigned char data. Then manually construct
> the text header and join the two together. It appears that the text header
> should look like this:
>
> P5
> xsize ysize zsize
> 255
>
> Then do the reverse to get back to a nifti file. Seems that the extended
> pgm format doesn't know about voxel sizes, so you may get weird results if
> the data is highly anisotropic.
>
>
> On Fri, Feb 28, 2014 at 1:11 AM, Nicolas Cordier <nicolas.cordier at inria.fr
> > wrote:
>
>> Hello,
>>
>> There is a tool (Power Watershed) from ICCV 2009 which only accepts .ppm
>> images:
>> http://powerwatershed.sourceforge.net/
>>
>> It seems convert3d does not support this image format, which I suspect is
>> the following one:
>> <http://netpbm.sourceforge.net/doc/pgm.html>
>> http://netpbm.sourceforge.net/doc/pgm.html
>>
>> Is there an easy way to convert my .nii (3D images) to .pgm files? Apply
>> this tool and then convert the way back?
>>
>> Best regards,
>> --
>>
>> *Nicolas CORDIER*
>>
>> ASCLEPIOS <http://www-sop.inria.fr/asclepios/> PhD Candidate
>>
>>
>> *INRIA SOPHIA ANTIPOLIS - MEDITERRANEE
>> <http://www.inria.fr/centre/sophia/>*
>>
>> 2004 route des Lucioles, BP93, 06902 Sophia Antipolis Cedex, FR
>> Tel : +33 (0)4 92 38 79 26 - Fax : +33 (0)4 92 38 76 69
>>
>>
>>
>>
>> _____________________________________
>> Powered by www.kitware.com
>>
>> Visit other Kitware open-source projects at
>> http://www.kitware.com/opensource/opensource.html
>>
>> Kitware offers ITK Training Courses, for more information visit:
>> http://www.kitware.com/products/protraining.php
>>
>> Please keep messages on-topic and check the ITK FAQ at:
>> http://www.itk.org/Wiki/ITK_FAQ
>>
>> Follow this link to subscribe/unsubscribe:
>> http://www.itk.org/mailman/listinfo/insight-users
>>
>>
>
> _____________________________________
> Powered by www.kitware.com
>
> Visit other Kitware open-source projects at
> http://www.kitware.com/opensource/opensource.html
>
> Kitware offers ITK Training Courses, for more information visit:
> http://www.kitware.com/products/protraining.php
>
> Please keep messages on-topic and check the ITK FAQ at:
> http://www.itk.org/Wiki/ITK_FAQ
>
> Follow this link to subscribe/unsubscribe:
> http://www.itk.org/mailman/listinfo/insight-users
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://www.itk.org/pipermail/insight-users/attachments/20140228/0cec932b/attachment.html>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: inria-logo-mail-scientifique-gb.jpg
Type: image/jpeg
Size: 5712 bytes
Desc: not available
URL: <http://www.itk.org/pipermail/insight-users/attachments/20140228/0cec932b/attachment.jpg>
-------------- next part --------------
#ifdef _MSC_VER
#pragma warning ( disable : 4786 )
#endif

#include <string>
#include <iterator>
#include "itkPGMImageIO.h"
#include "itkMacro.h"
#include "itkMetaDataObject.h"
#include "itkIOCommon.h"
#include "itksys/SystemTools.hxx"
#include <fstream>
#include <iomanip>
#include <ios>

typedef std::string::value_type char_t;

namespace itk {

	bool PGMImageIO::SupportsDimension(unsigned long dim)
	{
		return dim==3 || dim==2; //2D + extension to 3D
	}

	void PGMImageIO::PrintSelf(std::ostream& os, Indent indent) const
	{
		Superclass::PrintSelf(os, indent);
	}

	bool PGMImageIO::CanReadFile( const char* filename ) 
	{
		// Check the extension first to avoid opening files that do not
		// look like dats.  The file must have an appropriate extension to be
		// recognized.
		std::string fname = filename;

		if(  fname == "" )
		{
			itkDebugMacro(<<"No filename specified.");
			return false;
		}

		bool extensionFound = false;
		std::string::size_type datPos = fname.rfind(".pgm");
		if ((datPos != std::string::npos)
			&& (datPos == fname.length() - 4))
		{
			extensionFound = true;
		}

		if( !extensionFound )
		{
			itkDebugMacro(<<"The filename extension is not recognized");
			return false;
		}

		std::ifstream inputStream;

		inputStream.open( filename, std::ios::in | std::ios::binary );

		if( inputStream.fail() )
		{
			return false;
		}

		inputStream.close();
		return true;
	}

	void PGMImageIO::ReadImageInformation()
	{
		std::ifstream in(this->GetFileName());

		std::string s;
		char buf[1000];
		in>>s;
		if (s!="P5")
		{
			ExceptionObject exception(__FILE__, __LINE__);
			exception.SetDescription("P5 signature not found.");
			throw exception;
		}
		in.getline(buf, 999); //read endline char

		int xres, yres, zres, maxVal;
		in>>xres>>yres;

        this->SetComponentType(UCHAR);
		this->SetPixelType( ImageIOBase::SCALAR );
		this->SetNumberOfComponents(1);

        in.getline(buf, 999);
        if (buf[0]!=0)
        {
            this->SetNumberOfDimensions(3);
            zres=atoi(buf);
		    this->SetDimensions(2, zres);
        }
        else
        {
            this->SetNumberOfDimensions(2);
        }
		this->SetDimensions(0, xres);
		this->SetDimensions(1, yres);

        in>>maxVal;
        if (maxVal!=255)
            itkWarningMacro (<<"Maximum value should be 255, not "<<maxVal);
		in.close();
	}

	void PGMImageIO::Read(void* buffer)
	{
        size_t elems;
        if (this->GetNumberOfDimensions()==3)
            elems=this->GetDimensions(0)*this->GetDimensions(1)*this->GetDimensions(2);
        else
            elems=this->GetDimensions(0)*this->GetDimensions(1);
		size_t esize=this->GetComponentSize();
        std::ifstream in(this->GetFileName(), std::ios::binary);
        in.getline((char *)buffer, 999);
        in.getline((char *)buffer, 999);
        in.getline((char *)buffer, 999);
        in.read((char *)buffer, esize*elems);
        if (in.bad()||in.gcount()!=esize*elems)
		{
			ExceptionObject exception(__FILE__, __LINE__);
			exception.SetDescription("Error reading "+std::string(this->GetFileName()));
			throw exception;
		}
		in.close();
	} 

	bool PGMImageIO::CanWriteFile( const char * name )
	{
		std::string filename = name;
		if(  filename == "" )
		{
			return false;
		}

		std::string::size_type datPos = filename.rfind(".pgm");
		if ((datPos != std::string::npos)
			&& (datPos == filename.length() - 4))
            return true;

		return false;
	}

	void PGMImageIO::WriteImageInformation(void)
	{
        //nothing to do here
    }

	void PGMImageIO::Write( const void* buffer) 
	{
        size_t elems;
        if (this->GetNumberOfDimensions()==3)
            elems=this->GetDimensions(0)*this->GetDimensions(1)*this->GetDimensions(2);
        else
            elems=this->GetDimensions(0)*this->GetDimensions(1);
		std::ofstream f(this->GetFileName(), std::ios::binary);
        f<<"P5\n";
        f<<this->GetDimensions(0)<<' '<<this->GetDimensions(1);
        if (this->GetNumberOfDimensions()==3)
            f<<' '<<this->GetDimensions(2);
        f<<"\n255\n";
        f.write((char *)buffer, elems*this->GetComponentSize());

        if (f.bad())
		{
			ExceptionObject exception(__FILE__, __LINE__);
			exception.SetDescription("Error writing "+std::string(this->GetFileName()));
			throw exception;
		}
		f.close();		
	}

} // end namespace itk
-------------- next part --------------
A non-text attachment was scrubbed...
Name: itkPGMImageIO.h
Type: text/x-chdr
Size: 2017 bytes
Desc: not available
URL: <http://www.itk.org/pipermail/insight-users/attachments/20140228/0cec932b/attachment.h>
-------------- next part --------------
#include "itkPGMImageIOFactory.h"
#include "itkCreateObjectFunction.h"
#include "itkPGMImageIO.h"
#include "itkVersion.h"

  
namespace itk
{
PGMImageIOFactory::PGMImageIOFactory()
{
  this->RegisterOverride("itkImageIOBase",
                         "itkPGMImageIO",
                         "PGM Image IO",
                         1,
                         CreateObjectFunction<PGMImageIO>::New());
}
  
PGMImageIOFactory::~PGMImageIOFactory()
{
}

const char* 
PGMImageIOFactory::GetITKSourceVersion(void) const
{
  return ITK_SOURCE_VERSION;
}

const char* 
PGMImageIOFactory::GetDescription() const
{
  return "PGM ImageIO Factory, allows the loading of Netpbm PGM images into ITK";
}

} // end namespace itk
-------------- next part --------------
A non-text attachment was scrubbed...
Name: itkPGMImageIOFactory.h
Type: text/x-chdr
Size: 1359 bytes
Desc: not available
URL: <http://www.itk.org/pipermail/insight-users/attachments/20140228/0cec932b/attachment-0001.h>


More information about the Insight-users mailing list