From 64e548f2c8c2976f9573855e438437c9447d5d34 Mon Sep 17 00:00:00 2001 From: David Sarrut Date: Fri, 2 Jun 2017 13:04:12 +0200 Subject: [PATCH] add tool to compute MaskOfIntegratedIntensity --- CMakeLists.txt | 1 + tools/CMakeLists.txt | 6 + tools/clitkMaskOfIntegratedIntensity.cxx | 41 +++++ tools/clitkMaskOfIntegratedIntensity.ggo | 12 ++ ...tkMaskOfIntegratedIntensityGenericFilter.h | 75 ++++++++ ...MaskOfIntegratedIntensityGenericFilter.txx | 169 ++++++++++++++++++ 6 files changed, 304 insertions(+) create mode 100644 tools/clitkMaskOfIntegratedIntensity.cxx create mode 100644 tools/clitkMaskOfIntegratedIntensity.ggo create mode 100644 tools/clitkMaskOfIntegratedIntensityGenericFilter.h create mode 100644 tools/clitkMaskOfIntegratedIntensityGenericFilter.txx diff --git a/CMakeLists.txt b/CMakeLists.txt index c4fbc59..6554e49 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -6,6 +6,7 @@ cmake_policy(VERSION 2.8) if(COMMAND cmake_policy) cmake_policy(SET CMP0003 NEW) cmake_policy(SET CMP0007 NEW) + cmake_policy(SET CMP0053 NEW) endif(COMMAND cmake_policy) if(NOT DEFINED CLITK_SOURCE_DIR) set(CLITK_SOURCE_DIR ${PROJECT_SOURCE_DIR}) diff --git a/tools/CMakeLists.txt b/tools/CMakeLists.txt index 999b48a..1a4d9ee 100644 --- a/tools/CMakeLists.txt +++ b/tools/CMakeLists.txt @@ -345,6 +345,12 @@ if(CLITK_BUILD_TOOLS) target_link_libraries(clitkImageIntensityWindowing clitkCommon ) set(TOOLS_INSTALL ${TOOLS_INSTALL} clitkImageIntensityWindowing) + WRAP_GGO(clitkMaskOfIntegratedIntensity_GGO_C clitkMaskOfIntegratedIntensity.ggo) + add_executable(clitkMaskOfIntegratedIntensity clitkMaskOfIntegratedIntensity.cxx ${clitkMaskOfIntegratedIntensity_GGO_C}) + target_link_libraries(clitkMaskOfIntegratedIntensity clitkCommon ) + set(TOOLS_INSTALL ${TOOLS_INSTALL} clitkMaskOfIntegratedIntensity) + + WRAP_GGO(clitkBlurImage_GGO_C clitkBlurImage.ggo) add_executable(clitkBlurImage clitkBlurImage.cxx ${clitkBlurImage_GGO_C}) target_link_libraries(clitkBlurImage clitkCommon ) diff --git a/tools/clitkMaskOfIntegratedIntensity.cxx b/tools/clitkMaskOfIntegratedIntensity.cxx new file mode 100644 index 0000000..93d53e1 --- /dev/null +++ b/tools/clitkMaskOfIntegratedIntensity.cxx @@ -0,0 +1,41 @@ +/*========================================================================= + Program: vv http://www.creatis.insa-lyon.fr/rio/vv + + Authors belong to: + - University of LYON http://www.universite-lyon.fr/ + - Léon Bérard cancer center http://www.centreleonberard.fr + - CREATIS CNRS laboratory http://www.creatis.insa-lyon.fr + + This software is distributed WITHOUT ANY WARRANTY; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. See the copyright notices for more information. + + It is distributed under dual licence + + - BSD See included LICENSE.txt file + - CeCILL-B http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html +===========================================================================**/ + +// clitk +#include "clitkMaskOfIntegratedIntensity_ggo.h" +#include "clitkMaskOfIntegratedIntensityGenericFilter.h" + +//-------------------------------------------------------------------- +int main(int argc, char * argv[]) +{ + + // Init command line + GGO(clitkMaskOfIntegratedIntensity, args_info); + CLITK_INIT; + + // Filter + typedef clitk::MaskOfIntegratedIntensityGenericFilter FilterType; + FilterType::Pointer filter = FilterType::New(); + + filter->SetArgsInfo(args_info); + filter->Update(); + + return EXIT_SUCCESS; +}// end main + +//-------------------------------------------------------------------- diff --git a/tools/clitkMaskOfIntegratedIntensity.ggo b/tools/clitkMaskOfIntegratedIntensity.ggo new file mode 100644 index 0000000..c60f92f --- /dev/null +++ b/tools/clitkMaskOfIntegratedIntensity.ggo @@ -0,0 +1,12 @@ +#File clitkMaskOfIntegratedIntensity.ggo +package "clitkMaskOfIntegratedIntensity" +version "1.0" +purpose "Compute a mask that represent X% of the total pixels values" + +option "config" - "Config file" string optional +option "verbose" v "Verbose" flag off +option "imagetypes" - "Display allowed image types" flag off + +option "input" i "Input image filename" string required +option "output" o "Output image filename" string required +option "percentage" p "Percentage of total pixels values (in %)" double required diff --git a/tools/clitkMaskOfIntegratedIntensityGenericFilter.h b/tools/clitkMaskOfIntegratedIntensityGenericFilter.h new file mode 100644 index 0000000..a2df346 --- /dev/null +++ b/tools/clitkMaskOfIntegratedIntensityGenericFilter.h @@ -0,0 +1,75 @@ +/*========================================================================= + Program: vv http://www.creatis.insa-lyon.fr/rio/vv + + Authors belong to: + - University of LYON http://www.universite-lyon.fr/ + - Léon Bérard cancer center http://www.centreleonberard.fr + - CREATIS CNRS laboratory http://www.creatis.insa-lyon.fr + + This software is distributed WITHOUT ANY WARRANTY; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. See the copyright notices for more information. + + It is distributed under dual licence + + - BSD See included LICENSE.txt file + - CeCILL-B http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html + ===========================================================================**/ + +#ifndef CLITKMaskOfIntegratedIntensityGENERICFILTER_H +#define CLITKMaskOfIntegratedIntensityGENERICFILTER_H + +#include "clitkIO.h" +#include "clitkImageToImageGenericFilter.h" + +//-------------------------------------------------------------------- +namespace clitk +{ + + template + class ITK_EXPORT MaskOfIntegratedIntensityGenericFilter: + public ImageToImageGenericFilter > + { + + public: + + //-------------------------------------------------------------------- + MaskOfIntegratedIntensityGenericFilter(); + + //-------------------------------------------------------------------- + typedef MaskOfIntegratedIntensityGenericFilter Self; + typedef itk::SmartPointer Pointer; + typedef itk::SmartPointer ConstPointer; + + //-------------------------------------------------------------------- + // Method for creation through the object factory + // and Run-time type information (and related methods) + itkNewMacro(Self); + itkTypeMacro(MaskOfIntegratedIntensityGenericFilter, LightObject); + + //-------------------------------------------------------------------- + void SetArgsInfo(const args_info_type & a); + + void SetPercentage(double p) { mPercentage = p; } + double GetPercentage() const { return mPercentage; } + + //-------------------------------------------------------------------- + // Main function called each time the filter is updated + template + void UpdateWithInputImageType(); + + protected: + template void InitializeImageType(); + args_info_type mArgsInfo; + double mPercentage; + + }; // end class + //-------------------------------------------------------------------- + +} // end namespace clitk + +#ifndef ITK_MANUAL_INSTANTIATION +#include "clitkMaskOfIntegratedIntensityGenericFilter.txx" +#endif + +#endif // #define clitkMaskOfIntegratedIntensityGenericFilter_h diff --git a/tools/clitkMaskOfIntegratedIntensityGenericFilter.txx b/tools/clitkMaskOfIntegratedIntensityGenericFilter.txx new file mode 100644 index 0000000..3096d87 --- /dev/null +++ b/tools/clitkMaskOfIntegratedIntensityGenericFilter.txx @@ -0,0 +1,169 @@ +/*========================================================================= + Program: vv http://www.creatis.insa-lyon.fr/rio/vv + + Authors belong to: + - University of LYON http://www.universite-lyon.fr/ + - Léon Bérard cancer center http://www.centreleonberard.fr + - CREATIS CNRS laboratory http://www.creatis.insa-lyon.fr + + This software is distributed WITHOUT ANY WARRANTY; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. See the copyright notices for more information. + + It is distributed under dual licence + + - BSD See included LICENSE.txt file + - CeCILL-B http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html + ===========================================================================**/ + +#ifndef clitkMaskOfIntegratedIntensityGenericFilter_txx +#define clitkMaskOfIntegratedIntensityGenericFilter_txx + +// itk include +#include "itkIntensityWindowingImageFilter.h" +#include "itkLabelStatisticsImageFilter.h" +#include "itkMaskImageFilter.h" +#include "itkMaskNegatedImageFilter.h" +#include +#include + +namespace clitk +{ + + //-------------------------------------------------------------------- + template + MaskOfIntegratedIntensityGenericFilter::MaskOfIntegratedIntensityGenericFilter(): + ImageToImageGenericFilter("MaskOfIntegratedIntensity") + { + InitializeImageType<2>(); + InitializeImageType<3>(); + } + //-------------------------------------------------------------------- + + + //-------------------------------------------------------------------- + template + template + void MaskOfIntegratedIntensityGenericFilter::InitializeImageType() + { + ADD_DEFAULT_IMAGE_TYPES(Dim); + } + //-------------------------------------------------------------------- + + + //-------------------------------------------------------------------- + template + void MaskOfIntegratedIntensityGenericFilter::SetArgsInfo(const args_info_type & a) + { + mArgsInfo=a; + this->SetIOVerbose(mArgsInfo.verbose_flag); + if (mArgsInfo.imagetypes_flag) this->PrintAvailableImageTypes(); + + this->SetInputFilename(mArgsInfo.input_arg); + this->SetOutputFilename(mArgsInfo.output_arg); + this->SetPercentage(mArgsInfo.percentage_arg); + + } + //-------------------------------------------------------------------- + + + //-------------------------------------------------------------------- + // https://stackoverflow.com/questions/1577475/c-sorting-and-keeping-track-of-indexes + template + std::vector sort_indexes(const std::vector &v) { + + // initialize original index locations + std::vector idx(v.size()); + iota(idx.begin(), idx.end(), 0); + + // sort indexes based on comparing values in v + std::sort(idx.begin(), idx.end(), + [&v](size_t i1, size_t i2) {return v[i1] > v[i2];}); + + return idx; + } + //-------------------------------------------------------------------- + + + //-------------------------------------------------------------------- + // Update with the number of dimensions and the pixeltype + //-------------------------------------------------------------------- + template + template + void + MaskOfIntegratedIntensityGenericFilter::UpdateWithInputImageType() + { + // Main filter + typedef typename InputImageType::PixelType InputPixelType; + typedef itk::Image MaskImageType; + + // Reading input + typename InputImageType::Pointer input = this->template GetInput(0); + + typename MaskImageType::Pointer mask; + mask = MaskImageType::New(); + mask->SetRegions(input->GetLargestPossibleRegion()); + mask->SetOrigin(input->GetOrigin()); + mask->SetSpacing(input->GetSpacing()); + mask->Allocate(); + mask->FillBuffer(0); + + // Get a vector of all values (will be easier to sort) + // And compute total sum of values + std::vector values; + typedef itk::ImageRegionIterator IteratorInputType; + IteratorInputType iter(input, input->GetLargestPossibleRegion()); + iter.GoToBegin(); + double total = 0.0; + while (!iter.IsAtEnd()) { + values.push_back(iter.Get()); + total += iter.Get(); + ++iter; + } + + // Sort (reverse) + auto indices = sort_indexes(values); + + // Get max index of pixel to reach xx percent + double current = 0.0; + double max = GetPercentage()/100.0*total; + int i=0; + auto n = input->GetLargestPossibleRegion().GetNumberOfPixels(); + std::vector should_keep(values.size());; + std::fill(should_keep.begin(), should_keep.end(), 0); + while (current IteratorMaskType; + IteratorMaskType itm(mask, mask->GetLargestPossibleRegion()); + iter.GoToBegin(); + itm.GoToBegin(); + i = 0; + while (!iter.IsAtEnd()) { + if (should_keep[i]) itm.Set(1); + ++iter; + ++itm; + ++i; + } + + // Verbose option + if (this->m_IOVerbose) + std::cout << "Sum of pixel values : " << total << std::endl + << "Percentage : " << GetPercentage() << "%" << std::endl + << "Number of pixels : " << nb << "/" << n << std::endl + << "Number of pixels : " << nb/n*100.0 << "%" << std::endl; + + // Write/Save results + this->template SetNextOutput(mask); + } + //-------------------------------------------------------------------- + + +}//end clitk + +#endif //#define clitkMaskOfIntegratedIntensityGenericFilter_txx -- 2.47.1