From f79968f83cb36df7db9cb4e5f0ff1a47cb83a489 Mon Sep 17 00:00:00 2001 From: =?utf8?q?Leonardo=20Fl=C3=B3rez-Valencia?= Date: Tue, 26 Sep 2017 15:47:04 -0500 Subject: [PATCH] ... --- CMakeLists.txt | 57 ++ cmake/Definitions.cmake | 53 + cmake/Functions.cmake | 141 +++ cmake/InstallCommands.cmake | 40 + cmake/cpPluginsConfig.cmake.in | 26 + lib/CMakeLists.txt | 12 + lib/cpPlugins/CMakeLists.txt | 11 + lib/cpPlugins/Config.h.in | 43 + .../Interface/ComponentInterface.cxx | 64 ++ lib/cpPlugins/Interface/ComponentInterface.h | 66 ++ lib/cpPlugins/Interface/GarbageCollector.h | 50 + lib/cpPlugins/Interface/GarbageCollector.hxx | 65 ++ lib/cpPlugins/Interface/Manager.cxx | 225 +++++ lib/cpPlugins/Interface/Manager.h | 71 ++ lib/cpPlugins/Pipeline/Object.cxx | 207 ++++ lib/cpPlugins/Pipeline/Object.h | 79 ++ lib/cpPlugins/Pipeline/Parameters.cxx | 705 ++++++++++++++ lib/cpPlugins/Pipeline/Parameters.h | 207 ++++ lib/cpPlugins/Pipeline/ProcessObject.h | 46 + lib/cpPlugins/Utils/ExpandTemplates.cxx | 178 ++++ lib/cpPlugins/Utils/ExpandTemplates.h | 61 ++ lib/cpPlugins/Version.cxx.in | 7 + lib/ivq/CMakeLists.txt | 25 + lib/ivq/Config.h.in | 20 + lib/ivq/ITK/BooleanMapSaliencyFunction.h | 81 ++ lib/ivq/ITK/BooleanMapSaliencyFunction.hxx | 92 ++ lib/ivq/ITK/CPRImageFilter.h | 84 ++ lib/ivq/ITK/CPRImageFilter.hxx | 133 +++ lib/ivq/ITK/ExtractLabelFunction.h | 73 ++ lib/ivq/ITK/ExtractLabelFunction.hxx | 40 + lib/ivq/ITK/ImageROIFromFunction.h | 83 ++ lib/ivq/ITK/ImageROIFromFunction.hxx | 99 ++ lib/ivq/ITK/ImageStatisticsFromSeeds.h | 82 ++ lib/ivq/ITK/ImageStatisticsFromSeeds.hxx | 125 +++ lib/ivq/ITK/ImageUnaryFunctionFilter.h | 72 ++ lib/ivq/ITK/ImageUnaryFunctionFilter.hxx | 67 ++ lib/ivq/ITK/IncrementalMeanAndVariance.cxx | 75 ++ lib/ivq/ITK/IncrementalMeanAndVariance.h | 46 + lib/ivq/ITK/IsoImageSlicer.h | 214 ++++ lib/ivq/ITK/IsoImageSlicer.hxx | 209 ++++ lib/ivq/ITK/PeakDetector.cxx | 188 ++++ lib/ivq/ITK/PeakDetector.h | 76 ++ lib/ivq/ITK/RasterContourFilter.h | 108 +++ lib/ivq/ITK/RasterContourFilter.hxx | 175 ++++ lib/ivq/ITK/Simple3DCurve.cxx | 177 ++++ lib/ivq/ITK/Simple3DCurve.h | 83 ++ lib/ivq/ITK/ThresholdFunction.h | 89 ++ lib/ivq/ITK/ThresholdFunction.hxx | 98 ++ lib/ivq/Qt/DicomSeriesSelectorDialog.cxx | 34 + lib/ivq/Qt/DicomSeriesSelectorDialog.h | 46 + lib/ivq/Qt/DicomSeriesSelectorDialog.ui | 81 ++ lib/ivq/Qt/DicomSeriesSelectorWidget.cxx | 187 ++++ lib/ivq/Qt/DicomSeriesSelectorWidget.h | 75 ++ lib/ivq/Qt/DicomSeriesSelectorWidget.ui | 89 ++ lib/ivq/Qt/ImageViewerWidget.cxx | 33 + lib/ivq/Qt/ImageViewerWidget.h | 48 + lib/ivq/Qt/MPRViewersWidget.cxx | 70 ++ lib/ivq/Qt/MPRViewersWidget.h | 53 + lib/ivq/Qt/MPRViewersWidget.ui | 71 ++ lib/ivq/Qt/RendererWidget.cxx | 34 + lib/ivq/Qt/RendererWidget.h | 44 + lib/ivq/VTK/BrushWidget.cxx | 639 ++++++++++++ lib/ivq/VTK/BrushWidget.h | 112 +++ lib/ivq/VTK/ImageActor.cxx | 217 +++++ lib/ivq/VTK/ImageActor.h | 82 ++ lib/ivq/VTK/ImageSlicePointPlacer.cxx | 280 ++++++ lib/ivq/VTK/ImageSlicePointPlacer.h | 87 ++ lib/ivq/VTK/ImageViewer.cxx | 913 ++++++++++++++++++ lib/ivq/VTK/ImageViewer.h | 160 +++ lib/ivq/VTK/InteractorStyleImage.cxx | 275 ++++++ lib/ivq/VTK/InteractorStyleImage.h | 76 ++ lib/ivq/VTK/MPRViewers.cxx | 197 ++++ lib/ivq/VTK/MPRViewers.h | 78 ++ lib/ivq/VTK/PolyDataActor.cxx | 129 +++ lib/ivq/VTK/PolyDataActor.h | 80 ++ lib/ivq/VTK/SeedWidget.cxx | 109 +++ lib/ivq/VTK/SeedWidget.h | 54 ++ lib/ivq/VTK/SeedWidgetOverImageActor.cxx | 224 +++++ lib/ivq/VTK/SeedWidgetOverImageActor.h | 78 ++ lib/ivq/VTK/Simple3DCurveToPolyData.cxx | 119 +++ lib/ivq/VTK/Simple3DCurveToPolyData.h | 66 ++ lib/ivq/Version.cxx.in | 15 + 82 files changed, 9883 insertions(+) create mode 100644 CMakeLists.txt create mode 100644 cmake/Definitions.cmake create mode 100644 cmake/Functions.cmake create mode 100644 cmake/InstallCommands.cmake create mode 100644 cmake/cpPluginsConfig.cmake.in create mode 100644 lib/CMakeLists.txt create mode 100644 lib/cpPlugins/CMakeLists.txt create mode 100644 lib/cpPlugins/Config.h.in create mode 100644 lib/cpPlugins/Interface/ComponentInterface.cxx create mode 100644 lib/cpPlugins/Interface/ComponentInterface.h create mode 100644 lib/cpPlugins/Interface/GarbageCollector.h create mode 100644 lib/cpPlugins/Interface/GarbageCollector.hxx create mode 100644 lib/cpPlugins/Interface/Manager.cxx create mode 100644 lib/cpPlugins/Interface/Manager.h create mode 100644 lib/cpPlugins/Pipeline/Object.cxx create mode 100644 lib/cpPlugins/Pipeline/Object.h create mode 100644 lib/cpPlugins/Pipeline/Parameters.cxx create mode 100644 lib/cpPlugins/Pipeline/Parameters.h create mode 100644 lib/cpPlugins/Pipeline/ProcessObject.h create mode 100644 lib/cpPlugins/Utils/ExpandTemplates.cxx create mode 100644 lib/cpPlugins/Utils/ExpandTemplates.h create mode 100644 lib/cpPlugins/Version.cxx.in create mode 100644 lib/ivq/CMakeLists.txt create mode 100644 lib/ivq/Config.h.in create mode 100644 lib/ivq/ITK/BooleanMapSaliencyFunction.h create mode 100644 lib/ivq/ITK/BooleanMapSaliencyFunction.hxx create mode 100644 lib/ivq/ITK/CPRImageFilter.h create mode 100644 lib/ivq/ITK/CPRImageFilter.hxx create mode 100644 lib/ivq/ITK/ExtractLabelFunction.h create mode 100644 lib/ivq/ITK/ExtractLabelFunction.hxx create mode 100644 lib/ivq/ITK/ImageROIFromFunction.h create mode 100644 lib/ivq/ITK/ImageROIFromFunction.hxx create mode 100644 lib/ivq/ITK/ImageStatisticsFromSeeds.h create mode 100644 lib/ivq/ITK/ImageStatisticsFromSeeds.hxx create mode 100644 lib/ivq/ITK/ImageUnaryFunctionFilter.h create mode 100644 lib/ivq/ITK/ImageUnaryFunctionFilter.hxx create mode 100644 lib/ivq/ITK/IncrementalMeanAndVariance.cxx create mode 100644 lib/ivq/ITK/IncrementalMeanAndVariance.h create mode 100644 lib/ivq/ITK/IsoImageSlicer.h create mode 100644 lib/ivq/ITK/IsoImageSlicer.hxx create mode 100644 lib/ivq/ITK/PeakDetector.cxx create mode 100644 lib/ivq/ITK/PeakDetector.h create mode 100644 lib/ivq/ITK/RasterContourFilter.h create mode 100644 lib/ivq/ITK/RasterContourFilter.hxx create mode 100644 lib/ivq/ITK/Simple3DCurve.cxx create mode 100644 lib/ivq/ITK/Simple3DCurve.h create mode 100644 lib/ivq/ITK/ThresholdFunction.h create mode 100644 lib/ivq/ITK/ThresholdFunction.hxx create mode 100644 lib/ivq/Qt/DicomSeriesSelectorDialog.cxx create mode 100644 lib/ivq/Qt/DicomSeriesSelectorDialog.h create mode 100644 lib/ivq/Qt/DicomSeriesSelectorDialog.ui create mode 100644 lib/ivq/Qt/DicomSeriesSelectorWidget.cxx create mode 100644 lib/ivq/Qt/DicomSeriesSelectorWidget.h create mode 100644 lib/ivq/Qt/DicomSeriesSelectorWidget.ui create mode 100644 lib/ivq/Qt/ImageViewerWidget.cxx create mode 100644 lib/ivq/Qt/ImageViewerWidget.h create mode 100644 lib/ivq/Qt/MPRViewersWidget.cxx create mode 100644 lib/ivq/Qt/MPRViewersWidget.h create mode 100644 lib/ivq/Qt/MPRViewersWidget.ui create mode 100644 lib/ivq/Qt/RendererWidget.cxx create mode 100644 lib/ivq/Qt/RendererWidget.h create mode 100644 lib/ivq/VTK/BrushWidget.cxx create mode 100644 lib/ivq/VTK/BrushWidget.h create mode 100644 lib/ivq/VTK/ImageActor.cxx create mode 100644 lib/ivq/VTK/ImageActor.h create mode 100644 lib/ivq/VTK/ImageSlicePointPlacer.cxx create mode 100644 lib/ivq/VTK/ImageSlicePointPlacer.h create mode 100644 lib/ivq/VTK/ImageViewer.cxx create mode 100644 lib/ivq/VTK/ImageViewer.h create mode 100644 lib/ivq/VTK/InteractorStyleImage.cxx create mode 100644 lib/ivq/VTK/InteractorStyleImage.h create mode 100644 lib/ivq/VTK/MPRViewers.cxx create mode 100644 lib/ivq/VTK/MPRViewers.h create mode 100644 lib/ivq/VTK/PolyDataActor.cxx create mode 100644 lib/ivq/VTK/PolyDataActor.h create mode 100644 lib/ivq/VTK/SeedWidget.cxx create mode 100644 lib/ivq/VTK/SeedWidget.h create mode 100644 lib/ivq/VTK/SeedWidgetOverImageActor.cxx create mode 100644 lib/ivq/VTK/SeedWidgetOverImageActor.h create mode 100644 lib/ivq/VTK/Simple3DCurveToPolyData.cxx create mode 100644 lib/ivq/VTK/Simple3DCurveToPolyData.h create mode 100644 lib/ivq/Version.cxx.in diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..335f9e9 --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,57 @@ +## ========================================================================= +## @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) +## ========================================================================= + +cmake_minimum_required(VERSION 3.0) + +## == Basic project configuration +set(prj_NAME cpPlugins) +set(prj_MAJ 1) +set(prj_MIN 0) +set(prj_REL 0) + +## == Project definition +project(${prj_NAME} VERSION "${prj_MAJ}.${prj_MIN}.${prj_REL}") + +## == Project policies +set(_policies CMP0015 CMP0020 CMP0042 CMP0053) +foreach(_p ${_policies}) + if(POLICY ${_p}) + cmake_policy(SET ${_p} NEW) + endif(POLICY ${_p}) +endforeach(_p) + +## == Some general configuration +include(cmake/Definitions.cmake) +include(cmake/Functions.cmake) + +## == Find ITK +find_package(ITK CONFIG REQUIRED) +include(${ITK_USE_FILE}) + +## == Find VTK, only if linked against ITK +set(cpPlugins_USE_VTK 0) +if(ITKVtkGlue_LOADED) + find_package(VTK CONFIG REQUIRED) + include(${VTK_USE_FILE}) + set(cpPlugins_USE_VTK 1) +endif(ITKVtkGlue_LOADED) + +## == Find Qt5, only if linked against VTK +set(cpPlugins_USE_Qt5 0) +if(VTK_FOUND) + if(Qt5_DIR) + find_package(Qt5 CONFIG REQUIRED COMPONENTS Widgets) + set(CMAKE_INCLUDE_CURRENT_DIR ON) + set(CMAKE_AUTOMOC ON) + set(cpPlugins_USE_Qt5 1) + endif(Qt5_DIR) +endif(VTK_FOUND) + +## == Build packages +subdirs(lib) + +## == Installation commands +include(cmake/InstallCommands.cmake) + +## eof - $RCSfile$ diff --git a/cmake/Definitions.cmake b/cmake/Definitions.cmake new file mode 100644 index 0000000..46fb5cf --- /dev/null +++ b/cmake/Definitions.cmake @@ -0,0 +1,53 @@ +## ========================================================================= +## @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) +## ========================================================================= + +## == If working on a MacOSX, activate the use of RPATH's +## == Furthermore: prepare the type of executables +set(EXECUTABLE_TYPE "" CACHE STRING "Executable linking." FORCE) +if(APPLE) + set(EXECUTABLE_TYPE "MACOSX_BUNDLE" CACHE STRING "Executable linking." FORCE) + set(CMAKE_MACOSX_RPATH true CACHE BOOL "Use RPATH's on MacOSX." FORCE) + mark_as_advanced(CMAKE_MACOSX_RPATH) +elseif(WIN32) + set(EXECUTABLE_TYPE "WIN32" CACHE STRING "Executable linking." FORCE) +endif(APPLE) +mark_as_advanced(EXECUTABLE_TYPE) + +## == Force c++11 +if(NOT MSVC) + include(CheckCXXCompilerFlag) + check_cxx_compiler_flag("-std=c++11" COMPILER_SUPPORTS_CXX11) + if(COMPILER_SUPPORTS_CXX11) + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11") + else(COMPILER_SUPPORTS_CXX11) + check_cxx_compiler_flag("-std=c++0x" COMPILER_SUPPORTS_CXX0X) + if(COMPILER_SUPPORTS_CXX0X) + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++0x") + else(COMPILER_SUPPORTS_CXX0X) + message( + FATAL_ERROR + "The compiler ${CMAKE_CXX_COMPILER} has no C++11 support." + ) + endif(COMPILER_SUPPORTS_CXX0X) + endif(COMPILER_SUPPORTS_CXX11) +endif(NOT MSVC) + +## == Prepare header generator to build shared libs +include(GenerateExportHeader) + +## == Do not allow to build inside the source tree +if(PROJECT_BINARY_DIR STREQUAL ${PROJECT_SOURCE_DIR}) + message(FATAL_ERROR "Building in the source tree is not allowed.") +endif(PROJECT_BINARY_DIR STREQUAL ${PROJECT_SOURCE_DIR}) + +## == Where to put targets (executables and libs) +set(EXECUTABLE_OUTPUT_PATH ${PROJECT_BINARY_DIR}) +set(LIBRARY_OUTPUT_PATH ${PROJECT_BINARY_DIR}) +mark_as_advanced( + CMAKE_BACKWARDS_COMPATIBILITY + EXECUTABLE_OUTPUT_PATH + LIBRARY_OUTPUT_PATH + ) + +## eof - $RCSfile$ diff --git a/cmake/Functions.cmake b/cmake/Functions.cmake new file mode 100644 index 0000000..8ca0f15 --- /dev/null +++ b/cmake/Functions.cmake @@ -0,0 +1,141 @@ +## ========================================================================= +## @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) +## ========================================================================= + +## ------------------------------------------------------------------------- +function(BuildLibrary lib typ src maj min rel) + +## -- Get sources +set(_files) +foreach(_s ${src}) + + ## -- Canonicalize path + get_filename_component(_p "${_s}" ABSOLUTE) + + ## -- Check type of input + if(IS_DIRECTORY ${_p}) + file(GLOB _f "${_p}/*") + foreach(_x ${_f}) + if(NOT IS_DIRECTORY ${_x}) + list(APPEND _files ${_x}) + endif(NOT IS_DIRECTORY ${_x}) + endforeach(_x) + else(IS_DIRECTORY ${_p}) + list(APPEND _files ${_p}) + endif(IS_DIRECTORY ${_p}) + +endforeach(_s) + +## -- Process sources +set(_cpp) +set(_hpp) +set(_qui) +foreach(_f ${_files}) + + ## -- Separate filename from extension + string(REGEX REPLACE "\\.[^.]*$" "" _name ${_f}) + string(REPLACE ${_name} "" _ext ${_f}) + set(_out_name ${_name}) + set(_out_ext ${_ext}) + + ## -- Process .in files + string(COMPARE EQUAL "${_ext}" ".in" _in_cmp) + if(_in_cmp) + string(REPLACE ${PROJECT_SOURCE_DIR} ${PROJECT_BINARY_DIR} _out ${_name}) + configure_file(${_f} ${_out} @ONLY) + string(REGEX REPLACE "\\.[^.]*$" "" _out_name ${_out}) + string(REPLACE ${_out_name} "" _out_ext ${_out}) + endif(_in_cmp) + + ## -- Now, get real extension + string(SUBSTRING ${_out_ext} 0 2 _ext_cmp) + + ## -- Process .c?? files + string(COMPARE EQUAL "${_ext_cmp}" ".c" _c_cmp) + if(_c_cmp) + list(APPEND _cpp ${_out_name}${_out_ext}) + endif(_c_cmp) + + ## -- Process .h?? files + string(COMPARE EQUAL "${_ext_cmp}" ".h" _h_cmp) + if(_h_cmp) + list(APPEND _hpp ${_out_name}${_out_ext}) + endif(_h_cmp) + + ## -- Process .ui files + string(COMPARE EQUAL "${_out_ext}" ".ui" _u_cmp) + if(_u_cmp) + list(APPEND _qui ${_out_name}${_out_ext}) + endif(_u_cmp) + +endforeach(_f) + +## -- Process Qt ui files +list(LENGTH _qui _qui_len) +if(${_qui_len} GREATER 0) + qt5_wrap_ui(_qui_hpp ${_qui}) +endif(${_qui_len} GREATER 0) + +## -- Real build +add_library(${lib} ${typ} ${_cpp} ${_hpp} ${_qui_hpp}) + +## -- Header creation +generate_export_header(${lib}) +set_property(TARGET ${lib} PROPERTY VERSION "${maj}.${min}.${rel}") +set_property(TARGET ${lib} PROPERTY SOVERSION ${maj}) +set_property(TARGET ${lib} PROPERTY INTERFACE_${lib}_MAJOR_VERSION ${maj}) +set_property(TARGET ${lib} APPEND PROPERTY COMPATIBLE_INTERFACE_STRING ${maj}) + +## -- Link library +target_link_libraries(${lib} PUBLIC ${ARGN}) + +## -- Installation rules +option(${lib}_INSTALL_DEVEL "Install development files for ${lib}" OFF) +string(COMPARE EQUAL "${type}" "SHARED" _cmp) +if(_cmp OR ${lib}_INSTALL_DEVEL) + install( + TARGETS ${lib} + EXPORT "${targets_export_name}" + LIBRARY DESTINATION "lib" + ARCHIVE DESTINATION "lib" + RUNTIME DESTINATION "bin" + INCLUDES DESTINATION "${include_install_dir}" + ) +endif(_cmp OR ${lib}_INSTALL_DEVEL) +if(${lib}_INSTALL_DEVEL) + string(TOLOWER ${lib} _lower_lib) + set( + _install_hdr + ${_hpp} + ${CMAKE_CURRENT_BINARY_DIR}/${_lower_lib}_export.h + ) + set(_install_dirs) + foreach(_h ${_install_hdr}) + string(REPLACE ${CMAKE_CURRENT_SOURCE_DIR} "" _h_name ${_h}) + string(COMPARE EQUAL "${_h_name}" "${_h}" _h_cmp) + if(_h_cmp) + string(REPLACE ${CMAKE_CURRENT_BINARY_DIR} "" _h_name ${_h}) + endif(_h_cmp) + set(_h_out ${include_install_dir}/${lib}${_h_name}) + get_filename_component(_h_dir ${_h_out} DIRECTORY) + install( + FILES "${_h}" + DESTINATION "${_h_dir}" + ) + endforeach(_h) +endif(${lib}_INSTALL_DEVEL) + +endfunction() + +## ------------------------------------------------------------------------- +function(BuildLibraryRecursive lib typ dir maj min rel) + +## -- Globbing directory +file(GLOB_RECURSE _files "${dir}/*") + +## -- Build library +BuildLibrary(${lib} ${typ} "${_files}" ${maj} ${min} ${rel} ${ARGN}) + +endfunction() + +## eof - $RCSfile$ diff --git a/cmake/InstallCommands.cmake b/cmake/InstallCommands.cmake new file mode 100644 index 0000000..97500ae --- /dev/null +++ b/cmake/InstallCommands.cmake @@ -0,0 +1,40 @@ +## ========================================================================= +## @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) +## ========================================================================= + +## ========================= +## == Installation values == +## ========================= + +set(config_install_dir "lib/cmake/${PROJECT_NAME}") +set(include_install_dir "include") +set(generated_dir "${PROJECT_BINARY_DIR}/generated") +set(version_config "${generated_dir}/${PROJECT_NAME}ConfigVersion.cmake") +set(project_config "${generated_dir}/${PROJECT_NAME}Config.cmake") +set(targets_export_name "${PROJECT_NAME}Targets") +set(namespace "${PROJECT_NAME}::") + +## =============================== +## == Global installation rules == +## =============================== + +include(CMakePackageConfigHelpers) +write_basic_package_version_file( + "${version_config}" COMPATIBILITY SameMajorVersion + ) +configure_package_config_file( + "cmake/${PROJECT_NAME}Config.cmake.in" + "${project_config}" + INSTALL_DESTINATION "${config_install_dir}" + ) +install( + EXPORT "${targets_export_name}" + NAMESPACE "${namespace}" + DESTINATION "${config_install_dir}" + ) +install( + FILES "${project_config}" + DESTINATION "${config_install_dir}" + ) + +## eof - $RCSfile$ diff --git a/cmake/cpPluginsConfig.cmake.in b/cmake/cpPluginsConfig.cmake.in new file mode 100644 index 0000000..891261c --- /dev/null +++ b/cmake/cpPluginsConfig.cmake.in @@ -0,0 +1,26 @@ +@PACKAGE_INIT@ + +include("${CMAKE_CURRENT_LIST_DIR}/@targets_export_name@.cmake") +check_required_components("@PROJECT_NAME@") + +## =========================================== +## == Find needed packages and dependencies == +## =========================================== + +set(ITK_DIR "@ITK_DIR@") +set(VTK_DIR "@VTK_DIR@") +set(Qt5_DIR "@Qt5_DIR@") + +find_package(ITK CONFIG REQUIRED) +include(${ITK_USE_FILE}) +if(NOT "${VTK_DIR}" STREQUAL "") + find_package(VTK CONFIG REQUIRED) + include(${VTK_USE_FILE}) +endif(NOT "${VTK_DIR}" STREQUAL "") +if(NOT "${Qt5_DIR}" STREQUAL "") + find_package(Qt5 CONFIG REQUIRED COMPONENTS Widgets) + set(CMAKE_INCLUDE_CURRENT_DIR ON) + set(CMAKE_AUTOMOC ON) +endif(NOT "${Qt5_DIR}" STREQUAL "") + +## eof - $RCSfile$ diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt new file mode 100644 index 0000000..64b550f --- /dev/null +++ b/lib/CMakeLists.txt @@ -0,0 +1,12 @@ +## ========================================================================= +## @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) +## ========================================================================= + +## == Build libraries +include_directories( + ${CMAKE_CURRENT_SOURCE_DIR} + ${CMAKE_CURRENT_BINARY_DIR} + ) +subdirs(ivq cpPlugins) + +## eof - $RCSfile$ diff --git a/lib/cpPlugins/CMakeLists.txt b/lib/cpPlugins/CMakeLists.txt new file mode 100644 index 0000000..b663bc1 --- /dev/null +++ b/lib/cpPlugins/CMakeLists.txt @@ -0,0 +1,11 @@ +## ========================================================================= +## @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) +## ========================================================================= + +BuildLibraryRecursive( + cpPlugins SHARED . + ${prj_MAJ} ${prj_MIN} ${prj_REL} + ${ITK_LIBRARIES} ${VTK_LIBRARIES} + ) + +## eof - $RCSfile$ diff --git a/lib/cpPlugins/Config.h.in b/lib/cpPlugins/Config.h.in new file mode 100644 index 0000000..b6117ce --- /dev/null +++ b/lib/cpPlugins/Config.h.in @@ -0,0 +1,43 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __cpPlugins__Config__h__ +#define __cpPlugins__Config__h__ + +#include + +/* ========================================================================= + * Identify OS + * ========================================================================= + */ +#define cpPlugins_OS_@CMAKE_SYSTEM_NAME@ +#ifdef cpPlugins_OS_Windows +# define cpPlugins_LIB_PREFIX "" +# define cpPlugins_ENV_SEPARATOR ";" +# define cpPlugins_PATH_SEPARATOR '\\' +# define cpPlugins_LIB_EXT ".dll" +#else // cpPlugins_OS_Windows +# define cpPlugins_LIB_PREFIX "lib" +# define cpPlugins_ENV_SEPARATOR ":" +# define cpPlugins_PATH_SEPARATOR '/' +# ifdef cpPlugins_OS_Linux +# define cpPlugins_LIB_EXT ".so" +# else // cpPlugins_OS_Linux +# define cpPlugins_LIB_EXT ".dylib" +# endif // cpPlugins_OS_Linux +#endif // cpPlugins_OS_Windows + +#ifdef cpPlugins_OS_Windows +# ifndef WIN32_LEAN_AND_MEAN +# define WIN32_LEAN_AND_MEAN +# endif // WIN32_LEAN_AND_MEAN +# define NOMINMAX +# include +# include +#endif // cpPlugins_OS_Windows + +#endif // __cpPlugins__Config__h__ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Interface/ComponentInterface.cxx b/lib/cpPlugins/Interface/ComponentInterface.cxx new file mode 100644 index 0000000..46a63ad --- /dev/null +++ b/lib/cpPlugins/Interface/ComponentInterface.cxx @@ -0,0 +1,64 @@ +/* TODO + #include + + cpPlugins::ComponentInterface::ComponentInterface(void* lib_handle, void* component_reference, std::string component_name, + std::string lib_name) { + this->component_reference = component_reference; + this->component_name = component_name; + this->lib_name = lib_name; + this->destructor = (component_destructor)dlsym(lib_handle, "destroy_component"); + this->updater = (component_updater)dlsym(lib_handle, "update_component"); + this->getOutput = (component_getOutput)dlsym(lib_handle, "getOutput_component"); + this->setInput = (component_setInput)dlsym(lib_handle, "setInput_component"); + } + + cpPlugins::ComponentInterface::~ComponentInterface() { + // Destroy component reference + (this->destructor)(const_cast((this->component_name).c_str()), this->component_reference); + } + + void cpPlugins::ComponentInterface::Update() { + (this->updater)(const_cast((this->component_name).c_str()), this->component_reference); + } + + void cpPlugins::ComponentInterface::SetInput(void* input) { + (this->setInput)(const_cast((this->component_name).c_str()), this->component_reference, input); + } + + void* cpPlugins::ComponentInterface::GetOutput() { + return (this->getOutput)(const_cast((this->component_name).c_str()), this->component_reference); + } + + void* cpPlugins::ComponentInterface::GetComponent() { + return this->component_reference; + } + + void cpPlugins::ComponentInterface::SetComponent(void* component_reference) { + this->component_reference = component_reference; + } + + std::string cpPlugins::ComponentInterface::GetLibraryName() { + return this->lib_name; + } + + void cpPlugins::ComponentInterface::SetLibraryName(std::string lib_name) { + this->lib_name = lib_name; + } + + std::string cpPlugins::ComponentInterface::GetComponentName() { + return this->component_name; + } + + void cpPlugins::ComponentInterface::SetComponentName(std::string component_reference) { + this->component_name = component_name; + } + + void cpPlugins::ComponentInterface::SetComponentDestructor(void* lib_handle) { + this->destructor = (component_destructor)dlsym(lib_handle, "destroy_component");; + } + + void cpPlugins::ComponentInterface::SetComponentUpdater(void* lib_handle) { + this->updater = (component_updater)dlsym(lib_handle, "update_component"); + } + +*/ diff --git a/lib/cpPlugins/Interface/ComponentInterface.h b/lib/cpPlugins/Interface/ComponentInterface.h new file mode 100644 index 0000000..7e96515 --- /dev/null +++ b/lib/cpPlugins/Interface/ComponentInterface.h @@ -0,0 +1,66 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __cpPlugins__Interface__ComponentInterface__h__ +#define __cpPlugins__Interface__ComponentInterface__h__ + +/* TODO + #include + #include + #include + #include + + namespace cpPlugins + { + namespace Interface + { + class CPPLUGINS_EXPORT ComponentInterface + : public std::enable_shared_from_this< ComponentInterface > + { + public: + typedef ComponentInterface Self; + typedef std::enable_shared_from_this< ComponentInterface > Superclass; + + typedef void(*TDestructor)(char*, void*); + typedef void(*TUpdater)(char*, void*); + typedef void*(*TOutput)(char*, void*); + typedef void(*TInput)(char*, void*, void*); + + // Variable definition + private: + TDestructor destructor; + TUpdater updater; + TOutput getOutput; + TInput setInput; + std::string lib_name; + std::string component_name; + void* component_reference; + + // Method definition + public: + ComponentInterface(void* lib_handle, void* component_reference, + std::string component_name, std::string lib_name); + virtual ~ComponentInterface(); + void Update(); + void SetInput(void* input); + void* GetOutput(); + void* GetComponent(); + void SetComponent(void* reference); + std::string GetLibraryName(); + void SetLibraryName(std::string lib_name); + std::string GetComponentName(); + void SetComponentName(std::string component_name); + void SetComponentDestructor(void* lib_handle); + void SetComponentUpdater(void* lib_handle); + }; + + } // ecapseman + + } // ecapseman +*/ + +#endif // __cpPlugins__Interface__ComponentInterface__h__ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Interface/GarbageCollector.h b/lib/cpPlugins/Interface/GarbageCollector.h new file mode 100644 index 0000000..95b3311 --- /dev/null +++ b/lib/cpPlugins/Interface/GarbageCollector.h @@ -0,0 +1,50 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __cpPlugins__Interface__GarbageCollector__h__ +#define __cpPlugins__Interface__GarbageCollector__h__ + +/* TODO + #include + #include + #include + #include +*/ + +namespace cpPlugins +{ + namespace Interface + { + /** + */ + template< class _TComponent > + class GarbageCollector + { + public: + typedef GarbageCollector Self; + typedef _TComponent TComponent; + typedef uintptr_t TKey; + typedef std::shared_ptr< TComponent > TResource; + typedef std::weak_ptr< TComponent > TReference; + typedef std::map< TKey, TReference > THandler; + + public: + GarbageCollector( ); + virtual ~GarbageCollector( ); + TResource CreateManager( TComponent* component_object ); + TReference GetReference( TComponent* component_object ); + + private: + THandler m_Handler; + }; + + } // ecapseman + +} // ecapseman + +#include +#endif // __cpPlugins__Interface__GarbageCollector__h__ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Interface/GarbageCollector.hxx b/lib/cpPlugins/Interface/GarbageCollector.hxx new file mode 100644 index 0000000..6d0089c --- /dev/null +++ b/lib/cpPlugins/Interface/GarbageCollector.hxx @@ -0,0 +1,65 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __cpPlugins__Interface__GarbageCollector__hxx__ +#define __cpPlugins__Interface__GarbageCollector__hxx__ + +// ------------------------------------------------------------------------- +template< class _TComponent > +cpPlugins::Interface::GarbageCollector< _TComponent >:: +GarbageCollector( ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TComponent > +cpPlugins::Interface::GarbageCollector< _TComponent >:: +~GarbageCollector( ) +{ + /* TODO + std::cout << "Deleting garbage collector..." << std :: endl; + */ +} + +// ------------------------------------------------------------------------- +template< class _TComponent > +typename cpPlugins::Interface::GarbageCollector< _TComponent >::TResource +cpPlugins::Interface::GarbageCollector< _TComponent >:: +CreateManager( TComponent* component_object ) +{ + TKey new_key = reinterpret_cast< TKey >( component_object ); + TResource new_obj = + std::shared_ptr< TComponent >( + component_object, + [&]( TComponent* component_object ) + { // begin + /* TODO + std::cout << "Component " << component_object->GetComponentName( ) << "( " << component_object << " ) is going out of scope, deleting..." << std::endl; + */ + this->m_Handler.erase( reinterpret_cast< TKey >( component_object ) ); + delete component_object; + } // end + ); + this->m_Handler[ new_key ] = new_obj; + return( component_object->shared_from_this( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TComponent > +typename cpPlugins::Interface::GarbageCollector< _TComponent >::TReference +cpPlugins::Interface::GarbageCollector< _TComponent >:: +GetReference( TComponent* pointer ) +{ + TKey key = reinterpret_cast< TKey >( pointer ); + THandler::const_iterator it = this->m_Handler.find( key ); + if( it != this->m_Handler.end( ) ) + return( it->second ); + else + return( TReference( NULL ) ); +} + +#endif // __cpPlugins__Interface__GarbageCollector__hxx__ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Interface/Manager.cxx b/lib/cpPlugins/Interface/Manager.cxx new file mode 100644 index 0000000..d4c08c4 --- /dev/null +++ b/lib/cpPlugins/Interface/Manager.cxx @@ -0,0 +1,225 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#include + +// ------------------------------------------------------------------------- +cpPlugins::Interface::Manager:: +Manager( ) +{ +} + +// ------------------------------------------------------------------------- +cpPlugins::Interface::Manager:: +~Manager( ) +{ +} + +// ------------------------------------------------------------------------- +/* TODO + std::set< std::string > cpPlugins::Manager:: + GetContents( ) + { + // If there are no libraries loaded, throw empty handler exception + if( this->m_Libraries.empty( ) ) + throw std::runtime_error( "There are no libraries loaded in the system" ); + + std::set< std::string > libraries_components; + + // Iterate through map + std::map< std::string, void* >::iterator it; + for( it = this->m_Libraries.begin( ); it != this->m_Libraries.end( ); ++it ) + { + // Pointer to function names, adquire names + char**( *get_library_components )( ); + get_library_components = ( char**( * )( ) )dlsym( it->second, "get_library_components" ); + char** library_components = get_library_components( ); + char** iterator = library_components; + while( *iterator ) + { + // Insert "library_name::component_name" + libraries_components.insert( + it->first + std::string( "::" ) + std::string( *iterator ) + ); + + // Free memory + free( *iterator ); + iterator++; + + } // elihw + free( library_components ); + + } // rof + return( libraries_components ); + } + +// ------------------------------------------------------------------------- +void cpPlugins::Manager:: +LoadLibrary( const std::string& lib_name ) +{ +void* lib = dlopen( lib_name, RTLD_LAZY ); + +if( lib == NULL ) +throw std::runtime_error( +"Unable to load " + std::string( lib_name ) + +std::string( " library: " ) + std::string( dlerror( ) ) + "\n" +); + +// Get constructor function from lib +dispatcher component_dispatcher = +( dispatcher )dlsym( lib, "dispatch_component" ); + +if( component_dispatcher == NULL ) +throw std::runtime_error( +"Unable to load dispatcher method from dynamic library: " + +std::string( dlerror( ) ) + std::string( "\n" ) +); + + +// Get destructor function from lib +destructor component_destructor = ( destructor )dlsym( lib, "destroy_component" ); + +if( component_destructor == NULL ) +throw std::runtime_error( +"Unable to load destructor method from dynamic library: " + +std::string( dlerror( ) ) + std::string( "\n" ) +); + +// Get updater function from lib +updater component_updater = ( updater )dlsym( lib, "update_component" ); + +if( component_updater == NULL ) +throw std::runtime_error( +"Unable to load updater method from dynamic library: " + +std::string( dlerror( ) ) + std::string( "\n" ) +); + + +// Register into library handler +this->m_Libraries[ lib_name ] = lib; + +// Register garbage collector +GarbageCollector* garbage_collector = +new GarbageCollector( ); + +this->m_Collector. +insert( std::pair* > +( +std::string( lib_name ), garbage_collector +) +); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Manager:: +UnloadLibrary( const std::string& lib_name ) +{ +// Validate library existence +void* lib; +if( !this->m_Libraries.empty( ) ) +{ +try +{ +lib = this->m_Libraries.at( lib_name ); +} +catch( const std::exception& err ) +{ +throw std::runtime_error( +"The requested library has not been loaded into the system" +); + +} // yrt +} +else +throw std::runtime_error( "There are no libraries loaded in the system" ); + +// Close library handle +dlclose( lib ); + +// Erase register from handler +this->m_Libraries.erase( lib_name ); + +// Erase register from garbage collector +delete this->m_Collector.at( lib_name ); +this->m_Collector.erase( lib_name ); +} + +// ------------------------------------------------------------------------- +std::shared_ptr< cpPlugins::Manager::TComponent > cpPlugins::Manager:: +CreateComponent( +const std::string& lib_name, const std::string& component_name +) +{ +// Validate library existence +void* lib; +if( !this->m_Libraries.empty( ) ) +{ +try +{ +lib = this->m_Libraries.at( lib_name ); +} +catch( const std::exception& oor ) +{ +throw std::runtime_error( +"The requested library has not been loaded into the system" +); + +} // yrt +} +else +throw "There are no libraries loaded in the system"; + +// Validate component existence +component_validator component_exists = +( component_validator )dlsym( lib, "component_exists" ); + +if( !component_exists( component_name ) ) +throw std::runtime_error( +"The requested component ( " + std::string( component_name ) + +" ) doesn't exists in the library context\n" +); + +// Get constructor function from lib +dispatcher component_dispatcher = +( dispatcher )dlsym( lib, "dispatch_component" ); + +if( component_dispatcher == NULL ) +throw std::runtime_error( +"Unable to load dispatcher method from dynamic library: " + +std::string( dlerror( ) ) + std::string( "\n" ) +); + +// Get destructor function from lib +destructor component_destructor = ( destructor )dlsym( lib, "destroy_component" ); + +if( component_destructor == NULL ) +throw std::runtime_error( +"Unable to load destructor method from dynamic library: " + +std::string( dlerror( ) ) + std::string( "\n" ) +); + +// Get updater function from lib +updater component_updater = ( updater )dlsym( lib, "update_component" ); + +if( component_updater == NULL ) +throw std::runtime_error( +"Unable to load updater method from dynamic library: " + +std::string( dlerror( ) ) + std::string( "\n" ) +); + +// Dispatch requested component +void* component_reference = component_dispatcher( component_name ); + +// Create interface +ComponentInterface* component_interface = +new ComponentInterface( lib, component_reference, +std::string( component_name ), std::string( lib_name ) ); + +// Register into garbage collector and return smart_ptr +return( this->m_Collector.at( lib_name )->create_manager( component_interface ) ); +} +*/ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Interface/Manager.h b/lib/cpPlugins/Interface/Manager.h new file mode 100644 index 0000000..385ff22 --- /dev/null +++ b/lib/cpPlugins/Interface/Manager.h @@ -0,0 +1,71 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __cpPlugins__Interface__Manager__h__ +#define __cpPlugins__Interface__Manager__h__ + +#include +#include +#include +#include +/* TODO + #include + #include +*/ + +/* TODO + #include + #include + + typedef void*(*dispatcher)(char*); + typedef void(*destructor)(char*, void*); + typedef void(*updater)(char*, void*); + typedef bool(*component_validator)(char*); +*/ + +namespace cpPlugins +{ + namespace Interface + { + /** + */ + class CPPLUGINS_EXPORT Manager + { + public: + typedef Manager Self; + + /* TODO + typedef cpPlugins::Interface::ComponentInterface TComponent; + typedef cpPlugins::Interface::GarbageCollector< TComponent > TCollector; + */ + + public: + Manager( ); + virtual ~Manager( ); + + /* TODO + std::set< std::string > GetContents( ); + void LoadLibrary( const std::string& lib_name ); + void UnloadLibrary( const std::string& lib_name ); + std::shared_ptr< TComponent > CreateComponent( + const std::string& lib_name, const std::string& component_name + ); + */ + + /* TODO + private: + std::map< std::string, TCollector > m_Collectors; + std::map< std::string, void* > m_Libraries; + std::map< std::string, std::set< std::string > > m_Components; + */ + }; + + } // ecapseman + +} // ecapseman + +#endif // __cpPlugins__Interface__Manager__h__ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Pipeline/Object.cxx b/lib/cpPlugins/Pipeline/Object.cxx new file mode 100644 index 0000000..62468bf --- /dev/null +++ b/lib/cpPlugins/Pipeline/Object.cxx @@ -0,0 +1,207 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#include +#include +#include +#include +#include +#include + +// ------------------------------------------------------------------------- +cpPlugins::Pipeline::Object:: +Object( const std::string& category ) + : m_Name( "" ), + m_Category( category ), + m_Object( NULL ), + m_Type( Self::NeitherType ) +{ +} + +// ------------------------------------------------------------------------- +cpPlugins::Pipeline::Object:: +~Object( ) +{ + this->_DeleteObject( ); +} + +// ------------------------------------------------------------------------- +void* cpPlugins::Pipeline::Object:: +GetObject( ) +{ + return( this->m_Object ); +} + +// ------------------------------------------------------------------------- +const void* cpPlugins::Pipeline::Object:: +GetObject( ) const +{ + return( this->m_Object ); +} + +// ------------------------------------------------------------------------- +itk::LightObject* cpPlugins::Pipeline::Object:: +GetObjectAsITK( ) +{ + if( this->m_Object != NULL && this->m_Type == Self::ITKType ) + { + itk::LightObject::Pointer* o = + reinterpret_cast< itk::LightObject::Pointer* >( this->m_Object ); + return( o->GetPointer( ) ); + } + else + return( NULL ); +} + +// ------------------------------------------------------------------------- +const itk::LightObject* cpPlugins::Pipeline::Object:: +GetObjectAsITK( ) const +{ + if( this->m_Object != NULL && this->m_Type == Self::ITKType ) + { + const itk::LightObject::Pointer* o = + reinterpret_cast< const itk::LightObject::Pointer* >( this->m_Object ); + return( o->GetPointer( ) ); + } + else + return( NULL ); +} + +// ------------------------------------------------------------------------- +vtkObjectBase* cpPlugins::Pipeline::Object:: +GetObjectAsVTK( ) +{ + if( this->m_Object != NULL && this->m_Type == Self::VTKType ) + { + vtkSmartPointer< vtkObjectBase >* o = + reinterpret_cast< vtkSmartPointer< vtkObjectBase >* >( this->m_Object ); + return( o->GetPointer( ) ); + } + else + return( NULL ); +} + +// ------------------------------------------------------------------------- +const vtkObjectBase* cpPlugins::Pipeline::Object:: +GetObjectAsVTK( ) const +{ + if( this->m_Object != NULL && this->m_Type == Self::VTKType ) + { + const vtkSmartPointer< vtkObjectBase >* o = + reinterpret_cast< const vtkSmartPointer< vtkObjectBase >* >( + this->m_Object + ); + return( o->GetPointer( ) ); + } + else + return( NULL ); +} + +// ------------------------------------------------------------------------- +const char* cpPlugins::Pipeline::Object:: +GetClassName( ) const +{ + return( this->m_Name.c_str( ) ); +} + +// ------------------------------------------------------------------------- +const char* cpPlugins::Pipeline::Object:: +GetClassCategory( ) const +{ + return( this->m_Category.c_str( ) ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Object:: +SetClassName( const std::string& name ) +{ + this->m_Name = name; +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Object:: +Modified( ) +{ + const itk::Object* i = + dynamic_cast< const itk::Object* >( this->GetObjectAsITK( ) ); + vtkObject* v = + dynamic_cast< vtkObject* >( this->GetObjectAsVTK( ) ); + if( i != NULL ) i->Modified( ); + if( v != NULL ) v->Modified( ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Object:: +_DeleteObject( ) +{ + typedef itk::LightObject::Pointer _TIPtr; + typedef vtkSmartPointer< vtkObjectBase > _TVPtr; + if( this->m_Object != NULL ) + { + if( this->m_Type == Self::ITKType ) + { + _TIPtr* o = reinterpret_cast< _TIPtr* >( this->m_Object ); + delete o; + } + else if( this->m_Type == Self::VTKType ) + { + _TVPtr* o = reinterpret_cast< _TVPtr* >( this->m_Object ); + delete o; + + } // fi + this->m_Object = NULL; + + } // fi +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Object:: +_SetObject( itk::LightObject* obj ) +{ + if( obj != NULL ) + { + itk::LightObject::Pointer* p = new itk::LightObject::Pointer( obj ); + this->m_Object = p; + this->m_Type = Self::ITKType; + } + else + { + this->_DeleteObject( ); + this->m_Type = Self::NeitherType; + + } // fi +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Object:: +_SetObject( vtkObjectBase* obj ) +{ + if( obj != NULL ) + { + vtkSmartPointer< vtkObjectBase >* p = + new vtkSmartPointer< vtkObjectBase >( obj ); + this->m_Object = p; + this->m_Type = Self::VTKType; + } + else + { + this->_DeleteObject( ); + this->m_Type = Self::NeitherType; + + } // fi +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Object:: +_SetObject( void* obj ) +{ + if( obj != NULL ) + this->m_Object = obj; + else + this->_DeleteObject( ); + this->m_Type = Self::NeitherType; +} + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Pipeline/Object.h b/lib/cpPlugins/Pipeline/Object.h new file mode 100644 index 0000000..ec1bc94 --- /dev/null +++ b/lib/cpPlugins/Pipeline/Object.h @@ -0,0 +1,79 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __cpPlugins__Pipeline__Object__h__ +#define __cpPlugins__Pipeline__Object__h__ + +#include +#include + +// Some forward declarations +namespace itk { class LightObject; } +class vtkObjectBase; + +namespace cpPlugins +{ + namespace Pipeline + { + /** + */ + class CPPLUGINS_EXPORT Object + { + public: + typedef Object Self; + + enum TType + { + NeitherType = 0, + ITKType, + VTKType + }; + + public: + Object( const std::string& category = "" ); + virtual ~Object( ); + + virtual void* GetObject( ); + virtual const void* GetObject( ) const; + + virtual itk::LightObject* GetObjectAsITK( ); + virtual const itk::LightObject* GetObjectAsITK( ) const; + + virtual vtkObjectBase* GetObjectAsVTK( ); + virtual const vtkObjectBase* GetObjectAsVTK( ) const; + + const char* GetClassName( ) const; + const char* GetClassCategory( ) const; + void SetClassName( const std::string& name ); + + virtual void Modified( ); + + virtual Self* CreateAnother( ) const = 0; + + protected: + void _DeleteObject( ); + void _SetObject( itk::LightObject* obj ); + void _SetObject( vtkObjectBase* obj ); + void _SetObject( void* obj ); + + private: + // Purposely not implemented + Object( const Self& ); + Self& operator=( const Self& ); + + protected: + std::string m_Name; + std::string m_Category; + void* m_Object; + TType m_Type; + }; + + } // ecapseman + +} // ecapseman + +#endif // __cpPlugins__Pipeline__Object__h__ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Pipeline/Parameters.cxx b/lib/cpPlugins/Pipeline/Parameters.cxx new file mode 100644 index 0000000..93b5261 --- /dev/null +++ b/lib/cpPlugins/Pipeline/Parameters.cxx @@ -0,0 +1,705 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#include +#include +#include + +/* TODO + #include + #include + #include +*/ + +// ------------------------------------------------------------------------- +cpPlugins::Pipeline::Parameters:: +Parameters( ) + : m_ProcessObject( NULL ) +{ + this->Clear( ); +} + +// ------------------------------------------------------------------------- +cpPlugins::Pipeline::Parameters:: +~Parameters( ) +{ +} + +// ------------------------------------------------------------------------- +cpPlugins::Pipeline::ProcessObject* cpPlugins::Pipeline::Parameters:: +GetProcessObject( ) +{ + return( this->m_ProcessObject ); +} + +// ------------------------------------------------------------------------- +const cpPlugins::Pipeline::ProcessObject* cpPlugins::Pipeline::Parameters:: +GetProcessObject( ) const +{ + return( this->m_ProcessObject ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +SetProcessObject( cpPlugins::Pipeline::ProcessObject* po ) +{ + this->m_ProcessObject = po; +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +Modified( ) const +{ + /* TODO + if( this->m_ProcessObject != NULL ) + this->m_ProcessObject->Modified( ); + */ +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +Clear( ) +{ + this->m_Parameters.clear( ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +GetNames( std::vector< std::string >& container ) const +{ + container.clear( ); + TParameters::const_iterator i = this->m_Parameters.begin( ); + for( ; i != this->m_Parameters.end( ); ++i ) + container.push_back( i->first ); +} + +// ------------------------------------------------------------------------- +cpPlugins::Pipeline::Parameters:: +Type cpPlugins::Pipeline::Parameters:: +GetType( const std::string& name ) const +{ + TParameters::const_iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + return( i->second.first ); + else + return( Self::NoType ); +} + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_TypeAsString( Y ) \ + if( i->second.first == Self::Y ) \ + return( #Y ) + +std::string cpPlugins::Pipeline::Parameters:: +GetTypeAsString( const std::string& name ) const +{ + TParameters::const_iterator i = this->m_Parameters.find( name ); + cpPlugins_Pipeline_Parameters_TypeAsString( String ); + else cpPlugins_Pipeline_Parameters_TypeAsString( Bool ); + else cpPlugins_Pipeline_Parameters_TypeAsString( Int ); + else cpPlugins_Pipeline_Parameters_TypeAsString( Uint ); + else cpPlugins_Pipeline_Parameters_TypeAsString( Real ); + else cpPlugins_Pipeline_Parameters_TypeAsString( OpenFileName ); + else cpPlugins_Pipeline_Parameters_TypeAsString( SaveFileName ); + else cpPlugins_Pipeline_Parameters_TypeAsString( PathName ); + else cpPlugins_Pipeline_Parameters_TypeAsString( StringList ); + else cpPlugins_Pipeline_Parameters_TypeAsString( BoolList ); + else cpPlugins_Pipeline_Parameters_TypeAsString( IntList ); + else cpPlugins_Pipeline_Parameters_TypeAsString( UintList ); + else cpPlugins_Pipeline_Parameters_TypeAsString( RealList ); + else cpPlugins_Pipeline_Parameters_TypeAsString( OpenFileNameList ); + else cpPlugins_Pipeline_Parameters_TypeAsString( SaveFileNameList ); + else cpPlugins_Pipeline_Parameters_TypeAsString( PathNameList ); + else cpPlugins_Pipeline_Parameters_TypeAsString( Choices ); + else return( "NoType" ); +} + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_TypeFromString( Y, str ) \ + if( str == std::string( #Y ) ) \ + return( Self::Y ) + +cpPlugins::Pipeline::Parameters:: +Type cpPlugins::Pipeline::Parameters:: +GetTypeFromString( const std::string& t ) +{ + cpPlugins_Pipeline_Parameters_TypeFromString( String, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( Bool, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( Int, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( Uint, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( Real, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( OpenFileName, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( SaveFileName, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( PathName, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( StringList, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( BoolList, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( IntList, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( UintList, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( RealList, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( OpenFileNameList, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( SaveFileNameList, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( PathNameList, t ); + else cpPlugins_Pipeline_Parameters_TypeFromString( Choices, t ); + else return( Self::NoType ); +} + +// ------------------------------------------------------------------------- +std::string cpPlugins::Pipeline::Parameters:: +GetString( const std::string& name, bool force ) const +{ + TParameters::const_iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == Self::String || force ) + return( i->second.second ); + else + return( "" ); + } + else + return( "" ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +SetString( const std::string& name, const std::string& v, bool force ) +{ + TParameters::iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == Self::String || force ) + { + if( i->second.second != v ) + { + i->second.second = v; + this->Modified( ); + + } // fi + + } // fi + + } // fi +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +ConfigureAsChoices( + const std::string& name, const std::vector< std::string >& choices + ) +{ + // It is invalid not to give choices when configuring + if( choices.size( ) == 0 ) + return; + + std::stringstream str_choices; + str_choices << choices[ 0 ]; + for( unsigned int i = 1; i < choices.size( ); ++i ) + str_choices << "#" << choices[ i ]; + str_choices << "@"; + this->m_Parameters[ name ] = + TParameter( Self::Choices, str_choices.str( ) ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +ConfigureAsRealTypesChoices( const std::string& name ) +{ + std::vector< std::string > choices; + choices.push_back( "float" ); + choices.push_back( "double" ); + this->ConfigureAsChoices( name, choices ); + this->SetSelectedChoice( name, "float" ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +ConfigureAsIntTypesChoices( const std::string& name ) +{ + std::vector< std::string > choices; + choices.push_back( "char" ); + choices.push_back( "uchar" ); + choices.push_back( "short" ); + choices.push_back( "ushort" ); + choices.push_back( "int" ); + choices.push_back( "uint" ); + choices.push_back( "long" ); + choices.push_back( "ulong" ); + this->ConfigureAsChoices( name, choices ); + this->SetSelectedChoice( name, "char" ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +ConfigureAsScalarTypesChoices( const std::string& name ) +{ + std::vector< std::string > choices; + choices.push_back( "char" ); + choices.push_back( "uchar" ); + choices.push_back( "short" ); + choices.push_back( "ushort" ); + choices.push_back( "int" ); + choices.push_back( "uint" ); + choices.push_back( "long" ); + choices.push_back( "ulong" ); + choices.push_back( "float" ); + choices.push_back( "double" ); + this->ConfigureAsChoices( name, choices ); + this->SetSelectedChoice( name, "char" ); +} + +// ------------------------------------------------------------------------- +std::vector< std::string > cpPlugins::Pipeline::Parameters:: +GetChoices( const std::string& name ) const +{ + std::vector< std::string > choices; + + TParameters::const_iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == Self::Choices ) + { + std::istringstream str_choices( i->second.second ); + std::string real_choices; + std::getline( str_choices, real_choices, '@' ); + std::istringstream str( real_choices ); + std::string token; + while( std::getline( str, token, '#' ) ) + choices.push_back( token ); + + } // fi + + } // fi + return( choices ); +} + +// ------------------------------------------------------------------------- +std::string cpPlugins::Pipeline::Parameters:: +GetSelectedChoice( const std::string& name ) const +{ + TParameters::const_iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == Self::Choices ) + { + std::istringstream str_choices( i->second.second ); + std::string real_choice; + std::getline( str_choices, real_choice, '@' ); + std::getline( str_choices, real_choice, '@' ); + return( real_choice ); + } + else + return( "" ); + } + else + return( "" ); +} + +// ------------------------------------------------------------------------- +bool cpPlugins::Pipeline::Parameters:: +SetSelectedChoice( const std::string& name, const std::string& choice ) +{ + TParameters::iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == Self::Choices ) + { + std::istringstream str_choices( i->second.second ); + std::string choices; + std::getline( str_choices, choices, '@' ); + if( choices.find( choice ) != std::string::npos ) + { + std::stringstream new_choices; + new_choices << choices << "@" << choice; + i->second.second = new_choices.str( ); + this->Modified( ); + return( true ); + } + else + return( false ); + } + else + return( false ); + } + else + return( false ); +} + +// ------------------------------------------------------------------------- +std::string cpPlugins::Pipeline::Parameters:: +GetAcceptedFileExtensions( const std::string& name ) const +{ + std::map< std::string, std::string >::const_iterator i = + this->m_AcceptedFileExtensions.find( name ); + if( i != this->m_AcceptedFileExtensions.end( ) ) + return( i->second ); + else + return( "" ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +SetAcceptedFileExtensions( + const std::string& name, const std::string& extensions + ) +{ + TParameters::iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + bool is_valid = ( i->second.first == Self::OpenFileName ); + is_valid |= ( i->second.first == Self::SaveFileName ); + is_valid |= ( i->second.first == Self::OpenFileNameList ); + is_valid |= ( i->second.first == Self::SaveFileNameList ); + if( is_valid ) + this->m_AcceptedFileExtensions[ name ] = extensions; + + } // fi +} + +// ------------------------------------------------------------------------- +cpPlugins::Pipeline::Parameters:: +TParameters& cpPlugins::Pipeline::Parameters:: +GetRawParameters( ) +{ + return( this->m_Parameters ); +} + +// ------------------------------------------------------------------------- +const cpPlugins::Pipeline::Parameters:: +TParameters& cpPlugins::Pipeline::Parameters:: +GetRawParameters( ) const +{ + return( this->m_Parameters ); +} + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_Configure_Code( Y ) \ + void cpPlugins::Pipeline::Parameters:: \ + ConfigureAs##Y( const std::string& name, const T##Y& init ) \ + { \ + this->_Configure< Y >( name ); \ + this->Set##Y( name, init ); \ + } \ + bool cpPlugins::Pipeline::Parameters:: \ + Has##Y( const std::string& name ) const \ + { return( this->_Has< Y >( name ) ); } + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_ConfigureList_Code( Y ) \ + void cpPlugins::Pipeline::Parameters:: \ + ConfigureAs##Y##List( const std::string& name ) \ + { this->_Configure< Y##List >( name ); } \ + bool cpPlugins::Pipeline::Parameters:: \ + Has##Y##List( const std::string& name ) const \ + { return( this->_Has< Y##List >( name ) ); } + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_GetSet_Code( Y ) \ + cpPlugins::Pipeline::Parameters::T##Y \ + cpPlugins::Pipeline::Parameters:: \ + Get##Y( const std::string& name ) const \ + { return( this->_Get< T##Y, Y >( name ) ); } \ + void cpPlugins::Pipeline::Parameters::Set##Y( \ + const std::string& name, const T##Y& v \ + ) \ + { this->_Set< T##Y, Y >( name, v ); } + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_GetSetList_Code( Y ) \ + std::vector< cpPlugins::Pipeline::Parameters::T##Y > \ + cpPlugins::Pipeline::Parameters:: \ + Get##Y##List( const std::string& name ) const \ + { return( this->_GetList< T##Y, Y##List >( name ) ); } \ + void cpPlugins::Pipeline::Parameters::AddTo##Y##List( \ + const std::string& name, \ + const cpPlugins::Pipeline::Parameters::T##Y& v \ + ) \ + { this->_AddToList< T##Y, Y##List >( name, v ); } \ + void cpPlugins::Pipeline::Parameters:: \ + Clear##Y##List( const std::string& name ) \ + { this->_ClearList< Y##List >( name ); } + +// ------------------------------------------------------------------------- +cpPlugins_Pipeline_Parameters_Configure_Code( String ); +cpPlugins_Pipeline_Parameters_Configure_Code( Bool ); +cpPlugins_Pipeline_Parameters_Configure_Code( Int ); +cpPlugins_Pipeline_Parameters_Configure_Code( Uint ); +cpPlugins_Pipeline_Parameters_Configure_Code( Real ); +cpPlugins_Pipeline_Parameters_Configure_Code( OpenFileName ); +cpPlugins_Pipeline_Parameters_Configure_Code( SaveFileName ); +cpPlugins_Pipeline_Parameters_Configure_Code( PathName ); + +cpPlugins_Pipeline_Parameters_ConfigureList_Code( String ); +cpPlugins_Pipeline_Parameters_ConfigureList_Code( Bool ); +cpPlugins_Pipeline_Parameters_ConfigureList_Code( Int ); +cpPlugins_Pipeline_Parameters_ConfigureList_Code( Uint ); +cpPlugins_Pipeline_Parameters_ConfigureList_Code( Real ); +cpPlugins_Pipeline_Parameters_ConfigureList_Code( OpenFileName ); +cpPlugins_Pipeline_Parameters_ConfigureList_Code( SaveFileName ); +cpPlugins_Pipeline_Parameters_ConfigureList_Code( PathName ); + +cpPlugins_Pipeline_Parameters_GetSet_Code( Bool ); +cpPlugins_Pipeline_Parameters_GetSet_Code( Int ); +cpPlugins_Pipeline_Parameters_GetSet_Code( Uint ); +cpPlugins_Pipeline_Parameters_GetSet_Code( Real ); +cpPlugins_Pipeline_Parameters_GetSet_Code( OpenFileName ); +cpPlugins_Pipeline_Parameters_GetSet_Code( SaveFileName ); +cpPlugins_Pipeline_Parameters_GetSet_Code( PathName ); + +cpPlugins_Pipeline_Parameters_GetSetList_Code( String ); +cpPlugins_Pipeline_Parameters_GetSetList_Code( Bool ); +cpPlugins_Pipeline_Parameters_GetSetList_Code( Int ); +cpPlugins_Pipeline_Parameters_GetSetList_Code( Uint ); +cpPlugins_Pipeline_Parameters_GetSetList_Code( Real ); +cpPlugins_Pipeline_Parameters_GetSetList_Code( PathName ); + +// ------------------------------------------------------------------------- +std::vector< cpPlugins::Pipeline::Parameters::TOpenFileName > +cpPlugins::Pipeline::Parameters:: +GetOpenFileNameList( const std::string& name ) const +{ + return( this->_GetList< TOpenFileName, OpenFileNameList >( name ) ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +AddToOpenFileNameList( + const std::string& name, + const cpPlugins::Pipeline::Parameters::TOpenFileName& v + ) +{ + TParameters::iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == OpenFileNameList ) + { + size_t pos = v.find_last_of( "/\\" ); + if( i->second.second == "" ) + i->second.second = v.substr( 0, pos ); + i->second.second += std::string( "#" ); + i->second.second += v.substr( pos + 1 ); + this->Modified( ); + + } // fi + + } // fi +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +ClearOpenFileNameList( const std::string& name ) +{ + this->_ClearList< OpenFileNameList >( name ); +} + +// ------------------------------------------------------------------------- +std::vector< cpPlugins::Pipeline::Parameters::TSaveFileName > +cpPlugins::Pipeline::Parameters:: +GetSaveFileNameList( const std::string& name ) const +{ + return( this->_GetList< TSaveFileName, SaveFileNameList >( name ) ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +AddToSaveFileNameList( + const std::string& name, + const cpPlugins::Pipeline::Parameters::TSaveFileName& v + ) +{ + TParameters::iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == SaveFileNameList ) + { + size_t pos = v.find_last_of( "/\\" ); + if( i->second.second == "" ) + i->second.second = v.substr( 0, pos ); + i->second.second += std::string( "#" ); + i->second.second += v.substr( pos + 1 ); + this->Modified( ); + + } // fi + + } // fi +} + +// ------------------------------------------------------------------------- +void cpPlugins::Pipeline::Parameters:: +ClearSaveFileNameList( const std::string& name ) +{ + this->_ClearList< SaveFileNameList >( name ); +} + +// ------------------------------------------------------------------------- +template< unsigned int _Enum > +void cpPlugins::Pipeline::Parameters:: +_Configure( const std::string& name ) +{ + this->m_Parameters[ name ] = TParameter( ( Self::Type )( _Enum ), "" ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< unsigned int _Enum > +bool cpPlugins::Pipeline::Parameters:: +_Has( const std::string& name ) const +{ + TParameters::const_iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + return( i->second.first == ( Self::Type )( _Enum ) ); + else + return( false ); +} + +// ------------------------------------------------------------------------- +template< class _Type, unsigned int _Enum > +_Type cpPlugins::Pipeline::Parameters:: +_Get( const std::string& name ) const +{ + TParameters::const_iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == ( Self::Type )( _Enum ) ) + { + if( typeid( _Type ) != typeid( std::string ) ) + { + std::istringstream tok_str( i->second.second ); + _Type v; + tok_str >> v; + return( v ); + } + else + { + const _Type* ptr = + reinterpret_cast< const _Type* >( &( i->second.second ) ); + return( *ptr ); + + } // fi + + } // fi + + } // fi + return( _Type( 0 ) ); +} + +// ------------------------------------------------------------------------- +template< class _Type, unsigned int _Enum > +void cpPlugins::Pipeline::Parameters:: +_Set( const std::string& name, const _Type& v ) +{ + TParameters::iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == ( Self::Type )( _Enum ) ) + { + if( typeid( _Type ) != typeid( std::string ) ) + { + std::stringstream str; + str << v; + if( i->second.second != str.str( ) ) + { + i->second.second = str.str( ); + this->Modified( ); + + } // fi + } + else + { + const std::string* str = reinterpret_cast< const std::string* >( &v ); + if( i->second.second != *str ) + { + i->second.second = *str; + this->Modified( ); + + } // fi + + } // fi + + } // fi + + } // fi +} + +// ------------------------------------------------------------------------- +template< class _Type, unsigned int _Enum > +std::vector< _Type > cpPlugins::Pipeline::Parameters:: +_GetList( const std::string& name ) const +{ + std::vector< _Type > lst; + std::vector< std::string >* slst = + reinterpret_cast< std::vector< std::string >* >( &lst ); + TParameters::const_iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == ( Self::Type )( _Enum ) ) + { + std::istringstream tokens( i->second.second ); + std::string t; + while( std::getline( tokens, t, '#' ) ) + { + if( typeid( _Type ) != typeid( std::string ) ) + { + std::istringstream tok_str( t ); + _Type v; + tok_str >> v; + lst.push_back( v ); + } + else + slst->push_back( t ); + + } // elihw + + } // fi + + } // fi + return( lst ); +} + +// ------------------------------------------------------------------------- +template< class _Type, unsigned int _Enum > +void cpPlugins::Pipeline::Parameters:: +_AddToList( const std::string& name, const _Type& v ) +{ + TParameters::iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == ( Self::Type )( _Enum ) ) + { + std::stringstream str; + if( i->second.second != "" ) + str << i->second.second << "#"; + str << v; + i->second.second = str.str( ); + this->Modified( ); + + } // fi + + } // fi +} + +// ------------------------------------------------------------------------- +template< unsigned int _Enum > +void cpPlugins::Pipeline::Parameters:: +_ClearList( const std::string& name ) +{ + TParameters::iterator i = this->m_Parameters.find( name ); + if( i != this->m_Parameters.end( ) ) + { + if( i->second.first == ( Self::Type )( _Enum ) ) + { + if( i->second.second != "" ) + { + i->second.second = ""; + this->Modified( ); + + } // fi + + } // fi + + } // fi +} + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Pipeline/Parameters.h b/lib/cpPlugins/Pipeline/Parameters.h new file mode 100644 index 0000000..0d90f48 --- /dev/null +++ b/lib/cpPlugins/Pipeline/Parameters.h @@ -0,0 +1,207 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __cpPlugins__Pipeline__Parameters__h__ +#define __cpPlugins__Pipeline__Parameters__h__ + +#include + +#include +#include +#include + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_Configure( Y ) \ + void ConfigureAs##Y( const std::string& name, const T##Y& init ); \ + bool Has##Y( const std::string& name ) const + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_ConfigureList( Y ) \ + void ConfigureAs##Y##List( const std::string& name ); \ + bool Has##Y##List( const std::string& name ) const + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_GetSet( Y ) \ + T##Y Get##Y( const std::string& name ) const; \ + void Set##Y( const std::string& name, const T##Y& v ) + +// ------------------------------------------------------------------------- +#define cpPlugins_Pipeline_Parameters_GetSetList( Y ) \ + std::vector< T##Y > Get##Y##List( const std::string& name ) const; \ + void AddTo##Y##List( const std::string& name, const T##Y& v ); \ + void Clear##Y##List( const std::string& name ) + +// ------------------------------------------------------------------------- +namespace cpPlugins +{ + namespace Pipeline + { + class ProcessObject; + + /** + */ + class CPPLUGINS_EXPORT Parameters + { + friend std::ostream& operator<<( std::ostream& o, const Parameters& p ) + { + for( + auto i = p.m_Parameters.begin( ); + i != p.m_Parameters.end( ); + ++i + ) + o << i->first << ": (" + << i->second.first << " | " + << i->second.second << ")" + << std::endl; + return( o ); + } + + public: + typedef Parameters Self; + + enum Type + { + String , Bool , Int , + Uint , Real , OpenFileName , + SaveFileName , PathName , StringList , + BoolList , IntList , UintList , + RealList , OpenFileNameList , SaveFileNameList , + PathNameList , Choices , NoType + }; + + typedef bool TBool; + typedef long TInt; + typedef unsigned long TUint; + typedef double TReal; + typedef std::string TString; + typedef std::string TOpenFileName; + typedef std::string TSaveFileName; + typedef std::string TPathName; + + typedef std::pair< Self::Type, std::string > TParameter; + typedef std::map< std::string, TParameter > TParameters; + + public: + cpPlugins_Pipeline_Parameters_Configure( String ); + cpPlugins_Pipeline_Parameters_Configure( Bool ); + cpPlugins_Pipeline_Parameters_Configure( Int ); + cpPlugins_Pipeline_Parameters_Configure( Uint ); + cpPlugins_Pipeline_Parameters_Configure( Real ); + cpPlugins_Pipeline_Parameters_Configure( OpenFileName ); + cpPlugins_Pipeline_Parameters_Configure( SaveFileName ); + cpPlugins_Pipeline_Parameters_Configure( PathName ); + + cpPlugins_Pipeline_Parameters_ConfigureList( String ); + cpPlugins_Pipeline_Parameters_ConfigureList( Bool ); + cpPlugins_Pipeline_Parameters_ConfigureList( Int ); + cpPlugins_Pipeline_Parameters_ConfigureList( Uint ); + cpPlugins_Pipeline_Parameters_ConfigureList( Real ); + cpPlugins_Pipeline_Parameters_ConfigureList( OpenFileName ); + cpPlugins_Pipeline_Parameters_ConfigureList( SaveFileName ); + cpPlugins_Pipeline_Parameters_ConfigureList( PathName ); + + cpPlugins_Pipeline_Parameters_GetSet( Bool ); + cpPlugins_Pipeline_Parameters_GetSet( Int ); + cpPlugins_Pipeline_Parameters_GetSet( Uint ); + cpPlugins_Pipeline_Parameters_GetSet( Real ); + cpPlugins_Pipeline_Parameters_GetSet( OpenFileName ); + cpPlugins_Pipeline_Parameters_GetSet( SaveFileName ); + cpPlugins_Pipeline_Parameters_GetSet( PathName ); + + cpPlugins_Pipeline_Parameters_GetSetList( String ); + cpPlugins_Pipeline_Parameters_GetSetList( Bool ); + cpPlugins_Pipeline_Parameters_GetSetList( Int ); + cpPlugins_Pipeline_Parameters_GetSetList( Uint ); + cpPlugins_Pipeline_Parameters_GetSetList( Real ); + cpPlugins_Pipeline_Parameters_GetSetList( OpenFileName ); + cpPlugins_Pipeline_Parameters_GetSetList( SaveFileName ); + cpPlugins_Pipeline_Parameters_GetSetList( PathName ); + + public: + Parameters( ); + virtual ~Parameters( ); + + ProcessObject* GetProcessObject( ); + const ProcessObject* GetProcessObject( ) const; + void SetProcessObject( ProcessObject* po ); + virtual void Modified( ) const; + + // Parameters container configuration + void Clear( ); + + // Get methods + void GetNames( std::vector< std::string >& container ) const; + Type GetType( const std::string& name ) const; + std::string GetTypeAsString( const std::string& name ) const; + static Type GetTypeFromString( const std::string& t ); + + // Base string methods + std::string GetString( + const std::string& name, bool force = true + ) const; + void SetString( + const std::string& name, const std::string& v, bool force = true + ); + + void ConfigureAsChoices( + const std::string& name, const std::vector< std::string >& choices + ); + void ConfigureAsRealTypesChoices( const std::string& name ); + void ConfigureAsIntTypesChoices( const std::string& name ); + void ConfigureAsScalarTypesChoices( const std::string& name ); + std::vector< std::string > GetChoices( const std::string& name ) const; + std::string GetSelectedChoice( const std::string& name ) const; + bool SetSelectedChoice( + const std::string& name, const std::string& choice + ); + + std::string GetAcceptedFileExtensions( const std::string& name ) const; + void SetAcceptedFileExtensions( + const std::string& name, const std::string& extensions + ); + + protected: + TParameters& GetRawParameters( ); + const TParameters& GetRawParameters( ) const; + + template< unsigned int _Enum > + inline void _Configure( const std::string& name ); + + template< unsigned int _Enum > + inline bool _Has( const std::string& name ) const; + + template< class _Type, unsigned int _Enum > + inline _Type _Get( const std::string& name ) const; + + template< class _Type, unsigned int _Enum > + inline void _Set( const std::string& name, const _Type& v ); + + template< class _Type, unsigned int _Enum > + inline std::vector< _Type > _GetList( const std::string& name ) const; + + template< class _Type, unsigned int _Enum > + inline void _AddToList( const std::string& name, const _Type& v ); + + template< unsigned int _Enum > + inline void _ClearList( const std::string& name ); + + private: + // Purposely not implemented + Parameters( const Self& other ); + Self& operator=( const Self& other ); + + protected: + ProcessObject* m_ProcessObject; + TParameters m_Parameters; + std::map< std::string, std::string > m_AcceptedFileExtensions; + }; + + } // ecapseman + +} // ecapseman + +#endif // __cpPlugins__Pipeline__Parameters__h__ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Pipeline/ProcessObject.h b/lib/cpPlugins/Pipeline/ProcessObject.h new file mode 100644 index 0000000..da90921 --- /dev/null +++ b/lib/cpPlugins/Pipeline/ProcessObject.h @@ -0,0 +1,46 @@ +/* ========================================================================= + * @author ??? (???@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __cpPlugins__Pipeline__ProcessObject__h__ +#define __cpPlugins__Pipeline__ProcessObject__h__ + +#include + +namespace cpPlugins +{ + namespace Pipeline + { + /** + */ + class ProcessObject + : public cpPlugins::Pipeline::Object< void* > + { + public: + typedef Object Self; + typedef cpPlugins::Pipeline::Object< void* > Superclass; + typedef Superclass::TDecorated TDecorated; + + public: + ProcessObject( ); + virtual ~ProcessObject( ); + + virtual void Modified( ) const = 0; + + private: + // Purposely not implemented + Object( const Self& ); + Self& operator=( const Self& ); + + protected: + bool m_IsVTK; + }; + + } // ecapseman + +} // ecapseman + +#endif // __cpPlugins__Pipeline__ProcessObject__h__ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Utils/ExpandTemplates.cxx b/lib/cpPlugins/Utils/ExpandTemplates.cxx new file mode 100644 index 0000000..37442b6 --- /dev/null +++ b/lib/cpPlugins/Utils/ExpandTemplates.cxx @@ -0,0 +1,178 @@ +/* ========================================================================= + * @author Ricardo Montano-Barrera (@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#include +#include +#include +#include + +// ------------------------------------------------------------------------- +cpPlugins::Utils::ExpandTemplates:: +ExpandTemplates( ) +{ +} + +// ------------------------------------------------------------------------- +cpPlugins::Utils::ExpandTemplates:: +~ExpandTemplates( ) +{ +} + +// ------------------------------------------------------------------------- +void cpPlugins::Utils::ExpandTemplates:: +Parse( const std::string& filename ) +{ + // Load file in a string buffer + std::ifstream input( filename.c_str( ) ); + if( !input ) + throw std::runtime_error( "Unable to parse file \"" + filename + "\"" ); + typedef std::istreambuf_iterator< char > _TIt; + std::istringstream buffer( std::string( ( _TIt( input ) ), _TIt( ) ) ); + input.close( ); + + // Read line by line + TStringsMapQueue patterns; + TStrings lines; + Self::_ReadLines( &buffer, patterns, lines ); + + // Parse patterns + Self::_ParsePatterns( patterns, this->m_Patterns ); + + // Expand lines + this->m_Lines.clear( ); + for( std::string line: lines ) + Self::_Expand( this->m_Lines, line, this->m_Patterns ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Utils::ExpandTemplates:: +Save( const std::string& filename ) +{ + // Fill buffer + std::stringstream buffer; + for( std::string line: this->m_Lines ) + buffer << line << std::endl; + + // Save buffer to file + std::ofstream output( filename.c_str( ) ); + if( !output ) + throw std::runtime_error( "Unable to save file \"" + filename + "\"" ); + output << buffer.str( ); + output.close( ); +} + +// ------------------------------------------------------------------------- +std::string cpPlugins::Utils::ExpandTemplates:: +_Replace( const std::string& s, const std::string& f, const std::string& t ) +{ + std::string r = s; + size_t p = r.find( f ); + while( p != std::string::npos ) + { + r.replace( p, f.length( ), t ); + p = r.find( f ); + + } // elihw + return( r ); +} + +// ------------------------------------------------------------------------- +void cpPlugins::Utils::ExpandTemplates:: +_ReadLines( std::istream* str, TStringsMapQueue& patterns, TStrings& lines ) +{ + std::string line; + while( std::getline( *str, line ) ) + { + std::size_t f = line.find_first_not_of( " \t\r\n" ); + if( f != std::string::npos ) + { + if( line[ f ] == '@' ) + { + // New injection mark + std::string mark; + std::size_t s = line.find( "=" ); + mark = line.substr( f, s ) + "@"; + TStringsMapValue m( mark, TStrings( ) ); + std::istringstream v( line.substr( s + 1 ) ); + std::string t; + while( std::getline( v, t, ';' ) ) + m.second.push_back( t ); + patterns.push( m ); + } + else + lines.push_back( line ); + } + else + lines.push_back( line ); + + } // elihw +} + +// ------------------------------------------------------------------------- +void cpPlugins::Utils::ExpandTemplates:: +_ParsePatterns( TStringsMapQueue& q, TStringsMap& patterns ) +{ + patterns.clear( ); + while( q.size( ) > 0 ) + { + TStringsMapValue p = q.front( ); + q.pop( ); + + bool requeue = false; + TStrings new_v; + for( std::string v: p.second ) + { + size_t s = v.find( "@" ); + if( s != std::string::npos ) + { + size_t e = v.find( "@", s + 1 ); + if( e == std::string::npos ) + throw std::runtime_error( "Invalid syntax: " + v ); + std::string m = v.substr( s, e - s + 1 ); + TStringsMap::const_iterator pIt = patterns.find( m ); + if( pIt != patterns.end( ) ) + for( std::string w: pIt->second ) + new_v.push_back( Self::_Replace( v, m, w ) ); + requeue = true; + + } // fi + + } // rof + if( requeue ) + { + if( new_v.size( ) > 0 ) + p.second = new_v; + q.push( p ); + } + else + patterns.insert( p ); + + } // elihw +} + +// ------------------------------------------------------------------------- +void cpPlugins::Utils::ExpandTemplates:: +_Expand( + TStrings& expands, const std::string& line, const TStringsMap& patterns + ) +{ + size_t s = line.find( "@" ); + if( s != std::string::npos ) + { + size_t e = line.find( "@", s + 1 ); + if( e == std::string::npos ) + throw std::runtime_error( "Invalid syntax: " + line ); + std::string mark = line.substr( s, e - s + 1 ); + TStringsMap::const_iterator pIt = patterns.find( mark ); + if( pIt == patterns.end( ) ) + throw std::runtime_error( "Unknown mark: " + mark ); + for( std::string value: pIt->second ) + Self::_Expand( expands, Self::_Replace( line, mark, value ), patterns ); + } + else + expands.push_back( line ); +} + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Utils/ExpandTemplates.h b/lib/cpPlugins/Utils/ExpandTemplates.h new file mode 100644 index 0000000..ee98713 --- /dev/null +++ b/lib/cpPlugins/Utils/ExpandTemplates.h @@ -0,0 +1,61 @@ +/* ========================================================================= + * @author Ricardo Montano-Barrera (@javeriana.edu.co) + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __cpPlugins__Utils__ExpandTemplates__h__ +#define __cpPlugins__Utils__ExpandTemplates__h__ + +#include +#include +#include +#include +#include + +namespace cpPlugins +{ + namespace Utils + { + /** + */ + class CPPLUGINS_EXPORT ExpandTemplates + { + private: + typedef ExpandTemplates Self; + typedef std::vector< std::string > TStrings; + typedef std::map< std::string, TStrings > TStringsMap; + typedef TStringsMap::value_type TStringsMapValue; + typedef std::queue< TStringsMapValue > TStringsMapQueue; + + public: + ExpandTemplates( ); + virtual ~ExpandTemplates( ); + + void Parse( const std::string& filename ); + void Save( const std::string& filename ); + + protected: + static std::string _Replace( + const std::string& s, const std::string& f, const std::string& t + ); + static void _ReadLines( + std::istream* str, TStringsMapQueue& patterns, TStrings& lines + ); + static void _ParsePatterns( TStringsMapQueue& q, TStringsMap& patterns ); + static void _Expand( + TStrings& expands, + const std::string& line, const TStringsMap& patterns + ); + + private: + TStringsMap m_Patterns; + TStrings m_Lines; + }; + + } // ecapseman + +} // ecapseman + +#endif // __cpPlugins__Utils__ExpandTemplates__h__ + +// eof - $RCSfile$ diff --git a/lib/cpPlugins/Version.cxx.in b/lib/cpPlugins/Version.cxx.in new file mode 100644 index 0000000..ea3c9ad --- /dev/null +++ b/lib/cpPlugins/Version.cxx.in @@ -0,0 +1,7 @@ + +#include +#include + +std::string CPPLUGINS_EXPORT version( ) { return( "@prj_VER@" ); } + +// eof - $RCSfile$ diff --git a/lib/ivq/CMakeLists.txt b/lib/ivq/CMakeLists.txt new file mode 100644 index 0000000..1a55abc --- /dev/null +++ b/lib/ivq/CMakeLists.txt @@ -0,0 +1,25 @@ +## ========================================================================= +## @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) +## ========================================================================= + +option(BUILD_ivq "Build ITK/VTK/Qt extensions." OFF) +if(BUILD_ivq) + + ## -- Set directories + set(_dirs . ITK) + if(${cpPlugins_USE_VTK} EQUAL 1) + list(APPEND _dirs VTK) + endif(${cpPlugins_USE_VTK} EQUAL 1) + if(${cpPlugins_USE_Qt5} EQUAL 1) + list(APPEND _dirs Qt) + endif(${cpPlugins_USE_Qt5} EQUAL 1) + + ## -- Build + BuildLibrary( + ivq SHARED "${_dirs}" + ${prj_MAJ} ${prj_MIN} ${prj_REL} + ${ITK_LIBRARIES} ${VTK_LIBRARIES} + ) +endif(BUILD_ivq) + +## eof - $RCSfile$ diff --git a/lib/ivq/Config.h.in b/lib/ivq/Config.h.in new file mode 100644 index 0000000..46a0144 --- /dev/null +++ b/lib/ivq/Config.h.in @@ -0,0 +1,20 @@ +/* ========================================================================= + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ +#ifndef __ivq__Config__h__ +#define __ivq__Config__h__ + +#include + +#if @cpPlugins_USE_VTK@ == 1 +# define ivq_USE_VTK +#endif // @cpPlugins_USE_VTK@ == 1 + +#if @cpPlugins_USE_Qt5@ == 1 +# define ivq_USE_Qt5 +#endif // @cpPlugins_USE_Qt5@ == 1 + +#endif // __ivq__Config__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/BooleanMapSaliencyFunction.h b/lib/ivq/ITK/BooleanMapSaliencyFunction.h new file mode 100644 index 0000000..ce39ede --- /dev/null +++ b/lib/ivq/ITK/BooleanMapSaliencyFunction.h @@ -0,0 +1,81 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__BooleanMapSaliencyFunction__h__ +#define __ivq__ITK__BooleanMapSaliencyFunction__h__ + +#include + +#include +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TIn, class _TOut > + class BooleanMapSaliencyFunction + : public itk::FunctionBase< _TIn, _TOut > + { + public: + typedef BooleanMapSaliencyFunction Self; + typedef itk::FunctionBase< _TIn, _TOut > Superclass; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + typedef typename Superclass::InputType TInput; + typedef typename Superclass::OutputType TOutput; + + public: + itkNewMacro( Self ); + itkTypeMacro( ivq::ITK::BooleanMapSaliencyFunction, itk::FunctionBase ); + + itkBooleanMacro( UseBoundedThresholds ); + itkGetConstMacro( UseBoundedThresholds, bool ); + itkSetMacro( UseBoundedThresholds, bool ); + + // Concepts + itkConceptMacro( Concept0, ( itk::Concept::IsFloatingPoint< _TOut > ) ); + + public: + virtual _TOut Evaluate( const _TIn& in ) const override; + + unsigned int GetNumberOfThresholds( ) const; + void ClearThresholds( ); + void AddThreshold( const _TIn& v ); + void AddThresholds( + const _TIn& v_min, + const _TIn& v_max, + const _TIn& v_delta + ); + + protected: + BooleanMapSaliencyFunction( ); + virtual ~BooleanMapSaliencyFunction( ); + + private: + // Purposely not implemented + BooleanMapSaliencyFunction( const Self& other ); + Self& operator=( const Self& other ); + + protected: + std::set< _TIn > m_Thresholds; + bool m_UseBoundedThresholds; + }; + + } // ecapseman + +} // ecapseman + +#ifndef ITK_MANUAL_INSTANTIATION +# include +#endif // ITK_MANUAL_INSTANTIATION + +#endif // __ivq__ITK__BooleanMapSaliencyFunction__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/BooleanMapSaliencyFunction.hxx b/lib/ivq/ITK/BooleanMapSaliencyFunction.hxx new file mode 100644 index 0000000..8084ac1 --- /dev/null +++ b/lib/ivq/ITK/BooleanMapSaliencyFunction.hxx @@ -0,0 +1,92 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__BooleanMapSaliencyFilter__hxx__ +#define __ivq__ITK__BooleanMapSaliencyFilter__hxx__ + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +_TOut ivq::ITK::BooleanMapSaliencyFunction< _TIn, _TOut >:: +Evaluate( const _TIn& in ) const +{ + bool stop = false; + unsigned long count = 0; + if( this->m_UseBoundedThresholds ) + { + _TIn lower = *( this->m_Thresholds.begin( ) ); + _TIn upper = *( this->m_Thresholds.rbegin( ) ); + stop = ( in < lower || in > upper ); + + } // fi + typename std::set< _TIn >::const_iterator i = this->m_Thresholds.begin( ); + while( i != this->m_Thresholds.end( ) && !stop ) + { + stop = ( in < *i ); + count += ( !stop )? 1: 0; + ++i; + + } // elihw + return( _TOut( double( count ) / double( this->m_Thresholds.size( ) ) ) ); +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +unsigned int ivq::ITK::BooleanMapSaliencyFunction< _TIn, _TOut >:: +GetNumberOfThresholds( ) const +{ + return( this->m_Thresholds.size( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +void ivq::ITK::BooleanMapSaliencyFunction< _TIn, _TOut >:: +ClearThresholds( ) +{ + if( this->m_Thresholds.size( ) > 0 ) + { + this->m_Thresholds.clear( ); + this->Modified( ); + + } // fi +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +void ivq::ITK::BooleanMapSaliencyFunction< _TIn, _TOut >:: +AddThreshold( const _TIn& v ) +{ + if( this->m_Thresholds.insert( v ).second ) + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +void ivq::ITK::BooleanMapSaliencyFunction< _TIn, _TOut >:: +AddThresholds( const _TIn& v_min, const _TIn& v_max, const _TIn& v_delta ) +{ + for( _TIn v = v_min; v <= v_max; v += v_delta ) + this->AddThreshold( v ); +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +ivq::ITK::BooleanMapSaliencyFunction< _TIn, _TOut >:: +BooleanMapSaliencyFunction( ) + : Superclass( ), + m_UseBoundedThresholds( false ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +ivq::ITK::BooleanMapSaliencyFunction< _TIn, _TOut >:: +~BooleanMapSaliencyFunction( ) +{ +} + +#endif // __ivq__ITK__BooleanMapSaliencyFilter__hxx__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/CPRImageFilter.h b/lib/ivq/ITK/CPRImageFilter.h new file mode 100644 index 0000000..6d42fa0 --- /dev/null +++ b/lib/ivq/ITK/CPRImageFilter.h @@ -0,0 +1,84 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__CPRImageFilter__h__ +#define __ivq__ITK__CPRImageFilter__h__ + +#include + +#include +#include + +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TImage, class _TCurve > + class CPRImageFilter + : public itk::ImageToImageFilter< _TImage, _TImage > + { + public: + typedef CPRImageFilter Self; + typedef itk::ImageToImageFilter< _TImage, _TImage > Superclass; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + typedef _TImage TImage; + typedef _TCurve TCurve; + typedef typename TCurve::TScalar TScalar; + + typedef ivq::ITK::IsoImageSlicer< TImage, TScalar > TSlicer; + typedef typename TSlicer::TInterpolateFunction TInterpolateFunction; + typedef typename TSlicer::TSliceImage TSliceImage; + + typedef itk::JoinSeriesImageFilter< TSliceImage, TImage > TJoinFilter; + + public: + itkNewMacro( Self ); + itkTypeMacro( CPRImageFilter, itk::ImageToImageFilter ); + + itkGetConstMacro( SliceRadius, double ); + itkGetObjectMacro( Interpolator, TInterpolateFunction ); + + itkSetMacro( SliceRadius, double ); + itkSetObjectMacro( Interpolator, TInterpolateFunction ); + + public: + _TCurve* GetCurve( ); + const _TCurve* GetCurve( ) const; + void SetCurve( _TCurve* curve ); + + protected: + CPRImageFilter( ); + virtual ~CPRImageFilter( ); + + virtual void GenerateOutputInformation( ) override; + virtual void GenerateInputRequestedRegion( ) override; + virtual void GenerateData( ) override; + + protected: + double m_SliceRadius; + typename TInterpolateFunction::Pointer m_Interpolator; + + std::vector< typename TSlicer::Pointer > m_Slicers; + typename TJoinFilter::Pointer m_Join; + }; + + } // ecapseman + +} // ecapseman + +#ifndef ITK_MANUAL_INSTANTIATION +# include +#endif // ITK_MANUAL_INSTANTIATION + +#endif // __ivq__ITK__CPRImageFilter__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/CPRImageFilter.hxx b/lib/ivq/ITK/CPRImageFilter.hxx new file mode 100644 index 0000000..346cc0a --- /dev/null +++ b/lib/ivq/ITK/CPRImageFilter.hxx @@ -0,0 +1,133 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__CPRImageFilter__hxx__ +#define __ivq__ITK__CPRImageFilter__hxx__ + +#include + +// ------------------------------------------------------------------------- +template< class _TImage, class _TCurve > +_TCurve* ivq::ITK::CPRImageFilter< _TImage, _TCurve >:: +GetCurve( ) +{ + return( + dynamic_cast< _TCurve* >( this->itk::ProcessObject::GetInput( 1 ) ) + ); +} + +// ------------------------------------------------------------------------- +template< class _TImage, class _TCurve > +const _TCurve* ivq::ITK::CPRImageFilter< _TImage, _TCurve >:: +GetCurve( ) const +{ + return( + dynamic_cast< const _TCurve* >( this->itk::ProcessObject::GetInput( 1 ) ) + ); +} + +// ------------------------------------------------------------------------- +template< class _TImage, class _TCurve > +void ivq::ITK::CPRImageFilter< _TImage, _TCurve >:: +SetCurve( _TCurve* curve ) +{ + this->itk::ProcessObject::SetNthInput( 1, curve ); +} + +// ------------------------------------------------------------------------- +template< class _TImage, class _TCurve > +ivq::ITK::CPRImageFilter< _TImage, _TCurve >:: +CPRImageFilter( ) + : Superclass( ), + m_SliceRadius( 0 ) +{ + this->Superclass::SetNumberOfRequiredInputs( 2 ); +} + +// ------------------------------------------------------------------------- +template< class _TImage, class _TCurve > +ivq::ITK::CPRImageFilter< _TImage, _TCurve >:: +~CPRImageFilter( ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TImage, class _TCurve > +void ivq::ITK::CPRImageFilter< _TImage, _TCurve >:: +GenerateOutputInformation( ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TImage, class _TCurve > +void ivq::ITK::CPRImageFilter< _TImage, _TCurve >:: +GenerateInputRequestedRegion( ) +{ + TImage* input = const_cast< TImage* >( this->GetInput( ) ); + if( input != NULL ) + input->SetRequestedRegionToLargestPossibleRegion( ); +} + +// ------------------------------------------------------------------------- +template< class _TImage, class _TCurve > +void ivq::ITK::CPRImageFilter< _TImage, _TCurve >:: +GenerateData( ) +{ + typedef itk::MinimumMaximumImageCalculator< _TImage > _TMinMax; + + const _TImage* input = this->GetInput( ); + const _TCurve* curve = this->GetCurve( ); + _TImage* output = this->GetOutput( ); + + // Compute image intensity range + typename _TMinMax::Pointer minmax = _TMinMax::New( ); + minmax->SetImage( input ); + minmax->Compute( ); + + // Main loop + this->m_Join = TJoinFilter::New( ); + this->m_Slicers.clear( ); + unsigned long N = curve->GetNumberOfPoints( ); + double len = 0; + typename _TCurve::TPoint p, q; + for( unsigned long n = 0; n < N; ++n ) + { + p = curve->GetPoint( n ); + if( n > 0 ) + len += p.EuclideanDistanceTo( q ); + q = p; + + // Prepare slicer + typename TSlicer::Pointer slicer = TSlicer::New( ); + slicer->SetInput( input ); + slicer->SetDefaultValue( minmax->GetMinimum( ) ); + slicer->SpacingFromMinimumOn( ); + if( this->m_Interpolator.IsNotNull( ) ) + slicer->SetInterpolator( this->m_Interpolator ); + slicer->SizeFromMaximumOff( ); + if( this->m_SliceRadius > double( 0 ) ) + { + slicer->SizeFromMinimumOff( ); + slicer->SetSize( this->m_SliceRadius ); + } + else + slicer->SizeFromMinimumOn( ); + slicer->SetTranslation( p ); + slicer->SetRotation( curve->GetFrame( n ) ); + slicer->Update( ); + + this->m_Join->SetInput( n, slicer->GetOutput( ) ); + this->m_Slicers.push_back( slicer ); + + } // rof + this->m_Join->SetSpacing( len / double( N ) ); + this->m_Join->Update( ); + this->GetOutput( )->Graft( this->m_Join->GetOutput( ) ); +} + +#endif // __ivq__ITK__CPRImageFilter__hxx__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ExtractLabelFunction.h b/lib/ivq/ITK/ExtractLabelFunction.h new file mode 100644 index 0000000..bd9f70b --- /dev/null +++ b/lib/ivq/ITK/ExtractLabelFunction.h @@ -0,0 +1,73 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ExtractLabelFunction__h__ +#define __ivq__ITK__ExtractLabelFunction__h__ + +#include + +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TIn, class _TOut > + class ExtractLabelFunction + : public itk::FunctionBase< _TIn, _TOut > + { + public: + typedef ExtractLabelFunction Self; + typedef itk::FunctionBase< _TIn, _TOut > Superclass; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + typedef typename Superclass::InputType TInput; + typedef typename Superclass::OutputType TOutput; + + public: + itkNewMacro( Self ); + itkTypeMacro( ivq::ITK::ExtractLabelFunction, itk::FunctionBase ); + + itkGetConstMacro( Label, _TIn ); + itkGetConstMacro( InsideValue, _TOut ); + itkGetConstMacro( OutsideValue, _TOut ); + + itkSetMacro( Label, _TIn ); + itkSetMacro( InsideValue, _TOut ); + itkSetMacro( OutsideValue, _TOut ); + + public: + virtual _TOut Evaluate( const _TIn& in ) const override; + + protected: + ExtractLabelFunction( ); + virtual ~ExtractLabelFunction( ); + + private: + // Purposely not implemented + ExtractLabelFunction( const Self& other ); + Self& operator=( const Self& other ); + + protected: + _TIn m_Label; + _TOut m_InsideValue; + _TOut m_OutsideValue; + }; + + } // ecapseman + +} // ecapseman + +#ifndef ITK_MANUAL_INSTANTIATION +# include +#endif // ITK_MANUAL_INSTANTIATION + +#endif // __ivq__ITK__ExtractLabelFunction__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ExtractLabelFunction.hxx b/lib/ivq/ITK/ExtractLabelFunction.hxx new file mode 100644 index 0000000..1f009cf --- /dev/null +++ b/lib/ivq/ITK/ExtractLabelFunction.hxx @@ -0,0 +1,40 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ExtractLabelFunction__hxx__ +#define __ivq__ITK__ExtractLabelFunction__hxx__ + +#include + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +_TOut ivq::ITK::ExtractLabelFunction< _TIn, _TOut >:: +Evaluate( const _TIn& in ) const +{ + return( ( in == this->m_Label )? this->m_InsideValue: this->m_OutsideValue ); +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +ivq::ITK::ExtractLabelFunction< _TIn, _TOut >:: +ExtractLabelFunction( ) + : Superclass( ), + m_Label( _TIn( 0 ) ), + m_InsideValue( std::numeric_limits< _TOut >::max( ) ), + m_OutsideValue( _TOut( 0 ) ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +ivq::ITK::ExtractLabelFunction< _TIn, _TOut >:: +~ExtractLabelFunction( ) +{ +} + +#endif // __ivq__ITK__ExtractLabelFunction__hxx__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ImageROIFromFunction.h b/lib/ivq/ITK/ImageROIFromFunction.h new file mode 100644 index 0000000..6aef0f9 --- /dev/null +++ b/lib/ivq/ITK/ImageROIFromFunction.h @@ -0,0 +1,83 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ImageROIFromFunction__h__ +#define __ivq__ITK__ImageROIFromFunction__h__ + +#include +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TImage > + class ImageROIFromFunction + : public itk::Object + { + public: + typedef ImageROIFromFunction Self; + typedef itk::Object Superclass; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + typedef _TImage TImage; + typedef typename TImage::IndexType TIndex; + typedef typename TImage::PixelType TPixel; + typedef typename TImage::RegionType TRegion; + + typedef itk::FunctionBase< TPixel, bool > TFunction; + + public: + itkNewMacro( Self ); + itkTypeMacro( ivq::ITK::ImageROIFromFunction, itk::Object ); + + itkGetConstObjectMacro( Image, TImage ); + itkSetConstObjectMacro( Image, TImage ); + + itkGetObjectMacro( Function, TFunction ); + itkGetConstObjectMacro( Function, TFunction ); + itkSetObjectMacro( Function, TFunction ); + + itkGetConstMacro( Padding, unsigned int ); + itkSetMacro( Padding, unsigned int ); + + itkGetConstReferenceMacro( ROI, TRegion ); + + public: + virtual void Modified( ) const override; + virtual void Compute( ); + + protected: + ImageROIFromFunction( ); + virtual ~ImageROIFromFunction( ); + + private: + // Purposely not implemented + ImageROIFromFunction( Self& other ); + Self& operator=( Self& other ); + + protected: + typename TImage::ConstPointer m_Image; + typename TFunction::Pointer m_Function; + unsigned int m_Padding; + TRegion m_ROI; + mutable bool m_ROIUpdated; + }; + + } // ecapseman + +} // ecapseman + +#ifndef ITK_MANUAL_INSTANTIATION +# include +#endif // ITK_MANUAL_INSTANTIATION + +#endif // __ivq__ITK__ImageROIFromFunction__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ImageROIFromFunction.hxx b/lib/ivq/ITK/ImageROIFromFunction.hxx new file mode 100644 index 0000000..d7ba4e3 --- /dev/null +++ b/lib/ivq/ITK/ImageROIFromFunction.hxx @@ -0,0 +1,99 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ImageROIFromFunction__hxx__ +#define __ivq__ITK__ImageROIFromFunction__hxx__ + +#include + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::ImageROIFromFunction< _TImage >:: +Modified( ) const +{ + this->Superclass::Modified( ); + this->m_ROIUpdated = false; +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::ImageROIFromFunction< _TImage >:: +Compute( ) +{ + if( this->m_ROIUpdated || this->m_Image.IsNull( ) ) + return; + if( this->m_Function.IsNotNull( ) ) + { + // Initialize bounds + TRegion in_region = this->m_Image->GetRequestedRegion( ); + TIndex iMin = in_region.GetIndex( ); + TIndex iMax = iMin + in_region.GetSize( ); + for( unsigned int d = 0; d < TImage::ImageDimension; ++d ) + iMax[ d ] -= 1; + + // Compute bounds + typedef itk::ImageRegionConstIteratorWithIndex< TImage > _TIt; + _TIt it( this->m_Image, in_region ); + TIndex i0 = iMax; + TIndex i1 = iMin; + for( it.GoToBegin( ); !it.IsAtEnd( ); ++it ) + { + if( this->m_Function->Evaluate( it.Get( ) ) ) + { + TIndex i = it.GetIndex( ); + for( unsigned int d = 0; d < TImage::ImageDimension; ++d ) + { + i0[ d ] = ( i[ d ] < i0[ d ] )? i[ d ]: i0[ d ]; + i1[ d ] = ( i1[ d ] < i[ d ] )? i[ d ]: i1[ d ]; + + } // rof + + } // fi + + } // rof + + // Apply padding + for( unsigned int d = 0; d < TImage::ImageDimension; ++d ) + { + i0[ d ] -= this->m_Padding; + i1[ d ] += this->m_Padding; + i0[ d ] = ( i0[ d ] < iMin[ d ] )? iMin[ d ]: i0[ d ]; + i1[ d ] = ( iMax[ d ] < i1[ d ] )? iMax[ d ]: i1[ d ]; + + } // rof + + // Create new ROI + typename TImage::SizeType roi_size; + for( unsigned int d = 0; d < TImage::ImageDimension; ++d ) + roi_size[ d ] = i1[ d ] - i0[ d ] + 1; + this->m_ROI.SetIndex( i0 ); + this->m_ROI.SetSize( roi_size ); + } + else + this->m_ROI = this->m_Image->GetRequestedRegion( ); + this->m_ROIUpdated = true; +} + +// ------------------------------------------------------------------------- +template< class _TImage > +ivq::ITK::ImageROIFromFunction< _TImage >:: +ImageROIFromFunction( ) + : Superclass( ), + m_Padding( 0 ), + m_ROIUpdated( false ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TImage > +ivq::ITK::ImageROIFromFunction< _TImage >:: +~ImageROIFromFunction( ) +{ +} + +#endif // __ivq__ITK__ImageROIFromFunction__hxx__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ImageStatisticsFromSeeds.h b/lib/ivq/ITK/ImageStatisticsFromSeeds.h new file mode 100644 index 0000000..c9c24f1 --- /dev/null +++ b/lib/ivq/ITK/ImageStatisticsFromSeeds.h @@ -0,0 +1,82 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ImageStatisticsFromSeeds__h__ +#define __ivq__ITK__ImageStatisticsFromSeeds__h__ + +#include +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TImage > + class ImageStatisticsFromSeeds + : public itk::Object + { + public: + typedef itk::Object Superclass; + typedef ImageStatisticsFromSeeds Self; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + typedef _TImage TImage; + typedef typename TImage::IndexType TIndex; + + typedef typename TIndex::LexicographicCompare TIndexCompare; + typedef std::set< TIndex, TIndexCompare > TIndices; + + public: + itkNewMacro( Self ); + itkTypeMacro( ivq::ITK::ImageStatisticsFromSeeds, itk::Object ); + + itkGetConstObjectMacro( Image, TImage ); + itkGetConstMacro( Indices, TIndices ); + itkGetConstMacro( Mean, double ); + itkGetConstMacro( Deviation, double ); + itkGetConstMacro( Radius, unsigned int ); + + itkSetConstObjectMacro( Image, TImage ); + itkSetMacro( Radius, unsigned int ); + + public: + unsigned int GetNumberOfIndices( ) const; + void ClearIndices( ); + void AddIndex( const TIndex& i ); + void RemoveIndex( const TIndex& i ); + void Compute( ); + + protected: + ImageStatisticsFromSeeds( ); + virtual ~ImageStatisticsFromSeeds( ); + + private: + // Purposely not implemented + ImageStatisticsFromSeeds( Self& other ); + Self& operator=( Self& other ); + + protected: + typename TImage::ConstPointer m_Image; + TIndices m_Indices; + double m_Mean; + double m_Deviation; + unsigned int m_Radius; + }; + + } // ecapseman + +} // ecapseman + +#ifndef ITK_MANUAL_INSTANTIATION +# include +#endif // ITK_MANUAL_INSTANTIATION + +#endif // __ivq__ITK__ImageStatisticsFromSeeds__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ImageStatisticsFromSeeds.hxx b/lib/ivq/ITK/ImageStatisticsFromSeeds.hxx new file mode 100644 index 0000000..2bf9a10 --- /dev/null +++ b/lib/ivq/ITK/ImageStatisticsFromSeeds.hxx @@ -0,0 +1,125 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ImageStatisticsFromSeeds__hxx__ +#define __ivq__ITK__ImageStatisticsFromSeeds__hxx__ + +#include +#include + +// ------------------------------------------------------------------------- +template< class _TImage > +unsigned int ivq::ITK::ImageStatisticsFromSeeds< _TImage >:: +GetNumberOfIndices( ) const +{ + return( this->m_Indices.size( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::ImageStatisticsFromSeeds< _TImage >:: +ClearIndices( ) +{ + this->m_Indices.clear( ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::ImageStatisticsFromSeeds< _TImage >:: +AddIndex( const TIndex& i ) +{ + this->m_Indices.insert( i ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::ImageStatisticsFromSeeds< _TImage >:: +RemoveIndex( const TIndex& i ) +{ + typename TIndices::iterator it = this->m_Indices.find( i ); + if( it != this->m_Indices.end( ) ) + this->m_Indices.erase( it ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::ImageStatisticsFromSeeds< _TImage >:: +Compute( ) +{ + // Some values + const TImage* img = this->m_Image; + typename TImage::RegionType reg = img->GetRequestedRegion( ); + + // Prepare iterator + typedef itk::ConstNeighborhoodIterator< TImage > _TIt; + typename TImage::SizeType rad; + rad.Fill( this->m_Radius ); + _TIt nIt( rad, img, reg ); + unsigned long nSize = 1; + for( unsigned int d = 0; d < TImage::ImageDimension; ++d ) + nSize *= nIt.GetSize( d ); + + // Fill values + double s1 = double( 0 ); + double s2 = double( 0 ); + unsigned long N = 0; + typename TIndices::const_iterator idxIt = this->m_Indices.begin( ); + for( ; idxIt != this->m_Indices.end( ); ++idxIt ) + { + TIndex idx = *idxIt; + if( reg.IsInside( idx ) ) + { + nIt.SetLocation( idx ); + for( unsigned long i = 0; i < nSize; ++i ) + { + double v = double( nIt.GetPixel( i ) ); + s1 += v; + s2 += v * v; + N++; + + } // rof + + } // fi + + } // rof + + // Final computations + if( N > 0 ) + { + double n = double( N ); + this->m_Mean = s1 / n; + this->m_Deviation = std::sqrt( ( ( n * s2 ) - ( s1 * s1 ) ) / ( n * n ) ); + } + else + { + this->m_Mean = double( 0 ); + this->m_Deviation = double( 0 ); + + } // fi +} + +// ------------------------------------------------------------------------- +template< class _TImage > +ivq::ITK::ImageStatisticsFromSeeds< _TImage >:: +ImageStatisticsFromSeeds( ) + : Superclass( ), + m_Image( NULL ), + m_Mean( double( 0 ) ), + m_Deviation( double( 0 ) ), + m_Radius( 0 ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TImage > +ivq::ITK::ImageStatisticsFromSeeds< _TImage >:: +~ImageStatisticsFromSeeds( ) +{ +} + +#endif // __ivq__ITK__ImageStatisticsFromSeeds__hxx__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ImageUnaryFunctionFilter.h b/lib/ivq/ITK/ImageUnaryFunctionFilter.h new file mode 100644 index 0000000..2be71e6 --- /dev/null +++ b/lib/ivq/ITK/ImageUnaryFunctionFilter.h @@ -0,0 +1,72 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ImageUnaryFunctionFilter__h__ +#define __ivq__ITK__ImageUnaryFunctionFilter__h__ + +#include +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TInImage, class _TOutImage > + class ImageUnaryFunctionFilter + : public itk::ImageToImageFilter< _TInImage, _TOutImage > + { + public: + typedef itk::ImageToImageFilter< _TInImage, _TOutImage > Superclass; + typedef ImageUnaryFunctionFilter Self; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + typedef _TInImage TInImage; + typedef _TOutImage TOutImage; + typedef typename TInImage::PixelType TInPixel; + typedef typename TOutImage::PixelType TOutPixel; + typedef typename TOutImage::RegionType TRegion; + + typedef itk::FunctionBase< TInPixel, TOutPixel > TFunction; + + public: + itkNewMacro( Self ); + itkTypeMacro( + ivq::ITK::ImageUnaryFunctionFilter, itk::ImageToImageFilter + ); + + itkGetObjectMacro( Function, TFunction ); + itkGetConstObjectMacro( Function, TFunction ); + itkSetObjectMacro( Function, TFunction ); + + protected: + ImageUnaryFunctionFilter( ); + virtual ~ImageUnaryFunctionFilter( ); + + virtual void ThreadedGenerateData( const TRegion& region, itk::ThreadIdType threadId ) override; + + private: + // Purposely not implemented + ImageUnaryFunctionFilter( Self& other ); + Self& operator=( Self& other ); + + protected: + typename TFunction::Pointer m_Function; + }; + + } // ecapseman + +} // ecapseman + +#ifndef ITK_MANUAL_INSTANTIATION +# include +#endif // ITK_MANUAL_INSTANTIATION + +#endif // __ivq__ITK__ImageUnaryFunctionFilter__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ImageUnaryFunctionFilter.hxx b/lib/ivq/ITK/ImageUnaryFunctionFilter.hxx new file mode 100644 index 0000000..b90f73e --- /dev/null +++ b/lib/ivq/ITK/ImageUnaryFunctionFilter.hxx @@ -0,0 +1,67 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ImageUnaryFunctionFilter__hxx__ +#define __ivq__ITK__ImageUnaryFunctionFilter__hxx__ + +#include +#include +#include + +// ------------------------------------------------------------------------- +template< class _TInImage, class _TOutImage > +ivq::ITK::ImageUnaryFunctionFilter< _TInImage, _TOutImage >:: +ImageUnaryFunctionFilter( ) + : Superclass( ) +{ +} + + +// ------------------------------------------------------------------------- +template< class _TInImage, class _TOutImage > +ivq::ITK::ImageUnaryFunctionFilter< _TInImage, _TOutImage >:: +~ImageUnaryFunctionFilter( ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TInImage, class _TOutImage > +void ivq::ITK::ImageUnaryFunctionFilter< _TInImage, _TOutImage >:: +ThreadedGenerateData( const TRegion& region, itk::ThreadIdType threadId ) +{ + // Configure data for this thread + const typename TRegion::SizeType& regionSize = region.GetSize( ); + if( regionSize[ 0 ] == 0 ) + return; + const TInImage* in = this->GetInput( ); + TOutImage* out = this->GetOutput( 0 ); + const size_t nLines = region.GetNumberOfPixels( ) / regionSize[ 0 ]; + itk::ProgressReporter progress( this, threadId, nLines ); + + // Iterate over this region + itk::ImageScanlineConstIterator< _TInImage > iIt( in, region ); + itk::ImageScanlineIterator< _TOutImage > oIt( out, region ); + iIt.GoToBegin( ); + oIt.GoToBegin( ); + while( !iIt.IsAtEnd( ) ) + { + while( !iIt.IsAtEndOfLine( ) ) + { + oIt.Set( this->m_Function->Evaluate( iIt.Get( ) ) ); + ++iIt; + ++oIt; + + } // elihw + iIt.NextLine( ); + oIt.NextLine( ); + progress.CompletedPixel( ); + + } // elihw +} + +#endif // __ivq__ITK__ImageUnaryFunctionFilter__hxx__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/IncrementalMeanAndVariance.cxx b/lib/ivq/ITK/IncrementalMeanAndVariance.cxx new file mode 100644 index 0000000..eab1d28 --- /dev/null +++ b/lib/ivq/ITK/IncrementalMeanAndVariance.cxx @@ -0,0 +1,75 @@ +// ========================================================================= +// @author Leonardo Florez Valencia +// @email florez-l@javeriana.edu.co +// ========================================================================= + +#include +#include + +// ------------------------------------------------------------------------- +ivq::ITK::IncrementalMeanAndVariance:: +IncrementalMeanAndVariance( ) +{ + this->Clear( ); +} + +// ------------------------------------------------------------------------- +ivq::ITK::IncrementalMeanAndVariance:: +~IncrementalMeanAndVariance( ) +{ +} + +// ------------------------------------------------------------------------- +double ivq::ITK::IncrementalMeanAndVariance:: +GetMean( ) const +{ + return( this->m_M ); +} + +// ------------------------------------------------------------------------- +double ivq::ITK::IncrementalMeanAndVariance:: +GetVariance( ) const +{ + return( this->m_V ); +} + +// ------------------------------------------------------------------------- +double ivq::ITK::IncrementalMeanAndVariance:: +GetDeviation( ) const +{ + return( std::sqrt( this->m_V ) ); +} + +// ------------------------------------------------------------------------- +unsigned long ivq::ITK::IncrementalMeanAndVariance:: +GetNumberOfSamples( ) const +{ + return( ( unsigned long )( this->m_N ) ); +} + +// ------------------------------------------------------------------------- +void ivq::ITK::IncrementalMeanAndVariance:: +Clear( ) +{ + this->m_M = double( 0 ); + this->m_V = double( 0 ); + this->m_N = double( 0 ); +} + +// ------------------------------------------------------------------------- +void ivq::ITK::IncrementalMeanAndVariance:: +AddValue( double v ) +{ + this->m_N += double( 1 ); + double d = v - this->m_M; + if( this->m_N > double( 1 ) ) + { + double o = ( this->m_N - double( 2 ) ) / ( this->m_N - double( 1 ) ); + this->m_V = ( o * this->m_V ) + ( ( d * d ) / this->m_N ); + } + else + this->m_V = double( 0 ); + this->m_M += d / this->m_N; +} + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/IncrementalMeanAndVariance.h b/lib/ivq/ITK/IncrementalMeanAndVariance.h new file mode 100644 index 0000000..39e6c2e --- /dev/null +++ b/lib/ivq/ITK/IncrementalMeanAndVariance.h @@ -0,0 +1,46 @@ +// ========================================================================= +// @author Leonardo Florez Valencia +// @email florez-l@javeriana.edu.co +// ========================================================================= + +#ifndef __ivq__ITK__IncrementalMeanAndVariance__h__ +#define __ivq__ITK__IncrementalMeanAndVariance__h__ + +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + class IVQ_EXPORT IncrementalMeanAndVariance + { + public: + typedef IncrementalMeanAndVariance Self; + + public: + IncrementalMeanAndVariance( ); + virtual ~IncrementalMeanAndVariance( ); + + double GetMean( ) const; + double GetVariance( ) const; + double GetDeviation( ) const; + unsigned long GetNumberOfSamples( ) const; + + void Clear( ); + void AddValue( double v ); + + protected: + double m_M; + double m_V; + double m_N; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__ITK__IncrementalMeanAndVariance__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/IsoImageSlicer.h b/lib/ivq/ITK/IsoImageSlicer.h new file mode 100644 index 0000000..22b4526 --- /dev/null +++ b/lib/ivq/ITK/IsoImageSlicer.h @@ -0,0 +1,214 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__IsoImageSlicer__h__ +#define __ivq__ITK__IsoImageSlicer__h__ + +#include +#include +#include +#include +#include +#include +#include +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TSlicer, class _TInterpolateFunction > + class BaseImageSlicer + : public itk::ImageToImageFilter< typename _TSlicer::InputImageType, itk::Image< typename _TSlicer::InputImageType::PixelType, _TSlicer::ImageDimension - 1 > > + { + public: + // Basic types + typedef BaseImageSlicer Self; + typedef _TSlicer TSlicer; + typedef _TInterpolateFunction TInterpolateFunction; + typedef typename TSlicer::InputImageType TImage; + typedef typename TInterpolateFunction::CoordRepType TScalar; + typedef typename TImage::PixelType TPixel; + enum + { + Dim = TImage::ImageDimension, + SliceDim = TImage::ImageDimension - 1 + }; + typedef itk::Image< TPixel, Self::SliceDim > TSliceImage; + + // itk types + typedef itk::ImageToImageFilter< TImage, TSliceImage > Superclass; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + // Internal filters + typedef itk::ExtractImageFilter< TImage, TSliceImage > TCollapsor; + + // Various types + typedef typename TImage::IndexType TIndex; + typedef typename TImage::RegionType TRegion; + typedef typename TImage::SizeType TSize; + typedef typename TImage::SpacingType TSpacing; + typedef typename TSpacing::ValueType TSpacingValue; + + typedef itk::AffineTransform< TScalar, Self::Dim > TTransform; + typedef typename TTransform::MatrixType TMatrix; + typedef typename TTransform::OffsetType TVector; + + public: + itkNewMacro( Self ); + itkTypeMacro( BaseImageSlicer, itkImageToImageFilter ); + + itkBooleanMacro( SizeFromMaximum ); + itkBooleanMacro( SizeFromMinimum ); + itkBooleanMacro( SpacingFromMaximum ); + itkBooleanMacro( SpacingFromMinimum ); + + itkGetConstObjectMacro( Transform, TTransform ); + itkGetConstMacro( DefaultValue, TPixel ); + itkGetConstMacro( Size, TVector ); + itkGetConstMacro( SizeFromMaximum, bool ); + itkGetConstMacro( SizeFromMinimum, bool ); + itkGetConstMacro( Spacing, TSpacingValue ); + itkGetConstMacro( SpacingFromMaximum, bool ); + itkGetConstMacro( SpacingFromMinimum, bool ); + + itkSetObjectMacro( Transform, TTransform ); + itkSetMacro( Size, TVector ); + itkSetMacro( DefaultValue, TPixel ); + itkSetMacro( SizeFromMaximum, bool ); + itkSetMacro( SizeFromMinimum, bool ); + itkSetMacro( Spacing, TSpacingValue ); + itkSetMacro( SpacingFromMaximum, bool ); + itkSetMacro( SpacingFromMinimum, bool ); + + public: + virtual unsigned long GetMTime( ) const override; + + const TInterpolateFunction* GetInterpolator( ) const; + const TMatrix& GetRotation( ) const; + const TVector& GetTranslation( ) const; + + void SetInterpolator( TInterpolateFunction* f ); + + template< class _TOtherMatrix > + void SetRotation( const _TOtherMatrix& r ); + + template< class _TOtherVector > + void SetTranslation( const _TOtherVector& t ); + + void SetSize( TScalar s ); + + protected: + BaseImageSlicer( ); + virtual ~BaseImageSlicer( ); + + virtual void GenerateOutputInformation( ) override; // TODO { } + virtual void GenerateInputRequestedRegion( ) override; + virtual void GenerateData( ) override; + + private: + // Purposely not implemented + BaseImageSlicer( const Self& ); + void operator=( const Self& ); + + protected: + typename TSlicer::Pointer m_Slicer; + typename TCollapsor::Pointer m_Collapsor; + typename TTransform::Pointer m_Transform; + + TPixel m_DefaultValue; + + TVector m_Size; + bool m_SizeFromMaximum; + bool m_SizeFromMinimum; + + TSpacingValue m_Spacing; + bool m_SpacingFromMaximum; + bool m_SpacingFromMinimum; + }; + + } // ecapseman + +} // ecapseman + +// ------------------------------------------------------------------------- +#define ivq_ITK_DefineIsoImageSlicer( name, R, F ) \ + template< class _TImage, class _TScalar = double > \ + class name \ + : public ivq::ITK::BaseImageSlicer< R< _TImage, _TImage, _TScalar >, F< _TImage, _TScalar > > \ + { \ + public: \ + typedef ivq::ITK::BaseImageSlicer< R< _TImage, _TImage, _TScalar >, F< _TImage, _TScalar > > Superclass; \ + typedef name Self; \ + typedef itk::SmartPointer< Self > Pointer; \ + typedef itk::SmartPointer< const Self > ConstPointer; \ + public: \ + itkNewMacro( Self ); \ + itkTypeMacro( ivq::ITK::name, ivq::ITK::BaseSlicer ); \ + protected: \ + name( ) : Superclass( ) { } \ + virtual ~name( ) { } \ + private: \ + name( const Self& ); \ + void operator=( const Self& ); \ + }; + +namespace ivq +{ + namespace ITK + { + ivq_ITK_DefineIsoImageSlicer( + IsoImageSlicer, + itk::ResampleImageFilter, + itk::InterpolateImageFunction + ); + ivq_ITK_DefineIsoImageSlicer( + VectorIsoImageSlicer, + itk::VectorResampleImageFilter, + itk::VectorInterpolateImageFunction + ); + + } // ecapseman + +} // ecapseman + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +template< class _TOtherMatrix > +void ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +SetRotation( const _TOtherMatrix& r ) +{ + TMatrix rotation; + for( unsigned int i = 0; i < Self::Dim; ++i ) + for( unsigned int j = 0; j < Self::Dim; ++j ) + rotation[ i ][ j ] = r[ i ][ j ]; + this->m_Transform->SetMatrix( rotation ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +template< class _TOtherVector > +void ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +SetTranslation( const _TOtherVector& t ) +{ + TVector off; + for( unsigned int i = 0; i < Self::Dim; ++i ) + off[ i ] = t[ i ]; + this->m_Transform->SetOffset( off ); + this->Modified( ); +} + +#ifndef ITK_MANUAL_INSTANTIATION +# include +#endif // ITK_MANUAL_INSTANTIATION + +#endif // __ivq__ITK__IsoImageSlicer__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/IsoImageSlicer.hxx b/lib/ivq/ITK/IsoImageSlicer.hxx new file mode 100644 index 0000000..cfcfc5e --- /dev/null +++ b/lib/ivq/ITK/IsoImageSlicer.hxx @@ -0,0 +1,209 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__IsoImageSlicer__hxx__ +#define __ivq__ITK__IsoImageSlicer__hxx__ + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +unsigned long ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +GetMTime( ) const +{ + unsigned long t = this->Superclass::GetMTime( ); + unsigned long sT = this->m_Slicer->GetMTime( ); + unsigned long cT = this->m_Collapsor->GetMTime( ); + unsigned long tT = this->m_Transform->GetMTime( ); + t = ( sT > t )? sT: t; + t = ( cT > t )? cT: t; + t = ( tT > t )? tT: t; + return( t ); +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +const typename ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +TInterpolateFunction* +ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +GetInterpolator( ) const +{ + return( this->m_Slicer->GetInterpolator( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +const typename ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +TMatrix& ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +GetRotation( ) const +{ + return( this->m_Transform->GetMatrix( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +const typename ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +TVector& ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +GetTranslation( ) const +{ + return( this->m_Transform->GetOffset( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +void ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +SetInterpolator( TInterpolateFunction* f ) +{ + this->m_Slicer->SetInterpolator( f ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +void ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +SetSize( TScalar s ) +{ + this->m_Size.Fill( s ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +BaseImageSlicer( ) + : Superclass( ), + m_SizeFromMaximum( false ), + m_SizeFromMinimum( false ), + m_Spacing( TSpacingValue( 1 ) ), + m_SpacingFromMaximum( false ), + m_SpacingFromMinimum( false ) +{ + this->m_Size.Fill( TScalar( 1 ) ); + + // Slicer + this->m_Slicer = TSlicer::New( ); + + TIndex idx; + idx.Fill( 0 ); + this->m_Slicer->SetOutputStartIndex( idx ); + + // Dimension collapsor + this->m_Collapsor = TCollapsor::New( ); + this->m_Collapsor->SetInput( this->m_Slicer->GetOutput( ) ); + this->m_Collapsor->SetDirectionCollapseToIdentity( ); + + this->m_Transform = TTransform::New( ); + this->m_Transform->SetIdentity( ); +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +~BaseImageSlicer( ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +void ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +GenerateOutputInformation( ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +void ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +GenerateInputRequestedRegion( ) +{ + TImage* input = const_cast< TImage* >( this->GetInput( ) ); + if( input != NULL ) + input->SetRequestedRegionToLargestPossibleRegion( ); +} + +// ------------------------------------------------------------------------- +template< class _TSlicer, class _TInterpolateFunction > +void ivq::ITK::BaseImageSlicer< _TSlicer, _TInterpolateFunction >:: +GenerateData( ) +{ + const TImage* input = this->GetInput( ); + + // Spacing + TSpacing spac; + if( this->m_SpacingFromMaximum || this->m_SpacingFromMinimum ) + { + spac = input->GetSpacing( ); + TSpacingValue minIso = spac[ 0 ]; + TSpacingValue maxIso = spac[ 0 ]; + for( unsigned int i = 1; i < Self::Dim; i++ ) + { + minIso = ( spac[ i ] < minIso )? spac[ i ]: minIso; + maxIso = ( spac[ i ] > maxIso )? spac[ i ]: maxIso; + + } // rof + this->m_Spacing = ( this->m_SpacingFromMinimum )? minIso: maxIso; + + } // fi + spac.Fill( this->m_Spacing ); + + // Size and origin + if( this->m_SizeFromMaximum || this->m_SizeFromMinimum ) + { + TSize iSize = input->GetRequestedRegion( ).GetSize( ); + TSpacing iSpac = input->GetSpacing( ); + TScalar minSize = TScalar( iSize[ 0 ] ) * TScalar( iSpac[ 0 ] ); + TScalar maxSize = minSize; + for( unsigned int i = 1; i < Self::Dim; i++ ) + { + TScalar v = TScalar( iSize[ i ] ) * TScalar( iSpac[ i ] ); + minSize = ( v < minSize )? v: minSize; + maxSize = ( v > maxSize )? v: maxSize; + + } // rof + if( this->m_SizeFromMaximum ) + this->m_Size.Fill( maxSize ); + else + this->m_Size.Fill( minSize ); + + } // fi + + TSize size; + typename TSlicer::OriginPointType origin; + size[ 0 ] = 1; + origin[ 0 ] = 0; + for( unsigned int i = 1; i < Self::Dim; i++ ) + { + double s = double( this->m_Size[ i ] ) / double( spac[ i ] ); + size[ i ] = ( unsigned int )( s ); + origin[ i ] = -( 0.5 * this->m_Size[ i ] ); + + } // rof + + // Prepare slicer + this->m_Slicer->SetInput( input ); + this->m_Slicer->SetTransform( this->m_Transform ); + this->m_Slicer->SetOutputSpacing( spac ); + this->m_Slicer->SetOutputOrigin( origin ); + this->m_Slicer->SetSize( size ); + this->m_Slicer->SetDefaultPixelValue( this->m_DefaultValue ); + + // Slice! + // Note: UpdateLargestPossibleRegion( ) is used since we need the + // output regions to be updated at each filter call. + this->m_Slicer->UpdateLargestPossibleRegion( ); + + // Collapse result + TRegion region = this->m_Slicer->GetOutput( )->GetRequestedRegion( ); + TSize regionSize = region.GetSize( ); + regionSize[ 0 ] = 0; + region.SetSize( regionSize ); + this->m_Collapsor->SetExtractionRegion( region ); + + this->m_Collapsor->GraftOutput( this->GetOutput( ) ); + this->m_Collapsor->UpdateLargestPossibleRegion( ); + this->GraftOutput( this->m_Collapsor->GetOutput( ) ); +} + +#endif // __ivq__ITK__IsoImageSlicer__hxx__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/PeakDetector.cxx b/lib/ivq/ITK/PeakDetector.cxx new file mode 100644 index 0000000..2151313 --- /dev/null +++ b/lib/ivq/ITK/PeakDetector.cxx @@ -0,0 +1,188 @@ +// ========================================================================= +// @author Leonardo Florez Valencia +// @email florez-l@javeriana.edu.co +// ========================================================================= + +#include +#include + +// ------------------------------------------------------------------------- +ivq::ITK::PeakDetector:: +PeakDetector( ) + : m_K( 3 ), + m_T( 3.5 ), + m_I( 0.5 ) +{ +} + +// ------------------------------------------------------------------------- +ivq::ITK::PeakDetector:: +~PeakDetector( ) +{ +} + +// ------------------------------------------------------------------------- +unsigned long ivq::ITK::PeakDetector:: +GetKernelSize( ) const +{ + return( this->m_K ); +} + +// ------------------------------------------------------------------------- +double ivq::ITK::PeakDetector:: +GetThreshold( ) const +{ + return( this->m_T ); +} + +// ------------------------------------------------------------------------- +double ivq::ITK::PeakDetector:: +GetInfluence( ) const +{ + return( this->m_I ); +} + +// ------------------------------------------------------------------------- +void ivq::ITK::PeakDetector:: +SetKernelSize( unsigned long k ) +{ + this->m_K = k; + this->Clear( ); +} + +// ------------------------------------------------------------------------- +void ivq::ITK::PeakDetector:: +SetThreshold( double t ) +{ + this->m_T = t; + this->Clear( ); +} + +// ------------------------------------------------------------------------- +void ivq::ITK::PeakDetector:: +SetInfluence( double i ) +{ + this->m_I = i; + this->Clear( ); +} + +// ------------------------------------------------------------------------- +void ivq::ITK::PeakDetector:: +Clear( ) +{ + this->m_X.clear( ); + this->m_Y.clear( ); + this->m_YF.clear( ); + this->m_Avg.clear( ); + this->m_STD.clear( ); + this->m_Peaks.clear( ); + this->m_MeanAndVar.Clear( ); +} + +// ------------------------------------------------------------------------- +const std::vector< double >& ivq::ITK::PeakDetector:: +GetXValues( ) const +{ + return( this->m_X ); +} + +// ------------------------------------------------------------------------- +const std::vector< double >& ivq::ITK::PeakDetector:: +GetYValues( ) const +{ + return( this->m_Y ); +} + +// ------------------------------------------------------------------------- +const std::vector< double >& ivq::ITK::PeakDetector:: +GetFilteredYValues( ) const +{ + return( this->m_YF ); +} + +// ------------------------------------------------------------------------- +const std::vector< double >& ivq::ITK::PeakDetector:: +GetAverages( ) const +{ + return( this->m_Avg ); +} + +// ------------------------------------------------------------------------- +const std::vector< double >& ivq::ITK::PeakDetector:: +GetDeviations( ) const +{ + return( this->m_STD ); +} + +// ------------------------------------------------------------------------- +const std::vector< ivq::ITK::PeakDetector::TPeak >& ivq::ITK:: +PeakDetector::GetPeaks( ) const +{ + return( this->m_Peaks ); +} + +// ------------------------------------------------------------------------- +unsigned long ivq::ITK::PeakDetector:: +GetNumberOfSamples( ) const +{ + return( this->m_X.size( ) ); +} + +// ------------------------------------------------------------------------- +ivq::ITK::PeakDetector:: +TPeak ivq::ITK::PeakDetector:: +AddValue( double x, double y ) +{ + this->m_X.push_back( x ); + this->m_Y.push_back( y ); + + if( this->m_YF.size( ) < this->m_K ) + { + this->m_YF.push_back( y ); + this->m_Avg.push_back( double( 0 ) ); + this->m_STD.push_back( double( 0 ) ); + this->m_Peaks.push_back( Self::NoPeak ); + + this->m_MeanAndVar.AddValue( y ); + if( this->m_YF.size( ) == this->m_K ) + { + this->m_Avg.push_back( this->m_MeanAndVar.GetMean( ) ); + this->m_STD.push_back( this->m_MeanAndVar.GetDeviation( ) ); + + } // fi + } + else + { + unsigned long i = this->m_X.size( ) - 1; + if( + ( std::fabs( y - this->m_Avg[ i - 1 ] ) ) > + ( this->m_T * this->m_STD[ i - 1 ] ) + ) + { + this->m_Peaks.push_back( + ( y > this->m_Avg[ i - 1 ] )? Self::PosPeak: Self::NegPeak + ); + this->m_YF.push_back( + ( this->m_I * y ) + + ( ( double( 1 ) - this->m_I ) * this->m_YF[ i - 1 ] ) + ); + } + else + { + this->m_Peaks.push_back( Self::NoPeak ); + this->m_YF.push_back( y ); + + } // fi + + this->m_MeanAndVar.Clear( ); + unsigned long k = 0; + for( unsigned long j = i - this->m_K; j <= i; ++j, ++k ) + this->m_MeanAndVar.AddValue( this->m_YF[ j ] ); + this->m_Avg.push_back( this->m_MeanAndVar.GetMean( ) ); + this->m_STD.push_back( this->m_MeanAndVar.GetDeviation( ) ); + + } // fi + return( this->m_Peaks.back( ) ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/PeakDetector.h b/lib/ivq/ITK/PeakDetector.h new file mode 100644 index 0000000..0dfa494 --- /dev/null +++ b/lib/ivq/ITK/PeakDetector.h @@ -0,0 +1,76 @@ +// ========================================================================= +// @author Leonardo Florez Valencia +// @email florez-l@javeriana.edu.co +// ========================================================================= + +#ifndef __ivq__ITK__PeakDetector__h__ +#define __ivq__ITK__PeakDetector__h__ + +#include + +#include +#include + +namespace ivq +{ + namespace ITK + { + /** + * https://stackoverflow.com/questions/22583391/peak-signal-detection-in-realtime-timeseries-data + */ + class IVQ_EXPORT PeakDetector + { + public: + typedef PeakDetector Self; + + enum TPeak + { + NoPeak = 0, + PosPeak, + NegPeak + }; + + public: + PeakDetector( ); + virtual ~PeakDetector( ); + + unsigned long GetKernelSize( ) const; + double GetThreshold( ) const; + double GetInfluence( ) const; + + void SetKernelSize( unsigned long k ); + void SetThreshold( double t ); + void SetInfluence( double i ); + + const std::vector< double >& GetXValues( ) const; + const std::vector< double >& GetYValues( ) const; + const std::vector< double >& GetFilteredYValues( ) const; + const std::vector< double >& GetAverages( ) const; + const std::vector< double >& GetDeviations( ) const; + const std::vector< TPeak >& GetPeaks( ) const; + + void Clear( ); + unsigned long GetNumberOfSamples( ) const; + TPeak AddValue( double x, double y ); + + protected: + unsigned long m_K; + double m_T; + double m_I; + + std::vector< double > m_X; + std::vector< double > m_Y; + std::vector< double > m_YF; + std::vector< double > m_Avg; + std::vector< double > m_STD; + std::vector< TPeak > m_Peaks; + ivq::ITK::IncrementalMeanAndVariance m_MeanAndVar; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__ITK__PeakDetector__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/RasterContourFilter.h b/lib/ivq/ITK/RasterContourFilter.h new file mode 100644 index 0000000..2bec6f5 --- /dev/null +++ b/lib/ivq/ITK/RasterContourFilter.h @@ -0,0 +1,108 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__RasterContourFilter__h__ +#define __ivq__ITK__RasterContourFilter__h__ + +#include +#include + +// ------------------------------------------------------------------------- +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TImage > + class RasterContourFilter + : public itk::ImageSource< _TImage > + { + public: + // Basic types + typedef RasterContourFilter Self; + typedef itk::ImageSource< _TImage > Superclass; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + typedef _TImage TImage; + typedef typename _TImage::IndexType TIndex; + typedef typename _TImage::PixelType TPixel; + typedef typename _TImage::PointType TPoint; + typedef typename _TImage::RegionType TRegion; + typedef itk::ImageBase< 2 > TImageBase; + + public: + itkNewMacro( Self ); + itkTypeMacro( ivq::ITK::RasterContourFilter, itk::ImageSource ); + + itkGetConstObjectMacro( Template, TImageBase ); + itkGetConstMacro( InsideValue, TPixel ); + itkGetConstMacro( OutsideValue, TPixel ); + + itkSetConstObjectMacro( Template, TImageBase ); + itkSetMacro( InsideValue, TPixel ); + itkSetMacro( OutsideValue, TPixel ); + + public: + void AddPoint( double x, double y ); + void AddPoint( double p[ 2 ] ); + + template< class _TPoint > + inline void AddPoint( const _TPoint& p ); + + void ClearPoints( ); + + protected: + RasterContourFilter( ); + virtual ~RasterContourFilter( ); + + virtual void AllocateOutputs( ) override; + virtual void BeforeThreadedGenerateData( ) override; + virtual void AfterThreadedGenerateData( ) override; + virtual void ThreadedGenerateData( + const TRegion& region, itk::ThreadIdType id + ) override; + + private: + // Purposely not implemented + RasterContourFilter( const Self& ); + void operator=( const Self& ); + + protected: + std::deque< TPoint > m_Contour; + std::deque< TIndex > m_Polygon; + TRegion m_ROI; + typename TImageBase::ConstPointer m_Template; + TPixel m_InsideValue; + TPixel m_OutsideValue; + }; + + } // ecapseman + +} // ecapseman + +// ------------------------------------------------------------------------- +template< class _TImage > +template< class _TPoint > +void ivq::ITK::RasterContourFilter< _TImage >:: +AddPoint( const _TPoint& p ) +{ + TPoint pnt; + pnt[ 0 ] = p[ 0 ]; + pnt[ 1 ] = p[ 2 ]; + this->m_Contour.push_back( pnt ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +#ifndef ITK_MANUAL_INSTANTIATION +# include +#endif // ITK_MANUAL_INSTANTIATION + +#endif // __ivq__ITK__RasterContourFilter__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/RasterContourFilter.hxx b/lib/ivq/ITK/RasterContourFilter.hxx new file mode 100644 index 0000000..83eda54 --- /dev/null +++ b/lib/ivq/ITK/RasterContourFilter.hxx @@ -0,0 +1,175 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +// Inclusion test taken from: +// https://www.ecse.rpi.edu/Homepages/wrf/Research/Short_Notes/pnpoly.html + +#ifndef __ivq__ITK__RasterContourFilter__hxx__ +#define __ivq__ITK__RasterContourFilter__hxx__ + +#include +#include + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::RasterContourFilter< _TImage >:: +AddPoint( double x, double y ) +{ + TPoint pnt; + pnt[ 0 ] = x; + pnt[ 1 ] = y; + this->m_Contour.push_back( pnt ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::RasterContourFilter< _TImage >:: +AddPoint( double p[ 2 ] ) +{ + TPoint pnt; + pnt[ 0 ] = p[ 0 ]; + pnt[ 1 ] = p[ 1 ]; + this->m_Contour.push_back( pnt ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::RasterContourFilter< _TImage >:: +ClearPoints( ) +{ + this->m_Contour.clear( ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +ivq::ITK::RasterContourFilter< _TImage >:: +RasterContourFilter( ) + : Superclass( ), + m_InsideValue( TPixel( 1 ) ), + m_OutsideValue( TPixel( 0 ) ) +{ + this->ClearPoints( ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +ivq::ITK::RasterContourFilter< _TImage >:: +~RasterContourFilter( ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::RasterContourFilter< _TImage >:: +AllocateOutputs( ) +{ + _TImage* out = this->GetOutput( 0 ); + out->SetSpacing( this->m_Template->GetSpacing( ) ); + out->SetRegions( this->m_Template->GetRequestedRegion( ) ); + out->SetOrigin( this->m_Template->GetOrigin( ) ); + out->SetDirection( this->m_Template->GetDirection( ) ); + out->Allocate( ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::RasterContourFilter< _TImage >:: +BeforeThreadedGenerateData( ) +{ + // Keep just indices, not points + this->m_Polygon.clear( ); + _TImage* out = this->GetOutput( 0 ); + TIndex minIdx, maxIdx; + std::deque< TPoint >::const_iterator c = this->m_Contour.begin( ); + for( ; c != this->m_Contour.end( ); ++c ) + { + TIndex idx; + out->TransformPhysicalPointToIndex( *c, idx ); + bool added = true; + if( this->m_Polygon.size( ) > 0 ) + { + if( this->m_Polygon.back( ) != idx ) + { + this->m_Polygon.push_back( idx ); + minIdx[ 0 ] = ( idx[ 0 ] < minIdx[ 0 ] )? idx[ 0 ]: minIdx[ 0 ]; + minIdx[ 1 ] = ( idx[ 1 ] < minIdx[ 1 ] )? idx[ 1 ]: minIdx[ 1 ]; + maxIdx[ 0 ] = ( idx[ 0 ] > maxIdx[ 0 ] )? idx[ 0 ]: maxIdx[ 0 ]; + maxIdx[ 1 ] = ( idx[ 1 ] > maxIdx[ 1 ] )? idx[ 1 ]: maxIdx[ 1 ]; + + } // fi + } + else + { + this->m_Polygon.push_back( idx ); + minIdx = maxIdx = idx; + + } // fi + + } // rof + + // Set ROI + typename _TImage::SizeType size; + size[ 0 ] = maxIdx[ 0 ] - minIdx[ 0 ] + 1; + size[ 1 ] = maxIdx[ 1 ] - minIdx[ 1 ] + 1; + this->m_ROI.SetIndex( minIdx ); + this->m_ROI.SetSize( size ); +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::RasterContourFilter< _TImage >:: +AfterThreadedGenerateData( ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TImage > +void ivq::ITK::RasterContourFilter< _TImage >:: +ThreadedGenerateData( const TRegion& region, itk::ThreadIdType id ) +{ + long nVerts = this->m_Polygon.size( ); + _TImage* out = this->GetOutput( ); + itk::ImageRegionIteratorWithIndex< _TImage > iIt( out, region ); + for( iIt.GoToBegin( ); !iIt.IsAtEnd( ); ++iIt ) + { + TIndex p = iIt.GetIndex( ); + bool inside = false; + if( this->m_ROI.IsInside( p ) ) + { + long i, j; + for( i = 0, j = nVerts - 1; i < nVerts; j = i++ ) + { + TIndex pi = this->m_Polygon[ i ]; + TIndex pj = this->m_Polygon[ j ]; + double pi0 = double( pi[ 0 ] ); + double pi1 = double( pi[ 1 ] ); + double pj0 = double( pj[ 0 ] ); + double pj1 = double( pj[ 1 ] ); + double p0 = double( p[ 0 ] ); + double p1 = double( p[ 1 ] ); + double ji0 = pj0 - pi0; + double ji1 = pj1 - pi1; + double i1 = p1 - pi1; + if( + ( ( pi1 > p1 ) != ( pj1 > p1 ) ) && + ( p0 < ( ( ji0 * i1 ) / ji1 ) + pi0 ) + ) + inside = !inside; + + } // rof + + } // fi + iIt.Set( ( inside )? this->m_InsideValue: this->m_OutsideValue ); + + } // rof +} + +#endif // __ivq__ITK__RasterContourFilter__hxx__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/Simple3DCurve.cxx b/lib/ivq/ITK/Simple3DCurve.cxx new file mode 100644 index 0000000..e5649d5 --- /dev/null +++ b/lib/ivq/ITK/Simple3DCurve.cxx @@ -0,0 +1,177 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +// ------------------------------------------------------------------------- +template< class _TScalar > +void ivq::ITK::Simple3DCurve< _TScalar >:: +Modified( ) const +{ + this->Superclass::Modified( ); + this->m_FramesUpdated = false; +} + +// ------------------------------------------------------------------------- +template< class _TScalar > +void ivq::ITK::Simple3DCurve< _TScalar >:: +Clear( ) +{ + this->m_Points.clear( ); + this->m_Frames.clear( ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< class _TScalar > +void ivq::ITK::Simple3DCurve< _TScalar >:: +Smooth( const unsigned int& kernel_size ) +{ + std::vector< TPoint > new_points; + + TPoint p; + int k = int( kernel_size ); + unsigned int nPoints = this->m_Points.size( ); + for( unsigned int i = 0; i < nPoints; ++i ) + { + typename TPoint::VectorType v( TScalar( 0 ) ); + for( int j = -k; j <= k; ++j ) + { + int l = int( i ) + j; + if ( l < 0 ) p = this->m_Points[ 0 ]; + else if( l >= nPoints ) p = this->m_Points[ nPoints - 1 ]; + else p = this->m_Points[ l ]; + v += p.GetVectorFromOrigin( ); + + } // rof + v /= _TScalar( ( k << 1 ) + 1 ); + + p.Fill( 0 ); + p += v; + new_points.push_back( p ); + + } // rof + this->m_Points = new_points; + this->m_Frames.clear( ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +template< class _TScalar > +unsigned long ivq::ITK::Simple3DCurve< _TScalar >:: +GetNumberOfPoints( ) const +{ + return( this->m_Points.size( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TScalar > +const typename ivq::ITK::Simple3DCurve< _TScalar >:: +TMatrix& ivq::ITK::Simple3DCurve< _TScalar >:: +GetFrame( unsigned int id ) const +{ + if( !( this->m_FramesUpdated ) ) + { + unsigned long N = this->m_Points.size( ); + + std::vector< TVector > tg( N ); + tg[ 0 ] = this->m_Points[ 1 ] - this->m_Points[ 0 ]; + tg[ N - 1 ] = this->m_Points[ N - 1 ] - this->m_Points[ N - 2 ]; + for( unsigned int i = 1; i < N - 1; ++i ) + tg[ i ] = this->m_Points[ i + 1 ] - this->m_Points[ i - 1 ]; + + std::vector< TVector > no( N ); + std::vector< TVector > bn( N ); + TVector prev_tg( _TScalar( 0 ) ), prev_no( _TScalar( 0 ) ); + prev_tg[ 0 ] = _TScalar( 1 ); + prev_no[ 1 ] = _TScalar( 1 ); + for( unsigned int i = 0; i < N; ++i ) + { + auto ntg = tg[ i ].GetNorm( ); + if( double( ntg ) > double( 0 ) ) + tg[ i ] /= ntg; + + _TScalar ct = prev_tg * tg[ i ]; + TVector a = itk::CrossProduct( prev_tg, tg[ i ] ); + _TScalar st = a.GetNorm( ); + if( st > _TScalar( 0 ) ) + a /= st; + + no[ i ] = + ( prev_no * ct ) + + ( itk::CrossProduct( a, prev_no ) * st ) + + ( a * ( ( a * prev_no ) * ( _TScalar( 1 ) - ct ) ) ); + auto nno = no[ i ].GetNorm( ); + if( double( nno ) > double( 0 ) ) + no[ i ] /= nno; + + bn[ i ] = itk::CrossProduct( tg[ i ], no[ i ] ); + + prev_tg = tg[ i ]; + prev_no = no[ i ]; + + } // rof + + this->m_Frames.clear( ); + for( unsigned int i = 0; i < N; ++i ) + { + TMatrix m; + for( unsigned int d = 0; d < 3; ++d ) + { + m[ d ][ 0 ] = tg[ i ][ d ]; + m[ d ][ 1 ] = no[ i ][ d ]; + m[ d ][ 2 ] = bn[ i ][ d ]; + + } // rof + this->m_Frames.push_back( m ); + + } // rof + + this->m_FramesUpdated = true; + + } // fi + return( this->m_Frames[ id ] ); +} + +// ------------------------------------------------------------------------- +template< class _TScalar > +const typename ivq::ITK::Simple3DCurve< _TScalar >:: +TPoint& ivq::ITK::Simple3DCurve< _TScalar >:: +GetPoint( unsigned int id ) const +{ + return( this->m_Points[ id ] ); +} + +// ------------------------------------------------------------------------- +template< class _TScalar > +typename ivq::ITK::Simple3DCurve< _TScalar >:: +TVector ivq::ITK::Simple3DCurve< _TScalar >:: +GetVector( unsigned int id ) const +{ + return( this->m_Points[ id ].GetVectorFromOrigin( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TScalar > +ivq::ITK::Simple3DCurve< _TScalar >:: +Simple3DCurve( ) + : Superclass( ), + m_FramesUpdated( false ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TScalar > +ivq::ITK::Simple3DCurve< _TScalar >:: +~Simple3DCurve( ) +{ +} + +// ------------------------------------------------------------------------- +template class ivq::ITK::Simple3DCurve< float >; +template class ivq::ITK::Simple3DCurve< double >; + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/Simple3DCurve.h b/lib/ivq/ITK/Simple3DCurve.h new file mode 100644 index 0000000..c01abb9 --- /dev/null +++ b/lib/ivq/ITK/Simple3DCurve.h @@ -0,0 +1,83 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__Simple3DCurve__h__ +#define __ivq__ITK__Simple3DCurve__h__ + +#include + +#include +#include +#include +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TScalar > + class IVQ_EXPORT Simple3DCurve + : public itk::DataObject + { + public: + typedef Simple3DCurve Self; + typedef itk::DataObject Superclass; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + typedef _TScalar TScalar; + typedef itk::Matrix< TScalar, 3, 3 > TMatrix; + typedef itk::Point< TScalar, 3 > TPoint; + typedef typename TPoint::VectorType TVector; + + public: + itkNewMacro( Self ); + itkTypeMacro( ivq::ITK::Simple3DCurve, itk::DataObject ); + + public: + template< class _TVector > + inline void AddPoint( const _TVector& v ) + { + TPoint p; + p[ 0 ] = v[ 0 ]; + p[ 1 ] = v[ 1 ]; + p[ 2 ] = v[ 2 ]; + this->m_Points.push_back( p ); + this->Modified( ); + } + + virtual void Modified( ) const override; + void Clear( ); + void Smooth( const unsigned int& kernel_size = 1 ); + unsigned long GetNumberOfPoints( ) const; + const TMatrix& GetFrame( unsigned int id ) const; + const TPoint& GetPoint( unsigned int id ) const; + TVector GetVector( unsigned int id ) const; + + protected: + Simple3DCurve( ); + virtual ~Simple3DCurve( ); + + private: + // Purposely not implemented + Simple3DCurve( const Self& other ); + Self& operator=( const Self& other ); + + protected: + std::vector< TPoint > m_Points; + mutable std::vector< TMatrix > m_Frames; + mutable bool m_FramesUpdated; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__ITK__Simple3DCurve__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ThresholdFunction.h b/lib/ivq/ITK/ThresholdFunction.h new file mode 100644 index 0000000..690043c --- /dev/null +++ b/lib/ivq/ITK/ThresholdFunction.h @@ -0,0 +1,89 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ThresholdFunction__h__ +#define __ivq__ITK__ThresholdFunction__h__ + +#include + +#include + +namespace ivq +{ + namespace ITK + { + /** + */ + template< class _TIn, class _TOut > + class ThresholdFunction + : public itk::FunctionBase< _TIn, _TOut > + { + public: + typedef ThresholdFunction Self; + typedef itk::FunctionBase< _TIn, _TOut > Superclass; + typedef itk::SmartPointer< Self > Pointer; + typedef itk::SmartPointer< const Self > ConstPointer; + + typedef typename Superclass::InputType TInput; + typedef typename Superclass::OutputType TOutput; + + public: + itkNewMacro( Self ); + itkTypeMacro( ivq::ITK::ThresholdFunction, itk::FunctionBase ); + + itkBooleanMacro( Strict ); + itkBooleanMacro( Binary ); + + itkGetConstMacro( LowerThreshold, _TIn ); + itkGetConstMacro( UpperThreshold, _TIn ); + itkGetConstMacro( Strict, bool ); + itkGetConstMacro( Binary, bool ); + itkGetConstMacro( InsideValue, _TOut ); + itkGetConstMacro( OutsideValue, _TOut ); + + itkSetMacro( LowerThreshold, _TIn ); + itkSetMacro( UpperThreshold, _TIn ); + itkSetMacro( Strict, bool ); + itkSetMacro( Binary, bool ); + itkSetMacro( InsideValue, _TOut ); + itkSetMacro( OutsideValue, _TOut ); + + public: + void SetBetween( const _TIn& lower, const _TIn& upper ); + void SetBelow( const _TIn& value ); + void SetAbove( const _TIn& value ); + + virtual _TOut Evaluate( const _TIn& in ) const override; + + protected: + ThresholdFunction( ); + virtual ~ThresholdFunction( ); + + private: + // Purposely not implemented + ThresholdFunction( const Self& other ); + Self& operator=( const Self& other ); + + protected: + _TIn m_LowerThreshold; + _TIn m_UpperThreshold; + bool m_Strict; + bool m_Binary; + _TOut m_InsideValue; + _TOut m_OutsideValue; + }; + + } // ecapseman + +} // ecapseman + +#ifndef ITK_MANUAL_INSTANTIATION +# include +#endif // ITK_MANUAL_INSTANTIATION + +#endif // __ivq__ITK__ThresholdFunction__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/ITK/ThresholdFunction.hxx b/lib/ivq/ITK/ThresholdFunction.hxx new file mode 100644 index 0000000..090b278 --- /dev/null +++ b/lib/ivq/ITK/ThresholdFunction.hxx @@ -0,0 +1,98 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__ITK__ThresholdFunction__hxx__ +#define __ivq__ITK__ThresholdFunction__hxx__ + +#include + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +void ivq::ITK::ThresholdFunction< _TIn, _TOut >:: +SetBetween( const _TIn& lower, const _TIn& upper ) +{ + this->SetLowerThreshold( lower ); + this->SetUpperThreshold( upper ); +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +void ivq::ITK::ThresholdFunction< _TIn, _TOut >:: +SetBelow( const _TIn& value ) +{ + typedef std::numeric_limits< _TIn > _TTraits; + if( _TTraits::is_signed ) + this->SetLowerThreshold( -_TTraits::max( ) ); + else + this->SetLowerThreshold( _TIn( 0 ) ); + this->SetUpperThreshold( value ); +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +void ivq::ITK::ThresholdFunction< _TIn, _TOut >:: +SetAbove( const _TIn& value ) +{ + typedef std::numeric_limits< _TIn > _TTraits; + this->SetLowerThreshold( value ); + this->SetUpperThreshold( _TTraits::max( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +_TOut ivq::ITK::ThresholdFunction< _TIn, _TOut >:: +Evaluate( const _TIn& in ) const +{ + // Check threshold + bool inside = false; + if( this->m_Strict ) + { + inside = ( this->m_LowerThreshold < in ); + inside &= ( in < this->m_UpperThreshold ); + } + else + { + inside = ( this->m_LowerThreshold <= in ); + inside &= ( in <= this->m_UpperThreshold ); + + } // fi + + // Return value + if( inside ) + { + if( this->m_Binary ) + return( this->m_InsideValue ); + else + return( _TOut( in ) ); + } + else + return( this->m_OutsideValue ); +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +ivq::ITK::ThresholdFunction< _TIn, _TOut >:: +ThresholdFunction( ) + : Superclass( ), + m_LowerThreshold( _TIn( 0 ) ), + m_UpperThreshold( std::numeric_limits< _TIn >::max( ) ), + m_Strict( false ), + m_Binary( false ), + m_InsideValue( std::numeric_limits< _TOut >::max( ) ), + m_OutsideValue( _TOut( 0 ) ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TIn, class _TOut > +ivq::ITK::ThresholdFunction< _TIn, _TOut >:: +~ThresholdFunction( ) +{ +} + +#endif // __ivq__ITK__ThresholdFunction__hxx__ + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/DicomSeriesSelectorDialog.cxx b/lib/ivq/Qt/DicomSeriesSelectorDialog.cxx new file mode 100644 index 0000000..6e39f34 --- /dev/null +++ b/lib/ivq/Qt/DicomSeriesSelectorDialog.cxx @@ -0,0 +1,34 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include +#include + +// ------------------------------------------------------------------------- +ivq::Qt::DicomSeriesSelectorDialog:: +DicomSeriesSelectorDialog( QWidget* parent ) + : QDialog( parent ), + m_UI( new Ui::DicomSeriesSelectorDialog ) +{ + this->m_UI->setupUi( this ); + this->setWindowTitle( "Choose DICOM series" ); +} + +// ------------------------------------------------------------------------- +ivq::Qt::DicomSeriesSelectorDialog:: +~DicomSeriesSelectorDialog( ) +{ + delete this->m_UI; +} + +// ------------------------------------------------------------------------- +std::vector< std::string >* ivq::Qt::DicomSeriesSelectorDialog:: +selectedFilenames( ) +{ + return( this->m_UI->Selector->selectedFilenames( ) ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/DicomSeriesSelectorDialog.h b/lib/ivq/Qt/DicomSeriesSelectorDialog.h new file mode 100644 index 0000000..973dbcc --- /dev/null +++ b/lib/ivq/Qt/DicomSeriesSelectorDialog.h @@ -0,0 +1,46 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__Qt__DicomSeriesSelectorDialog__h__ +#define __ivq__Qt__DicomSeriesSelectorDialog__h__ + +#include + +#include +#include + +namespace Ui { class DicomSeriesSelectorDialog; } + +namespace ivq +{ + namespace Qt + { + /** + */ + class IVQ_EXPORT DicomSeriesSelectorDialog + : public QDialog + { + Q_OBJECT; + public: + typedef DicomSeriesSelectorDialog Self; + + public: + explicit DicomSeriesSelectorDialog( QWidget* parent = 0 ); + virtual ~DicomSeriesSelectorDialog( ); + + std::vector< std::string >* selectedFilenames( ); + + protected: + Ui::DicomSeriesSelectorDialog* m_UI; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__Qt__DicomSeriesSelectorDialog__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/DicomSeriesSelectorDialog.ui b/lib/ivq/Qt/DicomSeriesSelectorDialog.ui new file mode 100644 index 0000000..ee12b34 --- /dev/null +++ b/lib/ivq/Qt/DicomSeriesSelectorDialog.ui @@ -0,0 +1,81 @@ + + + DicomSeriesSelectorDialog + + + + 0 + 0 + 511 + 335 + + + + + 511 + 335 + + + + Dialog + + + + + + + + + Qt::Horizontal + + + QDialogButtonBox::Cancel|QDialogButtonBox::Ok + + + + + + + + ivq::Qt::DicomSeriesSelectorWidget + QWidget +
ivq/Qt/DicomSeriesSelectorWidget.h
+ 1 +
+
+ + + + ButtonBox + accepted() + DicomSeriesSelectorDialog + accept() + + + 248 + 254 + + + 157 + 274 + + + + + ButtonBox + rejected() + DicomSeriesSelectorDialog + reject() + + + 316 + 260 + + + 286 + 274 + + + + +
diff --git a/lib/ivq/Qt/DicomSeriesSelectorWidget.cxx b/lib/ivq/Qt/DicomSeriesSelectorWidget.cxx new file mode 100644 index 0000000..a98ac75 --- /dev/null +++ b/lib/ivq/Qt/DicomSeriesSelectorWidget.cxx @@ -0,0 +1,187 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include +#include + +#include +#include +#include + +// ------------------------------------------------------------------------- +ivq::Qt::DicomSeriesSelectorWidget:: +DicomSeriesSelectorWidget( QWidget* parent ) + : QWidget( parent ), + m_UI( new Ui::DicomSeriesSelectorWidget ) +{ + this->m_UI->setupUi( this ); + this->setStartDir( ".", false ); + this->connect( + this->m_UI->ChooseButton, SIGNAL( clicked( ) ), + this, SLOT( _Choose( ) ) + ); +} + +// ------------------------------------------------------------------------- +ivq::Qt::DicomSeriesSelectorWidget:: +~DicomSeriesSelectorWidget( ) +{ + delete this->m_UI; +} + +// ------------------------------------------------------------------------- +QString ivq::Qt::DicomSeriesSelectorWidget:: +startDir( ) const +{ + return( this->m_UI->Directory->text( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::Qt::DicomSeriesSelectorWidget:: +setStartDir( const QString& dir, bool build ) +{ + this->m_Series.clear( ); + + this->m_UI->Directory->setText( dir ); + if( !build ) + return; + + // Process subdirs + QApplication::setOverrideCursor( ::Qt::WaitCursor ); + + this->m_UI->Series->clear( ); + this->m_UI->Series->setColumnCount( 3 ); + QStringList labels; + labels << "Images count" << "Series UID" << "Series path"; + this->m_UI->Series->setHorizontalHeaderLabels( labels ); + + std::string main_dir_name = dir.toStdString( ); + std::queue< std::string > q; + q.push( main_dir_name ); + while( !( q.empty( ) ) ) + { + std::string dir_name = q.front( ); + q.pop( ); + + // Update queue + QDir dir( dir_name.c_str( ) ); + QFileInfoList contents = dir.entryInfoList( ); + QFileInfoList::const_iterator i = contents.begin( ); + std::set< std::string > files; + for( ; i != contents.end( ); ++i ) + { + if( i->isDir( ) ) + { + std::string new_dir_name = i->absoluteFilePath( ).toStdString( ); + if( new_dir_name.size( ) > dir_name.size( ) ) + q.push( new_dir_name ); + } + else + files.insert( i->absoluteFilePath( ).toStdString( ) ); + + } // rof + + if( files.size( ) > 0 ) + { + this->m_GDCMHelper.Clear( ); + this->m_GDCMHelper.SetUseSeriesDetails( true ); + this->m_GDCMHelper.SetLoadMode( 0 ); + this->m_GDCMHelper.AddRestriction( "0008|0021" ); + this->m_GDCMHelper.SetFileNames( files.begin( ), files.end( ) ); + + gdcm::FileList* flist = + this->m_GDCMHelper.GetFirstSingleSerieUIDFileSet( ); + while( flist != NULL ) + { + if( flist->size( ) > 0 ) + { + this->m_GDCMHelper.OrderFileList( flist ); + gdcm::File* file = ( *flist )[ 0 ]; + std::string id = + this->m_GDCMHelper.CreateUniqueSeriesIdentifier( file ).c_str( ); + + gdcm::FileList::iterator it; + for( it = flist->begin( ); it != flist->end( ); ++it ) + if( *it != NULL ) + this->m_Series[ id ].push_back( ( *it )->filename ); + + } // fi + flist = this->m_GDCMHelper.GetNextSingleSerieUIDFileSet( ); + + } // elihw + + } // fi + + } // elihw + + // Show series + std::map< std::string, std::vector< std::string > >::const_iterator sIt = + this->m_Series.begin( ); + for( ; sIt != this->m_Series.end( ); ++sIt ) + { + if( sIt->second.size( ) > 0 ) + { + QFileInfo fdir( sIt->second[ 0 ].c_str( ) ); + + unsigned long rows = this->m_UI->Series->rowCount( ); + this->m_UI->Series->insertRow( rows ); + std::stringstream str_count; + str_count << sIt->second.size( ); + QTableWidgetItem* count_item = + new QTableWidgetItem( str_count.str( ).c_str( ) ); + QTableWidgetItem* uid_item = + new QTableWidgetItem( sIt->first.c_str( ) ); + QTableWidgetItem* dir_item = + new QTableWidgetItem( fdir.dir( ).canonicalPath( ) ); + count_item->setFlags( count_item->flags( ) & ~::Qt::ItemIsEditable ); + uid_item->setFlags( uid_item->flags( ) & ~::Qt::ItemIsEditable ); + dir_item->setFlags( dir_item->flags( ) & ~::Qt::ItemIsEditable ); + this->m_UI->Series->setItem( rows, 0, count_item ); + this->m_UI->Series->setItem( rows, 1, uid_item ); + this->m_UI->Series->setItem( rows, 2, dir_item ); + + } // fi + + } // rof + + // Restore cursor + QApplication::restoreOverrideCursor( ); +} + +// ------------------------------------------------------------------------- +std::vector< std::string >* ivq::Qt::DicomSeriesSelectorWidget:: +selectedFilenames( ) +{ + QList< QTableWidgetItem* > items = this->m_UI->Series->selectedItems( ); + if( items.size( ) > 0 ) + { + std::string uid = + this->m_UI->Series-> + item( items[ 0 ]->row( ), 1 )->text( ).toStdString( ); + std::map< std::string, std::vector< std::string > >::iterator sIt = + this->m_Series.find( uid ); + if( sIt != this->m_Series.end( ) ) + return( &( sIt->second ) ); + + } // fi + return( NULL ); +} + +// ------------------------------------------------------------------------- +void ivq::Qt::DicomSeriesSelectorWidget:: +_Choose( ) +{ + QString qdir = + QFileDialog::getExistingDirectory( + this, tr( "Open Directory" ), + this->startDir( ), + QFileDialog::ShowDirsOnly | QFileDialog::DontResolveSymlinks + ); + if( qdir.toStdString( ) != "" ) + this->setStartDir( qdir ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/DicomSeriesSelectorWidget.h b/lib/ivq/Qt/DicomSeriesSelectorWidget.h new file mode 100644 index 0000000..6642803 --- /dev/null +++ b/lib/ivq/Qt/DicomSeriesSelectorWidget.h @@ -0,0 +1,75 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__Qt__DicomSeriesSelectorWidget__h__ +#define __ivq__Qt__DicomSeriesSelectorWidget__h__ + +#include + +#include +#include + +namespace Ui { class DicomSeriesSelectorWidget; } + +namespace ivq +{ + namespace Qt + { + /** + */ + class IVQ_EXPORT DicomSeriesSelectorWidget + : public QWidget + { + Q_OBJECT; + public: + typedef DicomSeriesSelectorWidget Self; + + protected: + /** + */ + class _GDCMSerieHelper + : public gdcm::SerieHelper + { + public: + _GDCMSerieHelper( ) + { + } + virtual ~_GDCMSerieHelper( ) + { + } + template< class _TIt > + void SetFileNames( _TIt b, _TIt e ) + { + for( _TIt i = b; i != e; ++i ) + this->AddFileName( *i ); + } + }; + + public: + explicit DicomSeriesSelectorWidget( QWidget* parent = 0 ); + virtual ~DicomSeriesSelectorWidget( ); + + QString startDir( ) const; + void setStartDir( const QString& dir, bool build = true ); + + std::vector< std::string >* selectedFilenames( ); + + protected slots: + void _Choose( ); + + protected: + Ui::DicomSeriesSelectorWidget* m_UI; + _GDCMSerieHelper m_GDCMHelper; + std::map< std::string, std::vector< std::string > > m_Series; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__Qt__DicomSeriesSelectorWidget__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/DicomSeriesSelectorWidget.ui b/lib/ivq/Qt/DicomSeriesSelectorWidget.ui new file mode 100644 index 0000000..d3b648f --- /dev/null +++ b/lib/ivq/Qt/DicomSeriesSelectorWidget.ui @@ -0,0 +1,89 @@ + + + DicomSeriesSelectorWidget + + + + 0 + 0 + 358 + 299 + + + + Form + + + + 1 + + + 1 + + + + + + + + 101 + 14 + + + + + 101 + 14 + + + + DICOM directory: + + + + + + + true + + + true + + + + + + + + 25 + 25 + + + + + 25 + 25 + + + + ... + + + + + + + + + QAbstractItemView::SingleSelection + + + QAbstractItemView::SelectRows + + + + + + + + \ No newline at end of file diff --git a/lib/ivq/Qt/ImageViewerWidget.cxx b/lib/ivq/Qt/ImageViewerWidget.cxx new file mode 100644 index 0000000..4e3d64e --- /dev/null +++ b/lib/ivq/Qt/ImageViewerWidget.cxx @@ -0,0 +1,33 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include +#include +#include + +// ------------------------------------------------------------------------- +ivq::Qt::ImageViewerWidget:: +ImageViewerWidget( QWidget* parent, ::Qt::WindowFlags f ) + : QVTKWidget( parent, f ) +{ + this->Viewer = vtkSmartPointer< ivq::VTK::ImageViewer >::New( ); + this->Viewer->SetRenderWindow( this->GetRenderWindow( ) ); +} + +// ------------------------------------------------------------------------- +ivq::Qt::ImageViewerWidget:: +~ImageViewerWidget( ) +{ +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageViewer* ivq::Qt::ImageViewerWidget:: +GetViewer( ) +{ + return( this->Viewer.GetPointer( ) ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/ImageViewerWidget.h b/lib/ivq/Qt/ImageViewerWidget.h new file mode 100644 index 0000000..1fd67bd --- /dev/null +++ b/lib/ivq/Qt/ImageViewerWidget.h @@ -0,0 +1,48 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__Qt__ImageViewerWidget__h__ +#define __ivq__Qt__ImageViewerWidget__h__ + +#include + +#include +#include + +namespace ivq +{ + namespace VTK + { + class ImageViewer; + + } // ecapseman + + namespace Qt + { + /** + */ + class IVQ_EXPORT ImageViewerWidget + : public QVTKWidget + { + Q_OBJECT; + + public: + ImageViewerWidget( QWidget* parent = NULL, ::Qt::WindowFlags f = 0 ); + virtual ~ImageViewerWidget( ); + + ivq::VTK::ImageViewer* GetViewer( ); + + protected: + vtkSmartPointer< ivq::VTK::ImageViewer > Viewer; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__Qt__ImageViewerWidget__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/MPRViewersWidget.cxx b/lib/ivq/Qt/MPRViewersWidget.cxx new file mode 100644 index 0000000..87b0812 --- /dev/null +++ b/lib/ivq/Qt/MPRViewersWidget.cxx @@ -0,0 +1,70 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include +#include + +#include + +// ------------------------------------------------------------------------- +ivq::Qt::MPRViewersWidget:: +MPRViewersWidget( QWidget* parent, ::Qt::WindowFlags f ) + : QWidget( parent, f ), + UI( new Ui::MPRViewersWidget ) +{ + this->UI->setupUi( this ); + this->Viewers = vtkSmartPointer< ivq::VTK::MPRViewers >::New( ); + this->Viewers->SetView( 0, this->UI->V1->GetViewer( ) ); + this->Viewers->SetView( 1, this->UI->V2->GetViewer( ) ); + this->Viewers->SetView( 2, this->UI->V3->GetViewer( ) ); + + // Connect slots + this->connect( + this->UI->Splitter12, SIGNAL( splitterMoved( int, int ) ), + this, SLOT( _Sync34( int, int ) ) + ); + this->connect( + this->UI->Splitter34, SIGNAL( splitterMoved( int, int ) ), + this, SLOT( _Sync12( int, int ) ) + ); +} + +// ------------------------------------------------------------------------- +ivq::Qt::MPRViewersWidget:: +~MPRViewersWidget( ) +{ + delete this->UI; +} + +// ------------------------------------------------------------------------- +ivq::VTK::MPRViewers* ivq::Qt::MPRViewersWidget:: +GetViewers( ) +{ + return( this->Viewers ); +} + +// ------------------------------------------------------------------------- +ivq::Qt::RendererWidget* ivq::Qt::MPRViewersWidget:: +GetRendererWidget( ) +{ + return( this->UI->V4 ); +} + +// ------------------------------------------------------------------------- +void ivq::Qt::MPRViewersWidget:: +_Sync34( int a, int b ) +{ + this->UI->Splitter34->setSizes( this->UI->Splitter12->sizes( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::Qt::MPRViewersWidget:: +_Sync12( int a, int b ) +{ + this->UI->Splitter12->setSizes( this->UI->Splitter34->sizes( ) ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/MPRViewersWidget.h b/lib/ivq/Qt/MPRViewersWidget.h new file mode 100644 index 0000000..6d82e57 --- /dev/null +++ b/lib/ivq/Qt/MPRViewersWidget.h @@ -0,0 +1,53 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__Qt__MPRViewersWidget__h__ +#define __ivq__Qt__MPRViewersWidget__h__ + +#include + +#include +#include + +namespace Ui { class MPRViewersWidget; } + +namespace ivq +{ + namespace VTK { class MPRViewers; } + namespace Qt + { + class RendererWidget; + + /** + */ + class IVQ_EXPORT MPRViewersWidget + : public QWidget + { + Q_OBJECT; + + public: + MPRViewersWidget( QWidget* parent = NULL, ::Qt::WindowFlags f = 0 ); + virtual ~MPRViewersWidget( ); + + ivq::VTK::MPRViewers* GetViewers( ); + ivq::Qt::RendererWidget* GetRendererWidget( ); + + private slots: + void _Sync34( int a, int b ); + void _Sync12( int a, int b ); + + protected: + Ui::MPRViewersWidget* UI; + vtkSmartPointer< ivq::VTK::MPRViewers > Viewers; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__Qt__MPRViewersWidget__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/MPRViewersWidget.ui b/lib/ivq/Qt/MPRViewersWidget.ui new file mode 100644 index 0000000..139b16f --- /dev/null +++ b/lib/ivq/Qt/MPRViewersWidget.ui @@ -0,0 +1,71 @@ + + + MPRViewersWidget + + + + 0 + 0 + 400 + 300 + + + + Form + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + Qt::Vertical + + + + Qt::Horizontal + + + + + + + Qt::Horizontal + + + + + + + + + + + ivq::Qt::ImageViewerWidget + QWidget +
ivq/Qt/ImageViewerWidget.h
+ 1 +
+ + ivq::Qt::RendererWidget + QWidget +
ivq/Qt/RendererWidget.h
+ 1 +
+
+ + +
diff --git a/lib/ivq/Qt/RendererWidget.cxx b/lib/ivq/Qt/RendererWidget.cxx new file mode 100644 index 0000000..f0d54ec --- /dev/null +++ b/lib/ivq/Qt/RendererWidget.cxx @@ -0,0 +1,34 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include +#include + +// ------------------------------------------------------------------------- +ivq::Qt::RendererWidget:: +RendererWidget( QWidget* parent, ::Qt::WindowFlags f ) + : QVTKWidget( parent, f ) +{ + this->Renderer = vtkSmartPointer< vtkRenderer >::New( ); + this->GetRenderWindow( )->AddRenderer( this->Renderer ); +} + +// ------------------------------------------------------------------------- +ivq::Qt::RendererWidget:: +~RendererWidget( ) +{ +} + +// ------------------------------------------------------------------------- +vtkRenderer* ivq::Qt::RendererWidget:: +GetRenderer( ) +{ + return( this->Renderer.GetPointer( ) ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/Qt/RendererWidget.h b/lib/ivq/Qt/RendererWidget.h new file mode 100644 index 0000000..362c8cc --- /dev/null +++ b/lib/ivq/Qt/RendererWidget.h @@ -0,0 +1,44 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__Qt__RendererWidget__h__ +#define __ivq__Qt__RendererWidget__h__ + +#include + +#include +#include + +class vtkRenderer; + +namespace ivq +{ + namespace Qt + { + /** + */ + class IVQ_EXPORT RendererWidget + : public QVTKWidget + { + Q_OBJECT; + + public: + RendererWidget( QWidget* parent = NULL, ::Qt::WindowFlags f = 0 ); + virtual ~RendererWidget( ); + + vtkRenderer* GetRenderer( ); + + protected: + vtkSmartPointer< vtkRenderer > Renderer; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__Qt__RendererWidget__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/BrushWidget.cxx b/lib/ivq/VTK/BrushWidget.cxx new file mode 100644 index 0000000..1d42a4a --- /dev/null +++ b/lib/ivq/VTK/BrushWidget.cxx @@ -0,0 +1,639 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +// ------------------------------------------------------------------------- +ivq::VTK::BrushWidget:: +Self* ivq::VTK::BrushWidget:: +New( ) +{ + return( new Self ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +SetEnabled( int enabling ) +{ + if( this->Interactor == NULL ) + { + vtkErrorMacro( + << "The interactor must be set prior to enabling/disabling widget" + ); + return; + + } // fi + if( this->Actor.GetPointer( ) == NULL ) + { + vtkErrorMacro( + << "The external prop must be set prior to enabling/disabling widget" + ); + return; + + } // fi + + if( enabling != 0 ) + { + if( this->Enabled != 0 ) + return; + if( this->CurrentRenderer == NULL ) + { + this->SetCurrentRenderer( + this->Interactor->FindPokedRenderer( + this->Interactor->GetLastEventPosition( )[ 0 ], + this->Interactor->GetLastEventPosition( )[ 1 ] + ) + ); + if( this->CurrentRenderer == NULL ) + return; + + } // fi + this->Enabled = 1; + this->Brushing = false; + this->Filling = false; + this->ActualColor = 1; + this->_AddObservers( ); + + this->CircleActor->GetProperty( )-> + SetColor( this->CanvasLUT->GetTableValue( this->ActualColor ) ); + this->CurrentRenderer->AddViewProp( this->CircleActor->GetActor( ) ); + this->CurrentRenderer->AddViewProp( this->CanvasActor ); + this->CircleActor->GetActor( )->VisibilityOff( ); + + // Turn on the handles + /* TODO + for ( int i = 0; i < this->NumberOfHandles; ++i ) + { + this->CurrentRenderer->AddViewProp(this->Handle[i]); + this->Handle[i]->SetProperty(this->HandleProperty); + this->Handle[i]->PickableOff(); + } + + this->SizeHandles(); + + this->CurrentRenderer->AddViewProp(this->LineActor); + this->LineActor->SetProperty(this->LineProperty); + this->LineActor->PickableOff(); + */ + this->InvokeEvent(vtkCommand::EnableEvent,NULL); + } + else + { + vtkDebugMacro( << "Disabling tracer widget" ); + if( this->Enabled == 0 ) + return; + + // If disabling occurs without finishing an activity, cleanup states + /* TODO + if ( this->State == vtkImageTracerWidget::Tracing ) + { + this->OnLeftButtonUp(); + } + else if ( this->State == vtkImageTracerWidget::Snapping ) + { + this->Interactor->SetControlKey( 1 ); + this->OnMiddleButtonUp(); + } + */ + this->Enabled = 0; + this->Brushing = false; + this->Filling = false; + this->Interactor->RemoveObserver( this->EventCallbackCommand ); + this->CurrentRenderer->RemoveViewProp( this->CircleActor->GetActor( ) ); + this->CurrentRenderer->RemoveViewProp( this->CanvasActor ); + + // Turn off the handles + /* TODO + for( int i = 0; i < this->NumberOfHandles; ++i ) + { + this->CurrentRenderer->RemoveViewProp(this->Handle[i]); + } + + this->CurrentRenderer->RemoveViewProp(this->LineActor); + + this->CurrentHandle = NULL; + */ + + this->InvokeEvent( vtkCommand::DisableEvent, NULL ); + this->SetCurrentRenderer( NULL ); + + } // fi + this->Interactor->Render( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +PlaceWidget( double bounds[ 6 ] ) +{ + double bds[ 6 ], ctr[ 3 ]; + this->AdjustBounds( bounds, bds, ctr ); + for( int i = 0; i < 6; ++i ) + this->InitialBounds[ i ] = bds[ i ]; + this->InitialLength = std::sqrt( + ( bds[ 1 ] - bds[ 0 ] ) * ( bds[ 1 ] - bds[ 0 ] ) + + ( bds[ 3 ] - bds[ 2 ] ) * ( bds[ 3 ] - bds[ 2 ] ) + + ( bds[ 5 ] - bds[ 4 ] ) * ( bds[ 5 ] - bds[ 4 ] ) + ); + this->SizeHandles( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +PlaceWidget( ) +{ + this->Superclass::PlaceWidget( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +PlaceWidget( + double xmin, double xmax, + double ymin, double ymax, + double zmin, double zmax + ) +{ + this->Superclass::PlaceWidget( xmin, xmax, ymin, ymax, zmin, zmax ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +SetImageActor( ivq::VTK::ImageActor* actor ) +{ + if( this->Actor != actor ) + { + this->Actor = actor; + this->PropPicker->InitializePickList( ); + if( this->Actor.GetPointer( ) != NULL ) + { + this->PropPicker->AddPickList( this->Actor ); + + vtkImageData* image = this->Actor->GetInput( ); + int ext[ 6 ]; + double ori[ 3 ], spa[ 3 ]; + image->GetExtent( ext ); + image->GetOrigin( ori ); + image->GetSpacing( spa ); + + this->Spacing = spa[ 0 ]; + this->Spacing = ( spa[ 1 ] < this->Spacing )? spa[ 1 ]: this->Spacing; + this->Spacing = ( spa[ 2 ] < this->Spacing )? spa[ 2 ]: this->Spacing; + this->Radius = this->Spacing; + this->CircleActor->GetActor( )->SetScale( this->Radius ); + + unsigned long canvas_size = ext[ 1 ] - ext[ 0 ] + 1; + canvas_size *= ext[ 3 ] - ext[ 2 ] + 1; + canvas_size *= ext[ 5 ] - ext[ 4 ] + 1; + + this->Canvas = vtkSmartPointer< vtkImageData >::New( ); + this->Canvas->SetExtent( ext ); + this->Canvas->SetOrigin( ori ); + this->Canvas->SetSpacing( spa ); + this->Canvas->AllocateScalars( VTK_UNSIGNED_CHAR, 1 ); + std::memset( + this->Canvas->GetScalarPointer( ), 0, + canvas_size + ); + + this->CanvasLUT = vtkSmartPointer< vtkLookupTable >::New( ); + this->CanvasLUT->SetNumberOfColors( 7 ); + this->CanvasLUT->SetNumberOfTableValues( 7 ); + this->CanvasLUT->SetTableRange( 0, 6 ); + this->CanvasLUT->Build( ); + this->CanvasLUT->SetTableValue( 0, 0.0, 0.0, 0.0, 0.0 ); + this->CanvasLUT->SetTableValue( 1, 1.0, 0.0, 0.0, 0.6 ); + this->CanvasLUT->SetTableValue( 2, 0.0, 1.0, 0.0, 0.6 ); + this->CanvasLUT->SetTableValue( 3, 0.0, 0.0, 1.0, 0.6 ); + this->CanvasLUT->SetTableValue( 4, 0.0, 1.0, 1.0, 0.6 ); + this->CanvasLUT->SetTableValue( 5, 1.0, 0.0, 1.0, 0.6 ); + this->CanvasLUT->SetTableValue( 6, 1.0, 1.0, 0.0, 0.6 ); + + this->CanvasVisualization = + vtkSmartPointer< vtkImageMapToColors >::New( ); + this->CanvasVisualization->SetInputData( this->Canvas ); + this->CanvasVisualization->SetLookupTable( this->CanvasLUT ); + this->CanvasVisualization->Update( ); + + this->CanvasActor = vtkSmartPointer< ivq::VTK::ImageActor >::New( ); + this->CanvasActor-> + SetInputConnection( this->CanvasVisualization->GetOutputPort( ) ); + this->CanvasActor->Update( ); + + } // fi + + } // fi +} + +// ------------------------------------------------------------------------- +vtkImageData* ivq::VTK::BrushWidget:: +GetCanvas( ) const +{ + return( this->Canvas.GetPointer( ) ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::BrushWidget:: +BrushWidget( ) + : Superclass( ), + Brushing( false ), + Filling( false ) +{ + this->PropPicker = vtkSmartPointer< vtkPropPicker >::New( ); + this->PropPicker->PickFromListOn( ); + this->EventCallbackCommand->SetCallback( Self::ProcessEvents ); + + double _2pi = double( 6.28318530718 ); + unsigned int circle_samples = 50; + double _off = _2pi / double( circle_samples ); + vtkSmartPointer< vtkPoints > circle_points = + vtkSmartPointer< vtkPoints >::New( ); + vtkSmartPointer< vtkCellArray > circle_lines = + vtkSmartPointer< vtkCellArray >::New( ); + circle_lines->InsertNextCell( circle_samples + 1 ); + for( unsigned int i = 0; i < circle_samples; ++i ) + { + double w = _off * double( i ); + circle_points->InsertNextPoint( + std::cos( w ), std::sin( w ), double( 0 ) + ); + circle_lines->InsertCellPoint( i ); + + } // rof + circle_lines->InsertCellPoint( 0 ); + + this->Circle = vtkSmartPointer< vtkPolyData >::New( ); + this->Circle->SetPoints( circle_points ); + this->Circle->SetLines( circle_lines ); + + this->CircleActor = vtkSmartPointer< ivq::VTK::PolyDataActor >::New( ); + this->CircleActor->SetInputData( this->Circle ); + this->CircleActor->GetProperty( )->SetLineWidth( 2 ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::BrushWidget:: +~BrushWidget( ) +{ +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +_AddObservers( ) +{ + vtkRenderWindowInteractor* i = this->Interactor; + if( i == NULL ) + return; + + i->AddObserver( + vtkCommand::KeyPressEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::KeyReleaseEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::MouseWheelBackwardEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::MouseWheelForwardEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::MouseMoveEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::LeftButtonPressEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::LeftButtonReleaseEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::MiddleButtonPressEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::MiddleButtonReleaseEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::RightButtonPressEvent, + this->EventCallbackCommand, + this->Priority + ); + i->AddObserver( + vtkCommand::RightButtonReleaseEvent, + this->EventCallbackCommand, + this->Priority + ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +ProcessEvents( + vtkObject* object, unsigned long event, void* clientdata, void* calldata + ) +{ + Self* self = reinterpret_cast< Self* >( clientdata ); + switch( event ) + { + case vtkCommand::KeyPressEvent: + self->OnKeyPress( ); + break; + case vtkCommand::KeyReleaseEvent: + self->OnKeyRelease( ); + break; + case vtkCommand::MouseWheelBackwardEvent: + self->OnMouseWheelBackward( ); + break; + case vtkCommand::MouseWheelForwardEvent: + self->OnMouseWheelForward( ); + break; + case vtkCommand::LeftButtonPressEvent: + self->OnLeftButtonDown( ); + break; + case vtkCommand::LeftButtonReleaseEvent: + self->OnLeftButtonUp( ); + break; + case vtkCommand::MiddleButtonPressEvent: + self->OnMiddleButtonDown( ); + break; + case vtkCommand::MiddleButtonReleaseEvent: + self->OnMiddleButtonUp( ); + break; + case vtkCommand::RightButtonPressEvent: + self->OnRightButtonDown( ); + break; + case vtkCommand::RightButtonReleaseEvent: + self->OnRightButtonUp( ); + break; + case vtkCommand::MouseMoveEvent: + self->OnMouseMove( ); + break; + } // hctiws +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnKeyPress( ) +{ + if( + this->Interactor->GetKeyCode( ) == 'b' || + this->Interactor->GetKeyCode( ) == 'B' + ) + { + this->Brushing = true; + this->CircleActor->GetActor( )->VisibilityOn( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnKeyRelease( ) +{ + if( + this->Interactor->GetKeyCode( ) == 'b' || + this->Interactor->GetKeyCode( ) == 'B' + ) + { + this->Brushing = false; + this->CircleActor->GetActor( )->VisibilityOff( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnMouseWheelBackward( ) +{ + if( this->Brushing ) + { + this->Radius -= this->Spacing; + if( this->Radius < this->Spacing ) + this->Radius = this->Spacing; + this->CircleActor->GetActor( )->SetScale( this->Radius ); + + // Interact, if desired + this->EventCallbackCommand->SetAbortFlag( 1 ); + this->InvokeEvent( vtkCommand::InteractionEvent, NULL ); + this->Interactor->Render( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnMouseWheelForward( ) +{ + if( this->Brushing ) + { + this->Radius += this->Spacing; + this->CircleActor->GetActor( )->SetScale( this->Radius ); + + // Interact, if desired + this->EventCallbackCommand->SetAbortFlag( 1 ); + this->InvokeEvent( vtkCommand::InteractionEvent, NULL ); + this->Interactor->Render( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnLeftButtonDown( ) +{ + if( this->Brushing ) + { + this->Filling = true; + + // Interact, if desired + this->EventCallbackCommand->SetAbortFlag( 1 ); + this->InvokeEvent( vtkCommand::InteractionEvent, NULL ); + this->Interactor->Render( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnLeftButtonUp( ) +{ + if( this->Brushing ) + { + this->Filling = false; + + // Interact, if desired + this->EventCallbackCommand->SetAbortFlag( 1 ); + this->InvokeEvent( vtkCommand::InteractionEvent, NULL ); + this->Interactor->Render( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnMiddleButtonDown( ) +{ + if( this->Brushing ) + { + // Interact, if desired + this->EventCallbackCommand->SetAbortFlag( 1 ); + this->InvokeEvent( vtkCommand::InteractionEvent, NULL ); + this->Interactor->Render( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnMiddleButtonUp( ) +{ + if( this->Brushing ) + { + // Interact, if desired + this->EventCallbackCommand->SetAbortFlag( 1 ); + this->InvokeEvent( vtkCommand::InteractionEvent, NULL ); + this->Interactor->Render( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnRightButtonDown( ) +{ + if( this->Brushing ) + { + // Interact, if desired + this->EventCallbackCommand->SetAbortFlag( 1 ); + this->InvokeEvent( vtkCommand::InteractionEvent, NULL ); + this->Interactor->Render( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnRightButtonUp( ) +{ + if( this->Brushing ) + { + this->ActualColor = this->ActualColor + 1; + if( this->ActualColor >= this->CanvasLUT->GetNumberOfTableValues( ) ) + this->ActualColor = 1; + this->CircleActor->GetProperty( )-> + SetColor( this->CanvasLUT->GetTableValue( this->ActualColor ) ); + + // Interact, if desired + this->EventCallbackCommand->SetAbortFlag( 1 ); + this->InvokeEvent( vtkCommand::InteractionEvent, NULL ); + this->Interactor->Render( ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::BrushWidget:: +OnMouseMove( ) +{ + if( this->Brushing ) + { + int X = this->Interactor->GetEventPosition( )[ 0 ]; + int Y = this->Interactor->GetEventPosition( )[ 1 ]; + int p = this->PropPicker->PickProp( X, Y, this->CurrentRenderer ); + if( p == 0 ) + return; + double pos[ 3 ]; + this->PropPicker->GetPickPosition( pos ); + this->CircleActor->GetActor( )->SetPosition( pos ); + + if( this->Filling ) + { + double x[ 3 ], y[ 3 ], pcoords[ 3 ], spac[ 3 ]; + int ijk[ 3 ], ext[ 6 ]; + this->CircleActor->GetActor( )->GetPosition( x ); + this->Canvas->ComputeStructuredCoordinates( x, ijk, pcoords ); + this->Canvas->GetSpacing( spac ); + this->Canvas->GetExtent( ext ); + + int min_h, max_h, min_v, max_v; + min_h = int( ( x[ 0 ] - this->Radius ) / spac[ 0 ] ); + max_h = int( ( x[ 0 ] + this->Radius ) / spac[ 0 ] ); + min_v = int( ( x[ 1 ] - this->Radius ) / spac[ 1 ] ); + max_v = int( ( x[ 1 ] + this->Radius ) / spac[ 1 ] ); + for( int h = min_h; h <= max_h; ++h ) + { + if( ext[ 0 ] <= h && h <= ext[ 1 ] ) + { + for( int v = min_v; v <= max_v; ++v ) + { + if( ext[ 2 ] <= v && v <= ext[ 3 ] ) + { + /* TODO + ijk[ 0 ] = h; + ijk[ 1 ] = v; + this->Canvas->GetPoint( this->Canvas->ComputePointId( ijk ), y ); + double d = ( y[ 0 ] - x[ 0 ] ) * ( y[ 0 ] - x[ 0 ] ); + d += ( y[ 1 ] - x[ 1 ] ) * ( y[ 1 ] - x[ 1 ] ); + d += ( y[ 2 ] - x[ 2 ] ) * ( y[ 2 ] - x[ 2 ] ); + std::cout << d << " " << this->Radius << std::endl; + if( std::sqrt( d ) <= this->Radius ) + */ + this->Canvas-> + SetScalarComponentFromFloat( h, v, 0, 0, this->ActualColor ); + + } // fi + + } // rof + + } // fi + + } // rof + this->Canvas->Modified( ); + this->CanvasActor->Modified( ); + + } // fi + + // Interact, if desired + this->EventCallbackCommand->SetAbortFlag( 1 ); + this->InvokeEvent( vtkCommand::InteractionEvent, NULL ); + this->Interactor->Render( ); + + } // fi +} + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/BrushWidget.h b/lib/ivq/VTK/BrushWidget.h new file mode 100644 index 0000000..78f9beb --- /dev/null +++ b/lib/ivq/VTK/BrushWidget.h @@ -0,0 +1,112 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__BrushWidget__h__ +#define __ivq__VTK__BrushWidget__h__ + +#include + +#include +#include + +class vtkImageData; +class vtkImageMapToColors; +class vtkLookupTable; +class vtkPolyData; +class vtkPropPicker; + +namespace ivq +{ + namespace VTK + { + class ImageActor; + class PolyDataActor; + + /** + */ + class IVQ_EXPORT BrushWidget + : public vtk3DWidget + { + public: + typedef BrushWidget Self; + + public: + vtkTypeMacro( BrushWidget, vtk3DWidget ); + + public: + static Self* New( ); + + virtual void SetEnabled( int enabling ) override; + virtual void PlaceWidget( double bounds[ 6 ] ) override; + virtual void PlaceWidget( ) override; + virtual void PlaceWidget( + double xmin, double xmax, + double ymin, double ymax, + double zmin, double zmax + ) override; + + virtual void SetImageActor( ivq::VTK::ImageActor* actor ); + + vtkImageData* GetCanvas( ) const; + + protected: + BrushWidget( ); + virtual ~BrushWidget( ); + + void _AddObservers( ); + + //handles the events + static void ProcessEvents( + vtkObject* object, + unsigned long event, + void* clientdata, + void* calldata + ); + + // ProcessEvents() dispatches to these methods. + virtual void OnKeyPress( ); + virtual void OnKeyRelease( ); + virtual void OnMouseWheelBackward( ); + virtual void OnMouseWheelForward( ); + virtual void OnLeftButtonDown( ); + virtual void OnLeftButtonUp( ); + virtual void OnMiddleButtonDown( ); + virtual void OnMiddleButtonUp( ); + virtual void OnRightButtonDown( ); + virtual void OnRightButtonUp( ); + virtual void OnMouseMove( ); + + private: + // Purposely not implemented + BrushWidget( const Self& ); + Self& operator=( const Self& ); + + protected: + vtkSmartPointer< ivq::VTK::ImageActor > Actor; + vtkSmartPointer< vtkPropPicker > PropPicker; + + vtkSmartPointer< vtkImageData > Canvas; + vtkSmartPointer< vtkLookupTable > CanvasLUT; + vtkSmartPointer< vtkImageMapToColors > CanvasVisualization; + vtkSmartPointer< ivq::VTK::ImageActor > CanvasActor; + + vtkSmartPointer< vtkPolyData > Circle; + vtkSmartPointer< ivq::VTK::PolyDataActor > CircleActor; + + bool Brushing; + bool Filling; + double Radius; + double Spacing; + unsigned int ActualColor; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__BrushWidget__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/ImageActor.cxx b/lib/ivq/VTK/ImageActor.cxx new file mode 100644 index 0000000..b9a4f85 --- /dev/null +++ b/lib/ivq/VTK/ImageActor.cxx @@ -0,0 +1,217 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include +#include +#include +#include +#include + +// ------------------------------------------------------------------------- +ivq::VTK::ImageActor:: +Self* ivq::VTK::ImageActor:: +New( ) +{ + return( new Self( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +Modified( ) +{ + if( this->Mapper != NULL ) + { + if( this->Mapper->GetNumberOfInputConnections( 0 ) > 0 ) + { + this->Mapper->Modified( ); + this->Mapper->Update( ); + this->Superclass::Modified( ); + + } // fi + } + else + this->Superclass::Modified( ); +} + +// ------------------------------------------------------------------------- +vtkImageData* ivq::VTK::ImageActor:: +GetInput( ) +{ + return( this->Mapper->GetInput( ) ); +} + +// ------------------------------------------------------------------------- +vtkAlgorithm* ivq::VTK::ImageActor:: +GetInputAlgorithm( ) +{ + return( this->Mapper->GetInputAlgorithm( ) ); +} + +// ------------------------------------------------------------------------- +vtkInformation* ivq::VTK::ImageActor:: +GetInputInformation( ) +{ + return( this->Mapper->GetInputInformation( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +SetInputData( vtkImageData* input ) +{ + this->Mapper->SetInputData( input ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +SetInputConnection( vtkAlgorithmOutput* aout ) +{ + this->Mapper->SetInputConnection( aout ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageActor:: +GetOrientation( ) const +{ + return( this->Mapper->GetOrientation( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +SetOrientation( int orientation ) +{ + this->Mapper->SetOrientation( ( orientation < 3 )? orientation: 2 ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageActor:: +GetSliceNumber( ) const +{ + return( this->Mapper->GetSliceNumber( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +SetSliceNumber( int slice ) +{ + static int s = 0; + vtkImageData* image = this->Mapper->GetInput( ); + if( image != NULL ) + { + // Update slice + s = slice; + if( s < this->Mapper->GetSliceNumberMinValue( ) ) + s = this->Mapper->GetSliceNumberMinValue( ); + if( s > this->Mapper->GetSliceNumberMaxValue( ) ) + s = this->Mapper->GetSliceNumberMaxValue( ); + this->Mapper->SetSliceNumber( s ); + + // Propagate modifications + this->InvokeEvent( vtkCommand::InteractionEvent ); + this->Modified( ); + + } // fi +} + +// ------------------------------------------------------------------------- +vtkPlane* ivq::VTK::ImageActor:: +GetSlicePlane( ) +{ + return( this->Mapper->GetSlicePlane( ) ); +} + +// ------------------------------------------------------------------------- +const vtkPlane* ivq::VTK::ImageActor:: +GetSlicePlane( ) const +{ + return( this->Mapper->GetSlicePlane( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +GetActorBounds( double bounds[ 6 ] ) +{ + double origin[ 3 ]; + this->GetInput( )->GetBounds( bounds ); + this->GetSlicePlane( )->GetOrigin( origin ); + int orientation = this->GetOrientation( ); + bounds[ ( orientation << 1 ) ] = + bounds[ ( orientation << 1 ) + 1 ] = origin[ orientation ]; +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +GetActorCenter( double center[ 3 ] ) +{ + this->GetSlicePlane( )->GetOrigin( center ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +ResetWindowLevel( ) +{ + double r[ 2 ]; + this->GetInput( )->GetScalarRange( r ); + this->GetProperty( )->SetColorWindow( r[ 1 ] - r[ 0 ] ); + this->GetProperty( )->SetColorLevel( ( r[ 1 ] + r[ 0 ] ) * 0.5 ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +double ivq::VTK::ImageActor:: +GetColorWindow( ) +{ + return( this->GetProperty( )->GetColorWindow( ) ); +} + +// ------------------------------------------------------------------------- +double ivq::VTK::ImageActor:: +GetColorLevel( ) +{ + return( this->GetProperty( )->GetColorLevel( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +SetColorWindow( const double& w ) +{ + this->GetProperty( )->SetColorWindow( w ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageActor:: +SetColorLevel( const double& l ) +{ + this->GetProperty( )->SetColorLevel( l ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageActor:: +ImageActor( ) + : Superclass( ) +{ + this->Mapper = vtkImageSliceMapper::New( ); + this->SetMapper( this->Mapper ); + this->GetProperty( )->SetInterpolationTypeToNearest( ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageActor:: +~ImageActor( ) +{ + if( this->Mapper != NULL ) + this->Mapper->Delete( ); + this->Mapper = NULL; + this->SetMapper( NULL ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/ImageActor.h b/lib/ivq/VTK/ImageActor.h new file mode 100644 index 0000000..e0e3ebb --- /dev/null +++ b/lib/ivq/VTK/ImageActor.h @@ -0,0 +1,82 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__ImageActor__h__ +#define __ivq__VTK__ImageActor__h__ + +#include + +#include + +class vtkAlgorithm; +class vtkAlgorithmOutput; +class vtkImageData; +class vtkImageSliceMapper; +class vtkPlane; + +namespace ivq +{ + namespace VTK + { + /** + */ + class IVQ_EXPORT ImageActor + : public vtkImageSlice + { + public: + typedef ImageActor Self; + + public: + vtkTypeMacro( ImageActor, vtkImageSlice ); + + public: + static Self* New( ); + + virtual void Modified( ) override; + + vtkImageData* GetInput( ); + vtkAlgorithm* GetInputAlgorithm( ); + vtkInformation* GetInputInformation( ); + void SetInputData( vtkImageData* input ); + void SetInputConnection( vtkAlgorithmOutput* aout ); + + int GetOrientation( ) const; + void SetOrientation( int orientation ); + + int GetSliceNumber( ) const; + void SetSliceNumber( int slice ); + + vtkPlane* GetSlicePlane( ); + const vtkPlane* GetSlicePlane( ) const; + void GetActorBounds( double bounds[ 6 ] ); + void GetActorCenter( double center[ 3 ] ); + + void ResetWindowLevel( ); + double GetColorWindow( ); + double GetColorLevel( ); + void SetColorWindow( const double& w ); + void SetColorLevel( const double& l ); + + protected: + ImageActor( ); + virtual ~ImageActor( ); + + private: + // Purposely not implemented + ImageActor( const Self& ); + Self& operator=( const Self& ); + + protected: + vtkImageSliceMapper* Mapper; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__ImageActor__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/ImageSlicePointPlacer.cxx b/lib/ivq/VTK/ImageSlicePointPlacer.cxx new file mode 100644 index 0000000..b209f4a --- /dev/null +++ b/lib/ivq/VTK/ImageSlicePointPlacer.cxx @@ -0,0 +1,280 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include +#include +#include +#include +#include +#include + +// ------------------------------------------------------------------------- +vtkCxxSetObjectMacro( + ivq::VTK::ImageSlicePointPlacer, ImageSlice, vtkImageSlice + ); + +// ------------------------------------------------------------------------- +ivq::VTK::ImageSlicePointPlacer:: +Self* ivq::VTK::ImageSlicePointPlacer:: +New( ) +{ + return( new Self( ) ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageSlicePointPlacer:: +ComputeWorldPosition( + vtkRenderer* ren, + double displayPos[ 2 ], + double worldPos[ 3 ], + double worldOrient[ 9 ] + ) +{ + if( !this->UpdateInternalState( ) ) + return( 0 ); + return( + this->Placer->ComputeWorldPosition( + ren, displayPos, worldPos, worldOrient + ) + ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageSlicePointPlacer:: +ComputeWorldPosition( + vtkRenderer* ren, + double displayPos[ 2 ], + double refWorldPos[ 2 ], + double worldPos[ 3 ], + double worldOrient[ 9 ] + ) +{ + if( !this->UpdateInternalState( ) ) + return( 0 ); + return( + this->Placer->ComputeWorldPosition( + ren, displayPos, refWorldPos, worldPos, worldOrient + ) + ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageSlicePointPlacer:: +ValidateWorldPosition( double worldPos[ 3 ] ) +{ + if( !this->UpdateInternalState( ) ) + return( 0 ); + return( this->Placer->ValidateWorldPosition( worldPos ) ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageSlicePointPlacer:: +ValidateWorldPosition( double worldPos[ 3 ], double worldOrient[ 9 ] ) +{ + if( !this->UpdateInternalState( ) ) + return( 0 ); + return( this->Placer->ValidateWorldPosition( worldPos, worldOrient ) ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageSlicePointPlacer:: +UpdateWorldPosition( + vtkRenderer* ren, double worldPos[ 3 ], double worldOrient[ 9 ] + ) +{ + if( !this->UpdateInternalState( ) ) + return( 0 ); + return( this->Placer->UpdateWorldPosition( ren, worldPos, worldOrient ) ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageSlicePointPlacer:: +UpdateInternalState( ) +{ + if( !this->ImageSlice ) + return( 0 ); + + vtkImageData* input = this->ImageSlice->GetMapper( )->GetInput( ); + if( !input ) + return( 0 ); + + double spacing[ 3 ]; + input->GetSpacing( spacing ); + + double origin[ 3 ]; + input->GetOrigin( origin ); + + double b[ 6 ]; + this->ImageSlice->GetBounds( b ); + if( this->Bounds[ 0 ] != VTK_DOUBLE_MAX) + { + b[ 0 ] = ( b[ 0 ] < this->Bounds[ 0 ] )? this->Bounds[ 0 ] : b[ 0 ]; + b[ 1 ] = ( b[ 1 ] > this->Bounds[ 1 ] )? this->Bounds[ 1 ] : b[ 1 ]; + b[ 2 ] = ( b[ 2 ] < this->Bounds[ 2 ] )? this->Bounds[ 2 ] : b[ 2 ]; + b[ 3 ] = ( b[ 3 ] > this->Bounds[ 3 ] )? this->Bounds[ 3 ] : b[ 3 ]; + b[ 4 ] = ( b[ 4 ] < this->Bounds[ 4 ] )? this->Bounds[ 4 ] : b[ 4 ]; + b[ 5 ] = ( b[ 5 ] > this->Bounds[ 5 ] )? this->Bounds[ 5 ] : b[ 5 ]; + + } // fi + + int displayExtent[ 6 ] = { 0, 1, 0, 1, 0, 1 }; + input->GetExtent( displayExtent ); + vtkImageSliceMapper* mapper = + vtkImageSliceMapper::SafeDownCast( this->ImageSlice->GetMapper( ) ); + if( mapper != NULL ) + { + int ori = mapper->GetOrientation( ); + displayExtent[ ( ori << 1 ) + 1 ] = + displayExtent[ ori << 1 ] = + mapper->GetSliceNumber( ); + + } // fi + + int axis; + double position; + if( displayExtent[ 0 ] == displayExtent[ 1 ] ) + { + axis = vtkBoundedPlanePointPlacer::XAxis; + position = origin[ 0 ] + displayExtent[ 0 ] * spacing[ 0 ]; + } + else if( displayExtent[ 2 ] == displayExtent[ 3 ] ) + { + axis = vtkBoundedPlanePointPlacer::YAxis; + position = origin[ 1 ] + displayExtent[ 2 ] * spacing[ 1 ]; + } + else if( displayExtent[ 4 ] == displayExtent[ 5 ] ) + { + axis = vtkBoundedPlanePointPlacer::ZAxis; + position = origin[ 2 ] + displayExtent[ 4 ] * spacing[ 2 ]; + } + else + { + vtkErrorMacro( "Incorrect display extent in Image Slice" ); + return( 0 ); + + } // fi + + if( + axis != this->Placer->GetProjectionNormal( ) || + position != this->Placer->GetProjectionPosition( ) || + b[ 0 ] != this->SavedBounds[ 0 ] || + b[ 1 ] != this->SavedBounds[ 1 ] || + b[ 2 ] != this->SavedBounds[ 2 ] || + b[ 3 ] != this->SavedBounds[ 3 ] || + b[ 4 ] != this->SavedBounds[ 4 ] || + b[ 5 ] != this->SavedBounds[ 5 ] + ) + { + this->SavedBounds[ 0 ] = b[ 0 ]; + this->SavedBounds[ 1 ] = b[ 1 ]; + this->SavedBounds[ 2 ] = b[ 2 ]; + this->SavedBounds[ 3 ] = b[ 3 ]; + this->SavedBounds[ 4 ] = b[ 4 ]; + this->SavedBounds[ 5 ] = b[ 5 ]; + + this->Placer->SetProjectionNormal( axis ); + this->Placer->SetProjectionPosition( position ); + + this->Placer->RemoveAllBoundingPlanes( ); + + vtkPlane* plane; + if( axis != vtkBoundedPlanePointPlacer::XAxis ) + { + plane = vtkPlane::New( ); + plane->SetOrigin( b[ 0 ], b[ 2 ], b[ 4 ] ); + plane->SetNormal( 1.0, 0.0, 0.0 ); + this->Placer->AddBoundingPlane( plane ); + plane->Delete( ); + + plane = vtkPlane::New(); + plane->SetOrigin( b[ 1 ], b[ 3 ], b[ 5 ] ); + plane->SetNormal( -1.0, 0.0, 0.0 ); + this->Placer->AddBoundingPlane( plane ); + plane->Delete( ); + + } // fi + + if( axis != vtkBoundedPlanePointPlacer::YAxis ) + { + plane = vtkPlane::New( ); + plane->SetOrigin( b[ 0 ], b[ 2 ], b[ 4 ] ); + plane->SetNormal( 0.0, 1.0, 0.0 ); + this->Placer->AddBoundingPlane( plane ); + plane->Delete( ); + + plane = vtkPlane::New( ); + plane->SetOrigin( b[ 1 ], b[ 3 ], b[ 5 ] ); + plane->SetNormal( 0.0, -1.0, 0.0 ); + this->Placer->AddBoundingPlane( plane ); + plane->Delete( ); + + } // fi + + if( axis != vtkBoundedPlanePointPlacer::ZAxis ) + { + plane = vtkPlane::New( ); + plane->SetOrigin( b[ 0 ], b[ 2 ], b[ 4 ] ); + plane->SetNormal( 0.0, 0.0, 1.0 ); + this->Placer->AddBoundingPlane( plane ); + plane->Delete( ); + + plane = vtkPlane::New( ); + plane->SetOrigin( b[ 1 ], b[ 3 ], b[ 5 ] ); + plane->SetNormal( 0.0, 0.0, -1.0 ); + this->Placer->AddBoundingPlane( plane ); + plane->Delete( ); + + } // fi + + this->Modified( ); + + } // fi + return( 1 ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageSlicePointPlacer:: +SetWorldTolerance( double tol ) +{ + double t = + ( tol < 0.0 )? 0.0: ( ( tol > VTK_DOUBLE_MAX )? VTK_DOUBLE_MAX: tol ); + if( this->WorldTolerance != t ) + { + this->WorldTolerance = t; + this->Placer->SetWorldTolerance( tol ); + this->Modified( ); + + } // fi +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageSlicePointPlacer:: +ImageSlicePointPlacer( ) + : Superclass( ) +{ + this->Placer = vtkBoundedPlanePointPlacer::New( ); + this->ImageSlice = NULL; + this->SavedBounds[ 0 ] = 0.0; + this->SavedBounds[ 1 ] = 0.0; + this->SavedBounds[ 2 ] = 0.0; + this->SavedBounds[ 3 ] = 0.0; + this->SavedBounds[ 4 ] = 0.0; + this->SavedBounds[ 5 ] = 0.0; + this->Bounds[ 0 ] = this->Bounds[ 2 ] = this->Bounds[ 4 ] = VTK_DOUBLE_MAX; + this->Bounds[ 1 ] = this->Bounds[ 3 ] = this->Bounds[ 5 ] = VTK_DOUBLE_MIN; +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageSlicePointPlacer:: +~ImageSlicePointPlacer( ) +{ + this->Placer->Delete( ); + this->SetImageSlice( NULL ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/ImageSlicePointPlacer.h b/lib/ivq/VTK/ImageSlicePointPlacer.h new file mode 100644 index 0000000..3ea5376 --- /dev/null +++ b/lib/ivq/VTK/ImageSlicePointPlacer.h @@ -0,0 +1,87 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__ImageSlicePointPlacer__h__ +#define __ivq__VTK__ImageSlicePointPlacer__h__ + +#include + +#include + +class vtkBoundedPlanePointPlacer; +class vtkImageSlice; +class vtkRenderer; + +namespace ivq +{ + namespace VTK + { + /** + */ + class IVQ_EXPORT ImageSlicePointPlacer + : public vtkPointPlacer + { + public: + typedef ImageSlicePointPlacer Self; + + public: + vtkTypeMacro( ImageSlicePointPlacer, vtkPointPlacer ); + + vtkGetObjectMacro( ImageSlice, vtkImageSlice ); + vtkSetVector6Macro( Bounds, double ); + vtkGetVector6Macro( Bounds, double ); + + public: + static Self* New( ); + + int ComputeWorldPosition( + vtkRenderer* ren, + double displayPos[ 2 ], + double worldPos[ 3 ], + double worldOrient[ 9 ] + ); + int ComputeWorldPosition( + vtkRenderer* ren, + double displayPos[ 2 ], + double refWorldPos[ 2 ], + double worldPos[ 3 ], + double worldOrient[ 9 ] + ); + int ValidateWorldPosition( double worldPos[ 3 ] ); + int ValidateWorldPosition( + double worldPos[ 3 ], double worldOrient[ 9 ] + ); + int UpdateWorldPosition( + vtkRenderer* ren, double worldPos[ 3 ], double worldOrient[ 9 ] + ); + int UpdateInternalState( ); + + void SetImageSlice( vtkImageSlice* slice ); + virtual void SetWorldTolerance( double tol ); + + protected: + ImageSlicePointPlacer( ); + virtual ~ImageSlicePointPlacer( ); + + private: + // Purposely not implemented + ImageSlicePointPlacer( const Self& ); + Self& operator=( const Self& ); + + protected: + vtkImageSlice* ImageSlice; + vtkBoundedPlanePointPlacer* Placer; + double SavedBounds[ 6 ]; + double Bounds[ 6 ]; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__ImageSlicePointPlacer__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/ImageViewer.cxx b/lib/ivq/VTK/ImageViewer.cxx new file mode 100644 index 0000000..564f74c --- /dev/null +++ b/lib/ivq/VTK/ImageViewer.cxx @@ -0,0 +1,913 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +// ------------------------------------------------------------------------- +const double ivq::VTK::ImageViewer::CursorColors[ 3 ][ 3 ] = +{ + { 0, 0, 1 }, + { 0, 1, 0 }, + { 1, 0, 0 } +}; + +// ------------------------------------------------------------------------- +template< typename T > +void ivq_VTK_ImageViewer_MessageTemplate( + vtkImageData* img, int* pos, std::stringstream& msg + ) +{ + T* tuple = ( T* )( img->GetScalarPointer( pos ) ); + if( tuple != NULL ) + { + int n = img->GetNumberOfScalarComponents( ); + for( int c = 0; c < n; ++c ) + { + msg << long( tuple[ c ] ); + if( c != ( n - 1 ) ) + msg << ", "; + + } // rof + msg << " )"; + + } // fi +} + +// ------------------------------------------------------------------------- +namespace ivq +{ + namespace VTK + { + /** + */ + class ImageViewerCallback + : public vtkCommand + { + public: + static ImageViewerCallback* New( ) + { + return( new ImageViewerCallback( ) ); + } + virtual void Execute( + vtkObject* caller, unsigned long eId, void* data + ) override + { + if( this->Viewer == NULL ) + return; + + if( eId == vtkCommand::MouseMoveEvent ) + { + vtkRenderWindowInteractor* iren = this->Viewer->Interactor; + vtkRenderer* ren = this->Viewer->Renderer; + ivq::VTK::ImageActor* actor = this->Viewer->ImageActor; + vtkImageData* image = actor->GetInput( ); + vtkInteractorStyle* style = + vtkInteractorStyle::SafeDownCast( iren->GetInteractorStyle( ) ); + vtkPropPicker* picker = this->Viewer->PropPicker; + vtkCornerAnnotation* annotation = this->Viewer->CornerAnnotation; + vtkCursor3D* cursor = this->Viewer->CursorSource; + + // Pick + double pos[ 3 ]; + int ijk[ 3 ]; + bool validPick = + ( + picker->Pick( + iren->GetEventPosition( )[ 0 ], + iren->GetEventPosition( )[ 1 ], + 0.0, ren + ) != 0 + ); + if( validPick ) + { + picker->GetPickPosition( pos ); + vtkProp* pprop = + ivq::VTK::ImageActor::SafeDownCast( picker->GetViewProp( ) ); + validPick = ( pprop == actor ); + + } // fi + if( validPick ) + { + int ext[ 6 ]; + double pcoords[ 3 ]; + image->ComputeStructuredCoordinates( pos, ijk, pcoords ); + ijk[ this->Viewer->GetSliceOrientation( ) ] = + actor->GetSliceNumber( ); + image->GetExtent( ext ); + validPick = + ( ext[ 0 ] <= ijk[ 0 ] && ijk[ 0 ] <= ext[ 1 ] ) && + ( ext[ 2 ] <= ijk[ 1 ] && ijk[ 1 ] <= ext[ 3 ] ) && + ( ext[ 4 ] <= ijk[ 2 ] && ijk[ 2 ] <= ext[ 5 ] ); + + } // fi + + if( validPick ) + { + // Build message + std::stringstream message; + message + << std::fixed << std::setprecision( 2 ) + << "Point: [ " + << pos[ 0 ] << ", " << pos[ 1 ] << ", " << pos[ 2 ] + << " ]" << std::endl + << "Index: ( " + << ijk[ 0 ] << ", " << ijk[ 1 ] << ", " << ijk[ 2 ] + << " )" << std::endl + << "Value: ( "; + switch( image->GetScalarType( ) ) + { + vtkTemplateMacro( + ( + ivq_VTK_ImageViewer_MessageTemplate< VTK_TT >( + image, ijk, message + ) + ) + ); + default: + return; + } // hctiws + annotation->SetText( 2, message.str( ).c_str( ) ); + cursor->SetFocalPoint( pos ); + } + else + { + double bounds[ 6 ]; + actor->GetActorBounds( bounds ); + annotation->SetText( 2, "Off image" ); + cursor->SetFocalPoint( + bounds[ 0 ], bounds[ 2 ], bounds[ 4 ] + ); + + } // fi + std::stringstream wl; + wl + << "W/L : <" + << actor->GetProperty( )->GetColorWindow( ) << ", " + << actor->GetProperty( )->GetColorLevel( ) << ">"; + annotation->SetText( 3, wl.str( ).c_str( ) ); + iren->Render( ); + style->OnMouseMove( ); + + } // fi + } + + protected: + ImageViewerCallback( ) + : vtkCommand( ), + Viewer( NULL ) + { + } + virtual ~ImageViewerCallback( ) + { + } + + private: + // Purposely not implemented + ImageViewerCallback( const ImageViewerCallback& other ); + ImageViewerCallback& operator=( const ImageViewerCallback& other ); + + public: + ivq::VTK::ImageViewer* Viewer; + }; + + } // ecapseman + +} // ecapseman + +// ------------------------------------------------------------------------- +ivq::VTK::ImageViewer:: +Self* ivq::VTK::ImageViewer:: +New( ) +{ + return( new Self( ) ); +} + +// ------------------------------------------------------------------------- +vtkRenderWindow* ivq::VTK::ImageViewer:: +GetRenderWindow( ) +{ + return( this->RenderWindow ); +} + +// ------------------------------------------------------------------------- +vtkRenderer* ivq::VTK::ImageViewer:: +GetRenderer( ) +{ + return( this->Renderer ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageActor* ivq::VTK::ImageViewer:: +GetImageActor( ) +{ + return( this->ImageActor ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::InteractorStyleImage* ivq::VTK::ImageViewer:: +GetInteractorStyle( ) +{ + return( this->InteractorStyle ); +} + +// ------------------------------------------------------------------------- +const char* ivq::VTK::ImageViewer:: +GetWindowName( ) +{ + return( this->RenderWindow->GetWindowName( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +Render( ) +{ + if( this->FirstRender ) + { + vtkAlgorithm* input = this->_GetInputAlgorithm( ); + if( input != NULL ) + { + input->UpdateInformation( ); + int* w_ext = this->_GetInputInformation( )->Get( + vtkStreamingDemandDrivenPipeline::WHOLE_EXTENT( ) + ); + int xs = 0, ys = 0; + switch( this->SliceOrientation ) + { + case Self::SLICE_ORIENTATION_XY: + default: + { + xs = w_ext[ 1 ] - w_ext[ 0 ] + 1; + ys = w_ext[ 3 ] - w_ext[ 2 ] + 1; + } + break; + case Self::SLICE_ORIENTATION_XZ: + { + xs = w_ext[ 1 ] - w_ext[ 0 ] + 1; + ys = w_ext[ 5 ] - w_ext[ 4 ] + 1; + } + break; + case Self::SLICE_ORIENTATION_YZ: + { + xs = w_ext[ 3 ] - w_ext[ 2 ] + 1; + ys = w_ext[ 5 ] - w_ext[ 4 ] + 1; + } + break; + } // hctiws + + if( this->RenderWindow->GetSize( )[ 0 ] == 0 ) + this->RenderWindow->SetSize( + ( xs < 150 )? 150: xs, + ( ys < 100 )? 100: ys + ); + + if( this->Renderer ) + { + this->Renderer->ResetCamera( ); + this->Renderer->GetActiveCamera( )->SetParallelScale( + ( xs < 150 )? 75: ( ( xs - 1 ) / 2.0 ) + ); + + } // fi + this->FirstRender = 0; + + } // fi + + } // fi + + if( this->GetInput( ) != NULL ) + this->RenderWindow->Render( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetInputData( vtkImageData* in ) +{ + this->ImageActor = vtkSmartPointer< ivq::VTK::ImageActor >::New( ); + this->_UnInstallPipeline( ); + this->_InstallPipeline( ); + this->SetupInteractor( ); + this->ImageActor->SetInputData( in ); + this->UpdateDisplayExtent( ); +} + +// ------------------------------------------------------------------------- +vtkImageData* ivq::VTK::ImageViewer:: +GetInput( ) +{ + return( vtkImageData::SafeDownCast( this->ImageActor->GetInput( ) ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetInputConnection( vtkAlgorithmOutput* input ) +{ + this->ImageActor = vtkSmartPointer< ivq::VTK::ImageActor >::New( ); + this->_UnInstallPipeline( ); + this->_InstallPipeline( ); + this->SetupInteractor( ); + this->ImageActor->SetInputConnection( input ); + this->UpdateDisplayExtent( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetSliceOrientation( int orientation ) +{ + if( + orientation < Self::SLICE_ORIENTATION_YZ || + orientation > Self::SLICE_ORIENTATION_XY + ) + { + vtkErrorMacro( "Error - invalid slice orientation " << orientation ); + return; + + } // fi + if( this->SliceOrientation == orientation ) + return; + this->SliceOrientation = orientation; + this->ImageActor->SetOrientation( this->SliceOrientation ); + this->FirstRender = 1; + + // Update the viewer + int* range = this->GetSliceRange( ); + if( range != NULL ) + this->Slice = static_cast< int >( ( range[ 0 ] + range[ 1 ] ) * 0.5 ); + this->_UpdateOrientation( ); + this->UpdateDisplayExtent( ); + if( this->Renderer != NULL && this->GetInput( ) != NULL ) + { + double scale = this->Renderer->GetActiveCamera( )->GetParallelScale( ); + this->Renderer->ResetCamera( ); + this->Renderer->GetActiveCamera( )->SetParallelScale( scale ); + + } // fi + this->Render( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetSliceOrientationToXY( ) +{ + this->SetSliceOrientation( ImageViewer::SLICE_ORIENTATION_XY ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetSliceOrientationToYZ( ) +{ + this->SetSliceOrientation( ImageViewer::SLICE_ORIENTATION_YZ ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetSliceOrientationToXZ( ) +{ + this->SetSliceOrientation( ImageViewer::SLICE_ORIENTATION_XZ ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetSlice( int s ) +{ + int* range = this->GetSliceRange( ); + if( range != NULL ) + { + if( s < range[ 0 ] ) + s = range[ 0 ]; + else if( s > range[ 1 ] ) + s = range[ 1 ]; + + } // fi + if( this->Slice == s ) + return; + this->Slice = s; + this->ImageActor->SetSliceNumber( this->Slice ); + this->ImageActor->Update( ); + double bounds[ 6 ], center[ 3 ], focus[ 3 ]; + this->ImageActor->GetActorBounds( bounds ); + this->ImageActor->GetActorCenter( center ); + this->CursorSource->GetFocalPoint( focus ); + focus[ this->SliceOrientation ] = center[ this->SliceOrientation ]; + this->CursorSource->SetModelBounds( bounds ); + this->CursorSource->SetFocalPoint( focus ); + this->CursorActor->Modified( ); + this->Render( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +UpdateDisplayExtent( ) +{ + vtkAlgorithm* input = this->_GetInputAlgorithm( ); + if( !input || !this->ImageActor ) + return; + input->UpdateInformation( ); + vtkInformation* outInfo = input->GetOutputInformation( 0 ); + + int* slice_range = this->GetSliceRange( ); + this->Slice = ( slice_range[ 0 ] + slice_range[ 1 ] ) >> 1; + this->ImageActor->SetSliceNumber( this->Slice ); + + // Reset window level + vtkImageData* image = this->ImageActor->GetInput( ); + double range[ 2 ]; + image->GetScalarRange( range ); + double color_window = range[ 1 ] - range[ 0 ]; + double color_level = ( range[ 1 ] + range[ 0 ] ) * 0.5; + this->ImageActor->GetProperty( )->SetColorWindow( color_window ); + this->ImageActor->GetProperty( )->SetColorLevel( color_level ); + + // Figure out the correct clipping range + if( this->Renderer != NULL ) + { + this->Renderer->RemoveAllViewProps( ); + this->Renderer->AddViewProp( this->ImageActor ); + if( + this->InteractorStyle == NULL || + !( this->InteractorStyle->GetAutoAdjustCameraClippingRange( ) ) + ) + { + vtkCamera* cam = this->Renderer->GetActiveCamera( ); + if( cam ) + { + double bounds[ 6 ]; + this->ImageActor->GetActorBounds( bounds ); + double spos = bounds[ this->SliceOrientation << 1 ]; + double cpos = cam->GetPosition( )[ this->SliceOrientation ]; + double range = std::fabs( spos - cpos ); + double* spacing = outInfo->Get( vtkDataObject::SPACING( ) ); + double avg_spacing = spacing[ 0 ] + spacing[ 1 ] + spacing[ 2 ]; + cam->SetClippingRange( range - avg_spacing, range + avg_spacing ); + + } // fi + } + else + this->Renderer->ResetCameraClippingRange( ); + + // Prepare picker + this->PropPicker = vtkSmartPointer< vtkPropPicker >::New( ); + this->PropPicker->PickFromListOn( ); + this->PropPicker->AddPickList( this->ImageActor ); + + // Cursor + this->CursorSource = vtkSmartPointer< vtkCursor3D >::New( ); + this->CursorActor = vtkSmartPointer< ivq::VTK::PolyDataActor >::New( ); + + double bounds[ 6 ], center[ 3 ]; + this->ImageActor->GetActorBounds( bounds ); + this->ImageActor->GetActorCenter( center ); + + this->CursorSource->SetModelBounds( bounds ); + this->CursorSource->SetFocalPoint( center ); + this->CursorSource->AllOn( ); + this->CursorActor-> + SetInputConnection( this->CursorSource->GetOutputPort( ) ); + this->CursorActor->GetProperty( )->SetColor( + Self::CursorColors[ this->SliceOrientation ][ 0 ], + Self::CursorColors[ this->SliceOrientation ][ 1 ], + Self::CursorColors[ this->SliceOrientation ][ 2 ] + ); + this->Renderer->AddViewProp( this->CursorActor->GetActor( ) ); + + // Annotations + this->CornerAnnotation = vtkSmartPointer< vtkCornerAnnotation >::New( ); + this->CornerAnnotation->SetLinearFontScaleFactor( 2 ); + this->CornerAnnotation->SetNonlinearFontScaleFactor( 1 ); + this->CornerAnnotation->SetMaximumFontSize( 20 ); + this->CornerAnnotation->SetText( 2, "Off image" ); + std::stringstream wl; + wl + << "W/L : <" + << this->ImageActor->GetProperty( )->GetColorWindow( ) << ", " + << this->ImageActor->GetProperty( )->GetColorLevel( ) << ">"; + this->CornerAnnotation->SetText( 3, wl.str( ).c_str( ) ); + this->CornerAnnotation->GetTextProperty( )->SetColor( 1, 1, 0 ); + this->CornerAnnotation->GetTextProperty( )->SetFontFamilyToCourier( ); + this->CornerAnnotation->GetTextProperty( )->BoldOn( ); + this->Renderer->AddViewProp( this->CornerAnnotation ); + + } // fi +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageViewer:: +GetSliceMin( ) +{ + int* range = this->GetSliceRange( ); + if( range != NULL ) + return( range[ 0 ] ); + else + return( 0 ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageViewer:: +GetSliceMax( ) +{ + int* range = this->GetSliceRange( ); + if( range != NULL ) + return( range[ 1 ] ); + else + return( 0 ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +GetSliceRange( int range[ 2 ] ) +{ + this->GetSliceRange( range[ 0 ], range[ 1 ] ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +GetSliceRange( int& min, int& max ) +{ + vtkAlgorithm* input = this->_GetInputAlgorithm( ); + if( input != NULL ) + { + input->UpdateInformation( ); + int* w_ext = input->GetOutputInformation( 0 )->Get( + vtkStreamingDemandDrivenPipeline::WHOLE_EXTENT( ) + ); + min = w_ext[ this->SliceOrientation << 1 ]; + max = w_ext[ ( this->SliceOrientation << 1 ) + 1 ]; + + } // fi +} + +// ------------------------------------------------------------------------- +int* ivq::VTK::ImageViewer:: +GetSliceRange( ) +{ + vtkAlgorithm *input = this->_GetInputAlgorithm( ); + if( input != NULL ) + { + input->UpdateInformation( ); + return( + input->GetOutputInformation( 0 )->Get( + vtkStreamingDemandDrivenPipeline::WHOLE_EXTENT( ) + ) + this->SliceOrientation * 2 + ); + } + else + return( NULL ); +} + +// ------------------------------------------------------------------------- +double ivq::VTK::ImageViewer:: +GetColorWindow( ) +{ + return( this->ImageActor->GetProperty( )->GetColorWindow( ) ); +} + +// ------------------------------------------------------------------------- +double ivq::VTK::ImageViewer:: +GetColorLevel( ) +{ + return( this->ImageActor->GetProperty( )->GetColorLevel( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetColorWindow( double s ) +{ + this->ImageActor->GetProperty( )->SetColorWindow( s ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetColorLevel( double s ) +{ + this->ImageActor->GetProperty( )->SetColorLevel( s ); + this->Modified( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetDisplayId( void* a ) +{ + this->RenderWindow->SetDisplayId( a ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetWindowId( void* a ) +{ + this->RenderWindow->SetWindowId( a ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetParentId( void* a ) +{ + this->RenderWindow->SetParentId( a ); +} + +// ------------------------------------------------------------------------- +int* ivq::VTK::ImageViewer:: +GetPosition( ) +{ + return( this->RenderWindow->GetPosition( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetPosition( int a, int b ) +{ + this->RenderWindow->SetPosition( a, b ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetPosition( int a[ 2 ] ) +{ + this->SetPosition( a[ 0 ], a[ 1 ] ); +} + +// ------------------------------------------------------------------------- +int* ivq::VTK::ImageViewer:: +GetSize( ) +{ + return( this->RenderWindow->GetSize( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetSize( int a, int b ) +{ + this->RenderWindow->SetSize( a, b ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetSize( int a[ 2 ] ) +{ + this->SetSize( a[ 0 ], a[ 1 ] ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetRenderWindow( vtkRenderWindow* win ) +{ + if( this->RenderWindow == win ) + return; + this->_UnInstallPipeline( ); + if( this->RenderWindow != NULL ) + this->RenderWindow->UnRegister( this ); + this->RenderWindow = win; + if( this->RenderWindow != NULL ) + this->RenderWindow->Register( this ); + this->_InstallPipeline( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetRenderer( vtkRenderer* ren ) +{ + if( this->Renderer == ren ) + return; + this->_UnInstallPipeline( ); + if( this->Renderer != NULL ) + this->Renderer->UnRegister( this ); + this->Renderer = ren; + if( this->Renderer ) + this->Renderer->Register( this ); + this->_InstallPipeline( ); + this->_UpdateOrientation( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetupInteractor( ) +{ + if( this->Interactor == NULL ) + { + vtkRenderWindowInteractor* rwi = this->RenderWindow->GetInteractor( ); + if( rwi == NULL ) + { + rwi = vtkRenderWindowInteractor::New( ); + this->SetupInteractor( rwi ); + rwi->Delete( ); + } + else + this->SetupInteractor( rwi ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetupInteractor( vtkRenderWindowInteractor* rwi ) +{ + if( this->Interactor == rwi ) + return; + this->_UnInstallPipeline( ); + if( this->Interactor != NULL ) + this->Interactor->UnRegister( this ); + this->Interactor = rwi; + if( this->Interactor != NULL ) + this->Interactor->Register( this ); + this->_InstallPipeline( ); + if( this->Renderer != NULL ) + this->Renderer->GetActiveCamera( )->ParallelProjectionOn( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +SetOffScreenRendering( int v ) +{ + this->RenderWindow->SetOffScreenRendering( v ); +} + +// ------------------------------------------------------------------------- +int ivq::VTK::ImageViewer:: +GetOffScreenRendering( ) +{ + return( this->RenderWindow->GetOffScreenRendering( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +ResetCamera( ) +{ + if( this->Renderer != NULL ) + this->Renderer->ResetCamera( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +Initialize( ) +{ + if( this->Interactor != NULL ) + this->Interactor->Initialize( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +Start( ) +{ + if( this->Interactor != NULL ) + this->Interactor->Start( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +GetFocalPoint( double point[ 3 ], int ijk[ 3 ] ) +{ + this->CursorSource->GetFocalPoint( point ); + + double pcoords[ 3 ]; + vtkImageData* image = this->GetInput( ); + image->ComputeStructuredCoordinates( point, ijk, pcoords ); + ijk[ this->SliceOrientation ] = this->ImageActor->GetSliceNumber( ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageViewer:: +ImageViewer( ) + : Superclass( ) +{ + this->Slice = 0; + this->FirstRender = 1; + this->SliceOrientation = Self::SLICE_ORIENTATION_XY; + + // Setup the pipeline + vtkRenderWindow* renwin = vtkRenderWindow::New( ); + this->SetRenderWindow( renwin ); + renwin->Delete( ); + + vtkRenderer* ren = vtkRenderer::New( ); + this->SetRenderer( ren ); + ren->Delete( ); + + this->_InstallPipeline( ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageViewer:: +~ImageViewer( ) +{ +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +_InstallPipeline( ) +{ + if( this->RenderWindow != NULL && this->Renderer != NULL ) + this->RenderWindow->AddRenderer( this->Renderer ); + if( this->Interactor != NULL ) + { + if( this->InteractorStyle == NULL ) + { + this->InteractorStyle = + vtkSmartPointer< ivq::VTK::InteractorStyleImage >::New( ); + this->InteractorStyle->SetViewer( this ); + ImageViewerCallback* cbk = ImageViewerCallback::New( ); + cbk->Viewer = this; + this->InteractorStyle->AddObserver( vtkCommand::MouseMoveEvent, cbk ); + cbk->Delete( ); + + } // fi + this->Interactor->SetInteractorStyle( this->InteractorStyle ); + this->Interactor->SetRenderWindow( this->RenderWindow ); + + } // fi + if( this->Renderer != NULL && this->ImageActor != NULL ) + this->Renderer->AddViewProp( this->ImageActor ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +_UnInstallPipeline( ) +{ + if( this->ImageActor != NULL ) + this->ImageActor->SetInputConnection( NULL ); + if( this->Renderer != NULL && this->ImageActor != NULL ) + this->Renderer->RemoveViewProp( this->ImageActor ); + if( this->RenderWindow != NULL && this->Renderer != NULL ) + this->RenderWindow->RemoveRenderer( this->Renderer ); + + if( this->Interactor != NULL ) + { + this->Interactor->SetInteractorStyle( NULL ); + this->Interactor->SetRenderWindow( NULL ); + } +} + +// ------------------------------------------------------------------------- +void ivq::VTK::ImageViewer:: +_UpdateOrientation( ) +{ + if( this->Renderer == NULL ) + return; + vtkCamera* cam = this->Renderer->GetActiveCamera( ); + if( cam == NULL ) + return; + switch( this->SliceOrientation ) + { + case Self::SLICE_ORIENTATION_XY: + { + cam->SetFocalPoint( 0, 0, 0 ); + cam->SetPosition( 0, 0, 1 ); // -1 if medical ? + cam->SetViewUp( 0, 1, 0 ); + } + break; + case Self::SLICE_ORIENTATION_XZ: + { + cam->SetFocalPoint( 0, 0, 0 ); + cam->SetPosition( 0, -1, 0 ); // 1 if medical ? + cam->SetViewUp( 0, 0, 1 ); + } + break; + case Self::SLICE_ORIENTATION_YZ: + { + cam->SetFocalPoint( 0, 0, 0 ); + cam->SetPosition( 1, 0, 0 ); // -1 if medical ? + cam->SetViewUp( 0, 0, 1 ); + } + break; + } // hctiws +} + +// ------------------------------------------------------------------------- +vtkAlgorithm* ivq::VTK::ImageViewer:: +_GetInputAlgorithm( ) +{ + return( this->ImageActor->GetInputAlgorithm( ) ); +} + +// ------------------------------------------------------------------------- +vtkInformation* ivq::VTK::ImageViewer:: +_GetInputInformation( ) +{ + return( this->ImageActor->GetInputInformation( ) ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/ImageViewer.h b/lib/ivq/VTK/ImageViewer.h new file mode 100644 index 0000000..cd6c33f --- /dev/null +++ b/lib/ivq/VTK/ImageViewer.h @@ -0,0 +1,160 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__ImageViewer__h__ +#define __ivq__VTK__ImageViewer__h__ + +#include + +#include +#include + +class vtkAlgorithm; +class vtkAlgorithmOutput; +class vtkCornerAnnotation; +class vtkCursor3D; +class vtkImageData; +class vtkInformation; +class vtkPropPicker; +class vtkRenderer; +class vtkRenderWindow; +class vtkRenderWindowInteractor; + +namespace ivq +{ + namespace VTK + { + class ImageActor; + class InteractorStyleImage; + class PolyDataActor; + + /** + */ + class IVQ_EXPORT ImageViewer + : public vtkObject + { + public: + typedef ImageViewer Self; + + public: + vtkTypeMacro( ImageViewer, vtkObject ); + + vtkGetMacro( SliceOrientation, int ); + vtkGetMacro( Slice, int ); + vtkBooleanMacro( OffScreenRendering, int ); + + public: + static Self* New( ); + + virtual vtkRenderWindow* GetRenderWindow( ); + virtual vtkRenderer* GetRenderer( ); + virtual ivq::VTK::ImageActor* GetImageActor( ); + virtual ivq::VTK::InteractorStyleImage* GetInteractorStyle( ); + + virtual const char* GetWindowName( ); + virtual void Render( ); + + virtual void SetInputData( vtkImageData* in ); + virtual vtkImageData* GetInput( ); + virtual void SetInputConnection( vtkAlgorithmOutput* input ); + + enum + { + SLICE_ORIENTATION_YZ = 0, + SLICE_ORIENTATION_XZ = 1, + SLICE_ORIENTATION_XY = 2 + }; + virtual void SetSliceOrientation( int orientation ); + virtual void SetSliceOrientationToXY( ); + virtual void SetSliceOrientationToYZ( ); + virtual void SetSliceOrientationToXZ( ); + + virtual void SetSlice( int s ); + + virtual void UpdateDisplayExtent( ); + + virtual int GetSliceMin( ); + virtual int GetSliceMax( ); + virtual void GetSliceRange( int range[ 2 ] ); + virtual void GetSliceRange( int& min, int& max ); + virtual int* GetSliceRange( ); + + virtual double GetColorWindow( ); + virtual double GetColorLevel( ); + virtual void SetColorWindow( double s ); + virtual void SetColorLevel( double s ); + + virtual void SetDisplayId( void* a ); + virtual void SetWindowId( void* a ); + virtual void SetParentId( void* a ); + + virtual int* GetPosition( ); + virtual void SetPosition( int a, int b ); + virtual void SetPosition( int a[ 2 ] ); + + virtual int* GetSize( ); + virtual void SetSize( int a, int b ); + virtual void SetSize( int a[ 2 ] ); + + virtual void SetRenderWindow( vtkRenderWindow* win ); + virtual void SetRenderer( vtkRenderer* ren ); + virtual void SetupInteractor( ); + virtual void SetupInteractor( vtkRenderWindowInteractor* rwi ); + + virtual void SetOffScreenRendering( int v ); + virtual int GetOffScreenRendering( ); + + virtual void ResetCamera( ); + virtual void Initialize( ); + virtual void Start( ); + + virtual void GetFocalPoint( double point[ 3 ], int ijk[ 3 ] ); + + protected: + ImageViewer( ); + virtual ~ImageViewer( ); + + virtual void _InstallPipeline( ); + virtual void _UnInstallPipeline( ); + virtual void _UpdateOrientation( ); + + vtkAlgorithm* _GetInputAlgorithm( ); + vtkInformation* _GetInputInformation( ); + + private: + // Purposely not implemented. + ImageViewer( const ImageViewer& other ); + void operator=( const ImageViewer& other ); + + protected: + vtkSmartPointer< vtkRenderWindow > RenderWindow; + vtkSmartPointer< vtkRenderer > Renderer; + vtkSmartPointer< ivq::VTK::ImageActor > ImageActor; + vtkSmartPointer< vtkRenderWindowInteractor > Interactor; + vtkSmartPointer< ivq::VTK::InteractorStyleImage > InteractorStyle; + + int SliceOrientation; + int FirstRender; + int Slice; + + vtkSmartPointer< vtkPropPicker > PropPicker; + vtkSmartPointer< vtkCornerAnnotation > CornerAnnotation; + + vtkSmartPointer< vtkCursor3D > CursorSource; + vtkSmartPointer< ivq::VTK::PolyDataActor > CursorActor; + + static const double CursorColors[ 3 ][ 3 ]; + + friend class ImageViewerCallback; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__ImageViewer__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/InteractorStyleImage.cxx b/lib/ivq/VTK/InteractorStyleImage.cxx new file mode 100644 index 0000000..4239bc5 --- /dev/null +++ b/lib/ivq/VTK/InteractorStyleImage.cxx @@ -0,0 +1,275 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include +#include +#include +#include +#include + +#include +#include + +// ------------------------------------------------------------------------- +ivq::VTK::InteractorStyleImage:: +Self* ivq::VTK::InteractorStyleImage:: +New( ) +{ + return( new Self( ) ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageViewer* ivq::VTK::InteractorStyleImage:: +GetViewer( ) +{ + return( this->Viewer ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +SetViewer( ivq::VTK::ImageViewer* v ) +{ + this->Viewer = v; + this->Modified( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +AddOtherViewer( ivq::VTK::ImageViewer* v ) +{ + if( this->Viewer != NULL ) + this->OtherViewers.insert( v ); + else + this->Viewer = v; + this->Modified( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnMouseMove( ) +{ + if( this->PressedButton == 1 && this->Viewer != NULL ) + { + if( + !this->Interactor->GetAltKey( ) && + !this->Interactor->GetShiftKey( ) && + !this->Interactor->GetControlKey( ) + ) + { + double dx = double( this->Interactor->GetEventPosition( )[ 0 ] ); + double dy = double( this->Interactor->GetEventPosition( )[ 1 ] ); + dx -= this->StartClick[ 0 ]; + dy -= this->StartClick[ 1 ]; + double sx = double( this->Interactor->GetSize( )[ 0 ] >> 1 ); + double sy = double( this->Interactor->GetSize( )[ 1 ] >> 1 ); + dx /= sx; + dy /= sy; + double off = double( 1 ); + double w = this->StartWL[ 0 ] * ( off + dx ); + double l = this->StartWL[ 1 ] * ( off + dy ); + this->Viewer->GetImageActor( )->SetColorWindow( w ); + this->Viewer->GetImageActor( )->SetColorLevel( l ); + this->Interactor->Render( ); + + std::set< ivq::VTK::ImageViewer* >::iterator vIt = + this->OtherViewers.begin( ); + for( ; vIt != this->OtherViewers.end( ); ++vIt ) + { + ivq::VTK::ImageViewer* v = *vIt; + v->GetImageActor( )->SetColorWindow( w ); + v->GetImageActor( )->SetColorLevel( l ); + v->Render( ); + + } // rof + } + else if( + !this->Interactor->GetAltKey( ) && + !this->Interactor->GetShiftKey( ) && + this->Interactor->GetControlKey( ) + ) + { + double pos[ 3 ]; + int ijk[ 3 ]; + this->Viewer->GetFocalPoint( pos, ijk ); + std::set< ivq::VTK::ImageViewer* >::iterator vIt = + this->OtherViewers.begin( ); + for( ; vIt != this->OtherViewers.end( ); ++vIt ) + { + ivq::VTK::ImageViewer* v = *vIt; + v->SetSlice( ijk[ v->GetSliceOrientation( ) ] ); + v->Render( ); + + } // rof + + } // fi + + } // fi + this->vtkInteractorStyleTrackballCamera::OnMouseMove( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnLeftButtonDown( ) +{ + if( this->Viewer != NULL ) + { + this->StartClick[ 0 ] = this->Interactor->GetEventPosition( )[ 0 ]; + this->StartClick[ 1 ] = this->Interactor->GetEventPosition( )[ 1 ]; + this->StartWL[ 0 ] = this->Viewer->GetImageActor( )->GetColorWindow( ); + this->StartWL[ 1 ] = this->Viewer->GetImageActor( )->GetColorLevel( ); + this->PressedButton = 1; + + } // fi + this->vtkInteractorStyleTrackballCamera::OnLeftButtonDown( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnLeftButtonUp( ) +{ + if( this->Viewer != NULL ) + this->PressedButton = 0; + this->vtkInteractorStyleTrackballCamera::OnLeftButtonUp( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnMiddleButtonDown( ) +{ + if( this->Viewer != NULL ) + { + this->StartClick[ 0 ] = this->Interactor->GetEventPosition( )[ 0 ]; + this->StartClick[ 1 ] = this->Interactor->GetEventPosition( )[ 1 ]; + this->PressedButton = 2; + + } // fi + this->vtkInteractorStyleTrackballCamera::OnMiddleButtonDown( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnMiddleButtonUp( ) +{ + if( this->Viewer != NULL ) + this->PressedButton = 0; + this->vtkInteractorStyleTrackballCamera::OnMiddleButtonUp( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnRightButtonDown( ) +{ + if( this->Viewer != NULL ) + { + this->StartClick[ 0 ] = this->Interactor->GetEventPosition( )[ 0 ]; + this->StartClick[ 1 ] = this->Interactor->GetEventPosition( )[ 1 ]; + this->PressedButton = 3; + + } // fi + this->vtkInteractorStyleTrackballCamera::OnRightButtonDown( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnRightButtonUp( ) +{ + if( this->Viewer != NULL ) + this->PressedButton = 0; + this->vtkInteractorStyleTrackballCamera::OnRightButtonUp( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnMouseWheelForward( ) +{ + if( this->Viewer != NULL ) + { + int off = ( this->Interactor->GetShiftKey( ) )? 10: 1; + int s = this->Viewer->GetSlice( ); + this->Viewer->SetSlice( s + off ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnMouseWheelBackward( ) +{ + if( this->Viewer != NULL ) + { + int off = ( this->Interactor->GetShiftKey( ) )? 10: 1; + int s = this->Viewer->GetSlice( ); + this->Viewer->SetSlice( s - off ); + + } // fi +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +OnChar( ) +{ + if( this->Viewer == NULL ) + return; + switch( this->Interactor->GetKeyCode( ) ) + { + case 'r': case 'R': + { + this->CurrentRenderer->ResetCamera( ); + this->Interactor->Render( ); + } + break; + case 'v': case 'V': + { + this->Viewer->GetImageActor( )->ResetWindowLevel( ); + this->Interactor->Render( ); + std::set< ivq::VTK::ImageViewer* >::iterator vIt = + this->OtherViewers.begin( ); + for( ; vIt != this->OtherViewers.end( ); ++vIt ) + { + ivq::VTK::ImageViewer* v = *vIt; + v->GetImageActor( )->ResetWindowLevel( ); + v->Render( ); + + } // rof + } + break; + default: + break; + + } // hctiws +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +Rotate( ) +{ +} + +// ------------------------------------------------------------------------- +void ivq::VTK::InteractorStyleImage:: +Spin( ) +{ +} + +// ------------------------------------------------------------------------- +ivq::VTK::InteractorStyleImage:: +InteractorStyleImage( ) + : Superclass( ), + Viewer( NULL ), + PressedButton( 0 ) +{ + this->SetInteractionModeToImage2D( ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::InteractorStyleImage:: +~InteractorStyleImage( ) +{ +} + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/InteractorStyleImage.h b/lib/ivq/VTK/InteractorStyleImage.h new file mode 100644 index 0000000..af83511 --- /dev/null +++ b/lib/ivq/VTK/InteractorStyleImage.h @@ -0,0 +1,76 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__InteractorStyleImage__h__ +#define __ivq__VTK__InteractorStyleImage__h__ + +#include + +#include +#include + +namespace ivq +{ + namespace VTK + { + class ImageViewer; + + /** + */ + class IVQ_EXPORT InteractorStyleImage + : public vtkInteractorStyleImage + { + public: + typedef InteractorStyleImage Self; + + public: + vtkTypeMacro( InteractorStyleImage, vtkInteractorStyleImage ); + + public: + static Self* New( ); + + ivq::VTK::ImageViewer* GetViewer( ); + void SetViewer( ivq::VTK::ImageViewer* v ); + void AddOtherViewer( ivq::VTK::ImageViewer* v ); + + virtual void OnMouseMove( ) override; + virtual void OnLeftButtonDown( ) override; + virtual void OnLeftButtonUp( ) override; + virtual void OnMiddleButtonDown( ) override; + virtual void OnMiddleButtonUp( ) override; + virtual void OnRightButtonDown( ) override; + virtual void OnRightButtonUp( ) override; + virtual void OnMouseWheelForward( ) override; + virtual void OnMouseWheelBackward( ) override; + virtual void OnChar( ) override; + + virtual void Rotate( ) override; + virtual void Spin( ) override; + + protected: + InteractorStyleImage( ); + virtual ~InteractorStyleImage( ); + + private: + // Purposely not implemented. + InteractorStyleImage( const InteractorStyleImage& other ); + void operator=( const InteractorStyleImage& other ); + + protected: + ivq::VTK::ImageViewer* Viewer; + std::set< ivq::VTK::ImageViewer* > OtherViewers; + double StartClick[ 2 ]; + double StartWL[ 2 ]; + unsigned char PressedButton; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__InteractorStyleImage__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/MPRViewers.cxx b/lib/ivq/VTK/MPRViewers.cxx new file mode 100644 index 0000000..8a15026 --- /dev/null +++ b/lib/ivq/VTK/MPRViewers.cxx @@ -0,0 +1,197 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include +#include + +// ------------------------------------------------------------------------- +ivq::VTK::MPRViewers:: +Self* ivq::VTK::MPRViewers:: +New( ) +{ + return( new Self( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +Render( ) +{ + for( unsigned int i = 0; i < 3; ++i ) + if( this->Viewers[ i ].GetPointer( ) != NULL ) + this->Viewers[ i ]->Render( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +SetInputData( vtkImageData* in ) +{ + bool need_to_configure = false; + for( unsigned int i = 0; i < 3; ++i ) + need_to_configure |= ( this->Viewers[ i ].GetPointer( ) == NULL ); + if( need_to_configure ) + this->_ConfigureViews( ); + for( unsigned int i = 0; i < 3; ++i ) + { + this->Viewers[ i ]->SetInputData( in ); + this->Viewers[ i ]->SetSliceOrientation( i ); + + } // rof + for( unsigned int i = 0; i < 3; ++i ) + for( unsigned int j = 0; j < 3; ++j ) + if( i != j ) + this->Viewers[ i ]->GetInteractorStyle( )-> + AddOtherViewer( this->Viewers[ j ] ); +} + +// ------------------------------------------------------------------------- +vtkImageData* ivq::VTK::MPRViewers:: +GetInput( ) +{ + if( this->Viewers[ 0 ].GetPointer( ) != NULL ) + return( this->Viewers[ 0 ]->GetInput( ) ); + else + return( NULL ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +SetInputConnection( vtkAlgorithmOutput* input ) +{ + bool need_to_configure = false; + for( unsigned int i = 0; i < 3; ++i ) + need_to_configure |= ( this->Viewers[ i ].GetPointer( ) == NULL ); + if( need_to_configure ) + this->_ConfigureViews( ); + for( unsigned int i = 0; i < 3; ++i ) + { + this->Viewers[ i ]->SetInputConnection( input ); + this->Viewers[ i ]->SetSliceOrientation( i ); + + } // rof + for( unsigned int i = 0; i < 3; ++i ) + for( unsigned int j = 0; j < 3; ++j ) + if( i != j ) + this->Viewers[ i ]->GetInteractorStyle( )-> + AddOtherViewer( this->Viewers[ j ] ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageViewer* ivq::VTK::MPRViewers:: +GetView( int o ) +{ + if( o < 3 ) + return( this->Viewers[ o ].GetPointer( ) ); + else + return( NULL ); +} + +// ------------------------------------------------------------------------- +const ivq::VTK::ImageViewer* ivq::VTK::MPRViewers:: +GetView( int o ) const +{ + if( o < 3 ) + return( this->Viewers[ o ].GetPointer( ) ); + else + return( NULL ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +SetView( int o, ivq::VTK::ImageViewer* v ) +{ + if( o < 3 ) + this->Viewers[ o ] = v; +} + +// ------------------------------------------------------------------------- +double ivq::VTK::MPRViewers:: +GetColorWindow( ) +{ + if( this->Viewers[ 0 ].GetPointer( ) != NULL ) + return( this->Viewers[ 0 ]->GetColorWindow( ) ); + else + return( 0 ); +} + +// ------------------------------------------------------------------------- +double ivq::VTK::MPRViewers:: +GetColorLevel( ) +{ + if( this->Viewers[ 0 ].GetPointer( ) != NULL ) + return( this->Viewers[ 0 ]->GetColorLevel( ) ); + else + return( 0 ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +SetColorWindow( double s ) +{ + for( unsigned int i = 0; i < 3; ++i ) + if( this->Viewers[ i ].GetPointer( ) != NULL ) + this->Viewers[ i ]->SetColorWindow( s ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +SetColorLevel( double s ) +{ + for( unsigned int i = 0; i < 3; ++i ) + if( this->Viewers[ i ].GetPointer( ) != NULL ) + this->Viewers[ i ]->SetColorLevel( s ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +ResetCameras( ) +{ + for( unsigned int i = 0; i < 3; ++i ) + if( this->Viewers[ i ].GetPointer( ) != NULL ) + this->Viewers[ i ]->ResetCamera( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +Initialize( ) +{ + for( unsigned int i = 0; i < 3; ++i ) + if( this->Viewers[ i ].GetPointer( ) != NULL ) + this->Viewers[ i ]->Initialize( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +Start( ) +{ + for( unsigned int i = 0; i < 3; ++i ) + if( this->Viewers[ i ].GetPointer( ) != NULL ) + this->Viewers[ i ]->Start( ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::MPRViewers:: +MPRViewers( ) + : Superclass( ) +{ +} + +// ------------------------------------------------------------------------- +ivq::VTK::MPRViewers:: +~MPRViewers( ) +{ +} + +// ------------------------------------------------------------------------- +void ivq::VTK::MPRViewers:: +_ConfigureViews( ) +{ + for( unsigned int i = 0; i < 3; ++i ) + this->Viewers[ i ] = vtkSmartPointer< ivq::VTK::ImageViewer >::New( ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/MPRViewers.h b/lib/ivq/VTK/MPRViewers.h new file mode 100644 index 0000000..b259b23 --- /dev/null +++ b/lib/ivq/VTK/MPRViewers.h @@ -0,0 +1,78 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__MPRViewers__h__ +#define __ivq__VTK__MPRViewers__h__ + +#include + +#include +#include + +class vtkAlgorithmOutput; +class vtkImageData; + +namespace ivq +{ + namespace VTK + { + class ImageViewer; + + /** + */ + class IVQ_EXPORT MPRViewers + : public vtkObject + { + public: + typedef MPRViewers Self; + + public: + vtkTypeMacro( MPRViewers, vtkObject ); + + public: + static Self* New( ); + + virtual void Render( ); + + virtual void SetInputData( vtkImageData* in ); + virtual vtkImageData* GetInput( ); + virtual void SetInputConnection( vtkAlgorithmOutput* input ); + + ivq::VTK::ImageViewer* GetView( int o ); + const ivq::VTK::ImageViewer* GetView( int o ) const; + void SetView( int o, ivq::VTK::ImageViewer* v ); + + virtual double GetColorWindow( ); + virtual double GetColorLevel( ); + virtual void SetColorWindow( double s ); + virtual void SetColorLevel( double s ); + + virtual void ResetCameras( ); + virtual void Initialize( ); + virtual void Start( ); + + protected: + MPRViewers( ); + virtual ~MPRViewers( ); + + void _ConfigureViews( ); + + private: + // Purposely not implemented. + MPRViewers( const MPRViewers& other ); + void operator=( const MPRViewers& other ); + + protected: + vtkSmartPointer< ivq::VTK::ImageViewer > Viewers[ 3 ]; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__MPRViewers__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/PolyDataActor.cxx b/lib/ivq/VTK/PolyDataActor.cxx new file mode 100644 index 0000000..50022be --- /dev/null +++ b/lib/ivq/VTK/PolyDataActor.cxx @@ -0,0 +1,129 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include +#include + +// ------------------------------------------------------------------------- +ivq::VTK::PolyDataActor:: +Self* ivq::VTK::PolyDataActor:: +New( ) +{ + return( new Self( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::PolyDataActor:: +Modified( ) +{ + this->Mapper->Modified( ); + this->Actor->Modified( ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::PolyDataActor:: +Update( ) +{ + this->Mapper->Update( ); + this->Actor->Modified( ); +} + +// ------------------------------------------------------------------------- +vtkPolyData* ivq::VTK::PolyDataActor:: +GetInput( ) +{ + return( this->Mapper->GetInput( ) ); +} + +// ------------------------------------------------------------------------- +vtkAlgorithm* ivq::VTK::PolyDataActor:: +GetInputAlgorithm( ) +{ + return( this->Mapper->GetInputAlgorithm( ) ); +} + +// ------------------------------------------------------------------------- +vtkInformation* ivq::VTK::PolyDataActor:: +GetInputInformation( ) +{ + return( this->Mapper->GetInputInformation( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::PolyDataActor:: +SetInputData( vtkPolyData* input ) +{ + this->Mapper->SetInputData( input ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::PolyDataActor:: +SetInputConnection( vtkAlgorithmOutput* aout ) +{ + this->Mapper->SetInputConnection( aout ); +} + +// ------------------------------------------------------------------------- +vtkPolyDataMapper* ivq::VTK::PolyDataActor:: +GetMapper( ) +{ + return( this->Mapper.GetPointer( ) ); +} + +// ------------------------------------------------------------------------- +const vtkPolyDataMapper* ivq::VTK::PolyDataActor:: +GetMapper( ) const +{ + return( this->Mapper.GetPointer( ) ); +} + +// ------------------------------------------------------------------------- +vtkActor* ivq::VTK::PolyDataActor:: +GetActor( ) +{ + return( this->Actor.GetPointer( ) ); +} + +// ------------------------------------------------------------------------- +const vtkActor* ivq::VTK::PolyDataActor:: +GetActor( ) const +{ + return( this->Actor.GetPointer( ) ); +} + +// ------------------------------------------------------------------------- +vtkProperty* ivq::VTK::PolyDataActor:: +GetProperty( ) +{ + return( this->Actor->GetProperty( ) ); +} + +// ------------------------------------------------------------------------- +const vtkProperty* ivq::VTK::PolyDataActor:: +GetProperty( ) const +{ + return( this->Actor->GetProperty( ) ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::PolyDataActor:: +PolyDataActor( ) + : Superclass( ) +{ + this->Mapper = vtkSmartPointer< vtkPolyDataMapper >::New( ); + this->Actor = vtkSmartPointer< vtkActor >::New( ); + this->Actor->SetMapper( this->Mapper ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::PolyDataActor:: +~PolyDataActor( ) +{ +} + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/PolyDataActor.h b/lib/ivq/VTK/PolyDataActor.h new file mode 100644 index 0000000..21be872 --- /dev/null +++ b/lib/ivq/VTK/PolyDataActor.h @@ -0,0 +1,80 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__PolyDataActor__h__ +#define __ivq__VTK__PolyDataActor__h__ + +#include + +#include + +#include + +class vtkActor; +class vtkAlgorithm; +class vtkAlgorithmOutput; +class vtkInformation; +class vtkPolyData; +class vtkPolyDataMapper; +class vtkProperty; + +namespace ivq +{ + namespace VTK + { + /** + */ + class IVQ_EXPORT PolyDataActor + : public vtkObject + { + public: + typedef PolyDataActor Self; + + public: + vtkTypeMacro( PolyDataActor, vtkObject ); + + public: + static Self* New( ); + + virtual void Modified( ) override; + virtual void Update( ); + + vtkPolyData* GetInput( ); + vtkAlgorithm* GetInputAlgorithm( ); + vtkInformation* GetInputInformation( ); + void SetInputData( vtkPolyData* input ); + void SetInputConnection( vtkAlgorithmOutput* aout ); + + vtkPolyDataMapper* GetMapper( ); + const vtkPolyDataMapper* GetMapper( ) const; + + vtkActor* GetActor( ); + const vtkActor* GetActor( ) const; + + vtkProperty* GetProperty( ); + const vtkProperty* GetProperty( ) const; + + protected: + PolyDataActor( ); + virtual ~PolyDataActor( ); + + private: + // Purposely not implemented + PolyDataActor( const Self& ); + Self& operator=( const Self& ); + + protected: + vtkSmartPointer< vtkPolyDataMapper > Mapper; + vtkSmartPointer< vtkActor > Actor; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__PolyDataActor__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/SeedWidget.cxx b/lib/ivq/VTK/SeedWidget.cxx new file mode 100644 index 0000000..be43205 --- /dev/null +++ b/lib/ivq/VTK/SeedWidget.cxx @@ -0,0 +1,109 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include +#include +#include +#include + +// ------------------------------------------------------------------------- +ivq::VTK::SeedWidget:: +Self* ivq::VTK::SeedWidget:: +New( ) +{ + return( new Self ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::SeedWidget:: +SeedWidget( ) + : Superclass( ) +{ + // These are the event callbacks supported by this widget + this->CallbackMapper->SetCallbackMethod( + vtkCommand::LeftButtonPressEvent, + vtkWidgetEvent::AddPoint, + this, Self::_AddPointAction + ); + this->CallbackMapper->SetCallbackMethod( + vtkCommand::RightButtonPressEvent, + vtkWidgetEvent::Completed, + this, Self::_CompletedAction + ); + this->CallbackMapper->SetCallbackMethod( + vtkCommand::MouseMoveEvent, + vtkWidgetEvent::Move, + this, Self::_MoveAction + ); + this->CallbackMapper->SetCallbackMethod( + vtkCommand::LeftButtonReleaseEvent, + vtkWidgetEvent::EndSelect, + this, Self::_EndSelectAction + ); + this->CallbackMapper->SetCallbackMethod( + vtkCommand::KeyPressEvent, + vtkEvent::NoModifier, 127, 1, "Delete", + vtkWidgetEvent::Delete, + this, Self::_DeleteAction + ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::SeedWidget:: +~SeedWidget( ) +{ +} + +// ------------------------------------------------------------------------- +void ivq::VTK::SeedWidget:: +_AddPointAction( vtkAbstractWidget* wdg ) +{ + Self* self = dynamic_cast< Self* >( wdg ); + if( self == NULL ) + return; + vtkRenderWindowInteractor* iren = self->GetInteractor( ); + if( iren == NULL ) + return; + int shift = iren->GetShiftKey( ); + if( shift == 1 ) + Self::AddPointAction( wdg ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::SeedWidget:: +_CompletedAction( vtkAbstractWidget* wdg ) +{ + // Do nothing + Self::CompletedAction( wdg ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::SeedWidget:: +_MoveAction( vtkAbstractWidget* wdg ) +{ + // Do nothing + Self::MoveAction( wdg ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::SeedWidget:: +_EndSelectAction( vtkAbstractWidget* wdg ) +{ + // Do nothing + Self::EndSelectAction( wdg ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::SeedWidget:: +_DeleteAction( vtkAbstractWidget* wdg ) +{ + // Do nothing + Self::DeleteAction( wdg ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/SeedWidget.h b/lib/ivq/VTK/SeedWidget.h new file mode 100644 index 0000000..49bff82 --- /dev/null +++ b/lib/ivq/VTK/SeedWidget.h @@ -0,0 +1,54 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__SeedWidget__h__ +#define __ivq__VTK__SeedWidget__h__ + +#include + +#include + +namespace ivq +{ + namespace VTK + { + /** + */ + class IVQ_EXPORT SeedWidget + : public vtkSeedWidget + { + public: + typedef SeedWidget Self; + + public: + vtkTypeMacro( SeedWidget, vtkSeedWidget ); + + public: + static Self* New( ); + + protected: + SeedWidget( ); + virtual ~SeedWidget( ); + + static void _AddPointAction( vtkAbstractWidget* wdg ); + static void _CompletedAction( vtkAbstractWidget* wdg ); + static void _MoveAction( vtkAbstractWidget* wdg ); + static void _EndSelectAction( vtkAbstractWidget* wdg ); + static void _DeleteAction( vtkAbstractWidget* wdg ); + + private: + // Purposely not implemented + SeedWidget( const Self& ); + Self& operator=( const Self& ); + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__SeedWidget__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/SeedWidgetOverImageActor.cxx b/lib/ivq/VTK/SeedWidgetOverImageActor.cxx new file mode 100644 index 0000000..dbd90ca --- /dev/null +++ b/lib/ivq/VTK/SeedWidgetOverImageActor.cxx @@ -0,0 +1,224 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#include + +#include +#include + +#include +#include +#include +#include +#include +#include + +// ------------------------------------------------------------------------- +namespace ivq +{ + namespace VTK + { + /** + */ + class SeedWidgetOverImageActorCallback + : public vtkCommand + { + public: + static SeedWidgetOverImageActorCallback* New( ) + { + return( new SeedWidgetOverImageActorCallback( ) ); + } + virtual void Execute( + vtkObject* caller, unsigned long eId, void* data + ) override + { + ivq::VTK::ImageActor* actor = + ivq::VTK::ImageActor::SafeDownCast( caller ); + ivq::VTK::SeedWidgetOverImageActor* widget = + ivq::VTK::SeedWidgetOverImageActor::SafeDownCast( caller ); + if( actor != NULL && this->Widget != NULL ) + { + if( eId == vtkCommand::InteractionEvent ) + { + widget = this->Widget; + if( widget->GetEnabled( ) != 0 ) + { + widget->CompleteInteraction( ); + widget->EnabledOff( ); + unsigned long nSeeds = + widget->Representation->GetNumberOfSeeds( ); + for( unsigned long i = 0; i < nSeeds; ++i ) + { + widget->Representation->RemoveLastHandle( ); + widget->DeleteSeed( + widget->Representation->GetNumberOfSeeds( ) + ); + + } // rof + + unsigned long slice = widget->Actor->GetSliceNumber( ); + std::map< unsigned long, std::vector< double > >::iterator + sIt = widget->Points.find( slice ); + if( sIt != widget->Points.end( ) ) + { + widget->Representation->BuildRepresentation( ); + vtkRenderer* ren = + widget->GetInteractor( )->FindPokedRenderer( + widget->GetInteractor( )->GetEventPosition( )[ 0 ], + widget->GetInteractor( )->GetEventPosition( )[ 1 ] + ); + unsigned int nCoords = sIt->second.size( ); + for( unsigned int c = 0; c < nCoords; c += 3 ) + { + double x[ 3 ]; + widget->ComputeWorldToDisplay( + ren, + sIt->second[ c ], + sIt->second[ c + 1 ], + sIt->second[ c + 2 ], + x + ); + x[ 2 ] = double( 0 ); + int s = widget->Representation->CreateHandle( x ); + vtkHandleWidget* curr_hnd = widget->CreateNewHandle( ); + widget->Representation->SetSeedDisplayPosition( s, x ); + curr_hnd->SetEnabled( 1 ); + + } // rof + + } // fi + widget->RestartInteraction( ); + widget->EnabledOn( ); + widget->Render( ); + + } // fi + + } // fi + } + else if( widget != NULL ) + { + if( eId == vtkCommand::InteractionEvent ) + { + unsigned long sId = *( static_cast< int* >( data ) ); + double pos[ 3 ]; + widget->Representation->GetSeedWorldPosition( sId, pos ); + unsigned long slice = widget->Actor->GetSliceNumber( ); + widget->Points[ slice ][ ( sId * 3 ) + 0 ] = pos[ 0 ]; + widget->Points[ slice ][ ( sId * 3 ) + 1 ] = pos[ 1 ]; + widget->Points[ slice ][ ( sId * 3 ) + 2 ] = pos[ 2 ]; + } + else if( eId == vtkCommand::PlacePointEvent ) + { + unsigned long sId = + widget->Representation->GetNumberOfSeeds( ) - 1; + double pos[ 3 ]; + widget->Representation->GetSeedWorldPosition( sId, pos ); + unsigned long slice = widget->Actor->GetSliceNumber( ); + widget->Points[ slice ].push_back( pos[ 0 ] ); + widget->Points[ slice ].push_back( pos[ 1 ] ); + widget->Points[ slice ].push_back( pos[ 2 ] ); + + } // fi + + } // fi + } + + protected: + SeedWidgetOverImageActorCallback( ) + : vtkCommand( ), + Widget( NULL ) + { + } + virtual ~SeedWidgetOverImageActorCallback( ) + { + } + + private: + // Purposely not implemented + SeedWidgetOverImageActorCallback( + const SeedWidgetOverImageActorCallback& other + ); + SeedWidgetOverImageActorCallback& operator=( + const SeedWidgetOverImageActorCallback& other + ); + + public: + ivq::VTK::SeedWidgetOverImageActor* Widget; + }; + + } // ecapseman + +} // ecapseman + +// ------------------------------------------------------------------------- +ivq::VTK::SeedWidgetOverImageActor:: +Self* ivq::VTK::SeedWidgetOverImageActor:: +New( ) +{ + return( new Self( ) ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::ImageActor* ivq::VTK::SeedWidgetOverImageActor:: +GetActor( ) +{ + return( this->Actor.GetPointer( ) ); +} + +// ------------------------------------------------------------------------- +void ivq::VTK::SeedWidgetOverImageActor:: +SetActor( ivq::VTK::ImageActor* actor ) +{ + if( this->Actor.GetPointer( ) != actor ) + { + this->Points.clear( ); + this->Actor = actor; + this->Placer = vtkSmartPointer< ivq::VTK::ImageSlicePointPlacer >::New( ); + this->Handles = vtkSmartPointer< vtkPointHandleRepresentation3D >::New( ); + this->Representation = vtkSmartPointer< vtkSeedRepresentation >::New( ); + + this->Placer->SetImageSlice( this->Actor ); + this->Handles->GetProperty( )->SetColor( 1, 0, 0 ); + this->Handles->SetPointPlacer( this->Placer ); + this->Representation->SetHandleRepresentation( this->Handles ); + this->SetRepresentation( this->Representation ); + this->Modified( ); + + vtkSmartPointer< SeedWidgetOverImageActorCallback > cbk = + vtkSmartPointer< SeedWidgetOverImageActorCallback >::New( ); + cbk->Widget = this; + this->ObserverId = + this->Actor->AddObserver( vtkCommand::InteractionEvent, cbk ); + this->AddObserver( vtkCommand::PlacePointEvent, cbk ); + this->AddObserver( vtkCommand::InteractionEvent, cbk ); + + } // fi +} + +// ------------------------------------------------------------------------- +const ivq::VTK::SeedWidgetOverImageActor:: +TSeeds& ivq::VTK::SeedWidgetOverImageActor:: +GetSeeds( ) const +{ + return( this->Points ); +} + +// ------------------------------------------------------------------------- +ivq::VTK::SeedWidgetOverImageActor:: +SeedWidgetOverImageActor( ) + : Superclass( ) +{ +} + +// ------------------------------------------------------------------------- +ivq::VTK::SeedWidgetOverImageActor:: +~SeedWidgetOverImageActor( ) +{ + if( this->Actor.GetPointer( ) != NULL ) + this->Actor->RemoveObserver( this->ObserverId ); +} + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/SeedWidgetOverImageActor.h b/lib/ivq/VTK/SeedWidgetOverImageActor.h new file mode 100644 index 0000000..81f05c9 --- /dev/null +++ b/lib/ivq/VTK/SeedWidgetOverImageActor.h @@ -0,0 +1,78 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__SeedWidgetOverImageActor__h__ +#define __ivq__VTK__SeedWidgetOverImageActor__h__ + +#include + +#include +#include + +#include + +#include + +class vtkPointHandleRepresentation3D; +class vtkSeedRepresentation; + +namespace ivq +{ + namespace VTK + { + class ImageActor; + class ImageSlicePointPlacer; + + /** + */ + class IVQ_EXPORT SeedWidgetOverImageActor + : public ivq::VTK::SeedWidget + { + public: + typedef SeedWidgetOverImageActor Self; + + typedef std::map< unsigned long, std::vector< double > > TSeeds; + + public: + vtkTypeMacro( SeedWidgetOverImageActor, ivq::VTK::SeedWidget ); + + public: + static Self* New( ); + + ivq::VTK::ImageActor* GetActor( ); + void SetActor( ivq::VTK::ImageActor* actor ); + + const TSeeds& GetSeeds( ) const; + + protected: + SeedWidgetOverImageActor( ); + virtual ~SeedWidgetOverImageActor( ); + + private: + // Purposely not implemented + SeedWidgetOverImageActor( const Self& ); + Self& operator=( const Self& ); + + protected: + vtkSmartPointer< ivq::VTK::ImageActor > Actor; + vtkSmartPointer< ivq::VTK::ImageSlicePointPlacer > Placer; + vtkSmartPointer< vtkPointHandleRepresentation3D > Handles; + vtkSmartPointer< vtkSeedRepresentation > Representation; + + unsigned long ObserverId; + + std::map< unsigned long, std::vector< double > > Points; + + friend class SeedWidgetOverImageActorCallback; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__SeedWidgetOverImageActor__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/Simple3DCurveToPolyData.cxx b/lib/ivq/VTK/Simple3DCurveToPolyData.cxx new file mode 100644 index 0000000..8b7e279 --- /dev/null +++ b/lib/ivq/VTK/Simple3DCurveToPolyData.cxx @@ -0,0 +1,119 @@ +#include + +#include +#include +#include +#include + +// ------------------------------------------------------------------------- +template< class _TCurve > +typename ivq::VTK::Simple3DCurveToPolyData< _TCurve >:: +Self* ivq::VTK::Simple3DCurveToPolyData< _TCurve >:: +New( ) +{ + return( new Self( ) ); +} + +// ------------------------------------------------------------------------- +template< class _TCurve > +const typename ivq::VTK::Simple3DCurveToPolyData< _TCurve >:: +TCurve* ivq::VTK::Simple3DCurveToPolyData< _TCurve >:: +GetInput( ) const +{ + return( this->m_Curve ); +} + +// ------------------------------------------------------------------------- +template< class _TCurve > +void +ivq::VTK::Simple3DCurveToPolyData< _TCurve >:: +SetInput( const TCurve* c ) +{ + if( this->m_Curve != c ) + { + this->m_Curve = c; + this->Modified( ); + + } // fi +} + +// ------------------------------------------------------------------------- +template< class _TCurve > +ivq::VTK::Simple3DCurveToPolyData< _TCurve >:: +Simple3DCurveToPolyData( ) + : vtkPolyDataAlgorithm( ), + m_Curve( NULL ) +{ + this->SetNumberOfInputPorts( 0 ); +} + +// ------------------------------------------------------------------------- +template< class _TCurve > +ivq::VTK::Simple3DCurveToPolyData< _TCurve >:: +~Simple3DCurveToPolyData( ) +{ +} + +// ------------------------------------------------------------------------- +template< class _TCurve > +int ivq::VTK::Simple3DCurveToPolyData< _TCurve >:: +RequestData( + vtkInformation* information, + vtkInformationVector** input, + vtkInformationVector* output + ) +{ + if( this->m_Curve == NULL ) + return( 0 ); + + // Get output + vtkInformation* info = output->GetInformationObject( 0 ); + vtkPolyData* out = vtkPolyData::SafeDownCast( + info->Get( vtkDataObject::DATA_OBJECT( ) ) + ); + + // Prepare data + out->SetPoints( vtkSmartPointer< vtkPoints >::New( ) ); + out->SetVerts( vtkSmartPointer< vtkCellArray >::New( ) ); + out->SetLines( vtkSmartPointer< vtkCellArray >::New( ) ); + out->SetPolys( vtkSmartPointer< vtkCellArray >::New( ) ); + out->SetStrips( vtkSmartPointer< vtkCellArray >::New( ) ); + vtkPoints* points = out->GetPoints( ); + vtkCellArray* lines = out->GetLines( ); + + // Get data + for( unsigned long i = 0; i < this->m_Curve->GetNumberOfPoints( ); ++i ) + { + typename _TCurve::TPoint pnt = this->m_Curve->GetPoint( i ); + points->InsertNextPoint( pnt[ 0 ], pnt[ 1 ], pnt[ 2 ] ); + if( i > 0 ) + { + lines->InsertNextCell( 2 ); + lines->InsertCellPoint( i - 1 ); + lines->InsertCellPoint( i ); + + } // fi + + } // rof + return( 1 ); +} + +// ------------------------------------------------------------------------- +template< class _TCurve > +int ivq::VTK::Simple3DCurveToPolyData< _TCurve >:: +RequestInformation( + vtkInformation* information, + vtkInformationVector** input, + vtkInformationVector* output + ) +{ + return( 1 ); +} + +// ------------------------------------------------------------------------- +#include + +template class ivq::VTK::Simple3DCurveToPolyData< ivq::ITK::Simple3DCurve< float > >; +template class ivq::VTK::Simple3DCurveToPolyData< ivq::ITK::Simple3DCurve< double > >; + +// eof - $RCSfile$ diff --git a/lib/ivq/VTK/Simple3DCurveToPolyData.h b/lib/ivq/VTK/Simple3DCurveToPolyData.h new file mode 100644 index 0000000..e7d38f9 --- /dev/null +++ b/lib/ivq/VTK/Simple3DCurveToPolyData.h @@ -0,0 +1,66 @@ +/* ======================================================================= + * @author: Leonardo Florez-Valencia + * @email: florez-l@javeriana.edu.co + * ======================================================================= + */ + +#ifndef __ivq__VTK__Simple3DCurveToPolyData__h__ +#define __ivq__VTK__Simple3DCurveToPolyData__h__ + +#include +#include + +namespace ivq +{ + namespace VTK + { + /** + */ + template< class _TCurve > + class IVQ_EXPORT Simple3DCurveToPolyData + : public vtkPolyDataAlgorithm + { + public: + typedef Simple3DCurveToPolyData Self; + typedef _TCurve TCurve; + + public: + vtkTypeMacro( Simple3DCurveToPolyData, vtkPolyDataAlgorithm ); + + public: + static Self* New( ); + + const TCurve* GetInput( ) const; + void SetInput( const TCurve* c ); + + protected: + Simple3DCurveToPolyData( ); + virtual ~Simple3DCurveToPolyData( ); + + int RequestData( + vtkInformation* information, + vtkInformationVector** input, + vtkInformationVector* output + ); + int RequestInformation( + vtkInformation* information, + vtkInformationVector** input, + vtkInformationVector* output + ); + + private: + // Purposely not implemented + Simple3DCurveToPolyData( const Self& ); + void operator=( const Self& ); + + protected: + const TCurve* m_Curve; + }; + + } // ecapseman + +} // ecapseman + +#endif // __ivq__VTK__Simple3DCurveToPolyData__h__ + +// eof - $RCSfile$ diff --git a/lib/ivq/Version.cxx.in b/lib/ivq/Version.cxx.in new file mode 100644 index 0000000..1ecb84a --- /dev/null +++ b/lib/ivq/Version.cxx.in @@ -0,0 +1,15 @@ +/* ========================================================================= + * @author Leonardo Florez-Valencia (florez-l@javeriana.edu.co) + * ========================================================================= + */ + +#include +#include + +// ------------------------------------------------------------------------- +std::string IVQ_EXPORT version( ) +{ + return( "@prj_MAJ@.@prj_MIN@.@prj_REL@" ); +} + +// eof - $RCSfile$ -- 2.47.1