Geting Scalars to DiscreteMarchingCubes

Hello,

I am currently applying discretemarchingcubes to extract multiple valued segmentation label. The filter is working fine. However I am applying computescalarson() but I am getting in trouble trying to retrieve each scalar label related to each segmentation label.

Thank you,

    #ifdef USE_FLYING_EDGES
  vtkNew<vtkDiscreteFlyingEdges3D> discrete_smooth_mesher;
#else
  vtkNew<vtkDiscreteMarchingCubes> discrete_smooth_mesher;
#endif



discrete_smooth_mesher->SetInputData(imported_image);
discrete_smooth_mesher->ComputeScalarsOn();
discrete_smooth_mesher->GenerateValues(num_labels, min_label,  max_label);
discrete_smooth_mesher->Update();

// Loop through each label and print scalar values

vtkSmartPointer<vtkPolyData> outputPolyData = discrete_smooth_mesher->GetOutput();

vtkCellData* pointData = outputPolyData->GetCellData();

    vtkDataArray* scalarArray = pointData->GetScalars(0);

I suggest that you also look into the filter vtkSurfaceNets3D. It’s a lot faster and can produce much better results depending on your volume resolution.

I’m not sure what you are trying to do, could you provide more information?? and why it’s not working? This works for me to get the 1000th cell scalar.

output = discrete.GetOutput()
cellData = output.GetCellData()
scalars = output.GetCellData().GetArray(0)
print(scalars.GetTuple1(1000))

Hello,

I am assiging a label value for each connected component in the image that I am using to generate the mesh. In the picture each rib has a different label in the original image.

I am just trying to check if the corrected label is assigned to each cell of the output mesh, I will need that information later.

I tryed to do something similar to your code but it does not print.

Thank you

vtkSmartPointer<vtkPolyData> outputPolyData = discrete_smooth_mesher->GetOutput();

vtkCellData* pointData = outputPolyData->GetCellData();
	

    vtkDataArray* scalarArray = pointData->GetArray(0);

    if (scalarArray) {
	    
	            std::unordered_set<int> uniqueValues;

		    for (vtkIdType i = 0; i < scalarArray->GetNumberOfTuples(); ++i) {
     			int scalarValue = static_cast<int>(scalarArray->GetTuple1(i));

			uniqueValues.insert(scalarValue);}

tissue 6

How many labels in the input image? How many labels are inserted into uniqueValues? Can you share the data?

Sure,

Those are the labels of the ribs, which are the input of the filter:

There are more tissues thant the ribs I pass them one by one…

Hello,

I was able to acess only point data with discretemarchingcubes and sufracenets3d through this code. The labels are correct.

CELL DATA CODE:

vtkCellData* cellData = polydataCopy->GetCellData();

if (!cellData) {std::cerr << "Error: Cell data is nullptr." << std::endl;}
 else{   std::cout << "Number of cell arrays: " << cellData->GetNumberOfArrays() << std::endl;}


vtkInformation* outputInfo = discrete_smooth_mesher->GetOutputPortInformation(0);
if (outputInfo->Has(vtkDataObject::CELL_DATA_VECTOR())) {
    vtkCellData* cellData = polydataCopy->GetCellData();} 
    else {std::cerr << "Error: No cell data available in the output." << std::endl;}

	

    vtkDataArray* scalarArray = cellData->GetArray(0);
    if(!scalarArray)vtkDataArray* scalarArray = cellData->GetArray("ImageScalars");
     

    if (scalarArray) {
    		    std::unordered_set<int> uniqueValues;

		    for (vtkIdType i = 0; i < scalarArray->GetNumberOfTuples(); ++i) {
     			double scalarValue = scalarArray->GetTuple1(i);
			int scalarValue_2 = static_cast<int>(scalarValue);
			
			uniqueValues.insert(scalarValue_2);}
		    

	    
	                // Print unique values
		    for (int value : uniqueValues) {
			std::cout << value << " ";
		    }


	}else {    std::cerr << "Error: Scalar array is nullptr." << std::endl;}

POINT DATA CODE:

	vtkPointData* pointData = polydataCopy->GetPointData();

	if (!pointData) {std::cerr << "Error: Point data is nullptr." << std::endl;
	} else {std::cout << "Number of point arrays: " << pointData->GetNumberOfArrays() << std::endl;

	    for (vtkIdType i = 0; i < pointData->GetNumberOfArrays(); ++i) {
		vtkDataArray* array = pointData->GetArray(i);
		const char* arrayName = array->GetName();
		std::cout << "Array " << i << ": " << (arrayName ? arrayName : "NoName") << std::endl;
	    }

	    vtkDataArray* scalarArray = pointData->GetScalars();

	    if (scalarArray) {
		// Assuming the scalar array is of type vtkDoubleArray
		std::unordered_set<int> uniqueValues;

		for (vtkIdType i = 0; i < scalarArray->GetNumberOfTuples(); ++i) {
		    int scalarValue = static_cast<int>(scalarArray->GetTuple1(i));
		    uniqueValues.insert(scalarValue);}

		// Print unique values
		for (int value : uniqueValues) {
		    std::cout << value << " ";}
	    } else {std::cerr << "Error: Scalar array is nullptr." << std::endl;}}

TERMINAL:

	Number of cell arrays: 0
	Error: No cell data available in the output.
	Error: Scalar array is nullptr.
	Number of point arrays: 2
	Array 0: scalars
	Array 1: Normals
	46 45 44 43 42 41 40 39 38 37 20 19 18 17 16 15 14 13 12 11 10 9 8 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36