source: trunk/packages/vizservers/vtkvis/RpContour2D.cpp @ 2238

Last change on this file since 2238 was 2194, checked in by ldelgass, 14 years ago

Fix pan/zoom for VTK contours, add command to control data range mapping for
multiple datasets. Still need to fix 3D panning, allow absolute rotation/
orientation of the camera.

  • Property svn:eol-style set to native
File size: 6.3 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 <vtkContourFilter.h>
9#include <vtkPolyDataMapper.h>
10#include <vtkProperty.h>
11
12#include "RpContour2D.h"
13#include "Trace.h"
14
15using namespace Rappture::VtkVis;
16
17Contour2D::Contour2D() :
18    _dataSet(NULL),
19    _numContours(0),
20    _edgeWidth(1.0f),
21    _opacity(1.0)
22{
23    _dataRange[0] = 0;
24    _dataRange[1] = 1;
25    _edgeColor[0] = 0;
26    _edgeColor[1] = 0;
27    _edgeColor[2] = 0;
28}
29
30Contour2D::~Contour2D()
31{
32#ifdef WANT_TRACE
33    if (_dataSet != NULL)
34        TRACE("Deleting Contour2D for %s", _dataSet->getName().c_str());
35    else
36        TRACE("Deleting Contour2D with NULL DataSet");
37#endif
38}
39
40/**
41 * \brief Specify input DataSet used to extract contours
42 */
43void Contour2D::setDataSet(DataSet *dataSet)
44{
45    if (_dataSet != dataSet) {
46        _dataSet = dataSet;
47
48        if (_dataSet != NULL) {
49            double dataRange[2];
50            _dataSet->getDataRange(dataRange);
51            _dataRange[0] = dataRange[0];
52            _dataRange[1] = dataRange[1];
53        }
54
55        update();
56    }
57}
58
59/**
60 * \brief Returns the DataSet this Contour2D renders
61 */
62DataSet *Contour2D::getDataSet()
63{
64    return _dataSet;
65}
66
67/**
68 * \brief Get the VTK Actor for the contour lines
69 */
70vtkActor *Contour2D::getActor()
71{
72    return _contourActor;
73}
74
75/**
76 * \brief Create and initialize a VTK actor to render isolines
77 */
78void Contour2D::initActor()
79{
80    if (_contourActor == NULL) {
81        _contourActor = vtkSmartPointer<vtkActor>::New();
82        _contourActor->GetProperty()->EdgeVisibilityOn();
83        _contourActor->GetProperty()->SetEdgeColor(_edgeColor[0], _edgeColor[1], _edgeColor[2]);
84        _contourActor->GetProperty()->SetLineWidth(_edgeWidth);
85        _contourActor->GetProperty()->SetOpacity(_opacity);
86        _contourActor->GetProperty()->LightingOff();
87    }
88}
89
90/**
91 * \brief Internal method to re-compute contours after a state change
92 */
93void Contour2D::update()
94{
95    if (_dataSet == NULL) {
96        return;
97    }
98
99    initActor();
100
101    // Contour filter to generate isolines
102    if (_contourFilter == NULL) {
103        _contourFilter = vtkSmartPointer<vtkContourFilter>::New();
104    }
105
106    _contourFilter->SetInput(_dataSet->getVtkDataSet());
107
108    _contourFilter->ComputeNormalsOff();
109    _contourFilter->ComputeGradientsOff();
110
111    // Speed up multiple contour computation at cost of extra memory use
112    if (_numContours > 1) {
113        _contourFilter->UseScalarTreeOn();
114    } else {
115        _contourFilter->UseScalarTreeOff();
116    }
117
118    _contourFilter->SetNumberOfContours(_numContours);
119
120    if (_contours.empty()) {
121        // Evenly spaced isovalues
122        _contourFilter->GenerateValues(_numContours, _dataRange[0], _dataRange[1]);
123    } else {
124        // User-supplied isovalues
125        for (int i = 0; i < _numContours; i++) {
126            _contourFilter->SetValue(i, _contours[i]);
127        }
128    }
129    if (_contourMapper == NULL) {
130        _contourMapper = vtkSmartPointer<vtkPolyDataMapper>::New();
131        _contourMapper->SetResolveCoincidentTopologyToPolygonOffset();
132        _contourActor->SetMapper(_contourMapper);
133        _contourMapper->SetInput(_contourFilter->GetOutput());
134    }
135}
136
137/**
138 * \brief Specify number of evenly spaced contour lines to render
139 *
140 * Will override any existing contours
141 */
142void Contour2D::setContours(int numContours)
143{
144    _contours.clear();
145    _numContours = numContours;
146
147    if (_dataSet != NULL) {
148        double dataRange[2];
149        _dataSet->getDataRange(dataRange);
150        _dataRange[0] = dataRange[0];
151        _dataRange[1] = dataRange[1];
152    }
153
154    update();
155}
156
157/**
158 * \brief Specify number of evenly spaced contour lines to render
159 * between the given range (including range endpoints)
160 *
161 * Will override any existing contours
162 */
163void Contour2D::setContours(int numContours, double range[2])
164{
165    _contours.clear();
166    _numContours = numContours;
167
168    _dataRange[0] = range[0];
169    _dataRange[1] = range[1];
170
171    update();
172}
173
174/**
175 * \brief Specify an explicit list of contour isovalues
176 *
177 * Will override any existing contours
178 */
179void Contour2D::setContourList(const std::vector<double>& contours)
180{
181    _contours = contours;
182    _numContours = (int)_contours.size();
183
184    update();
185}
186
187/**
188 * \brief Get the number of contours
189 */
190int Contour2D::getNumContours() const
191{
192    return _numContours;
193}
194
195/**
196 * \brief Get the contour list (may be empty if number of contours
197 * was specified in place of a list)
198 */
199const std::vector<double>& Contour2D::getContourList() const
200{
201    return _contours;
202}
203
204/**
205 * \brief Turn on/off rendering of this contour set
206 */
207void Contour2D::setVisibility(bool state)
208{
209    if (_contourActor != NULL) {
210        _contourActor->SetVisibility((state ? 1 : 0));
211    }
212}
213
214/**
215 * \brief Get visibility state of the contour set
216 *
217 * \return Is contour set visible?
218 */
219bool Contour2D::getVisibility() const
220{
221    if (_contourActor == NULL) {
222        return false;
223    } else {
224        return (_contourActor->GetVisibility() != 0);
225    }
226}
227
228/**
229 * \brief Set opacity used to render contour lines
230 */
231void Contour2D::setOpacity(double opacity)
232{
233    _opacity = opacity;
234    if (_contourActor != NULL)
235        _contourActor->GetProperty()->SetOpacity(opacity);
236}
237
238/**
239 * \brief Set RGB color of contour lines
240 */
241void Contour2D::setEdgeColor(float color[3])
242{
243    _edgeColor[0] = color[0];
244    _edgeColor[1] = color[1];
245    _edgeColor[2] = color[2];
246    if (_contourActor != NULL)
247        _contourActor->GetProperty()->SetEdgeColor(_edgeColor[0], _edgeColor[1], _edgeColor[2]);
248}
249
250/**
251 * \brief Set pixel width of contour lines (may be a no-op)
252 */
253void Contour2D::setEdgeWidth(float edgeWidth)
254{
255    _edgeWidth = edgeWidth;
256    if (_contourActor != NULL)
257        _contourActor->GetProperty()->SetLineWidth(_edgeWidth);
258}
259
260/**
261 * \brief Set a group of world coordinate planes to clip rendering
262 *
263 * Passing NULL for planes will remove all cliping planes
264 */
265void Contour2D::setClippingPlanes(vtkPlaneCollection *planes)
266{
267    if (_contourMapper != NULL) {
268        _contourMapper->SetClippingPlanes(planes);
269    }
270}
271
272/**
273 * \brief Turn on/off lighting of this object
274 */
275void Contour2D::setLighting(bool state)
276{
277    if (_contourActor != NULL)
278        _contourActor->GetProperty()->SetLighting((state ? 1 : 0));
279}
Note: See TracBrowser for help on using the repository browser.