We have a 3D model mace like the above image.
Let’s delete the cells that are in the negative X-axis space, there are some invalid points in the model after the operation.

    vtkSPtrNew( reader, vtkSTLReader );
    reader->SetFileName( "/Users/weiyang/Desktop/mace.stl" );
    reader->Update();

    vtkSPtrNew( data, vtkPolyData );
    data->DeepCopy( reader->GetOutput() );

    vtkSPtrNew( cutPlane, vtkPlane );
    cutPlane->SetNormal( 1, 0, 0 );
    cutPlane->SetOrigin( 0, 0, 0 );

    // =============== delete some cells, clip by cutPlane ====================
    cout << "point count: " << data->GetNumberOfPoints() << endl;
    for( int i = 0; i < data->GetNumberOfCells(); ++i )
    {
        vtkCell *cell = data->GetCell( i );
        Point center( 0, 0, 0 );
        for( int j = 0; j < cell->GetNumberOfPoints(); j++ )
        {
            Point pt( data->GetPoint( cell->GetPointId( j ) ) );
            center = center + pt;
        }
        center /= 3;
        if ( cutPlane->EvaluateFunction( center.point ) < 0 )
        {
            data->DeleteCell( i );
        }
    }
    data->RemoveDeletedCells();
    cout << "point count: " << data->GetNumberOfPoints() << endl;
    // ===================== end! ===================

Here is a interesting truth about storing the data. The class vtkXMLPolyDataWriter will write all points to file but vtkSTLWriter writes only points which are used by cells.

    // vtkXMLPolyDataWriter will write all points to file
    vtkSPtrNew( xmlWriter, vtkXMLPolyDataWriter );
    xmlWriter->SetInputData( data );
    xmlWriter->SetFileName( "/Users/weiyang/Desktop/clipped.vtp" );
    xmlWriter->Update();

    // vtkSTLWriter write only points which are used by cells
    vtkSPtrNew( stlWriter, vtkSTLWriter );
    stlWriter->SetInputData( data );
    stlWriter->SetFileName( "/Users/weiyang/Desktop/clipped.stl" );
    stlWriter->Update();

Generate a new polyData which has not invalid point. We have to colloct the points that are used by cells and update the point ids in the cell lists. I used binary search algorithm to speed up the process.

int binary_Find( std::vector<int> array, int value )
{
    int l = 0;
    int r = array.size() - 1;
    int mid = -1;
    while( l <= r )
    {
        mid = (l + r) / 2;
        if( array[mid] == value )
        {
            return mid;
        }
        else if( array[mid] < value )
        {
            l = mid+1;
        }
        else {
            r = mid-1;
        }
    }
    return -1;
}

int main()
{
//...
    // ================ generate a new polyData without invalid points ===============
    std::vector<bool> validPts;
    for( int i = 0; i < data->GetNumberOfPoints(); ++i )
    {
        validPts.push_back( false );
    }
    for( int i = 0; i < data->GetNumberOfCells(); ++i )
    {
        vtkIdType npts;
        const vtkIdType *pts;
        data->GetCellPoints( i, npts, pts );
        for( int j = 0; j < npts; ++j )
        {
            validPts[ pts[j] ] = true;
        }
    }

    vtkSPtrNew( newData, vtkPolyData );
    vtkSPtrNew( newPoints, vtkPoints );
    vtkSPtrNew( newCells, vtkCellArray);
    std::vector<int> newPtIds;
    for( int i = 0; i < data->GetNumberOfPoints(); ++i )
    {
        if( validPts[i] )
        {
            newPoints->InsertNextPoint( data->GetPoint( i ) );
            newPtIds.push_back( i );
        }
    }
    for( int i = 0; i < data->GetNumberOfCells(); ++i )
    {
        vtkIdType npts;
        const vtkIdType *pts;
        data->GetCellPoints( i, npts, pts );
        vtkSPtrNew( list, vtkIdList );
        for( int j = 0; j < npts; ++j )
        {
            int index = binary_Find( newPtIds, pts[j] );
            list->InsertNextId( index );
        }
        newCells->InsertNextCell( list );
    }
    newData->SetPoints( newPoints );
    newData->SetPolys( newCells );
    newData->Modified();

We can find that the number of points of the original model is 700 and the new result is 394.



Categories: VTK

0 0 votes
Article Rating
Subscribe
Notify of
guest
0 Comments
Inline Feedbacks
View all comments

3D Model Viewer: add grid plane and convex hull.

X
A prohibited operation
0
Would love your thoughts, please comment.x
()
x