source: trunk/packages/vizservers/vtkvis/RpPseudoColor.cpp @ 2263

Last change on this file since 2263 was 2261, checked in by ldelgass, 13 years ago

Add GPU volume rendering support to vtkvis render server

  • Property svn:eol-style set to native
File size: 8.2 KB
Line 
1/* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- */
2/*
3 * Copyright (C) 2011, Purdue Research Foundation
4 *
5 * Author: Leif Delgass <ldelgass@purdue.edu>
6 */
7
8#include <cassert>
9
10#include <vtkDataSet.h>
11#include <vtkDataSetMapper.h>
12#include <vtkUnstructuredGrid.h>
13#include <vtkProperty.h>
14#include <vtkPointData.h>
15#include <vtkImageData.h>
16#include <vtkLookupTable.h>
17#include <vtkDelaunay2D.h>
18#include <vtkDelaunay3D.h>
19#include <vtkGaussianSplatter.h>
20#include <vtkExtractVOI.h>
21#include <vtkDataSetSurfaceFilter.h>
22
23#include "RpPseudoColor.h"
24#include "Trace.h"
25
26using namespace Rappture::VtkVis;
27
28PseudoColor::PseudoColor() :
29    _dataSet(NULL),
30    _opacity(1.0),
31    _edgeWidth(1.0)
32{
33    _edgeColor[0] = 0.0;
34    _edgeColor[1] = 0.0;
35    _edgeColor[2] = 0.0;
36}
37
38PseudoColor::~PseudoColor()
39{
40#ifdef WANT_TRACE
41    if (_dataSet != NULL)
42        TRACE("Deleting PseudoColor for %s", _dataSet->getName().c_str());
43    else
44        TRACE("Deleting PseudoColor with NULL DataSet");
45#endif
46}
47
48/**
49 * \brief Specify input DataSet with scalars to colormap
50 *
51 * Currently the DataSet must be image data (2D uniform grid)
52 */
53void PseudoColor::setDataSet(DataSet *dataSet)
54{
55    if (_dataSet != dataSet) {
56        _dataSet = dataSet;
57        update();
58    }
59}
60
61/**
62 * \brief Returns the DataSet this PseudoColor renders
63 */
64DataSet *PseudoColor::getDataSet()
65{
66    return _dataSet;
67}
68
69/**
70 * \brief Internal method to set up color mapper after a state change
71 */
72void PseudoColor::update()
73{
74    if (_dataSet == NULL)
75        return;
76
77    vtkDataSet *ds = _dataSet->getVtkDataSet();
78
79    double dataRange[2];
80    _dataSet->getDataRange(dataRange);
81
82    // Mapper, actor to render color-mapped data set
83    if (_dsMapper == NULL) {
84        _dsMapper = vtkSmartPointer<vtkDataSetMapper>::New();
85    }
86
87    vtkPolyData *pd = vtkPolyData::SafeDownCast(ds);
88    if (pd) {
89        // DataSet is a vtkPolyData
90        if (pd->GetNumberOfLines() == 0 &&
91            pd->GetNumberOfPolys() == 0 &&
92            pd->GetNumberOfStrips() == 0) {
93            // DataSet is a point cloud
94            if (_dataSet->is2D()) {
95#if 0
96                vtkSmartPointer<vtkDelaunay2D> mesher = vtkSmartPointer<vtkDelaunay2D>::New();
97                mesher->SetInput(pd);
98                pd = mesher->GetOutput();
99#else
100                vtkSmartPointer<vtkGaussianSplatter> splatter = vtkSmartPointer<vtkGaussianSplatter>::New();
101                splatter->SetInput(pd);
102                int dims[3];
103                splatter->GetSampleDimensions(dims);
104                TRACE("Sample dims: %d %d %d", dims[0], dims[1], dims[2]);
105                dims[2] = 3;
106                splatter->SetSampleDimensions(dims);
107                double bounds[6];
108                splatter->Update();
109                splatter->GetModelBounds(bounds);
110                TRACE("Model bounds: %g %g %g %g %g %g",
111                      bounds[0], bounds[1],
112                      bounds[2], bounds[3],
113                      bounds[4], bounds[5]);
114                vtkSmartPointer<vtkExtractVOI> slicer = vtkSmartPointer<vtkExtractVOI>::New();
115                slicer->SetInput(splatter->GetOutput());
116                slicer->SetVOI(0, dims[0]-1, 0, dims[1]-1, 1, 1);
117                slicer->SetSampleRate(1, 1, 1);
118                vtkSmartPointer<vtkDataSetSurfaceFilter> gf = vtkSmartPointer<vtkDataSetSurfaceFilter>::New();
119                gf->SetInput(slicer->GetOutput());
120                gf->Update();
121                pd = gf->GetOutput();
122#endif
123                assert(pd);
124                _dsMapper->SetInput(pd);
125            } else {
126                vtkSmartPointer<vtkDelaunay3D> mesher = vtkSmartPointer<vtkDelaunay3D>::New();
127                mesher->SetInput(pd);
128                vtkSmartPointer<vtkDataSetSurfaceFilter> gf = vtkSmartPointer<vtkDataSetSurfaceFilter>::New();
129                gf->SetInput(mesher->GetOutput());
130                gf->Update();
131                pd = gf->GetOutput();
132                assert(pd);
133                _dsMapper->SetInput(pd);
134             }
135        } else {
136            // DataSet is a vtkPolyData with lines and/or polygons
137            _dsMapper->SetInput(ds);
138        }
139    } else {
140        TRACE("Generating surface for data set");
141        // DataSet is NOT a vtkPolyData
142        vtkSmartPointer<vtkDataSetSurfaceFilter> gf = vtkSmartPointer<vtkDataSetSurfaceFilter>::New();
143        gf->SetInput(ds);
144        gf->Update();
145        pd = gf->GetOutput();
146        assert(pd);
147        _dsMapper->SetInput(pd);
148    }
149
150    //_dsMapper->StaticOn();
151
152    if (ds->GetPointData() == NULL ||
153        ds->GetPointData()->GetScalars() == NULL) {
154        ERROR("No scalar point data in dataset %s", _dataSet->getName().c_str());
155        if (_lut == NULL) {
156            _lut = vtkSmartPointer<vtkLookupTable>::New();
157        }
158    } else {
159        vtkLookupTable *lut = ds->GetPointData()->GetScalars()->GetLookupTable();
160        TRACE("Data set scalars lookup table: %p\n", lut);
161        if (_lut == NULL) {
162            if (lut)
163                _lut = lut;
164            else
165                _lut = vtkSmartPointer<vtkLookupTable>::New();
166        }
167    }
168
169    _lut->SetRange(dataRange);
170
171    _dsMapper->UseLookupTableScalarRangeOn();
172    _dsMapper->SetLookupTable(_lut);
173    //_dsMapper->InterpolateScalarsBeforeMappingOn();
174
175    initProp();
176    _dsActor->SetMapper(_dsMapper);
177}
178
179/**
180 * \brief Get the VTK Prop for the colormapped dataset
181 */
182vtkProp *PseudoColor::getProp()
183{
184    return _dsActor;
185}
186
187/**
188 * \brief Create and initialize a VTK Prop to render the colormapped dataset
189 */
190void PseudoColor::initProp()
191{
192    if (_dsActor == NULL) {
193        _dsActor = vtkSmartPointer<vtkActor>::New();
194        _dsActor->GetProperty()->SetOpacity(_opacity);
195        _dsActor->GetProperty()->SetEdgeColor(_edgeColor[0], _edgeColor[1], _edgeColor[2]);
196        _dsActor->GetProperty()->SetLineWidth(_edgeWidth);
197        _dsActor->GetProperty()->EdgeVisibilityOff();
198    }
199}
200
201/**
202 * \brief Get the VTK colormap lookup table in use
203 */
204vtkLookupTable *PseudoColor::getLookupTable()
205{
206    return _lut;
207}
208
209/**
210 * \brief Associate a colormap lookup table with the DataSet
211 */
212void PseudoColor::setLookupTable(vtkLookupTable *lut)
213{
214    if (lut == NULL) {
215        _lut = vtkSmartPointer<vtkLookupTable>::New();
216    } else {
217        _lut = lut;
218    }
219
220    if (_dsMapper != NULL) {
221        _dsMapper->UseLookupTableScalarRangeOn();
222        _dsMapper->SetLookupTable(_lut);
223    }
224}
225
226/**
227 * \brief Turn on/off rendering of this colormapped dataset
228 */
229void PseudoColor::setVisibility(bool state)
230{
231    if (_dsActor != NULL) {
232        _dsActor->SetVisibility((state ? 1 : 0));
233    }
234}
235
236/**
237 * \brief Get visibility state of the colormapped dataset
238 *
239 * \return Is PseudoColor visible?
240 */
241bool PseudoColor::getVisibility()
242{
243    if (_dsActor == NULL) {
244        return false;
245    } else {
246        return (_dsActor->GetVisibility() != 0);
247    }
248}
249
250/**
251 * \brief Set opacity used to render the colormapped dataset
252 */
253void PseudoColor::setOpacity(double opacity)
254{
255    _opacity = opacity;
256    if (_dsActor != NULL)
257        _dsActor->GetProperty()->SetOpacity(opacity);
258}
259
260/**
261 * \brief Turn on/off rendering of mesh edges
262 */
263void PseudoColor::setEdgeVisibility(bool state)
264{
265    if (_dsActor != NULL) {
266        _dsActor->GetProperty()->SetEdgeVisibility((state ? 1 : 0));
267    }
268}
269
270/**
271 * \brief Set RGB color of polygon edges
272 */
273void PseudoColor::setEdgeColor(float color[3])
274{
275    _edgeColor[0] = color[0];
276    _edgeColor[1] = color[1];
277    _edgeColor[2] = color[2];
278    if (_dsActor != NULL)
279        _dsActor->GetProperty()->SetEdgeColor(_edgeColor[0], _edgeColor[1], _edgeColor[2]);
280}
281
282/**
283 * \brief Set pixel width of polygon edges (may be a no-op)
284 */
285void PseudoColor::setEdgeWidth(float edgeWidth)
286{
287    _edgeWidth = edgeWidth;
288    if (_dsActor != NULL)
289        _dsActor->GetProperty()->SetLineWidth(_edgeWidth);
290}
291
292/**
293 * \brief Set a group of world coordinate planes to clip rendering
294 *
295 * Passing NULL for planes will remove all cliping planes
296 */
297void PseudoColor::setClippingPlanes(vtkPlaneCollection *planes)
298{
299    if (_dsMapper != NULL) {
300        _dsMapper->SetClippingPlanes(planes);
301    }
302}
303
304/**
305 * \brief Turn on/off lighting of this object
306 */
307void PseudoColor::setLighting(bool state)
308{
309    if (_dsActor != NULL)
310        _dsActor->GetProperty()->SetLighting((state ? 1 : 0));
311}
Note: See TracBrowser for help on using the repository browser.