00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032 #include <vlCore/GlobalSettings.hpp>
00033 #include <vlGraphics/OpenGLContext.hpp>
00034 #include <vlGraphics/OpenGL.hpp>
00035 #include <vlGraphics/IVertexAttribSet.hpp>
00036 #include <vlGraphics/Shader.hpp>
00037 #include <vlGraphics/GLSL.hpp>
00038 #include <vlGraphics/Light.hpp>
00039 #include <vlGraphics/ClipPlane.hpp>
00040 #include <vlCore/Log.hpp>
00041 #include <vlCore/Say.hpp>
00042 #include <algorithm>
00043 #include <sstream>
00044
00045 using namespace vl;
00046
00047
00048
00049
00050 OpenGLContext* UIEventListener::openglContext() { return mOpenGLContext; }
00051
00052
00053
00054 OpenGLContext::OpenGLContext(int w, int h)
00055 {
00056 VL_DEBUG_SET_OBJECT_NAME()
00057 mFramebuffer = new Framebuffer(this, w, h);
00058
00059
00060 memset( mTexUnitBinding, 0, sizeof(mTexUnitBinding) );
00061
00062
00063 memset( mCurrentRenderState, 0xFF, sizeof(mCurrentRenderState) );
00064 memset( mRenderStateTable, 0xFF, sizeof(mRenderStateTable) );
00065 memset( mCurrentEnable, 0xFF, sizeof(mCurrentEnable) );
00066 memset( mEnableTable, 0xFF, sizeof(mEnableTable) );
00067 memset( mPrevRenderStates, 0xFF, sizeof(mPrevRenderStates) );
00068 memset( mPrevEnables, 0xFF, sizeof(mPrevEnables) );
00069
00070 mPrevRenderStatesCount = 0;
00071 mPrevEnablesCount = 0;
00072
00073 mIsInitialized = false;
00074 mHasDoubleBuffer = false;
00075 mMaxVertexAttrib = 0;
00076 mTextureSamplerCount = 0;
00077 mCurVAS = NULL;
00078
00079 mNormal = fvec3(0,1,0);
00080 mColor = fvec4(1,1,1,1);
00081 mSecondaryColor = fvec3(1,1,1);
00082
00083
00084
00085 mMouseVisible = true;
00086 mContinuousUpdate = true;
00087 mIgnoreNextMouseMoveEvent = false;
00088 mFullscreen = false;
00089 }
00090
00091 OpenGLContext::~OpenGLContext()
00092 {
00093 if (mFramebufferObject.size() || mEventListeners.size())
00094 Log::warning("~OpenGLContext(): you should have called dispatchDestroyEvent() before destroying the OpenGLContext!\nNow it's too late to cleanup things!\n");
00095
00096
00097 mFramebuffer->mOpenGLContext = NULL;
00098
00099
00100 for(unsigned i=0; i<mFramebufferObject.size(); ++i)
00101 {
00102
00103
00104 mFramebufferObject[i]->mOpenGLContext = NULL;
00105 }
00106
00107
00108 eraseAllEventListeners();
00109 }
00110
00111 ref<FramebufferObject> OpenGLContext::createFramebufferObject(int width, int height)
00112 {
00113 makeCurrent();
00114 mFramebufferObject.push_back(new FramebufferObject(this, width, height));
00115 mFramebufferObject.back()->createFBO();
00116 return mFramebufferObject.back();
00117 }
00118
00119 void OpenGLContext::destroyFramebufferObject(FramebufferObject* fbort)
00120 {
00121 makeCurrent();
00122 for(unsigned i=0; i<mFramebufferObject.size(); ++i)
00123 {
00124 if (mFramebufferObject[i] == fbort)
00125 {
00126 mFramebufferObject[i]->deleteFBO();
00127 mFramebufferObject[i]->mOpenGLContext = NULL;
00128 mFramebufferObject.erase(mFramebufferObject.begin()+i);
00129 return;
00130 }
00131 }
00132 }
00133
00134 void OpenGLContext::destroyAllFramebufferObjects()
00135 {
00136 makeCurrent();
00137 for(unsigned i=0; i<mFramebufferObject.size(); ++i)
00138 {
00139 mFramebufferObject[i]->deleteFBO();
00140 mFramebufferObject[i]->mOpenGLContext = NULL;
00141 }
00142 mFramebufferObject.clear();
00143 }
00144
00145 void OpenGLContext::addEventListener(UIEventListener* el)
00146 {
00147 VL_CHECK( el );
00148 VL_CHECK( el->mOpenGLContext == NULL );
00149 if (el->mOpenGLContext == NULL)
00150 {
00151 mEventListeners.push_back(el);
00152 el->mOpenGLContext = this;
00153 el->addedListenerEvent(this);
00154 if (isInitialized())
00155 el->initEvent();
00156 }
00157 }
00158
00159 void OpenGLContext::removeEventListener(UIEventListener* el)
00160 {
00161 VL_CHECK( el );
00162 VL_CHECK( el->mOpenGLContext == this || el->mOpenGLContext == NULL );
00163 if (el->mOpenGLContext == this)
00164 {
00165 std::vector< ref<UIEventListener> >::iterator pos = std::find(mEventListeners.begin(), mEventListeners.end(), el);
00166 if( pos != mEventListeners.end() )
00167 {
00168 mEventListeners.erase( pos );
00169
00170 el->removedListenerEvent(this);
00171 el->mOpenGLContext = NULL;
00172 }
00173 }
00174 }
00175
00176 void OpenGLContext::eraseAllEventListeners()
00177 {
00178
00179
00180 std::vector< ref<UIEventListener> > temp = mEventListeners;
00181 mEventListeners.clear();
00182 for(size_t i=0; i<temp.size(); ++i)
00183 {
00184 VL_CHECK( temp[i]->mOpenGLContext == this );
00185 temp[i]->removedListenerEvent(this);
00186 temp[i]->mOpenGLContext = NULL;
00187 }
00188 }
00189
00190 void OpenGLContext::setVSyncEnabled(bool enable)
00191 {
00192 #if defined(VL_OPENGL) && defined(VL_PLATFORM_WINDOWS)
00193 makeCurrent();
00194 if (Has_GL_EXT_swap_control)
00195 wglSwapIntervalEXT(enable?1:0);
00196 #else
00197
00198 #endif
00199 }
00200
00201 bool OpenGLContext::vsyncEnabled() const
00202 {
00203 #if defined(VL_OPENGL) && defined(VL_PLATFORM_WINDOWS)
00204 if (Has_GL_EXT_swap_control)
00205 return wglGetSwapIntervalEXT() != 0;
00206 else
00207 return false;
00208 #else
00209 return false;
00210 #endif
00211 }
00212
00213 bool OpenGLContext::initGLContext(bool log)
00214 {
00215 mIsInitialized = false;
00216
00217 makeCurrent();
00218
00219
00220 if (!initializeOpenGL())
00221 {
00222 Log::error("Error initializing OpenGL!\n");
00223 VL_TRAP()
00224 return false;
00225 }
00226
00227 mExtensions = getOpenGLExtensions();
00228
00229 if (log)
00230 logOpenGLInfo();
00231
00232 VL_CHECK_OGL();
00233
00234
00235 mTextureSamplerCount = 1;
00236 if (Has_GL_ARB_multitexture||Has_GL_Version_1_3||Has_GLES_Version_1_1)
00237 {
00238 int max_tmp = 0;
00239 glGetIntegerv(GL_MAX_TEXTURE_UNITS, &max_tmp); VL_CHECK_OGL();
00240 mTextureSamplerCount = max_tmp > mTextureSamplerCount ? max_tmp : mTextureSamplerCount;
00241 }
00242 if (Has_GL_Version_2_0)
00243 {
00244 int max_tmp = 0;
00245 glGetIntegerv(GL_MAX_TEXTURE_COORDS, &max_tmp); VL_CHECK_OGL();
00246 mTextureSamplerCount = max_tmp > mTextureSamplerCount ? max_tmp : mTextureSamplerCount;
00247 }
00248 if (Has_GLSL)
00249 {
00250 int max_tmp = 0;
00251 glGetIntegerv(GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS, &max_tmp); VL_CHECK_OGL();
00252 mTextureSamplerCount = max_tmp > mTextureSamplerCount ? max_tmp : mTextureSamplerCount;
00253 }
00254 mTextureSamplerCount = mTextureSamplerCount < VL_MAX_TEXTURE_UNITS ? mTextureSamplerCount : VL_MAX_TEXTURE_UNITS;
00255
00256
00257 mMaxVertexAttrib = 0;
00258 if(Has_GLSL)
00259 glGetIntegerv(GL_MAX_VERTEX_ATTRIBS, &mMaxVertexAttrib);
00260 mMaxVertexAttrib = mMaxVertexAttrib < VL_MAX_GENERIC_VERTEX_ATTRIB ? mMaxVertexAttrib : VL_MAX_GENERIC_VERTEX_ATTRIB;
00261
00262 VL_CHECK_OGL();
00263
00264 #if defined(VL_OPENGL)
00265
00266 glDrawBuffer(GL_BACK);
00267 if ( glGetError() )
00268 mHasDoubleBuffer = false;
00269 else
00270 mHasDoubleBuffer = true;
00271 #else
00272 mHasDoubleBuffer = true;
00273 #endif
00274
00275 setupDefaultRenderStates();
00276
00277 return mIsInitialized = true;;
00278 }
00279
00280 bool OpenGLContext::isExtensionSupported(const char* ext_name)
00281 {
00282 makeCurrent();
00283 size_t len = strlen(ext_name);
00284 const char* ext = mExtensions.c_str();
00285 const char* ext_end = ext + strlen(ext);
00286
00287 for( const char* pos = strstr(ext,ext_name); pos && pos < ext_end; pos = strstr(pos,ext_name) )
00288 {
00289 if (pos[len] == ' ' || pos[len] == 0)
00290 return true;
00291 else
00292 pos += len;
00293 }
00294
00295 return false;
00296 }
00297
00298 void* OpenGLContext::getProcAddress(const char* function_name)
00299 {
00300 makeCurrent();
00301 return getGLProcAddress(function_name);
00302 }
00303
00304 void OpenGLContext::logOpenGLInfo()
00305 {
00306 makeCurrent();
00307
00308 Log::debug(" --- OpenGL Info ---\n");
00309 Log::debug( Say("OpenGL version: %s\n") << glGetString(GL_VERSION) );
00310 Log::debug( Say("OpenGL vendor: %s\n") << glGetString(GL_VENDOR) );
00311 Log::debug( Say("OpenGL renderer: %s\n") << glGetString(GL_RENDERER) );
00312 Log::debug( Say("OpenGL profile: %s\n") << (Has_Fixed_Function_Pipeline ? "Compatible" : "Core") );
00313
00314 if (Has_GLSL)
00315 Log::debug( Say("GLSL version: %s\n") << glGetString(GL_SHADING_LANGUAGE_VERSION) );
00316
00317 int max_val = 0;
00318 glGetIntegerv(GL_MAX_TEXTURE_SIZE, &max_val);
00319 Log::debug( Say("Max texture size: %n\n")<<max_val);
00320
00321 max_val = 1;
00322 if (Has_GL_ARB_multitexture||Has_GL_Version_1_3||Has_GLES_Version_1_1)
00323 glGetIntegerv(GL_MAX_TEXTURE_UNITS, &max_val);
00324 Log::debug( Say("Texture units (legacy): %n\n") << max_val);
00325
00326 max_val = 0;
00327 if (Has_GL_Version_2_0)
00328 {
00329 glGetIntegerv(GL_MAX_TEXTURE_COORDS, &max_val);
00330 Log::debug( Say("Texture units (client): %n\n") << max_val);
00331 }
00332 if (Has_GLSL)
00333 {
00334 int tmp = 0;
00335 glGetIntegerv(GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS, &tmp);
00336
00337 max_val = tmp > max_val ? tmp : max_val;
00338 Log::debug( Say("Texture units (combined): %n\n") << max_val);
00339 }
00340
00341 max_val = 0;
00342 if (Has_GLSL)
00343 {
00344 glGetIntegerv(GL_MAX_TEXTURE_IMAGE_UNITS, &max_val);
00345 Log::debug( Say("Texture units (fragment shader): %n\n") << max_val);
00346 }
00347
00348 max_val = 0;
00349 if (Has_GL_EXT_texture_filter_anisotropic)
00350 glGetIntegerv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &max_val);
00351 Log::debug( Say("Anisotropic texture filter: %s, ") << (Has_GL_EXT_texture_filter_anisotropic? "YES" : "NO") );
00352 Has_GL_EXT_texture_filter_anisotropic ? Log::debug( Say("%nX\n") << max_val) : Log::debug("\n");
00353 Log::debug( Say("S3 Texture Compression: %s\n") << (Has_GL_EXT_texture_compression_s3tc? "YES" : "NO") );
00354 Log::debug( Say("Vertex Buffer Object: %s\n") << (Has_BufferObject? "YES" : "NO"));
00355 Log::debug( Say("Pixel Buffer Object: %s\n") << (Has_PBO ? "YES" : "NO"));
00356 Log::debug( Say("Framebuffer Object: %s\n") << (Has_FBO? "YES" : "NO"));
00357
00358 max_val = 0;
00359 if(Has_GLSL)
00360 {
00361 glGetIntegerv(GL_MAX_VERTEX_ATTRIBS, &max_val); VL_CHECK_OGL();
00362 Log::debug( Say("Max vertex attributes: %n\n")<<max_val);
00363 }
00364
00365 VL_CHECK_OGL();
00366
00367 max_val = 0;
00368 if(Has_GLSL)
00369 {
00370 if (Has_GLES_Version_2_0||Has_GL_Version_3_0||Has_GL_Version_4_0)
00371 {
00372 glGetIntegerv(GL_MAX_VARYING_VECTORS, &max_val); VL_CHECK_OGL();
00373 }
00374 if (Has_GL_Version_2_0)
00375 {
00376 glGetIntegerv(GL_MAX_VARYING_FLOATS, &max_val); VL_CHECK_OGL();
00377 max_val /= 4;
00378 }
00379 Log::debug( Say("Max varying vectors: %n\n")<<max_val);
00380 }
00381
00382 max_val = 0;
00383 if(Has_GLSL)
00384 {
00385 if (Has_GLES_Version_2_0)
00386 {
00387 glGetIntegerv(GL_MAX_FRAGMENT_UNIFORM_VECTORS, &max_val); VL_CHECK_OGL();
00388 }
00389 else
00390 {
00391 glGetIntegerv(GL_MAX_FRAGMENT_UNIFORM_COMPONENTS, &max_val); VL_CHECK_OGL();
00392 max_val /= 4;
00393 }
00394
00395 Log::debug( Say("Max fragment uniform vectors: %n\n")<<max_val);
00396 }
00397
00398 max_val = 0;
00399 if(Has_GLSL)
00400 {
00401 if (Has_GLES_Version_2_0)
00402 {
00403 glGetIntegerv(GL_MAX_VERTEX_UNIFORM_VECTORS, &max_val); VL_CHECK_OGL();
00404 }
00405 else
00406 {
00407 glGetIntegerv(GL_MAX_VERTEX_UNIFORM_COMPONENTS, &max_val); VL_CHECK_OGL();
00408 max_val /= 4;
00409 }
00410
00411 Log::debug( Say("Max vertex uniform vectors: %n\n")<<max_val);
00412 }
00413
00414 max_val = 0;
00415 if(Has_GL_Version_1_2||Has_GL_Version_3_0||Has_GL_Version_4_0)
00416 {
00417 glGetIntegerv(GL_MAX_ELEMENTS_VERTICES, &max_val); VL_CHECK_OGL();
00418 Log::debug( Say("Max elements vertices: %n\n") << max_val );
00419 }
00420
00421 max_val = 0;
00422 if(Has_GL_Version_1_2||Has_GL_Version_3_0||Has_GL_Version_4_0)
00423 {
00424 glGetIntegerv(GL_MAX_ELEMENTS_INDICES, &max_val ); VL_CHECK_OGL();
00425 Log::debug( Say("Max elements indices: %n\n") << max_val );
00426 }
00427
00428 if (Has_Fixed_Function_Pipeline)
00429 {
00430 max_val = 0;
00431 glGetIntegerv(GL_MAX_CLIP_PLANES, &max_val ); VL_CHECK_OGL();
00432 Log::debug( Say("Max clipping planes: %n\n") << max_val );
00433 }
00434 else
00435 if (Has_GLSL && !Has_GLES_Version_2_0)
00436 {
00437 max_val = 0;
00438 glGetIntegerv(GL_MAX_CLIP_DISTANCES, &max_val ); VL_CHECK_OGL();
00439 Log::debug( Say("Max clip distances: %n\n") << max_val );
00440 }
00441
00442
00443
00444 Log::debug("\n --- OpenGL Extensions --- \n");
00445
00446 std::stringstream sstream;
00447 sstream << extensions();
00448 std::string ext, line;
00449 for( int i=0; !sstream.eof(); ++i )
00450 {
00451 sstream >> ext;
00452 if (sstream.eof())
00453 break;
00454
00455 if (i && i % 2)
00456 {
00457 line.resize(40,' ');
00458 line += ext;
00459 Log::debug( Say("%s\n") << line );
00460 line.clear();
00461 }
00462 else
00463 line = ext;
00464 }
00465 if (line.length())
00466 Log::debug( Say("%s\n") << line );
00467 Log::debug("\n");
00468
00469 VL_CHECK_OGL();
00470 }
00471
00472 void OpenGLContext::applyEnables( const EnableSet* cur )
00473 {
00474 VL_CHECK_OGL()
00475
00476
00477
00478 if (cur)
00479 for( size_t i=0; i<cur->enables().size(); ++i )
00480 mEnableTable[ cur->enables()[i] ] |= 2;
00481
00482
00483
00484
00485
00486
00487
00488
00489 for( size_t i=0; i<mPrevEnablesCount; ++i )
00490 {
00491 const EEnable& prev_en = mPrevEnables[i];
00492 VL_CHECK(mEnableTable[prev_en] == 1 || mEnableTable[prev_en] == 2 || mEnableTable[prev_en] == 3);
00493 if ( mEnableTable[prev_en] == 1 )
00494 {
00495 mEnableTable[prev_en] = 0;
00496 VL_CHECK( mCurrentEnable[prev_en] == true )
00497 mCurrentEnable[prev_en] = false;
00498 glDisable( Translate_Enable[prev_en] ); VL_CHECK_OGL()
00499 #ifndef NDEBUG
00500 if (glGetError() != GL_NO_ERROR)
00501 {
00502 Log::error( Say("An unsupported enum has been disabled: %s.\n") << Translate_Enable_String[prev_en]);
00503 VL_TRAP()
00504 }
00505 #endif
00506 }
00507 }
00508
00509
00510
00511 if (cur)
00512 {
00513 mPrevEnablesCount = cur->enables().size();
00514 for( size_t i=0; i<cur->enables().size(); ++i )
00515 {
00516 const EEnable& cur_en = cur->enables()[i];
00517 mPrevEnables[i] = cur_en;
00518 mEnableTable[cur_en] >>= 1; VL_CHECK( mEnableTable[cur_en] == 1 );
00519
00520 if ( !mCurrentEnable[cur_en] )
00521 {
00522 glEnable( Translate_Enable[cur_en] );
00523 mCurrentEnable[ cur_en ] = true;
00524 #ifndef NDEBUG
00525 if (glGetError() != GL_NO_ERROR)
00526 {
00527 Log::error( Say("An unsupported function has been enabled: %s.\n") << Translate_Enable_String[cur_en]);
00528 VL_TRAP()
00529 }
00530 #endif
00531 }
00532 }
00533 }
00534 else
00535 {
00536 mPrevEnablesCount = 0;
00537 }
00538
00539 }
00540
00541 void OpenGLContext::applyRenderStates( const RenderStateSet* cur, const Camera* camera )
00542 {
00543 VL_CHECK_OGL()
00544
00545
00546
00547 if (cur)
00548 for( size_t i=0; i<cur->renderStatesCount(); ++i )
00549 mRenderStateTable[ cur->renderStates()[i].type() ] |= 2;
00550
00551
00552
00553
00554
00555
00556
00557
00558 for( size_t i=0; i<mPrevRenderStatesCount; ++i )
00559 {
00560 const ERenderState& prev_rs = mPrevRenderStates[i];
00561 VL_CHECK(mRenderStateTable[prev_rs] == 1 || mRenderStateTable[prev_rs] == 2 || mRenderStateTable[prev_rs] == 3);
00562 if ( mRenderStateTable[prev_rs] == 1 )
00563 {
00564 mRenderStateTable[prev_rs] = 0;
00565 VL_CHECK( mCurrentRenderState[prev_rs] != mDefaultRenderStates[prev_rs].mRS.get() );
00566 mCurrentRenderState[prev_rs] = mDefaultRenderStates[prev_rs].mRS.get();
00567
00568 #ifndef NDEBUG
00569 if (!mDefaultRenderStates[prev_rs].mRS)
00570 {
00571
00572 vl::Log::error( Say("Render state type '%n' not supported by the current OpenGL implementation! (version=%s, vendor=%s)\n") << prev_rs << glGetString(GL_VERSION) << glGetString(GL_VENDOR) );
00573 VL_TRAP()
00574 }
00575 #endif
00576
00577
00578 mDefaultRenderStates[prev_rs].apply(NULL, this); VL_CHECK_OGL()
00579 }
00580 }
00581
00582
00583
00584 if (cur)
00585 {
00586 mPrevRenderStatesCount = cur->renderStatesCount();
00587 for( size_t i=0; i<cur->renderStatesCount(); ++i )
00588 {
00589 const RenderStateSlot& cur_rs = cur->renderStates()[i];
00590 mPrevRenderStates[i] = cur_rs.type();
00591 mRenderStateTable[cur_rs.type()] >>= 1; VL_CHECK(mRenderStateTable[cur_rs.type()] == 1)
00592
00593 if ( mCurrentRenderState[cur_rs.type()] != cur_rs.mRS.get() )
00594 {
00595 mCurrentRenderState[cur_rs.type()] = cur_rs.mRS.get();
00596 VL_CHECK(cur_rs.mRS.get());
00597 cur_rs.apply(camera, this); VL_CHECK_OGL()
00598 }
00599 }
00600 }
00601 else
00602 {
00603 mPrevRenderStatesCount = 0;
00604 }
00605
00606 }
00607
00608 void OpenGLContext::setupDefaultRenderStates()
00609 {
00610 if ( Has_Fixed_Function_Pipeline )
00611 {
00612 mDefaultRenderStates[RS_Color] = RenderStateSlot(new Color, 0);
00613 mDefaultRenderStates[RS_SecondaryColor] = RenderStateSlot(new SecondaryColor, 0);
00614 mDefaultRenderStates[RS_Normal] = RenderStateSlot(new Normal, 0);
00615
00616 mDefaultRenderStates[RS_AlphaFunc] = RenderStateSlot(new AlphaFunc, 0);
00617 mDefaultRenderStates[RS_Fog] = RenderStateSlot(new Fog, 0);
00618 mDefaultRenderStates[RS_ShadeModel] = RenderStateSlot(new ShadeModel, 0);
00619 mDefaultRenderStates[RS_LightModel] = RenderStateSlot(new LightModel, 0);
00620 mDefaultRenderStates[RS_Material] = RenderStateSlot(new Material, 0);
00621 if(!Has_GLES_Version_1_1)
00622 {
00623 mDefaultRenderStates[RS_PixelTransfer] = RenderStateSlot(new PixelTransfer, 0);
00624 mDefaultRenderStates[RS_LineStipple] = RenderStateSlot(new LineStipple, 0);
00625 mDefaultRenderStates[RS_PolygonStipple] = RenderStateSlot(new PolygonStipple, 0);
00626 }
00627
00628 mDefaultRenderStates[RS_Light ] = RenderStateSlot(new Light, 0);
00629 mDefaultRenderStates[RS_Light1] = RenderStateSlot(new Light, 1);
00630 mDefaultRenderStates[RS_Light2] = RenderStateSlot(new Light, 2);
00631 mDefaultRenderStates[RS_Light3] = RenderStateSlot(new Light, 3);
00632 mDefaultRenderStates[RS_Light4] = RenderStateSlot(new Light, 4);
00633 mDefaultRenderStates[RS_Light5] = RenderStateSlot(new Light, 5);
00634 mDefaultRenderStates[RS_Light6] = RenderStateSlot(new Light, 6);
00635 mDefaultRenderStates[RS_Light7] = RenderStateSlot(new Light, 7);
00636
00637 mDefaultRenderStates[RS_ClipPlane ] = RenderStateSlot(new ClipPlane, 0);
00638 mDefaultRenderStates[RS_ClipPlane1] = RenderStateSlot(new ClipPlane, 1);
00639 mDefaultRenderStates[RS_ClipPlane2] = RenderStateSlot(new ClipPlane, 2);
00640 mDefaultRenderStates[RS_ClipPlane3] = RenderStateSlot(new ClipPlane, 3);
00641 mDefaultRenderStates[RS_ClipPlane4] = RenderStateSlot(new ClipPlane, 4);
00642 mDefaultRenderStates[RS_ClipPlane5] = RenderStateSlot(new ClipPlane, 5);
00643 }
00644
00645 if (Has_GL_EXT_blend_color||Has_GL_Version_1_4||Has_GL_Version_3_0||Has_GL_Version_4_0||Has_GLES_Version_2_0)
00646 mDefaultRenderStates[RS_BlendColor] = RenderStateSlot(new BlendColor, 0);
00647
00648 if (Has_GL_Version_1_4||Has_GL_Version_3_0||Has_GL_Version_4_0||Has_GL_OES_blend_subtract||Has_GLES_Version_2_0)
00649 mDefaultRenderStates[RS_BlendEquation] = RenderStateSlot(new BlendEquation, 0);
00650
00651 if(!Has_GLES)
00652 mDefaultRenderStates[RS_PolygonMode] = RenderStateSlot(new PolygonMode, 0);
00653
00654 if(!Has_GLES_Version_2_0)
00655 {
00656 mDefaultRenderStates[RS_LogicOp] = RenderStateSlot(new LogicOp, 0);
00657 mDefaultRenderStates[RS_PointSize] = RenderStateSlot(new PointSize, 0);
00658 }
00659
00660 mDefaultRenderStates[RS_PolygonOffset] = RenderStateSlot(new PolygonOffset, 0);
00661 mDefaultRenderStates[RS_BlendFunc] = RenderStateSlot(new BlendFunc, 0);
00662 mDefaultRenderStates[RS_ColorMask] = RenderStateSlot(new ColorMask, 0);
00663 mDefaultRenderStates[RS_CullFace] = RenderStateSlot(new CullFace, 0);
00664 mDefaultRenderStates[RS_DepthFunc] = RenderStateSlot(new DepthFunc, 0);
00665 mDefaultRenderStates[RS_DepthMask] = RenderStateSlot(new DepthMask, 0);
00666 mDefaultRenderStates[RS_DepthRange] = RenderStateSlot(new DepthRange, 0);
00667 mDefaultRenderStates[RS_FrontFace] = RenderStateSlot(new FrontFace, 0);
00668 mDefaultRenderStates[RS_Hint] = RenderStateSlot(new Hint, 0);
00669 mDefaultRenderStates[RS_LineWidth] = RenderStateSlot(new LineWidth, 0);
00670
00671 if (Has_GL_ARB_point_parameters||Has_GL_Version_1_4||Has_GL_Version_3_0||Has_GL_Version_4_0||Has_GLES_Version_1_1)
00672 mDefaultRenderStates[RS_PointParameter] = RenderStateSlot(new PointParameter, 0);
00673
00674 if (Has_GL_ARB_multisample||Has_GL_Version_1_3||Has_GL_Version_3_0||Has_GL_Version_4_0||Has_GLES_Version_1_1||Has_GLES_Version_2_0)
00675 mDefaultRenderStates[RS_SampleCoverage] = RenderStateSlot(new SampleCoverage, 0);
00676
00677 mDefaultRenderStates[RS_StencilFunc] = RenderStateSlot(new StencilFunc, 0);
00678 mDefaultRenderStates[RS_StencilMask] = RenderStateSlot(new StencilMask, 0);
00679 mDefaultRenderStates[RS_StencilOp] = RenderStateSlot(new StencilOp, 0);
00680 mDefaultRenderStates[RS_GLSLProgram] = RenderStateSlot(new GLSLProgram, 0);
00681
00682 for(int i=0; i<VL_MAX_TEXTURE_UNITS; ++i)
00683 {
00684 if (i < textureUnitCount())
00685 {
00686 mDefaultRenderStates[RS_TextureSampler + i] = RenderStateSlot(new TextureSampler, i);
00687 if( Has_Fixed_Function_Pipeline )
00688 {
00689
00690 if(!Has_GLES_Version_1_1 || Has_GL_OES_texture_cube_map)
00691 mDefaultRenderStates[RS_TexGen + i] = RenderStateSlot(new TexGen, i);
00692 mDefaultRenderStates[RS_TexEnv + i] = RenderStateSlot(new TexEnv, i);
00693 mDefaultRenderStates[RS_TextureMatrix + i] = RenderStateSlot(new TextureMatrix, i);
00694 }
00695 }
00696 }
00697
00698 VL_CHECK_OGL();
00699
00700
00701 for( int i=RS_RenderStateCount; i--; )
00702 {
00703
00704 if (mDefaultRenderStates[i].mRS)
00705 {
00706 mDefaultRenderStates[i].apply(NULL, this); VL_CHECK_OGL();
00707 }
00708 }
00709 }
00710
00711 void OpenGLContext::resetRenderStates()
00712 {
00713 memset( mCurrentRenderState, 0, sizeof(mCurrentRenderState) );
00714 memset( mRenderStateTable, 0, sizeof(mRenderStateTable) );
00715 memset( mTexUnitBinding, 0, sizeof( mTexUnitBinding ) );
00716 memset( mPrevRenderStates, 0xFF, sizeof(mPrevRenderStates) );
00717 mPrevRenderStatesCount = 0;
00718 }
00719
00720 void OpenGLContext::resetEnables()
00721 {
00722 memset( mCurrentEnable, 0, sizeof(mCurrentEnable) );
00723 memset( mEnableTable, 0, sizeof(mEnableTable) );
00724 memset( mPrevEnables, 0xFF, sizeof(mPrevEnables) );
00725 mPrevEnablesCount = 0;
00726 }
00727
00728 bool OpenGLContext::isCleanState(bool verbose)
00729 {
00730 struct contract {
00731 contract() { VL_CHECK_OGL(); }
00732 ~contract() { VL_CHECK_OGL(); }
00733 } contract_instance;
00734
00735 bool ok = true;
00736
00737
00738 for( unsigned i=0; i<EN_EnableCount; ++i )
00739 {
00740 if (!Is_Enable_Supported[i])
00741 continue;
00742
00743 if (i == EN_DITHER || i == EN_MULTISAMPLE)
00744 continue;
00745
00746 GLboolean enabled = glIsEnabled( Translate_Enable[i] ); VL_CHECK_OGL();
00747
00748 if (enabled)
00749 {
00750 if (verbose)
00751 vl::Log::error( Say("Capability %s was enabled!\n") << Translate_Enable_String[i] );
00752 VL_TRAP();
00753 ok = false;
00754 }
00755 }
00756
00757 if (Has_Fixed_Function_Pipeline)
00758 {
00759 int max_lights = 0;
00760 glGetIntegerv(GL_MAX_LIGHTS, &max_lights);
00761
00762 for( int i=0; i<max_lights; ++i)
00763 {
00764 if (glIsEnabled(GL_LIGHT0+i))
00765 {
00766 if (verbose)
00767 vl::Log::error( Say("GL_LIGHT%n was enabled!\n") << i );
00768 VL_TRAP();
00769 ok = false;
00770 }
00771 }
00772
00773
00774 int max_planes = 0;
00775 glGetIntegerv(GL_MAX_CLIP_PLANES, &max_planes);
00776
00777 for( int i=0; i<max_planes; ++i)
00778 {
00779 if (glIsEnabled(GL_CLIP_PLANE0+i))
00780 {
00781 if (verbose)
00782 vl::Log::error( Say("GL_CLIP_PLANE%n was enabled!\n") << i );
00783 VL_TRAP();
00784 ok = false;
00785 }
00786 }
00787 }
00788
00789 if (Has_Primitive_Restart && glIsEnabled(GL_PRIMITIVE_RESTART))
00790 {
00791 if (verbose)
00792 vl::Log::error( "GL_PRIMITIVE_RESTART was enabled!\n" );
00793 VL_TRAP();
00794 ok = false;
00795 }
00796
00797 if(Has_Multitexture)
00798 {
00799 int active_tex = -1;
00800
00801 #if !defined(VL_OPENGL_ES2)
00802 glGetIntegerv(GL_ACTIVE_TEXTURE, &active_tex); VL_CHECK_OGL();
00803 active_tex -= GL_TEXTURE0;
00804 if (active_tex != 0)
00805 {
00806 if (verbose)
00807 vl::Log::error( Say("Active texture unit is #%n instead of #0!\n") << active_tex );
00808 VL_TRAP();
00809 ok = false;
00810 }
00811 #endif
00812
00813 if (Has_Fixed_Function_Pipeline)
00814 {
00815 active_tex = -1;
00816 glGetIntegerv(GL_CLIENT_ACTIVE_TEXTURE, &active_tex); VL_CHECK_OGL();
00817 active_tex -= GL_TEXTURE0;
00818 if (active_tex != 0)
00819 {
00820 if (verbose)
00821 vl::Log::error( Say("Active client texture unit is #%n instead of #0!\n") << active_tex );
00822 VL_TRAP();
00823 ok = false;
00824 }
00825 }
00826 }
00827
00828 VL_CHECK_OGL()
00829
00830
00831
00832 int coord_count = 16;
00833 if (Has_GL_ARB_multitexture||Has_GL_Version_1_3||Has_GLES_Version_1_1)
00834 {
00835 int max_tmp = 0;
00836 glGetIntegerv(GL_MAX_TEXTURE_UNITS, &max_tmp); VL_CHECK_OGL();
00837 coord_count = max_tmp < coord_count ? max_tmp : coord_count;
00838 }
00839
00840 VL_CHECK_OGL()
00841
00842 if (Has_GLSL)
00843 {
00844 int max_tmp = 0;
00845 glGetIntegerv(GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS, &max_tmp); VL_CHECK_OGL();
00846 coord_count = max_tmp < coord_count ? max_tmp : coord_count;
00847 }
00848
00849 if (Has_GL_Version_2_0)
00850 {
00851 int max_tmp = 0;
00852 glGetIntegerv(GL_MAX_TEXTURE_COORDS, &max_tmp); VL_CHECK_OGL();
00853 coord_count = max_tmp < coord_count ? max_tmp : coord_count;
00854 }
00855
00856 VL_CHECK_OGL()
00857
00858 while(coord_count--)
00859 {
00860 VL_CHECK_OGL()
00861 VL_glActiveTexture(GL_TEXTURE0+coord_count); VL_CHECK_OGL()
00862
00863 if (Has_Fixed_Function_Pipeline)
00864 {
00865 VL_glClientActiveTexture(GL_TEXTURE0+coord_count); VL_CHECK_OGL()
00866
00867 float matrix[16];
00868 float imatrix[16];
00869 glGetFloatv(GL_TEXTURE_MATRIX, matrix); VL_CHECK_OGL()
00870 glMatrixMode(GL_TEXTURE); VL_CHECK_OGL()
00871 glLoadIdentity(); VL_CHECK_OGL()
00872 glGetFloatv(GL_TEXTURE_MATRIX, imatrix); VL_CHECK_OGL()
00873 glLoadMatrixf(matrix); VL_CHECK_OGL()
00874 if (memcmp(matrix,imatrix,sizeof(matrix)) != 0)
00875 {
00876 if (verbose)
00877 vl::Log::error( Say("Texture matrix was not set to identity on texture unit %n!\n") << coord_count );
00878 VL_TRAP();
00879 ok = false;
00880 }
00881
00882 if (glIsEnabled(GL_TEXTURE_COORD_ARRAY))
00883 {
00884 if (verbose)
00885 vl::Log::error( Say("GL_TEXTURE_COORD_ARRAY was enabled on texture unit %n!\n") << coord_count );
00886 VL_TRAP();
00887 ok = false;
00888 }
00889
00890
00891
00892 if (!Has_GLES)
00893 {
00894 if (glIsEnabled(GL_TEXTURE_1D))
00895 {
00896 if (verbose)
00897 vl::Log::error( Say("GL_TEXTURE_1D was enabled on texture unit #%n!\n") << coord_count );
00898 VL_TRAP();
00899 ok = false;
00900 }
00901
00902 GLint bound_tex = 0;
00903 glGetIntegerv(GL_TEXTURE_BINDING_1D, &bound_tex); VL_CHECK_OGL()
00904 if (bound_tex != 0)
00905 {
00906 if (verbose)
00907 vl::Log::error( Say("GL_TEXTURE_BINDING_1D != 0 on texture unit #%n!\n") << coord_count );
00908 VL_TRAP();
00909 ok = false;
00910 }
00911 }
00912
00913 if (glIsEnabled(GL_TEXTURE_2D))
00914 {
00915 if (verbose)
00916 vl::Log::error( Say("GL_TEXTURE_2D was enabled on texture unit #%n!\n") << coord_count );
00917 VL_TRAP();
00918 ok = false;
00919 }
00920 }
00921
00922 GLint bound_tex = 0;
00923 glGetIntegerv(GL_TEXTURE_BINDING_2D, &bound_tex); VL_CHECK_OGL()
00924 if (bound_tex != 0)
00925 {
00926 if (verbose)
00927 vl::Log::error( Say("GL_TEXTURE_BINDING_2D != 0 on texture unit #%n!\n") << coord_count );
00928 VL_TRAP();
00929 ok = false;
00930 }
00931
00932 if (Has_Texture_Rectangle)
00933 {
00934 if (Has_Fixed_Function_Pipeline && glIsEnabled(GL_TEXTURE_RECTANGLE))
00935 {
00936 if (verbose)
00937 vl::Log::error( Say("GL_TEXTURE_RECTANGLE was enabled on texture unit #%n!\n") << coord_count );
00938 VL_TRAP();
00939 ok = false;
00940 }
00941
00942 bound_tex = 0;
00943 glGetIntegerv(GL_TEXTURE_BINDING_RECTANGLE, &bound_tex); VL_CHECK_OGL()
00944 if (bound_tex != 0)
00945 {
00946 if (verbose)
00947 vl::Log::error( Say("GL_TEXTURE_BINDING_RECTANGLE != 0 on texture unit #%n!\n") << coord_count );
00948 VL_TRAP();
00949 ok = false;
00950 }
00951 }
00952
00953 if (Has_Texture_3D)
00954 {
00955 if (Has_Fixed_Function_Pipeline && glIsEnabled(GL_TEXTURE_3D))
00956 {
00957 if (verbose)
00958 vl::Log::error( Say("GL_TEXTURE_3D was enabled on texture unit #%n!\n") << coord_count );
00959 VL_TRAP();
00960 ok = false;
00961 }
00962
00963 bound_tex = 0;
00964 glGetIntegerv(GL_TEXTURE_BINDING_3D, &bound_tex); VL_CHECK_OGL()
00965 if (bound_tex != 0)
00966 {
00967 if (verbose)
00968 vl::Log::error( Say("GL_TEXTURE_BINDING_3D != 0 on texture unit #%n!\n") << coord_count );
00969 VL_TRAP();
00970 ok = false;
00971 }
00972 }
00973
00974 if (Has_Cubemap_Textures)
00975 {
00976 if (Has_Fixed_Function_Pipeline && glIsEnabled(GL_TEXTURE_CUBE_MAP))
00977 {
00978 if (verbose)
00979 vl::Log::error( Say("GL_TEXTURE_CUBE_MAP was enabled on texture unit #%n!\n") << coord_count );
00980 VL_TRAP();
00981 ok = false;
00982 }
00983
00984 bound_tex = 0;
00985 glGetIntegerv(GL_TEXTURE_BINDING_CUBE_MAP, &bound_tex); VL_CHECK_OGL()
00986 if (bound_tex != 0)
00987 {
00988 if (verbose)
00989 vl::Log::error( Say("GL_TEXTURE_BINDING_CUBE_MAP != 0 on texture unit #%n!\n") << coord_count );
00990 VL_TRAP();
00991 ok = false;
00992 }
00993 }
00994
00995 if (Has_Texture_Array)
00996 {
00997 bound_tex = 0;
00998 glGetIntegerv(GL_TEXTURE_BINDING_1D_ARRAY, &bound_tex);
00999 if (bound_tex != 0)
01000 {
01001 if (verbose)
01002 vl::Log::error( Say("GL_TEXTURE_BINDING_1D_ARRAY != 0 on texture unit #%n!\n") << coord_count );
01003 VL_TRAP();
01004 ok = false;
01005 }
01006
01007 bound_tex = 0;
01008 glGetIntegerv(GL_TEXTURE_BINDING_2D_ARRAY, &bound_tex);
01009 if (bound_tex != 0)
01010 {
01011 if (verbose)
01012 vl::Log::error( Say("GL_TEXTURE_BINDING_2D_ARRAY != 0 on texture unit #%n!\n") << coord_count );
01013 VL_TRAP();
01014 ok = false;
01015 }
01016 }
01017
01018 if (Has_Texture_Multisample)
01019 {
01020 bound_tex = 0;
01021 glGetIntegerv(GL_TEXTURE_BINDING_2D_MULTISAMPLE, &bound_tex);
01022 if (bound_tex != 0)
01023 {
01024 if (verbose)
01025 vl::Log::error( Say("GL_TEXTURE_BINDING_2D_MULTISAMPLE != 0 on texture unit #%n!\n") << coord_count );
01026 VL_TRAP();
01027 ok = false;
01028 }
01029
01030 bound_tex = 0;
01031 glGetIntegerv(GL_TEXTURE_BINDING_2D_MULTISAMPLE_ARRAY, &bound_tex);
01032 if (bound_tex != 0)
01033 {
01034 if (verbose)
01035 vl::Log::error( Say("GL_TEXTURE_BINDING_2D_MULTISAMPLE_ARRAY != 0 on texture unit #%n!\n") << coord_count );
01036 VL_TRAP();
01037 ok = false;
01038 }
01039 }
01040
01041 if (Has_Texture_Buffer)
01042 {
01043 bound_tex = 0;
01044 glGetIntegerv(GL_TEXTURE_BINDING_BUFFER, &bound_tex);
01045 if (bound_tex != 0)
01046 {
01047 if (verbose)
01048 vl::Log::error( Say("GL_TEXTURE_BINDING_BUFFER != 0 on texture unit #%n!\n") << coord_count );
01049 VL_TRAP();
01050 ok = false;
01051 }
01052 }
01053
01054 if (Has_Fixed_Function_Pipeline)
01055 {
01056 #if defined(VL_OPENGL)
01057 if (glIsEnabled(GL_TEXTURE_GEN_S))
01058 {
01059 if (verbose)
01060 vl::Log::error( "GL_TEXTURE_GEN_S was enabled!\n" );
01061 VL_TRAP();
01062 ok = false;
01063 }
01064
01065 if (glIsEnabled(GL_TEXTURE_GEN_T))
01066 {
01067 if (verbose)
01068 vl::Log::error( "GL_TEXTURE_GEN_T was enabled!\n" );
01069 VL_TRAP();
01070 ok = false;
01071 }
01072
01073 if (glIsEnabled(GL_TEXTURE_GEN_R))
01074 {
01075 if (verbose)
01076 vl::Log::error( "GL_TEXTURE_GEN_R was enabled!\n" );
01077 VL_TRAP();
01078 ok = false;
01079 }
01080
01081 if (glIsEnabled(GL_TEXTURE_GEN_Q))
01082 {
01083 if (verbose)
01084 vl::Log::error( "GL_TEXTURE_GEN_Q was enabled!\n" );
01085 VL_TRAP();
01086 ok = false;
01087 }
01088 #elif defined(VL_OPENGL_ES1)
01089 if (Has_GL_OES_texture_cube_map && glIsEnabled(GL_TEXTURE_GEN_STR_OES))
01090 {
01091 if (verbose)
01092 vl::Log::error( "GL_TEXTURE_GEN_STR_OES was enabled!\n" );
01093 VL_TRAP();
01094 ok = false;
01095 }
01096 #endif
01097 }
01098 }
01099
01100 if (Has_GL_Version_1_1 && glIsEnabled(GL_COLOR_MATERIAL))
01101 {
01102 if (verbose)
01103 vl::Log::error( "GL_COLOR_MATERIAL was enabled!\n");
01104 VL_TRAP();
01105 ok = false;
01106 }
01107
01108 if (Has_GL_Version_1_4 || Has_GL_EXT_fog_coord)
01109 {
01110 if (glIsEnabled(GL_FOG_COORD_ARRAY))
01111 {
01112 if (verbose)
01113 vl::Log::error( "GL_FOG_COORD_ARRAY was enabled!\n");
01114 VL_TRAP();
01115 ok = false;
01116 }
01117 }
01118
01119 if (Has_GL_Version_1_4 || Has_GL_EXT_secondary_color)
01120 {
01121 if (glIsEnabled(GL_SECONDARY_COLOR_ARRAY))
01122 {
01123 if (verbose)
01124 vl::Log::error( "GL_SECONDARY_COLOR_ARRAY was enabled!\n");
01125 VL_TRAP();
01126 ok = false;
01127 }
01128 }
01129
01130 if (Has_Fixed_Function_Pipeline && glIsEnabled(GL_COLOR_ARRAY))
01131 {
01132 if (verbose)
01133 vl::Log::error( "GL_COLOR_ARRAY was enabled!\n");
01134 VL_TRAP();
01135 ok = false;
01136 }
01137
01138 if (Has_GL_Version_1_1 && glIsEnabled(GL_EDGE_FLAG_ARRAY))
01139 {
01140 if (verbose)
01141 vl::Log::error( "GL_EDGE_FLAG_ARRAY was enabled!\n");
01142 VL_TRAP();
01143 ok = false;
01144 }
01145
01146 if (Has_GL_Version_1_1 && glIsEnabled(GL_INDEX_ARRAY))
01147 {
01148 if (verbose)
01149 vl::Log::error( "GL_INDEX_ARRAY was enabled!\n");
01150 VL_TRAP();
01151 ok = false;
01152 }
01153
01154 if (Has_Fixed_Function_Pipeline && glIsEnabled(GL_NORMAL_ARRAY))
01155 {
01156 if (verbose)
01157 vl::Log::error( "GL_NORMAL_ARRAY was enabled!\n");
01158 VL_TRAP();
01159 ok = false;
01160 }
01161
01162 if (Has_Fixed_Function_Pipeline && glIsEnabled(GL_VERTEX_ARRAY))
01163 {
01164 if (verbose)
01165 vl::Log::error( "GL_VERTEX_ARRAY was enabled!\n");
01166 VL_TRAP();
01167 ok = false;
01168 }
01169
01170 if (glIsEnabled(GL_SCISSOR_TEST))
01171 {
01172 if (verbose)
01173 vl::Log::error( "GL_SCISSOR_TEST was enabled!\n");
01174 VL_TRAP();
01175 ok = false;
01176 }
01177
01178 GLint max_vert_attribs = 0;
01179 if (Has_GLSL)
01180 glGetIntegerv(GL_MAX_VERTEX_ATTRIBS, &max_vert_attribs);
01181 for(int i=0; i<max_vert_attribs; ++i)
01182 {
01183 GLint is_enabled = 0;
01184 glGetVertexAttribiv(i, GL_VERTEX_ATTRIB_ARRAY_ENABLED, &is_enabled);
01185 if (is_enabled)
01186 {
01187 vl::Log::error( Say("GL_VERTEX_ATTRIB_ARRAY #%n is enabled!\n") << i );
01188 ok = false;
01189 }
01190 }
01191
01192 if (Has_GL_ARB_imaging)
01193 {
01194 if (glIsEnabled(GL_HISTOGRAM))
01195 {
01196 if (verbose)
01197 vl::Log::error( "GL_HISTOGRAM was enabled!\n");
01198 VL_TRAP();
01199 ok = false;
01200 }
01201
01202 if (glIsEnabled(GL_MINMAX))
01203 {
01204 if (verbose)
01205 vl::Log::error( "GL_MINMAX was enabled!\n");
01206 VL_TRAP();
01207 ok = false;
01208 }
01209 }
01210
01211
01212 #if defined(VL_OPENGL_ES2)
01213 GLint blend_src = 0;
01214 GLint blend_dst = 0;
01215 glGetIntegerv( GL_BLEND_SRC_RGB, &blend_src ); VL_CHECK_OGL();
01216 glGetIntegerv( GL_BLEND_DST_RGB, &blend_dst ); VL_CHECK_OGL();
01217 if (blend_src != GL_SRC_ALPHA)
01218 {
01219 if (verbose)
01220 vl::Log::error( "GL_BLEND_SRC is not GL_SRC_ALPHA!\n");
01221 VL_TRAP();
01222 ok = false;
01223 }
01224 if (blend_dst != GL_ONE_MINUS_SRC_ALPHA)
01225 {
01226 if (verbose)
01227 vl::Log::error( "GL_BLEND_DST is not GL_ONE_MINUS_SRC_ALPHA!\n");
01228 VL_TRAP();
01229 ok = false;
01230 }
01231 #else
01232 GLint blend_src = 0;
01233 GLint blend_dst = 0;
01234 glGetIntegerv( GL_BLEND_SRC, &blend_src ); VL_CHECK_OGL();
01235 glGetIntegerv( GL_BLEND_DST, &blend_dst ); VL_CHECK_OGL();
01236 if (blend_src != GL_SRC_ALPHA)
01237 {
01238 if (verbose)
01239 vl::Log::error( "GL_BLEND_SRC is not GL_SRC_ALPHA!\n");
01240 VL_TRAP();
01241 ok = false;
01242 }
01243 if (blend_dst != GL_ONE_MINUS_SRC_ALPHA)
01244 {
01245 if (verbose)
01246 vl::Log::error( "GL_BLEND_DST is not GL_ONE_MINUS_SRC_ALPHA!\n");
01247 VL_TRAP();
01248 ok = false;
01249 }
01250 #endif
01251
01252
01253
01254 GLint buf_bind = 0;
01255 if (Has_BufferObject)
01256 {
01257 glGetIntegerv(GL_ARRAY_BUFFER_BINDING, &buf_bind); VL_CHECK_OGL();
01258 if (buf_bind != 0)
01259 {
01260 if (verbose)
01261 vl::Log::error( "GL_ARRAY_BUFFER_BINDING should be 0!\n");
01262 VL_TRAP();
01263 ok = false;
01264 }
01265 buf_bind = 0;
01266 glGetIntegerv(GL_ELEMENT_ARRAY_BUFFER_BINDING, &buf_bind); VL_CHECK_OGL();
01267 if (buf_bind != 0)
01268 {
01269 if (verbose)
01270 vl::Log::error( "GL_ELEMENT_ARRAY_BUFFER_BINDING should be 0!\n");
01271 VL_TRAP();
01272 ok = false;
01273 }
01274 }
01275 if (Has_GL_Version_2_1)
01276 {
01277 buf_bind = 0;
01278 glGetIntegerv(GL_PIXEL_PACK_BUFFER_BINDING, &buf_bind); VL_CHECK_OGL();
01279 if (buf_bind != 0)
01280 {
01281 if (verbose)
01282 vl::Log::error( "GL_PIXEL_PACK_BUFFER_BINDING should be 0!\n");
01283 VL_TRAP();
01284 ok = false;
01285 }
01286 buf_bind = 0;
01287 glGetIntegerv(GL_PIXEL_UNPACK_BUFFER_BINDING, &buf_bind); VL_CHECK_OGL();
01288 if (buf_bind != 0)
01289 {
01290 if (verbose)
01291 vl::Log::error( "GL_PIXEL_UNPACK_BUFFER_BINDING should be 0!\n");
01292 VL_TRAP();
01293 ok = false;
01294 }
01295 }
01296 if (Has_GL_ARB_uniform_buffer_object)
01297 {
01298 buf_bind = 0;
01299 glGetIntegerv(GL_UNIFORM_BUFFER_BINDING, &buf_bind); VL_CHECK_OGL();
01300 if (buf_bind != 0)
01301 {
01302 if (verbose)
01303 vl::Log::error( "GL_UNIFORM_BUFFER_BINDING should be 0!\n");
01304 VL_TRAP();
01305 ok = false;
01306 }
01307 }
01308 if(Has_Transform_Feedback)
01309 {
01310 buf_bind = 0;
01311 glGetIntegerv(GL_TRANSFORM_FEEDBACK_BUFFER_BINDING, &buf_bind); VL_CHECK_OGL();
01312 if (buf_bind != 0)
01313 {
01314 if (verbose)
01315 vl::Log::error( "GL_TRANSFORM_FEEDBACK_BUFFER_BINDING should be 0!\n");
01316 VL_TRAP();
01317 ok = false;
01318 }
01319 }
01320
01321 #if 0
01322
01323 GLint viewport[4] = {0,0,0,0};
01324 glGetIntegerv(GL_VIEWPORT, viewport);
01325 if (viewport[2] * viewport[3] == 1)
01326 {
01327 if (verbose)
01328 vl::Log::error( "Viewport dimension is 1 pixel!\n"
01329 "Did you forget to call camera()->viewport()->setWidth()/setHeight() upon window resize event?\n");
01330 VL_TRAP();
01331 ok = false;
01332 }
01333 #endif
01334
01335 GLboolean write_mask[4];
01336 glGetBooleanv(GL_COLOR_WRITEMASK, write_mask); VL_CHECK_OGL();
01337 if( !write_mask[0] || !write_mask[1] || !write_mask[2] || !write_mask[3] )
01338 {
01339 vl::Log::error( "Color write-mask should be glColorMask(GL_TRUE ,GL_TRUE, GL_TRUE, GL_TRUE)!\n" );
01340 ok = false;
01341 }
01342
01343 glGetBooleanv(GL_DEPTH_WRITEMASK, write_mask); VL_CHECK_OGL();
01344 if ( !write_mask[0] )
01345 {
01346 vl::Log::error( "Depth write-mask should be glDepthMask(GL_TRUE)!\n" );
01347 ok = false;
01348 }
01349
01350 #if defined(VL_OPENGL)
01351 GLint poly_mode[2];
01352 glGetIntegerv(GL_POLYGON_MODE, poly_mode); VL_CHECK_OGL();
01353 if ( poly_mode[0] != GL_FILL || poly_mode[1] != GL_FILL )
01354 {
01355 vl::Log::error( "Polygon mode should be glPolygonMode(GL_FRONT_AND_BACK, GL_FILL)!\n" );
01356 ok = false;
01357 }
01358 #endif
01359
01360 VL_CHECK_OGL();
01361 return ok;
01362 }
01363
01364 bool OpenGLContext::areUniformsColliding(const UniformSet* u1, const UniformSet* u2)
01365 {
01366 if (!u1 || !u2)
01367 return false;
01368
01369
01370 std::set<std::string> name_set;
01371 for( size_t i=0; i<u1->uniforms().size(); ++i )
01372 name_set.insert( u1->uniforms()[i]->name() );
01373
01374 bool ok = false;
01375
01376 for( size_t j=0; j<u2->uniforms().size(); ++j )
01377 if ( name_set.find( u2->uniforms()[j]->name() ) != name_set.end() )
01378 {
01379 vl::Log::error( Say("Uniform name collision detected: %s\n") << u2->uniforms()[j]->name() );
01380 ok = true;
01381 }
01382
01383 return ok;
01384 }
01385
01386 void OpenGLContext::resetContextStates(EResetContextStates start_or_finish)
01387 {
01388
01389
01390
01391 VL_CHECK_OGL();
01392
01393
01394 if (globalSettings()->checkOpenGLStates() && !isCleanState(true))
01395 {
01396 VL_TRAP();
01397 return;
01398 }
01399
01400 VL_glBindFramebuffer(GL_FRAMEBUFFER, 0); VL_CHECK_OGL();
01401
01402
01403 #if defined(VL_OPENGL)
01404 if ( hasDoubleBuffer() )
01405 {
01406 glDrawBuffer(GL_BACK); VL_CHECK_OGL();
01407 glReadBuffer(GL_BACK); VL_CHECK_OGL();
01408 }
01409 else
01410 {
01411 glDrawBuffer(GL_FRONT); VL_CHECK_OGL();
01412 glReadBuffer(GL_FRONT); VL_CHECK_OGL();
01413 }
01414 #endif
01415
01416
01417
01418 if (start_or_finish == RCS_RenderingStarted)
01419 {
01420
01421 resetEnables();
01422 resetRenderStates();
01423
01424
01425 bindVAS(NULL, false, true); VL_CHECK_OGL();
01426 }
01427 }
01428
01429 void OpenGLContext::bindVAS(const IVertexAttribSet* vas, bool use_bo, bool force)
01430 {
01431 VL_CHECK_OGL();
01432
01433
01434
01435 if (vas != mCurVAS || force)
01436 {
01437
01438 if (!vas || force)
01439 {
01440 mCurVAS = NULL;
01441
01442
01443
01444 for(int i=0; i<VL_MAX_GENERIC_VERTEX_ATTRIB; ++i)
01445 {
01446 mVertexAttrib[i].mEnabled = false;
01447 mVertexAttrib[i].mPtr = 0;
01448 mVertexAttrib[i].mBufferObject = 0;
01449 mVertexAttrib[i].mState = 0;
01450 }
01451
01452 for(int i=0; i<VL_MAX_TEXTURE_UNITS; ++i)
01453 {
01454 mTexCoordArray[i].mEnabled = false;
01455 mTexCoordArray[i].mPtr = 0;
01456 mTexCoordArray[i].mBufferObject = 0;
01457 mTexCoordArray[i].mState = 0;
01458 }
01459
01460 mVertexArray.mEnabled = false;
01461 mVertexArray.mPtr = 0;
01462 mVertexArray.mBufferObject = 0;
01463 mVertexArray.mState = 0;
01464
01465 mNormalArray.mEnabled = false;
01466 mNormalArray.mPtr = 0;
01467 mNormalArray.mBufferObject = 0;
01468 mNormalArray.mState = 0;
01469
01470 mColorArray.mEnabled = false;
01471 mColorArray.mPtr = 0;
01472 mColorArray.mBufferObject = 0;
01473 mColorArray.mState = 0;
01474
01475 mSecondaryColorArray.mEnabled = false;
01476 mSecondaryColorArray.mPtr = 0;
01477 mSecondaryColorArray.mBufferObject = 0;
01478 mSecondaryColorArray.mState = 0;
01479
01480 mFogArray.mEnabled = false;
01481 mFogArray.mPtr = 0;
01482 mFogArray.mBufferObject = 0;
01483 mFogArray.mState = 0;
01484
01485
01486
01487 for(int i=0; i<mMaxVertexAttrib; ++i)
01488 VL_glDisableVertexAttribArray(i); VL_CHECK_OGL();
01489
01490
01491 VL_glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0); VL_CHECK_OGL();
01492
01493 VL_glBindBuffer(GL_ARRAY_BUFFER, 0); VL_CHECK_OGL();
01494
01495 if(Has_Fixed_Function_Pipeline)
01496 {
01497
01498 for ( int i=mTextureSamplerCount; i--; )
01499 {
01500 VL_glClientActiveTexture(GL_TEXTURE0 + i); VL_CHECK_OGL();
01501 glDisableClientState(GL_TEXTURE_COORD_ARRAY); VL_CHECK_OGL();
01502 }
01503
01504 glDisableClientState(GL_VERTEX_ARRAY); VL_CHECK_OGL();
01505 glDisableClientState(GL_NORMAL_ARRAY); VL_CHECK_OGL();
01506 glDisableClientState(GL_COLOR_ARRAY); VL_CHECK_OGL();
01507
01508
01509 #if defined(VL_OPENGL)
01510 glDisableClientState(GL_SECONDARY_COLOR_ARRAY); VL_CHECK_OGL();
01511 glDisableClientState(GL_FOG_COORD_ARRAY); VL_CHECK_OGL();
01512 #endif
01513 }
01514 }
01515
01516 if (vas)
01517 {
01518 int buf_obj = 0;
01519 const unsigned char* ptr = 0;
01520 bool enabled = false;
01521
01522 if(Has_Fixed_Function_Pipeline)
01523 {
01524
01525
01526
01527 enabled = vas->vertexArray() != NULL;
01528 if ( mVertexArray.mEnabled || enabled )
01529 {
01530 if (enabled)
01531 {
01532 if ( use_bo && vas->vertexArray()->bufferObject()->handle() )
01533 {
01534 buf_obj = vas->vertexArray()->bufferObject()->handle();
01535 ptr = 0;
01536 }
01537 else
01538 {
01539 buf_obj = 0;
01540 ptr = vas->vertexArray()->bufferObject()->ptr();
01541 }
01542 if ( mVertexArray.mPtr != ptr || mVertexArray.mBufferObject != buf_obj )
01543 {
01544 if (!mVertexArray.mEnabled)
01545 {
01546 glEnableClientState(GL_VERTEX_ARRAY); VL_CHECK_OGL();
01547 }
01548
01549
01550
01551
01552 VL_glBindBuffer(GL_ARRAY_BUFFER, buf_obj); VL_CHECK_OGL();
01553 glVertexPointer((int)vas->vertexArray()->glSize(), vas->vertexArray()->glType(), 0, ptr); VL_CHECK_OGL();
01554 mVertexArray.mPtr = ptr;
01555 mVertexArray.mBufferObject = buf_obj;
01556 }
01557 }
01558 else
01559 {
01560 glDisableClientState(GL_VERTEX_ARRAY); VL_CHECK_OGL();
01561 mVertexArray.mPtr = 0;
01562 mVertexArray.mBufferObject = 0;
01563 }
01564 mVertexArray.mEnabled = enabled;
01565 }
01566
01567
01568
01569 enabled = vas->normalArray() != NULL;
01570 if ( mNormalArray.mEnabled || enabled )
01571 {
01572 if (enabled)
01573 {
01574 if ( use_bo && vas->normalArray()->bufferObject()->handle() )
01575 {
01576 buf_obj = vas->normalArray()->bufferObject()->handle();
01577 ptr = 0;
01578 }
01579 else
01580 {
01581 buf_obj = 0;
01582 ptr = vas->normalArray()->bufferObject()->ptr();
01583 }
01584 if ( mNormalArray.mPtr != ptr || mNormalArray.mBufferObject != buf_obj )
01585 {
01586 if (!mNormalArray.mEnabled)
01587 {
01588 glEnableClientState(GL_NORMAL_ARRAY); VL_CHECK_OGL();
01589 }
01590 VL_glBindBuffer(GL_ARRAY_BUFFER, buf_obj); VL_CHECK_OGL();
01591 glNormalPointer(vas->normalArray()->glType(), 0, ptr); VL_CHECK_OGL();
01592 mNormalArray.mPtr = ptr;
01593 mNormalArray.mBufferObject = buf_obj;
01594 }
01595 }
01596 else
01597 {
01598 glDisableClientState(GL_NORMAL_ARRAY); VL_CHECK_OGL();
01599
01600
01601 glNormal3f( mNormal.x(), mNormal.y(), mNormal.z() );
01602
01603 mNormalArray.mPtr = 0;
01604 mNormalArray.mBufferObject = 0;
01605 }
01606 mNormalArray.mEnabled = enabled;
01607 }
01608
01609
01610
01611 enabled = vas->colorArray() != NULL;
01612 if ( mColorArray.mEnabled || enabled )
01613 {
01614 if (enabled)
01615 {
01616 if ( use_bo && vas->colorArray()->bufferObject()->handle() )
01617 {
01618 buf_obj = vas->colorArray()->bufferObject()->handle();
01619 ptr = 0;
01620 }
01621 else
01622 {
01623 buf_obj = 0;
01624 ptr = vas->colorArray()->bufferObject()->ptr();
01625 }
01626 if ( mColorArray.mPtr != ptr || mColorArray.mBufferObject != buf_obj )
01627 {
01628 if (!mColorArray.mEnabled)
01629 {
01630 glEnableClientState(GL_COLOR_ARRAY); VL_CHECK_OGL();
01631 }
01632 VL_glBindBuffer(GL_ARRAY_BUFFER, buf_obj); VL_CHECK_OGL();
01633 glColorPointer((int)vas->colorArray()->glSize(), vas->colorArray()->glType(), 0, ptr); VL_CHECK_OGL();
01634 mColorArray.mPtr = ptr;
01635 mColorArray.mBufferObject = buf_obj;
01636 }
01637 }
01638 else
01639 {
01640 glDisableClientState(GL_COLOR_ARRAY); VL_CHECK_OGL();
01641
01642
01643 glColor4f( mColor.r(), mColor.g(), mColor.b(), mColor.a() );
01644
01645 mColorArray.mPtr = 0;
01646 mColorArray.mBufferObject = 0;
01647 }
01648 mColorArray.mEnabled = enabled;
01649 }
01650
01651
01652
01653 enabled = vas->secondaryColorArray() != NULL;
01654 if ( mSecondaryColorArray.mEnabled || enabled )
01655 {
01656 if (enabled)
01657 {
01658 if ( use_bo && vas->secondaryColorArray()->bufferObject()->handle() )
01659 {
01660 buf_obj = vas->secondaryColorArray()->bufferObject()->handle();
01661 ptr = 0;
01662 }
01663 else
01664 {
01665 buf_obj = 0;
01666 ptr = vas->secondaryColorArray()->bufferObject()->ptr();
01667 }
01668 if ( mSecondaryColorArray.mPtr != ptr || mSecondaryColorArray.mBufferObject != buf_obj )
01669 {
01670 if (!mSecondaryColorArray.mEnabled)
01671 {
01672 glEnableClientState(GL_SECONDARY_COLOR_ARRAY); VL_CHECK_OGL();
01673 }
01674 VL_glBindBuffer(GL_ARRAY_BUFFER, buf_obj); VL_CHECK_OGL();
01675 glSecondaryColorPointer((int)vas->secondaryColorArray()->glSize(), vas->secondaryColorArray()->glType(), 0, ptr); VL_CHECK_OGL();
01676 mSecondaryColorArray.mPtr = ptr;
01677 mSecondaryColorArray.mBufferObject = buf_obj;
01678 }
01679 }
01680 else
01681 {
01682 glDisableClientState(GL_SECONDARY_COLOR_ARRAY); VL_CHECK_OGL();
01683
01684
01685 VL_glSecondaryColor3f( mSecondaryColor.r(), mSecondaryColor.g(), mSecondaryColor.b() );
01686
01687 mSecondaryColorArray.mPtr = 0;
01688 mSecondaryColorArray.mBufferObject = 0;
01689 }
01690 mSecondaryColorArray.mEnabled = enabled;
01691 }
01692
01693
01694
01695 enabled = vas->fogCoordArray() != NULL;
01696 if ( mFogArray.mEnabled || enabled )
01697 {
01698 if (enabled)
01699 {
01700 if ( use_bo && vas->fogCoordArray()->bufferObject()->handle() )
01701 {
01702 buf_obj = vas->fogCoordArray()->bufferObject()->handle();
01703 ptr = 0;
01704 }
01705 else
01706 {
01707 buf_obj = 0;
01708 ptr = vas->fogCoordArray()->bufferObject()->ptr();
01709 }
01710 if ( mFogArray.mPtr != ptr || mFogArray.mBufferObject != buf_obj )
01711 {
01712 if (!mFogArray.mEnabled)
01713 {
01714 glEnableClientState(GL_FOG_COORD_ARRAY); VL_CHECK_OGL();
01715 }
01716 VL_glBindBuffer(GL_ARRAY_BUFFER, buf_obj); VL_CHECK_OGL();
01717 glFogCoordPointer(vas->fogCoordArray()->glType(), 0, ptr); VL_CHECK_OGL();
01718 mFogArray.mPtr = ptr;
01719 mFogArray.mBufferObject = buf_obj;
01720 }
01721 }
01722 else
01723 {
01724 glDisableClientState(GL_FOG_COORD_ARRAY); VL_CHECK_OGL();
01725 mFogArray.mPtr = 0;
01726 mFogArray.mBufferObject = 0;
01727 }
01728 mFogArray.mEnabled = enabled;
01729 }
01730
01731
01732
01733
01734 for(int i=0; i<vas->texCoordArrayCount(); ++i)
01735 {
01736
01737 const ArrayAbstract* texarr = NULL;
01738 int tex_unit = 0;
01739 vas->getTexCoordArrayAt(i, tex_unit, texarr);
01740 VL_CHECK(tex_unit<VL_MAX_TEXTURE_UNITS);
01741
01742 mTexCoordArray[tex_unit].mState += 1;
01743 VL_CHECK( mTexCoordArray[tex_unit].mState == 1 || mTexCoordArray[tex_unit].mState == 2 );
01744
01745 if ( use_bo && texarr->bufferObject()->handle() )
01746 {
01747 buf_obj = texarr->bufferObject()->handle();
01748 ptr = 0;
01749 }
01750 else
01751 {
01752 buf_obj = 0;
01753 ptr = texarr->bufferObject()->ptr();
01754 }
01755 if ( mTexCoordArray[tex_unit].mPtr != ptr || mTexCoordArray[tex_unit].mBufferObject != buf_obj )
01756 {
01757 mTexCoordArray[tex_unit].mPtr = ptr;
01758 mTexCoordArray[tex_unit].mBufferObject = buf_obj;
01759
01760 VL_glClientActiveTexture(GL_TEXTURE0 + tex_unit); VL_CHECK_OGL();
01761 VL_glBindBuffer(GL_ARRAY_BUFFER, buf_obj); VL_CHECK_OGL();
01762 #if !defined(NDEBUG)
01763 if ( Has_GLES_Version_1_1 && texarr->glSize() == 1)
01764 {
01765 Log::error("OpenGL ES does not allow 1D texture coordinates.\n"); VL_TRAP();
01766 }
01767 #endif
01768 glTexCoordPointer((int)texarr->glSize(), texarr->glType(), 0, ptr); VL_CHECK_OGL();
01769
01770
01771 if (mTexCoordArray[tex_unit].mState == 1)
01772 {
01773 glEnableClientState(GL_TEXTURE_COORD_ARRAY); VL_CHECK_OGL();
01774 }
01775 else
01776 {
01777 VL_CHECK(glIsEnabled(GL_TEXTURE_COORD_ARRAY));
01778 }
01779 }
01780 }
01781
01782
01783 if (mCurVAS)
01784 {
01785 for(int i=0; i<mCurVAS->texCoordArrayCount(); ++i)
01786 {
01787
01788 const ArrayAbstract* texarr = NULL;
01789 int tex_unit = 0;
01790 mCurVAS->getTexCoordArrayAt(i, tex_unit, texarr);
01791 VL_CHECK(tex_unit<VL_MAX_TEXTURE_UNITS);
01792
01793
01794 if ( mTexCoordArray[tex_unit].mState == 1 )
01795 {
01796 VL_glClientActiveTexture(GL_TEXTURE0 + tex_unit); VL_CHECK_OGL();
01797 glDisableClientState(GL_TEXTURE_COORD_ARRAY); VL_CHECK_OGL();
01798
01799 mTexCoordArray[tex_unit].mPtr = 0;
01800 mTexCoordArray[tex_unit].mBufferObject = 0;
01801 }
01802
01803 mTexCoordArray[tex_unit].mState >>= 1;
01804 }
01805 }
01806
01807 }
01808
01809
01810
01811
01812 for(int i=0; i<vas->vertexAttribArrays()->size(); ++i)
01813 {
01814 const VertexAttribInfo* info = vas->vertexAttribArrays()->at(i);
01815 int idx = info->attribLocation();
01816
01817 mVertexAttrib[idx].mState += 1;
01818 VL_CHECK( mVertexAttrib[idx].mState == 1 || mVertexAttrib[idx].mState == 2 );
01819
01820 if ( use_bo && info->data()->bufferObject()->handle() )
01821 {
01822 buf_obj = info->data()->bufferObject()->handle();
01823 ptr = 0;
01824 }
01825 else
01826 {
01827 buf_obj = 0;
01828 ptr = info->data()->bufferObject()->ptr();
01829 }
01830 if ( mVertexAttrib[idx].mPtr != ptr || mVertexAttrib[idx].mBufferObject != buf_obj )
01831 {
01832 mVertexAttrib[idx].mPtr = ptr;
01833 mVertexAttrib[idx].mBufferObject = buf_obj;
01834 VL_glBindBuffer(GL_ARRAY_BUFFER, buf_obj); VL_CHECK_OGL();
01835
01836 if ( info->interpretation() == VAI_NORMAL )
01837 {
01838 VL_glVertexAttribPointer( idx, (int)info->data()->glSize(), info->data()->glType(), info->normalize(), 0, ptr ); VL_CHECK_OGL();
01839 }
01840 else
01841 if ( info->interpretation() == VAI_INTEGER )
01842 {
01843 VL_glVertexAttribIPointer( idx, (int)info->data()->glSize(), info->data()->glType(), 0, ptr ); VL_CHECK_OGL();
01844 }
01845 else
01846 if ( info->interpretation() == VAI_DOUBLE )
01847 {
01848 VL_glVertexAttribLPointer( idx, (int)info->data()->glSize(), info->data()->glType(), 0, ptr ); VL_CHECK_OGL();
01849 }
01850
01851
01852 if (mVertexAttrib[idx].mState == 1)
01853 {
01854 VL_glEnableVertexAttribArray( idx ); VL_CHECK_OGL();
01855 }
01856 else
01857 {
01858
01859 #if !defined(NDEBUG)
01860 GLint enabled = 0;
01861 glGetVertexAttribiv( idx, GL_VERTEX_ATTRIB_ARRAY_ENABLED, &enabled); VL_CHECK(enabled);
01862 #endif
01863 }
01864 }
01865 }
01866
01867
01868 if (mCurVAS)
01869 {
01870 for(int i=0; i<mCurVAS->vertexAttribArrays()->size(); ++i)
01871 {
01872
01873 const VertexAttribInfo* info = mCurVAS->vertexAttribArrays()->at(i);
01874 VL_CHECK(info)
01875 int idx = info->attribLocation();
01876
01877 if ( mVertexAttrib[idx].mState == 1 )
01878 {
01879 VL_glDisableVertexAttribArray( idx ); VL_CHECK_OGL();
01880
01881
01882 glVertexAttrib4fv( idx, mVertexAttribValue[idx].ptr() ); VL_CHECK_OGL();
01883
01884 mVertexAttrib[idx].mPtr = 0;
01885 mVertexAttrib[idx].mBufferObject = 0;
01886 }
01887
01888 mVertexAttrib[idx].mState >>= 1;
01889 }
01890 }
01891
01892
01893
01894
01895
01896
01897 }
01898
01899 }
01900
01901 mCurVAS = vas;
01902
01903 VL_CHECK_OGL();
01904 }
01905