Developer Documentation
BaseNode.cc
1 /*===========================================================================*\
2  * *
3  * OpenFlipper *
4  * Copyright (c) 2001-2015, RWTH-Aachen University *
5  * Department of Computer Graphics and Multimedia *
6  * All rights reserved. *
7  * www.openflipper.org *
8  * *
9  *---------------------------------------------------------------------------*
10  * This file is part of OpenFlipper. *
11  *---------------------------------------------------------------------------*
12  * *
13  * Redistribution and use in source and binary forms, with or without *
14  * modification, are permitted provided that the following conditions *
15  * are met: *
16  * *
17  * 1. Redistributions of source code must retain the above copyright notice, *
18  * this list of conditions and the following disclaimer. *
19  * *
20  * 2. Redistributions in binary form must reproduce the above copyright *
21  * notice, this list of conditions and the following disclaimer in the *
22  * documentation and/or other materials provided with the distribution. *
23  * *
24  * 3. Neither the name of the copyright holder nor the names of its *
25  * contributors may be used to endorse or promote products derived from *
26  * this software without specific prior written permission. *
27  * *
28  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS *
29  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED *
30  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A *
31  * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER *
32  * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, *
33  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, *
34  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR *
35  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF *
36  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING *
37  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS *
38  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. *
39  * *
40 \*===========================================================================*/
41 
42 
43 
44 
45 
46 
47 //=============================================================================
48 //
49 // CLASS BaseNode - IMPLEMENTATION
50 //
51 //=============================================================================
52 
53 
54 //== INCLUDES =================================================================
55 
56 #include "BaseNode.hh"
57 
58 
59 //== NAMESPACES ===============================================================
60 
61 namespace ACG {
62 namespace SceneGraph {
63 
64 
65 //== IMPLEMENTATION ==========================================================
66 
67 
68 unsigned int BaseNode::last_id_used__ = 0;
69 
70 
71 //----------------------------------------------------------------------------
72 
73 
75 BaseNode(BaseNode* _parent, std::string _name)
76  : multipassStatus_(ALLPASSES),
77  multipassNode_(PASS_1),
78  parent_(_parent),
79  name_(_name),
80  status_(Active),
81  drawMode_(DrawModes::DEFAULT),
82  pickingEnabled_(true),
83  dirty_ (false),
84  traverseMode_ (BaseNode::NodeFirst),
85  uniformPool_(0),
86  renderModifier_(0)
87 {
88  id_ = ++last_id_used__;
89  if (_parent!=0) _parent->push_back(this);
90 
92 }
93 
94 
95 //----------------------------------------------------------------------------
96 
97 
99 BaseNode(BaseNode* _parent, BaseNode* _child, std::string _name)
100  : multipassStatus_(ALLPASSES),
101  multipassNode_(PASS_1),
102  parent_(_parent),
103  name_(_name),
104  status_(Active),
105  drawMode_(DrawModes::DEFAULT),
106  pickingEnabled_(true),
107  dirty_ (false),
109 {
110  assert(_parent != 0 && _child != 0);
111 
112  id_ = ++last_id_used__;
113 
114  _parent->push_back(this);
115  _child->set_parent(this);
116 
118 }
119 
120 
121 //----------------------------------------------------------------------------
122 
123 
125 {
126  // remove myself from parent's children
127  if (parent_!=0)
128  {
129  ChildIter me(parent_->find(this));
130  assert(me != parent_->childrenEnd());
131  parent_->remove(me);
132  }
133 
134 
135  // remove me (as parent) from my children
136  for (BaseNode::ChildIter cIt=childrenBegin(); cIt!=childrenEnd(); ++cIt)
137  (*cIt)->parent_ = 0;
138 }
139 
140 
141 //----------------------------------------------------------------------------
142 
143 
144 void
147 {
148  if (parent_)
149  {
150  ChildIter me(parent_->find(this));
151  if (me != parent_->childrenEnd())
152  parent_->remove(me);
153  }
154 
155  parent_ = _parent;
156 
157  if (parent_)
158  {
159  ChildIter me(parent_->find(this));
160  if (me == parent_->childrenEnd())
161  parent_->push_back(this);
162  }
163 }
164 
165 
166 //----------------------------------------------------------------------------
167 
168 
169 void
171 {
172  while (!children_.empty())
173  children_.front()->delete_subtree();
174  delete this;
175 }
176 
177 //----------------------------------------------------------------------------
178 
179 void
180 BaseNode::enterPick(GLState& _state, PickTarget /*_target*/, const DrawModes::DrawMode& _drawMode)
181 {
182  enter (_state, _drawMode);
183 }
184 
185 //----------------------------------------------------------------------------
186 
187 void
188 BaseNode::leavePick(GLState& _state, PickTarget /*_target*/, const DrawModes::DrawMode& _drawMode)
189 {
190  leave (_state, _drawMode);
191 }
192 
193 //----------------------------------------------------------------------------
194 
195 void BaseNode::multipassStatusSetActive(const unsigned int _i, bool _active) {
196 
197  if ( _i == NOPASS ) {
198  multipassStatus_ = NOPASS;
199  } else if ( _i == ALLPASSES ) {
200  if ( _active )
201  multipassStatus_ = ALLPASSES;
202  else
203  multipassStatus_ = NOPASS;
204  } else {
205  if ( _active )
206  multipassStatus_ |= (1 << (_i == 0 ? 0 : _i - 1));
207  else
208  multipassStatus_ &= ~(1 << (_i == 0 ? 0 : _i - 1));
209  }
210 
211 }
212 
213 //----------------------------------------------------------------------------
214 
215 bool BaseNode::multipassStatusActive(const unsigned int _i) const {
216 
217  if ( multipassStatus_ == NOPASS )
218  return false;
219  else if ( multipassStatus_ & ALLPASSES )
220  return true;
221  else
222  return ((1 << (_i == 0 ? 0 : _i - 1)) & multipassStatus_) != 0;
223 
224 }
225 
226 //----------------------------------------------------------------------------
227 
228 void BaseNode::multipassNodeSetActive(const unsigned int _i , bool _active) {
229 
230  if ( _i == NOPASS ) {
231  multipassNode_ = NOPASS;
232  } else if ( _i == ALLPASSES ) {
233  if ( _active )
234  multipassNode_ = ALLPASSES;
235  else
236  multipassNode_ = NOPASS;
237  } else {
238  if ( _active )
239  multipassNode_ |= (1 << (_i == 0 ? 0 : _i - 1));
240  else
241  multipassNode_ &= ~(1 << (_i == 0 ? 0 : _i - 1));
242  }
243 
244 }
245 
246 //----------------------------------------------------------------------------
247 
248 bool BaseNode::multipassNodeActive(const unsigned int _i) const {
249 
250  if ( multipassNode_ == NOPASS )
251  return false;
252  else if ( multipassNode_ & ALLPASSES )
253  return true;
254  else
255  return ((1 << (_i == 0 ? 0 : _i - 1)) & multipassNode_) != 0;
256 
257 }
258 
259 //----------------------------------------------------------------------------
260 
261 void BaseNode::setRenderObjectShaders( const std::string& _vertexShaderFile, const std::string& _geometryShaderFile, const std::string& _fragmentShaderFile, bool _relativePaths, ACG::SceneGraph::DrawModes::DrawModePrimitive _primitiveType ) {
262 
263  ShaderSet s;
264  s.vs_ = _vertexShaderFile;
265  s.gs_ = _geometryShaderFile;
266  s.fs_ = _fragmentShaderFile;
267  s.relativePaths_ = _relativePaths;
268 
269  shaderSettings_[_primitiveType] = s;
270 }
271 
272 //----------------------------------------------------------------------------
273 
274 void BaseNode::setRenderObjectShaders( const std::string& _vertexShaderFile, const std::string& _tessControlShaderFile, const std::string& _tessEvalShaderFile, const std::string& _geometryShaderFile, const std::string& _fragmentShaderFile, bool _relativePaths, ACG::SceneGraph::DrawModes::DrawModePrimitive _primitiveType ) {
275 
276  ShaderSet s;
277  s.vs_ = _vertexShaderFile;
278  s.gs_ = _geometryShaderFile;
279  s.fs_ = _fragmentShaderFile;
280  s.tcs_ = _tessControlShaderFile;
281  s.tes_ = _tessEvalShaderFile;
282  s.relativePaths_ = _relativePaths;
283 
284  shaderSettings_[_primitiveType] = s;
285 }
286 
287 //----------------------------------------------------------------------------
288 
289 void BaseNode::setRenderObjectTexture( int _samplerSlot, GLuint _texId, GLenum _texType ) {
290 
292  t.id = _texId;
293  t.type = _texType;
294  t.shadow = false;
295 
296  textureSettings_[_samplerSlot] = t;
297 }
298 
299 //----------------------------------------------------------------------------
300 
302 
303  // Copy texture settings
304  for (std::map<int, RenderObject::Texture>::const_iterator it = textureSettings_.begin(); it != textureSettings_.end(); ++it)
305  _obj->addTexture(it->second, size_t(it->first), false);
306 
307  // Copy uniforms from provided pool
308  if (uniformPool_)
310 
311 
312 std::map<DrawModes::DrawModePrimitive, ShaderSet>::const_iterator shaderSet = shaderSettings_.find(_primitive);
313 
314  bool defaultShaders = shaderSet == shaderSettings_.end();
315 
316  if (!defaultShaders) {
317 
318  // prepend openflipper shader dir
319  if (shaderSet->second.relativePaths_) {
320  _obj->shaderDesc.tessControlTemplateFile =
321  _obj->shaderDesc.tessEvaluationTemplateFile =
322  _obj->shaderDesc.vertexTemplateFile =
323  _obj->shaderDesc.geometryTemplateFile =
324  _obj->shaderDesc.fragmentTemplateFile = ShaderProgGenerator::getShaderDir();
325  }
326 
327  _obj->shaderDesc.vertexTemplateFile += shaderSet->second.vs_.c_str();
328  _obj->shaderDesc.tessControlTemplateFile += shaderSet->second.tcs_.c_str();
329  _obj->shaderDesc.tessEvaluationTemplateFile += shaderSet->second.tes_.c_str();
330  _obj->shaderDesc.geometryTemplateFile += shaderSet->second.gs_.c_str();
331  _obj->shaderDesc.fragmentTemplateFile += shaderSet->second.fs_.c_str();
332  }
333 
334  if (renderModifier_)
335  renderModifier_->apply(_obj);
336 }
337 
338 //=============================================================================
339 } // namespace SceneGraph
340 } // namespace ACG
341 //=============================================================================
Namespace providing different geometric functions concerning angles.
void addTexture(const Texture &_t)
adds a texture to stage RenderObjects::numTextures()
std::map< DrawModes::DrawModePrimitive, ShaderSet > shaderSettings_
shader settings for primitive modes
bool multipassStatusActive(const unsigned int _i) const
Get multipass status to traverse in a specific pass.
Definition: BaseNode.cc:215
void push_back(BaseNode *_node)
Insert _node at the end of the list of children.
virtual void leave(GLState &, const DrawModes::DrawMode &)
std::vector< BaseNode * > children_
list of children
DrawModePrimitive
Primitive mode of a mesh.
Definition: DrawModes.hh:118
void multipassStatusSetActive(const unsigned int _i, bool _active)
Set multipass status to traverse in a specific pass.
Definition: BaseNode.cc:195
Interface class between scenegraph and renderer.
Definition: RenderObject.hh:98
void addUniformPool(const GLSL::UniformPool &_pool)
add all uniforms from a pool
bool dirty_
Flag indicating that the node has to be redrawn.
void setRenderObjectTexture(int _samplerSlot, GLuint _texId, GLenum _texType=GL_TEXTURE_2D)
Set textures for shader based rendering.
Definition: BaseNode.cc:289
BaseNode * parent_
pointer to parent node
std::map< int, RenderObject::Texture > textureSettings_
texture settings for shader based rendering
bool multipassNodeActive(const unsigned int _i) const
Get Node status to traverse in a specific pass.
Definition: BaseNode.cc:248
BaseNode(BaseNode *_parent=0, std::string _name="<unknown>")
Default constructor.
virtual void leavePick(GLState &_state, PickTarget _target, const DrawModes::DrawMode &_drawMode)
Definition: BaseNode.cc:188
virtual void enterPick(GLState &_state, PickTarget _target, const DrawModes::DrawMode &_drawMode)
Definition: BaseNode.cc:180
std::vector< BaseNode * >::iterator ChildIter
allows to iterate over children
virtual void apply(RenderObject *_obj)=0
apply the modifier
static unsigned int last_id_used__
used to provide unique IDs to nodes
RenderObjectModifier * renderModifier_
render-object modifier
static unsigned int last_id_used__
used to provide unique IDs to nodes
Definition: BaseNode.hh:722
void applyRenderObjectSettings(DrawModes::DrawModePrimitive _primitive, RenderObject *_obj) const
Set shaders, textures and uniforms as provided by user to a render-object.
Definition: BaseNode.cc:301
static QString getShaderDir()
virtual void enter(GLState &, const DrawModes::DrawMode &)
ChildIter childrenBegin()
Returns: begin-iterator of children.
ShaderGenDesc shaderDesc
Drawmode and other shader params.
BaseNode(BaseNode *_parent=0, std::string _name="<unknown>")
Default constructor.
Definition: BaseNode.cc:75
Texture to be used.
void setRenderObjectShaders(const std::string &_vertexShaderFile, const std::string &_geometryShaderFile, const std::string &_fragmentShaderFile, bool _relativePaths=true, DrawModes::DrawModePrimitive _primitiveType=DrawModes::PRIMITIVE_POLYGON)
Set custom shaders.
Definition: BaseNode.cc:261
void multipassNodeSetActive(const unsigned int _i, bool _active)
Set Node status to traverse in a specific pass.
Definition: BaseNode.cc:228
void delete_subtree()
Delete the whole subtree of this node.
Definition: BaseNode.cc:170
ChildIter childrenEnd()
Returns: end-iterator of children.
DrawModes::DrawMode drawMode_
private draw mode
Execute action on node first and then on its children.
std::vector< BaseNode * >::iterator ChildIter
allows to iterate over children
Definition: BaseNode.hh:286
void initializeDefaultDrawModes(void)
Definition: DrawModes.cc:639
const GLSL::UniformPool * uniformPool_
user provided uniform pool for shader constants
void set_parent(BaseNode *_parent)
Set the parent of this node.
Definition: BaseNode.cc:146