1 // Created on: 2011-07-13
2 // Created by: Sergey ZERCHANINOV
3 // Copyright (c) 2011-2013 OPEN CASCADE SAS
5 // This file is part of Open CASCADE Technology software library.
7 // This library is free software; you can redistribute it and/or modify it under
8 // the terms of the GNU Lesser General Public License version 2.1 as published
9 // by the Free Software Foundation, with special exception defined in the file
10 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
11 // distribution for complete text of the license and disclaimer of any warranty.
13 // Alternatively, this file may be used under the terms of Open CASCADE
14 // commercial license or contractual agreement.
16 #include <OpenGl_AspectText.hxx>
17 #include <OpenGl_GlCore11.hxx>
18 #include <OpenGl_GraphicDriver.hxx>
19 #include <OpenGl_ShaderManager.hxx>
20 #include <OpenGl_ShaderProgram.hxx>
21 #include <OpenGl_ShaderStates.hxx>
22 #include <OpenGl_Text.hxx>
23 #include <OpenGl_Utils.hxx>
24 #include <OpenGl_Workspace.hxx>
26 #include <Font_FontMgr.hxx>
27 #include <TCollection_HAsciiString.hxx>
35 static const GLdouble THE_IDENTITY_MATRIX[16] =
44 static char const* TheFamily[] = {"Helvetica", "Courier", "Times"};
45 static char const* TheItalic[] = {"Oblique", "Oblique", "Italic"};
46 static char const* TheBase[] = {"", "", "-Roman"};
48 //! Convert font name used for rendering to some "good" font names
49 //! that produce good vector text.
50 static void getGL2PSFontName (const char* theSrcFont,
53 if (strstr (theSrcFont, "Symbol"))
55 sprintf (thePsFont, "%s", "Symbol");
58 else if (strstr (theSrcFont, "ZapfDingbats"))
60 sprintf (thePsFont, "%s", "WingDings");
66 bool isItalic = false;
67 if (strstr (theSrcFont, "Courier"))
71 else if (strstr (theSrcFont, "Times"))
76 if (strstr (theSrcFont, "Bold"))
80 if (strstr (theSrcFont, "Italic")
81 || strstr (theSrcFont, "Oblique"))
90 sprintf (thePsFont, "%s-Bold%s", TheFamily[aFontId], TheItalic[aFontId]);
94 sprintf (thePsFont, "%s-Bold", TheFamily[aFontId]);
99 sprintf (thePsFont, "%s-%s", TheFamily[aFontId], TheItalic[aFontId]);
103 sprintf (thePsFont, "%s%s", TheFamily[aFontId], TheBase[aFontId]);
107 static void exportText (const NCollection_String& theText,
108 const Standard_Boolean theIs2d,
109 const OpenGl_AspectText& theAspect,
110 const Standard_Integer theHeight)
114 getGL2PSFontName (theAspect.FontName().ToCString(), aPsFont);
116 #if !defined(GL_ES_VERSION_2_0)
119 glRasterPos2f (0.0f, 0.0f);
123 glRasterPos3f (0.0f, 0.0f, 0.0f);
127 glBitmap (1, 1, 0, 0, 0, 0, &aZero);
130 // Standard GL2PS's alignment isn't used, because it doesn't work correctly
131 // for all formats, therefore alignment is calculated manually relative
132 // to the bottom-left corner, which corresponds to the GL2PS_TEXT_BL value
133 gl2psTextOpt (theText.ToCString(), aPsFont, (GLshort)theHeight, GL2PS_TEXT_BL, theAspect.Angle());
139 // =======================================================================
140 // function : OpenGl_Text
142 // =======================================================================
143 OpenGl_Text::OpenGl_Text()
147 myScaleHeight (1.0f),
148 myPoint (0.0f, 0.0f, 0.0f),
151 myParams.Height = 10;
152 myParams.HAlign = Graphic3d_HTA_LEFT;
153 myParams.VAlign = Graphic3d_VTA_BOTTOM;
156 // =======================================================================
157 // function : OpenGl_Text
159 // =======================================================================
160 OpenGl_Text::OpenGl_Text (const Standard_Utf8Char* theText,
161 const OpenGl_Vec3& thePoint,
162 const OpenGl_TextParam& theParams)
166 myScaleHeight (1.0f),
167 myExportHeight (1.0f),
168 myParams (theParams),
176 // =======================================================================
177 // function : SetPosition
179 // =======================================================================
180 void OpenGl_Text::SetPosition (const OpenGl_Vec3& thePoint)
185 // =======================================================================
186 // function : SetFontSize
188 // =======================================================================
189 void OpenGl_Text::SetFontSize (const Handle(OpenGl_Context)& theCtx,
190 const Standard_Integer theFontSize)
192 if (myParams.Height != theFontSize)
194 Release (theCtx.operator->());
196 myParams.Height = theFontSize;
199 // =======================================================================
202 // =======================================================================
203 void OpenGl_Text::Init (const Handle(OpenGl_Context)& theCtx,
204 const Standard_Utf8Char* theText,
205 const OpenGl_Vec3& thePoint)
207 releaseVbos (theCtx.operator->());
210 myString.FromUnicode (theText);
213 // =======================================================================
216 // =======================================================================
217 void OpenGl_Text::Init (const Handle(OpenGl_Context)& theCtx,
218 const Standard_Utf8Char* theText,
219 const OpenGl_Vec3& thePoint,
220 const OpenGl_TextParam& theParams)
222 if (myParams.Height != theParams.Height)
224 Release (theCtx.operator->());
228 releaseVbos (theCtx.operator->());
231 myParams = theParams;
233 myString.FromUnicode (theText);
236 // =======================================================================
239 // =======================================================================
240 void OpenGl_Text::Init (const Handle(OpenGl_Context)& theCtx,
241 const TCollection_ExtendedString& theText,
242 const OpenGl_Vec2& thePoint,
243 const OpenGl_TextParam& theParams)
245 if (myParams.Height != theParams.Height)
247 Release (theCtx.operator->());
251 releaseVbos (theCtx.operator->());
254 myParams = theParams;
255 myPoint.xy() = thePoint;
257 myString.FromUnicode ((Standard_Utf16Char* )theText.ToExtString());
260 // =======================================================================
261 // function : ~OpenGl_Text
263 // =======================================================================
264 OpenGl_Text::~OpenGl_Text()
269 // =======================================================================
270 // function : releaseVbos
272 // =======================================================================
273 void OpenGl_Text::releaseVbos (OpenGl_Context* theCtx)
275 for (Standard_Integer anIter = 0; anIter < myVertsVbo.Length(); ++anIter)
277 Handle(OpenGl_VertexBuffer)& aVerts = myVertsVbo.ChangeValue (anIter);
278 Handle(OpenGl_VertexBuffer)& aTCrds = myTCrdsVbo.ChangeValue (anIter);
282 theCtx->DelayedRelease (aVerts);
283 theCtx->DelayedRelease (aTCrds);
293 // =======================================================================
294 // function : Release
296 // =======================================================================
297 void OpenGl_Text::Release (OpenGl_Context* theCtx)
299 releaseVbos (theCtx);
300 if (!myFont.IsNull())
302 Handle(OpenGl_Context) aCtx = theCtx;
303 const TCollection_AsciiString aKey = myFont->ResourceKey();
306 aCtx->ReleaseResource (aKey, Standard_True);
310 // =======================================================================
311 // function : StringSize
313 // =======================================================================
314 void OpenGl_Text::StringSize (const Handle(OpenGl_Context)& theCtx,
315 const NCollection_String& theText,
316 const OpenGl_AspectText& theTextAspect,
317 const OpenGl_TextParam& theParams,
318 Standard_ShortReal& theWidth,
319 Standard_ShortReal& theAscent,
320 Standard_ShortReal& theDescent)
325 const TCollection_AsciiString aFontKey = FontKey (theTextAspect, theParams.Height);
326 Handle(OpenGl_Font) aFont = FindFont (theCtx, theTextAspect, theParams.Height, aFontKey);
327 if (aFont.IsNull() || !aFont->IsValid())
332 theAscent = aFont->Ascender();
333 theDescent = aFont->Descender();
335 GLfloat aWidth = 0.0f;
336 for (NCollection_Utf8Iter anIter = theText.Iterator(); *anIter != 0;)
338 const Standard_Utf32Char aCharThis = *anIter;
339 const Standard_Utf32Char aCharNext = *++anIter;
341 if (aCharThis == '\x0D' // CR (carriage return)
342 || aCharThis == '\a' // BEL (alarm)
343 || aCharThis == '\f' // FF (form feed) NP (new page)
344 || aCharThis == '\b' // BS (backspace)
345 || aCharThis == '\v') // VT (vertical tab)
347 continue; // skip unsupported carriage control codes
349 else if (aCharThis == '\x0A') // LF (line feed, new line)
351 theWidth = Max (theWidth, aWidth);
355 else if (aCharThis == ' ')
357 aWidth += aFont->AdvanceX (aCharThis, aCharNext);
360 else if (aCharThis == '\t')
362 aWidth += aFont->AdvanceX (' ', aCharNext) * 8.0f;
366 aWidth += aFont->AdvanceX (aCharThis, aCharNext);
368 theWidth = Max (theWidth, aWidth);
370 Handle(OpenGl_Context) aCtx = theCtx;
372 aCtx->ReleaseResource (aFontKey, Standard_True);
375 // =======================================================================
378 // =======================================================================
379 void OpenGl_Text::Render (const Handle(OpenGl_Workspace)& theWorkspace) const
381 const OpenGl_AspectText* aTextAspect = theWorkspace->AspectText (Standard_True);
382 const Handle(OpenGl_Texture) aPrevTexture = theWorkspace->DisableTexture();
383 const Handle(OpenGl_Context)& aCtx = theWorkspace->GetGlContext();
385 // Bind custom shader program or generate default version
386 if (aCtx->core20fwd != NULL)
388 aCtx->ShaderManager()->BindProgram (
389 aTextAspect, aTextAspect->ShaderProgramRes (aCtx));
392 // use highlight color or colors from aspect
393 if (theWorkspace->NamedStatus & OPENGL_NS_HIGHLIGHT)
395 render (theWorkspace->PrinterContext(),
398 *theWorkspace->HighlightColor,
399 *theWorkspace->HighlightColor);
403 render (theWorkspace->PrinterContext(),
406 aTextAspect->Color(),
407 aTextAspect->SubtitleColor());
410 aCtx->BindProgram (NULL);
413 if (!aPrevTexture.IsNull())
415 theWorkspace->EnableTexture (aPrevTexture);
418 // restore Z buffer settings
419 if (theWorkspace->UseZBuffer())
421 glEnable (GL_DEPTH_TEST);
425 // =======================================================================
428 // =======================================================================
429 void OpenGl_Text::Render (const Handle(OpenGl_PrinterContext)& thePrintCtx,
430 const Handle(OpenGl_Context)& theCtx,
431 const OpenGl_AspectText& theTextAspect) const
433 render (thePrintCtx, theCtx, theTextAspect, theTextAspect.Color(), theTextAspect.SubtitleColor());
436 // =======================================================================
437 // function : setupMatrix
439 // =======================================================================
440 void OpenGl_Text::setupMatrix (const Handle(OpenGl_PrinterContext)& thePrintCtx,
441 const Handle(OpenGl_Context)& theCtx,
442 const OpenGl_AspectText& theTextAspect,
443 const OpenGl_Vec3 theDVec) const
445 OpenGl_Mat4d aModViewMat;
449 OpenGl_Utils::Translate<GLdouble> (aModViewMat, myPoint.x() + theDVec.x(), myPoint.y() + theDVec.y(), 0.f);
450 OpenGl_Utils::Scale<GLdouble> (aModViewMat, 1.f, -1.f, 1.f);
451 OpenGl_Utils::Rotate<GLdouble> (aModViewMat, theTextAspect.Angle(), 0.f, 0.f, 1.f);
455 // align coordinates to the nearest integer
456 // to avoid extra interpolation issues
457 GLdouble anObjX, anObjY, anObjZ;
458 OpenGl_Utils::UnProject<Standard_Real> (std::floor (myWinX + theDVec.x()),
459 std::floor (myWinY + theDVec.y()),
460 myWinZ + theDVec.z(),
461 OpenGl_Mat4d::Map (THE_IDENTITY_MATRIX),
462 OpenGl_Mat4d::Map (myProjMatrix),
468 OpenGl_Utils::Translate<GLdouble> (aModViewMat, anObjX, anObjY, anObjZ);
469 OpenGl_Utils::Rotate<GLdouble> (aModViewMat, theTextAspect.Angle(), 0.0, 0.0, 1.0);
471 if (!theTextAspect.IsZoomable())
474 // if the context has assigned printer context, use it's parameters
475 if (!thePrintCtx.IsNull())
477 // get printing scaling in x and y dimensions
478 GLfloat aTextScalex = 1.0f, aTextScaley = 1.0f;
479 thePrintCtx->GetScale (aTextScalex, aTextScaley);
481 // text should be scaled in all directions with same
482 // factor to save its proportions, so use height (y) scaling
483 // as it is better for keeping text/3d graphics proportions
484 OpenGl_Utils::Scale<GLdouble> (aModViewMat, aTextScaley, aTextScaley, aTextScaley);
487 OpenGl_Utils::Scale<GLdouble> (aModViewMat, myScaleHeight, myScaleHeight, myScaleHeight);
491 theCtx->WorldViewState.SetCurrent<Standard_Real> (aModViewMat);
492 theCtx->ApplyWorldViewMatrix();
494 if (!theCtx->ActiveProgram().IsNull())
496 // Upload updated state to shader program
497 theCtx->ShaderManager()->PushState (theCtx->ActiveProgram());
501 // =======================================================================
502 // function : drawText
504 // =======================================================================
506 void OpenGl_Text::drawText (const Handle(OpenGl_PrinterContext)& ,
507 const Handle(OpenGl_Context)& theCtx,
509 const OpenGl_AspectText& theTextAspect) const
511 const OpenGl_AspectText& ) const
515 if (theCtx->IsFeedback())
517 // position of the text and alignment is calculated by transformation matrix
518 exportText (myString, myIs2d, theTextAspect, (Standard_Integer )myExportHeight);
523 if (myVertsVbo.Length() != myTextures.Length()
524 || myTextures.IsEmpty())
529 for (Standard_Integer anIter = 0; anIter < myTextures.Length(); ++anIter)
531 const GLuint aTexId = myTextures.Value (anIter);
532 glBindTexture (GL_TEXTURE_2D, aTexId);
534 const Handle(OpenGl_VertexBuffer)& aVerts = myVertsVbo.Value (anIter);
535 const Handle(OpenGl_VertexBuffer)& aTCrds = myTCrdsVbo.Value (anIter);
536 aVerts->BindAttribute (theCtx, Graphic3d_TOA_POS);
537 aTCrds->BindAttribute (theCtx, Graphic3d_TOA_UV);
539 glDrawArrays (GL_TRIANGLES, 0, GLsizei(aVerts->GetElemsNb()));
541 aTCrds->UnbindAttribute (theCtx, Graphic3d_TOA_UV);
542 aVerts->UnbindAttribute (theCtx, Graphic3d_TOA_POS);
544 glBindTexture (GL_TEXTURE_2D, 0);
547 // =======================================================================
548 // function : FontKey
550 // =======================================================================
551 TCollection_AsciiString OpenGl_Text::FontKey (const OpenGl_AspectText& theAspect,
552 const Standard_Integer theHeight)
554 const Font_FontAspect anAspect = (theAspect.FontAspect() != Font_FA_Undefined) ? theAspect.FontAspect() : Font_FA_Regular;
555 return theAspect.FontName()
556 + TCollection_AsciiString(":") + Standard_Integer(anAspect)
557 + TCollection_AsciiString(":") + theHeight;
560 // =======================================================================
561 // function : FindFont
563 // =======================================================================
564 Handle(OpenGl_Font) OpenGl_Text::FindFont (const Handle(OpenGl_Context)& theCtx,
565 const OpenGl_AspectText& theAspect,
566 const Standard_Integer theHeight,
567 const TCollection_AsciiString theKey)
569 Handle(OpenGl_Font) aFont;
572 return aFont; // invalid parameters
575 if (!theCtx->GetResource (theKey, aFont))
577 Handle(Font_FontMgr) aFontMgr = Font_FontMgr::GetInstance();
578 const Handle(TCollection_HAsciiString) aFontName = new TCollection_HAsciiString (theAspect.FontName());
579 const Font_FontAspect anAspect = (theAspect.FontAspect() != Font_FA_Undefined) ? theAspect.FontAspect() : Font_FA_Regular;
580 Handle(Font_SystemFont) aRequestedFont = aFontMgr->FindFont (aFontName, anAspect, theHeight);
581 Handle(Font_FTFont) aFontFt;
582 if (!aRequestedFont.IsNull())
584 aFontFt = new Font_FTFont (NULL);
585 if (aFontFt->Init (aRequestedFont->FontPath()->ToCString(), theHeight))
587 aFont = new OpenGl_Font (aFontFt, theKey);
588 if (!aFont->Init (theCtx))
590 TCollection_ExtendedString aMsg;
592 aMsg += theAspect.FontName();
593 aMsg += "' - initialization of GL resources has failed!";
594 theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMsg);
596 aFont->Release (theCtx.operator->());
597 aFont = new OpenGl_Font (aFontFt, theKey);
602 TCollection_ExtendedString aMsg;
604 aMsg += theAspect.FontName();
605 aMsg += "' is broken or has incompatible format! File path: ";
606 aMsg += aRequestedFont->FontPath()->ToCString();
607 theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMsg);
609 aFont = new OpenGl_Font (aFontFt, theKey);
614 TCollection_ExtendedString aMsg;
616 aMsg += theAspect.FontName();
617 aMsg += "' is not found in the system!";
618 theCtx->PushMessage (GL_DEBUG_SOURCE_APPLICATION_ARB, GL_DEBUG_TYPE_ERROR_ARB, 0, GL_DEBUG_SEVERITY_HIGH_ARB, aMsg);
619 aFont = new OpenGl_Font (aFontFt, theKey);
622 theCtx->ShareResource (theKey, aFont);
627 // =======================================================================
630 // =======================================================================
631 void OpenGl_Text::render (const Handle(OpenGl_PrinterContext)& thePrintCtx,
632 const Handle(OpenGl_Context)& theCtx,
633 const OpenGl_AspectText& theTextAspect,
634 const TEL_COLOUR& theColorText,
635 const TEL_COLOUR& theColorSubs) const
637 if (myString.IsEmpty())
642 const TCollection_AsciiString aFontKey = FontKey (theTextAspect, myParams.Height);
644 && !myFont->ResourceKey().IsEqual (aFontKey))
647 const_cast<OpenGl_Text* > (this)->Release (theCtx.operator->());
652 myFont = FindFont (theCtx, theTextAspect, myParams.Height, aFontKey);
654 if (!myFont->WasInitialized())
659 if (myTextures.IsEmpty())
661 OpenGl_TextFormatter aFormatter;
662 aFormatter.SetupAlignment (myParams.HAlign, myParams.VAlign);
664 aFormatter.Append (theCtx, myString, *myFont.operator->());
667 aFormatter.Result (theCtx, myTextures, myVertsVbo, myTCrdsVbo);
668 aFormatter.BndBox (myBndBox);
671 if (myTextures.IsEmpty())
676 myExportHeight = 1.0f;
677 myScaleHeight = 1.0f;
679 theCtx->WorldViewState.Push();
681 myModelMatrix.Convert (theCtx->WorldViewState.Current() * theCtx->ModelWorldState.Current());
685 glGetIntegerv (GL_VIEWPORT, myViewport);
686 myProjMatrix.Convert (theCtx->ProjectionState.Current());
688 OpenGl_Utils::Project<Standard_Real> (myPoint.x(),
698 // compute scale factor for constant text height
700 OpenGl_Utils::UnProject<Standard_Real> (myWinX,
703 OpenGl_Mat4d::Map (THE_IDENTITY_MATRIX),
711 const GLdouble h = (GLdouble )myFont->FTFont()->PointSize();
712 OpenGl_Utils::UnProject<Standard_Real> (myWinX,
715 OpenGl_Mat4d::Map (THE_IDENTITY_MATRIX),
722 myScaleHeight = (y2 - y1) / h;
723 if (theTextAspect.IsZoomable())
725 myExportHeight = (float )h;
728 myExportHeight = (float )myFont->FTFont()->PointSize() / myExportHeight;
730 #if !defined(GL_ES_VERSION_2_0)
731 if (theCtx->core11 != NULL)
733 glDisable (GL_LIGHTING);
739 || theTextAspect.StyleType() == Aspect_TOST_ANNOTATION)
741 glDisable (GL_DEPTH_TEST);
744 if (theCtx->core15fwd != NULL)
746 theCtx->core15fwd->glActiveTexture (GL_TEXTURE0);
748 #if !defined(GL_ES_VERSION_2_0)
749 // activate texture unit
750 GLint aTexEnvParam = GL_REPLACE;
751 if (theCtx->core11 != NULL)
754 glAlphaFunc (GL_GEQUAL, 0.285f);
755 glEnable (GL_ALPHA_TEST);
757 glDisable (GL_TEXTURE_1D);
758 glEnable (GL_TEXTURE_2D);
759 glGetTexEnviv (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, &aTexEnvParam);
760 if (aTexEnvParam != GL_REPLACE)
762 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
769 glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
772 switch (theTextAspect.DisplayType())
774 case Aspect_TODT_BLEND:
776 #if !defined(GL_ES_VERSION_2_0)
777 glEnable (GL_COLOR_LOGIC_OP);
782 case Aspect_TODT_SUBTITLE:
784 #if !defined(GL_ES_VERSION_2_0)
785 if (theCtx->core11 != NULL)
787 theCtx->core11->glColor3fv (theColorSubs.rgb);
788 setupMatrix (thePrintCtx, theCtx, theTextAspect, OpenGl_Vec3 (0.0f, 0.0f, 0.00001f));
790 glBindTexture (GL_TEXTURE_2D, 0);
792 glVertex2f (myBndBox.Left, myBndBox.Top);
793 glVertex2f (myBndBox.Right, myBndBox.Top);
794 glVertex2f (myBndBox.Right, myBndBox.Bottom);
795 glVertex2f (myBndBox.Left, myBndBox.Bottom);
801 case Aspect_TODT_DEKALE:
803 theCtx->SetColor4fv (*(const OpenGl_Vec4* )theColorSubs.rgb);
804 setupMatrix (thePrintCtx, theCtx, theTextAspect, OpenGl_Vec3 (+1.0f, +1.0f, 0.00001f));
805 drawText (thePrintCtx, theCtx, theTextAspect);
806 setupMatrix (thePrintCtx, theCtx, theTextAspect, OpenGl_Vec3 (-1.0f, -1.0f, 0.00001f));
807 drawText (thePrintCtx, theCtx, theTextAspect);
808 setupMatrix (thePrintCtx, theCtx, theTextAspect, OpenGl_Vec3 (-1.0f, +1.0f, 0.00001f));
809 drawText (thePrintCtx, theCtx, theTextAspect);
810 setupMatrix (thePrintCtx, theCtx, theTextAspect, OpenGl_Vec3 (+1.0f, -1.0f, 0.00001f));
811 drawText (thePrintCtx, theCtx, theTextAspect);
814 case Aspect_TODT_DIMENSION:
815 case Aspect_TODT_NORMAL:
822 theCtx->SetColor4fv (*(const OpenGl_Vec4* )theColorText.rgb);
823 setupMatrix (thePrintCtx, theCtx, theTextAspect, OpenGl_Vec3 (0.0f, 0.0f, 0.0f));
824 drawText (thePrintCtx, theCtx, theTextAspect);
826 #if !defined(GL_ES_VERSION_2_0)
827 if (theCtx->core11 != NULL)
829 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, aTexEnvParam);
833 if (theTextAspect.DisplayType() == Aspect_TODT_DIMENSION)
835 setupMatrix (thePrintCtx, theCtx, theTextAspect, OpenGl_Vec3 (0.0f, 0.0f, 0.00001f));
837 glDisable (GL_BLEND);
840 glDisable (GL_DEPTH_TEST);
842 #if !defined(GL_ES_VERSION_2_0)
843 if (theCtx->core11 != NULL)
845 glDisable (GL_TEXTURE_2D);
846 glDisable (GL_ALPHA_TEST);
849 glColorMask (GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE);
851 glClear (GL_STENCIL_BUFFER_BIT);
852 glEnable (GL_STENCIL_TEST);
853 glStencilFunc (GL_ALWAYS, 1, 0xFF);
854 glStencilOp (GL_KEEP, GL_KEEP, GL_REPLACE);
856 #if !defined(GL_ES_VERSION_2_0)
857 if (theCtx->core11 != NULL)
860 glVertex2f (myBndBox.Left, myBndBox.Top);
861 glVertex2f (myBndBox.Right, myBndBox.Top);
862 glVertex2f (myBndBox.Right, myBndBox.Bottom);
863 glVertex2f (myBndBox.Left, myBndBox.Bottom);
868 glStencilFunc (GL_ALWAYS, 0, 0xFF);
870 glColorMask (GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
873 // reset OpenGL state
874 glDisable (GL_BLEND);
875 glDisable (GL_STENCIL_TEST);
876 #if !defined(GL_ES_VERSION_2_0)
877 if (theCtx->core11 != NULL)
879 glDisable (GL_ALPHA_TEST);
881 glDisable (GL_COLOR_LOGIC_OP);
884 // model view matrix was modified
885 theCtx->WorldViewState.Pop();
886 theCtx->ApplyModelViewMatrix();