// Created on: 2011-07-13
// Created by: Sergey ZERCHANINOV
-// Copyright (c) 2011-2012 OPEN CASCADE SAS
+// Copyright (c) 2011-2013 OPEN CASCADE SAS
//
-// The content of this file is subject to the Open CASCADE Technology Public
-// License Version 6.5 (the "License"). You may not use the content of this file
-// except in compliance with the License. Please obtain a copy of the License
-// at http://www.opencascade.org and read it completely before using this file.
+// This file is part of Open CASCADE Technology software library.
//
-// The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
-// main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
+// This library is free software; you can redistribute it and/or modify it under
+// the terms of the GNU Lesser General Public License version 2.1 as published
+// by the Free Software Foundation, with special exception defined in the file
+// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
+// distribution for complete text of the license and disclaimer of any warranty.
//
-// The Original Code and all software distributed under the License is
-// distributed on an "AS IS" basis, without warranty of any kind, and the
-// Initial Developer hereby disclaims all such warranties, including without
-// limitation, any warranties of merchantability, fitness for a particular
-// purpose or non-infringement. Please see the License for the specific terms
-// and conditions governing the rights and limitations under the License.
-
-
-#include <OpenGl_IndexBuffer.hxx>
-#include <OpenGl_Context.hxx>
-
-#include <OpenGl_PrimitiveArray.hxx>
+// Alternatively, this file may be used under the terms of Open CASCADE
+// commercial license or contractual agreement.
#include <OpenGl_AspectFace.hxx>
+#include <OpenGl_Context.hxx>
#include <OpenGl_GraphicDriver.hxx>
+#include <OpenGl_IndexBuffer.hxx>
+#include <OpenGl_PointSprite.hxx>
+#include <OpenGl_PrimitiveArray.hxx>
+#include <OpenGl_Sampler.hxx>
+#include <OpenGl_ShaderManager.hxx>
+#include <OpenGl_ShaderProgram.hxx>
#include <OpenGl_Structure.hxx>
-#include <OpenGl_TextureBox.hxx>
-
-#include <InterfaceGraphic_PrimitiveArray.hxx>
+#include <OpenGl_VertexBufferCompat.hxx>
+#include <OpenGl_View.hxx>
+#include <OpenGl_Workspace.hxx>
+#include <Graphic3d_TextureParams.hxx>
+#include <NCollection_AlignedAllocator.hxx>
namespace
{
- static unsigned long vRand = 1L;
- #define OGL_Rand() (vRand = vRand * 214013L + 2531011L)
-};
-
-// =======================================================================
-// function : clearMemoryOwn
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::clearMemoryOwn() const
-{
- Standard::Free ((Standard_Address& )myPArray->edges);
- Standard::Free ((Standard_Address& )myPArray->vertices);
- Standard::Free ((Standard_Address& )myPArray->vcolours);
- Standard::Free ((Standard_Address& )myPArray->vnormals);
- Standard::Free ((Standard_Address& )myPArray->vtexels);
- Standard::Free ((Standard_Address& )myPArray->edge_vis); /// ???
-
- myPArray->edges = NULL;
- myPArray->vertices = NULL;
- myPArray->vcolours = NULL;
- myPArray->vnormals = NULL;
- myPArray->vtexels = NULL;
- myPArray->edge_vis = NULL;
-}
-
-// =======================================================================
-// function : clearMemoryGL
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::clearMemoryGL (const Handle(OpenGl_Context)& theGlCtx) const
-{
- for (Standard_Integer anIter = 0; anIter < VBOMaxType; ++anIter)
+ //! Convert data type to GL info
+ inline GLenum toGlDataType (const Graphic3d_TypeOfData theType,
+ GLint& theNbComp)
{
- if (!myVbos[anIter].IsNull())
+ switch (theType)
{
- myVbos[anIter]->Release (theGlCtx.operator->());
- myVbos[anIter].Nullify();
+ case Graphic3d_TOD_USHORT:
+ theNbComp = 1;
+ return GL_UNSIGNED_SHORT;
+ case Graphic3d_TOD_UINT:
+ theNbComp = 1;
+ return GL_UNSIGNED_INT;
+ case Graphic3d_TOD_VEC2:
+ theNbComp = 2;
+ return GL_FLOAT;
+ case Graphic3d_TOD_VEC3:
+ theNbComp = 3;
+ return GL_FLOAT;
+ case Graphic3d_TOD_VEC4:
+ theNbComp = 4;
+ return GL_FLOAT;
+ case Graphic3d_TOD_VEC4UB:
+ theNbComp = 4;
+ return GL_UNSIGNED_BYTE;
+ case Graphic3d_TOD_FLOAT:
+ theNbComp = 1;
+ return GL_FLOAT;
}
+ theNbComp = 0;
+ return GL_NONE;
}
+
}
-// =======================================================================
-// function : BuildVBO
-// purpose :
-// =======================================================================
-Standard_Boolean OpenGl_PrimitiveArray::BuildVBO (const Handle(OpenGl_Workspace)& theWorkspace) const
+//! Auxiliary template for VBO with interleaved attributes.
+template<class TheBaseClass, int NbAttributes>
+class OpenGl_VertexBufferT : public TheBaseClass
{
- const Handle(OpenGl_Context)& aGlCtx = theWorkspace->GetGlContext();
- if (myPArray->vertices == NULL)
+public:
+
+ //! Create uninitialized VBO.
+ OpenGl_VertexBufferT (const Graphic3d_Buffer& theAttribs)
+ : Stride (theAttribs.IsInterleaved() ? theAttribs.Stride : 0)
{
- // vertices should be always defined - others are optional
- return Standard_False;
+ memcpy (Attribs, theAttribs.AttributesArray(), sizeof(Graphic3d_Attribute) * NbAttributes);
}
- myVbos[VBOVertices] = new OpenGl_VertexBuffer();
- if (!myVbos[VBOVertices]->Init (aGlCtx, 3, myPArray->num_vertexs, &myPArray->vertices[0].xyz[0]))
+
+ virtual bool HasColorAttribute() const
{
- clearMemoryGL (aGlCtx);
- return Standard_False;
+ for (Standard_Integer anAttribIter = 0; anAttribIter < NbAttributes; ++anAttribIter)
+ {
+ const Graphic3d_Attribute& anAttrib = Attribs[anAttribIter];
+ if (anAttrib.Id == Graphic3d_TOA_COLOR)
+ {
+ return true;
+ }
+ }
+ return false;
}
- if (myPArray->edges != NULL)
+ virtual bool HasNormalAttribute() const
{
- myVbos[VBOEdges] = new OpenGl_IndexBuffer();
- if (!myVbos[VBOEdges]->Init (aGlCtx, 1, myPArray->num_edges, (GLuint* )myPArray->edges))
+ for (Standard_Integer anAttribIter = 0; anAttribIter < NbAttributes; ++anAttribIter)
{
- clearMemoryGL (aGlCtx);
- return Standard_False;
+ const Graphic3d_Attribute& anAttrib = Attribs[anAttribIter];
+ if (anAttrib.Id == Graphic3d_TOA_NORM)
+ {
+ return true;
+ }
}
+ return false;
}
- if (myPArray->vcolours != NULL)
+
+ virtual void BindPositionAttribute (const Handle(OpenGl_Context)& theGlCtx) const
{
- myVbos[VBOVcolours] = new OpenGl_VertexBuffer();
- if (!myVbos[VBOVcolours]->Init (aGlCtx, 4, myPArray->num_vertexs, (GLubyte* )myPArray->vcolours))
+ if (!TheBaseClass::IsValid())
{
- clearMemoryGL (aGlCtx);
- return Standard_False;
+ return;
+ }
+
+ TheBaseClass::Bind (theGlCtx);
+ GLint aNbComp;
+ const GLubyte* anOffset = TheBaseClass::myOffset;
+ const Standard_Size aMuliplier = Stride != 0 ? 1 : TheBaseClass::myElemsNb;
+ for (Standard_Integer anAttribIter = 0; anAttribIter < NbAttributes; ++anAttribIter)
+ {
+ const Graphic3d_Attribute& anAttrib = Attribs[anAttribIter];
+ const GLenum aDataType = toGlDataType (anAttrib.DataType, aNbComp);
+ if (anAttrib.Id == Graphic3d_TOA_POS
+ && aDataType != GL_NONE)
+ {
+ TheBaseClass::bindAttribute (theGlCtx, Graphic3d_TOA_POS, aNbComp, aDataType, Stride, anOffset);
+ break;
+ }
+
+ anOffset += aMuliplier * Graphic3d_Attribute::Stride (anAttrib.DataType);
}
}
- if (myPArray->vnormals != NULL)
+
+ virtual void BindAllAttributes (const Handle(OpenGl_Context)& theGlCtx) const
{
- myVbos[VBOVnormals] = new OpenGl_VertexBuffer();
- if (!myVbos[VBOVnormals]->Init (aGlCtx, 3, myPArray->num_vertexs, &myPArray->vnormals[0].xyz[0]))
+ if (!TheBaseClass::IsValid())
{
- clearMemoryGL (aGlCtx);
- return Standard_False;
+ return;
+ }
+
+ TheBaseClass::Bind (theGlCtx);
+ GLint aNbComp;
+ const GLubyte* anOffset = TheBaseClass::myOffset;
+ const Standard_Size aMuliplier = Stride != 0 ? 1 : TheBaseClass::myElemsNb;
+ for (Standard_Integer anAttribIter = 0; anAttribIter < NbAttributes; ++anAttribIter)
+ {
+ const Graphic3d_Attribute& anAttrib = Attribs[anAttribIter];
+ const GLenum aDataType = toGlDataType (anAttrib.DataType, aNbComp);
+ if (aDataType != GL_NONE)
+ {
+ TheBaseClass::bindAttribute (theGlCtx, anAttrib.Id, aNbComp, aDataType, Stride, anOffset);
+ }
+ anOffset += aMuliplier * Graphic3d_Attribute::Stride (anAttrib.DataType);
}
}
- if (myPArray->vtexels)
+
+ virtual void UnbindAllAttributes (const Handle(OpenGl_Context)& theGlCtx) const
{
- myVbos[VBOVtexels] = new OpenGl_VertexBuffer();
- if (!myVbos[VBOVtexels]->Init (aGlCtx, 2, myPArray->num_vertexs, &myPArray->vtexels[0].xy[0]))
+ if (!TheBaseClass::IsValid())
{
- clearMemoryGL (aGlCtx);
- return Standard_False;
+ return;
+ }
+ TheBaseClass::Unbind (theGlCtx);
+
+ for (Standard_Integer anAttribIter = 0; anAttribIter < NbAttributes; ++anAttribIter)
+ {
+ const Graphic3d_Attribute& anAttrib = Attribs[anAttribIter];
+ TheBaseClass::unbindAttribute (theGlCtx, anAttrib.Id);
}
}
- clearMemoryOwn();
- return Standard_True;
-}
+private:
+
+ Graphic3d_Attribute Attribs[NbAttributes];
+ Standard_Integer Stride;
+
+};
// =======================================================================
-// function : DrawArray
+// function : clearMemoryGL
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawArray (Tint theLightingModel,
- const Aspect_InteriorStyle theInteriorStyle,
- Tint theEdgeFlag,
- const TEL_COLOUR* theInteriorColour,
- const TEL_COLOUR* theLineColour,
- const TEL_COLOUR* theEdgeColour,
- const OPENGL_SURF_PROP* theFaceProp,
- const Handle(OpenGl_Workspace)& theWorkspace) const
+void OpenGl_PrimitiveArray::clearMemoryGL (const Handle(OpenGl_Context)& theGlCtx) const
{
- const Handle(OpenGl_Context)& aGlContext = theWorkspace->GetGlContext();
-
- Tint i,n;
- Tint transp = 0;
- // Following pointers have been provided for performance improvement
- tel_colour pfc = myPArray->fcolours;
- Tint* pvc = myPArray->vcolours;
- if (pvc != NULL)
+ if (!myVboIndices.IsNull())
{
- for (i = 0; i < myPArray->num_vertexs; ++i)
- {
- transp = int(theFaceProp->trans * 255.0f);
- #if defined (sparc) || defined (__sparc__) || defined (__sparc)
- pvc[i] = (pvc[i] & 0xffffff00);
- pvc[i] += transp;
- #else
- pvc[i] = (pvc[i] & 0x00ffffff);
- pvc[i] += transp << 24;
- #endif
- }
+ myVboIndices->Release (theGlCtx.operator->());
+ myVboIndices.Nullify();
}
+ if (!myVboAttribs.IsNull())
+ {
+ myVboAttribs->Release (theGlCtx.operator->());
+ myVboAttribs.Nullify();
+ }
+}
- switch (myPArray->type)
+// =======================================================================
+// function : initNormalVbo
+// purpose :
+// =======================================================================
+Standard_Boolean OpenGl_PrimitiveArray::initNormalVbo (const Handle(OpenGl_Context)& theCtx) const
+{
+ switch (myAttribs->NbAttributes)
{
- case TelPointsArrayType:
- case TelPolylinesArrayType:
- case TelSegmentsArrayType:
- glColor3fv (theLineColour->rgb);
- break;
- case TelPolygonsArrayType:
- case TelTrianglesArrayType:
- case TelQuadranglesArrayType:
- case TelTriangleStripsArrayType:
- case TelQuadrangleStripsArrayType:
- case TelTriangleFansArrayType:
- glColor3fv (theInteriorColour->rgb);
- break;
+ case 1: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 1> (*myAttribs); break;
+ case 2: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 2> (*myAttribs); break;
+ case 3: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 3> (*myAttribs); break;
+ case 4: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 4> (*myAttribs); break;
+ case 5: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 5> (*myAttribs); break;
+ case 6: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 6> (*myAttribs); break;
+ case 7: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 7> (*myAttribs); break;
+ case 8: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 8> (*myAttribs); break;
+ case 9: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 9> (*myAttribs); break;
+ case 10: myVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBuffer, 10>(*myAttribs); break;
}
- // Temporarily disable environment mapping
- if (myDrawMode <= GL_LINE_STRIP)
+ const Standard_Boolean isAttribMutable = myAttribs->IsMutable();
+ const Standard_Boolean isAttribInterleaved = myAttribs->IsInterleaved();
+ if (myAttribs->NbElements != myAttribs->NbMaxElements()
+ && myIndices.IsNull()
+ && (!isAttribInterleaved || isAttribMutable))
{
- glPushAttrib (GL_ENABLE_BIT);
- glDisable (GL_TEXTURE_1D);
- glDisable (GL_TEXTURE_2D);
+ throw Standard_ProgramError ("OpenGl_PrimitiveArray::buildVBO() - vertex attribute data with reserved size is not supported");
}
- if (theWorkspace->DegenerateModel < 2 &&
- ((myDrawMode > GL_LINE_STRIP && theInteriorStyle != Aspect_IS_EMPTY) ||
- (myDrawMode <= GL_LINE_STRIP)))
+ // specify data type as Byte and NbComponents as Stride, so that OpenGl_VertexBuffer::EstimatedDataSize() will return correct value
+ const Standard_Integer aNbVertexes = (isAttribMutable || !isAttribInterleaved) ? myAttribs->NbMaxElements() : myAttribs->NbElements;
+ if (!myVboAttribs->init (theCtx, myAttribs->Stride, aNbVertexes, myAttribs->Data(), GL_UNSIGNED_BYTE, myAttribs->Stride))
{
- if (theWorkspace->NamedStatus & OPENGL_NS_HIGHLIGHT)
- {
- pfc = NULL;
- pvc = NULL;
- }
+ TCollection_ExtendedString aMsg = TCollection_ExtendedString("VBO creation for Primitive Array has failed for ") + aNbVertexes + " vertices. Out of memory?";
+ theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION, GL_DEBUG_TYPE_PERFORMANCE, 0, GL_DEBUG_SEVERITY_LOW, aMsg);
- if (theInteriorStyle == Aspect_IS_HIDDENLINE)
+ clearMemoryGL (theCtx);
+ return Standard_False;
+ }
+ else if (myIndices.IsNull())
+ {
+ if (isAttribMutable && isAttribInterleaved)
{
- theEdgeFlag = 1;
- pfc = NULL;
- pvc = NULL;
+ // for mutable interlaced array we can change dynamically number of vertexes (they will be just skipped at the end of buffer);
+ // this doesn't matter in case if we have indexed array
+ myVboAttribs->SetElemsNb (myAttribs->NbElements);
}
+ return Standard_True;
+ }
- // Sometimes the GL_LIGHTING mode is activated here
- // without glEnable(GL_LIGHTING) call for an unknown reason, so it is necessary
- // to call glEnable(GL_LIGHTING) to synchronize Light On/Off mechanism*
- if (theLightingModel == 0 || myDrawMode <= GL_LINE_STRIP)
- glDisable (GL_LIGHTING);
- else
- glEnable (GL_LIGHTING);
-
- if (!toDrawVbo())
- {
- if (myPArray->vertices != NULL)
- {
- glVertexPointer (3, GL_FLOAT, 0, myPArray->vertices); // array of vertices
- glEnableClientState (GL_VERTEX_ARRAY);
- }
- if (myPArray->vnormals != NULL)
- {
- glNormalPointer (GL_FLOAT, 0, myPArray->vnormals); // array of normals
- glEnableClientState (GL_NORMAL_ARRAY);
- }
- if (myPArray->vtexels != NULL)
- {
- glTexCoordPointer (2, GL_FLOAT, 0, myPArray->vtexels); // array of texture coordinates
- glEnableClientState (GL_TEXTURE_COORD_ARRAY);
- }
-
- if (pvc != NULL)
- {
- glColorPointer (4, GL_UNSIGNED_BYTE, 0, pvc); // array of colors
- glEnableClientState (GL_COLOR_ARRAY);
- glColorMaterial (GL_FRONT_AND_BACK,GL_AMBIENT_AND_DIFFUSE);
- glEnable (GL_COLOR_MATERIAL);
- }
- }
- else
+ const Standard_Integer aNbIndexes = !myIndices->IsMutable() ? myIndices->NbElements : myIndices->NbMaxElements();
+ myVboIndices = new OpenGl_IndexBuffer();
+ bool isOk = false;
+ switch (myIndices->Stride)
+ {
+ case 2:
{
- // Bindings concrete pointer in accordance with VBO buffer
- myVbos[VBOVertices]->BindFixed (aGlContext, GL_VERTEX_ARRAY);
- if (!myVbos[VBOVnormals].IsNull())
- {
- myVbos[VBOVnormals]->BindFixed (aGlContext, GL_NORMAL_ARRAY);
- }
- if (!myVbos[VBOVtexels].IsNull() && (theWorkspace->NamedStatus & OPENGL_NS_FORBIDSETTEX) == 0)
- {
- myVbos[VBOVtexels]->BindFixed (aGlContext, GL_TEXTURE_COORD_ARRAY);
- }
- if (!myVbos[VBOVcolours].IsNull())
- {
- myVbos[VBOVcolours]->BindFixed (aGlContext, GL_COLOR_ARRAY);
- glColorMaterial (GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE);
- glEnable (GL_COLOR_MATERIAL);
- }
+ isOk = myVboIndices->Init (theCtx, 1, aNbIndexes, reinterpret_cast<const GLushort*> (myIndices->Data()));
+ myVboIndices->SetElemsNb (myIndices->NbElements);
+ myIndices->Validate();
+ break;
}
-
- /// OCC22236 NOTE: draw for all situations:
- /// 1) draw elements from myPArray->bufferVBO[VBOEdges] indicies array
- /// 2) draw elements from vertice array, when bounds defines count of primitive's verts.
- /// 3) draw primitive by vertexes if no edges and bounds array is specified
- if (toDrawVbo())
+ case 4:
{
- if (!myVbos[VBOEdges].IsNull())
- {
- myVbos[VBOEdges]->Bind (aGlContext);
- if (myPArray->num_bounds > 0)
- {
- // draw primitives by vertex count with the indicies
- Tint* anOffset = NULL;
- for (i = 0; i < myPArray->num_bounds; ++i)
- {
- glDrawElements (myDrawMode, myPArray->bounds[i], myVbos[VBOEdges]->GetDataType(), anOffset);
- anOffset += myPArray->bounds[i];
- }
- }
- else
- {
- // draw one (or sequential) primitive by the indicies
- glDrawElements (myDrawMode, myPArray->num_edges, myVbos[VBOEdges]->GetDataType(), NULL);
- }
- myVbos[VBOEdges]->Unbind (aGlContext);
- }
- else if (myPArray->num_bounds > 0)
- {
- for (i = n = 0; i < myPArray->num_bounds; ++i)
- {
- glDrawArrays (myDrawMode, n, myPArray->bounds[i]);
- n += myPArray->bounds[i];
- }
- }
- else
- {
- glDrawArrays (myDrawMode, 0, myVbos[VBOVertices]->GetElemsNb());
- }
-
- // bind with 0
- myVbos[VBOVertices]->UnbindFixed (aGlContext, GL_VERTEX_ARRAY);
- if (!myVbos[VBOVnormals].IsNull())
- {
- myVbos[VBOVnormals]->UnbindFixed (aGlContext, GL_NORMAL_ARRAY);
- }
- if (!myVbos[VBOVtexels].IsNull() && (theWorkspace->NamedStatus & OPENGL_NS_FORBIDSETTEX) == 0)
- {
- myVbos[VBOVtexels]->UnbindFixed (aGlContext, GL_TEXTURE_COORD_ARRAY);
- }
- if (!myVbos[VBOVcolours].IsNull())
- {
- myVbos[VBOVcolours]->UnbindFixed (aGlContext, GL_COLOR_ARRAY);
- glDisable (GL_COLOR_MATERIAL);
- theWorkspace->NamedStatus |= OPENGL_NS_RESMAT; // Reset material
- }
- }
- else
- {
- if (myPArray->num_bounds > 0)
- {
- if (myPArray->num_edges > 0)
- {
- for (i = n = 0; i < myPArray->num_bounds; ++i)
- {
- if (pfc != NULL) glColor3fv (pfc[i].rgb);
- glDrawElements (myDrawMode, myPArray->bounds[i], GL_UNSIGNED_INT, (GLenum* )&myPArray->edges[n]);
- n += myPArray->bounds[i];
- }
- }
- else
- {
- for (i = n = 0; i < myPArray->num_bounds; ++i)
- {
- if (pfc != NULL)
- {
- glColor3fv (pfc[i].rgb);
- }
- glDrawArrays (myDrawMode, n, myPArray->bounds[i]);
- n += myPArray->bounds[i];
- }
- }
- }
- else if (myPArray->num_edges > 0)
- {
- glDrawElements (myDrawMode, myPArray->num_edges, GL_UNSIGNED_INT, (GLenum* )myPArray->edges);
- }
- else
- {
- glDrawArrays (myDrawMode, 0, myPArray->num_vertexs);
- }
-
- if (pvc != NULL)
- {
- glDisable (GL_COLOR_MATERIAL);
- theWorkspace->NamedStatus |= OPENGL_NS_RESMAT; // Reset material
- }
-
- glDisableClientState (GL_VERTEX_ARRAY);
- if (myPArray->vcolours != NULL)
- glDisableClientState (GL_COLOR_ARRAY);
- if (myPArray->vnormals != NULL)
- glDisableClientState (GL_NORMAL_ARRAY);
- if (myPArray->vtexels != NULL)
- glDisableClientState (GL_TEXTURE_COORD_ARRAY);
+ isOk = myVboIndices->Init (theCtx, 1, aNbIndexes, reinterpret_cast<const GLuint*> (myIndices->Data()));
+ myVboIndices->SetElemsNb (myIndices->NbElements);
+ myIndices->Validate();
+ break;
}
-
- if (theWorkspace->DegenerateModel)
+ default:
{
- if (myDrawMode <= GL_LINE_STRIP)
- {
- glPopAttrib();
- }
- return;
+ clearMemoryGL (theCtx);
+ return Standard_False;
}
}
-
- if (theEdgeFlag || theWorkspace->DegenerateModel)
+ if (!isOk)
{
- switch (theWorkspace->DegenerateModel)
- {
- default: // XXX_TDM_NODE or TINY
- // On some NVIDIA graphic cards, using glEdgeFlagPointer() in
- // combination with VBO ( edge flag data put into a VBO buffer)
- // leads to a crash in a driver. Therefore, edge flags are simply
- // igonored when VBOs are enabled, so all the edges are drawn if
- // edge visibility is turned on. In order to draw edges selectively,
- // either disable VBO or turn off edge visibilty in the current
- // primitive array and create a separate primitive array (segments)
- // and put edges to be drawn into it.
- if (myDrawMode > GL_LINE_STRIP)
- {
- DrawEdges (theEdgeFlag ? theEdgeColour : theInteriorColour, theWorkspace);
- }
- break;
- // DegenerateModel(as Lines, Points, BBoxs) are used only without VBO
- case 2: // XXX_TDM_WIREFRAME
- if (!toDrawVbo())
- DrawDegeneratesAsLines ((theEdgeFlag ? theEdgeColour : theInteriorColour), theWorkspace);
- break;
- case 3: // XXX_TDM_MARKER
- if (!toDrawVbo())
- DrawDegeneratesAsPoints ((theEdgeFlag ? theEdgeColour : theInteriorColour), theWorkspace->SkipRatio);
- break;
- case 4: // XXX_TDM_BBOX
- if (!toDrawVbo())
- DrawDegeneratesAsBBoxs (theEdgeFlag ? theEdgeColour : theInteriorColour);
- break;
- }
+ TCollection_ExtendedString aMsg = TCollection_ExtendedString("VBO creation for Primitive Array has failed for ") + aNbIndexes + " indices. Out of memory?";
+ theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION, GL_DEBUG_TYPE_PERFORMANCE, 0, GL_DEBUG_SEVERITY_LOW, aMsg);
+ clearMemoryGL (theCtx);
+ return Standard_False;
}
-
- if (myDrawMode <= GL_LINE_STRIP)
- glPopAttrib();
+ return Standard_True;
}
// =======================================================================
-// function : DrawEdges
+// function : buildVBO
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawEdges (const TEL_COLOUR* theEdgeColour,
- const Handle(OpenGl_Workspace)& theWorkspace) const
+Standard_Boolean OpenGl_PrimitiveArray::buildVBO (const Handle(OpenGl_Context)& theCtx,
+ const Standard_Boolean theToKeepData) const
{
- glDisable (GL_LIGHTING);
-
- const Handle(OpenGl_Context)& aGlContext = theWorkspace->GetGlContext();
- const OpenGl_AspectLine* anAspectLineOld = NULL;
- if (myDrawMode > GL_LINE_STRIP)
+ bool isNormalMode = theCtx->ToUseVbo();
+ clearMemoryGL (theCtx);
+ if (myAttribs.IsNull()
+ || myAttribs->IsEmpty()
+ || myAttribs->NbElements < 1
+ || myAttribs->NbAttributes < 1
+ || myAttribs->NbAttributes > 10)
{
- anAspectLineOld = theWorkspace->SetAspectLine (theWorkspace->AspectFace (Standard_True)->AspectEdge());
- theWorkspace->AspectLine (Standard_True);
-
- glPushAttrib (GL_POLYGON_BIT);
- glPolygonMode (GL_FRONT_AND_BACK, GL_LINE);
+ // vertices should be always defined - others are optional
+ return Standard_False;
}
- Tint i, j, n;
-
- /// OCC22236 NOTE: draw edges for all situations:
- /// 1) draw elements with GL_LINE style as edges from myPArray->bufferVBO[VBOEdges] indicies array
- /// 2) draw elements from vertice array, when bounds defines count of primitive's verts.
- /// 3) draw primitive's edges by vertexes if no edges and bounds array is specified
- if (toDrawVbo())
- {
- myVbos[VBOVertices]->BindFixed (aGlContext, GL_VERTEX_ARRAY);
- glColor3fv (theEdgeColour->rgb);
- if (!myVbos[VBOEdges].IsNull())
- {
- myVbos[VBOEdges]->Bind (aGlContext);
-
- // draw primitives by vertex count with the indicies
- if (myPArray->num_bounds > 0)
- {
- Tint* offset = 0;
- for (i = 0, offset = 0; i < myPArray->num_bounds; ++i)
- {
- glDrawElements (myDrawMode, myPArray->bounds[i], myVbos[VBOEdges]->GetDataType(), offset);
- offset += myPArray->bounds[i];
- }
- }
- // draw one (or sequential) primitive by the indicies
- else
- {
- glDrawElements (myDrawMode, myVbos[VBOEdges]->GetElemsNb(), myVbos[VBOEdges]->GetDataType(), NULL);
- }
- myVbos[VBOEdges]->Unbind (aGlContext);
- }
- else if (myPArray->num_bounds > 0)
+ if (isNormalMode
+ && initNormalVbo (theCtx))
+ {
+ if (!theCtx->caps->keepArrayData
+ && !theToKeepData
+ && !myAttribs->IsMutable())
{
- for (i = n = 0; i < myPArray->num_bounds; ++i)
- {
- glDrawArrays (myDrawMode, n, myPArray->bounds[i]);
- n += myPArray->bounds[i];
- }
+ myIndices.Nullify();
+ myAttribs.Nullify();
}
else
{
- glDrawArrays (myDrawMode, 0, myPArray->num_vertexs);
+ myAttribs->Validate();
}
+ return Standard_True;
+ }
- // unbind buffers
- myVbos[VBOVertices]->UnbindFixed (aGlContext, GL_VERTEX_ARRAY);
+ Handle(OpenGl_VertexBufferCompat) aVboAttribs;
+ switch (myAttribs->NbAttributes)
+ {
+ case 1: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 1> (*myAttribs); break;
+ case 2: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 2> (*myAttribs); break;
+ case 3: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 3> (*myAttribs); break;
+ case 4: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 4> (*myAttribs); break;
+ case 5: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 5> (*myAttribs); break;
+ case 6: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 6> (*myAttribs); break;
+ case 7: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 7> (*myAttribs); break;
+ case 8: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 8> (*myAttribs); break;
+ case 9: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 9> (*myAttribs); break;
+ case 10: aVboAttribs = new OpenGl_VertexBufferT<OpenGl_VertexBufferCompat, 10>(*myAttribs); break;
}
- else
+ aVboAttribs->initLink (myAttribs, 0, myAttribs->NbElements, GL_NONE);
+ if (!myIndices.IsNull())
{
- glEnableClientState (GL_VERTEX_ARRAY);
- glVertexPointer (3, GL_FLOAT, 0, myPArray->vertices); // array of vertices
-
- glColor3fv (theEdgeColour->rgb);
- if (myPArray->num_bounds > 0)
+ Handle(OpenGl_VertexBufferCompat) aVboIndices = new OpenGl_VertexBufferCompat();
+ switch (myIndices->Stride)
{
- if (myPArray->num_edges > 0)
- {
- for (i = n = 0; i < myPArray->num_bounds; ++i)
- {
- if (myPArray->edge_vis)
- {
- glBegin (myDrawMode);
- for (j = 0; j < myPArray->bounds[i]; ++j)
- {
- glEdgeFlag (myPArray->edge_vis[n+j]);
- glVertex3fv (&myPArray->vertices[myPArray->edges[n+j]].xyz[0]);
- }
- glEnd();
- }
- else
- {
- glDrawElements (myDrawMode, myPArray->bounds[i], GL_UNSIGNED_INT, (GLenum* )&myPArray->edges[n]);
- }
- n += myPArray->bounds[i];
- }
- }
- else
+ case 2:
{
- for (i = n = 0 ; i < myPArray->num_bounds; ++i)
- {
- glDrawArrays (myDrawMode, n, myPArray->bounds[i]);
- n += myPArray->bounds[i];
- }
+ aVboIndices->initLink (myIndices, 1, myIndices->NbElements, GL_UNSIGNED_SHORT);
+ break;
}
- }
- else if (myPArray->num_edges > 0)
- {
- if (myPArray->edge_vis)
+ case 4:
{
- glBegin (myDrawMode);
- for (i = 0; i < myPArray->num_edges; ++i)
- {
- glEdgeFlag (myPArray->edge_vis[i]);
- glVertex3fv (&myPArray->vertices[myPArray->edges[i]].xyz[0]);
- }
- glEnd();
+ aVboIndices->initLink (myIndices, 1, myIndices->NbElements, GL_UNSIGNED_INT);
+ break;
}
- else
+ default:
{
- glDrawElements (myDrawMode, myPArray->num_edges, GL_UNSIGNED_INT, (GLenum* )myPArray->edges);
+ return Standard_False;
}
}
- else
- {
- glDrawArrays (myDrawMode, 0, myPArray->num_vertexs);
- }
+ myVboIndices = aVboIndices;
}
-
- if (myDrawMode > GL_LINE_STRIP)
+ myVboAttribs = aVboAttribs;
+ if (!theCtx->caps->keepArrayData
+ && !theToKeepData)
{
- // Restore line context
- theWorkspace->SetAspectLine (anAspectLineOld);
- glPopAttrib();
+ // does not make sense for compatibility mode
+ //myIndices.Nullify();
+ //myAttribs.Nullify();
}
-}
-// =======================================================================
-// function : DrawDegeneratesPointsAsPoints
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesPointsAsPoints() const
-{
- tel_point pv = myPArray->vertices;
- for (Tint aVertId = 0; aVertId < myPArray->num_vertexs; ++aVertId)
- {
- glVertex3fv (&pv[aVertId].xyz[0]);
- }
+ return Standard_True;
}
// =======================================================================
-// function : DrawDegeneratesLinesAsPoints
+// function : updateVBO
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesLinesAsPoints() const
+void OpenGl_PrimitiveArray::updateVBO (const Handle(OpenGl_Context)& theCtx) const
{
- GLfloat pt[3];
- tel_point pv = myPArray->vertices;
-
- Tint j = 0;
- while (j < myPArray->num_vertexs)
- {
- pt[0] = pv[j].xyz[0];
- pt[1] = pv[j].xyz[1];
- pt[2] = pv[j].xyz[2]; ++j;
- pt[0] += pv[j].xyz[0];
- pt[1] += pv[j].xyz[1];
- pt[2] += pv[j].xyz[2]; ++j;
- pt[0] *= 0.5f;
- pt[1] *= 0.5f;
- pt[2] *= 0.5f;
- glVertex3fv (pt);
- }
-}
-
-// =======================================================================
-// function : DrawDegeneratesTrianglesAsPoints
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesTrianglesAsPoints() const
-{
- Tint i, j, iv;
- GLfloat pt[ 3 ];
- tel_point pv = myPArray->vertices;
-
- if (myPArray->num_edges > 0)
+ if (!myAttribs.IsNull())
{
- for (j = 0; j < myPArray->num_edges; j += 3)
+ Graphic3d_BufferRange aRange = myAttribs->InvalidatedRange();
+ if (!aRange.IsEmpty()
+ && myVboAttribs->IsValid()
+ && !myVboAttribs->IsVirtual())
{
- iv = myPArray->edges[j];
- pt[0] = pv[iv].xyz[0];
- pt[1] = pv[iv].xyz[1];
- pt[2] = pv[iv].xyz[2];
- for (i = 1; i < 3; ++i)
+ myVboAttribs->Bind (theCtx);
+ theCtx->core15fwd->glBufferSubData (myVboAttribs->GetTarget(),
+ aRange.Start,
+ aRange.Length,
+ myAttribs->Data() + aRange.Start);
+ myVboAttribs->Unbind (theCtx);
+ if (myAttribs->IsInterleaved())
{
- iv = myPArray->edges[j+i];
- pt[0] += pv[iv].xyz[0];
- pt[1] += pv[iv].xyz[1];
- pt[2] += pv[iv].xyz[2];
+ myVboAttribs->SetElemsNb (myAttribs->NbElements);
}
- pt[0] /= 3.f;
- pt[1] /= 3.f;
- pt[2] /= 3.f;
- glVertex3fv (pt);
}
+ myAttribs->Validate();
}
- else
+ if (!myIndices.IsNull())
{
- for (j = 0; j < myPArray->num_vertexs; j += 3)
+ Graphic3d_BufferRange aRange = myIndices->InvalidatedRange();
+ if (!aRange.IsEmpty()
+ && myVboIndices->IsValid()
+ && !myVboIndices->IsVirtual())
{
- pt[0] = pv[j].xyz[0];
- pt[1] = pv[j].xyz[1];
- pt[2] = pv[j].xyz[2];
- for (i = 1; i < 3; ++i)
- {
- pt[0] += pv[j+i].xyz[0];
- pt[1] += pv[j+i].xyz[1];
- pt[2] += pv[j+i].xyz[2];
- }
- pt[0] /= 3.f;
- pt[1] /= 3.f;
- pt[2] /= 3.f;
- glVertex3fv (pt);
+ myVboIndices->Bind (theCtx);
+ theCtx->core15fwd->glBufferSubData (myVboIndices->GetTarget(),
+ aRange.Start,
+ aRange.Length,
+ myIndices->Data() + aRange.Start);
+ myVboIndices->Unbind (theCtx);
+ myVboIndices->SetElemsNb (myIndices->NbElements);
}
+ myIndices->Validate();
}
}
// =======================================================================
-// function : DrawDegeneratesTrianglesAsPoints
+// function : drawArray
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesTrianglestripsAsPoints() const
-{
- Tint i, j, k, n;
- GLfloat pt[ 3 ];
- tel_point pv = myPArray->vertices;
-
- if (myPArray->num_bounds > 0)
+void OpenGl_PrimitiveArray::drawArray (const Handle(OpenGl_Workspace)& theWorkspace,
+ const Graphic3d_Vec4* theFaceColors,
+ const Standard_Boolean theHasVertColor) const
+{
+ if (myVboAttribs.IsNull())
{
- for (k = n = 0; k < myPArray->num_bounds; ++k)
+ #if !defined(GL_ES_VERSION_2_0)
+ if (myDrawMode == GL_POINTS)
{
- for (j = 0; j < myPArray->bounds[k] - 2; ++j)
- {
- pt[0] = pv[n+j].xyz[0];
- pt[1] = pv[n+j].xyz[1];
- pt[2] = pv[n+j].xyz[2];
- for (i = 1; i < 3; ++i)
- {
- pt[0] += pv[n+j+i].xyz[0];
- pt[1] += pv[n+j+i].xyz[1];
- pt[2] += pv[n+j+i].xyz[2];
- }
- pt[0] /= 3.f;
- pt[1] /= 3.f;
- pt[2] /= 3.f;
- glVertex3fv (pt);
- }
- n += myPArray->bounds[k];
+ // extreme compatibility mode - without sprites but with markers
+ drawMarkers (theWorkspace);
}
+ #endif
+ return;
}
- else
+
+ const Handle(OpenGl_Context)& aGlContext = theWorkspace->GetGlContext();
+ const bool toHilight = theWorkspace->ToHighlight();
+ const GLenum aDrawMode = !aGlContext->ActiveProgram().IsNull()
+ && aGlContext->ActiveProgram()->HasTessellationStage()
+ ? GL_PATCHES
+ : myDrawMode;
+ myVboAttribs->BindAllAttributes (aGlContext);
+ if (theHasVertColor && toHilight)
{
- for (j = 0; j < myPArray->num_vertexs - 2; ++j)
- {
- pt[0] = pv[j].xyz[0];
- pt[1] = pv[j].xyz[1];
- pt[2] = pv[j].xyz[2];
- for (i = 1; i < 3; ++i)
- {
- pt[0] += pv[j+i].xyz[0];
- pt[1] += pv[j+i].xyz[1];
- pt[2] += pv[j+i].xyz[2];
- }
- pt[0] /= 3.f;
- pt[1] /= 3.f;
- pt[2] /= 3.f;
- glVertex3fv (pt);
- }
+ // disable per-vertex color
+ OpenGl_VertexBuffer::unbindAttribute (aGlContext, Graphic3d_TOA_COLOR);
}
-}
-
-// =======================================================================
-// function : DrawDegeneratesPolygonsAsPoints
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesPolygonsAsPoints() const
-{
- Tint j, k, n, iv;
- GLfloat pt[3];
- tel_point pv = myPArray->vertices;
-
- if (myPArray->num_bounds > 0)
+ if (!myVboIndices.IsNull())
{
- if (myPArray->num_edges > 0)
+ myVboIndices->Bind (aGlContext);
+ GLubyte* anOffset = myVboIndices->GetDataOffset();
+ if (!myBounds.IsNull())
{
- for (k = n = 0; k < myPArray->num_bounds; ++k)
+ // draw primitives by vertex count with the indices
+ const size_t aStride = myVboIndices->GetDataType() == GL_UNSIGNED_SHORT ? sizeof(unsigned short) : sizeof(unsigned int);
+ for (Standard_Integer aGroupIter = 0; aGroupIter < myBounds->NbBounds; ++aGroupIter)
{
- pt[0] = pt[1] = pt[2] = 0.0;
- for (j = 0; j < myPArray->bounds[k]; ++j)
- {
- iv = myPArray->edges[n+j];
- pt[0] += pv[iv].xyz[0];
- pt[1] += pv[iv].xyz[1];
- pt[2] += pv[iv].xyz[2];
- }
- pt[0] /= myPArray->bounds[k];
- pt[1] /= myPArray->bounds[k];
- pt[2] /= myPArray->bounds[k];
- glVertex3fv (pt);
- n += myPArray->bounds[k];
+ const GLint aNbElemsInGroup = myBounds->Bounds[aGroupIter];
+ if (theFaceColors != NULL) aGlContext->SetColor4fv (theFaceColors[aGroupIter]);
+ glDrawElements (aDrawMode, aNbElemsInGroup, myVboIndices->GetDataType(), anOffset);
+ anOffset += aStride * aNbElemsInGroup;
}
}
else
{
- for (k = n = 0; k < myPArray->num_bounds; ++k)
- {
- pt[0] = pt[1] = pt[2] = 0.0;
- for (j = 0; j < myPArray->bounds[k]; ++j)
- {
- pt[0] += pv[n+j].xyz[0];
- pt[1] += pv[n+j].xyz[1];
- pt[2] += pv[n+j].xyz[2];
- }
- pt[0] /= myPArray->bounds[k];
- pt[1] /= myPArray->bounds[k];
- pt[2] /= myPArray->bounds[k];
- glVertex3fv (pt);
- n += myPArray->bounds[k];
- }
+ // draw one (or sequential) primitive by the indices
+ glDrawElements (aDrawMode, myVboIndices->GetElemsNb(), myVboIndices->GetDataType(), anOffset);
}
+ myVboIndices->Unbind (aGlContext);
}
- else if (myPArray->num_edges > 0)
+ else if (!myBounds.IsNull())
{
- pt[0] = pt[1] = pt[2] = 0.0;
- for (j = 0; j < myPArray->num_edges; ++j)
+ GLint aFirstElem = 0;
+ for (Standard_Integer aGroupIter = 0; aGroupIter < myBounds->NbBounds; ++aGroupIter)
{
- iv = myPArray->edges[j];
- pt[0] += pv[iv].xyz[0];
- pt[1] += pv[iv].xyz[1];
- pt[2] += pv[iv].xyz[2];
+ const GLint aNbElemsInGroup = myBounds->Bounds[aGroupIter];
+ if (theFaceColors != NULL) aGlContext->SetColor4fv (theFaceColors[aGroupIter]);
+ glDrawArrays (aDrawMode, aFirstElem, aNbElemsInGroup);
+ aFirstElem += aNbElemsInGroup;
}
- pt[0] /= myPArray->num_edges;
- pt[1] /= myPArray->num_edges;
- pt[2] /= myPArray->num_edges;
- glVertex3fv (pt);
}
else
{
- pt[0] = pt[1] = pt[2] = 0.0;
- for (j = 0; j < myPArray->num_vertexs; ++j)
+ if (myDrawMode == GL_POINTS)
+ {
+ drawMarkers (theWorkspace);
+ }
+ else
{
- pt[0] += pv[j].xyz[0];
- pt[1] += pv[j].xyz[1];
- pt[2] += pv[j].xyz[2];
+ glDrawArrays (aDrawMode, 0, myVboAttribs->GetElemsNb());
}
- pt[0] /= myPArray->num_vertexs;
- pt[1] /= myPArray->num_vertexs;
- pt[2] /= myPArray->num_vertexs;
- glVertex3fv (pt);
}
+
+ // bind with 0
+ myVboAttribs->UnbindAllAttributes (aGlContext);
}
// =======================================================================
-// function : DrawDegeneratesQuadranglesAsPoints
+// function : drawEdges
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesQuadranglesAsPoints() const
+void OpenGl_PrimitiveArray::drawEdges (const OpenGl_Vec4& theEdgeColour,
+ const Handle(OpenGl_Workspace)& theWorkspace) const
{
- Tint i, j, iv;
- GLfloat pt[ 3 ];
- tel_point pv = myPArray->vertices;
+ const Handle(OpenGl_Context)& aGlContext = theWorkspace->GetGlContext();
+ if (myVboAttribs.IsNull())
+ {
+ return;
+ }
+
+ const OpenGl_AspectLine* anAspectLineOld = theWorkspace->SetAspectLine (theWorkspace->AspectFace()->AspectEdge());
+ const OpenGl_AspectLine* anAspect = theWorkspace->ApplyAspectLine();
+#if !defined(GL_ES_VERSION_2_0)
+ const Standard_Integer aPolyModeOld = aGlContext->SetPolygonMode (GL_LINE);
+#endif
- if (myPArray->num_edges > 0)
+ if (aGlContext->core20fwd != NULL)
{
- for (j = 0; j < myPArray->num_edges; j += 4)
- {
- pt[0] = pt[1] = pt[2] = 0.0;
- for (i = 0; i < 4; ++i)
- {
- iv = myPArray->edges[j+i];
- pt[0] += pv[iv].xyz[0];
- pt[1] += pv[iv].xyz[1];
- pt[2] += pv[iv].xyz[2];
- }
- pt[0] /= 4;
- pt[1] /= 4;
- pt[2] /= 4;
- glVertex3fv ( pt );
- }
+ aGlContext->ShaderManager()->BindLineProgram (Handle(OpenGl_TextureSet)(), anAspect->Aspect()->Type(),
+ Graphic3d_TOSM_UNLIT, Graphic3d_AlphaMode_Opaque, Standard_False,
+ anAspect->ShaderProgramRes (aGlContext));
}
- else
+ const GLenum aDrawMode = !aGlContext->ActiveProgram().IsNull()
+ && aGlContext->ActiveProgram()->HasTessellationStage()
+ ? GL_PATCHES
+ : myDrawMode;
+#if !defined(GL_ES_VERSION_2_0)
+ if (aGlContext->ActiveProgram().IsNull()
+ && aGlContext->core11 != NULL)
{
- for (j = 0; j < myPArray->num_vertexs; j += 4)
- {
- pt[0] = pt[1] = pt[2] = 0.0;
- for (i = 0; i < 4; ++i)
- {
- pt[0] += pv[j+i].xyz[0];
- pt[1] += pv[j+i].xyz[1];
- pt[2] += pv[j+i].xyz[2];
- }
- pt[0] /= 4;
- pt[1] /= 4;
- pt[2] /= 4;
- glVertex3fv (pt);
- }
+ glDisable (GL_LIGHTING);
}
-}
+#endif
-// =======================================================================
-// function : DrawDegeneratesAsPoints
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesQuadranglestripsAsPoints() const
-{
- Tint i, j, k, n;
- GLfloat pt[3];
- tel_point pv = myPArray->vertices;
+ /// OCC22236 NOTE: draw edges for all situations:
+ /// 1) draw elements with GL_LINE style as edges from myPArray->bufferVBO[VBOEdges] indices array
+ /// 2) draw elements from vertex array, when bounds defines count of primitive's vertices.
+ /// 3) draw primitive's edges by vertexes if no edges and bounds array is specified
+ myVboAttribs->BindPositionAttribute (aGlContext);
+
+ aGlContext->SetColor4fv (theEdgeColour);
+ aGlContext->SetTypeOfLine (anAspect->Aspect()->Type());
+ aGlContext->SetLineWidth (anAspect->Aspect()->Width());
- if (myPArray->num_bounds > 0)
+ if (!myVboIndices.IsNull())
{
- for (k = n = 0; k < myPArray->num_bounds; ++k)
+ myVboIndices->Bind (aGlContext);
+ GLubyte* anOffset = myVboIndices->GetDataOffset();
+
+ // draw primitives by vertex count with the indices
+ if (!myBounds.IsNull())
{
- for (j = 0; j < myPArray->bounds[k] - 2; j += 2)
+ const size_t aStride = myVboIndices->GetDataType() == GL_UNSIGNED_SHORT ? sizeof(unsigned short) : sizeof(unsigned int);
+ for (Standard_Integer aGroupIter = 0; aGroupIter < myBounds->NbBounds; ++aGroupIter)
{
- pt[0] = pt[1] = pt[2] = 0.;
- for (i = 0; i < 4; ++i)
- {
- pt[0] += pv[n+j+i].xyz[0];
- pt[1] += pv[n+j+i].xyz[1];
- pt[2] += pv[n+j+i].xyz[2];
- }
- pt[0] /= 4;
- pt[1] /= 4;
- pt[2] /= 4;
- glVertex3fv (pt);
+ const GLint aNbElemsInGroup = myBounds->Bounds[aGroupIter];
+ glDrawElements (aDrawMode, aNbElemsInGroup, myVboIndices->GetDataType(), anOffset);
+ anOffset += aStride * aNbElemsInGroup;
}
- n += myPArray->bounds[k];
}
+ // draw one (or sequential) primitive by the indices
+ else
+ {
+ glDrawElements (aDrawMode, myVboIndices->GetElemsNb(), myVboIndices->GetDataType(), anOffset);
+ }
+ myVboIndices->Unbind (aGlContext);
}
- else
+ else if (!myBounds.IsNull())
{
- for (j = 0; j < myPArray->num_vertexs - 2; j += 2)
+ GLint aFirstElem = 0;
+ for (Standard_Integer aGroupIter = 0; aGroupIter < myBounds->NbBounds; ++aGroupIter)
{
- pt[0] = pt[1] = pt[2] = 0.;
- for (i = 0; i < 4; ++i)
- {
- pt[0] += pv[j+i].xyz[0];
- pt[1] += pv[j+i].xyz[1];
- pt[2] += pv[j+i].xyz[2];
- }
- pt[0] /= 4;
- pt[1] /= 4;
- pt[2] /= 4;
- glVertex3fv (pt);
+ const GLint aNbElemsInGroup = myBounds->Bounds[aGroupIter];
+ glDrawArrays (aDrawMode, aFirstElem, aNbElemsInGroup);
+ aFirstElem += aNbElemsInGroup;
}
}
-}
-
-// =======================================================================
-// function : DrawDegeneratesAsPoints
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesAsPoints (const TEL_COLOUR* theEdgeColour,
- const float theSkipRatio) const
-{
- if (theSkipRatio >= 1.0f)
- return;
-
- GLboolean zbuff_state = glIsEnabled (GL_DEPTH_TEST);
- glDisable (GL_LIGHTING);
- if (zbuff_state)
- glDisable (GL_DEPTH_TEST);
- glColor3fv (theEdgeColour->rgb);
-
- glBegin (GL_POINTS);
- switch (myDrawMode)
- {
- case GL_POINTS:
- DrawDegeneratesPointsAsPoints();
- break;
- case GL_LINES:
- DrawDegeneratesLinesAsPoints();
- break;
- case GL_LINE_STRIP:
- case GL_POLYGON:
- DrawDegeneratesPolygonsAsPoints();
- break;
- case GL_TRIANGLES:
- DrawDegeneratesTrianglesAsPoints();
- break;
- case GL_QUADS:
- DrawDegeneratesQuadranglesAsPoints();
- break;
- case GL_TRIANGLE_FAN:
- case GL_TRIANGLE_STRIP:
- DrawDegeneratesTrianglestripsAsPoints();
- break;
- case GL_QUAD_STRIP:
- DrawDegeneratesQuadranglestripsAsPoints();
- break;
- default:
- break;
+ else
+ {
+ glDrawArrays (aDrawMode, 0, !myVboAttribs.IsNull() ? myVboAttribs->GetElemsNb() : myAttribs->NbElements);
}
- glEnd();
- if (zbuff_state)
- glEnable (GL_DEPTH_TEST);
+
+ // unbind buffers
+ myVboAttribs->UnbindAttribute (aGlContext, Graphic3d_TOA_POS);
+
+ // restore line context
+ theWorkspace->SetAspectLine (anAspectLineOld);
+#if !defined(GL_ES_VERSION_2_0)
+ aGlContext->SetPolygonMode (aPolyModeOld);
+#endif
}
// =======================================================================
-// function : DrawDegeneratesLinesAsLines
+// function : drawMarkers
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesLinesAsLines (const float theSkipRatio) const
+void OpenGl_PrimitiveArray::drawMarkers (const Handle(OpenGl_Workspace)& theWorkspace) const
{
- Tint i, iv;
- tel_point pv = myPArray->vertices;
-
- Tint n = myPArray->num_vertexs;
- Tint j = int((1.0f - theSkipRatio) * n);
- for (; j > 0; --j)
+ const OpenGl_AspectMarker* anAspectMarker = theWorkspace->ApplyAspectMarker();
+ const Handle(OpenGl_Context)& aCtx = theWorkspace->GetGlContext();
+ const GLenum aDrawMode = !aCtx->ActiveProgram().IsNull()
+ && aCtx->ActiveProgram()->HasTessellationStage()
+ ? GL_PATCHES
+ : myDrawMode;
+
+ const Handle(OpenGl_TextureSet)& aSpriteNormRes = anAspectMarker->SpriteRes (aCtx);
+ const OpenGl_PointSprite* aSpriteNorm = !aSpriteNormRes.IsNull() ? dynamic_cast<const OpenGl_PointSprite*> (aSpriteNormRes->First().get()) : NULL;
+ if (aSpriteNorm != NULL
+ && !aSpriteNorm->IsDisplayList())
{
- i = OGL_Rand() % n;
- myPArray->keys[i] = -myPArray->keys[i];
- }
+ // Textured markers will be drawn with the point sprites
+ aCtx->SetPointSize (anAspectMarker->MarkerSize());
+ aCtx->SetPointSpriteOrigin();
+ #if !defined(GL_ES_VERSION_2_0)
+ if (aCtx->core11 != NULL)
+ {
+ aCtx->core11fwd->glEnable (GL_ALPHA_TEST);
+ aCtx->core11fwd->glAlphaFunc (GL_GEQUAL, 0.1f);
+ }
+ #endif
- if (myPArray->num_bounds > 0)
- {
- if (myPArray->num_edges > 0)
+ aCtx->core11fwd->glEnable (GL_BLEND);
+ aCtx->core11fwd->glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+
+ aCtx->core11fwd->glDrawArrays (aDrawMode, 0, !myVboAttribs.IsNull() ? myVboAttribs->GetElemsNb() : myAttribs->NbElements);
+
+ aCtx->core11fwd->glDisable (GL_BLEND);
+ #if !defined(GL_ES_VERSION_2_0)
+ if (aCtx->core11 != NULL)
{
- for (i = n = 0; i < myPArray->num_bounds; ++i)
+ if (aCtx->ShaderManager()->MaterialState().AlphaCutoff() >= ShortRealLast())
{
- glBegin (GL_LINES);
- for (j = 0; j < myPArray->bounds[i]; ++j)
- {
- iv = myPArray->edges[n + j];
- if (myPArray->keys[iv] < 0)
- {
- myPArray->keys[iv] = -myPArray->keys[iv];
- glVertex3fv (pv[iv].xyz);
- }
- }
- glEnd();
- n += myPArray->bounds[i];
+ aCtx->core11fwd->glDisable (GL_ALPHA_TEST);
}
- }
- else
- {
- for (i = n = 0; i < myPArray->num_bounds; ++i)
+ else
{
- glBegin (GL_LINES);
- for (j = 0; j < myPArray->bounds[i]; ++j)
- {
- if (myPArray->keys[n+j] < 0)
- {
- myPArray->keys[n+j] = -myPArray->keys[n+j];
- glVertex3fv (pv[n+j].xyz);
- }
- }
- glEnd();
- n += myPArray->bounds[i];
+ aCtx->core11fwd->glAlphaFunc (GL_GEQUAL, aCtx->ShaderManager()->MaterialState().AlphaCutoff());
}
}
+ #endif
+ aCtx->SetPointSize (1.0f);
+ return;
}
- else if (myPArray->num_edges > 0)
+ else if (anAspectMarker->Aspect()->Type() == Aspect_TOM_POINT)
{
- glBegin (GL_LINES);
- for (j = 0; j < myPArray->num_edges; ++j)
+ aCtx->SetPointSize (anAspectMarker->MarkerSize());
+ aCtx->core11fwd->glDrawArrays (aDrawMode, 0, !myVboAttribs.IsNull() ? myVboAttribs->GetElemsNb() : myAttribs->NbElements);
+ aCtx->SetPointSize (1.0f);
+ }
+#if !defined(GL_ES_VERSION_2_0)
+ // Textured markers will be drawn with the glBitmap
+ else if (anAspectMarker->Aspect()->Type() != Aspect_TOM_POINT
+ && aSpriteNorm != NULL)
+ {
+ /**if (!isHilight && (myPArray->vcolours != NULL))
{
- iv = myPArray->edges[j];
- if (myPArray->keys[iv] < 0)
+ for (Standard_Integer anIter = 0; anIter < myAttribs->NbElements; anIter++)
{
- myPArray->keys[iv] = -myPArray->keys[iv];
- glVertex3fv (pv[iv].xyz);
+ glColor4ubv (myPArray->vcolours[anIter].GetData());
+ glRasterPos3fv (myAttribs->Value<Graphic3d_Vec3> (anIter).GetData());
+ aSpriteNorm->DrawBitmap (theWorkspace->GetGlContext());
}
}
- glEnd();
- }
- else
- {
- glBegin (GL_LINES);
- for (j = 0; j < myPArray->num_vertexs; ++j)
+ else*/
{
- if (myPArray->keys[j] < 0)
+ for (Standard_Integer anIter = 0; anIter < myAttribs->NbElements; anIter++)
{
- myPArray->keys[j] = -myPArray->keys[j];
- glVertex3fv (pv[j].xyz);
+ aCtx->core11->glRasterPos3fv (myAttribs->Value<Graphic3d_Vec3> (anIter).GetData());
+ aSpriteNorm->DrawBitmap (theWorkspace->GetGlContext());
}
}
- glEnd();
}
+#endif
}
// =======================================================================
-// function : DrawDegeneratesTrianglesAsLines
+// function : OpenGl_PrimitiveArray
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesTrianglesAsLines (const float theSkipRatio) const
-{
- Tint i, iv;
- tel_point pv = myPArray->vertices;
-
- Tint n = myPArray->num_vertexs / 3;
- Tint j = int((1.0f - theSkipRatio) * n);
- for (; j > 0; --j)
+OpenGl_PrimitiveArray::OpenGl_PrimitiveArray (const OpenGl_GraphicDriver* theDriver)
+
+: myDrawMode (DRAW_MODE_NONE),
+ myIsFillType(Standard_False),
+ myIsVboInit (Standard_False)
+{
+ if (theDriver != NULL)
{
- i = OGL_Rand() % n; i *= 3;
- myPArray->keys[i] = -myPArray->keys[i];
+ myUID = theDriver->GetNextPrimitiveArrayUID();
}
+}
- if (myPArray->num_edges > 0)
+// =======================================================================
+// function : OpenGl_PrimitiveArray
+// purpose :
+// =======================================================================
+OpenGl_PrimitiveArray::OpenGl_PrimitiveArray (const OpenGl_GraphicDriver* theDriver,
+ const Graphic3d_TypeOfPrimitiveArray theType,
+ const Handle(Graphic3d_IndexBuffer)& theIndices,
+ const Handle(Graphic3d_Buffer)& theAttribs,
+ const Handle(Graphic3d_BoundBuffer)& theBounds)
+
+: myIndices (theIndices),
+ myAttribs (theAttribs),
+ myBounds (theBounds),
+ myDrawMode (DRAW_MODE_NONE),
+ myIsFillType(Standard_False),
+ myIsVboInit (Standard_False)
+{
+ if (!myIndices.IsNull()
+ && myIndices->NbElements < 1)
{
- for (j = 0; j < myPArray->num_edges; j += 3)
- {
- iv = myPArray->edges[j];
- if (myPArray->keys[iv] < 0)
- {
- myPArray->keys[iv] = -myPArray->keys[iv];
- glBegin (GL_LINE_LOOP);
- for (i = 0; i < 3; ++i)
- {
- iv = myPArray->edges[j+i];
- glVertex3fv (pv[iv].xyz);
- }
- glEnd();
- }
- }
+ // dummy index buffer?
+ myIndices.Nullify();
}
- else
+
+ if (theDriver != NULL)
{
- for (j = 0; j < myPArray->num_vertexs; j += 3)
+ myUID = theDriver->GetNextPrimitiveArrayUID();
+ #if defined (GL_ES_VERSION_2_0)
+ const Handle(OpenGl_Context)& aCtx = theDriver->GetSharedContext();
+ if (!aCtx.IsNull())
{
- if (myPArray->keys[j] < 0)
- {
- myPArray->keys[j] = -myPArray->keys[j];
- glBegin (GL_LINE_LOOP);
- for (i = 0; i < 3; ++i)
- {
- glVertex3fv (pv[j+i].xyz);
- }
- glEnd();
- }
+ processIndices (aCtx);
}
+ #endif
}
+
+ setDrawMode (theType);
}
// =======================================================================
-// function : DrawDegeneratesTrianglesAsLines
+// function : ~OpenGl_PrimitiveArray
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesTrianglestripsAsLines (const float theSkipRatio) const
-{
- Tint i, j, k, n, ni;
- tel_point pv = myPArray->vertices;
+OpenGl_PrimitiveArray::~OpenGl_PrimitiveArray()
+{
+ //
+}
- if (myPArray->num_bounds > 0)
+// =======================================================================
+// function : Release
+// purpose :
+// =======================================================================
+void OpenGl_PrimitiveArray::Release (OpenGl_Context* theContext)
+{
+ myIsVboInit = Standard_False;
+ if (!myVboIndices.IsNull())
{
- for (i = n = 0; i < myPArray->num_bounds; ++i)
+ if (theContext)
{
- ni = myPArray->bounds[i] - 2;
- k = int((1.0f - theSkipRatio) * ni);
- for (; k > 0; --k)
- {
- j = OGL_Rand() % ni; j += 2;
- myPArray->keys[n+j] = -myPArray->keys[n+j];
- }
- for (j = 2; j < myPArray->bounds[i]; ++j)
- {
- if (myPArray->keys[n+j] < 0)
- {
- myPArray->keys[n+j] = -myPArray->keys[n+j];
- glBegin (GL_LINE_LOOP);
- glVertex3fv (pv[n+j-2].xyz);
- glVertex3fv (pv[n+j-1].xyz);
- glVertex3fv (pv[n+j].xyz);
- glEnd();
- }
- }
- n += myPArray->bounds[i];
+ theContext->DelayedRelease (myVboIndices);
}
+ myVboIndices.Nullify();
}
- else
+ if (!myVboAttribs.IsNull())
{
- ni = myPArray->num_vertexs - 2;
- k = int((1.0f - theSkipRatio) * ni);
- for (; k > 0; --k)
- {
- j = OGL_Rand() % ni; j += 2;
- myPArray->keys[j] = -myPArray->keys[j];
- }
- for (j = 2; j < myPArray->num_vertexs; ++j)
+ if (theContext)
{
- if (myPArray->keys[j] < 0)
- {
- myPArray->keys[j] = -myPArray->keys[j];
- glBegin (GL_LINE_LOOP);
- glVertex3fv (pv[j-2].xyz);
- glVertex3fv (pv[j-1].xyz);
- glVertex3fv (pv[j].xyz);
- glEnd();
- }
+ theContext->DelayedRelease (myVboAttribs);
}
+ myVboAttribs.Nullify();
}
}
// =======================================================================
-// function : DrawDegeneratesPolygonsAsLines
+// function : Render
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesPolygonsAsLines (const float theSkipRatio) const
-{
- Tint i, iv;
- tel_point pv = myPArray->vertices;
-
- Tint n = myPArray->num_vertexs;
- Tint j = int((1.0f - theSkipRatio) * n);
- for (; j > 0; --j)
+void OpenGl_PrimitiveArray::Render (const Handle(OpenGl_Workspace)& theWorkspace) const
+{
+ if (myDrawMode == DRAW_MODE_NONE)
{
- i = OGL_Rand() % n;
- myPArray->keys[i] = -myPArray->keys[i];
+ return;
}
- if (myPArray->num_bounds > 0)
+ const OpenGl_AspectFace* anAspectFace = theWorkspace->ApplyAspectFace();
+ const OpenGl_AspectLine* anAspectLine = theWorkspace->ApplyAspectLine();
+ const OpenGl_AspectMarker* anAspectMarker = myDrawMode == GL_POINTS
+ ? theWorkspace->ApplyAspectMarker()
+ : theWorkspace->AspectMarker();
+
+ const Handle(OpenGl_Context)& aCtx = theWorkspace->GetGlContext();
+
+ Handle(OpenGl_TextureSet) aTextureBack;
+ bool toDrawArray = true;
+ int toDrawInteriorEdges = 0; // 0 - no edges, 1 - glsl edges, 2 - polygonMode
+ if (myIsFillType)
{
- if (myPArray->num_edges > 0)
+ toDrawArray = anAspectFace->Aspect()->InteriorStyle() != Aspect_IS_EMPTY;
+ if (anAspectFace->Aspect()->ToDrawEdges())
{
- for (i = n = 0; i < myPArray->num_bounds; ++i)
+ toDrawInteriorEdges = 1;
+ toDrawArray = true;
+ #if !defined(GL_ES_VERSION_2_0)
+ if (anAspectFace->Aspect()->EdgeLineType() != Aspect_TOL_SOLID
+ || aCtx->hasGeometryStage == OpenGl_FeatureNotAvailable
+ || aCtx->caps->usePolygonMode)
{
- glBegin (GL_LINE_LOOP);
- for (j = 0; j < myPArray->bounds[i]; ++j)
+ toDrawInteriorEdges = 2;
+ if (anAspectFace->Aspect()->InteriorStyle() == Aspect_IS_EMPTY)
{
- iv = myPArray->edges[n+j];
- if (myPArray->keys[iv] < 0)
+ if (anAspectFace->Aspect()->EdgeLineType() != Aspect_TOL_SOLID)
{
- myPArray->keys[iv] = -myPArray->keys[iv];
- glVertex3fv (pv[iv].xyz);
+ toDrawArray = false;
}
- }
- glEnd();
- n += myPArray->bounds[i];
- }
- }
- else
- {
- for (i = n = 0; i < myPArray->num_bounds; ++i)
- {
- glBegin (GL_LINE_LOOP);
- for (j = 0; j < myPArray->bounds[i]; ++j)
- {
- if (myPArray->keys[n+j] < 0)
+ else
{
- myPArray->keys[n+j] = -myPArray->keys[n+j];
- glVertex3fv (pv[n+j].xyz);
+ aCtx->SetPolygonMode (GL_LINE);
}
}
- glEnd();
- n += myPArray->bounds[i];
}
+ #endif
}
}
- else if (myPArray->num_edges > 0)
+ else
{
- glBegin (GL_LINE_LOOP);
- for (j = 0; j < myPArray->num_edges; ++j)
+ if (myDrawMode == GL_POINTS)
{
- iv = myPArray->edges[j];
- if (myPArray->keys[iv] < 0)
+ if (anAspectMarker->Aspect()->Type() == Aspect_TOM_EMPTY)
{
- myPArray->keys[iv] = -myPArray->keys[iv];
- glVertex3fv (pv[iv].xyz);
+ return;
}
}
- glEnd();
- }
- else
- {
- glBegin (GL_LINE_LOOP);
- for (j = 0; j < myPArray->num_vertexs; ++j)
+ else
{
- if (myPArray->keys[j] < 0)
+ if (anAspectLine->Aspect()->Type() == Aspect_TOL_EMPTY)
{
- myPArray->keys[j] = -myPArray->keys[j];
- glVertex3fv (pv[j].xyz);
+ return;
}
}
- glEnd();
- }
-}
-// =======================================================================
-// function : DrawDegeneratesQuadranglesAsLines
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesQuadranglesAsLines (const float theSkipRatio) const
-{
- Tint i, iv;
- tel_point pv = myPArray->vertices;
+ // Temporarily disable environment mapping
+ aTextureBack = aCtx->BindTextures (Handle(OpenGl_TextureSet)());
+ }
- Tint n = myPArray->num_vertexs / 4;
- Tint j = int((1.0f - theSkipRatio) * n);
- for (; j > 0; --j)
+ // create VBOs on first render call
+ if (!myIsVboInit)
+ {
+ // compatibility - keep data to draw markers using display lists
+ Standard_Boolean toKeepData = Standard_False;
+ if (myDrawMode == GL_POINTS)
+ {
+ const Handle(OpenGl_TextureSet)& aSpriteNormRes = anAspectMarker->SpriteRes (aCtx);
+ const OpenGl_PointSprite* aSpriteNorm = !aSpriteNormRes.IsNull() ? dynamic_cast<const OpenGl_PointSprite*> (aSpriteNormRes->First().get()) : NULL;
+ toKeepData = aSpriteNorm != NULL
+ && aSpriteNorm->IsDisplayList();
+ }
+ #if defined (GL_ES_VERSION_2_0)
+ processIndices (aCtx);
+ #endif
+ buildVBO (aCtx, toKeepData);
+ myIsVboInit = Standard_True;
+ }
+ else if ((!myAttribs.IsNull()
+ && myAttribs->IsMutable())
+ || (!myIndices.IsNull()
+ && myIndices->IsMutable()))
{
- i = OGL_Rand() % n; i *= 4;
- myPArray->keys[i] = -myPArray->keys[i];
+ updateVBO (aCtx);
}
- if (myPArray->num_edges > 0)
+ Graphic3d_TypeOfShadingModel aShadingModel = Graphic3d_TOSM_UNLIT;
+ if (toDrawArray)
{
- for (j = 0; j < myPArray->num_edges; j += 4)
+ const bool hasColorAttrib = !myVboAttribs.IsNull()
+ && myVboAttribs->HasColorAttribute();
+ const bool toHilight = theWorkspace->ToHighlight();
+ const bool hasVertColor = hasColorAttrib && !toHilight;
+ const bool hasVertNorm = !myVboAttribs.IsNull() && myVboAttribs->HasNormalAttribute();
+ switch (myDrawMode)
{
- iv = myPArray->edges[j];
- if (myPArray->keys[iv] < 0)
+ case GL_POINTS:
{
- myPArray->keys[iv] = -myPArray->keys[iv];
- glBegin (GL_LINE_LOOP);
- for (i = 0; i < 4; ++i)
+ aShadingModel = aCtx->ShaderManager()->ChooseMarkerShadingModel (anAspectFace->ShadingModel(), hasVertNorm);
+ const Handle(OpenGl_TextureSet)& aSpriteNormRes = anAspectMarker->SpriteRes (aCtx);
+ const OpenGl_PointSprite* aSpriteNorm = !aSpriteNormRes.IsNull() ? dynamic_cast<const OpenGl_PointSprite*> (aSpriteNormRes->First().get()) : NULL;
+ if (aSpriteNorm != NULL
+ && !aSpriteNorm->IsDisplayList())
+ {
+ const Handle(OpenGl_TextureSet)& aSprite = toHilight && anAspectMarker->SpriteHighlightRes (aCtx)->First()->IsValid()
+ ? anAspectMarker->SpriteHighlightRes (aCtx)
+ : aSpriteNormRes;
+ aCtx->BindTextures (aSprite);
+ aCtx->ShaderManager()->BindMarkerProgram (aSprite, aShadingModel, Graphic3d_AlphaMode_Opaque, hasVertColor, anAspectMarker->ShaderProgramRes (aCtx));
+ }
+ else
{
- iv = myPArray->edges[j+i];
- glVertex3fv (pv[iv].xyz);
+ aCtx->ShaderManager()->BindMarkerProgram (Handle(OpenGl_TextureSet)(), aShadingModel, Graphic3d_AlphaMode_Opaque, hasVertColor, anAspectMarker->ShaderProgramRes (aCtx));
}
- glEnd();
+ break;
}
- }
- }
- else
- {
- for (j = 0; j < myPArray->num_vertexs; j += 4)
- {
- if (myPArray->keys[j] < 0)
+ case GL_LINES:
+ case GL_LINE_STRIP:
+ {
+ aShadingModel = aCtx->ShaderManager()->ChooseLineShadingModel (anAspectFace->ShadingModel(), hasVertNorm);
+ aCtx->ShaderManager()->BindLineProgram (NULL,
+ anAspectLine->Aspect()->Type(),
+ aShadingModel,
+ Graphic3d_AlphaMode_Opaque,
+ hasVertColor,
+ anAspectLine->ShaderProgramRes (aCtx));
+ break;
+ }
+ default:
{
- myPArray->keys[j] = -myPArray->keys[j];
- glBegin (GL_LINE_LOOP);
- for (i = 0; i < 4; ++i)
+ aShadingModel = aCtx->ShaderManager()->ChooseFaceShadingModel (anAspectFace->ShadingModel(), hasVertNorm);
+ const Handle(OpenGl_TextureSet)& aTextures = aCtx->ActiveTextures();
+ const Standard_Boolean toEnableEnvMap = (!aTextures.IsNull() && (aTextures == theWorkspace->EnvironmentTexture()));
+ aCtx->ShaderManager()->BindFaceProgram (aTextures,
+ aShadingModel,
+ aCtx->ShaderManager()->MaterialState().HasAlphaCutoff() ? Graphic3d_AlphaMode_Mask : Graphic3d_AlphaMode_Opaque,
+ toDrawInteriorEdges == 1 ? anAspectFace->Aspect()->InteriorStyle() : Aspect_IS_SOLID,
+ hasVertColor,
+ toEnableEnvMap,
+ toDrawInteriorEdges == 1,
+ anAspectFace->ShaderProgramRes (aCtx));
+ if (toDrawInteriorEdges == 1)
{
- glVertex3fv (pv[j+i].xyz);
+ aCtx->ShaderManager()->PushInteriorState (aCtx->ActiveProgram(), anAspectFace->Aspect());
}
- glEnd();
+ break;
}
}
- }
-}
-
-// =======================================================================
-// function : DrawDegeneratesQuadranglesAsLines
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesQuadranglestripsAsLines (const float theSkipRatio) const
-{
- Tint i, j, k, n, ni;
- tel_point pv = myPArray->vertices;
- if (myPArray->num_bounds > 0)
- {
- for (i = n = 0; i < myPArray->num_bounds; ++i)
+ #if !defined(GL_ES_VERSION_2_0)
+ // manage FFP lighting
+ if (aCtx->ActiveProgram().IsNull()
+ && aCtx->core11 != NULL)
{
- ni = myPArray->bounds[i] / 2 - 2;
- k = int((1.0f - theSkipRatio) * ni);
- for (; k > 0; --k)
+ if (aShadingModel == Graphic3d_TOSM_UNLIT)
{
- j = OGL_Rand() % ni; j = j * 2 + 2;
- myPArray->keys[n+j] = -myPArray->keys[n+j];
+ glDisable (GL_LIGHTING);
}
- for (j = 3; j < myPArray->bounds[i]; j += 2)
+ else
{
- if (myPArray->keys[n+j] < 0)
- {
- myPArray->keys[n+j] = -myPArray->keys[n+j];
- glBegin (GL_LINE_LOOP);
- glVertex3fv (pv[n+j-3].xyz);
- glVertex3fv (pv[n+j-2].xyz);
- glVertex3fv (pv[n+j-1].xyz);
- glVertex3fv (pv[n+j].xyz);
- glEnd();
- }
+ glEnable (GL_LIGHTING);
}
- n += myPArray->bounds[i];
}
- }
- else
- {
- ni = myPArray->num_vertexs / 2 - 2;
- k = int((1.0f - theSkipRatio) * ni);
- for (; k > 0; --k)
+ #endif
+
+ if (!aCtx->ActiveTextures().IsNull()
+ && !aCtx->ActiveTextures()->IsEmpty()
+ && !aCtx->ActiveTextures()->First().IsNull()
+ && myDrawMode != GL_POINTS) // transformation is not supported within point sprites
{
- j = OGL_Rand() % ni; j = j * 2 + 2;
- myPArray->keys[j] = -myPArray->keys[j];
+ aCtx->SetTextureMatrix (aCtx->ActiveTextures()->First()->Sampler()->Parameters());
}
- for (j = 3; j < myPArray->num_vertexs; j += 2)
+
+ const Graphic3d_Vec4* aFaceColors = !myBounds.IsNull() && !toHilight && anAspectFace->Aspect()->InteriorStyle() != Aspect_IS_HIDDENLINE
+ ? myBounds->Colors
+ : NULL;
+ if (!myIsFillType)
{
- if (myPArray->keys[j] < 0)
+ const OpenGl_Vec4& aLineColor = myDrawMode == GL_POINTS ? theWorkspace->MarkerColor() : theWorkspace->LineColor();
+ aCtx->SetColor4fv (aLineColor);
+ if (myDrawMode == GL_LINES
+ || myDrawMode == GL_LINE_STRIP)
{
- myPArray->keys[j] = -myPArray->keys[j];
- glBegin (GL_LINE_LOOP);
- glVertex3fv (pv[j-3].xyz);
- glVertex3fv (pv[j-2].xyz);
- glVertex3fv (pv[j-1].xyz);
- glVertex3fv (pv[j].xyz);
- glEnd();
+ aCtx->SetTypeOfLine (anAspectLine->Aspect()->Type());
+ aCtx->SetLineWidth (anAspectLine->Aspect()->Width());
}
- }
- }
-}
-// =======================================================================
-// function : DrawDegeneratesAsLines
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesAsLines (const TEL_COLOUR* theEdgeColour,
- const Handle(OpenGl_Workspace)& theWorkspace) const
-{
- const float aSkipRatio = theWorkspace->SkipRatio;
+ drawArray (theWorkspace, aFaceColors, hasColorAttrib);
+ aCtx->BindTextures (aTextureBack);
+ return;
+ }
- GLboolean zbuff_state = glIsEnabled (GL_DEPTH_TEST);
+ const OpenGl_Vec4& anInteriorColor = theWorkspace->InteriorColor();
+ aCtx->SetColor4fv (anInteriorColor);
+ drawArray (theWorkspace, aFaceColors, hasColorAttrib);
- glDisable (GL_LIGHTING);
+ // draw outline - only closed triangulation with defined vertex normals can be drawn in this way
+ if (anAspectFace->Aspect()->ToDrawSilhouette()
+ && aCtx->ToCullBackFaces()
+ && aCtx->ShaderManager()->BindOutlineProgram())
+ {
+ const Graphic3d_Vec2i aViewSize (aCtx->Viewport()[2], aCtx->Viewport()[3]);
+ const Standard_Integer aMin = aViewSize.minComp();
+ const GLfloat anEdgeWidth = (GLfloat )anAspectFace->Aspect()->EdgeWidth() * aCtx->LineWidthScale() / (GLfloat )aMin;
+ const GLfloat anOrthoScale = theWorkspace->View()->Camera()->IsOrthographic() ? (GLfloat )theWorkspace->View()->Camera()->Scale() : -1.0f;
- if (zbuff_state)
- glDisable (GL_DEPTH_TEST);
+ const Handle(OpenGl_ShaderProgram)& anOutlineProgram = aCtx->ActiveProgram();
+ anOutlineProgram->SetUniform (aCtx, anOutlineProgram->GetStateLocation (OpenGl_OCCT_SILHOUETTE_THICKNESS), anEdgeWidth);
+ anOutlineProgram->SetUniform (aCtx, anOutlineProgram->GetStateLocation (OpenGl_OCCT_ORTHO_SCALE), anOrthoScale);
+ aCtx->SetColor4fv (anAspectFace->Aspect()->EdgeColorRGBA());
- glColor3fv (theEdgeColour->rgb);
+ aCtx->core11fwd->glCullFace (GL_FRONT);
+ drawArray (theWorkspace, NULL, false);
- if (aSkipRatio != 0.0f)
- {
- switch (myDrawMode)
- {
- case GL_POINTS:
- if (aSkipRatio < 1.0f)
- DrawDegeneratesPointsAsPoints();
- break;
- case GL_LINES:
- DrawDegeneratesLinesAsLines (aSkipRatio);
- break;
- case GL_LINE_STRIP:
- case GL_POLYGON:
- DrawDegeneratesPolygonsAsLines (aSkipRatio);
- break;
- case GL_TRIANGLES:
- DrawDegeneratesTrianglesAsLines (aSkipRatio);
- break;
- case GL_QUADS:
- DrawDegeneratesQuadranglesAsLines (aSkipRatio);
- break;
- case GL_TRIANGLE_FAN:
- case GL_TRIANGLE_STRIP:
- DrawDegeneratesTrianglestripsAsLines (aSkipRatio);
- break;
- case GL_QUAD_STRIP:
- DrawDegeneratesQuadranglestripsAsLines (aSkipRatio);
- break;
- default:
- break;
+ aCtx->core11fwd->glCullFace (GL_BACK);
}
}
- else
- {
- int i,n;
- glPushAttrib (GL_POLYGON_BIT);
- glPolygonMode (GL_FRONT_AND_BACK, GL_LINE);
-
- GLboolean color_array_mode = glIsEnabled (GL_COLOR_ARRAY);
- GLboolean edge_flag_array_mode = glIsEnabled (GL_EDGE_FLAG_ARRAY);
- GLboolean index_array_mode = glIsEnabled (GL_INDEX_ARRAY);
- GLboolean normal_array_mode = glIsEnabled (GL_NORMAL_ARRAY);
- GLboolean texture_coord_array_mode = glIsEnabled (GL_TEXTURE_COORD_ARRAY);
- GLboolean vertex_array_mode = glIsEnabled (GL_VERTEX_ARRAY);
-
- glDisableClientState (GL_COLOR_ARRAY);
- glDisableClientState (GL_EDGE_FLAG_ARRAY);
- glDisableClientState (GL_INDEX_ARRAY);
- glDisableClientState (GL_NORMAL_ARRAY);
- glDisableClientState (GL_TEXTURE_COORD_ARRAY);
-
- if (!vertex_array_mode)
- glEnableClientState (GL_VERTEX_ARRAY);
- glVertexPointer (3, GL_FLOAT, 0, myPArray->vertices); // array of vertices
-
- if (myPArray->num_bounds > 0)
- {
- if (myPArray->num_edges > 0)
- {
- for (i = n = 0; i < myPArray->num_bounds; ++i)
- {
- glDrawElements (myDrawMode, myPArray->bounds[i], GL_UNSIGNED_INT, (GLenum* )&myPArray->edges[n]);
- n += myPArray->bounds[i];
- }
- }
- else
- {
- for (i = n = 0; i < myPArray->num_bounds; ++i)
- {
- glDrawArrays (myDrawMode, n, myPArray->bounds[i]);
- n += myPArray->bounds[i];
- }
- }
- }
- else if (myPArray->num_edges > 0)
+#if !defined(GL_ES_VERSION_2_0)
+ // draw triangulation edges using Polygon Mode
+ if (toDrawInteriorEdges == 2)
+ {
+ if (anAspectFace->Aspect()->InteriorStyle() == Aspect_IS_HOLLOW
+ && anAspectFace->Aspect()->EdgeLineType() == Aspect_TOL_SOLID)
{
- glDrawElements (myDrawMode, myPArray->num_edges, GL_UNSIGNED_INT, (GLenum* )myPArray->edges);
+ aCtx->SetPolygonMode (GL_FILL);
}
else
{
- glDrawArrays (myDrawMode, 0, myPArray->num_vertexs);
+ const OpenGl_Vec4& anEdgeColor = theWorkspace->EdgeColor();
+ drawEdges (anEdgeColor, theWorkspace);
}
-
- if (!vertex_array_mode) glDisableClientState (GL_VERTEX_ARRAY);
-
- if (color_array_mode) glEnableClientState (GL_COLOR_ARRAY);
- if (edge_flag_array_mode) glEnableClientState (GL_EDGE_FLAG_ARRAY);
- if (index_array_mode) glEnableClientState (GL_INDEX_ARRAY);
- if (normal_array_mode) glEnableClientState (GL_NORMAL_ARRAY);
- if (texture_coord_array_mode) glEnableClientState (GL_TEXTURE_COORD_ARRAY);
-
- glPopAttrib();
}
-
- if (zbuff_state)
- glEnable(GL_DEPTH_TEST);
-}
+#endif
+}
// =======================================================================
-// function : DrawDegeneratesAsBBoxs
+// function : setDrawMode
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::DrawDegeneratesAsBBoxs (const TEL_COLOUR* theEdgeColour) const
+void OpenGl_PrimitiveArray::setDrawMode (const Graphic3d_TypeOfPrimitiveArray theType)
{
- GLfloat minp[3] = { FLT_MAX, FLT_MAX, FLT_MAX };
- GLfloat maxp[3] = { FLT_MIN, FLT_MIN, FLT_MIN };
- tel_point pv = myPArray->vertices;
-
- glDisable (GL_LIGHTING);
-
- glColor3fv (theEdgeColour->rgb);
-
- for (Tint i = 0; i < myPArray->num_vertexs; ++i)
+ if (myAttribs.IsNull())
{
- if (pv[i].xyz[0] < minp[0])
- minp[0] = pv[i].xyz[0];
- if (pv[i].xyz[1] < minp[1])
- minp[1] = pv[i].xyz[1];
- if (pv[i].xyz[2] < minp[2])
- minp[2] = pv[i].xyz[2];
-
- if (pv[i].xyz[0] > maxp[0])
- maxp[0] = pv[i].xyz[0];
- if (pv[i].xyz[1] > maxp[1])
- maxp[1] = pv[i].xyz[1];
- if (pv[i].xyz[2] > maxp[2])
- maxp[2] = pv[i].xyz[2];
+ myDrawMode = DRAW_MODE_NONE;
+ myIsFillType = false;
+ return;
}
- glBegin (GL_LINE_STRIP);
-
- glVertex3fv (minp);
- glVertex3f (minp[0], maxp[1], minp[2]);
- glVertex3f (minp[0], maxp[1], maxp[2]);
- glVertex3f (minp[0], minp[1], maxp[2]);
- glVertex3f (minp[0], minp[1], minp[2]);
-
- glVertex3f (maxp[0], minp[1], minp[2]);
- glVertex3f (maxp[0], maxp[1], minp[2]);
- glVertex3f (maxp[0], maxp[1], maxp[2]);
- glVertex3f (maxp[0], minp[1], maxp[2]);
- glVertex3f (maxp[0], minp[1], minp[2]);
-
- glVertex3f (maxp[0], minp[1], maxp[2]);
- glVertex3f (minp[0], minp[1], maxp[2]);
- glVertex3f (minp[0], maxp[1], maxp[2]);
- glVertex3fv (maxp);
- glVertex3f (maxp[0], maxp[1], minp[2]);
- glVertex3f (minp[0], maxp[1], minp[2]);
-
- glEnd();
-}
-
-// =======================================================================
-// function : OpenGl_PrimitiveArray
-// purpose :
-// =======================================================================
-OpenGl_PrimitiveArray::OpenGl_PrimitiveArray (CALL_DEF_PARRAY* thePArray)
-: myPArray (thePArray),
- myDrawMode (DRAW_MODE_NONE),
- myIsVboInit (Standard_False)
-{
- switch (myPArray->type)
+ switch (theType)
{
- case TelPointsArrayType:
- myDrawMode = GL_POINTS;
+ case Graphic3d_TOPA_POINTS:
+ myDrawMode = GL_POINTS;
+ myIsFillType = false;
break;
- case TelPolylinesArrayType:
- myDrawMode = GL_LINE_STRIP;
+ case Graphic3d_TOPA_SEGMENTS:
+ myDrawMode = GL_LINES;
+ myIsFillType = false;
break;
- case TelSegmentsArrayType:
- myDrawMode = GL_LINES;
+ case Graphic3d_TOPA_POLYLINES:
+ myDrawMode = GL_LINE_STRIP;
+ myIsFillType = false;
break;
- case TelPolygonsArrayType:
- myDrawMode = GL_POLYGON;
+ case Graphic3d_TOPA_TRIANGLES:
+ myDrawMode = GL_TRIANGLES;
+ myIsFillType = true;
break;
- case TelTrianglesArrayType:
- myDrawMode = GL_TRIANGLES;
+ case Graphic3d_TOPA_TRIANGLESTRIPS:
+ myDrawMode = GL_TRIANGLE_STRIP;
+ myIsFillType = true;
break;
- case TelQuadranglesArrayType:
- myDrawMode = GL_QUADS;
+ case Graphic3d_TOPA_TRIANGLEFANS:
+ myDrawMode = GL_TRIANGLE_FAN;
+ myIsFillType = true;
break;
- case TelTriangleStripsArrayType:
- myDrawMode = GL_TRIANGLE_STRIP;
+ //
+ case Graphic3d_TOPA_LINES_ADJACENCY:
+ myDrawMode = GL_LINES_ADJACENCY;
+ myIsFillType = false;
break;
- case TelQuadrangleStripsArrayType:
- myDrawMode = GL_QUAD_STRIP;
+ case Graphic3d_TOPA_LINE_STRIP_ADJACENCY:
+ myDrawMode = GL_LINE_STRIP_ADJACENCY;
+ myIsFillType = false;
break;
- case TelTriangleFansArrayType:
- myDrawMode = GL_TRIANGLE_FAN;
+ case Graphic3d_TOPA_TRIANGLES_ADJACENCY:
+ myDrawMode = GL_TRIANGLES_ADJACENCY;
+ myIsFillType = true;
+ break;
+ case Graphic3d_TOPA_TRIANGLE_STRIP_ADJACENCY:
+ myDrawMode = GL_TRIANGLE_STRIP_ADJACENCY;
+ myIsFillType = true;
+ break;
+ //
+ #if !defined(GL_ES_VERSION_2_0)
+ case Graphic3d_TOPA_QUADRANGLES:
+ myDrawMode = GL_QUADS;
+ myIsFillType = true;
+ break;
+ case Graphic3d_TOPA_QUADRANGLESTRIPS:
+ myDrawMode = GL_QUAD_STRIP;
+ myIsFillType = true;
+ break;
+ case Graphic3d_TOPA_POLYGONS:
+ myDrawMode = GL_POLYGON;
+ myIsFillType = true;
+ break;
+ #else
+ case Graphic3d_TOPA_QUADRANGLES:
+ case Graphic3d_TOPA_QUADRANGLESTRIPS:
+ case Graphic3d_TOPA_POLYGONS:
+ #endif
+ case Graphic3d_TOPA_UNDEFINED:
+ myDrawMode = DRAW_MODE_NONE;
+ myIsFillType = false;
break;
}
}
// =======================================================================
-// function : ~OpenGl_PrimitiveArray
-// purpose :
-// =======================================================================
-OpenGl_PrimitiveArray::~OpenGl_PrimitiveArray()
-{
- //
-}
-
-// =======================================================================
-// function : Release
-// purpose :
-// =======================================================================
-void OpenGl_PrimitiveArray::Release (const Handle(OpenGl_Context)& theContext)
-{
- for (Standard_Integer anIter = 0; anIter < VBOMaxType; ++anIter)
- {
- if (!myVbos[anIter].IsNull())
- {
- theContext->DelayedRelease (myVbos[anIter]);
- myVbos[anIter].Nullify();
- }
- }
-}
-
-// =======================================================================
-// function : Render
+// function : processIndices
// purpose :
// =======================================================================
-void OpenGl_PrimitiveArray::Render (const Handle(OpenGl_Workspace)& theWorkspace) const
+Standard_Boolean OpenGl_PrimitiveArray::processIndices (const Handle(OpenGl_Context)& theContext) const
{
- if (myPArray == NULL || myDrawMode == DRAW_MODE_NONE || myPArray->num_vertexs <= 0)
- return;
-
- // create VBOs on first render call
- if (!myIsVboInit && OpenGl_GraphicDriver::ToUseVBO() && theWorkspace->GetGlContext()->core15 != NULL)
+ if (myIndices.IsNull()
+ || myAttribs.IsNull()
+ || theContext->hasUintIndex)
{
- BuildVBO (theWorkspace);
- myIsVboInit = Standard_True;
+ return Standard_True;
}
- switch (myPArray->type)
+ if (myAttribs->NbElements > std::numeric_limits<GLushort>::max())
{
- case TelPointsArrayType:
- case TelPolylinesArrayType:
- case TelSegmentsArrayType:
+ Handle(Graphic3d_Buffer) anAttribs = new Graphic3d_Buffer (new NCollection_AlignedAllocator (16));
+ if (!anAttribs->Init (myIndices->NbElements, myAttribs->AttributesArray(), myAttribs->NbAttributes))
{
- glDisable (GL_LIGHTING);
-
- if ((theWorkspace->NamedStatus & OPENGL_NS_ANIMATION) != 0 &&
- (theWorkspace->NamedStatus & OPENGL_NS_WIREFRAME) == 0 &&
- theWorkspace->DegenerateModel)
- {
- glDisable (GL_DEPTH_TEST);
- if (theWorkspace->NamedStatus & OPENGL_NS_TEXTURE)
- DisableTexture();
- theWorkspace->NamedStatus |= OPENGL_NS_WIREFRAME;
- }
- break;
+ return Standard_False; // failed to initialize attribute array
}
- case TelPolygonsArrayType:
- case TelTrianglesArrayType:
- case TelQuadranglesArrayType:
- case TelTriangleStripsArrayType:
- case TelTriangleFansArrayType:
- case TelQuadrangleStripsArrayType:
+
+ for (Standard_Integer anIdxIdx = 0; anIdxIdx < myIndices->NbElements; ++anIdxIdx)
{
- if ((theWorkspace->NamedStatus & OPENGL_NS_ANIMATION) != 0 &&
- (theWorkspace->NamedStatus & OPENGL_NS_WIREFRAME) != 0 &&
- theWorkspace->DegenerateModel < 2)
- {
- if (theWorkspace->NamedStatus & OPENGL_NS_TEXTURE)
- EnableTexture();
- glEnable (GL_DEPTH_TEST);
- theWorkspace->NamedStatus &= ~OPENGL_NS_WIREFRAME;
- }
- break;
+ const Standard_Integer anIndex = myIndices->Index (anIdxIdx);
+ memcpy (anAttribs->ChangeData() + myAttribs->Stride * anIdxIdx,
+ myAttribs->Data() + myAttribs->Stride * anIndex,
+ myAttribs->Stride);
}
- default:
- break;
- }
- const OpenGl_AspectFace* anAspectFace = theWorkspace->AspectFace (Standard_True);
- const OpenGl_AspectLine* anAspectLine = theWorkspace->AspectLine (Standard_True);
- const OpenGl_AspectMarker* anAspectMarker = theWorkspace->AspectMarker (myPArray->type == TelPointsArrayType);
+ myIndices.Nullify();
+ myAttribs = anAttribs;
+ }
- Tint aFrontLightingModel = anAspectFace->Context().IntFront.color_mask;
- const TEL_COLOUR* anInteriorColor = &anAspectFace->Context().IntFront.matcol;
- const TEL_COLOUR* anEdgeColor = &anAspectFace->AspectEdge()->Color();
- const TEL_COLOUR* aLineColor = (myPArray->type == TelPointsArrayType) ? &anAspectMarker->Color() : &anAspectLine->Color();
+ return Standard_True;
+}
- // Use highlight colors
- if (theWorkspace->NamedStatus & OPENGL_NS_HIGHLIGHT)
- {
- anEdgeColor = anInteriorColor = aLineColor = theWorkspace->HighlightColor;
- aFrontLightingModel = 0;
- }
+// =======================================================================
+// function : InitBuffers
+// purpose :
+// =======================================================================
+void OpenGl_PrimitiveArray::InitBuffers (const Handle(OpenGl_Context)& theContext,
+ const Graphic3d_TypeOfPrimitiveArray theType,
+ const Handle(Graphic3d_IndexBuffer)& theIndices,
+ const Handle(Graphic3d_Buffer)& theAttribs,
+ const Handle(Graphic3d_BoundBuffer)& theBounds)
+{
+ // Release old graphic resources
+ Release (theContext.operator->());
- DrawArray (aFrontLightingModel,
- anAspectFace->Context().InteriorStyle,
- anAspectFace->Context().Edge,
- anInteriorColor,
- aLineColor,
- anEdgeColor,
- &anAspectFace->Context().IntFront,
- theWorkspace);
+ myIndices = theIndices;
+ myAttribs = theAttribs;
+ myBounds = theBounds;
+#if defined(GL_ES_VERSION_2_0)
+ processIndices (theContext);
+#endif
- switch (myPArray->type)
- {
- case TelPointsArrayType:
- case TelPolylinesArrayType:
- case TelSegmentsArrayType:
- {
- if (theWorkspace->NamedStatus & OPENGL_NS_TEXTURE)
- EnableTexture();
- }
- }
+ setDrawMode (theType);
}