From: rnv Date: Mon, 5 Sep 2016 11:36:26 +0000 (+0300) Subject: Merge remote-tracking branch 'origin/rnv/vtk_opengl2_backend' into V8_1_BR X-Git-Tag: V8_1_0rc1~8 X-Git-Url: http://git.salome-platform.org/gitweb/?a=commitdiff_plain;h=e4de1ecd1242ddd90a60bc87beefc8d2af6020db;hp=dbb4ff3fe5d2081effa5d1c33abb482eaad22134;p=modules%2Fgui.git Merge remote-tracking branch 'origin/rnv/vtk_opengl2_backend' into V8_1_BR --- diff --git a/CMakeLists.txt b/CMakeLists.txt index a93a9a76c..cf51d49d4 100755 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -211,10 +211,15 @@ IF(SALOME_USE_VTKVIEWER) # Required components are listed in the FindSalomeVTK.cmake file: FIND_PACKAGE(SalomeVTK) SALOME_LOG_OPTIONAL_PACKAGE(VTK SALOME_USE_VTKVIEWER) + IF(${VTK_RENDERING_BACKEND} STREQUAL "OpenGL2") + ADD_DEFINITIONS("-DVTK_OPENGL2") + SET(SALOME_GUI_USE_OPENGL2 TRUE) + ENDIF() ELSE() ADD_DEFINITIONS("-DDISABLE_VTKVIEWER") ENDIF() + # - Plot2d viewer: Qwt IF(SALOME_USE_PLOT2DVIEWER) FIND_PACKAGE(SalomeQwt) diff --git a/SalomeGUIConfig.cmake.in b/SalomeGUIConfig.cmake.in index 0c9f163cd..74af92640 100644 --- a/SalomeGUIConfig.cmake.in +++ b/SalomeGUIConfig.cmake.in @@ -65,6 +65,7 @@ SET(SALOME_USE_PYCONSOLE @SALOME_USE_PYCONSOLE@) SET(SALOME_USE_SALOMEOBJECT @SALOME_USE_SALOMEOBJECT@) SET(SALOME_USE_SINGLE_DESKTOP @SALOME_USE_SINGLE_DESKTOP@) SET(SALOME_GUI_USE_OBSERVERS @SALOME_GUI_USE_OBSERVERS@) +SET(SALOME_GUI_USE_OPENGL2 @SALOME_GUI_USE_OPENGL2@) IF(SALOME_GUI_LIGHT_ONLY) LIST(APPEND GUI_DEFINITIONS "-DGUI_DISABLE_CORBA") @@ -84,6 +85,10 @@ ENDIF() IF(NOT SALOME_USE_VTKVIEWER) LIST(APPEND GUI_DEFINITIONS "-DDISABLE_VTKVIEWER") +ELSE() + IF(SALOME_GUI_USE_OPENGL2) + LIST(APPEND GUI_DEFINITIONS "-DVTK_OPENGL2") + ENDIF() ENDIF() IF(NOT SALOME_USE_PLOT2DVIEWER) LIST(APPEND GUI_DEFINITIONS "-DDISABLE_PLOT2DVIEWER") diff --git a/src/OpenGLUtils/OpenGLUtils_FrameBuffer.cxx b/src/OpenGLUtils/OpenGLUtils_FrameBuffer.cxx index 95c68c1df..d0f822174 100755 --- a/src/OpenGLUtils/OpenGLUtils_FrameBuffer.cxx +++ b/src/OpenGLUtils/OpenGLUtils_FrameBuffer.cxx @@ -20,6 +20,10 @@ // File : OpenGLUtils_FrameBuffer.cxx // Module : SALOME // +#ifdef VTK_OPENGL2 +#define GL_GLEXT_PROTOTYPES +#endif + #include "OpenGLUtils_FrameBuffer.h" #include @@ -128,8 +132,21 @@ OpenGLUtils_FrameBuffer::~OpenGLUtils_FrameBuffer() bool OpenGLUtils_FrameBuffer::init( const GLsizei& xSize, const GLsizei& ySize ) { +#ifdef VTK_OPENGL2 + int n = 0; + std::ostringstream strm; + glGetIntegerv(GL_NUM_EXTENSIONS, &n); + for (int i = 0; i < n; i++) + { + const char *exti = (const char *)glGetStringi(GL_EXTENSIONS, i); + strm<< exti <<" "; + } + std::string s = strm.str(); + const char* ext = s.c_str(); +#else char* ext = (char*)glGetString( GL_EXTENSIONS ); - if( !IsEXTInitialized || +#endif + if( !IsEXTInitialized || !ext || strstr( ext, "GL_EXT_framebuffer_object" ) == NULL ) { MESSAGE( "Initializing OpenGL FrameBuffer extension failed" ); diff --git a/src/VTKViewer/CMakeLists.txt b/src/VTKViewer/CMakeLists.txt index 6bb54339b..7d0d468e2 100755 --- a/src/VTKViewer/CMakeLists.txt +++ b/src/VTKViewer/CMakeLists.txt @@ -69,6 +69,7 @@ SET(_other_HEADERS VTKViewer_InteractorStyle.h VTKViewer_MarkerDef.h VTKViewer_MarkerUtils.h + VTKViewer_OpenGLHelper.h VTKViewer_OpenGLRenderer.h VTKViewer_PolyDataMapper.h VTKViewer_ShrinkFilter.h @@ -152,6 +153,7 @@ SET(_other_SOURCES VTKViewer_MarkerDlg.cxx VTKViewer_MarkerUtils.cxx VTKViewer_MarkerWidget.cxx + VTKViewer_OpenGLHelper.cxx VTKViewer_OpenGLRenderer.cxx VTKViewer_PolyDataMapper.cxx VTKViewer_RenderWindow.cxx @@ -188,3 +190,6 @@ INSTALL(FILES ${GUIVTI_DATA} DESTINATION ${SALOME_GUI_INSTALL_RES_DATA}) FILE(GLOB GUITXT_DATA "${CMAKE_CURRENT_SOURCE_DIR}/resources/*.txt") INSTALL(FILES ${GUITXT_DATA} DESTINATION ${SALOME_GUI_INSTALL_RES_DATA}) + +FILE(GLOB GUIGLSL_DATA "${CMAKE_CURRENT_SOURCE_DIR}/resources/*.glsl") +INSTALL(FILES ${GUIGLSL_DATA} DESTINATION ${SALOME_GUI_INSTALL_RES_DATA}) diff --git a/src/VTKViewer/VTKViewer_OpenGLHelper.cxx b/src/VTKViewer/VTKViewer_OpenGLHelper.cxx new file mode 100644 index 000000000..b92c14dc9 --- /dev/null +++ b/src/VTKViewer/VTKViewer_OpenGLHelper.cxx @@ -0,0 +1,362 @@ +// Copyright (C) 2007-2016 CEA/DEN, EDF R&D, OPEN CASCADE +// +// Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN, +// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License, or (at your option) any later version. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + + +#include "VTKViewer_OpenGLHelper.h" + +#ifndef WIN32 +# ifndef GLX_GLXEXT_LEGACY +# define GLX_GLXEXT_LEGACY +# endif +# include +# include +#else +# include +#endif + +#ifndef WIN32 +#define GL_GetProcAddress( x ) glXGetProcAddressARB( (const GLubyte*)x ) +#else +#define GL_GetProcAddress( x ) wglGetProcAddress( (const LPCSTR)x ) +#endif + +// ============================================================================ +// function : VTKViewer_OpenGLHelper +// purpose : +// ============================================================================ +VTKViewer_OpenGLHelper::VTKViewer_OpenGLHelper() +: vglShaderSourceARB (NULL), + vglCreateShaderObjectARB (NULL), + vglCompileShaderARB (NULL), + vglCreateProgramObjectARB (NULL), + vglAttachObjectARB (NULL), + vglLinkProgramARB (NULL), + vglUseProgramObjectARB (NULL), + vglGenBuffersARB (NULL), + vglBindBufferARB (NULL), + vglBufferDataARB (NULL), + vglDeleteBuffersARB (NULL), + vglGetAttribLocationARB (NULL), + vglVertexAttribPointerARB (NULL), + vglEnableVertexAttribArrayARB (NULL), + vglDisableVertexAttribArrayARB (NULL), +#ifdef VTK_OPENGL2 + vglDetachObjectARB (NULL), + vglDeleteObjectARB (NULL), + vglValidateProgramARB (NULL), + vglGetShaderivARB (NULL), + vglGetProgramivARB (NULL), + vglGetShaderInfoLogARB (NULL), + vglUniformMatrix4fvARB (NULL), + vglGenVertexArraysARB (NULL), + vglBindVertexArrayARB (NULL), + vglUniform1iARB (NULL), + vglGetUniformLocationARB (NULL), +#endif + mIsInitialized (false) +{ + Init(); +} + +// ============================================================================ +// function : ~VTKViewer_OpenGLHelper +// purpose : +// ============================================================================ +VTKViewer_OpenGLHelper::~VTKViewer_OpenGLHelper() +{ + // +} + +// ============================================================================ +// function : Init +// purpose : +// ============================================================================ +void VTKViewer_OpenGLHelper::Init() +{ + if (mIsInitialized) + return; + + vglShaderSourceARB = (PFNGLSHADERSOURCEARBPROC)GL_GetProcAddress( "glShaderSourceARB" ); + if( !vglShaderSourceARB ) + return; + + vglCreateShaderObjectARB = (PFNGLCREATESHADEROBJECTARBPROC)GL_GetProcAddress( "glCreateShaderObjectARB" ); + if( !vglCreateShaderObjectARB ) + return; + + vglCompileShaderARB = (PFNGLCOMPILESHADERARBPROC)GL_GetProcAddress( "glCompileShaderARB" ); + if( !vglCompileShaderARB ) + return; + + vglCreateProgramObjectARB = (PFNGLCREATEPROGRAMOBJECTARBPROC)GL_GetProcAddress( "glCreateProgramObjectARB" ); + if( !vglCreateProgramObjectARB ) + return; + + vglAttachObjectARB = (PFNGLATTACHOBJECTARBPROC)GL_GetProcAddress( "glAttachObjectARB" ); + if( !vglAttachObjectARB ) + return; + + vglLinkProgramARB = (PFNGLLINKPROGRAMARBPROC)GL_GetProcAddress( "glLinkProgramARB" ); + if( !vglLinkProgramARB ) + return; + + vglUseProgramObjectARB = (PFNGLUSEPROGRAMOBJECTARBPROC)GL_GetProcAddress( "glUseProgramObjectARB" ); + if( !vglUseProgramObjectARB ) + return; + + vglGenBuffersARB = (PFNGLGENBUFFERSARBPROC)GL_GetProcAddress( "glGenBuffersARB" ); + if( !vglGenBuffersARB ) + return; + + vglBindBufferARB = (PFNGLBINDBUFFERARBPROC)GL_GetProcAddress( "glBindBufferARB" ); + if( !vglBindBufferARB ) + return; + + vglBufferDataARB = (PFNGLBUFFERDATAARBPROC)GL_GetProcAddress( "glBufferDataARB" ); + if( !vglBufferDataARB ) + return; + + vglDeleteBuffersARB = (PFNGLDELETEBUFFERSARBPROC)GL_GetProcAddress( "glDeleteBuffersARB" ); + if( !vglDeleteBuffersARB ) + return; + + vglGetAttribLocationARB = (PFNGLGETATTRIBLOCATIONARBPROC)GL_GetProcAddress( "glGetAttribLocation" ); + if( !vglGetAttribLocationARB ) + return; + + vglVertexAttribPointerARB = (PFNGLVERTEXATTRIBPOINTERARBPROC)GL_GetProcAddress( "glVertexAttribPointer" ); + if( !vglVertexAttribPointerARB ) + return; + + vglEnableVertexAttribArrayARB = (PFNGLENABLEVERTEXATTRIBARRAYARBPROC)GL_GetProcAddress( "glEnableVertexAttribArray" ); + if(!vglEnableVertexAttribArrayARB) + return; + + vglDisableVertexAttribArrayARB = (PFNGLDISABLEVERTEXATTRIBARRAYARBPROC)GL_GetProcAddress( "glDisableVertexAttribArray" ); + if(!vglDisableVertexAttribArrayARB) + return; + +#ifdef VTK_OPENGL2 + vglDetachObjectARB = (PFNGLDETACHOBJECTARBPROC)GL_GetProcAddress( "glDetachObjectARB" ); + if( !vglDetachObjectARB ) + return; + + vglDeleteObjectARB = (PFNGLDELETEOBJECTARBPROC)GL_GetProcAddress( "glDeleteObjectARB" ); + if( !vglDeleteObjectARB ) + return; + + vglValidateProgramARB = (PFNGLVALIDATEPROGRAMARBPROC)GL_GetProcAddress( "glValidateProgramARB" ); + if ( !vglValidateProgramARB ) + return; + + vglGetUniformLocationARB = (PFNGLGETUNIFORMLOCATIONARBPROC)GL_GetProcAddress( "glGetUniformLocationARB" ); + if( !vglGetUniformLocationARB ) + return; + + vglGetShaderivARB = (PFNGLGETSHADERIVPROC)GL_GetProcAddress( "glGetShaderiv" ); + if( !vglGetShaderivARB ) + return; + + vglGetProgramivARB = (PFNGLGETPROGRAMIVPROC)GL_GetProcAddress( "glGetProgramiv" ); + if( !vglGetProgramivARB ) + return; + + vglGetShaderInfoLogARB = (PFNGLGETSHADERINFOLOGPROC)GL_GetProcAddress( "glGetShaderInfoLog" ); + if( !vglGetShaderInfoLogARB ) + return; + + vglUniformMatrix4fvARB = (PFNGLUNIFORMMATRIX4FVARBPROC)GL_GetProcAddress( "glUniformMatrix4fv" ); + if( !vglUniformMatrix4fvARB ) + return; + + vglGenVertexArraysARB = (PFNGLGENVERTEXARRAYSARBPROC)GL_GetProcAddress( "glGenVertexArrays" ); + if( !vglGenVertexArraysARB ) + return; + + vglBindVertexArrayARB = (PFNGLBINDVERTEXARRAYARBPROC)GL_GetProcAddress( "glBindVertexArray" ); + if( !vglBindVertexArrayARB ) + return; + + vglUniform1iARB = (PFNGLUNIFORM1IARBPROC)GL_GetProcAddress( "glUniform1i" ); + if( !vglUniform1iARB ) + return; +#endif + + mIsInitialized = true; + return; +} + +namespace +{ + char* readFromFile( std::string fileName ) + { + FILE* file = fopen( fileName.c_str(), "r" ); + + char* content = NULL; + int count = 0; + + if( file != NULL ) + { + fseek( file, 0, SEEK_END ); + count = ftell( file ); + rewind( file ); + + if( count > 0 ) + { + content = ( char* )malloc( sizeof( char ) * ( count + 1 ) ); + count = fread( content, sizeof( char ), count, file ); + content[ count ] = '\0'; + } + fclose( file ); + } + + return content; + } +} +// ============================================================================ +// function : CreateShaderProgram +// purpose : +// ============================================================================ +bool VTKViewer_OpenGLHelper::CreateShaderProgram (const std::string& theFilePath, + GLhandleARB& theProgram, + GLhandleARB& theVertexShader, + GLhandleARB& theFragmentShader) const +{ +#ifdef VTK_OPENGL2 + // Create program. + theProgram = vglCreateProgramObjectARB(); + if (theProgram == 0) + { + std::cerr << "Can't create opengl program." << std::endl; + return false; + } + + std::string fileName; + char* shaderContent; + GLint linked, compileStatus, validateStatus; + + // Create vertex shader. + fileName = theFilePath + ".vs.glsl"; + + shaderContent = readFromFile (fileName); + + theVertexShader = vglCreateShaderObjectARB (GL_VERTEX_SHADER_ARB); + vglShaderSourceARB (theVertexShader, 1, (const GLcharARB**)&shaderContent, NULL); + vglCompileShaderARB (theVertexShader); + + free( shaderContent ); + + vglGetShaderivARB (theVertexShader, GL_COMPILE_STATUS, &compileStatus); + if (compileStatus != GL_TRUE) + { + GLint size; + GLchar info[1024]; + + vglGetShaderInfoLogARB (theVertexShader, 1024, &size, info); + std::cerr << "Can't compile vertex shader." << std::endl; + std::cerr << info << std::endl; + + return false; + } + + // Create fragment shader. + fileName = theFilePath + ".fs.glsl"; + + shaderContent = readFromFile (fileName); + + theFragmentShader = vglCreateShaderObjectARB (GL_FRAGMENT_SHADER_ARB); + vglShaderSourceARB (theFragmentShader, 1, (const GLcharARB**)&shaderContent, NULL); + vglCompileShaderARB (theFragmentShader); + + free (shaderContent); + + vglGetShaderivARB (theFragmentShader, GL_COMPILE_STATUS, &compileStatus); + if (compileStatus != GL_TRUE) + { + GLint size; + GLchar info[1024]; + + vglGetShaderInfoLogARB (theVertexShader, 1024, &size, info); + std::cerr << "Can't compile fragment shader." << std::endl; + std::cerr << info << std::endl; + return false; + } + + // Attach shaders. + vglAttachObjectARB (theProgram, theVertexShader); + vglAttachObjectARB (theProgram, theFragmentShader); + vglLinkProgramARB (theProgram); + + vglGetProgramivARB (theProgram, GL_LINK_STATUS, &linked); + if (!linked) + { + std::cerr << "Can't link program." << std::endl; + return false; + } + + vglValidateProgramARB (theProgram); + vglGetProgramivARB (theProgram, GL_VALIDATE_STATUS, &validateStatus); + + if (validateStatus != GL_TRUE) + { + std::cerr << "Shader program is not validate." << std::endl; + return false; + } + + return true; +#else + return false; +#endif +} + +// ============================================================================ +// function : DestroyShaderProgram +// purpose : +// ============================================================================ +void VTKViewer_OpenGLHelper::DestroyShaderProgram (GLhandleARB theProgram, + GLhandleARB theVertexShader, + GLhandleARB theFragmentShader) const +{ +#ifdef VTK_OPENGL2 + vglDetachObjectARB (theProgram, theVertexShader); + vglDetachObjectARB (theProgram, theFragmentShader); + + vglDeleteObjectARB (theVertexShader); + vglDeleteObjectARB (theFragmentShader); +#endif +} + +// ============================================================================ +// function : SetUniformMatrix +// purpose : +// ============================================================================ +void VTKViewer_OpenGLHelper::SetUniformMatrix (const GLint theLocation, + const vtkMatrix4x4* theMatrix) const +{ + float data[16]; + for (int i = 0; i < 16; ++i) + { + data[i] = theMatrix->Element[i / 4][i % 4]; + } + + this->vglUniformMatrix4fvARB (theLocation, 1, GL_FALSE, data); +} diff --git a/src/VTKViewer/VTKViewer_OpenGLHelper.h b/src/VTKViewer/VTKViewer_OpenGLHelper.h new file mode 100644 index 000000000..26333be2d --- /dev/null +++ b/src/VTKViewer/VTKViewer_OpenGLHelper.h @@ -0,0 +1,160 @@ +// Copyright (C) 2007-2016 CEA/DEN, EDF R&D, OPEN CASCADE +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License, or (at your option) any later version. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + +#ifndef VTKVIEWER_OPENGLHELPER_H +#define VTKVIEWER_OPENGLHELPER_H + +#include +#include +#include "VTKViewer.h" + +#include + + +#ifndef GL_ARB_shader_objects +typedef GLuint GLhandleARB; +#endif + +#ifndef APIENTRY +#define APIENTRY +#endif +#ifndef APIENTRYP +#define APIENTRYP APIENTRY * +#endif + +#ifndef GL_ARB_shader_objects +typedef char GLcharARB; +#endif + +#ifndef GL_VERTEX_PROGRAM_POINT_SIZE_ARB +#define GL_VERTEX_PROGRAM_POINT_SIZE_ARB 0x8642 +#endif + +#ifndef GL_VERTEX_SHADER_ARB +#define GL_VERTEX_SHADER_ARB 0x8B31 +#endif + +#ifndef GL_FRAGMENT_SHADER_ARB +#define GL_FRAGMENT_SHADER_ARB 0x8B30 +#endif + +#ifndef GL_ARB_point_sprite +#define GL_POINT_SPRITE_ARB 0x8861 +#define GL_COORD_REPLACE_ARB 0x8862 +#endif + +#ifndef GL_ARB_vertex_buffer_object +typedef ptrdiff_t GLsizeiptrARB; + +#define GL_ARRAY_BUFFER_ARB 0x8892 +#define GL_STATIC_DRAW_ARB 0x88E4 +#endif + +class VTKVIEWER_EXPORT VTKViewer_OpenGLHelper +{ +public: + VTKViewer_OpenGLHelper(); + ~VTKViewer_OpenGLHelper(); + + void Init(); + + bool IsInitialized() const { return mIsInitialized; } + +public: + bool CreateShaderProgram (const std::string& theFilePath, + GLhandleARB& theProgram, + GLhandleARB& theVertexShader, + GLhandleARB& theFragmentShader) const; + + void DestroyShaderProgram (GLhandleARB theProgram, + GLhandleARB theVertexShader, + GLhandleARB theFragmentShader) const; + + void SetUniformMatrix (const GLint theLocation, + const vtkMatrix4x4* theMatrix) const; + +protected: + typedef void (APIENTRYP PFNGLSHADERSOURCEARBPROC) (GLhandleARB shaderObj, GLsizei count, const GLcharARB* *string, const GLint *length); + typedef GLhandleARB (APIENTRYP PFNGLCREATESHADEROBJECTARBPROC) (GLenum shaderType); + typedef void (APIENTRYP PFNGLBINDBUFFERARBPROC) (GLenum target, GLuint buffer); + typedef void (APIENTRYP PFNGLDELETEBUFFERSARBPROC) (GLsizei n, const GLuint *buffers); + typedef void (APIENTRYP PFNGLGENBUFFERSARBPROC) (GLsizei n, GLuint *buffers); + typedef void (APIENTRYP PFNGLBUFFERDATAARBPROC) (GLenum target, GLsizeiptrARB size, const GLvoid *data, GLenum usage); + typedef void (APIENTRYP PFNGLCOMPILESHADERARBPROC) (GLhandleARB shaderObj); + typedef GLhandleARB (APIENTRYP PFNGLCREATEPROGRAMOBJECTARBPROC) (void); + typedef void (APIENTRYP PFNGLATTACHOBJECTARBPROC) (GLhandleARB containerObj, GLhandleARB obj); + typedef void (APIENTRYP PFNGLLINKPROGRAMARBPROC) (GLhandleARB programObj); + typedef void (APIENTRYP PFNGLUSEPROGRAMOBJECTARBPROC) (GLhandleARB programObj); + typedef GLint (APIENTRYP PFNGLGETATTRIBLOCATIONARBPROC) (GLhandleARB programObj, const GLcharARB *name); + typedef void (APIENTRYP PFNGLVERTEXATTRIBPOINTERARBPROC) (GLuint index, GLint size, GLenum type, GLboolean normalized, GLsizei stride, const GLvoid *pointer); + typedef void (APIENTRYP PFNGLENABLEVERTEXATTRIBARRAYARBPROC) (GLuint index); + typedef void (APIENTRYP PFNGLDISABLEVERTEXATTRIBARRAYARBPROC) (GLuint index); + +#ifdef VTK_OPENGL2 + typedef void (APIENTRYP PFNGLDETACHOBJECTARBPROC) (GLhandleARB containerObj, GLhandleARB obj); + typedef void (APIENTRYP PFNGLDELETEOBJECTARBPROC) (GLhandleARB obj); + typedef void (APIENTRYP PFNGLVALIDATEPROGRAMARBPROC) (GLhandleARB program); + typedef GLint (APIENTRYP PFNGLGETUNIFORMLOCATIONARBPROC) (GLhandleARB program, const GLcharARB *name ); + typedef void (APIENTRYP PFNGLGETSHADERIVARBPROC) (GLuint shader, GLenum pname, GLint *params); + typedef void (APIENTRYP PFNGLGETPROGRAMIVARBPROC) (GLuint program, GLenum pname, GLint *params); + typedef void (APIENTRYP PFNGLGETSHADERINFOLOGARBPROC) (GLuint shader, GLsizei maxLength, GLsizei *length, GLchar *infoLog); + typedef void (APIENTRYP PFNGLUNIFORMMATRIX4FVARBPROC) (GLint location, GLsizei count, GLboolean transpose, const GLfloat *value); + typedef void (APIENTRYP PFNGLGENVERTEXARRAYSARBPROC) (GLsizei n, GLuint *arrays); + typedef void (APIENTRYP PFNGLBINDVERTEXARRAYARBPROC) (GLuint array); + typedef void (APIENTRYP PFNGLUNIFORM1IARBPROC) (GLint location, GLint v0); +#endif + +public: + PFNGLSHADERSOURCEARBPROC vglShaderSourceARB; + PFNGLCREATESHADEROBJECTARBPROC vglCreateShaderObjectARB; + PFNGLCOMPILESHADERARBPROC vglCompileShaderARB; + PFNGLCREATEPROGRAMOBJECTARBPROC vglCreateProgramObjectARB; + PFNGLATTACHOBJECTARBPROC vglAttachObjectARB; + PFNGLLINKPROGRAMARBPROC vglLinkProgramARB; + PFNGLUSEPROGRAMOBJECTARBPROC vglUseProgramObjectARB; + + PFNGLGENBUFFERSARBPROC vglGenBuffersARB; + PFNGLBINDBUFFERARBPROC vglBindBufferARB; + PFNGLBUFFERDATAARBPROC vglBufferDataARB; + PFNGLDELETEBUFFERSARBPROC vglDeleteBuffersARB; + PFNGLGETATTRIBLOCATIONARBPROC vglGetAttribLocationARB; + PFNGLVERTEXATTRIBPOINTERARBPROC vglVertexAttribPointerARB; + PFNGLENABLEVERTEXATTRIBARRAYARBPROC vglEnableVertexAttribArrayARB; + PFNGLDISABLEVERTEXATTRIBARRAYARBPROC vglDisableVertexAttribArrayARB; + +#ifdef VTK_OPENGL2 + PFNGLDETACHOBJECTARBPROC vglDetachObjectARB; + PFNGLDELETEOBJECTARBPROC vglDeleteObjectARB; + PFNGLVALIDATEPROGRAMARBPROC vglValidateProgramARB; + PFNGLGETSHADERIVARBPROC vglGetShaderivARB; + PFNGLGETPROGRAMIVARBPROC vglGetProgramivARB; + PFNGLGETSHADERINFOLOGARBPROC vglGetShaderInfoLogARB; + + PFNGLUNIFORMMATRIX4FVARBPROC vglUniformMatrix4fvARB; + PFNGLGENVERTEXARRAYSARBPROC vglGenVertexArraysARB; + PFNGLBINDVERTEXARRAYARBPROC vglBindVertexArrayARB; + PFNGLUNIFORM1IARBPROC vglUniform1iARB; + PFNGLGETUNIFORMLOCATIONARBPROC vglGetUniformLocationARB; +#endif + +protected: + bool mIsInitialized; +}; + +#endif diff --git a/src/VTKViewer/VTKViewer_OpenGLRenderer.cxx b/src/VTKViewer/VTKViewer_OpenGLRenderer.cxx index 0a681e443..53a65830a 100644 --- a/src/VTKViewer/VTKViewer_OpenGLRenderer.cxx +++ b/src/VTKViewer/VTKViewer_OpenGLRenderer.cxx @@ -30,8 +30,10 @@ #include #include #include +#ifndef VTK_OPENGL2 #include #include // vtkgl namespace +#endif #include #include #include @@ -44,6 +46,15 @@ vtkStandardNewMacro(VTKViewer_OpenGLRenderer); VTKViewer_OpenGLRenderer::VTKViewer_OpenGLRenderer() { this->GradientType = HorizontalGradient; + +#ifdef VTK_OPENGL2 + this->BackgroundProgram = 0; + this->BackgroundVertexShader = 0; + this->BackgroundFragmentShader = 0; + this->VertexArrayObject = 0; + + this->OpenGLHelper.Init(); +#endif } VTKViewer_OpenGLRenderer::~VTKViewer_OpenGLRenderer() @@ -57,6 +68,30 @@ void VTKViewer_OpenGLRenderer::SetGradientType( const int theGradientType ) void VTKViewer_OpenGLRenderer::Clear(void) { +#ifdef VTK_OPENGL2 + if (this->OpenGLHelper.IsInitialized()) + { + if (this->BackgroundProgram == 0) + { + std::string filePath = std::string( getenv( "GUI_ROOT_DIR") ) + "/share/salome/resources/gui/Background"; + if (!this->OpenGLHelper.CreateShaderProgram (filePath, + this->BackgroundProgram, + this->BackgroundVertexShader, + this->BackgroundFragmentShader)) + { + return; + } + // Get uniform locations. + this->OpenGLHelper.vglUseProgramObjectARB (this->BackgroundProgram); + + this->myLocations.UseTexture = this->OpenGLHelper.vglGetUniformLocationARB (this->BackgroundProgram, "uUseTexture"); + this->myLocations.BackgroundTexture = this->OpenGLHelper.vglGetUniformLocationARB (this->BackgroundProgram, "uBackgroundTexture"); + + this->OpenGLHelper.vglUseProgramObjectARB (0); + } + } +#endif + GLbitfield clear_mask = 0; if( !this->Transparent() ) @@ -90,6 +125,9 @@ void VTKViewer_OpenGLRenderer::Clear(void) glDisable( GL_TEXTURE_1D ); glDisable( GL_TEXTURE_2D ); glDisable( GL_BLEND ); + + GLint oldShadeModel; + glGetIntegerv(GL_SHADE_MODEL, &oldShadeModel); glShadeModel( GL_SMOOTH ); // color interpolation glMatrixMode( GL_PROJECTION ); @@ -174,6 +212,62 @@ void VTKViewer_OpenGLRenderer::Clear(void) break; } +#ifdef VTK_OPENGL2 + if (this->OpenGLHelper.IsInitialized()) + { + if (this->VertexArrayObject == 0) + { + this->OpenGLHelper.vglGenVertexArraysARB (1, &this->VertexArrayObject); + } + + this->OpenGLHelper.vglUseProgramObjectARB (this->BackgroundProgram); + this->OpenGLHelper.vglBindVertexArrayARB (this->VertexArrayObject); + + GLfloat data[7 * 4]; + if( this->GradientType != FirstCornerGradient && this->GradientType != ThirdCornerGradient ) + { + const float tmpData[] = { (float)corner1[0], (float)corner1[1], (float)corner1[2], 1.0f, -1.0f, 1.0f, 0.0f, + (float)corner2[0], (float)corner2[1], (float)corner2[2], 1.0f, -1.0f, -1.0f, 0.0f, + (float)corner3[0], (float)corner3[1], (float)corner3[2], 1.0f, 1.0f, -1.0f, 0.0f, + (float)corner4[0], (float)corner4[1], (float)corner4[2], 1.0f, 1.0f, 1.0f, 0.0f }; + memcpy (data, tmpData, sizeof(float) * 7 * 4); + } + else //if( this->GradientType == FirstCornerGradient || this->GradientType == ThirdCornerGradient ) + { + const float tmpData[] = { (float)corner2[0], (float)corner2[1], (float)corner2[2], 1.0f, -1.0f, -1.0f, 0.0f, + (float)corner3[0], (float)corner3[1], (float)corner3[2], 1.0f, -1.0f, 1.0f, 0.0f, + (float)corner4[0], (float)corner4[1], (float)corner4[2], 1.0f, 1.0f, 1.0f, 0.0f, + (float)corner1[0], (float)corner1[1], (float)corner1[2], 1.0f, 1.0f, -1.0f, 0.0f }; + memcpy (data, tmpData, sizeof(float) * 7 * 4); + } + + GLuint vertexBuffer; + this->OpenGLHelper.vglGenBuffersARB (1, &vertexBuffer); + this->OpenGLHelper.vglBindBufferARB (GL_ARRAY_BUFFER_ARB, vertexBuffer); + this->OpenGLHelper.vglBufferDataARB (GL_ARRAY_BUFFER_ARB, sizeof(data), data, GL_STATIC_DRAW_ARB); + + GLint colorAttrib = this->OpenGLHelper.vglGetAttribLocationARB (this->BackgroundProgram, "Color"); + GLint vertexAttrib = this->OpenGLHelper.vglGetAttribLocationARB (this->BackgroundProgram, "Vertex"); + GLsizei vertexSize = sizeof(GLfloat) * 7; + + this->OpenGLHelper.vglVertexAttribPointerARB (colorAttrib, 4, GL_FLOAT, GL_FALSE, vertexSize, (const GLvoid*)0); + this->OpenGLHelper.vglEnableVertexAttribArrayARB (colorAttrib); + + this->OpenGLHelper.vglVertexAttribPointerARB (vertexAttrib, 3, GL_FLOAT, GL_FALSE, vertexSize, (const GLvoid*)(sizeof(GLfloat) * 4)); + this->OpenGLHelper.vglEnableVertexAttribArrayARB (vertexAttrib); + + this->OpenGLHelper.vglUniform1iARB (this->myLocations.UseTexture, 0); + + glDrawArrays(GL_TRIANGLE_FAN, 0, 4); + + this->OpenGLHelper.vglDisableVertexAttribArrayARB (0); + this->OpenGLHelper.vglBindBufferARB (GL_ARRAY_BUFFER_ARB, 0); + this->OpenGLHelper.vglDeleteBuffersARB (1, &vertexBuffer); + this->OpenGLHelper.vglBindVertexArrayARB (0); + this->OpenGLHelper.vglUseProgramObjectARB (0); + } +#else + glBegin( GL_TRIANGLE_FAN ); if( this->GradientType != FirstCornerGradient && this->GradientType != ThirdCornerGradient ) { @@ -190,6 +284,7 @@ void VTKViewer_OpenGLRenderer::Clear(void) glColor3f( corner1[0], corner1[1], corner1[2] ); glVertex2f( 0.F, 0.F ); } glEnd(); +#endif } if( this->TexturedBackground && this->BackgroundTexture ) @@ -214,31 +309,80 @@ void VTKViewer_OpenGLRenderer::Clear(void) GLfloat texX = 1.F; // texture coordinate GLfloat texY = 1.F; // texture coordinate - GLfloat x_offset = 0.5, y_offset = 0.5; - GLfloat coeff = 0.5; - - // OCCT issue 0023102: Change the algorithm of rendering the - // 3d viewer background using tiled texture - // Setting this coefficient to -1.F allows to tile textures relatively - // to the top-left corner of the view (value 1.F corresponds to the - // initial behaviour - tiling from the bottom-left corner) - GLfloat aCoef = -1.F; int aPosition = aTexture->GetPosition(); int aWidth = aTexture->GetWidth(); int aHeight = aTexture->GetHeight(); int aViewWidth = this->RenderWindow->GetSize()[0]; - int aViewHeight = this->RenderWindow->GetSize()[1]; + int aViewHeight = this->RenderWindow->GetSize()[1]; + + if( aPosition == VTKViewer_Texture::Tiled ) + { + texX = (GLfloat)aViewWidth / (GLfloat)aWidth; + texY = (GLfloat)aViewHeight / (GLfloat)aHeight; + } +#ifdef VTK_OPENGL2 + if (this->OpenGLHelper.IsInitialized()) + { + if (this->VertexArrayObject == 0) + { + this->OpenGLHelper.vglGenVertexArraysARB (1, &this->VertexArrayObject); + } + + this->OpenGLHelper.vglUseProgramObjectARB (this->BackgroundProgram); + this->OpenGLHelper.vglBindVertexArrayARB (this->VertexArrayObject); + + GLfloat dx = (aPosition == VTKViewer_Texture::Centered) ? (( (GLfloat)aWidth / (GLfloat)aViewWidth )) : 1.0f; + GLfloat dy = (aPosition == VTKViewer_Texture::Centered) ? (( (GLfloat)aHeight / (GLfloat)aViewHeight )) : 1.0f; + + + // First 4 components of Vertex is TexCoords now. + GLfloat data[7 * 4] = { 0.0f, texY, 0.0f, 1.0f, -dx, dy, 0.0f, + 0.0f, 0.0f, 0.0f, 1.0f, -dx, -dy, 0.0f, + texX, 0.0f, 0.0f, 1.0f, dx, -dy, 0.0f, + texX, texY, 0.0f, 1.0f, dx, dy, 0.0f }; + + GLuint vertexBuffer; + this->OpenGLHelper.vglGenBuffersARB (1, &vertexBuffer); + this->OpenGLHelper.vglBindBufferARB (GL_ARRAY_BUFFER_ARB, vertexBuffer); + this->OpenGLHelper.vglBufferDataARB (GL_ARRAY_BUFFER_ARB, sizeof(data), data, GL_STATIC_DRAW_ARB); + + GLint colorAttrib = this->OpenGLHelper.vglGetAttribLocationARB (this->BackgroundProgram, "Color"); + GLint vertexAttrib = this->OpenGLHelper.vglGetAttribLocationARB (this->BackgroundProgram, "Vertex"); + GLsizei vertexSize = sizeof(GLfloat) * 7; + + this->OpenGLHelper.vglVertexAttribPointerARB (colorAttrib, 4, GL_FLOAT, GL_FALSE, vertexSize, (const GLvoid*)0); + this->OpenGLHelper.vglEnableVertexAttribArrayARB (colorAttrib); + + this->OpenGLHelper.vglVertexAttribPointerARB (vertexAttrib, 3, GL_FLOAT, GL_FALSE, vertexSize, (const GLvoid*)(sizeof(GLfloat) * 4)); + this->OpenGLHelper.vglEnableVertexAttribArrayARB (vertexAttrib); + + this->OpenGLHelper.vglUniform1iARB (this->myLocations.UseTexture, 1); + this->OpenGLHelper.vglUniform1iARB (this->myLocations.BackgroundTexture, GL_TEXTURE0); + + glDrawArrays(GL_TRIANGLE_FAN, 0, 4); + + this->OpenGLHelper.vglDisableVertexAttribArrayARB (0); + this->OpenGLHelper.vglBindBufferARB (GL_ARRAY_BUFFER_ARB, 0); + this->OpenGLHelper.vglDeleteBuffersARB (1, &vertexBuffer); + this->OpenGLHelper.vglBindVertexArrayARB (0); + this->OpenGLHelper.vglUseProgramObjectARB (0); + } +#else + GLfloat x_offset = 0.5f, y_offset = 0.5f; + GLfloat coeff = 0.5f; if( aPosition == VTKViewer_Texture::Centered ) { x_offset = ( (GLfloat)aWidth / (GLfloat)aViewWidth ) / 2.; y_offset = ( (GLfloat)aHeight / (GLfloat)aViewHeight ) / 2.; } - else if( aPosition == VTKViewer_Texture::Tiled ) - { - texX = (GLfloat)aViewWidth / (GLfloat)aWidth; - texY = (GLfloat)aViewHeight / (GLfloat)aHeight; - } + + // OCCT issue 0023102: Change the algorithm of rendering the + // 3d viewer background using tiled texture + // Setting this coefficient to -1.F allows to tile textures relatively + // to the top-left corner of the view (value 1.F corresponds to the + // initial behaviour - tiling from the bottom-left corner) + GLfloat aCoef = -1.F; // Note that texture is mapped using GL_REPEAT wrapping mode so integer part // is simply ignored, and negative multiplier is here for convenience only @@ -249,9 +393,22 @@ void VTKViewer_OpenGLRenderer::Clear(void) glTexCoord2f( texX, aCoef * texY ); glVertex2f( x_offset + coeff, aCoef * y_offset + coeff ); glTexCoord2f( 0.F, aCoef * texY ); glVertex2f( -x_offset + coeff, aCoef * y_offset + coeff ); glEnd(); +#endif } } + // Restore settings. + { + glEnable( GL_ALPHA_TEST ); + glEnable( GL_DEPTH_TEST ); + glEnable( GL_LIGHTING ); + glEnable( GL_TEXTURE_1D ); + glEnable( GL_TEXTURE_2D ); + glEnable( GL_BLEND ); + + glShadeModel( oldShadeModel ); // color interpolation + } + glPopMatrix(); glMatrixMode( GL_PROJECTION ); glPopMatrix(); diff --git a/src/VTKViewer/VTKViewer_OpenGLRenderer.h b/src/VTKViewer/VTKViewer_OpenGLRenderer.h index e6b662614..81ec8a98b 100644 --- a/src/VTKViewer/VTKViewer_OpenGLRenderer.h +++ b/src/VTKViewer/VTKViewer_OpenGLRenderer.h @@ -25,6 +25,7 @@ #include "VTKViewer.h" #include "vtkOpenGLRenderer.h" +#include "VTKViewer_OpenGLHelper.h" class VTKVIEWER_EXPORT VTKViewer_OpenGLRenderer : public vtkOpenGLRenderer { @@ -55,6 +56,31 @@ protected: private: int GradientType; +#ifdef VTK_OPENGL2 + VTKViewer_OpenGLHelper OpenGLHelper; + GLhandleARB BackgroundProgram; + GLhandleARB BackgroundVertexShader; + GLhandleARB BackgroundFragmentShader; + GLuint VertexArrayObject; + + struct Locations + { + static const GLint INVALID_LOCATION = -1; + + GLint UseTexture; + GLint BackgroundTexture; + + Locations() + : UseTexture (INVALID_LOCATION), + BackgroundTexture (INVALID_LOCATION) + { + // + } + + } myLocations; +#endif + + private: VTKViewer_OpenGLRenderer(const VTKViewer_OpenGLRenderer&); // Not implemented. void operator=(const VTKViewer_OpenGLRenderer&); // Not implemented. diff --git a/src/VTKViewer/VTKViewer_PolyDataMapper.cxx b/src/VTKViewer/VTKViewer_PolyDataMapper.cxx index af561e0f3..3f08ccfbb 100644 --- a/src/VTKViewer/VTKViewer_PolyDataMapper.cxx +++ b/src/VTKViewer/VTKViewer_PolyDataMapper.cxx @@ -16,6 +16,9 @@ // // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com // +#ifdef VTK_OPENGL2 +#define GL_GLEXT_PROTOTYPES +#endif #include "VTKViewer_PolyDataMapper.h" #include "VTKViewer_MarkerUtils.h" @@ -62,78 +65,7 @@ vtkStandardNewMacro(VTKViewer_PolyDataMapper); #define VTK_PDPSM_NORMAL_TYPE_DOUBLE 0x0020 #define VTK_PDPSM_OPAQUE_COLORS 0x0040 -#ifndef APIENTRY -#define APIENTRY -#endif -#ifndef APIENTRYP -#define APIENTRYP APIENTRY * -#endif - -#ifndef GL_ARB_shader_objects -typedef char GLcharARB; -#endif - -#ifndef GL_VERTEX_PROGRAM_POINT_SIZE_ARB -#define GL_VERTEX_PROGRAM_POINT_SIZE_ARB 0x8642 -#endif - -#ifndef GL_VERTEX_SHADER_ARB -#define GL_VERTEX_SHADER_ARB 0x8B31 -#endif - -#ifndef GL_ARB_point_sprite -#define GL_POINT_SPRITE_ARB 0x8861 -#define GL_COORD_REPLACE_ARB 0x8862 -#endif - -#ifndef GL_ARB_vertex_buffer_object -typedef ptrdiff_t GLsizeiptrARB; - -#define GL_ARRAY_BUFFER_ARB 0x8892 -#define GL_STATIC_DRAW_ARB 0x88E4 -#endif -typedef void (APIENTRYP PFNGLSHADERSOURCEARBPROC) (GLhandleARB shaderObj, GLsizei count, const GLcharARB* *string, const GLint *length); -typedef GLhandleARB (APIENTRYP PFNGLCREATESHADEROBJECTARBPROC) (GLenum shaderType); -typedef void (APIENTRYP PFNGLBINDBUFFERARBPROC) (GLenum target, GLuint buffer); -typedef void (APIENTRYP PFNGLDELETEBUFFERSARBPROC) (GLsizei n, const GLuint *buffers); -typedef void (APIENTRYP PFNGLGENBUFFERSARBPROC) (GLsizei n, GLuint *buffers); -typedef void (APIENTRYP PFNGLBUFFERDATAARBPROC) (GLenum target, GLsizeiptrARB size, const GLvoid *data, GLenum usage); -typedef void (APIENTRYP PFNGLCOMPILESHADERARBPROC) (GLhandleARB shaderObj); -typedef GLhandleARB (APIENTRYP PFNGLCREATEPROGRAMOBJECTARBPROC) (void); -typedef void (APIENTRYP PFNGLATTACHOBJECTARBPROC) (GLhandleARB containerObj, GLhandleARB obj); -typedef void (APIENTRYP PFNGLLINKPROGRAMARBPROC) (GLhandleARB programObj); -typedef void (APIENTRYP PFNGLUSEPROGRAMOBJECTARBPROC) (GLhandleARB programObj); -typedef GLint (APIENTRYP PFNGLGETATTRIBLOCATIONARBPROC) (GLhandleARB programObj, const GLcharARB *name); -typedef void (APIENTRYP PFNGLVERTEXATTRIBPOINTERARBPROC) (GLuint index, GLint size, GLenum type, GLboolean normalized, GLsizei stride, const GLvoid *pointer); -typedef void (APIENTRYP PFNGLENABLEVERTEXATTRIBARRAYARBPROC) (GLuint index); -typedef void (APIENTRYP PFNGLDISABLEVERTEXATTRIBARRAYARBPROC) (GLuint index); - -typedef GLfloat TBall; - - -static PFNGLSHADERSOURCEARBPROC vglShaderSourceARB = NULL; -static PFNGLCREATESHADEROBJECTARBPROC vglCreateShaderObjectARB = NULL; -static PFNGLCOMPILESHADERARBPROC vglCompileShaderARB = NULL; -static PFNGLCREATEPROGRAMOBJECTARBPROC vglCreateProgramObjectARB = NULL; -static PFNGLATTACHOBJECTARBPROC vglAttachObjectARB = NULL; -static PFNGLLINKPROGRAMARBPROC vglLinkProgramARB = NULL; -static PFNGLUSEPROGRAMOBJECTARBPROC vglUseProgramObjectARB = NULL; - -static PFNGLGENBUFFERSARBPROC vglGenBuffersARB = NULL; -static PFNGLBINDBUFFERARBPROC vglBindBufferARB = NULL; -static PFNGLBUFFERDATAARBPROC vglBufferDataARB = NULL; -static PFNGLDELETEBUFFERSARBPROC vglDeleteBuffersARB = NULL; -static PFNGLGETATTRIBLOCATIONARBPROC vglGetAttribLocationARB = NULL; -static PFNGLVERTEXATTRIBPOINTERARBPROC vglVertexAttribPointerARB = NULL; -static PFNGLENABLEVERTEXATTRIBARRAYARBPROC vglEnableVertexAttribArrayARB = NULL; -static PFNGLDISABLEVERTEXATTRIBARRAYARBPROC vglDisableVertexAttribArrayARB = NULL; - - -#ifndef WIN32 -#define GL_GetProcAddress( x ) glXGetProcAddressARB( (const GLubyte*)x ) -#else -#define GL_GetProcAddress( x ) wglGetProcAddress( (const LPCSTR)x ) -#endif +typedef GLfloat TBall; #ifdef WIN32 #ifdef max @@ -145,100 +77,6 @@ static PFNGLDISABLEVERTEXATTRIBARRAYARBPROC vglDisableVertexAttribArrayARB = NUL // texture id for balls drawing #define BallTextureId 0 -bool InitializeBufferExtensions() -{ - vglShaderSourceARB = (PFNGLSHADERSOURCEARBPROC)GL_GetProcAddress( "glShaderSourceARB" ); - if( !vglShaderSourceARB ) - return false; - - vglCreateShaderObjectARB = (PFNGLCREATESHADEROBJECTARBPROC)GL_GetProcAddress( "glCreateShaderObjectARB" ); - if( !vglCreateShaderObjectARB ) - return false; - - vglCompileShaderARB = (PFNGLCOMPILESHADERARBPROC)GL_GetProcAddress( "glCompileShaderARB" ); - if( !vglCompileShaderARB ) - return false; - - vglCreateProgramObjectARB = (PFNGLCREATEPROGRAMOBJECTARBPROC)GL_GetProcAddress( "glCreateProgramObjectARB" ); - if( !vglCreateProgramObjectARB ) - return false; - - vglAttachObjectARB = (PFNGLATTACHOBJECTARBPROC)GL_GetProcAddress( "glAttachObjectARB" ); - if( !vglAttachObjectARB ) - return false; - - vglLinkProgramARB = (PFNGLLINKPROGRAMARBPROC)GL_GetProcAddress( "glLinkProgramARB" ); - if( !vglLinkProgramARB ) - return false; - - vglUseProgramObjectARB = (PFNGLUSEPROGRAMOBJECTARBPROC)GL_GetProcAddress( "glUseProgramObjectARB" ); - if( !vglUseProgramObjectARB ) - return false; - - vglGenBuffersARB = (PFNGLGENBUFFERSARBPROC)GL_GetProcAddress( "glGenBuffersARB" ); - if( !vglGenBuffersARB ) - return false; - - vglBindBufferARB = (PFNGLBINDBUFFERARBPROC)GL_GetProcAddress( "glBindBufferARB" ); - if( !vglBindBufferARB ) - return false; - - vglBufferDataARB = (PFNGLBUFFERDATAARBPROC)GL_GetProcAddress( "glBufferDataARB" ); - if( !vglBufferDataARB ) - return false; - - vglDeleteBuffersARB = (PFNGLDELETEBUFFERSARBPROC)GL_GetProcAddress( "glDeleteBuffersARB" ); - if( !vglDeleteBuffersARB ) - return false; - - vglGetAttribLocationARB = (PFNGLGETATTRIBLOCATIONARBPROC)GL_GetProcAddress( "glGetAttribLocation" ); - if( !vglGetAttribLocationARB ) - return false; - - vglVertexAttribPointerARB = (PFNGLVERTEXATTRIBPOINTERARBPROC)GL_GetProcAddress( "glVertexAttribPointer" ); - if( !vglVertexAttribPointerARB ) - return false; - - vglEnableVertexAttribArrayARB = (PFNGLENABLEVERTEXATTRIBARRAYARBPROC)GL_GetProcAddress( "glEnableVertexAttribArray" ); - if(!vglEnableVertexAttribArrayARB) - return false; - - vglDisableVertexAttribArrayARB = (PFNGLDISABLEVERTEXATTRIBARRAYARBPROC)GL_GetProcAddress( "glDisableVertexAttribArray" ); - - if(!vglDisableVertexAttribArrayARB) - return false; - - - return true; -}; - -//----------------------------------------------------------------------------- -char* readFromFile( std::string fileName ) -{ - FILE* file = fopen( fileName.c_str(), "r" ); - - char* content = NULL; - int count = 0; - - if( file != NULL ) - { - fseek( file, 0, SEEK_END ); - count = ftell( file ); - rewind( file ); - - if( count > 0 ) - { - content = ( char* )malloc( sizeof( char ) * ( count + 1 ) ); - count = fread( content, sizeof( char ), count, file ); - content[ count ] = '\0'; - } - fclose( file ); - } - - return content; -} - -static bool IsBufferExtensionsInitialized = InitializeBufferExtensions(); //----------------------------------------------------------------------------- VTKViewer_PolyDataMapper::VTKViewer_PolyDataMapper() @@ -255,7 +93,13 @@ VTKViewer_PolyDataMapper::VTKViewer_PolyDataMapper() this->MarkerId = 0; this->BallEnabled = false; this->BallScale = 1.0; - this->VertexProgram = 0; + this->PointProgram = 0; +#ifdef VTK_OPENGL2 + this->VertexShader = 0; + this->FragmentShader = 0; +#endif + + this->OpenGLHelper.Init(); } //----------------------------------------------------------------------------- @@ -263,25 +107,49 @@ VTKViewer_PolyDataMapper::~VTKViewer_PolyDataMapper() { if( PointSpriteTexture > 0 ) glDeleteTextures( 1, &PointSpriteTexture ); + +#ifdef VTK_OPENGL2 + this->OpenGLHelper.DestroyShaderProgram( this->PointProgram, this->VertexShader, this->FragmentShader); +#endif } //----------------------------------------------------------------------------- -void VTKViewer_PolyDataMapper::InitShader() +int VTKViewer_PolyDataMapper::InitShader() { +#ifdef VTK_OPENGL2 + std::string filePath = std::string( getenv( "GUI_ROOT_DIR") ) + "/share/salome/resources/gui/Point"; + if( !this->OpenGLHelper.CreateShaderProgram(filePath, this->PointProgram, this->VertexShader, this->FragmentShader) ) + return false; + + // Get uniform locations. + this->OpenGLHelper.vglUseProgramObjectARB( this->PointProgram ); + + this->myLocations.ModelViewProjection = this->OpenGLHelper.vglGetUniformLocationARB( this->PointProgram, "uModelViewProjectionMatrix" ); + this->myLocations.Projection = this->OpenGLHelper.vglGetUniformLocationARB( this->PointProgram, "uProjectionMatrix" ); + this->myLocations.GeneralPointSize = this->OpenGLHelper.vglGetUniformLocationARB( this->PointProgram, "uGeneralPointSize" ); + this->myLocations.PointSprite = this->OpenGLHelper.vglGetUniformLocationARB( this->PointProgram, "uPointSprite" ); + + this->OpenGLHelper.vglUseProgramObjectARB( 0 ); + + this->OpenGLHelper.vglGenVertexArraysARB(1, &this->VertexArrayObject); +#else std::string fileName = std::string( getenv( "GUI_ROOT_DIR") ) + "/share/salome/resources/gui/Vertex_Program_ARB.txt"; char* shader = readFromFile( fileName ); - GLhandleARB VertexShader = vglCreateShaderObjectARB( GL_VERTEX_SHADER_ARB ); - vglShaderSourceARB( VertexShader, 1, (const GLcharARB**)&shader, NULL ); - vglCompileShaderARB( VertexShader ); + GLhandleARB VertexShader = this->OpenGLHelper.vglCreateShaderObjectARB( GL_VERTEX_SHADER_ARB ); + this->OpenGLHelper.vglShaderSourceARB( VertexShader, 1, (const GLcharARB**)&shader, NULL ); + this->OpenGLHelper.vglCompileShaderARB( VertexShader ); - this->VertexProgram = vglCreateProgramObjectARB(); - vglAttachObjectARB( this->VertexProgram, VertexShader ); + this->PointProgram = this->OpenGLHelper.vglCreateProgramObjectARB(); + this->OpenGLHelper.vglAttachObjectARB( this->PointProgram, VertexShader ); - vglLinkProgramARB( this->VertexProgram ); + this->OpenGLHelper.vglLinkProgramARB( this->PointProgram ); free( shader ); +#endif + + return ES_Ok; } @@ -467,8 +335,21 @@ int VTKViewer_PolyDataMapper::GetMarkerTexture() //----------------------------------------------------------------------------- int VTKViewer_PolyDataMapper::InitExtensions() { - char* ext = (char*)glGetString( GL_EXTENSIONS ); - if( !IsBufferExtensionsInitialized || +#ifdef VTK_OPENGL2 + int n = 0; + std::ostringstream strm; + glGetIntegerv(GL_NUM_EXTENSIONS, &n); + for (int i = 0; i < n; i++) + { + const char *exti = (const char *)glGetStringi(GL_EXTENSIONS, i); + strm<< exti <<" "; + } + std::string s = strm.str(); + const char* ext = s.c_str(); +#else + const char* ext = (const char*)glGetString( GL_EXTENSIONS ); +#endif + if( !this->OpenGLHelper.IsInitialized() || !ext || strstr( ext, "GL_ARB_point_sprite" ) == NULL || strstr( ext, "GL_ARB_vertex_buffer_object" ) == NULL || strstr( ext, "GL_ARB_shader_objects") == NULL ) @@ -477,10 +358,7 @@ int VTKViewer_PolyDataMapper::InitExtensions() return ES_Error; } - if( this->BallEnabled ) - this->InitShader(); - - return ES_Ok; + return this->InitShader(); } //----------------------------------------------------------------------------- @@ -526,6 +404,9 @@ void VTKViewer_PolyDataMapper::InitTextures() if( this->PointSpriteTexture == 0 ) { glGenTextures( 1, &this->PointSpriteTexture ); } +#ifdef VTK_OPENGL2 + glActiveTexture( GL_TEXTURE0 ); +#endif glBindTexture( GL_TEXTURE_2D, this->PointSpriteTexture ); glTexEnvf( GL_POINT_SPRITE_ARB, GL_COORD_REPLACE_ARB, GL_TRUE ); glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT ); @@ -543,6 +424,11 @@ void VTKViewer_PolyDataMapper::InitTextures() unsigned char* dataPtr = (unsigned char*)this->ImageData->GetScalarPointer(); glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA, aSize[0], aSize[1], 0, GL_RGBA, GL_UNSIGNED_BYTE, dataPtr ); + +#ifdef VTK_OPENGL2 + // Set sampler. + this->OpenGLHelper.vglUniform1iARB( this->myLocations.PointSprite, GL_TEXTURE0 ); +#endif } //----------------------------------------------------------------------------- @@ -552,7 +438,7 @@ void VTKViewer_PolyDataMapper::RenderPiece( vtkRenderer* ren, vtkActor* act ) this->BallEnabled; if( isUsePointSprites ) { - if( this->ExtensionsInitialized == ES_None ) + if( this->ExtensionsInitialized != ES_Ok ) this->ExtensionsInitialized = this->InitExtensions(); this->InitPointSprites(); this->InitTextures(); @@ -596,8 +482,9 @@ void VTKViewer_PolyDataMapper::RenderPiece( vtkRenderer* ren, vtkActor* act ) ren->GetRenderWindow()->MakeCurrent(); - vglUseProgramObjectARB( this->VertexProgram ); + this->OpenGLHelper.vglUseProgramObjectARB( this->PointProgram ); +#ifndef VTK_OPENGL2 // // if something has changed regenerate colors and display lists // if required @@ -670,8 +557,13 @@ void VTKViewer_PolyDataMapper::RenderPiece( vtkRenderer* ren, vtkActor* act ) // time so that it is not zero if ( this->TimeToDraw == 0.0 ) this->TimeToDraw = 0.0001; - - vglUseProgramObjectARB( 0 ); +#else + //this->RenderPieceStart(ren, act); + this->RenderPieceDraw(ren, act); + // this->RenderEdges(ren,act); + //this->RenderPieceFinish(ren, act); +#endif + this->OpenGLHelper.vglUseProgramObjectARB( 0 ); this->CleanupPointSprites(); glBindTexture( GL_TEXTURE_2D, 0 ); } @@ -863,16 +755,40 @@ namespace VTK } } // namespace VTK +#ifndef VTK_OPENGL2 //----------------------------------------------------------------------------- int VTKViewer_PolyDataMapper::Draw( vtkRenderer* ren, vtkActor* act ) -{ +{ + int noAbort = 1; if( (!this->MarkerEnabled || this->MarkerType == VTK::MT_NONE || !this->ImageData.GetPointer()) && !this->BallEnabled) return MAPPER_SUPERCLASS::Draw( ren, act ); + InternalDraw( ren, act ); + + return noAbort; +} +#else +//----------------------------------------------------------------------------- +void VTKViewer_PolyDataMapper::RenderPieceDraw( vtkRenderer* ren, vtkActor* act ) { + int noAbort = 1; + if( (!this->MarkerEnabled || this->MarkerType == VTK::MT_NONE || !this->ImageData.GetPointer()) && !this->BallEnabled) { + MAPPER_SUPERCLASS::RenderPieceDraw( ren, act ); + return; + } + InternalDraw( ren, act ); +} +#endif + +#ifdef VTK_OPENGL2 +#include +#include +#include +#endif + +void VTKViewer_PolyDataMapper::InternalDraw(vtkRenderer* ren, vtkActor* act ) { vtkUnsignedCharArray* colors = NULL; vtkPolyData* input = this->GetInput(); vtkPoints* points; - int noAbort = 1; int cellScalars = 0; vtkProperty* prop = act->GetProperty(); @@ -924,7 +840,7 @@ int VTKViewer_PolyDataMapper::Draw( vtkRenderer* ren, vtkActor* act ) } int* aSize = this->ImageData->GetDimensions(); - glPointSize( std::max( aSize[0], aSize[1] ) ); + //glPointSize( std::max( aSize[0], aSize[1] ) ); int aMode = 0; // to remove { @@ -946,18 +862,100 @@ int VTKViewer_PolyDataMapper::Draw( vtkRenderer* ren, vtkActor* act ) } if( this->ExtensionsInitialized == ES_Ok ) { +#ifdef VTK_OPENGL2 + this->OpenGLHelper.vglUseProgramObjectARB( this->PointProgram ); + + vtkOpenGLCamera *cam = (vtkOpenGLCamera *)(ren->GetActiveCamera()); + vtkMatrix4x4 *wcdc; + vtkMatrix4x4 *wcvc; + vtkMatrix3x3 *norms; + vtkMatrix4x4 *vcdc; + cam->GetKeyMatrices(ren,wcvc,norms,vcdc,wcdc); + if (!act->GetIsIdentity()) + { + vtkMatrix4x4 *mcwc; + vtkMatrix3x3 *anorms; + ((vtkOpenGLActor *)act)->GetKeyMatrices( mcwc, anorms ); + vtkMatrix4x4::Multiply4x4( mcwc, wcdc, this->TempMatrix4 ); + + this->OpenGLHelper.SetUniformMatrix( this->myLocations.ModelViewProjection, this->TempMatrix4 ); + } + else + { + this->OpenGLHelper.SetUniformMatrix( this->myLocations.ModelViewProjection, wcdc ); + } + this->OpenGLHelper.SetUniformMatrix( this->myLocations.Projection, vcdc ); + + this->OpenGLHelper.vglUniform1iARB( this->myLocations.GeneralPointSize, std::max( aSize[0], aSize[1] ) ); + GLuint aBufferObjectID, aDiamsID = 0; - GLint attribute_diams = -1; - vglGenBuffersARB( 1, &aBufferObjectID ); - vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aBufferObjectID ); + + this->OpenGLHelper.vglBindVertexArrayARB( this->VertexArrayObject ); + this->OpenGLHelper.vglGenBuffersARB( 1, &aBufferObjectID ); + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aBufferObjectID ); int anArrayObjectSize = sizeof( VTK::TVertex ) * aTotalConnectivitySize; - vglBufferDataARB( GL_ARRAY_BUFFER_ARB, anArrayObjectSize, aVertexArr, GL_STATIC_DRAW_ARB ); + this->OpenGLHelper.vglBufferDataARB( GL_ARRAY_BUFFER_ARB, anArrayObjectSize, aVertexArr, GL_STATIC_DRAW_ARB ); delete [] aVertexArr; - vglBindBufferARB( GL_ARRAY_BUFFER_ARB, 0 ); - vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aBufferObjectID ); + + GLint colorAttrib = this->OpenGLHelper.vglGetAttribLocationARB( this->PointProgram, "Color" ); + GLint vertexAttrib = this->OpenGLHelper.vglGetAttribLocationARB( this->PointProgram, "Vertex" ); + GLint diamAttrib = this->OpenGLHelper.vglGetAttribLocationARB( this->PointProgram, "Diameter" ); + + GLsizei vertexSize = sizeof(VTK::TVertex); + + this->OpenGLHelper.vglVertexAttribPointerARB( colorAttrib, 4, GL_FLOAT, GL_FALSE, vertexSize, (const GLvoid*)0 ); + this->OpenGLHelper.vglEnableVertexAttribArrayARB( colorAttrib ); + + this->OpenGLHelper.vglVertexAttribPointerARB( vertexAttrib, 3, GL_FLOAT, GL_FALSE, vertexSize, (const GLvoid*)(sizeof(GLfloat) * 4) ); + this->OpenGLHelper.vglEnableVertexAttribArrayARB( vertexAttrib ); + + if(this->BallEnabled) { + // Don't use uniform variable. + this->OpenGLHelper.vglUniform1iARB( this->myLocations.GeneralPointSize, -1 ); + this->OpenGLHelper.vglGenBuffersARB( 1, &aDiamsID); + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aDiamsID); + + int aDiamsSize = sizeof(TBall)*aNbCells; + this->OpenGLHelper.vglBufferDataARB( GL_ARRAY_BUFFER_ARB, aDiamsSize, aBallArray, GL_STATIC_DRAW_ARB); + + delete [] aBallArray; + + this->OpenGLHelper.vglVertexAttribPointerARB( diamAttrib, 1, GL_FLOAT, GL_FALSE, 0, 0 ); + this->OpenGLHelper.vglEnableVertexAttribArrayARB( diamAttrib ); + } + + glDrawArrays( GL_POINTS, 0, aTotalConnectivitySize ); + + if( this->BallEnabled ) { + this->OpenGLHelper.vglDisableVertexAttribArrayARB( diamAttrib ); + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, 0 ); + this->OpenGLHelper.vglDeleteBuffersARB( 1, &aDiamsID ); + } + + this->OpenGLHelper.vglDisableVertexAttribArrayARB( colorAttrib ); + this->OpenGLHelper.vglDisableVertexAttribArrayARB( vertexAttrib ); + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, 0 ); + this->OpenGLHelper.vglDeleteBuffersARB( 1, &aBufferObjectID ); + this->OpenGLHelper.vglBindVertexArrayARB( 0 ); + + this->OpenGLHelper.vglUseProgramObjectARB( 0 ); +#else + GLuint aBufferObjectID, aDiamsID = 0; + GLint attribute_diams = -1; + + this->OpenGLHelper.vglGenBuffersARB( 1, &aBufferObjectID ); + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aBufferObjectID ); + + int anArrayObjectSize = sizeof( VTK::TVertex ) * aTotalConnectivitySize; + this->OpenGLHelper.vglBufferDataARB( GL_ARRAY_BUFFER_ARB, anArrayObjectSize, aVertexArr, GL_STATIC_DRAW_ARB ); + + delete [] aVertexArr; + + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, 0 ); + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aBufferObjectID ); glColorPointer( 4, GL_FLOAT, sizeof(VTK::TVertex), (void*)0 ); glVertexPointer( 3, GL_FLOAT, sizeof(VTK::TVertex), (void*)(4*sizeof(GLfloat)) ); @@ -966,20 +964,20 @@ int VTKViewer_PolyDataMapper::Draw( vtkRenderer* ren, vtkActor* act ) glEnableClientState( GL_COLOR_ARRAY ); if(this->BallEnabled) { - vglGenBuffersARB( 2, &aDiamsID); - vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aDiamsID); + this->OpenGLHelper.vglGenBuffersARB( 1, &aDiamsID); + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aDiamsID); int aDiamsSize = sizeof(TBall)*aNbCells; - vglBufferDataARB( GL_ARRAY_BUFFER_ARB, aDiamsSize, aBallArray, GL_STATIC_DRAW_ARB); + this->OpenGLHelper.vglBufferDataARB( GL_ARRAY_BUFFER_ARB, aDiamsSize, aBallArray, GL_STATIC_DRAW_ARB); delete [] aBallArray; - vglBindBufferARB( GL_ARRAY_BUFFER_ARB, 0 ); - vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aDiamsID ); + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, 0 ); + this->OpenGLHelper.vglBindBufferARB( GL_ARRAY_BUFFER_ARB, aDiamsID ); - attribute_diams = vglGetAttribLocationARB(this->VertexProgram, "diameter"); - vglEnableVertexAttribArrayARB(attribute_diams); - vglBindBufferARB(GL_ARRAY_BUFFER_ARB, aDiamsID); - vglVertexAttribPointerARB( + attribute_diams = vglGetAttribLocationARB(this->PointProgram, "diameter"); + this->OpenGLHelper.vglEnableVertexAttribArrayARB(attribute_diams); + this->OpenGLHelper.vglBindBufferARB(GL_ARRAY_BUFFER_ARB, aDiamsID); + this->OpenGLHelper.vglVertexAttribPointerARB( attribute_diams, // attribute 1, // number of elements per vertex, here (diameter) GL_FLOAT, // the type of each element @@ -993,13 +991,14 @@ int VTKViewer_PolyDataMapper::Draw( vtkRenderer* ren, vtkActor* act ) glDisableClientState( GL_COLOR_ARRAY ); glDisableClientState( GL_VERTEX_ARRAY ); - vglDeleteBuffersARB( 1, &aBufferObjectID ); + this->OpenGLHelper.vglDeleteBuffersARB( 1, &aBufferObjectID ); if(this->BallEnabled) { - vglDisableVertexAttribArrayARB(attribute_diams); - vglDeleteBuffersARB( 2, &aDiamsID ); + this->OpenGLHelper.vglDisableVertexAttribArrayARB(attribute_diams); + this->OpenGLHelper.vglDeleteBuffersARB( 1, &aDiamsID ); } +#endif } else { // there are no extensions glColorPointer( 4, GL_FLOAT, sizeof(VTK::TVertex), aVertexArr ); glVertexPointer( 3, GL_FLOAT, sizeof(VTK::TVertex), @@ -1019,5 +1018,4 @@ int VTKViewer_PolyDataMapper::Draw( vtkRenderer* ren, vtkActor* act ) } this->UpdateProgress(1.0); - return noAbort; } diff --git a/src/VTKViewer/VTKViewer_PolyDataMapper.h b/src/VTKViewer/VTKViewer_PolyDataMapper.h index f945ed59e..8fa5725b0 100644 --- a/src/VTKViewer/VTKViewer_PolyDataMapper.h +++ b/src/VTKViewer/VTKViewer_PolyDataMapper.h @@ -43,10 +43,7 @@ class vtkImageData; #define MAPPER_SUPERCLASS vtkMesaPolyDataMapper #endif -#ifndef GL_ARB_shader_objects -typedef GLuint GLhandleARB; -#endif - +#include "VTKViewer_OpenGLHelper.h" //---------------------------------------------------------------------------- //! OpenGL Point Sprites PolyData Mapper. @@ -97,9 +94,12 @@ public: //! Implement superclass render method. virtual void RenderPiece( vtkRenderer*, vtkActor* ); - //! Draw method for OpenGL. +#ifndef VTK_OPENGL2 virtual int Draw( vtkRenderer*, vtkActor* ); +#else + virtual void RenderPieceDraw( vtkRenderer*, vtkActor* ); +#endif protected: VTKViewer_PolyDataMapper(); @@ -118,7 +118,9 @@ protected: void InitTextures(); //! Initializing of the Vertex Shader. - void InitShader(); + int InitShader(); + + void InternalDraw(vtkRenderer*, vtkActor*); private: int ExtensionsInitialized; @@ -126,11 +128,35 @@ private: GLuint PointSpriteTexture; vtkSmartPointer ImageData; - - GLhandleARB VertexProgram; + + VTKViewer_OpenGLHelper OpenGLHelper; + GLhandleARB PointProgram; +#ifdef VTK_OPENGL2 + GLhandleARB VertexShader; + GLhandleARB FragmentShader; + GLuint VertexArrayObject; +#endif + + struct Locations { + static const GLint INVALID_LOCATION = -1; + + GLint ModelViewProjection; + GLint Projection; + GLint GeneralPointSize; + GLint PointSprite; + + Locations() + : ModelViewProjection (INVALID_LOCATION), + Projection (INVALID_LOCATION), + GeneralPointSize (INVALID_LOCATION), + PointSprite (INVALID_LOCATION) + { + // + } + } myLocations; bool MarkerEnabled; - bool BallEnabled; + bool BallEnabled; double BallScale; VTK::MarkerType MarkerType; VTK::MarkerScale MarkerScale; diff --git a/src/VTKViewer/VTKViewer_Texture.cxx b/src/VTKViewer/VTKViewer_Texture.cxx index 2a54a03ee..7b20cd5e1 100644 --- a/src/VTKViewer/VTKViewer_Texture.cxx +++ b/src/VTKViewer/VTKViewer_Texture.cxx @@ -28,12 +28,17 @@ #include "vtkOpenGLRenderer.h" #include "vtkPointData.h" #include "vtkRenderWindow.h" +#ifndef VTK_OPENGL2 #include "vtkOpenGLExtensionManager.h" +#include "vtkgl.h" // vtkgl namespace +#else +#include "vtkTextureObject.h" +#include "vtkOpenGLError.h" +#endif #include "vtkOpenGLRenderWindow.h" #include "vtkTransform.h" #include "vtkPixelBufferObject.h" #include "vtkOpenGL.h" -#include "vtkgl.h" // vtkgl namespace #include vtkStandardNewMacro(VTKViewer_Texture); @@ -56,6 +61,7 @@ VTKViewer_Texture::~VTKViewer_Texture() // Implement base class method. void VTKViewer_Texture::Load(vtkRenderer *ren) { +#ifndef VTK_OPENGL2 GLenum format = GL_LUMINANCE; vtkImageData *input = this->GetInput(); @@ -464,6 +470,204 @@ void VTKViewer_Texture::Load(vtkRenderer *ren) vtkgl::Uniform1i(uTexture,0); // active texture 0 } */ +#else + if (!this->ExternalTextureObject) + { + vtkImageData *input = this->GetInput(); + + // Need to reload the texture. + // There used to be a check on the render window's mtime, but + // this is too broad of a check (e.g. it would cause all textures + // to load when only the desired update rate changed). + // If a better check is required, check something more specific, + // like the graphics context. + vtkOpenGLRenderWindow* renWin = + static_cast(ren->GetRenderWindow()); + + // has something changed so that we need to rebuild the texture? + if (this->GetMTime() > this->LoadTime.GetMTime() || + input->GetMTime() > this->LoadTime.GetMTime() || + (this->GetLookupTable() && this->GetLookupTable()->GetMTime () > + this->LoadTime.GetMTime()) || + renWin != this->RenderWindow.GetPointer() || + renWin->GetContextCreationTime() > this->LoadTime) + { + int size[3]; + unsigned char *dataPtr; + unsigned char *resultData = 0; + int xsize, ysize; + + this->RenderWindow = renWin; + if (this->TextureObject == 0) + { + this->TextureObject = vtkTextureObject::New(); + } + this->TextureObject->ResetFormatAndType(); + this->TextureObject->SetContext(renWin); + + // Get the scalars the user choose to color with. + vtkDataArray* scalars = this->GetInputArrayToProcess(0, input); + + // make sure scalars are non null + if (!scalars) + { + vtkErrorMacro(<< "No scalar values found for texture input!"); + return; + } + + // get some info + input->GetDimensions(size); + + if (input->GetNumberOfCells() == scalars->GetNumberOfTuples()) + { + // we are using cell scalars. Adjust image size for cells. + for (int kk = 0; kk < 3; kk++) + { + if (size[kk]>1) + { + size[kk]--; + } + } + } + + int bytesPerPixel = scalars->GetNumberOfComponents(); + + // make sure using unsigned char data of color scalars type + if (this->IsDepthTexture != 1 && + (this->MapColorScalarsThroughLookupTable || + scalars->GetDataType() != VTK_UNSIGNED_CHAR )) + { + dataPtr = this->MapScalarsToColors (scalars); + bytesPerPixel = 4; + } + else + { + dataPtr = static_cast(scalars)->GetPointer(0); + } + + // we only support 2d texture maps right now + // so one of the three sizes must be 1, but it + // could be any of them, so lets find it + if (size[0] == 1) + { + xsize = size[1]; ysize = size[2]; + } + else + { + xsize = size[0]; + if (size[1] == 1) + { + ysize = size[2]; + } + else + { + ysize = size[1]; + if (size[2] != 1) + { + vtkErrorMacro(<< "3D texture maps currently are not supported!"); + return; + } + } + } + + // -- decide whether the texture needs to be resampled -- + GLint maxDimGL; + glGetIntegerv(GL_MAX_TEXTURE_SIZE, &maxDimGL); + vtkOpenGLCheckErrorMacro("failed at glGetIntegerv"); + // if larger than permitted by the graphics library then must resample + bool resampleNeeded = xsize > maxDimGL || ysize > maxDimGL; + if(resampleNeeded) + { + vtkDebugMacro( "Texture too big for gl, maximum is " << maxDimGL); + } + + if (resampleNeeded) + { + vtkDebugMacro(<< "Resampling texture to power of two for OpenGL"); + resultData = this->ResampleToPowerOfTwo(xsize, ysize, dataPtr, + bytesPerPixel); + } + + if (!resultData) + { + resultData = dataPtr; + } + + // create the texture + if (this->IsDepthTexture) + { + this->TextureObject->CreateDepthFromRaw( + xsize, ysize, vtkTextureObject::Float32, scalars->GetDataType(), resultData); + } + else + { + this->TextureObject->Create2DFromRaw( + xsize, ysize, bytesPerPixel, VTK_UNSIGNED_CHAR, resultData); + } + myWidth = xsize; + myHeight = ysize; + // activate a free texture unit for this texture + this->TextureObject->Activate(); + + // update parameters + if (this->Interpolate) + { + this->TextureObject->SetMinificationFilter(vtkTextureObject::Linear); + this->TextureObject->SetMagnificationFilter(vtkTextureObject::Linear); + } + else + { + this->TextureObject->SetMinificationFilter(vtkTextureObject::Nearest); + this->TextureObject->SetMagnificationFilter(vtkTextureObject::Nearest); + } + if (this->Repeat) + { + this->TextureObject->SetWrapS(vtkTextureObject::Repeat); + this->TextureObject->SetWrapT(vtkTextureObject::Repeat); + this->TextureObject->SetWrapR(vtkTextureObject::Repeat); + } + else + { + this->TextureObject->SetWrapS(vtkTextureObject::ClampToEdge); + this->TextureObject->SetWrapT(vtkTextureObject::ClampToEdge); + this->TextureObject->SetWrapR(vtkTextureObject::ClampToEdge); + } + + // modify the load time to the current time + this->LoadTime.Modified(); + + // free memory + if (resultData != dataPtr) + { + delete [] resultData; + resultData = 0; + } + } + } + else + { + vtkOpenGLRenderWindow* renWin = + static_cast(ren->GetRenderWindow()); + + // has something changed so that we need to rebuild the texture? + if (this->GetMTime() > this->LoadTime.GetMTime() || + renWin != this->RenderWindow.GetPointer() || + renWin->GetContextCreationTime() > this->LoadTime) + { + this->RenderWindow = renWin; + this->TextureObject->SetContext(renWin); + } + } + // activate a free texture unit for this texture + this->TextureObject->Activate(); + + if (this->PremultipliedAlpha) + { + // make the blend function correct for textures premultiplied by alpha. + glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA); + } + vtkOpenGLCheckErrorMacro("failed after Load"); +#endif } void VTKViewer_Texture::Initialize(vtkRenderer * vtkNotUsed(ren)) diff --git a/src/VTKViewer/resources/Background.fs.glsl b/src/VTKViewer/resources/Background.fs.glsl new file mode 100644 index 000000000..2c68fe90a --- /dev/null +++ b/src/VTKViewer/resources/Background.fs.glsl @@ -0,0 +1,21 @@ +#version 130 + +#if (__VERSION__ >= 130) + out vec4 outColor; + #define Texture2D texture +#else + #define outColor gl_FragColor + #define Texture2D texture2D +#endif + +uniform int uUseTexture; +uniform sampler2D uBackgroundTexture; + +in vec4 VSColor; +void main() +{ + if (uUseTexture == 1) + outColor = Texture2D(uBackgroundTexture, VSColor.xy); + else + outColor = VSColor; +} diff --git a/src/VTKViewer/resources/Background.vs.glsl b/src/VTKViewer/resources/Background.vs.glsl new file mode 100644 index 000000000..da9d1c700 --- /dev/null +++ b/src/VTKViewer/resources/Background.vs.glsl @@ -0,0 +1,15 @@ +#version 330 core +#if (__VERSION__ >= 130) + in vec4 Color; + in vec3 Vertex; +#else + #define Vertex gl_Vertex + #define Color gl_Color; +#endif + +out vec4 VSColor; +void main() +{ + gl_Position = vec4 (Vertex.xyz, 1.0); + VSColor = Color; +} diff --git a/src/VTKViewer/resources/Point.fs.glsl b/src/VTKViewer/resources/Point.fs.glsl new file mode 100644 index 000000000..d13a97713 --- /dev/null +++ b/src/VTKViewer/resources/Point.fs.glsl @@ -0,0 +1,21 @@ +#version 130 + +#if (__VERSION__ >= 130) + out vec4 outColor; + #define Texture2D texture +#else + #define outColor gl_FragColor + #define Texture2D texture2D +#endif + +uniform sampler2D uPointSprite; + +in vec4 VSColor; +void main() +{ + vec4 aColor = Texture2D(uPointSprite, gl_PointCoord) * VSColor; + if (aColor.a < 0.5) + discard; + + outColor = aColor; +} diff --git a/src/VTKViewer/resources/Point.vs.glsl b/src/VTKViewer/resources/Point.vs.glsl new file mode 100644 index 000000000..50f109e63 --- /dev/null +++ b/src/VTKViewer/resources/Point.vs.glsl @@ -0,0 +1,27 @@ +#version 130 +#if (__VERSION__ >= 130) + in vec4 Color; + in vec3 Vertex; + in float Diameter; +#else + #define Vertex gl_Vertex + #define Color gl_Color; + attribute float Diameter; +#endif + +uniform mat4 uProjectionMatrix; +uniform mat4 uModelViewProjectionMatrix; +uniform int uGeneralPointSize; + +out vec4 VSColor; +void main() +{ + gl_Position = uModelViewProjectionMatrix * vec4 (Vertex.xyz, 1.0); + + if (uGeneralPointSize == -1) + gl_PointSize = 1400 * uProjectionMatrix[1].y * Diameter; + else + gl_PointSize = uGeneralPointSize; + + VSColor = Color; +} diff --git a/src/VTKViewer/resources/Vertex_Program_ARB.txt b/src/VTKViewer/resources/Vertex_Program_ARB.txt index 46d01a88f..10eb1b536 100644 --- a/src/VTKViewer/resources/Vertex_Program_ARB.txt +++ b/src/VTKViewer/resources/Vertex_Program_ARB.txt @@ -4,5 +4,5 @@ void main() { gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; gl_FrontColor = gl_Color; - gl_PointSize = 1400 * gl_ProjectionMatrix[1].y * diameter; + gl_PointSize = 1400.0 * gl_ProjectionMatrix[1].y * diameter; }