0025475: Visualization, TKOpenGl - draw background using primitive arrays
authoraba <aba@opencascade.com>
Thu, 5 Feb 2015 11:48:39 +0000 (14:48 +0300)
committerbugmaster <bugmaster@opencascade.com>
Thu, 5 Feb 2015 11:49:28 +0000 (14:49 +0300)
Move background arrays to separate class OpenGl_BackgroundArray
for texture and gradient arrays.

Eliminated warnings on Linux

src/Graphic3d/Graphic3d.cdl
src/OpenGl/FILES
src/OpenGl/OpenGl_BackgroundArray.cxx [new file with mode: 0644]
src/OpenGl/OpenGl_BackgroundArray.hxx [new file with mode: 0644]
src/OpenGl/OpenGl_PrimitiveArray.hxx
src/OpenGl/OpenGl_View.cxx
src/OpenGl/OpenGl_View.hxx
src/OpenGl/OpenGl_View_2.cxx
src/OpenGl/OpenGl_Workspace_Raytrace.cxx
tests/bugs/vis/bug25475 [new file with mode: 0644]

index 5acd620..63fe9aa 100644 (file)
@@ -344,6 +344,11 @@ is
     -- - RM_RASTERIZATION: enables OpenGL rasterization mode;
     -- - RM_RAYTRACING: enables GPU ray-tracing mode.
 
+    enumeration TypeOfBackground is
+      TOB_NONE, TOB_GRADIENT, TOB_TEXTURE
+    end TypeOfBackground;
+     ---Purpose: Describes type of view background.
+
     ---------------------------
     -- Category: Imported types
     ---------------------------
index be3e8c3..9e8664d 100755 (executable)
@@ -165,3 +165,5 @@ OpenGl_Disk.hxx
 OpenGl_Disk.cxx
 OpenGl_Sphere.hxx
 OpenGl_Sphere.cxx
+OpenGl_BackgroundArray.hxx
+OpenGl_BackgroundArray.cxx
diff --git a/src/OpenGl/OpenGl_BackgroundArray.cxx b/src/OpenGl/OpenGl_BackgroundArray.cxx
new file mode 100644 (file)
index 0000000..a8ef36a
--- /dev/null
@@ -0,0 +1,382 @@
+// Created on: 2015-01-16
+// Created by: Anastasia BORISOVA
+// Copyright (c) 2015 OPEN CASCADE SAS
+//
+// This file is part of Open CASCADE Technology software library.
+//
+// This library is free software; you can redistribute it and/or modify it under
+// the terms of the GNU Lesser General Public License version 2.1 as published
+// by the Free Software Foundation, with special exception defined in the file
+// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
+// distribution for complete text of the license and disclaimer of any warranty.
+//
+// Alternatively, this file may be used under the terms of Open CASCADE
+// commercial license or contractual agreement.
+
+#include <OpenGl_BackgroundArray.hxx>
+
+#include <Aspect_FillMethod.hxx>
+#include <NCollection_AlignedAllocator.hxx>
+#include <OpenGl_Texture.hxx>
+
+// =======================================================================
+// method  : Constructor
+// purpose :
+// =======================================================================
+OpenGl_BackgroundArray::OpenGl_BackgroundArray (const Graphic3d_TypeOfBackground theType)
+: OpenGl_PrimitiveArray (NULL, Graphic3d_TOPA_TRIANGLESTRIPS, NULL, NULL, NULL),
+  myToUpdate (Standard_False),
+  myType (theType),
+  myViewWidth (0),
+  myViewHeight (0),
+  myFillMethod (Aspect_FM_NONE)
+{
+  Handle(NCollection_AlignedAllocator) anAlloc = new NCollection_AlignedAllocator (16);
+  myAttribs = new Graphic3d_Buffer (anAlloc);
+
+  myDrawMode = Graphic3d_TOPA_TRIANGLESTRIPS;
+
+  myGradientParams.color1 = OpenGl_Vec4 (0.0f, 0.0f, 0.0f, 1.0f);
+  myGradientParams.color2 = OpenGl_Vec4 (0.0f, 0.0f, 0.0f, 1.0f);
+  myGradientParams.type   = Aspect_GFM_NONE;
+}
+
+// =======================================================================
+// method  : SetTextureParameters
+// purpose :
+// =======================================================================
+void OpenGl_BackgroundArray::SetTextureParameters (const Aspect_FillMethod theFillMethod)
+{
+  if (myType != Graphic3d_TOB_TEXTURE)
+  {
+    return;
+  }
+
+  myFillMethod = theFillMethod;
+  invalidateData();
+}
+
+// =======================================================================
+// method  : SetTextureFillMethod
+// purpose :
+// =======================================================================
+void OpenGl_BackgroundArray::SetTextureFillMethod (const Aspect_FillMethod theFillMethod)
+{
+  myFillMethod = theFillMethod;
+  invalidateData();
+}
+
+// =======================================================================
+// method  : SetGradientParameters
+// purpose :
+// =======================================================================
+void OpenGl_BackgroundArray::SetGradientParameters (const Quantity_Color&           theColor1,
+                                                    const Quantity_Color&           theColor2,
+                                                    const Aspect_GradientFillMethod theType)
+{
+  if (myType != Graphic3d_TOB_GRADIENT)
+  {
+    return;
+  }
+
+  Standard_Real anR, aG, aB;
+  theColor1.Values (anR, aG, aB, Quantity_TOC_RGB);
+  myGradientParams.color1 = OpenGl_Vec4 ((float)anR, (float)aG, (float)aB, 0.0f);
+
+  theColor2.Values (anR, aG, aB, Quantity_TOC_RGB);
+  myGradientParams.color2 = OpenGl_Vec4 ((float)anR, (float)aG, (float)aB, 0.0f);
+
+  myGradientParams.type = theType;
+  invalidateData();
+}
+
+// =======================================================================
+// method  : SetGradientFillMethod
+// purpose :
+// =======================================================================
+void OpenGl_BackgroundArray::SetGradientFillMethod (const Aspect_GradientFillMethod theType)
+{
+  if (myType != Graphic3d_TOB_GRADIENT)
+  {
+    return;
+  }
+
+  myGradientParams.type = theType;
+  invalidateData();
+}
+
+// =======================================================================
+// method  : IsDefined
+// purpose :
+// =======================================================================
+bool OpenGl_BackgroundArray::IsDefined() const
+{
+  switch (myType)
+  {
+    case Graphic3d_TOB_GRADIENT: return myGradientParams.type != Aspect_GFM_NONE;
+    case Graphic3d_TOB_TEXTURE:  return myFillMethod          != Aspect_FM_NONE;
+    case Graphic3d_TOB_NONE:     return Standard_False;
+  }
+  return Standard_False;
+}
+
+// =======================================================================
+// method  : invalidateData
+// purpose :
+// =======================================================================
+void OpenGl_BackgroundArray::invalidateData()
+{
+  myToUpdate = Standard_True;
+}
+
+// =======================================================================
+// method  : Init
+// purpose :
+// =======================================================================
+Standard_Boolean OpenGl_BackgroundArray::Init (const Handle(OpenGl_Workspace)& theWorkspace)
+{
+  switch (myType)
+  {
+    case Graphic3d_TOB_GRADIENT:
+    {
+      if (!createGradientArray())
+      {
+        return Standard_False;
+      }
+      break;
+    }
+    case Graphic3d_TOB_TEXTURE:
+    {
+      myViewWidth  = theWorkspace->Width();
+      myViewHeight = theWorkspace->Height();
+      if (!createTextureArray (theWorkspace))
+      {
+        return Standard_False;
+      }
+      break;
+    }
+    case Graphic3d_TOB_NONE:
+    default:
+    {
+      return Standard_False;
+    }
+  }
+
+  // Init VBO
+  const Handle(OpenGl_Context)& aCtx = theWorkspace->GetGlContext();
+  if (myIsVboInit)
+  {
+    clearMemoryGL (aCtx);
+  }
+  buildVBO (aCtx, Standard_True);
+  myIsVboInit = Standard_True;
+
+  // Data is up-to-date
+  myToUpdate = Standard_False;
+  return Standard_True;
+}
+
+// =======================================================================
+// method  : createGradientArray
+// purpose :
+// =======================================================================
+Standard_Boolean OpenGl_BackgroundArray::createGradientArray()
+{
+  // Initialize data for primitive array
+  Graphic3d_Attribute aGragientAttribInfo[] =
+  {
+    { Graphic3d_TOA_POS,   Graphic3d_TOD_VEC2 },
+    { Graphic3d_TOA_COLOR, Graphic3d_TOD_VEC3 }
+  };
+
+  if (!myAttribs->Init (4, aGragientAttribInfo, 2))
+  {
+    return Standard_False;
+  }
+
+  OpenGl_Vec2 aVertices[4] =
+  {
+    OpenGl_Vec2(-1.0f, -1.0f),
+    OpenGl_Vec2( 1.0f, -1.0f),
+    OpenGl_Vec2( 1.0f,  1.0f),
+    OpenGl_Vec2(-1.0f,  1.0f)
+  };
+
+  Tfloat* aCorners[4]     = {};
+  Tfloat  aDiagCorner1[3] = {};
+  Tfloat  aDiagCorner2[3] = {};
+
+  switch (myGradientParams.type)
+  {
+    case Aspect_GFM_HOR:
+    {
+      aCorners[0] = myGradientParams.color1.xyz().ChangeData();
+      aCorners[1] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[2] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[3] = myGradientParams.color1.xyz().ChangeData();
+      break;
+    }
+    case Aspect_GFM_VER:
+    {
+      aCorners[0] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[1] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[2] = myGradientParams.color1.xyz().ChangeData();
+      aCorners[3] = myGradientParams.color1.xyz().ChangeData();
+      break;
+    }
+    case Aspect_GFM_DIAG1:
+    {
+      aCorners[1] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[3] = myGradientParams.color1.xyz().ChangeData();
+      aDiagCorner1[0] = aDiagCorner2[0] = 0.5f * (aCorners[1][0] + aCorners[3][0]);
+      aDiagCorner1[1] = aDiagCorner2[1] = 0.5f * (aCorners[1][1] + aCorners[3][1]);
+      aDiagCorner1[2] = aDiagCorner2[2] = 0.5f * (aCorners[1][2] + aCorners[3][2]);
+      aCorners[0] = aDiagCorner1;
+      aCorners[2] = aDiagCorner2;
+      break;
+    }
+    case Aspect_GFM_DIAG2:
+    {
+      aCorners[0] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[2] = myGradientParams.color1.xyz().ChangeData();
+      aDiagCorner1[0] = aDiagCorner2[0] = 0.5f * (aCorners[0][0] + aCorners[2][0]);
+      aDiagCorner1[1] = aDiagCorner2[1] = 0.5f * (aCorners[0][1] + aCorners[2][1]);
+      aDiagCorner1[2] = aDiagCorner2[2] = 0.5f * (aCorners[0][2] + aCorners[2][2]);
+      aCorners[1] = aDiagCorner1;
+      aCorners[3] = aDiagCorner2;
+      break;
+    }
+    case Aspect_GFM_CORNER1:
+    {
+      aCorners[0] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[1] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[2] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[3] = myGradientParams.color1.xyz().ChangeData();
+      break;
+    }
+    case Aspect_GFM_CORNER2:
+    {
+      aCorners[0] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[1] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[2] = myGradientParams.color1.xyz().ChangeData();
+      aCorners[3] = myGradientParams.color2.xyz().ChangeData();
+      break;
+    }
+    case Aspect_GFM_CORNER3:
+    {
+      aCorners[0] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[1] = myGradientParams.color1.xyz().ChangeData();
+      aCorners[2] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[3] = myGradientParams.color2.xyz().ChangeData();
+      break;
+    }
+    case Aspect_GFM_CORNER4:
+    {
+      aCorners[0] = myGradientParams.color1.xyz().ChangeData();
+      aCorners[1] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[2] = myGradientParams.color2.xyz().ChangeData();
+      aCorners[3] = myGradientParams.color2.xyz().ChangeData();
+      break;
+    }
+    case Aspect_GFM_NONE:
+    {
+      break;
+    }
+  }
+
+  if (myGradientParams.type != Aspect_GFM_CORNER1
+   && myGradientParams.type != Aspect_GFM_CORNER3)
+  {
+    for (Standard_Integer anIt = 0; anIt < 4; ++anIt)
+    {
+      OpenGl_Vec2* aVertData  = reinterpret_cast<OpenGl_Vec2* >(myAttribs->changeValue (anIt));
+      *aVertData = aVertices[anIt];
+
+      OpenGl_Vec3* aColorData = reinterpret_cast<OpenGl_Vec3* >(myAttribs->changeValue (anIt) + myAttribs->AttributeOffset (1));
+      *aColorData = OpenGl_Vec3(aCorners[anIt][0], aCorners[anIt][1], aCorners[anIt][2]);
+    }
+  }
+  else //if (myGradientParams.type == Aspect_GFM_CORNER1 || myGradientParams.type == Aspect_GFM_CORNER3)
+  {
+    for (Standard_Integer anIt = 0; anIt < 4; ++anIt)
+    {
+      // Indices should be in sequence 1, 2, 3, 0
+      Standard_Integer anIndex = (anIt + 1) % 4;
+      OpenGl_Vec2* aVertData  = reinterpret_cast<OpenGl_Vec2* >(myAttribs->changeValue (anIt));
+      *aVertData = aVertices[anIndex];
+
+      OpenGl_Vec3* aColorData = reinterpret_cast<OpenGl_Vec3* >(myAttribs->changeValue (anIt) + myAttribs->AttributeOffset (1));
+      *aColorData = OpenGl_Vec3(aCorners[anIndex][0], aCorners[anIndex][1], aCorners[anIndex][2]);
+    }
+  }
+
+  return Standard_True;
+}
+
+// =======================================================================
+// method  : createTextureArray
+// purpose :
+// =======================================================================
+Standard_Boolean OpenGl_BackgroundArray::createTextureArray (const Handle(OpenGl_Workspace)& theWorkspace)
+{
+  Graphic3d_Attribute aTextureAttribInfo[] =
+  {
+    { Graphic3d_TOA_POS, Graphic3d_TOD_VEC2 },
+    { Graphic3d_TOA_UV,  Graphic3d_TOD_VEC2 }
+  };
+
+  if (!myAttribs->Init (4, aTextureAttribInfo, 2))
+  {
+    return Standard_False;
+  }
+
+  GLfloat aTexRangeX = 1.0f; // texture <s> coordinate
+  GLfloat aTexRangeY = 1.0f; // texture <t> coordinate
+
+  // Set up for stretching or tiling
+  GLfloat anOffsetX = 1.0f;
+  GLfloat anOffsetY = 1.0f;
+
+  // Setting this coefficient to -1.0f allows to tile textures relatively to the top-left corner of the view
+  // (value 1.0f corresponds to the initial behavior - tiling from the bottom-left corner)
+  GLfloat aCoef = -1.0f;
+
+  // Get texture parameters
+  const Handle(OpenGl_Context)& aCtx = theWorkspace->GetGlContext();
+  const OpenGl_AspectFace* anAspectFace = theWorkspace->AspectFace (Standard_False);
+  GLfloat aTextureWidth  = (GLfloat )anAspectFace->TextureRes (aCtx)->SizeX();
+  GLfloat aTextureHeight = (GLfloat )anAspectFace->TextureRes (aCtx)->SizeY();
+
+  if (myFillMethod == Aspect_FM_CENTERED)
+  {
+    anOffsetX = aTextureWidth  / (GLfloat )myViewWidth;
+    anOffsetY = aTextureHeight / (GLfloat )myViewHeight;
+  }
+  else if (myFillMethod == Aspect_FM_TILED)
+  {
+    aTexRangeX = (GLfloat )myViewWidth  / aTextureWidth;
+    aTexRangeY = (GLfloat )myViewHeight / aTextureHeight;
+  }
+
+  // NOTE: texture is mapped using GL_REPEAT wrapping mode so integer part
+  // is simply ignored, and negative multiplier is here for convenience only
+  // and does not result e.g. in texture mirroring
+
+  OpenGl_Vec2* aData = reinterpret_cast<OpenGl_Vec2* >(myAttribs->changeValue (0));
+  aData[0] = OpenGl_Vec2 (-anOffsetX, -aCoef * anOffsetY);
+  aData[1] = OpenGl_Vec2 (0.0f, 0.0f);
+
+  aData = reinterpret_cast<OpenGl_Vec2* >(myAttribs->changeValue (1));
+  aData[0] = OpenGl_Vec2 (anOffsetX, -aCoef * anOffsetY);
+  aData[1] = OpenGl_Vec2 (aTexRangeX, 0.0f);
+
+  aData = reinterpret_cast<OpenGl_Vec2* >(myAttribs->changeValue (2));
+  aData[0] = OpenGl_Vec2 (anOffsetX,  aCoef * anOffsetY);
+  aData[1] = OpenGl_Vec2 (aTexRangeX, aCoef * aTexRangeY);
+
+  aData = reinterpret_cast<OpenGl_Vec2* >(myAttribs->changeValue (3));
+  aData[0] = OpenGl_Vec2 (-anOffsetX, aCoef * anOffsetY);
+  aData[1] = OpenGl_Vec2 (0.0f, aCoef * aTexRangeY);
+
+  return Standard_True;
+}
diff --git a/src/OpenGl/OpenGl_BackgroundArray.hxx b/src/OpenGl/OpenGl_BackgroundArray.hxx
new file mode 100644 (file)
index 0000000..ab45828
--- /dev/null
@@ -0,0 +1,109 @@
+// Created on: 2015-01-16
+// Created by: Anastasia BORISOVA
+// Copyright (c) 2015 OPEN CASCADE SAS
+//
+// This file is part of Open CASCADE Technology software library.
+//
+// This library is free software; you can redistribute it and/or modify it under
+// the terms of the GNU Lesser General Public License version 2.1 as published
+// by the Free Software Foundation, with special exception defined in the file
+// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
+// distribution for complete text of the license and disclaimer of any warranty.
+//
+// Alternatively, this file may be used under the terms of Open CASCADE
+// commercial license or contractual agreement.
+
+#ifndef OpenGl_BackgroundArray_Header
+#define OpenGl_BackgroundArray_Header
+
+#include <Aspect_GradientFillMethod.hxx>
+#include <Aspect_FillMethod.hxx>
+#include <Graphic3d_TypeOfBackground.hxx>
+#include <OpenGl_AspectFace.hxx>
+#include <OpenGl_PrimitiveArray.hxx>
+#include <OpenGl_Vec.hxx>
+#include <OpenGl_Workspace.hxx>
+
+//! Tool class for generating reusable data for
+//! gradient or texture background rendering.
+class OpenGl_BackgroundArray : public OpenGl_PrimitiveArray
+{
+public:
+
+  //! Main constructor.
+  Standard_EXPORT OpenGl_BackgroundArray (const Graphic3d_TypeOfBackground theType);
+
+  //! Check if background parameters are set properly
+  Standard_EXPORT bool IsDefined() const;
+
+  //! Fill attributes arrays for background array according to its type:
+  //! - for gradient background its attributes consist of colors and gradient coordinates
+  //! - for texture one its attributes consist of position and texure coordinates.
+  Standard_EXPORT Standard_Boolean Init (const Handle(OpenGl_Workspace)& theWorkspace);
+
+  //! Sets background texture parameters
+  Standard_EXPORT void SetTextureParameters (const Aspect_FillMethod theFillMethod);
+
+  //! Sets texture fill method
+  Standard_EXPORT void SetTextureFillMethod (const Aspect_FillMethod theFillMethod);
+
+  //! Gets background texture fill method
+  Aspect_FillMethod TextureFillMethod() const { return myFillMethod; }
+
+  //! Gets background gradient fill method
+  Aspect_GradientFillMethod GradientFillMethod() const { return myGradientParams.type; }
+
+  //! Sets type of gradient fill method
+  Standard_EXPORT void SetGradientFillMethod (const Aspect_GradientFillMethod theType);
+
+  //! Sets background gradient parameters
+  Standard_EXPORT void SetGradientParameters (const Quantity_Color&           theColor1,
+                                              const Quantity_Color&           theColor2,
+                                              const Aspect_GradientFillMethod theType);
+
+  //! Shows if array parameters were changed
+  Standard_Boolean IsDataChanged() const { return myToUpdate; }
+
+  //! Shows if view sizes were changed
+  //! (texture coordinates is no be changed)
+  Standard_Boolean IsViewSizeChanged (const Handle(OpenGl_Workspace)& theWorkspace) const
+  {
+    return myType == Graphic3d_TOB_TEXTURE
+       && (myViewWidth  != theWorkspace->Width()
+        || myViewHeight != theWorkspace->Height());
+  }
+
+protected: //! @name Internal structure for storing gradient parameters
+
+  struct OpenGl_GradientParameters
+  {
+    OpenGl_Vec4 color1;
+    OpenGl_Vec4 color2;
+    Aspect_GradientFillMethod type;
+  };
+
+protected:
+
+  //! Initializes gradient arrays.
+  Standard_EXPORT Standard_Boolean createGradientArray();
+
+  //! Initializes texture arrays.
+  //! @param theWorkspace OpenGl workspace that stores texture in the current enabled face aspect.
+  Standard_EXPORT Standard_Boolean createTextureArray (const Handle(OpenGl_Workspace)& theWorkspace);
+
+  //! Marks array parameters as changed,
+  //! on next rendering stage array data is to be updated.
+  Standard_EXPORT void invalidateData();
+
+protected:
+
+  Standard_Boolean           myToUpdate;       //!< Shows if array parameters were changed and data (myAttribs storage) is to be updated
+  Graphic3d_TypeOfBackground myType;           //!< Type of background: texture or gradient.
+  Standard_Integer           myViewWidth;      //!< view width  used for array initialization
+  Standard_Integer           myViewHeight;     //!< view height used for array initialization
+  Aspect_FillMethod          myFillMethod;     //!< Texture parameters
+  OpenGl_GradientParameters  myGradientParams; //!< Gradient parameters
+
+};
+
+#endif // OpenGl_BackgroundArray_Header
index c086204..97956d0 100644 (file)
@@ -69,17 +69,20 @@ public:
   //! Returns unique ID of primitive array. 
   const Standard_Size GetUID() const { return myUID; }
 
-private:
-
-  //! Initialize normal (OpenGL-provided) VBO
-  Standard_Boolean initNormalVbo (const Handle(OpenGl_Context)& theCtx) const;
+protected:
 
   //! VBO initialization procedures
   //! @param theCtx        bound GL context
   //! @param theToKeepData when true, myAttribs will not be nullified after VBO creation
-  Standard_Boolean buildVBO (const Handle(OpenGl_Context)& theCtx,
-                             const Standard_Boolean        theToKeepData) const;
-  void clearMemoryGL (const Handle(OpenGl_Context)& theGlCtx) const;
+  Standard_EXPORT Standard_Boolean buildVBO (const Handle(OpenGl_Context)& theCtx,
+                                             const Standard_Boolean        theToKeepData) const;
+
+  Standard_EXPORT void clearMemoryGL (const Handle(OpenGl_Context)& theGlCtx) const;
+
+private:
+
+  //! Initialize normal (OpenGL-provided) VBO
+  Standard_Boolean initNormalVbo (const Handle(OpenGl_Context)& theCtx) const;
 
   //! Main procedure to draw array
   void drawArray (const Handle(OpenGl_Workspace)& theWorkspace,
index 4dce502..9803c07 100644 (file)
@@ -35,8 +35,6 @@ IMPLEMENT_STANDARD_RTTIEXT(OpenGl_View,MMgt_TShared)
 
 /*----------------------------------------------------------------------*/
 
-static const OPENGL_BG_TEXTURE myDefaultBgTexture = { 0, 0, 0, Aspect_FM_CENTERED };
-static const OPENGL_BG_GRADIENT myDefaultBgGradient = { {{ 0.F, 0.F, 0.F, 1.F }}, {{ 0.F, 0.F, 0.F, 1.F }}, Aspect_GFM_NONE };
 static const Tmatrix3 myDefaultMatrix = { { 1.F, 0.F, 0.F, 0.F }, { 0.F, 1.F, 0.F, 0.F }, { 0.F, 0.F, 1.F, 0.F }, { 0.F, 0.F, 0.F, 1.F } };
 static const OPENGL_ZCLIP myDefaultZClip = { { Standard_True, 0.F }, { Standard_True, 1.F } };
 
@@ -56,8 +54,6 @@ OpenGl_View::OpenGl_View (const CALL_DEF_VIEWCONTEXT &AContext,
                           OpenGl_StateCounter*       theCounter)
 : mySurfaceDetail(Visual3d_TOD_ALL),
   myBackfacing(0),
-  myBgTexture(myDefaultBgTexture),
-  myBgGradient(myDefaultBgGradient),
   //shield_indicator = TOn,
   //shield_colour = { { 0.F, 0.F, 0.F, 1.F } },
   //border_indicator = TOff,
@@ -76,19 +72,25 @@ OpenGl_View::OpenGl_View (const CALL_DEF_VIEWCONTEXT &AContext,
   myProjectionState (0),
   myModelViewState (0),
   myStateCounter (theCounter),
-  myLastLightSourceState (0, 0)
+  myLastLightSourceState (0, 0),
+  myModificationState (1), // initial state
+  myTextureParams   (new OpenGl_AspectFace()),
+  myBgGradientArray (new OpenGl_BackgroundArray (Graphic3d_TOB_GRADIENT)),
+  myBgTextureArray  (new OpenGl_BackgroundArray (Graphic3d_TOB_TEXTURE))
 {
   myCurrLightSourceState = myStateCounter->Increment();
-  myModificationState = 1; // initial state
 }
 
 /*----------------------------------------------------------------------*/
 
-OpenGl_View::~OpenGl_View ()
+OpenGl_View::~OpenGl_View()
 {
   ReleaseGlResources (NULL); // ensure ReleaseGlResources() was called within valid context
   OpenGl_Element::Destroy (NULL, myTrihedron);
   OpenGl_Element::Destroy (NULL, myGraduatedTrihedron);
+  OpenGl_Element::Destroy (NULL, myBgGradientArray);
+  OpenGl_Element::Destroy (NULL, myBgTextureArray);
+  OpenGl_Element::Destroy (NULL, myTextureParams);
 }
 
 void OpenGl_View::ReleaseGlResources (const Handle(OpenGl_Context)& theCtx)
@@ -107,10 +109,18 @@ void OpenGl_View::ReleaseGlResources (const Handle(OpenGl_Context)& theCtx)
     theCtx->DelayedRelease (myTextureEnv);
     myTextureEnv.Nullify();
   }
-  if (myBgTexture.TexId != 0)
+
+  if (myTextureParams != NULL)
+  {
+    myTextureParams->Release (theCtx.operator->());
+  }
+  if (myBgGradientArray != NULL)
+  {
+    myBgGradientArray->Release (theCtx.operator->());
+  }
+  if (myBgTextureArray != NULL)
   {
-    glDeleteTextures (1, (GLuint*)&(myBgTexture.TexId));
-    myBgTexture.TexId = 0;
+    myBgTextureArray->Release (theCtx.operator->());
   }
 }
 
index e1b1e86..8afca96 100644 (file)
@@ -38,6 +38,8 @@
 #include <Visual3d_TypeOfSurfaceDetail.hxx>
 #include <Visual3d_TypeOfModel.hxx>
 
+#include <OpenGl_AspectFace.hxx>
+#include <OpenGl_BackgroundArray.hxx>
 #include <OpenGl_BVHTreeSelector.hxx>
 #include <OpenGl_LayerList.hxx>
 #include <OpenGl_Light.hxx>
 #include <Handle_OpenGl_View.hxx>
 #include <Handle_OpenGl_Texture.hxx>
 
-struct OPENGL_BG_TEXTURE
-{
-  Tuint             TexId;
-  Tint              Width;
-  Tint              Height;
-  Aspect_FillMethod Style;
-};
-
-struct OPENGL_BG_GRADIENT
-{
-  TEL_COLOUR color1;
-  TEL_COLOUR color2;
-  Aspect_GradientFillMethod type;
-};
-
 struct OPENGL_ZCLIP
 {
   struct {
@@ -171,7 +158,9 @@ class OpenGl_View : public MMgt_TShared
   void ChangePriority (const OpenGl_Structure* theStructure,
                        const Standard_Integer  theNewPriority);
 
-  void CreateBackgroundTexture (const Standard_CString AFileName, const Aspect_FillMethod AFillStyle);
+  void CreateBackgroundTexture (const Standard_CString AFileName,
+                                const Aspect_FillMethod AFillStyle);
+
   void SetBackgroundTextureStyle (const Aspect_FillMethod FillStyle);
   void SetBackgroundGradient (const Quantity_Color& AColor1, const Quantity_Color& AColor2, const Aspect_GradientFillMethod AType);
   void SetBackgroundGradientType (const Aspect_GradientFillMethod AType);
@@ -184,7 +173,7 @@ class OpenGl_View : public MMgt_TShared
                const Standard_Boolean               theToDrawImmediate);
 
 
-  void DrawBackground (OpenGl_Workspace& theWorkspace);
+  void DrawBackground (const Handle(OpenGl_Workspace)& theWorkspace);
 
   //! Returns list of OpenGL Z-layers.
   const OpenGl_LayerList& LayerList() const { return myZLayers; }
@@ -249,9 +238,6 @@ protected:
   Visual3d_TypeOfSurfaceDetail  mySurfaceDetail;
   Standard_Integer              myBackfacing;
 
-  OPENGL_BG_TEXTURE  myBgTexture;
-  OPENGL_BG_GRADIENT myBgGradient;
-
   OPENGL_ZCLIP   myZClip;
 
   Graphic3d_SequenceOfHClipPlane myClipPlanes;
@@ -299,6 +285,12 @@ protected:
 
   Standard_Size myModificationState;
 
+protected: //! @name Background parameters
+
+  OpenGl_AspectFace*      myTextureParams;   //!< Stores texture and its parameters for textured background
+  OpenGl_BackgroundArray* myBgGradientArray; //!< Primitive array for gradient background
+  OpenGl_BackgroundArray* myBgTextureArray;  //!< Primitive array for texture  background
+
 public:
 
   DEFINE_STANDARD_ALLOC
index e088cda..e988c00 100644 (file)
@@ -19,6 +19,8 @@
 #include <OpenGl_GlCore11.hxx>
 #include <OpenGl_tgl_funcs.hxx>
 
+#include <Graphic3d_TextureParams.hxx>
+#include <Graphic3d_Texture2Dmanual.hxx>
 #include <Image_AlienPixMap.hxx>
 #include <Visual3d_Layer.hxx>
 
@@ -31,6 +33,7 @@
 #include <OpenGl_View.hxx>
 #include <OpenGl_Trihedron.hxx>
 #include <OpenGl_GraduatedTrihedron.hxx>
+#include <OpenGl_PrimitiveArray.hxx>
 #include <OpenGl_PrinterContext.hxx>
 #include <OpenGl_ShaderManager.hxx>
 #include <OpenGl_ShaderProgram.hxx>
@@ -160,200 +163,88 @@ static void bindLight (const OpenGl_Light&             theLight,
 
 /*----------------------------------------------------------------------*/
 
-void OpenGl_View::DrawBackground (OpenGl_Workspace& theWorkspace)
+void OpenGl_View::DrawBackground (const Handle(OpenGl_Workspace)& theWorkspace)
 {
-#if !defined(GL_ES_VERSION_2_0)
-  if ( (theWorkspace.NamedStatus & OPENGL_NS_WHITEBACK) == 0 &&
-       ( myBgTexture.TexId != 0 || myBgGradient.type != Aspect_GFM_NONE ) )
-  {
-    const Standard_Integer aViewWidth = theWorkspace.Width();
-    const Standard_Integer aViewHeight = theWorkspace.Height();
-
-    glPushAttrib( GL_ENABLE_BIT | GL_TEXTURE_BIT );
+  const Handle(OpenGl_Context)& aCtx = theWorkspace->GetGlContext();
 
-    const Handle(OpenGl_Context)& aContext = theWorkspace.GetGlContext();
-
-    aContext->WorldViewState.Push();
-    aContext->ProjectionState.Push();
+  if ((theWorkspace->NamedStatus & OPENGL_NS_WHITEBACK) != 0 // no background
+    || (!myBgTextureArray->IsDefined()                       // no texture
+     && !myBgGradientArray->IsDefined()))                    // no gradient
+  {
+    return;
+  }
 
-    aContext->WorldViewState.SetIdentity();
-    aContext->ProjectionState.SetIdentity();
+  aCtx->core11fwd->glDisable (GL_DEPTH_TEST);
+
+  aCtx->WorldViewState.Push();
+  aCtx->ProjectionState.Push();
+  aCtx->WorldViewState.SetIdentity();
+  aCtx->ProjectionState.SetIdentity();
+  aCtx->ApplyProjectionMatrix();
+  aCtx->ApplyWorldViewMatrix();
+
+  // Drawing background gradient if:
+  // - gradient fill type is not Aspect_GFM_NONE and
+  // - either background texture is no specified or it is drawn in Aspect_FM_CENTERED mode
+  if (myBgGradientArray->IsDefined()
+    && (!myBgTextureArray->IsDefined()
+      || myBgTextureArray->TextureFillMethod() == Aspect_FM_CENTERED
+      || myBgTextureArray->TextureFillMethod() == Aspect_FM_NONE))
+  {
+  #if !defined(GL_ES_VERSION_2_0)
+    GLint aShadingModelOld = GL_SMOOTH;
+    if (aCtx->core11 != NULL)
+    {
+      aCtx->core11fwd->glDisable (GL_LIGHTING);
+      aCtx->core11fwd->glGetIntegerv (GL_SHADE_MODEL, &aShadingModelOld);
+      aCtx->core11->glShadeModel (GL_SMOOTH);
+    }
+  #endif
 
-    aContext->ApplyProjectionMatrix();
-    aContext->ApplyWorldViewMatrix();
+    if (myBgGradientArray->IsDataChanged())
+    {
+      myBgGradientArray->Init (theWorkspace);
+    }
 
-    if ( glIsEnabled( GL_DEPTH_TEST ) )
-      glDisable( GL_DEPTH_TEST ); //push GL_ENABLE_BIT
+    myBgGradientArray->Render (theWorkspace);
 
-    // drawing bg gradient if:
-    // - gradient fill type is not Aspect_GFM_NONE and
-    // - either background texture is no specified or it is drawn in Aspect_FM_CENTERED mode
-    if ( ( myBgGradient.type != Aspect_GFM_NONE ) &&
-      ( myBgTexture.TexId == 0 || myBgTexture.Style == Aspect_FM_CENTERED ||
-      myBgTexture.Style == Aspect_FM_NONE ) )
+  #if !defined(GL_ES_VERSION_2_0)
+    if (aCtx->core11 != NULL)
     {
-      Tfloat* corner1 = 0;/* -1,-1*/
-      Tfloat* corner2 = 0;/*  1,-1*/
-      Tfloat* corner3 = 0;/*  1, 1*/
-      Tfloat* corner4 = 0;/* -1, 1*/
-      Tfloat dcorner1[3];
-      Tfloat dcorner2[3];
-
-      switch( myBgGradient.type )
-      {
-      case Aspect_GFM_HOR:
-        corner1 = myBgGradient.color1.rgb;
-        corner2 = myBgGradient.color2.rgb;
-        corner3 = myBgGradient.color2.rgb;
-        corner4 = myBgGradient.color1.rgb;
-        break;
-      case Aspect_GFM_VER:
-        corner1 = myBgGradient.color2.rgb;
-        corner2 = myBgGradient.color2.rgb;
-        corner3 = myBgGradient.color1.rgb;
-        corner4 = myBgGradient.color1.rgb;
-        break;
-      case Aspect_GFM_DIAG1:
-        corner2 = myBgGradient.color2.rgb;
-        corner4 = myBgGradient.color1.rgb;
-        dcorner1 [0] = dcorner2[0] = 0.5F * (corner2[0] + corner4[0]);
-        dcorner1 [1] = dcorner2[1] = 0.5F * (corner2[1] + corner4[1]);
-        dcorner1 [2] = dcorner2[2] = 0.5F * (corner2[2] + corner4[2]);
-        corner1 = dcorner1;
-        corner3 = dcorner2;
-        break;
-      case Aspect_GFM_DIAG2:
-        corner1 = myBgGradient.color2.rgb;
-        corner3 = myBgGradient.color1.rgb;
-        dcorner1 [0] = dcorner2[0] = 0.5F * (corner1[0] + corner3[0]);
-        dcorner1 [1] = dcorner2[1] = 0.5F * (corner1[1] + corner3[1]);
-        dcorner1 [2] = dcorner2[2] = 0.5F * (corner1[2] + corner3[2]);
-        corner2 = dcorner1;
-        corner4 = dcorner2;
-        break;
-      case Aspect_GFM_CORNER1:
-        corner1 = myBgGradient.color2.rgb;
-        corner2 = myBgGradient.color2.rgb;
-        corner3 = myBgGradient.color2.rgb;
-        corner4 = myBgGradient.color1.rgb;
-        break;
-      case Aspect_GFM_CORNER2:
-        corner1 = myBgGradient.color2.rgb;
-        corner2 = myBgGradient.color2.rgb;
-        corner3 = myBgGradient.color1.rgb;
-        corner4 = myBgGradient.color2.rgb;
-        break;
-      case Aspect_GFM_CORNER3:
-        corner1 = myBgGradient.color2.rgb;
-        corner2 = myBgGradient.color1.rgb;
-        corner3 = myBgGradient.color2.rgb;
-        corner4 = myBgGradient.color2.rgb;
-        break;
-      case Aspect_GFM_CORNER4:
-        corner1 = myBgGradient.color1.rgb;
-        corner2 = myBgGradient.color2.rgb;
-        corner3 = myBgGradient.color2.rgb;
-        corner4 = myBgGradient.color2.rgb;
-        break;
-      default:
-        //printf("gradient background type not right\n");
-        break;
-      }
+      aCtx->core11->glShadeModel (aShadingModelOld);
+    }
+  #endif
+  }
 
-      // Save GL parameters
-      glDisable( GL_LIGHTING ); //push GL_ENABLE_BIT
+  // Drawing background image if it is defined
+  // (texture is defined and fill type is not Aspect_FM_NONE)
+  if (myBgTextureArray->IsDefined()
+   && myTextureParams->DoTextureMap())
+  {
+    aCtx->core11fwd->glDisable (GL_BLEND);
 
-      GLint curSM;
-      glGetIntegerv( GL_SHADE_MODEL, &curSM );
-      if ( curSM != GL_SMOOTH )
-        glShadeModel( GL_SMOOTH ); //push GL_LIGHTING_BIT
+    const OpenGl_AspectFace* anOldAspectFace = theWorkspace->SetAspectFace (myTextureParams);
 
-      glBegin(GL_TRIANGLE_FAN);
-      if( myBgGradient.type != Aspect_GFM_CORNER1 && myBgGradient.type != Aspect_GFM_CORNER3 )
-      {
-        glColor3f(corner1[0],corner1[1],corner1[2]); glVertex2f(-1.,-1.);
-        glColor3f(corner2[0],corner2[1],corner2[2]); glVertex2f( 1.,-1.);
-        glColor3f(corner3[0],corner3[1],corner3[2]); glVertex2f( 1., 1.);
-        glColor3f(corner4[0],corner4[1],corner4[2]); glVertex2f(-1., 1.);
-      }
-      else //if ( myBgGradient.type == Aspect_GFM_CORNER1 || myBgGradient.type == Aspect_GFM_CORNER3 )
-      {
-        glColor3f(corner2[0],corner2[1],corner2[2]); glVertex2f( 1.,-1.);
-        glColor3f(corner3[0],corner3[1],corner3[2]); glVertex2f( 1., 1.);
-        glColor3f(corner4[0],corner4[1],corner4[2]); glVertex2f(-1., 1.);
-        glColor3f(corner1[0],corner1[1],corner1[2]); glVertex2f(-1.,-1.);
-      }
-      glEnd();
-
-      // Restore GL parameters
-      if ( curSM != GL_SMOOTH )
-        glShadeModel( curSM );
-    }
-    // drawing bg image if:
-    // - it is defined and
-    // - fill type is not Aspect_FM_NONE
-    if ( myBgTexture.TexId != 0 && myBgTexture.Style != Aspect_FM_NONE )
+    if (myBgTextureArray->IsDataChanged()
+     || myBgTextureArray->IsViewSizeChanged (theWorkspace))
     {
-      GLfloat texX_range = 1.F; // texture <s> coordinate
-      GLfloat texY_range = 1.F; // texture <t> coordinate
-
-      // Set up for stretching or tiling
-      GLfloat x_offset, y_offset;
-      if ( myBgTexture.Style == Aspect_FM_CENTERED )
-      {
-        x_offset = (GLfloat)myBgTexture.Width / (GLfloat)aViewWidth;
-        y_offset = (GLfloat)myBgTexture.Height / (GLfloat)aViewHeight;
-      }
-      else
-      {
-        x_offset = 1.F;
-        y_offset = 1.F;
-        if ( myBgTexture.Style == Aspect_FM_TILED )
-        {
-          texX_range = (GLfloat)aViewWidth / (GLfloat)myBgTexture.Width;
-          texY_range = (GLfloat)aViewHeight / (GLfloat)myBgTexture.Height;
-        }
-      }
-
-      // OCCT issue 0023000: Improve the way the gradient and textured
-      // background is managed in 3d viewer (note 0020339)
-      // 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;
-
-      glEnable( GL_TEXTURE_2D ); //push GL_ENABLE_BIT
-      glBindTexture( GL_TEXTURE_2D, myBgTexture.TexId ); //push GL_TEXTURE_BIT
-
-      glDisable( GL_BLEND ); //push GL_ENABLE_BIT
-
-      glColor3fv (theWorkspace.BackgroundColor().rgb);
-      glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL); //push GL_TEXTURE_BIT
-
-      // Note that texture is mapped using GL_REPEAT wrapping mode so integer part
-      // is simply ignored, and negative multiplier is here for convenience only
-      // and does not result e.g. in texture mirroring
-      glBegin( GL_QUADS );
-      glTexCoord2f(0.F, 0.F); glVertex2f( -x_offset, -aCoef * y_offset );
-      glTexCoord2f(texX_range, 0.F); glVertex2f( x_offset, -aCoef * y_offset );
-      glTexCoord2f(texX_range, aCoef * texY_range); glVertex2f( x_offset, aCoef * y_offset );
-      glTexCoord2f(0.F, aCoef * texY_range); glVertex2f( -x_offset, aCoef * y_offset );
-      glEnd();
+      myBgTextureArray->Init (theWorkspace);
     }
 
-    aContext->WorldViewState.Pop();
-    aContext->ProjectionState.Pop();
+    myBgTextureArray->Render (theWorkspace);
 
-    aContext->ApplyProjectionMatrix();
+    // restore aspects
+    theWorkspace->SetAspectFace (anOldAspectFace);
+  }
 
-    glPopAttrib(); //GL_ENABLE_BIT | GL_TEXTURE_BIT
+  aCtx->WorldViewState.Pop();
+  aCtx->ProjectionState.Pop();
+  aCtx->ApplyProjectionMatrix();
 
-    if (theWorkspace.UseZBuffer())
-    {
-      glEnable (GL_DEPTH_TEST);
-    }
+  if (theWorkspace->UseZBuffer())
+  {
+    aCtx->core11fwd->glEnable (GL_DEPTH_TEST);
   }
-#endif
 }
 
 /*----------------------------------------------------------------------*/
@@ -452,7 +343,7 @@ void OpenGl_View::Render (const Handle(OpenGl_PrinterContext)& thePrintContext,
   if (theWorkspace->ToRedrawGL()
   && !theToDrawImmediate)
   {
-    DrawBackground (*theWorkspace);
+    DrawBackground (theWorkspace);
   }
 
 #if !defined(GL_ES_VERSION_2_0)
@@ -895,116 +786,58 @@ void OpenGl_View::RedrawTrihedron (const Handle(OpenGl_Workspace) &theWorkspace)
 void OpenGl_View::CreateBackgroundTexture (const Standard_CString  theFilePath,
                                            const Aspect_FillMethod theFillStyle)
 {
-  if (myBgTexture.TexId != 0)
-  {
-    // delete existing texture
-    glDeleteTextures (1, (GLuint* )&(myBgTexture.TexId));
-    myBgTexture.TexId = 0;
-  }
-
-  // load image from file
-  Image_AlienPixMap anImageLoaded;
-  if (!anImageLoaded.Load (theFilePath))
-  {
-    return;
-  }
-
-  Image_PixMap anImage;
-  if (anImageLoaded.RowExtraBytes() == 0 &&
-      (anImageLoaded.Format() == Image_PixMap::ImgRGB
-    || anImageLoaded.Format() == Image_PixMap::ImgRGB32
-    || anImageLoaded.Format() == Image_PixMap::ImgRGBA))
+  // Prepare aspect for texture storage
+  Handle(Graphic3d_AspectFillArea3d) anAspect = new Graphic3d_AspectFillArea3d();
+  Handle(Graphic3d_Texture2Dmanual) aTextureMap = new Graphic3d_Texture2Dmanual (TCollection_AsciiString (theFilePath));
+  aTextureMap->EnableRepeat();
+  aTextureMap->DisableModulate();
+  aTextureMap->GetParams()->SetGenMode (Graphic3d_TOTM_MANUAL,
+                                        Graphic3d_Vec4 (0.0f, 0.0f, 0.0f, 0.0f),
+                                        Graphic3d_Vec4 (0.0f, 0.0f, 0.0f, 0.0f));
+  anAspect->SetTextureMap (aTextureMap);
+  anAspect->SetInteriorStyle (Aspect_IS_SOLID);
+  // Enable texture mapping
+  if (aTextureMap->IsDone())
   {
-    anImage.InitWrapper (anImageLoaded.Format(), anImageLoaded.ChangeData(),
-                         anImageLoaded.SizeX(), anImageLoaded.SizeY(), anImageLoaded.SizeRowBytes());
+    anAspect->SetTextureMapOn();
   }
   else
   {
-    // convert image to RGB format
-    if (!anImage.InitTrash (Image_PixMap::ImgRGB, anImageLoaded.SizeX(), anImageLoaded.SizeY()))
-    {
-      return;
-    }
+    anAspect->SetTextureMapOff();
+    return;
 
-    anImage.SetTopDown (false);
-    Quantity_Color aSrcColor;
-    for (Standard_Size aRow = 0; aRow < anImage.SizeY(); ++aRow)
-    {
-      for (Standard_Size aCol = 0; aCol < anImage.SizeX(); ++aCol)
-      {
-        aSrcColor = anImageLoaded.PixelColor ((Standard_Integer )aCol, (Standard_Integer )aRow);
-        Image_ColorRGB& aColor = anImage.ChangeValue<Image_ColorRGB> (aRow, aCol);
-        aColor.r() = Standard_Byte(255.0 * aSrcColor.Red());
-        aColor.g() = Standard_Byte(255.0 * aSrcColor.Green());
-        aColor.b() = Standard_Byte(255.0 * aSrcColor.Blue());
-      }
-    }
-    anImageLoaded.Clear();
   }
 
-  // create MipMapped texture
-  glPixelStorei (GL_UNPACK_ALIGNMENT, 1);
-
-  GLuint aTextureId = 0;
-  glGenTextures (1, &aTextureId);
-  glBindTexture (GL_TEXTURE_2D, aTextureId);
-
-  glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_WRAP_S,     GL_REPEAT);
-  glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_WRAP_T,     GL_REPEAT);
-  glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
-  glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_NEAREST);
-
-  const GLenum aDataFormat = (anImage.Format() == Image_PixMap::ImgRGB) ? GL_RGB : GL_RGBA;
-
-#if !defined(GL_ES_VERSION_2_0)
-  gluBuild2DMipmaps (GL_TEXTURE_2D, 3/*4*/,
-                     GLint(anImage.SizeX()), GLint(anImage.SizeY()),
-                     aDataFormat, GL_UNSIGNED_BYTE, anImage.Data());
-#endif
+  // Set texture parameters
+  myTextureParams->SetAspect (anAspect);
 
-  myBgTexture.TexId  = aTextureId;
-  myBgTexture.Width  = (Standard_Integer )anImage.SizeX();
-  myBgTexture.Height = (Standard_Integer )anImage.SizeY();
-  myBgTexture.Style  = theFillStyle;
+  myBgTextureArray->SetTextureParameters (theFillStyle);
 }
 
 /*----------------------------------------------------------------------*/
 
 //call_togl_set_bg_texture_style
-void OpenGl_View::SetBackgroundTextureStyle (const Aspect_FillMethod AFillStyle)
+void OpenGl_View::SetBackgroundTextureStyle (const Aspect_FillMethod theFillStyle)
 {
-  myBgTexture.Style = AFillStyle;
+  myBgTextureArray->SetTextureFillMethod (theFillStyle);
 }
 
 /*----------------------------------------------------------------------*/
 
 //call_togl_gradient_background
-void OpenGl_View::SetBackgroundGradient (const Quantity_Color& AColor1,
-                                        const Quantity_Color& AColor2,
-                                        const Aspect_GradientFillMethod AType)
+void OpenGl_View::SetBackgroundGradient (const Quantity_Color& theColor1,
+                                        const Quantity_Color& theColor2,
+                                        const Aspect_GradientFillMethod theType)
 {
-  Standard_Real R,G,B;
-  AColor1.Values( R, G, B, Quantity_TOC_RGB );
-  myBgGradient.color1.rgb[0] = ( Tfloat )R;
-  myBgGradient.color1.rgb[1] = ( Tfloat )G;
-  myBgGradient.color1.rgb[2] = ( Tfloat )B;
-  myBgGradient.color1.rgb[3] = 0.F;
-
-  AColor2.Values( R, G, B, Quantity_TOC_RGB );
-  myBgGradient.color2.rgb[0] = ( Tfloat )R;
-  myBgGradient.color2.rgb[1] = ( Tfloat )G;
-  myBgGradient.color2.rgb[2] = ( Tfloat )B;
-  myBgGradient.color2.rgb[3] = 0.F;
-
-  myBgGradient.type = AType;
+  myBgGradientArray->SetGradientParameters (theColor1, theColor2, theType);
 }
 
 /*----------------------------------------------------------------------*/
 
 //call_togl_set_gradient_type
-void OpenGl_View::SetBackgroundGradientType (const Aspect_GradientFillMethod AType)
+void OpenGl_View::SetBackgroundGradientType (const Aspect_GradientFillMethod theType)
 {
-  myBgGradient.type = AType;
+  myBgGradientArray->SetGradientFillMethod (theType);
 }
 
 //=======================================================================
index acf15d1..2f1118f 100644 (file)
@@ -2363,7 +2363,7 @@ Standard_Boolean OpenGl_Workspace::Raytrace (const Graphic3d_CView& theCView,
 
   glClear (GL_COLOR_BUFFER_BIT);
 
-  myView->DrawBackground (*this);
+  myView->DrawBackground (this);
 
   myView->RedrawLayer2d (myPrintContext, this, theCView, theCUnderLayer);
 
diff --git a/tests/bugs/vis/bug25475 b/tests/bugs/vis/bug25475
new file mode 100644 (file)
index 0000000..2169acd
--- /dev/null
@@ -0,0 +1,30 @@
+puts "============"
+puts "OCC25475"
+puts "============"
+puts ""
+#######################################################################
+puts "Tests textured background"
+#######################################################################
+
+set aTextureFile [locate_data_file hatch_1.png]
+set anImage1 $imagedir/${casename}_1.png
+set anImage2 $imagedir/${casename}_2.png
+set anImage3 $imagedir/${casename}_3.png
+set anImage4 $imagedir/${casename}_4.png
+
+pload VISUALIZATION
+vinit
+
+vsetbg $aTextureFile STRETCH
+vdump $anImage1
+
+vsetbg $aTextureFile NONE
+vsetbg $aTextureFile TILED
+vdump $anImage2
+
+vsetgradientbg 255 0 0 0 0 255 1
+vsetbg $aTextureFile CENTERED
+vdump $anImage3
+
+vsetbg $aTextureFile NONE
+vdump $anImage4