Skip to content

Commit f5f3993

Browse files
committed
WIP: ENH: Add WebAssembly interface
1 parent 4427e06 commit f5f3993

8 files changed

+189
-3
lines changed

CMakeLists.txt

+7-3
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,6 @@ project(Cleaver)
33

44
set(CMAKE_CXX_STANDARD 17)
55

6-
set(Cleaver_LIBRARIES cleaver)
7-
86
include(FetchContent)
97
set(_itk_build_testing ${BUILD_TESTING})
108
#set(BUILD_TESTING OFF)
@@ -29,7 +27,11 @@ endif()
2927
set(BUILD_TESTING ${_itk_build_testing})
3028
set(BUILD_SHARED_LIBS ${_itk_build_shared})
3129

32-
include_directories(${cleaver_lib_SOURCE_DIR}/src/lib)
30+
set(Cleaver_LIBRARIES cleaver)
31+
set(Cleaver_INCLUDE_DIRS
32+
${Cleaver_SOURCE_DIR}/include
33+
${cleaver_lib_SOURCE_DIR}/src/lib
34+
)
3335

3436
if(NOT ITK_SOURCE_DIR)
3537
find_package(ITK REQUIRED)
@@ -39,3 +41,5 @@ else()
3941
set(ITK_DIR ${CMAKE_BINARY_DIR})
4042
itk_module_impl()
4143
endif()
44+
45+
itk_module_target(cleaver NO_INSTALL)

examples/CMakeLists.txt

+49
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
cmake_minimum_required(VERSION 3.10)
2+
project(ITKCleaverWebAssembly)
3+
4+
set(CMAKE_CXX_STANDARD 17)
5+
6+
if(EMSCRIPTEN)
7+
set(io_components
8+
)
9+
elseif(WASI)
10+
set(io_components
11+
ITKIONRRD
12+
ITKIOMeshVTK
13+
)
14+
else()
15+
set(io_components
16+
ITKMeshIO
17+
ITKImageIO
18+
)
19+
endif()
20+
find_package(ITK REQUIRED
21+
COMPONENTS
22+
${io_components}
23+
WebAssemblyInterface
24+
Cleaver
25+
)
26+
include(${ITK_USE_FILE})
27+
28+
add_executable(ITKCleaverWasm ITKCleaverWasm.cxx)
29+
target_link_libraries(ITKCleaverWasm PUBLIC ${ITK_LIBRARIES})
30+
31+
enable_testing()
32+
add_test(NAME ITKCleaverWasmLabelImageTest
33+
COMMAND ITKCleaverWasm
34+
--input
35+
${CMAKE_CURRENT_SOURCE_DIR}/mickey.nrrd
36+
--triangle
37+
${CMAKE_CURRENT_BINARY_DIR}/mickey-triangle.vtk
38+
)
39+
40+
add_test(NAME ITKCleaverIndicatorFunctionTest
41+
COMMAND ITKCleaverWasm
42+
--input
43+
${CMAKE_CURRENT_SOURCE_DIR}/spheres1.nrrd
44+
${CMAKE_CURRENT_SOURCE_DIR}/spheres2.nrrd
45+
${CMAKE_CURRENT_SOURCE_DIR}/spheres3.nrrd
46+
${CMAKE_CURRENT_SOURCE_DIR}/spheres4.nrrd
47+
--triangle
48+
${CMAKE_CURRENT_BINARY_DIR}/indicator-triangle.vtk
49+
)

examples/ITKCleaverWasm.cxx

+133
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,133 @@
1+
/*=========================================================================
2+
*
3+
* Copyright NumFOCUS
4+
*
5+
* Licensed under the Apache License, Version 2.0 (the "License");
6+
* you may not use this file except in compliance with the License.
7+
* You may obtain a copy of the License at
8+
*
9+
* http://www.apache.org/licenses/LICENSE-2.0.txt
10+
*
11+
* Unless required by applicable law or agreed to in writing, software
12+
* distributed under the License is distributed on an "AS IS" BASIS,
13+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14+
* See the License for the specific language governing permissions and
15+
* limitations under the License.
16+
*
17+
*=========================================================================*/
18+
#include "itkCleaverImageToMeshFilter.h"
19+
#include "itkPipeline.h"
20+
#include "itkInputImage.h"
21+
#include "itkOutputMesh.h"
22+
#include "itkSupportInputImageTypesNoVectorImage.h"
23+
#include "itkMesh.h"
24+
25+
template<typename TImage>
26+
int
27+
Mesher(itk::wasm::Pipeline & pipeline, std::vector<const TImage *> & inputImages)
28+
{
29+
using ImageType = TImage;
30+
31+
using MeshType = itk::Mesh<typename ImageType::PixelType, 3>;
32+
using OutputMeshType = itk::wasm::OutputMesh<MeshType>;
33+
OutputMeshType outputTriangleMesh;
34+
pipeline.add_option("-t,--triangle", outputTriangleMesh, "Output triangle mesh");
35+
36+
unsigned int radius = 1;
37+
pipeline.add_option("-r,--radius", radius, "Kernel radius in pixels");
38+
39+
unsigned int maxTotalSplits = 1;
40+
pipeline.add_option("-m,--max-splits", maxTotalSplits, "Max total processing splits");
41+
42+
unsigned int split = 1;
43+
pipeline.add_option("-s,--split", split, "Split to process");
44+
45+
ITK_WASM_PARSE(pipeline);
46+
47+
using FilterType = itk::CleaverImageToMeshFilter<ImageType, MeshType>;
48+
typename FilterType::Pointer filter = FilterType::New();
49+
50+
for(size_t ii = 0; ii < inputImages.size(); ii++)
51+
{
52+
filter->SetInput(ii, inputImages[ii]);
53+
}
54+
55+
56+
//using ROIFilterType = itk::ExtractImageFilter< ImageType, ImageType >;
57+
//auto roiFilter = ROIFilterType::New();
58+
//roiFilter->InPlaceOn();
59+
//if (maxTotalSplits > 1)
60+
//{
61+
//smoother->UpdateOutputInformation();
62+
//using RegionType = typename ImageType::RegionType;
63+
//smoother->UpdateOutputInformation();
64+
//const RegionType largestRegion( smoother->GetOutput()->GetLargestPossibleRegion() );
65+
66+
//using SplitterType = itk::ImageRegionSplitterSlowDimension;
67+
//auto splitter = SplitterType::New();
68+
//const unsigned int numberOfSplits = splitter->GetNumberOfSplits( largestRegion, maxTotalSplits );
69+
//if (split >= numberOfSplits)
70+
//{
71+
//std::cerr << "Error: requested split: " << split << " is outside the number of splits: " << numberOfSplits << std::endl;
72+
//return EXIT_FAILURE;
73+
//}
74+
75+
//RegionType requestedRegion( largestRegion );
76+
//splitter->GetSplit( split, numberOfSplits, requestedRegion );
77+
//roiFilter->SetInput( smoother->GetOutput() );
78+
//roiFilter->SetExtractionRegion( requestedRegion );
79+
//roiFilter->Update();
80+
//outputImage.Set( roiFilter->GetOutput() );
81+
//}
82+
//else
83+
//{
84+
//smoother->Update();
85+
//outputImage.Set( smoother->GetOutput() );
86+
//}
87+
ITK_WASM_CATCH_EXCEPTION(pipeline, filter->Update());
88+
89+
outputTriangleMesh.Set(filter->GetOutput(1));
90+
91+
return EXIT_SUCCESS;
92+
}
93+
94+
template<typename TImage>
95+
class PipelineFunctor
96+
{
97+
public:
98+
int operator()(itk::wasm::Pipeline & pipeline)
99+
{
100+
using ImageType = TImage;
101+
102+
using InputImageType = itk::wasm::InputImage<ImageType>;
103+
std::vector<InputImageType> inputImages;
104+
pipeline.add_option("-i,--input", inputImages, "Input label image or multiple indicator function images");
105+
106+
ITK_WASM_PRE_PARSE(pipeline);
107+
108+
std::vector<const ImageType *> loadedInputImages;
109+
for(auto image: inputImages)
110+
{
111+
loadedInputImages.push_back(image.Get());
112+
}
113+
114+
int result = Mesher<ImageType>(pipeline, loadedInputImages);
115+
return result;
116+
}
117+
};
118+
119+
int main( int argc, char * argv[] )
120+
{
121+
itk::wasm::Pipeline pipeline("Create a multi-material mesh suitable for simulation/modeling from an input label image or indicator function images", argc, argv);
122+
123+
return itk::wasm::SupportInputImageTypesNoVectorImage<PipelineFunctor,
124+
//uint8_t,
125+
//int8_t,
126+
uint16_t,
127+
//int16_t,
128+
//float,
129+
//double
130+
float
131+
>
132+
::Dimensions<3U>("Input", pipeline);
133+
}

examples/mickey.nrrd

489 KB
Binary file not shown.

examples/spheres1.nrrd

85.9 KB
Binary file not shown.

examples/spheres2.nrrd

85.9 KB
Binary file not shown.

examples/spheres3.nrrd

85.9 KB
Binary file not shown.

examples/spheres4.nrrd

85.9 KB
Binary file not shown.

0 commit comments

Comments
 (0)