53 #define ACG_POLYLINENODET_C 57 #include "PolyLineNodeT.hh" 58 #include <ACG/GL/gl.hh> 59 #include <ACG/GL/ShaderCache.hh> 60 #include <ACG/Utils/VSToolsT.hh> 71 template <
class PolyLine>
92 drawMode(DrawModes::WIREFRAME | DrawModes::POINTS );
97 template <
class PolyLine>
105 template <
class PolyLine>
110 for (
unsigned int i=0; i< polyline_.n_vertices(); ++i)
112 _bbMin.
minimize(polyline_.point(i));
113 _bbMax.
maximize(polyline_.point(i));
121 template <
class PolyLine>
126 return (DrawModes::WIREFRAME | DrawModes::POINTS | DrawModes::POINTS_COLORED | POINTS_SPHERES | POINTS_SPHERES_SCREEN | DrawModes::EDGES_COLORED);
133 template <
class PolyLine>
139 if ( polyline_.n_vertices() == 0 )
155 if (_drawMode & DrawModes::POINTS || _drawMode & DrawModes::POINTS_COLORED)
157 vertexDecl_.activateFixedFunction();
160 if( polyline_.vertex_selections_available() && !selectedVertexIndexBuffer_.empty())
167 glDrawElements(GL_POINTS, selectedVertexIndexBuffer_.size(), GL_UNSIGNED_INT, &(selectedVertexIndexBuffer_[0]));
175 if (_drawMode & DrawModes::POINTS_COLORED)
177 vertexDecl_.deactivateFixedFunction();
178 vertexDeclVCol_.activateFixedFunction();
182 glDrawArrays(GL_POINTS, 0, polyline_.n_vertices());
184 if (_drawMode & DrawModes::POINTS_COLORED)
185 vertexDeclVCol_.deactivateFixedFunction();
187 vertexDecl_.deactivateFixedFunction();
191 if (_drawMode & DrawModes::WIREFRAME) {
192 vertexDecl_.activateFixedFunction();
195 if (polyline_.edge_selections_available() && !selectedEdgeIndexBuffer_.empty()) {
201 glDrawElements(GL_LINES, selectedEdgeIndexBuffer_.size(), GL_UNSIGNED_INT, &(selectedEdgeIndexBuffer_[0]));
208 if ( polyline_.is_closed() )
209 glDrawArrays(GL_LINE_STRIP, 0, polyline_.n_vertices() + 1);
211 glDrawArrays(GL_LINE_STRIP, 0, polyline_.n_vertices());
213 vertexDecl_.deactivateFixedFunction();
217 if (_drawMode & DrawModes::EDGES_COLORED) {
218 vertexDecl_.activateFixedFunction();
221 if (polyline_.edge_selections_available() && !selectedEdgeIndexBuffer_.empty()) {
227 glDrawElements(GL_LINES, selectedEdgeIndexBuffer_.size(), GL_UNSIGNED_INT, &(selectedEdgeIndexBuffer_[0]));
232 vertexDecl_.deactivateFixedFunction();
237 vertexDeclECol_.activateFixedFunction();
238 if (polyline_.is_closed())
239 glDrawArrays(GL_LINE_STRIP, 0, polyline_.n_vertices() + 1);
241 glDrawArrays(GL_LINE_STRIP, 0, polyline_.n_vertices());
243 vertexDeclECol_.deactivateFixedFunction();
248 if (polyline_.vertex_normals_available()) {
249 double avg_len = polyline_.n_edges() > 0 ? (polyline_.length() / polyline_.n_edges() * 0.75) : 0;
250 std::vector<Point> ps;
251 for (
unsigned int i = 0; i < polyline_.n_vertices(); ++i) {
252 ps.push_back(polyline_.point(i));
253 ps.push_back(polyline_.point(i) + polyline_.vertex_normal(i) * avg_len);
254 if (polyline_.vertex_binormals_available())
255 ps.push_back(polyline_.point(i) + polyline_.vertex_binormal(i) * avg_len);
266 int stride = polyline_.vertex_binormals_available() ? 3 : 2;
268 for (
unsigned int i = 0; i < polyline_.n_vertices(); ++i) {
269 glArrayElement(stride * i);
270 glArrayElement(stride * i + 1);
274 if (polyline_.vertex_binormals_available()) {
277 for (
unsigned int i = 0; i < polyline_.n_vertices(); ++i) {
278 glArrayElement(stride * i);
279 glArrayElement(stride * i + 2);
293 if (_drawMode & POINTS_SPHERES)
299 if( polyline_.vertex_selections_available())
301 for(
unsigned int i=0; i<polyline_.n_vertices(); ++i)
303 if(polyline_.vertex_selected(i))
314 for(
unsigned int i=0; i<polyline_.n_vertices(); ++i)
319 if (_drawMode & POINTS_SPHERES_SCREEN)
328 if( polyline_.vertex_selections_available())
330 for(
unsigned int i=0; i<polyline_.n_vertices(); ++i)
332 if(polyline_.vertex_selected(i))
340 sphere_->draw(_state, r*l, (
Vec3f)polyline_.point(i));
346 for(
unsigned int i=0; i<polyline_.n_vertices(); ++i)
351 sphere_->draw(_state, r*l, (
Vec3f)polyline_.point(i));
361 template <
class PolyLine>
366 if ( polyline_.n_vertices() == 0 )
374 unsigned int n_end = polyline_.n_edges()+1;
375 if( !polyline_.is_closed()) --n_end;
387 if (drawMode() & DrawModes::POINTS)
388 pick_vertices( _state);
390 if (drawMode() & POINTS_SPHERES)
391 pick_spheres( _state);
393 if (drawMode() & POINTS_SPHERES_SCREEN)
394 pick_spheres_screen( _state);
402 pick_edges(_state, 0);
410 if (drawMode() & DrawModes::POINTS)
411 pick_vertices( _state);
413 if (drawMode() & POINTS_SPHERES)
414 pick_spheres( _state);
416 if (drawMode() & POINTS_SPHERES_SCREEN)
417 pick_spheres_screen( _state);
419 pick_edges( _state, polyline_.n_vertices());
439 template <
class PolyLine>
444 if (!polyline_.n_vertices())
450 glDepthRange(0.0, 0.999999);
453 desc.vertexTemplateFile =
"Picking/pick_vertices_vs.glsl";
454 desc.fragmentTemplateFile =
"Picking/pick_vertices_fs.glsl";
457 if (pickShader && pickShader->
isLinked())
468 vertexDecl_.activateShaderPipeline(pickShader);
475 pickShader->
setUniform(
"pickVertexOffset", pickOffsetIndex);
477 glDrawArrays(GL_POINTS, 0, polyline_.n_vertices());
479 vertexDecl_.deactivateShaderPipeline(pickShader);
487 for (
unsigned int i = 0; i < polyline_.n_vertices(); ++i) {
495 glDepthRange(0.0, 1.0);
499 glPointSize(point_size_old);
506 template <
class PolyLine>
516 for(
unsigned int i=0; i<polyline_.n_vertices(); ++i)
526 template <
class PolyLine>
539 for(
unsigned int i=0; i<polyline_.n_vertices(); ++i)
545 sphere_->draw(_state, r*l, (
Vec3f)polyline_.point(i));
556 template <
class PolyLine>
562 if ( polyline_.n_edges() == 0 )
565 glDepthRange(0.0, 0.999999);
570 desc.vertexTemplateFile =
"Picking/vertex.glsl";
571 desc.fragmentTemplateFile =
"Picking/pick_vertices_fs2.glsl";
575 desc.vertexTemplateFile =
"Picking/pick_vertices_vs.glsl";
576 desc.fragmentTemplateFile =
"Picking/pick_vertices_fs.glsl";
580 if (pickShader && pickShader->
isLinked())
591 vertexDecl_.activateShaderPipeline(pickShader);
598 pickShader->
setUniform(
"pickVertexOffset", pickOffsetIndex);
600 int numIndices = polyline_.n_vertices() + (polyline_.is_closed() ? 1 : 0);
601 glDrawArrays(GL_LINE_STRIP, 0, numIndices);
603 vertexDecl_.deactivateShaderPipeline(pickShader);
615 unsigned int n_end = polyline_.n_edges() + 1;
616 if (!polyline_.is_closed()) --n_end;
618 for (
unsigned int i = 0; i < n_end; ++i) {
621 glArrayElement(i % polyline_.n_vertices());
622 glArrayElement((i + 1) % polyline_.n_vertices());
629 glDepthRange(0.0, 1.0);
635 template <
class PolyLine>
647 size_t curOffset = 12;
650 if (polyline_.vertex_normals_available())
657 if (polyline_.vertex_colors_available())
659 if (_colorSource == 1)
664 if (polyline_.edge_colors_available())
666 if (_colorSource == 2)
673 for (
size_t i = 0; i < customBuffers_.size(); ++i) {
680 curOffset += VertexDeclaration::getElementSize(&tmp);
688 template <
class PolyLine>
695 for (
unsigned int i = 0; i < polyline_.get_num_custom_properties(); ++i) {
697 typename PolyLine::CustomPropertyHandle proph = polyline_.enumerate_custom_property_handles(i);
701 const void* propDataBuf = polyline_.get_custom_property_buffer(proph);
703 typename std::map< typename PolyLine::CustomPropertyHandle, int >::iterator mapEntry = polylinePropMap_.
find(proph);
706 if (mapEntry == polylinePropMap_.end()) {
711 unsigned int propSize = 0;
712 if (polyline_.get_custom_property_shader_binding(proph, &propSize, &desc.
shaderInputName_, &desc.
type_)) {
717 polylinePropMap_[proph] = addCustomBuffer(desc, propDataBuf);
721 setCustomBuffer(mapEntry->second, propDataBuf);
726 setupVertexDeclaration(&vertexDecl_, 0);
727 setupVertexDeclaration(&vertexDeclVCol_, 1);
728 setupVertexDeclaration(&vertexDeclECol_, 2);
733 const unsigned int stride = vertexDecl_.getVertexStride();
735 char* data =
static_cast<char*
>(_buf);
736 size_t bytesWritten = 0;
738 for (
unsigned int i = 0 ; i < polyline_.n_vertices() && bytesWritten + stride <= _bufSize; ++i) {
739 writeVertex(i, data + i * stride);
740 bytesWritten += stride;
743 if (_addLineStripEndVertex && bytesWritten + stride <= _bufSize) {
745 writeVertex(0, data + polyline_.n_vertices() * stride);
746 bytesWritten += stride;
754 template <
class PolyLine>
759 setupVertexDeclaration(&vertexDecl_, 0);
761 const unsigned int stride = vertexDecl_.getVertexStride();
764 size_t bufferSize = stride * (polyline_.n_vertices() + 1);
767 std::vector<char> vboData(bufferSize);
769 if (bufferSize > 0) {
770 size_t bytesWritten = fillVertexBuffer(&vboData[0], bufferSize,
true);
772 if (bytesWritten != bufferSize)
773 std::cerr <<
"PolyLineNode: fill vertex buffer only wrote " << bytesWritten <<
" bytes instead of expected " << bufferSize <<
" bytes" << std::endl;
776 vbo_.upload(bufferSize, &vboData[0], GL_STATIC_DRAW);
781 selectedVertexIndexBuffer_.clear();
784 selectedEdgeIndexBuffer_.clear();
786 for (
unsigned int i = 0 ; i < polyline_.n_vertices(); ++i) {
789 if ( polyline_.vertex_selections_available() && polyline_.vertex_selected(i) )
790 selectedVertexIndexBuffer_.push_back(i);
793 if ( polyline_.edge_selections_available() && polyline_.edge_selected(i) ) {
794 selectedEdgeIndexBuffer_.push_back(i);
795 selectedEdgeIndexBuffer_.push_back( (i + 1) % polyline_.n_vertices() );
806 template <
class PolyLine>
811 const VertexDeclaration* declToUse = _colorSourceVertex ? &vertexDeclVCol_ : &vertexDeclECol_;
814 unsigned char* ucdata = ((
unsigned char*)_dst) + byteOffset;
817 if (_colorSourceVertex)
818 col = polyline_.vertex_color(_vertex);
823 int edgeID = (_vertex + polyline_.n_edges() - 1) % polyline_.n_edges();
824 col = polyline_.edge_color(edgeID);
828 for (
int i = 0; i < 3; ++i)
831 int ival = int(col[i] * 255.0);
832 ival = std::min(std::max(ival, 0), 255);
840 template <
class PolyLine>
846 float* fdata = (
float*)_dst;
849 for (
unsigned int j = 0 ; j < 3 ; ++j)
850 *(fdata++) = polyline_.point(_vertex)[j];
853 if ( polyline_.vertex_normals_available() )
854 for (
unsigned int j = 0 ; j < 3 ; ++j)
855 *(fdata++) = polyline_.vertex_normal(_vertex)[j];
857 if (polyline_.vertex_colors_available())
858 writeVertexColor(_vertex,
true, _dst);
860 if (polyline_.edge_colors_available())
861 writeVertexColor(_vertex,
false, _dst);
865 if (customElementOffset >= 0)
868 for (
unsigned int i = 0; i < customBuffers_.size(); ++i) {
875 if (!elementInputStride)
876 elementInputStride = elementSize;
879 const ACG::VertexElement* ve = vertexDeclVCol_.getElement(i + static_cast<unsigned int>(customElementOffset));
881 const char* src = (
const char*)customBuffers_[i].second;
883 memcpy((
char*)_dst + ve->
getByteOffset(), src + elementInputStride * _vertex, elementSize);
890 template <
class PolyLine>
896 if ( polyline_.n_vertices() == 0 )
902 _state.
enable(GL_COLOR_MATERIAL);
903 _state.
enable(GL_LIGHTING);
906 ro.setMaterial(_mat);
919 ro.debugName =
"PolyLine";
930 for (
unsigned int i = 0; i < _drawMode.
getNumLayers(); ++i) {
944 ro.setMaterial(&localMaterial);
947 switch (props->primitive()) {
949 case ACG::SceneGraph::DrawModes::PRIMITIVE_POINT:
952 ro.debugName =
"polyline.Points.selected";
954 ro.setMaterial(&localMaterial);
962 if (!selectedVertexIndexBuffer_.empty())
964 ro.glDrawElements(GL_POINTS, selectedVertexIndexBuffer_.size(), GL_UNSIGNED_INT, &(selectedVertexIndexBuffer_[0]));
966 applyRenderObjectSettings(props->primitive(), &ro);
972 ro.debugName =
"polyline.Points";
974 ro.setMaterial(&localMaterial);
975 ro.glDrawArrays(GL_POINTS, 0, polyline_.n_vertices());
977 if (props->
colored() && polyline_.vertex_colors_available())
988 applyRenderObjectSettings(props->primitive(), &ro);
994 case ACG::SceneGraph::DrawModes::PRIMITIVE_WIREFRAME:
995 case ACG::SceneGraph::DrawModes::PRIMITIVE_EDGE:
998 ro.debugName =
"polyline.Wireframe.selected";
1000 ro.setMaterial(&localMaterial);
1008 if (!selectedEdgeIndexBuffer_.empty())
1010 ro.glDrawElements(GL_LINES, selectedEdgeIndexBuffer_.size(), GL_UNSIGNED_INT, &(selectedEdgeIndexBuffer_[0]));
1013 applyRenderObjectSettings(props->primitive(), &ro);
1018 ro.debugName =
"polyline.Wireframe";
1020 ro.setMaterial(&localMaterial);
1023 if ( polyline_.is_closed() )
1024 ro.glDrawArrays(GL_LINE_STRIP, 0, polyline_.n_vertices() + 1);
1026 ro.glDrawArrays(GL_LINE_STRIP, 0, polyline_.n_vertices());
1028 if (props->
colored() && polyline_.edge_colors_available())
1038 applyRenderObjectSettings(props->primitive(), &ro);
1045 case ACG::SceneGraph::DrawModes::PRIMITIVE_POLYGON:
1051 bool screenScale = _drawMode & POINTS_SPHERES_SCREEN;
1072 if (polyline_.vertex_selections_available())
1074 ro.debugName =
"polyline.Sphere.selected";
1075 localMaterial.
baseColor(selectionColor);
1076 ro.setMaterial(&localMaterial);
1078 for (
unsigned int i = 0; i < polyline_.n_vertices(); ++i)
1080 if (polyline_.vertex_selected(i))
1086 const Vec3d p = (
Vec3d)polyline_.point(i) - eyePos;
1087 radius = (p | viewDir) * r;
1090 sphere_->addToRenderer(_renderer, &ro, radius, (
Vec3f)polyline_.point(i));
1096 ro.debugName =
"polyline.Sphere";
1098 ro.setMaterial(&localMaterial);
1100 for (
unsigned int i = 0; i < polyline_.n_vertices(); ++i)
1102 if (!polyline_.vertex_selections_available() || !polyline_.vertex_selected(i))
1108 const Vec3d p = (
Vec3d)polyline_.point(i) - eyePos;
1109 radius = (p | viewDir) * r;
1112 sphere_->addToRenderer(_renderer, &ro, radius, (
Vec3f)polyline_.point(i));
1128 template <
class PolyLine>
1134 customBuffers_.
push_back( std::pair<ACG::VertexElement, const void*>(_desc, _buffer) );
1137 return int(customBuffers_.size()-1);
1141 std::cerr <<
"PolyLineNodeT::addCustomBuffer - null pointer buffer" << std::endl;
1148 template <
class PolyLine>
1153 customBuffers_[_id].second = _buffer;
double fovy() const
get field of view in y direction
const Vec4f & diffuse_color() const
get diffuse color
void setVertexStride(unsigned int _stride)
void initFromState(GLState *_glState)
Initializes a RenderObject instance.
Vec3d viewing_direction() const
get viewing ray
const char * shaderInputName_
set shader input name, if usage_ = VERTEX_USAGE_USER_DEFINED otherwise this is set automatically...
void pointSize(float _sz)
set point size (default: 1.0)
Vec3d eye() const
get eye point
float line_width() const
get line width
defined by user via VertexElement::shaderInputName_
unsigned int numElements_
how many elements of type_
double fovy() const
get field of view in y direction
float point_size() const
get point size
void use()
Enables the program object for using.
const void * pointer_
Offset in bytes to the first occurrence of this element in vertex buffer; Or address to vertex data i...
Namespace providing different geometric functions concerning angles.
VectorT< float, 4 > Vec4f
void baseColor(const Vec4f &_c)
set the base color (Sets the baseColor which is the same as the emission(const Vec4f& _c) ) ...
int viewport_height() const
get viewport height
Class to define the vertex input layout.
ShaderGenDesc shaderDesc
Drawmode and other shader params.
size_t pick_current_index() const
Returns the current color picking index (can be used for caching)
vector_type & maximize(const vector_type &_rhs)
maximize values: same as *this = max(*this, _rhs), but faster
GLuint vertexBuffer
VBO, IBO ids, ignored if VAO is provided.
const Vec4f & diffuse_color() const
get diffuse color
VERTEX_USAGE usage_
position, normal, shader input ..
static void vertexPointer(GLint _size, GLenum _type, GLsizei _stride, const GLvoid *_pointer)
replaces glVertexPointer, supports locking
bool isLinked()
Returns if the program object has been succesfully linked.
void setupLineRendering(float _lineWidth, const Vec2f &_screenSize)
Setup rendering of thick lines.
bool colored() const
Are colors used?
bool ACGDLLEXPORT openGLVersionTest(const int _major, const int _minor)
void push_back(BaseNode *_node)
Insert _node at the end of the list of children.
PickTarget
What target to use for picking.
static void disable(GLenum _cap, bool _warnRemoved=true)
replaces glDisable, but supports locking
Description of one vertex element.
void setByteOffset(unsigned int _offset)
static ShaderCache * getInstance()
Return instance of the ShaderCache singleton.
void addElement(const VertexElement *_pElement)
void setupPointRendering(float _pointSize, const Vec2f &_screenSize)
Setup rendering of circle points.
static void disableClientState(GLenum _cap)
replaces glDisableClientState, supports locking
void set_point_size(float _f)
set point size
bool pick_set_maximum(size_t _idx)
Set the maximal number of primitives/components of your object.
static void enableClientState(GLenum _cap)
replaces glEnableClientState, supports locking
int viewport_height() const
get viewport height
float point_size() const
get point size
vector_type & minimize(const vector_type &_rhs)
minimize values: same as *this = min(*this, _rhs), but faster
GLSL::Program * getProgram(const ShaderGenDesc *_desc, const std::vector< unsigned int > &_mods)
Query a dynamically generated program from cache.
void setUniform(const char *_name, GLint _value)
Set int uniform to specified value.
const Vec4f & ambient_color() const
get ambient color
PolyLineNodeT(PolyLine &_pl, BaseNode *_parent=0, std::string _name="<PolyLineNode>")
Constructor.
int viewport_width() const
get viewport width
const VertexDeclaration * vertexDecl
Defines the vertex buffer layout, ignored if VAO is provided.
const DrawMode & addDrawMode(const std::string &_name, bool _propertyBased)
Add a custom DrawMode.
unsigned int getByteOffset() const
void disable()
Resets to standard rendering pipeline.
DrawModeProperties stores a set of properties that defines, how to render an object.
void set_color(const Vec4f &_col)
set color
virtual void addRenderObject(RenderObject *_renderObject)
Callback for the scenegraph nodes, which send new render objects via this function.
int priority
Priority to allow sorting of objects.
Vec3d viewing_direction() const
get viewing ray
void set_line_width(float _f)
set line width
static size_t getElementSize(const VertexElement *_pElement)
void pick_set_name(size_t _idx)
sets the current name/color (like glLoadName(_idx))
ChildIter find(BaseNode *_node)
unsigned int type_
GL_FLOAT, GL_UNSIGNED_BYTE, GL_INT, ...
const GLMatrixd & modelview() const
get modelview matrix
static void enable(GLenum _cap, bool _warnRemoved=true)
replaces glEnable, but supports locking
void setupShaderGenFromDrawmode(const SceneGraph::DrawModes::DrawModeProperties *_props)
Fills out ShaderGenDesc parameters based on Drawmode properties.
float line_width() const
get line width
const VertexElement * findElementByUsage(VERTEX_USAGE _usage) const
const DrawModeProperties * getLayer(unsigned int _i) const
returns the property set at layer i
const GLMatrixd & projection() const
get projection matrix
Interface class between scenegraph and renderer.
size_t getNumLayers() const
returns the layer count
static void bindBuffer(GLenum _target, GLuint _buffer)
replaces glBindBuffer, supports locking
Vec3d eye() const
get eye point
const Vec4f & ambient_color() const
get ambient color