[vtkusers] how to use PolyData::GetPolys()?

Dominik Szczerba domi at vision.ee.ethz.ch
Tue Oct 10 16:54:20 EDT 2006


In addition to my previous email, additional info, direct array methods 
do work faster than general GetCell methods, I measure about a factor of 
2x, but that might pretty much depend on a concrete dataset.
bye
Dominik

Dominik Szczerba wrote:
> John,
> 
> Thanks a lot for the hints, but after your previous hints I was not 
> copying anything already. There were two things:
> 
> 1) To use e.g.
>      const double* p1 = 
> (double*)(polydata->GetPoints()->GetData())->GetVoidPointer(3*id1);
> 
> instead
>      const double* p1 = 
> vtkDoubleArray::SafeDownCast(polydata->GetPoints()->GetData())->GetPointer(3*id1); 
> 
> 
> Somehow this works twice faster for me, maybe tricks g++ does to -Ox 
> switches
> 
> 2) to control refresh rate. The RenderInteractor timers segfaults for me 
> so I cannot use elegant idle calls. I took over the main loop calling 
> Render() by hand. When reduced to 40 miliseconds (timing up things 
> myself) factor another 2 is back.
> 
> Still, there is some slight decrease in performance compared to the 
> other code but I can live with it for now.
> 
> Thanks a lot for your help,
> Looking forward to help you too some day,
> Dominik
> 
> John Biddiscombe wrote:
>> Dominik
>>
>> OK, OK. Don't give up yet. If the previous method wasn't fast enough, 
>> then you need to avoid copying any ID's or points from the cell array 
>> and work directly from the Id's and points
>>
>> fisr get a pointer to the raw points float data using float *rawdata = 
>> vtkFloatArray::SafeDownCast(points->GetData())->GetPointer(0);
>> or double according to tase...
>>
>> then get a pointer to the cell array
>>   vtkCellArray *cells = input->GetPolys();
>> now walk the cell array using something like this
>>
>>  vtkIdType *ptIds = cells->GetPointer();
>>  for (int i=0; i<numCells; i++) {
>>    vtkIdType nverts = *ptIds++;
>>    while (nverts>0) {
>>      vtkIdType Id = *ptIds++;
>>       you can now use the ID to index directly the points and do 
>> whatever you need
>>        we haven't copied any Id's or points so it doesn't get much 
>> faster then this
>>      }
>>      nverts--;
>>    }
>>  }
>>
>> Now come on - we must be getting there now? I should have suggested 
>> this first time, but it's better to build up a bit of suspense :)
>>
>> JB
>>
>>> John, you have been most helpful, I could take over from your points.
>>> However, I do not observe any significant speed gain compared to the 
>>> "normal" GetCell style...?
>>> Thanks a lot!
>>> Dominik
>>>
>>> John Biddiscombe wrote:
>>>> Dominik
>>>>
>>>> Does this code snippet help you.(snippet from an old filter of mine, 
>>>> ignore the preamble etc
>>>>
>>>>    vtkPolyData  *input    = (vtkPolyData *)this->GetInput();
>>>>    vtkPolyData  *output   = (vtkPolyData *)this->GetOutput();
>>>>    vtkPolyData  *failOut  = this->GetFailedData();
>>>>    vtkPoints    *in_Pts   = input->GetPoints();
>>>>    vtkCellArray *in_Polys = input->GetPolys();
>>>>    if (input->GetNumberOfPoints()==0) return;
>>>>    int nc = in_Polys->GetNumberOfCells();
>>>>    //
>>>>    vtkCellArray *out_Polys    = vtkCellArray::New();
>>>>    vtkCellArray *bad_Polys    = vtkCellArray::New();
>>>>    //
>>>>    // Should have same polys out as in if no bad ones are found
>>>>    //
>>>>    out_Polys->Allocate(nc,nc);
>>>>    bad_Polys->Allocate(nc,nc);
>>>>    //
>>>>    // Walk Polygons and test them all
>>>>    //
>>>>    vtkIdType npoints, *pt_IDs, polyID=0;
>>>>    int m_c_s = input->GetMaxCellSize();
>>>>    doublevector3 *points = new doublevector3[m_c_s];
>>>>    double fnormal[3];
>>>>    for (in_Polys->InitTraversal(); 
>>>> in_Polys->GetNextCell(npoints,pt_IDs); polyID++) {
>>>>        // make local copy of cell points
>>>>        for (int i=0; i<npoints; i++) 
>>>> in_Pts->GetPoint(pt_IDs[i],&points[i].x);
>>>> ....
>>>>
>>>> now replace the line
>>>>        for (int i=0; i<npoints; i++) 
>>>> in_Pts->GetPoint(pt_IDs[i],&points[i].x);
>>>> with something more like float *rawdata = (float 
>>>> *)in_Pts->GetData()->GetVoidPointer()
>>>> and then
>>>>        for (int i=0; i<npoints; i++) points[i] = rawdata[i] - times 
>>>> 3 for x,y,z
>>>>
>>>> any use?
>>>>
>>>> JB
>>>>
>>>>
>>>>
>>>>
>>>>> I still dont get how the GetNextCell works but I cann access the 
>>>>> raw int connectivity array - I guess PolyData::GetPolys::Get*Cell 
>>>>> methods base on it. Unfortunately it doesnt work any faster, 
>>>>> against as promised in the docu. I get ~ 5x better performance 
>>>>> using an ugly glut code on the same dataset. Missed anything?
>>>>> Thanks,
>>>>> Dominik
>>>>>
>>>>> Dominik Szczerba wrote:
>>>>>> Hi,
>>>>>> I am retrieving cells in a polydata using GetCell and it works, 
>>>>>> only very slow. I read I can use GetPolys to get faster, but there 
>>>>>> are no examples and hitting blind just leads me nowhere. I guess 
>>>>>> PolyData::GetPolys::GetCell(id, &N, &ids) should fill ids with 
>>>>>> connectivity array of a cell id, and set N to number of points in 
>>>>>> the cell. Even though it compiles it doenst work. Could someone 
>>>>>> provide me with one line example?
>>>>>> Regards,
>>>>>> Dominik
>>>>>
>>>>
>>>>
>>>
>>
>>
> 

-- 
Dominik Szczerba, Ph.D.
Computer Vision Lab, ETH
http://www.vision.ee.ethz.ch/~domi



More information about the vtkusers mailing list