mirror of
https://git.dev.opencascade.org/repos/occt.git
synced 2025-04-04 18:06:22 +03:00
0025556: Visualization - support stereo pair formats recognized by consumer display devices
Graphic3d_StereoMode - add new enumeration for stereoscopic outputs: - Graphic3d_StereoMode_QuadBuffer - Graphic3d_StereoMode_Anaglyph - Graphic3d_StereoMode_RowInterlaced - Graphic3d_StereoMode_ColumnInterlaced - Graphic3d_StereoMode_ChessBoard - Graphic3d_StereoMode_SideBySide - Graphic3d_StereoMode_OverUnder Graphic3d_RenderingParams - add new options controlling stereo output: - StereoMode - ToReverseStereo - AnaglyphFilter OpenGl_ShaderManager - add predefined GLSL programs for new stereo outputs. OpenGl_Workspace::Redraw() - do not implicitly disable stereo to allow stereo dump as is. OpenGl_Caps - add flag swapInterval to control VSync. OpenGl_Workspace::BufferDump() - handle cases with non-applicable GL_PACK_ROW_LENGTH. CALL_DEF_WINDOW - drop unused fields; add fields "left" and "top" to reverse stereo pair for interlaced output depending on window position. Draw Harness, ViewerTest: - Extend syntax of command vstereo to setup stereo. - Extend vdump command to allow dump of stereoscopic pair in different formats. - Extend command vcaps with option vsync. - Use mouse scroll to zoom and adjust ZFocus in WinAPI. - Use "/" and "*" to adjust IOD. v3d/glsl/stereo - add test case for stereo modes. Cocoa_LocalPool, OSD_EnvironmentIterator - fix compilation issues on OS X Snow Leopard.
This commit is contained in:
parent
f809e94b93
commit
f978241fb6
@ -14,7 +14,13 @@
|
||||
#ifndef __Cocoa_LocalPool_h_
|
||||
#define __Cocoa_LocalPool_h_
|
||||
|
||||
#if defined(__clang__) && (__clang_major__ >= 4) && __has_feature(objc_arc)
|
||||
#if defined(__clang__) && (__clang_major__ >= 4)
|
||||
#if __has_feature(objc_arc)
|
||||
#define HAVE_OBJC_ARC
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_OBJC_ARC
|
||||
|
||||
// @autoreleasepool should be used within ARC
|
||||
|
||||
|
@ -23,9 +23,7 @@
|
||||
#import <Cocoa/Cocoa.h>
|
||||
#endif
|
||||
|
||||
#if defined(__clang__) && (__clang_major__ >= 4) && __has_feature(objc_arc)
|
||||
// ARC
|
||||
#else
|
||||
#ifndef HAVE_OBJC_ARC
|
||||
|
||||
// =======================================================================
|
||||
// function : Cocoa_LocalPool
|
||||
|
@ -32,10 +32,6 @@
|
||||
IMPLEMENT_STANDARD_HANDLE (Cocoa_Window, Aspect_Window)
|
||||
IMPLEMENT_STANDARD_RTTIEXT(Cocoa_Window, Aspect_Window)
|
||||
|
||||
#if defined(__clang__) && (__clang_major__ >= 4) && __has_feature(objc_arc)
|
||||
#define HAVE_OBJC_ARC
|
||||
#endif
|
||||
|
||||
#if defined(TARGET_OS_IPHONE) && TARGET_OS_IPHONE
|
||||
//
|
||||
#else
|
||||
|
@ -30,6 +30,7 @@ Graphic3d_ShaderProgram.cxx
|
||||
Graphic3d_ShaderVariable.hxx
|
||||
Graphic3d_ShaderVariable.cxx
|
||||
Graphic3d_ShaderVariable.lxx
|
||||
Graphic3d_StereoMode.hxx
|
||||
Graphic3d_MapOfStructure.hxx
|
||||
Graphic3d_MapIteratorOfMapOfStructure.hxx
|
||||
Graphic3d_IndexedMapOfAddress.hxx
|
||||
|
@ -17,6 +17,9 @@
|
||||
#define _Graphic3d_RenderingParams_HeaderFile
|
||||
|
||||
#include <Graphic3d_RenderingMode.hxx>
|
||||
#include <Graphic3d_StereoMode.hxx>
|
||||
#include <Graphic3d_Mat4.hxx>
|
||||
#include <Graphic3d_Vec4.hxx>
|
||||
|
||||
//! Helper class to store rendering parameters.
|
||||
class Graphic3d_RenderingParams
|
||||
@ -29,51 +32,64 @@ public:
|
||||
//! Default ray-tracing depth.
|
||||
static const Standard_Integer THE_DEFAULT_DEPTH = 3;
|
||||
|
||||
//! Anaglyph filter presets.
|
||||
enum Anaglyph
|
||||
{
|
||||
Anaglyph_RedCyan_Simple, //!< simple filter for Red-Cyan glasses (R+GB)
|
||||
Anaglyph_RedCyan_Optimized, //!< optimized filter for Red-Cyan glasses (R+GB)
|
||||
Anaglyph_YellowBlue_Simple, //!< simple filter for Yellow-Blue glasses (RG+B)
|
||||
Anaglyph_YellowBlue_Optimized, //!< optimized filter for Yellow-Blue glasses (RG+B)
|
||||
Anaglyph_GreenMagenta_Simple, //!< simple filter for Green-Magenta glasses (G+RB)
|
||||
Anaglyph_UserDefined //!< use externally specified matrices
|
||||
};
|
||||
|
||||
public:
|
||||
|
||||
//! Creates default rendering parameters.
|
||||
Graphic3d_RenderingParams()
|
||||
: Method (Graphic3d_RM_RASTERIZATION),
|
||||
RaytracingDepth (THE_DEFAULT_DEPTH),
|
||||
IsGlobalIlluminationEnabled (Standard_False),
|
||||
SamplesPerPixel (THE_DEFAULT_SPP),
|
||||
RaytracingDepth (THE_DEFAULT_DEPTH),
|
||||
IsShadowEnabled (Standard_True),
|
||||
IsReflectionEnabled (Standard_False),
|
||||
IsAntialiasingEnabled (Standard_False),
|
||||
IsTransparentShadowEnabled (Standard_False),
|
||||
IsGlobalIlluminationEnabled (Standard_False),
|
||||
UseEnvironmentMapBackground (Standard_False)
|
||||
|
||||
UseEnvironmentMapBackground (Standard_False),
|
||||
StereoMode (Graphic3d_StereoMode_QuadBuffer),
|
||||
AnaglyphFilter (Anaglyph_RedCyan_Optimized),
|
||||
ToReverseStereo (Standard_False)
|
||||
{
|
||||
//
|
||||
const Graphic3d_Vec4 aZero (0.0f, 0.0f, 0.0f, 0.0f);
|
||||
AnaglyphLeft .SetRow (0, Graphic3d_Vec4 (1.0f, 0.0f, 0.0f, 0.0f));
|
||||
AnaglyphLeft .SetRow (1, aZero);
|
||||
AnaglyphLeft .SetRow (2, aZero);
|
||||
AnaglyphLeft .SetRow (3, aZero);
|
||||
AnaglyphRight.SetRow (0, aZero);
|
||||
AnaglyphRight.SetRow (1, Graphic3d_Vec4 (0.0f, 1.0f, 0.0f, 0.0f));
|
||||
AnaglyphRight.SetRow (2, Graphic3d_Vec4 (0.0f, 0.0f, 1.0f, 0.0f));
|
||||
AnaglyphRight.SetRow (3, aZero);
|
||||
}
|
||||
|
||||
public:
|
||||
|
||||
//! Specifies rendering mode.
|
||||
Graphic3d_RenderingMode Method;
|
||||
Graphic3d_RenderingMode Method; //!< specifies rendering mode, Graphic3d_RM_RASTERIZATION by default
|
||||
|
||||
//! Maximum ray-tracing depth.
|
||||
Standard_Integer RaytracingDepth;
|
||||
Standard_Boolean IsGlobalIlluminationEnabled; //!< enables/disables global illumination effects (path tracing)
|
||||
Standard_Integer SamplesPerPixel; //!< number of samples per pixel (SPP)
|
||||
Standard_Integer RaytracingDepth; //!< maximum ray-tracing depth, 3 by default
|
||||
Standard_Boolean IsShadowEnabled; //!< enables/disables shadows rendering, True by default
|
||||
Standard_Boolean IsReflectionEnabled; //!< enables/disables specular reflections, False by default
|
||||
Standard_Boolean IsAntialiasingEnabled; //!< enables/disables adaptive anti-aliasing, False by default
|
||||
Standard_Boolean IsTransparentShadowEnabled; //!< enables/disables light propagation through transparent media, False by default
|
||||
Standard_Boolean UseEnvironmentMapBackground; //!< enables/disables environment map background
|
||||
|
||||
//! Number of samples per pixel (SPP).
|
||||
Standard_Integer SamplesPerPixel;
|
||||
|
||||
//! Enables/disables shadows rendering.
|
||||
Standard_Boolean IsShadowEnabled;
|
||||
|
||||
//! Enables/disables specular reflections.
|
||||
Standard_Boolean IsReflectionEnabled;
|
||||
|
||||
//! Enables/disables adaptive anti-aliasing.
|
||||
Standard_Boolean IsAntialiasingEnabled;
|
||||
|
||||
//! Enables/disables light propagation through transparent media.
|
||||
Standard_Boolean IsTransparentShadowEnabled;
|
||||
|
||||
//! Enables/disables global illumination effects (uses path tracing).
|
||||
Standard_Boolean IsGlobalIlluminationEnabled;
|
||||
|
||||
//! Enables/disables environment map background (instead of OCCT background).
|
||||
Standard_Boolean UseEnvironmentMapBackground;
|
||||
Graphic3d_StereoMode StereoMode; //!< stereoscopic output mode, Graphic3d_StereoMode_QuadBuffer by default
|
||||
Anaglyph AnaglyphFilter; //!< filter for anaglyph output, Anaglyph_RedCyan_Optimized by default
|
||||
Graphic3d_Mat4 AnaglyphLeft; //!< left anaglyph filter (in normalized colorspace), Color = AnaglyphRight * theColorRight + AnaglyphLeft * theColorLeft;
|
||||
Graphic3d_Mat4 AnaglyphRight; //!< right anaglyph filter (in normalized colorspace), Color = AnaglyphRight * theColorRight + AnaglyphLeft * theColorLeft;
|
||||
Standard_Boolean ToReverseStereo; //!< flag to reverse stereo pair, FALSE by default
|
||||
|
||||
};
|
||||
|
||||
|
33
src/Graphic3d/Graphic3d_StereoMode.hxx
Normal file
33
src/Graphic3d/Graphic3d_StereoMode.hxx
Normal file
@ -0,0 +1,33 @@
|
||||
// Created on: 2015-06-05
|
||||
// Created by: Kirill Gavrilov
|
||||
// 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 _Graphic3d_StereoMode_HeaderFile
|
||||
#define _Graphic3d_StereoMode_HeaderFile
|
||||
|
||||
//! This enumeration defines the list of stereoscopic output modes.
|
||||
enum Graphic3d_StereoMode
|
||||
{
|
||||
Graphic3d_StereoMode_QuadBuffer, //!< OpenGL QuadBuffer
|
||||
Graphic3d_StereoMode_Anaglyph, //!< Anaglyph glasses, the type should be specified in addition
|
||||
Graphic3d_StereoMode_RowInterlaced, //!< Row-interlaced stereo
|
||||
Graphic3d_StereoMode_ColumnInterlaced, //!< Column-interlaced stereo
|
||||
Graphic3d_StereoMode_ChessBoard, //!< chess-board stereo for DLP TVs
|
||||
Graphic3d_StereoMode_SideBySide, //!< horizontal pair
|
||||
Graphic3d_StereoMode_OverUnder, //!< vertical pair
|
||||
Graphic3d_StereoMode_SoftPageFlip, //!< software PageFlip for shutter glasses, should NOT be used!
|
||||
Graphic3d_StereoMode_NB //!< the number of modes
|
||||
};
|
||||
|
||||
#endif // _Graphic3d_StereoMode_HeaderFile
|
@ -18,10 +18,6 @@
|
||||
#include <Aspect_Drawable.hxx>
|
||||
#include <Aspect_RenderingContext.hxx>
|
||||
|
||||
typedef struct {
|
||||
int mapped;
|
||||
} EXT_WINDOW ;
|
||||
|
||||
/* WINDOW */
|
||||
|
||||
typedef struct {
|
||||
@ -31,17 +27,8 @@ typedef struct {
|
||||
Aspect_Drawable XWindow;
|
||||
Aspect_Drawable XParentWindow;
|
||||
|
||||
EXT_WINDOW *ext_data;
|
||||
|
||||
struct {
|
||||
float xm, ym, xM, yM;
|
||||
} Position;
|
||||
|
||||
int dx, dy;
|
||||
|
||||
char *Title;
|
||||
|
||||
char *Icon;
|
||||
int left, top;
|
||||
|
||||
struct {
|
||||
float r, g, b;
|
||||
|
@ -21,11 +21,12 @@
|
||||
|
||||
//const OSD_WhoAmI Iam = OSD_WEnvironmentIterator;
|
||||
#ifdef __APPLE__
|
||||
#import <TargetConditionals.h>
|
||||
#if defined(TARGET_OS_IPHONE) && TARGET_OS_IPHONE
|
||||
extern char **environ;
|
||||
#else
|
||||
#include <crt_externs.h>
|
||||
#define environ (*_NSGetEnviron())
|
||||
#else
|
||||
extern char **environ;
|
||||
#endif
|
||||
#else
|
||||
extern char **environ;
|
||||
|
@ -33,6 +33,7 @@ OpenGl_Caps::OpenGl_Caps()
|
||||
#else
|
||||
ffpEnable (Standard_False),
|
||||
#endif
|
||||
swapInterval (1),
|
||||
buffersNoSwap (Standard_False),
|
||||
contextStereo (Standard_False),
|
||||
#ifdef OCCT_DEBUG
|
||||
@ -64,6 +65,7 @@ OpenGl_Caps& OpenGl_Caps::operator= (const OpenGl_Caps& theCopy)
|
||||
pntSpritesDisable = theCopy.pntSpritesDisable;
|
||||
keepArrayData = theCopy.keepArrayData;
|
||||
ffpEnable = theCopy.ffpEnable;
|
||||
swapInterval = theCopy.swapInterval;
|
||||
buffersNoSwap = theCopy.buffersNoSwap;
|
||||
contextStereo = theCopy.contextStereo;
|
||||
contextDebug = theCopy.contextDebug;
|
||||
|
@ -31,6 +31,7 @@ public: //! @name flags to disable particular functionality, should be used only
|
||||
Standard_Boolean pntSpritesDisable; //!< flag permits Point Sprites usage, will significantly affect performance (OFF by default)
|
||||
Standard_Boolean keepArrayData; //!< Disables freeing CPU memory after building VBOs (OFF by default)
|
||||
Standard_Boolean ffpEnable; //!< Enables FFP (fixed-function pipeline), do not use built-in GLSL programs (ON by default on desktop OpenGL and OFF on OpenGL ES)
|
||||
Standard_Integer swapInterval; //!< controls swap interval - 0 for VSync off and 1 for VSync on, 1 by default
|
||||
|
||||
public: //! @name context creation parameters
|
||||
|
||||
|
@ -45,6 +45,11 @@
|
||||
//
|
||||
#elif defined(__APPLE__) && !defined(MACOSX_USE_GLX)
|
||||
#include <dlfcn.h>
|
||||
#if defined(TARGET_OS_IPHONE) && TARGET_OS_IPHONE
|
||||
//
|
||||
#else
|
||||
#include <OpenGL/OpenGL.h>
|
||||
#endif
|
||||
#else
|
||||
#include <GL/glx.h> // glXGetProcAddress()
|
||||
#endif
|
||||
@ -526,6 +531,48 @@ void OpenGl_Context::SwapBuffers()
|
||||
|
||||
#endif // __APPLE__
|
||||
|
||||
// =======================================================================
|
||||
// function : SetSwapInterval
|
||||
// purpose :
|
||||
// =======================================================================
|
||||
Standard_Boolean OpenGl_Context::SetSwapInterval (const Standard_Integer theInterval)
|
||||
{
|
||||
#if defined(HAVE_EGL)
|
||||
if (::eglSwapInterval ((EGLDisplay )myDisplay, theInterval) == EGL_TRUE)
|
||||
{
|
||||
return Standard_True;
|
||||
}
|
||||
#elif defined(_WIN32)
|
||||
if (myFuncs->wglSwapIntervalEXT != NULL)
|
||||
{
|
||||
myFuncs->wglSwapIntervalEXT (theInterval);
|
||||
return Standard_True;
|
||||
}
|
||||
#elif defined(TARGET_OS_IPHONE) && TARGET_OS_IPHONE
|
||||
//
|
||||
#elif defined(__APPLE__)
|
||||
if (::CGLSetParameter (CGLGetCurrentContext(), kCGLCPSwapInterval, &theInterval) == kCGLNoError)
|
||||
{
|
||||
return Standard_True;
|
||||
}
|
||||
#else
|
||||
if (theInterval == -1
|
||||
&& myFuncs->glXSwapIntervalEXT != NULL)
|
||||
{
|
||||
typedef int (*glXSwapIntervalEXT_t_x)(Display* theDisplay, GLXDrawable theDrawable, int theInterval);
|
||||
glXSwapIntervalEXT_t_x aFuncPtr = (glXSwapIntervalEXT_t_x )myFuncs->glXSwapIntervalEXT;
|
||||
aFuncPtr ((Display* )myDisplay, (GLXDrawable )myWindow, theInterval);
|
||||
return Standard_True;
|
||||
}
|
||||
else if (myFuncs->glXSwapIntervalSGI != NULL)
|
||||
{
|
||||
myFuncs->glXSwapIntervalSGI (theInterval);
|
||||
return Standard_True;
|
||||
}
|
||||
#endif
|
||||
return Standard_False;
|
||||
}
|
||||
|
||||
// =======================================================================
|
||||
// function : findProc
|
||||
// purpose :
|
||||
@ -1127,7 +1174,9 @@ void OpenGl_Context::init (const Standard_Boolean theIsCoreProfile)
|
||||
#define FindProcShort(theFunc) FindProc(#theFunc, myFuncs->theFunc)
|
||||
|
||||
// retrieve platform-dependent extensions
|
||||
#if defined(_WIN32) && !defined(HAVE_EGL)
|
||||
#if defined(HAVE_EGL)
|
||||
//
|
||||
#elif defined(_WIN32)
|
||||
if (FindProcShort (wglGetExtensionsStringARB))
|
||||
{
|
||||
const char* aWglExts = myFuncs->wglGetExtensionsStringARB (wglGetCurrentDC());
|
||||
@ -1155,6 +1204,19 @@ void OpenGl_Context::init (const Standard_Boolean theIsCoreProfile)
|
||||
FindProcShort (wglDXUnlockObjectsNV);
|
||||
}
|
||||
}
|
||||
#elif defined(__APPLE__)
|
||||
//
|
||||
#else
|
||||
const char* aGlxExts = ::glXQueryExtensionsString ((Display* )myDisplay, DefaultScreen ((Display* )myDisplay));
|
||||
if (CheckExtension (aGlxExts, "GLX_EXT_swap_control"))
|
||||
{
|
||||
FindProcShort (glXSwapIntervalEXT);
|
||||
}
|
||||
if (CheckExtension (aGlxExts, "GLX_SGI_swap_control"))
|
||||
{
|
||||
FindProcShort (glXSwapIntervalSGI);
|
||||
}
|
||||
//extSwapTear = CheckExtension (aGlxExts, "GLX_EXT_swap_control_tear");
|
||||
#endif
|
||||
|
||||
// initialize debug context extension
|
||||
|
@ -299,6 +299,9 @@ public:
|
||||
|| (myGlVerMajor == theVerMajor && myGlVerMinor >= theVerMinor);
|
||||
}
|
||||
|
||||
//! Access entire map of loaded OpenGL functions.
|
||||
const OpenGl_GlFunctions* Functions() const { return myFuncs.operator->(); }
|
||||
|
||||
//! Clean up errors stack for this GL context (glGetError() in loop).
|
||||
Standard_EXPORT void ResetErrors();
|
||||
|
||||
@ -314,6 +317,9 @@ public:
|
||||
//! Swap front/back buffers for this GL context (should be activated before!).
|
||||
Standard_EXPORT void SwapBuffers();
|
||||
|
||||
//! Setup swap interval (VSync).
|
||||
Standard_EXPORT Standard_Boolean SetSwapInterval (const Standard_Integer theInterval);
|
||||
|
||||
//! Return true if active mode is GL_RENDER (cached state)
|
||||
Standard_Boolean IsRender() const
|
||||
{
|
||||
|
@ -310,6 +310,13 @@ Standard_Boolean OpenGl_GraphicDriver::BufferDump (const Graphic3d_CView& t
|
||||
return (aCView != NULL) && aCView->WS->BufferDump ((OpenGl_FrameBuffer* )theCView.ptrFBO, theImage, theBufferType);
|
||||
}
|
||||
|
||||
//! Compute aligned number greater or equal to specified one
|
||||
inline Standard_Size getAligned (const Standard_Size theNumber,
|
||||
const Standard_Size theAlignment)
|
||||
{
|
||||
return theNumber + theAlignment - 1 - (theNumber - 1) % theAlignment;
|
||||
}
|
||||
|
||||
Standard_Boolean OpenGl_Workspace::BufferDump (OpenGl_FrameBuffer* theFBOPtr,
|
||||
Image_PixMap& theImage,
|
||||
const Graphic3d_BufferType& theBufferType)
|
||||
@ -348,14 +355,30 @@ Standard_Boolean OpenGl_Workspace::BufferDump (OpenGl_FrameBuffer* theFB
|
||||
// setup alignment
|
||||
const GLint anAligment = Min (GLint(theImage.MaxRowAligmentBytes()), 8); // limit to 8 bytes for OpenGL
|
||||
glPixelStorei (GL_PACK_ALIGNMENT, anAligment);
|
||||
bool isBatchCopy = !theImage.IsTopDown();
|
||||
|
||||
const GLint anExtraBytes = GLint(theImage.RowExtraBytes());
|
||||
GLint aPixelsWidth = GLint(theImage.SizeRowBytes() / theImage.SizePixelBytes());
|
||||
Standard_Size aSizeRowBytesEstim = getAligned (theImage.SizePixelBytes() * aPixelsWidth, anAligment);
|
||||
if (anExtraBytes < anAligment)
|
||||
{
|
||||
aPixelsWidth = 0;
|
||||
}
|
||||
else if (aSizeRowBytesEstim != theImage.SizeRowBytes())
|
||||
{
|
||||
aPixelsWidth = 0;
|
||||
isBatchCopy = false;
|
||||
}
|
||||
#if !defined(GL_ES_VERSION_2_0)
|
||||
const GLint anExtraBytes = (GLint )theImage.RowExtraBytes();
|
||||
const GLint aPixelsWidth = GLint(theImage.SizeRowBytes() / theImage.SizePixelBytes());
|
||||
glPixelStorei (GL_PACK_ROW_LENGTH, (anExtraBytes >= anAligment) ? aPixelsWidth : 0);
|
||||
glPixelStorei (GL_PACK_ROW_LENGTH, aPixelsWidth);
|
||||
#else
|
||||
if (aPixelsWidth != 0)
|
||||
{
|
||||
isBatchCopy = false;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (theImage.IsTopDown())
|
||||
if (!isBatchCopy)
|
||||
{
|
||||
// copy row by row
|
||||
for (Standard_Size aRow = 0; aRow < theImage.SizeY(); ++aRow)
|
||||
|
@ -237,7 +237,10 @@ void OpenGl_ShaderManager::clear()
|
||||
myMapOfLightPrograms.Clear();
|
||||
myFontProgram.Nullify();
|
||||
myBlitProgram.Nullify();
|
||||
myAnaglyphProgram.Nullify();
|
||||
for (Standard_Integer aModeIter = 0; aModeIter < Graphic3d_StereoMode_NB; ++aModeIter)
|
||||
{
|
||||
myStereoPrograms[aModeIter].Nullify();
|
||||
}
|
||||
switchLightPrograms();
|
||||
}
|
||||
|
||||
@ -1629,10 +1632,11 @@ Standard_Boolean OpenGl_ShaderManager::prepareStdProgramPhong (Handle(OpenGl_Sha
|
||||
}
|
||||
|
||||
// =======================================================================
|
||||
// function : prepareStdProgramAnaglyph
|
||||
// function : prepareStdProgramStereo
|
||||
// purpose :
|
||||
// =======================================================================
|
||||
Standard_Boolean OpenGl_ShaderManager::prepareStdProgramAnaglyph()
|
||||
Standard_Boolean OpenGl_ShaderManager::prepareStdProgramStereo (Handle(OpenGl_ShaderProgram)& theProgram,
|
||||
const Graphic3d_StereoMode theStereoMode)
|
||||
{
|
||||
Handle(Graphic3d_ShaderProgram) aProgramSrc = new Graphic3d_ShaderProgram();
|
||||
TCollection_AsciiString aSrcVert =
|
||||
@ -1643,21 +1647,188 @@ Standard_Boolean OpenGl_ShaderManager::prepareStdProgramAnaglyph()
|
||||
EOL" gl_Position = vec4(occVertex.x, occVertex.y, 0.0, 1.0);"
|
||||
EOL"}";
|
||||
|
||||
TCollection_AsciiString aSrcFrag =
|
||||
EOL"uniform sampler2D uLeftSampler;"
|
||||
EOL"uniform sampler2D uRightSampler;"
|
||||
EOL
|
||||
EOL"THE_SHADER_IN vec2 TexCoord;"
|
||||
EOL
|
||||
EOL"void main()"
|
||||
EOL"{"
|
||||
EOL" vec4 aColorL = occTexture2D (uLeftSampler, TexCoord);"
|
||||
EOL" vec4 aColorR = occTexture2D (uRightSampler, TexCoord);"
|
||||
EOL" aColorL.b = 0.0;"
|
||||
EOL" aColorL.g = 0.0;"
|
||||
EOL" aColorR.r = 0.0;"
|
||||
EOL" occFragColor = aColorL + aColorR;"
|
||||
EOL"}";
|
||||
TCollection_AsciiString aSrcFrag;
|
||||
switch (theStereoMode)
|
||||
{
|
||||
case Graphic3d_StereoMode_Anaglyph:
|
||||
{
|
||||
aSrcFrag =
|
||||
EOL"uniform sampler2D uLeftSampler;"
|
||||
EOL"uniform sampler2D uRightSampler;"
|
||||
EOL
|
||||
EOL"uniform mat4 uMultL;"
|
||||
EOL"uniform mat4 uMultR;"
|
||||
EOL
|
||||
EOL"vec4 THE_POW_UP = vec4 (2.2, 2.2, 2.2, 1.0);"
|
||||
EOL"vec4 THE_POW_DOWN = 1.0 / THE_POW_UP;"
|
||||
EOL
|
||||
EOL"THE_SHADER_IN vec2 TexCoord;"
|
||||
EOL
|
||||
EOL"void main()"
|
||||
EOL"{"
|
||||
EOL" vec4 aColorL = occTexture2D (uLeftSampler, TexCoord);"
|
||||
EOL" vec4 aColorR = occTexture2D (uRightSampler, TexCoord);"
|
||||
EOL" aColorL = pow (aColorL, THE_POW_UP);" // normalize
|
||||
EOL" aColorR = pow (aColorR, THE_POW_UP);"
|
||||
EOL" vec4 aColor = uMultR * aColorR + uMultL * aColorL;"
|
||||
EOL" occFragColor = pow (aColor, THE_POW_DOWN);"
|
||||
EOL"}";
|
||||
break;
|
||||
}
|
||||
case Graphic3d_StereoMode_RowInterlaced:
|
||||
{
|
||||
aSrcFrag =
|
||||
EOL"uniform sampler2D uLeftSampler;"
|
||||
EOL"uniform sampler2D uRightSampler;"
|
||||
EOL
|
||||
EOL"THE_SHADER_IN vec2 TexCoord;"
|
||||
EOL
|
||||
EOL"void main()"
|
||||
EOL"{"
|
||||
EOL" vec4 aColorL = occTexture2D (uLeftSampler, TexCoord);"
|
||||
EOL" vec4 aColorR = occTexture2D (uRightSampler, TexCoord);"
|
||||
EOL" if (int (mod (gl_FragCoord.y + 1.5, 2.0)) == 1)"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorL;"
|
||||
EOL" }"
|
||||
EOL" else"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorR;"
|
||||
EOL" }"
|
||||
EOL"}";
|
||||
break;
|
||||
}
|
||||
case Graphic3d_StereoMode_ColumnInterlaced:
|
||||
{
|
||||
aSrcFrag =
|
||||
EOL"uniform sampler2D uLeftSampler;"
|
||||
EOL"uniform sampler2D uRightSampler;"
|
||||
EOL
|
||||
EOL"THE_SHADER_IN vec2 TexCoord;"
|
||||
EOL
|
||||
EOL"void main()"
|
||||
EOL"{"
|
||||
EOL" vec4 aColorL = occTexture2D (uLeftSampler, TexCoord);"
|
||||
EOL" vec4 aColorR = occTexture2D (uRightSampler, TexCoord);"
|
||||
EOL" if (int (mod (gl_FragCoord.x + 1.5, 2.0)) != 1)"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorL;"
|
||||
EOL" }"
|
||||
EOL" else"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorR;"
|
||||
EOL" }"
|
||||
EOL"}";
|
||||
break;
|
||||
}
|
||||
case Graphic3d_StereoMode_ChessBoard:
|
||||
{
|
||||
aSrcFrag =
|
||||
EOL"uniform sampler2D uLeftSampler;"
|
||||
EOL"uniform sampler2D uRightSampler;"
|
||||
EOL
|
||||
EOL"THE_SHADER_IN vec2 TexCoord;"
|
||||
EOL
|
||||
EOL"void main()"
|
||||
EOL"{"
|
||||
EOL" vec4 aColorL = occTexture2D (uLeftSampler, TexCoord);"
|
||||
EOL" vec4 aColorR = occTexture2D (uRightSampler, TexCoord);"
|
||||
EOL" bool isEvenX = int(mod(floor(gl_FragCoord.x + 1.5), 2.0)) == 1;"
|
||||
EOL" bool isEvenY = int(mod(floor(gl_FragCoord.y + 1.5), 2.0)) != 1;"
|
||||
EOL" if ((isEvenX && isEvenY) || (!isEvenX && !isEvenY))"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorL;"
|
||||
EOL" }"
|
||||
EOL" else"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorR;"
|
||||
EOL" }"
|
||||
EOL"}";
|
||||
break;
|
||||
}
|
||||
case Graphic3d_StereoMode_SideBySide:
|
||||
{
|
||||
aSrcFrag =
|
||||
EOL"uniform sampler2D uLeftSampler;"
|
||||
EOL"uniform sampler2D uRightSampler;"
|
||||
EOL
|
||||
EOL"THE_SHADER_IN vec2 TexCoord;"
|
||||
EOL
|
||||
EOL"void main()"
|
||||
EOL"{"
|
||||
EOL" vec2 aTexCoord = vec2 (TexCoord.x * 2.0, TexCoord.y);"
|
||||
EOL" if (TexCoord.x > 0.5)"
|
||||
EOL" {"
|
||||
EOL" aTexCoord.x -= 1.0;"
|
||||
EOL" }"
|
||||
EOL" vec4 aColorL = occTexture2D (uLeftSampler, aTexCoord);"
|
||||
EOL" vec4 aColorR = occTexture2D (uRightSampler, aTexCoord);"
|
||||
EOL" if (TexCoord.x <= 0.5)"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorL;"
|
||||
EOL" }"
|
||||
EOL" else"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorR;"
|
||||
EOL" }"
|
||||
EOL"}";
|
||||
break;
|
||||
}
|
||||
case Graphic3d_StereoMode_OverUnder:
|
||||
{
|
||||
aSrcFrag =
|
||||
EOL"uniform sampler2D uLeftSampler;"
|
||||
EOL"uniform sampler2D uRightSampler;"
|
||||
EOL
|
||||
EOL"THE_SHADER_IN vec2 TexCoord;"
|
||||
EOL
|
||||
EOL"void main()"
|
||||
EOL"{"
|
||||
EOL" vec2 aTexCoord = vec2 (TexCoord.x, TexCoord.y * 2.0);"
|
||||
EOL" if (TexCoord.y > 0.5)"
|
||||
EOL" {"
|
||||
EOL" aTexCoord.y -= 1.0;"
|
||||
EOL" }"
|
||||
EOL" vec4 aColorL = occTexture2D (uLeftSampler, aTexCoord);"
|
||||
EOL" vec4 aColorR = occTexture2D (uRightSampler, aTexCoord);"
|
||||
EOL" if (TexCoord.y <= 0.5)"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorL;"
|
||||
EOL" }"
|
||||
EOL" else"
|
||||
EOL" {"
|
||||
EOL" occFragColor = aColorR;"
|
||||
EOL" }"
|
||||
EOL"}";
|
||||
break;
|
||||
}
|
||||
case Graphic3d_StereoMode_QuadBuffer:
|
||||
case Graphic3d_StereoMode_SoftPageFlip:
|
||||
default:
|
||||
{
|
||||
/*const Handle(OpenGl_ShaderProgram)& aProgram = myStereoPrograms[Graphic3d_StereoMode_QuadBuffer];
|
||||
if (!aProgram.IsNull())
|
||||
{
|
||||
return aProgram->IsValid();
|
||||
}*/
|
||||
aSrcFrag =
|
||||
EOL"uniform sampler2D uLeftSampler;"
|
||||
EOL"uniform sampler2D uRightSampler;"
|
||||
EOL
|
||||
EOL"THE_SHADER_IN vec2 TexCoord;"
|
||||
EOL
|
||||
EOL"void main()"
|
||||
EOL"{"
|
||||
EOL" vec4 aColorL = occTexture2D (uLeftSampler, TexCoord);"
|
||||
EOL" vec4 aColorR = occTexture2D (uRightSampler, TexCoord);"
|
||||
EOL" aColorL.b = 0.0;"
|
||||
EOL" aColorL.g = 0.0;"
|
||||
EOL" aColorR.r = 0.0;"
|
||||
EOL" occFragColor = aColorL + aColorR;"
|
||||
EOL"}";
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
#if !defined(GL_ES_VERSION_2_0)
|
||||
if (myContext->core32 != NULL)
|
||||
@ -1669,15 +1840,15 @@ Standard_Boolean OpenGl_ShaderManager::prepareStdProgramAnaglyph()
|
||||
aProgramSrc->AttachShader (Graphic3d_ShaderObject::CreateFromSource (Graphic3d_TOS_VERTEX, aSrcVert));
|
||||
aProgramSrc->AttachShader (Graphic3d_ShaderObject::CreateFromSource (Graphic3d_TOS_FRAGMENT, aSrcFrag));
|
||||
TCollection_AsciiString aKey;
|
||||
if (!Create (aProgramSrc, aKey, myAnaglyphProgram))
|
||||
if (!Create (aProgramSrc, aKey, theProgram))
|
||||
{
|
||||
myAnaglyphProgram = new OpenGl_ShaderProgram(); // just mark as invalid
|
||||
theProgram = new OpenGl_ShaderProgram(); // just mark as invalid
|
||||
return Standard_False;
|
||||
}
|
||||
|
||||
myContext->BindProgram (myAnaglyphProgram);
|
||||
myAnaglyphProgram->SetSampler (myContext, "uLeftSampler", 0);
|
||||
myAnaglyphProgram->SetSampler (myContext, "uRightSampler", 1);
|
||||
myContext->BindProgram (theProgram);
|
||||
theProgram->SetSampler (myContext, "uLeftSampler", 0);
|
||||
theProgram->SetSampler (myContext, "uRightSampler", 1);
|
||||
myContext->BindProgram (NULL);
|
||||
return Standard_True;
|
||||
}
|
||||
|
@ -17,6 +17,7 @@
|
||||
#define _OpenGl_ShaderManager_HeaderFile
|
||||
|
||||
#include <Graphic3d_ShaderProgram.hxx>
|
||||
#include <Graphic3d_StereoMode.hxx>
|
||||
|
||||
#include <NCollection_DataMap.hxx>
|
||||
#include <NCollection_Sequence.hxx>
|
||||
@ -161,15 +162,21 @@ public:
|
||||
&& myContext->BindProgram (myBlitProgram);
|
||||
}
|
||||
|
||||
//! Bind program for rendering Anaglyph image.
|
||||
Standard_Boolean BindAnaglyphProgram()
|
||||
//! Bind program for rendering stereoscopic image.
|
||||
Standard_Boolean BindStereoProgram (const Graphic3d_StereoMode theStereoMode)
|
||||
{
|
||||
if (myAnaglyphProgram.IsNull())
|
||||
if (theStereoMode < 0 || theStereoMode >= Graphic3d_StereoMode_NB)
|
||||
{
|
||||
prepareStdProgramAnaglyph();
|
||||
return Standard_False;
|
||||
}
|
||||
return !myAnaglyphProgram.IsNull()
|
||||
&& myContext->BindProgram (myAnaglyphProgram);
|
||||
|
||||
if (myStereoPrograms[theStereoMode].IsNull())
|
||||
{
|
||||
prepareStdProgramStereo (myStereoPrograms[theStereoMode], theStereoMode);
|
||||
}
|
||||
const Handle(OpenGl_ShaderProgram)& aProgram = myStereoPrograms[theStereoMode];
|
||||
return !aProgram.IsNull()
|
||||
&& myContext->BindProgram (aProgram);
|
||||
}
|
||||
|
||||
public:
|
||||
@ -370,8 +377,9 @@ protected:
|
||||
//! Set pointer myLightPrograms to active lighting programs set from myMapOfLightPrograms
|
||||
Standard_EXPORT void switchLightPrograms();
|
||||
|
||||
//! Prepare standard GLSL program for Anaglyph image.
|
||||
Standard_EXPORT Standard_Boolean prepareStdProgramAnaglyph();
|
||||
//! Prepare standard GLSL program for stereoscopic image.
|
||||
Standard_EXPORT Standard_Boolean prepareStdProgramStereo (Handle(OpenGl_ShaderProgram)& theProgram,
|
||||
const Graphic3d_StereoMode theStereoMode);
|
||||
|
||||
protected:
|
||||
|
||||
@ -383,7 +391,7 @@ protected:
|
||||
Handle(OpenGl_ShaderProgram) myBlitProgram; //!< standard program for FBO blit emulation
|
||||
OpenGl_MapOfShaderPrograms myMapOfLightPrograms; //!< map of lighting programs depending on shading model and lights configuration
|
||||
|
||||
Handle(OpenGl_ShaderProgram) myAnaglyphProgram; //!< standard program for Anaglyph image
|
||||
Handle(OpenGl_ShaderProgram) myStereoPrograms[Graphic3d_StereoMode_NB]; //!< standard stereo programs
|
||||
|
||||
OpenGl_Context* myContext; //!< OpenGL context
|
||||
|
||||
|
@ -141,7 +141,8 @@ OpenGl_Window::OpenGl_Window (const Handle(OpenGl_GraphicDriver)& theDriver,
|
||||
myOwnGContext (theGContext == 0),
|
||||
myWidth (theCWindow.dx),
|
||||
myHeight (theCWindow.dy),
|
||||
myBgColor (THE_DEFAULT_BG_COLOR)
|
||||
myBgColor (THE_DEFAULT_BG_COLOR),
|
||||
mySwapInterval (theCaps->swapInterval)
|
||||
{
|
||||
myBgColor.rgb[0] = theCWindow.Background.r;
|
||||
myBgColor.rgb[1] = theCWindow.Background.g;
|
||||
@ -672,7 +673,7 @@ OpenGl_Window::OpenGl_Window (const Handle(OpenGl_GraphicDriver)& theDriver,
|
||||
myGlContext->Init ((Aspect_Drawable )aWindow, (Aspect_Display )aDisp, (Aspect_RenderingContext )aGContext, isCoreProfile);
|
||||
#endif
|
||||
myGlContext->Share (theShareCtx);
|
||||
|
||||
myGlContext->SetSwapInterval (mySwapInterval);
|
||||
Init();
|
||||
}
|
||||
|
||||
|
@ -98,6 +98,8 @@ protected:
|
||||
Standard_Integer myHeight; //!< window height in pixels
|
||||
TEL_COLOUR myBgColor; //!< background color
|
||||
|
||||
Standard_Integer mySwapInterval;//!< last assigned swap interval (VSync) for this window
|
||||
|
||||
public:
|
||||
|
||||
DEFINE_STANDARD_RTTI(OpenGl_Window) // Type definition
|
||||
|
@ -74,7 +74,8 @@ OpenGl_Window::OpenGl_Window (const Handle(OpenGl_GraphicDriver)& theDriver,
|
||||
#endif
|
||||
myWidth (theCWindow.dx),
|
||||
myHeight (theCWindow.dy),
|
||||
myBgColor (THE_DEFAULT_BG_COLOR)
|
||||
myBgColor (THE_DEFAULT_BG_COLOR),
|
||||
mySwapInterval (theCaps->swapInterval)
|
||||
{
|
||||
myBgColor.rgb[0] = theCWindow.Background.r;
|
||||
myBgColor.rgb[1] = theCWindow.Background.g;
|
||||
@ -217,6 +218,7 @@ OpenGl_Window::OpenGl_Window (const Handle(OpenGl_GraphicDriver)& theDriver,
|
||||
#endif
|
||||
|
||||
myGlContext->Share (theShareCtx);
|
||||
myGlContext->SetSwapInterval (mySwapInterval);
|
||||
Init();
|
||||
}
|
||||
|
||||
|
@ -706,6 +706,10 @@ bool OpenGl_Workspace::blitBuffers (OpenGl_FrameBuffer* theReadFbo,
|
||||
{
|
||||
return false;
|
||||
}
|
||||
else if (theReadFbo == theDrawFbo)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
// clear destination before blitting
|
||||
if (theDrawFbo != NULL
|
||||
@ -807,7 +811,7 @@ bool OpenGl_Workspace::blitBuffers (OpenGl_FrameBuffer* theReadFbo,
|
||||
// function : drawStereoPair
|
||||
// purpose :
|
||||
// =======================================================================
|
||||
void OpenGl_Workspace::drawStereoPair()
|
||||
void OpenGl_Workspace::drawStereoPair (const Graphic3d_CView& theCView)
|
||||
{
|
||||
OpenGl_FrameBuffer* aPair[2] =
|
||||
{
|
||||
@ -815,7 +819,8 @@ void OpenGl_Workspace::drawStereoPair()
|
||||
myImmediateSceneFbos[1]->IsValid() ? myImmediateSceneFbos[1].operator->() : NULL
|
||||
};
|
||||
if (aPair[0] == NULL
|
||||
|| aPair[1] == NULL)
|
||||
|| aPair[1] == NULL
|
||||
|| !myTransientDrawToFront)
|
||||
{
|
||||
aPair[0] = myMainSceneFbos[0]->IsValid() ? myMainSceneFbos[0].operator->() : NULL;
|
||||
aPair[1] = myMainSceneFbos[1]->IsValid() ? myMainSceneFbos[1].operator->() : NULL;
|
||||
@ -827,6 +832,27 @@ void OpenGl_Workspace::drawStereoPair()
|
||||
return;
|
||||
}
|
||||
|
||||
Standard_Boolean toReverse = theCView.RenderParams.ToReverseStereo;
|
||||
const Standard_Boolean isOddY = (theCView.DefWindow.top + theCView.DefWindow.dy) % 2 == 1;
|
||||
const Standard_Boolean isOddX = theCView.DefWindow.left % 2 == 1;
|
||||
if (isOddY
|
||||
&& (theCView.RenderParams.StereoMode == Graphic3d_StereoMode_RowInterlaced
|
||||
|| theCView.RenderParams.StereoMode == Graphic3d_StereoMode_ChessBoard))
|
||||
{
|
||||
toReverse = !toReverse;
|
||||
}
|
||||
if (isOddX
|
||||
&& (theCView.RenderParams.StereoMode == Graphic3d_StereoMode_ColumnInterlaced
|
||||
|| theCView.RenderParams.StereoMode == Graphic3d_StereoMode_ChessBoard))
|
||||
{
|
||||
toReverse = !toReverse;
|
||||
}
|
||||
|
||||
if (toReverse)
|
||||
{
|
||||
std::swap (aPair[0], aPair[1]);
|
||||
}
|
||||
|
||||
myGlContext->core20fwd->glDepthFunc (GL_ALWAYS);
|
||||
myGlContext->core20fwd->glDepthMask (GL_TRUE);
|
||||
myGlContext->core20fwd->glEnable (GL_DEPTH_TEST);
|
||||
@ -846,8 +872,71 @@ void OpenGl_Workspace::drawStereoPair()
|
||||
|
||||
const Handle(OpenGl_ShaderManager)& aManager = myGlContext->ShaderManager();
|
||||
if (myFullScreenQuad.IsValid()
|
||||
&& aManager->BindAnaglyphProgram())
|
||||
&& aManager->BindStereoProgram (theCView.RenderParams.StereoMode))
|
||||
{
|
||||
if (theCView.RenderParams.StereoMode == Graphic3d_StereoMode_Anaglyph)
|
||||
{
|
||||
OpenGl_Mat4 aFilterL, aFilterR;
|
||||
aFilterL.SetDiagonal (Graphic3d_Vec4 (0.0f, 0.0f, 0.0f, 0.0f));
|
||||
aFilterR.SetDiagonal (Graphic3d_Vec4 (0.0f, 0.0f, 0.0f, 0.0f));
|
||||
switch (theCView.RenderParams.AnaglyphFilter)
|
||||
{
|
||||
case Graphic3d_RenderingParams::Anaglyph_RedCyan_Simple:
|
||||
{
|
||||
aFilterL.SetRow (0, Graphic3d_Vec4 (1.0f, 0.0f, 0.0f, 0.0f));
|
||||
aFilterR.SetRow (1, Graphic3d_Vec4 (0.0f, 1.0f, 0.0f, 0.0f));
|
||||
aFilterR.SetRow (2, Graphic3d_Vec4 (0.0f, 0.0f, 1.0f, 0.0f));
|
||||
break;
|
||||
}
|
||||
case Graphic3d_RenderingParams::Anaglyph_RedCyan_Optimized:
|
||||
{
|
||||
aFilterL.SetRow (0, Graphic3d_Vec4 ( 0.4154f, 0.4710f, 0.16666667f, 0.0f));
|
||||
aFilterL.SetRow (1, Graphic3d_Vec4 (-0.0458f, -0.0484f, -0.0257f, 0.0f));
|
||||
aFilterL.SetRow (2, Graphic3d_Vec4 (-0.0547f, -0.0615f, 0.0128f, 0.0f));
|
||||
aFilterL.SetRow (3, Graphic3d_Vec4 ( 0.0f, 0.0f, 0.0f, 0.0f));
|
||||
aFilterR.SetRow (0, Graphic3d_Vec4 (-0.01090909f, -0.03636364f, -0.00606061f, 0.0f));
|
||||
aFilterR.SetRow (1, Graphic3d_Vec4 ( 0.37560000f, 0.73333333f, 0.01111111f, 0.0f));
|
||||
aFilterR.SetRow (2, Graphic3d_Vec4 (-0.06510000f, -0.12870000f, 1.29710000f, 0.0f));
|
||||
aFilterR.SetRow (3, Graphic3d_Vec4 ( 0.0f, 0.0f, 0.0f, 0.0f));
|
||||
break;
|
||||
}
|
||||
case Graphic3d_RenderingParams::Anaglyph_YellowBlue_Simple:
|
||||
{
|
||||
aFilterL.SetRow (0, Graphic3d_Vec4 (1.0f, 0.0f, 0.0f, 0.0f));
|
||||
aFilterL.SetRow (1, Graphic3d_Vec4 (0.0f, 1.0f, 0.0f, 0.0f));
|
||||
aFilterR.SetRow (2, Graphic3d_Vec4 (0.0f, 0.0f, 1.0f, 0.0f));
|
||||
break;
|
||||
}
|
||||
case Graphic3d_RenderingParams::Anaglyph_YellowBlue_Optimized:
|
||||
{
|
||||
aFilterL.SetRow (0, Graphic3d_Vec4 ( 1.062f, -0.205f, 0.299f, 0.0f));
|
||||
aFilterL.SetRow (1, Graphic3d_Vec4 (-0.026f, 0.908f, 0.068f, 0.0f));
|
||||
aFilterL.SetRow (2, Graphic3d_Vec4 (-0.038f, -0.173f, 0.022f, 0.0f));
|
||||
aFilterL.SetRow (3, Graphic3d_Vec4 ( 0.0f, 0.0f, 0.0f, 0.0f));
|
||||
aFilterR.SetRow (0, Graphic3d_Vec4 (-0.016f, -0.123f, -0.017f, 0.0f));
|
||||
aFilterR.SetRow (1, Graphic3d_Vec4 ( 0.006f, 0.062f, -0.017f, 0.0f));
|
||||
aFilterR.SetRow (2, Graphic3d_Vec4 ( 0.094f, 0.185f, 0.911f, 0.0f));
|
||||
aFilterR.SetRow (3, Graphic3d_Vec4 ( 0.0f, 0.0f, 0.0f, 0.0f));
|
||||
break;
|
||||
}
|
||||
case Graphic3d_RenderingParams::Anaglyph_GreenMagenta_Simple:
|
||||
{
|
||||
aFilterR.SetRow (0, Graphic3d_Vec4 (1.0f, 0.0f, 0.0f, 0.0f));
|
||||
aFilterL.SetRow (1, Graphic3d_Vec4 (0.0f, 1.0f, 0.0f, 0.0f));
|
||||
aFilterR.SetRow (2, Graphic3d_Vec4 (0.0f, 0.0f, 1.0f, 0.0f));
|
||||
break;
|
||||
}
|
||||
case Graphic3d_RenderingParams::Anaglyph_UserDefined:
|
||||
{
|
||||
aFilterL = theCView.RenderParams.AnaglyphLeft;
|
||||
aFilterR = theCView.RenderParams.AnaglyphRight;
|
||||
break;
|
||||
}
|
||||
}
|
||||
myGlContext->ActiveProgram()->SetUniform (myGlContext, "uMultL", aFilterL);
|
||||
myGlContext->ActiveProgram()->SetUniform (myGlContext, "uMultR", aFilterR);
|
||||
}
|
||||
|
||||
aPair[0]->ColorTexture()->Bind (myGlContext, GL_TEXTURE0 + 0);
|
||||
aPair[1]->ColorTexture()->Bind (myGlContext, GL_TEXTURE0 + 1);
|
||||
myFullScreenQuad.BindVertexAttrib (myGlContext, 0);
|
||||
@ -883,8 +972,17 @@ void OpenGl_Workspace::Redraw (const Graphic3d_CView& theCView,
|
||||
return;
|
||||
}
|
||||
|
||||
if (mySwapInterval != myGlContext->caps->swapInterval)
|
||||
{
|
||||
mySwapInterval = myGlContext->caps->swapInterval;
|
||||
myGlContext->SetSwapInterval (mySwapInterval);
|
||||
}
|
||||
|
||||
++myFrameCounter;
|
||||
myIsCullingEnabled = theCView.IsCullingEnabled;
|
||||
const Graphic3d_StereoMode aStereoMode = theCView.RenderParams.StereoMode;
|
||||
const Handle(Graphic3d_Camera)& aCamera = myView->Camera();
|
||||
Graphic3d_Camera::Projection aProjectType = aCamera->ProjectionType();
|
||||
|
||||
// release pending GL resources
|
||||
myGlContext->ReleaseDelayed();
|
||||
@ -908,7 +1006,7 @@ void OpenGl_Workspace::Redraw (const Graphic3d_CView& theCView,
|
||||
}
|
||||
|
||||
if (myHasFboBlit
|
||||
&& myTransientDrawToFront)
|
||||
&& (myTransientDrawToFront || aProjectType == Graphic3d_Camera::Projection_Stereo))
|
||||
{
|
||||
if (myMainSceneFbos[0]->GetVPSizeX() != aSizeX
|
||||
|| myMainSceneFbos[0]->GetVPSizeY() != aSizeY)
|
||||
@ -933,35 +1031,29 @@ void OpenGl_Workspace::Redraw (const Graphic3d_CView& theCView,
|
||||
myImmediateSceneFbos[1]->ChangeViewport (0, 0);
|
||||
}
|
||||
|
||||
// draw entire frame using normal OpenGL pipeline
|
||||
const Handle(Graphic3d_Camera)& aCamera = myView->Camera();
|
||||
Graphic3d_Camera::Projection aProjectType = aCamera->ProjectionType();
|
||||
if (aProjectType == Graphic3d_Camera::Projection_Stereo)
|
||||
if (aProjectType == Graphic3d_Camera::Projection_Stereo
|
||||
&& myMainSceneFbos[0]->IsValid())
|
||||
{
|
||||
if (aFrameBuffer != NULL
|
||||
|| !myGlContext->IsRender())
|
||||
myMainSceneFbos[1]->InitLazy (myGlContext, aSizeX, aSizeY);
|
||||
if (!myMainSceneFbos[1]->IsValid())
|
||||
{
|
||||
// implicitly switch to mono camera for image dump
|
||||
// no enough memory?
|
||||
aProjectType = Graphic3d_Camera::Projection_Perspective;
|
||||
}
|
||||
else if (myMainSceneFbos[0]->IsValid())
|
||||
else if (!myTransientDrawToFront)
|
||||
{
|
||||
myMainSceneFbos[1]->InitLazy (myGlContext, aSizeX, aSizeY);
|
||||
if (!myMainSceneFbos[1]->IsValid())
|
||||
//
|
||||
}
|
||||
else if (!myGlContext->HasStereoBuffers()
|
||||
|| aStereoMode != Graphic3d_StereoMode_QuadBuffer)
|
||||
{
|
||||
myImmediateSceneFbos[0]->InitLazy (myGlContext, aSizeX, aSizeY);
|
||||
myImmediateSceneFbos[1]->InitLazy (myGlContext, aSizeX, aSizeY);
|
||||
if (!myImmediateSceneFbos[0]->IsValid()
|
||||
|| !myImmediateSceneFbos[1]->IsValid())
|
||||
{
|
||||
// no enough memory?
|
||||
aProjectType = Graphic3d_Camera::Projection_Perspective;
|
||||
}
|
||||
else if (!myGlContext->HasStereoBuffers())
|
||||
{
|
||||
myImmediateSceneFbos[0]->InitLazy (myGlContext, aSizeX, aSizeY);
|
||||
myImmediateSceneFbos[1]->InitLazy (myGlContext, aSizeX, aSizeY);
|
||||
if (!myImmediateSceneFbos[0]->IsValid()
|
||||
|| !myImmediateSceneFbos[1]->IsValid())
|
||||
{
|
||||
aProjectType = Graphic3d_Camera::Projection_Perspective;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -978,23 +1070,40 @@ void OpenGl_Workspace::Redraw (const Graphic3d_CView& theCView,
|
||||
myImmediateSceneFbos[1]->IsValid() ? myImmediateSceneFbos[1].operator->() : NULL
|
||||
};
|
||||
|
||||
if (!myTransientDrawToFront)
|
||||
{
|
||||
anImmFbos[0] = aMainFbos[0];
|
||||
anImmFbos[1] = aMainFbos[1];
|
||||
}
|
||||
else if (aStereoMode == Graphic3d_StereoMode_SoftPageFlip
|
||||
|| aStereoMode == Graphic3d_StereoMode_QuadBuffer)
|
||||
{
|
||||
anImmFbos[0] = NULL;
|
||||
anImmFbos[1] = NULL;
|
||||
}
|
||||
|
||||
#if !defined(GL_ES_VERSION_2_0)
|
||||
myGlContext->SetReadDrawBuffer (GL_BACK_LEFT);
|
||||
myGlContext->SetReadDrawBuffer (aStereoMode == Graphic3d_StereoMode_QuadBuffer ? GL_BACK_LEFT : GL_BACK);
|
||||
#endif
|
||||
redraw1 (theCView, theCUnderLayer, theCOverLayer,
|
||||
aMainFbos[0], Graphic3d_Camera::Projection_MonoLeftEye);
|
||||
myBackBufferRestored = Standard_True;
|
||||
myIsImmediateDrawn = Standard_False;
|
||||
#if !defined(GL_ES_VERSION_2_0)
|
||||
myGlContext->SetReadDrawBuffer (GL_BACK_LEFT);
|
||||
myGlContext->SetReadDrawBuffer (aStereoMode == Graphic3d_StereoMode_QuadBuffer ? GL_BACK_LEFT : GL_BACK);
|
||||
#endif
|
||||
if (!redrawImmediate (theCView, theCOverLayer, theCUnderLayer, aMainFbos[0], aProjectType, anImmFbos[0]))
|
||||
{
|
||||
toSwap = false;
|
||||
}
|
||||
else if (aStereoMode == Graphic3d_StereoMode_SoftPageFlip
|
||||
&& toSwap)
|
||||
{
|
||||
myGlContext->SwapBuffers();
|
||||
}
|
||||
|
||||
#if !defined(GL_ES_VERSION_2_0)
|
||||
myGlContext->SetReadDrawBuffer (GL_BACK_RIGHT);
|
||||
myGlContext->SetReadDrawBuffer (aStereoMode == Graphic3d_StereoMode_QuadBuffer ? GL_BACK_RIGHT : GL_BACK);
|
||||
#endif
|
||||
redraw1 (theCView, theCUnderLayer, theCOverLayer,
|
||||
aMainFbos[1], Graphic3d_Camera::Projection_MonoRightEye);
|
||||
@ -1008,7 +1117,7 @@ void OpenGl_Workspace::Redraw (const Graphic3d_CView& theCView,
|
||||
if (anImmFbos[0] != NULL)
|
||||
{
|
||||
bindDefaultFbo (aFrameBuffer);
|
||||
drawStereoPair();
|
||||
drawStereoPair (theCView);
|
||||
}
|
||||
}
|
||||
else
|
||||
@ -1227,6 +1336,7 @@ void OpenGl_Workspace::RedrawImmediate (const Graphic3d_CView& theCView,
|
||||
aFrameBuffer = myGlContext->DefaultFrameBuffer().operator->();
|
||||
}
|
||||
|
||||
const Graphic3d_StereoMode aStereoMode = theCView.RenderParams.StereoMode;
|
||||
if (aProjectType == Graphic3d_Camera::Projection_Stereo)
|
||||
{
|
||||
if (aFrameBuffer != NULL)
|
||||
@ -1266,6 +1376,12 @@ void OpenGl_Workspace::RedrawImmediate (const Graphic3d_CView& theCView,
|
||||
myImmediateSceneFbos[0]->IsValid() ? myImmediateSceneFbos[0].operator->() : NULL,
|
||||
myImmediateSceneFbos[1]->IsValid() ? myImmediateSceneFbos[1].operator->() : NULL
|
||||
};
|
||||
if (aStereoMode == Graphic3d_StereoMode_SoftPageFlip
|
||||
|| aStereoMode == Graphic3d_StereoMode_QuadBuffer)
|
||||
{
|
||||
anImmFbos[0] = NULL;
|
||||
anImmFbos[1] = NULL;
|
||||
}
|
||||
|
||||
if (myGlContext->arbFBO != NULL)
|
||||
{
|
||||
@ -1274,7 +1390,7 @@ void OpenGl_Workspace::RedrawImmediate (const Graphic3d_CView& theCView,
|
||||
#if !defined(GL_ES_VERSION_2_0)
|
||||
if (anImmFbos[0] == NULL)
|
||||
{
|
||||
myGlContext->SetReadDrawBuffer (GL_BACK_LEFT);
|
||||
myGlContext->SetReadDrawBuffer (aStereoMode == Graphic3d_StereoMode_QuadBuffer ? GL_BACK_LEFT : GL_BACK);
|
||||
}
|
||||
#endif
|
||||
toSwap = redrawImmediate (theCView, theCUnderLayer, theCOverLayer,
|
||||
@ -1282,6 +1398,12 @@ void OpenGl_Workspace::RedrawImmediate (const Graphic3d_CView& theCView,
|
||||
Graphic3d_Camera::Projection_MonoLeftEye,
|
||||
anImmFbos[0],
|
||||
Standard_True) || toSwap;
|
||||
if (aStereoMode == Graphic3d_StereoMode_SoftPageFlip
|
||||
&& toSwap
|
||||
&& !myGlContext->caps->buffersNoSwap)
|
||||
{
|
||||
myGlContext->SwapBuffers();
|
||||
}
|
||||
|
||||
if (myGlContext->arbFBO != NULL)
|
||||
{
|
||||
@ -1290,7 +1412,7 @@ void OpenGl_Workspace::RedrawImmediate (const Graphic3d_CView& theCView,
|
||||
#if !defined(GL_ES_VERSION_2_0)
|
||||
if (anImmFbos[1] == NULL)
|
||||
{
|
||||
myGlContext->SetReadDrawBuffer (GL_BACK_RIGHT);
|
||||
myGlContext->SetReadDrawBuffer (aStereoMode == Graphic3d_StereoMode_QuadBuffer ? GL_BACK_RIGHT : GL_BACK);
|
||||
}
|
||||
#endif
|
||||
toSwap = redrawImmediate (theCView, theCUnderLayer, theCOverLayer,
|
||||
@ -1301,7 +1423,7 @@ void OpenGl_Workspace::RedrawImmediate (const Graphic3d_CView& theCView,
|
||||
if (anImmFbos[0] != NULL)
|
||||
{
|
||||
bindDefaultFbo (aFrameBuffer);
|
||||
drawStereoPair();
|
||||
drawStereoPair (theCView);
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -295,7 +295,7 @@ protected:
|
||||
void bindDefaultFbo (OpenGl_FrameBuffer* theCustomFbo = NULL);
|
||||
|
||||
//! Blend together views pair into stereo image.
|
||||
void drawStereoPair();
|
||||
void drawStereoPair (const Graphic3d_CView& theCView);
|
||||
|
||||
//! Blit snapshot containing main scene (myMainSceneFbos or BackBuffer)
|
||||
//! into presentation buffer (myMainSceneFbos -> offscreen FBO or myMainSceneFbos -> BackBuffer or BackBuffer -> FrontBuffer),
|
||||
|
@ -12,3 +12,4 @@ V3d_View_5.cxx
|
||||
V3d_Plane.hxx
|
||||
V3d_Plane.cxx
|
||||
V3d_ListOfTransient.hxx
|
||||
V3d_StereoDumpOptions.hxx
|
||||
|
@ -156,16 +156,7 @@ is
|
||||
-- TOBM_ALWAYS_DISPLAYED force display of back faces
|
||||
-- TOBM_NEVER_DISPLAYED disable display of back faces
|
||||
|
||||
enumeration StereoDumpOptions is
|
||||
SDO_MONO,
|
||||
SDO_LEFT_EYE,
|
||||
SDO_RIGHT_EYE
|
||||
end StereoDumpOptions;
|
||||
---Purpose : Options to be used with image dumping.
|
||||
--
|
||||
-- SDO_MONO dump monographic projection for stereo camera
|
||||
-- SDO_LEFT_EYE dump left eye projection for stereo camera
|
||||
-- SDO_RIGHT_EYE dump right eye projection for stereo camera
|
||||
primitive StereoDumpOptions;
|
||||
|
||||
------------------------
|
||||
---Category: The classes
|
||||
|
29
src/V3d/V3d_StereoDumpOptions.hxx
Normal file
29
src/V3d/V3d_StereoDumpOptions.hxx
Normal file
@ -0,0 +1,29 @@
|
||||
// Created on: 2015-06-05
|
||||
// Created by: Kirill Gavrilov
|
||||
// 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 _V3d_StereoDumpOptions_HeaderFile
|
||||
#define _V3d_StereoDumpOptions_HeaderFile
|
||||
|
||||
//! Options to be used with image dumping.
|
||||
//! Notice that the value will have no effect with disabled stereo output.
|
||||
enum V3d_StereoDumpOptions
|
||||
{
|
||||
V3d_SDO_MONO, //!< ignore stereo mode and dump monographic projection for stereo camera
|
||||
V3d_SDO_LEFT_EYE, //!< dump only left eye projection for stereo camera
|
||||
V3d_SDO_RIGHT_EYE, //!< dump only right eye projection for stereo camera
|
||||
V3d_SDO_BLENDED //!< dump blended pair specific to the active device output Graphic3d_StereoMode (result will be undefined for modes like Graphic3d_StereoMode_QuadBuffer)
|
||||
};
|
||||
|
||||
#endif // _V3d_StereoDumpOptions_HeaderFile
|
@ -2872,17 +2872,25 @@ Standard_Boolean V3d_View::ToPixMap (Image_PixMap& theImage,
|
||||
{
|
||||
switch (theStereoOptions)
|
||||
{
|
||||
case V3d_SDO_MONO :
|
||||
case V3d_SDO_MONO:
|
||||
{
|
||||
myCamera->SetProjectionType (Graphic3d_Camera::Projection_Perspective);
|
||||
break;
|
||||
|
||||
case V3d_SDO_LEFT_EYE :
|
||||
}
|
||||
case V3d_SDO_LEFT_EYE:
|
||||
{
|
||||
myCamera->SetProjectionType (Graphic3d_Camera::Projection_MonoLeftEye);
|
||||
break;
|
||||
|
||||
case V3d_SDO_RIGHT_EYE :
|
||||
}
|
||||
case V3d_SDO_RIGHT_EYE:
|
||||
{
|
||||
myCamera->SetProjectionType (Graphic3d_Camera::Projection_MonoRightEye);
|
||||
break;
|
||||
}
|
||||
case V3d_SDO_BLENDED:
|
||||
{
|
||||
break; // dump as is
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -759,6 +759,14 @@ static int VSelPrecision(Draw_Interpretor& di, Standard_Integer argc, const char
|
||||
return 0;
|
||||
}
|
||||
|
||||
//! Auxiliary enumeration
|
||||
enum ViewerTest_StereoPair
|
||||
{
|
||||
ViewerTest_SP_Single,
|
||||
ViewerTest_SP_SideBySide,
|
||||
ViewerTest_SP_OverUnder
|
||||
};
|
||||
|
||||
//==============================================================================
|
||||
//function : VDump
|
||||
//purpose : To dump the active view snapshot to image file
|
||||
@ -777,42 +785,108 @@ static Standard_Integer VDump (Draw_Interpretor& theDI,
|
||||
Standard_CString aFilePath = theArgVec[anArgIter++];
|
||||
Graphic3d_BufferType aBufferType = Graphic3d_BT_RGB;
|
||||
V3d_StereoDumpOptions aStereoOpts = V3d_SDO_MONO;
|
||||
ViewerTest_StereoPair aStereoPair = ViewerTest_SP_Single;
|
||||
Standard_Integer aWidth = 0;
|
||||
Standard_Integer aHeight = 0;
|
||||
for (; anArgIter < theArgNb; ++anArgIter)
|
||||
{
|
||||
TCollection_AsciiString anArg (theArgVec[anArgIter]);
|
||||
anArg.LowerCase();
|
||||
if (anArg == "rgba")
|
||||
if (anArg == "-buffer")
|
||||
{
|
||||
if (++anArgIter >= theArgNb)
|
||||
{
|
||||
std::cout << "Error: wrong syntax at '" << anArg << "'\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
TCollection_AsciiString aBufArg (theArgVec[anArgIter]);
|
||||
aBufArg.LowerCase();
|
||||
if (aBufArg == "rgba")
|
||||
{
|
||||
aBufferType = Graphic3d_BT_RGBA;
|
||||
}
|
||||
else if (aBufArg == "rgb")
|
||||
{
|
||||
aBufferType = Graphic3d_BT_RGB;
|
||||
}
|
||||
else if (aBufArg == "depth")
|
||||
{
|
||||
aBufferType = Graphic3d_BT_Depth;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << "Error: unknown buffer '" << aBufArg << "'\n";
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
else if (anArg == "-stereo")
|
||||
{
|
||||
if (++anArgIter >= theArgNb)
|
||||
{
|
||||
std::cout << "Error: wrong syntax at '" << anArg << "'\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
TCollection_AsciiString aStereoArg (theArgVec[anArgIter]);
|
||||
aStereoArg.LowerCase();
|
||||
if (aStereoArg == "l"
|
||||
|| aStereoArg == "left")
|
||||
{
|
||||
aStereoOpts = V3d_SDO_LEFT_EYE;
|
||||
}
|
||||
else if (aStereoArg == "r"
|
||||
|| aStereoArg == "right")
|
||||
{
|
||||
aStereoOpts = V3d_SDO_RIGHT_EYE;
|
||||
}
|
||||
else if (aStereoArg == "mono")
|
||||
{
|
||||
aStereoOpts = V3d_SDO_MONO;
|
||||
}
|
||||
else if (aStereoArg == "blended"
|
||||
|| aStereoArg == "blend"
|
||||
|| aStereoArg == "stereo")
|
||||
{
|
||||
aStereoOpts = V3d_SDO_BLENDED;
|
||||
}
|
||||
else if (aStereoArg == "sbs"
|
||||
|| aStereoArg == "sidebyside")
|
||||
{
|
||||
aStereoPair = ViewerTest_SP_SideBySide;
|
||||
}
|
||||
else if (aStereoArg == "ou"
|
||||
|| aStereoArg == "overunder")
|
||||
{
|
||||
aStereoPair = ViewerTest_SP_OverUnder;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << "Error: unknown stereo format '" << aStereoArg << "'\n";
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
else if (anArg == "-rgba"
|
||||
|| anArg == "rgba")
|
||||
{
|
||||
aBufferType = Graphic3d_BT_RGBA;
|
||||
}
|
||||
else if (anArg == "rgb")
|
||||
else if (anArg == "-rgb"
|
||||
|| anArg == "rgb")
|
||||
{
|
||||
aBufferType = Graphic3d_BT_RGB;
|
||||
}
|
||||
else if (anArg == "depth")
|
||||
else if (anArg == "-depth"
|
||||
|| anArg == "depth")
|
||||
{
|
||||
aBufferType = Graphic3d_BT_Depth;
|
||||
}
|
||||
else if (anArg == "l"
|
||||
|| anArg == "left")
|
||||
|
||||
else if (anArg == "-width"
|
||||
|| anArg == "width"
|
||||
|| anArg == "sizex")
|
||||
{
|
||||
aStereoOpts = V3d_SDO_LEFT_EYE;
|
||||
}
|
||||
else if (anArg == "r"
|
||||
|| anArg == "right")
|
||||
{
|
||||
aStereoOpts = V3d_SDO_RIGHT_EYE;
|
||||
}
|
||||
else if (anArg == "mono")
|
||||
{
|
||||
aStereoOpts = V3d_SDO_MONO;
|
||||
}
|
||||
else if (anArg == "w"
|
||||
|| anArg == "width")
|
||||
{
|
||||
if (aWidth != 0)
|
||||
if (aWidth != 0)
|
||||
{
|
||||
std::cout << "Error: wrong syntax at " << theArgVec[anArgIter] << "\n";
|
||||
return 1;
|
||||
@ -824,38 +898,22 @@ static Standard_Integer VDump (Draw_Interpretor& theDI,
|
||||
}
|
||||
aWidth = Draw::Atoi (theArgVec[anArgIter]);
|
||||
}
|
||||
else if (anArg == "h"
|
||||
|| anArg == "height")
|
||||
else if (anArg == "-height"
|
||||
|| anArg == "height"
|
||||
|| anArg == "-sizey")
|
||||
{
|
||||
if (aHeight != 0)
|
||||
{
|
||||
std::cout << "Error: wrong syntax at " << theArgVec[anArgIter] << "\n";
|
||||
return 1;
|
||||
}
|
||||
if (++anArgIter >= theArgNb)
|
||||
else if (++anArgIter >= theArgNb)
|
||||
{
|
||||
std::cout << "Error: integer value is expected right after 'height'\n";
|
||||
return 1;
|
||||
}
|
||||
aHeight = Draw::Atoi (theArgVec[anArgIter]);
|
||||
}
|
||||
else if (anArg.IsIntegerValue())
|
||||
{
|
||||
// compatibility with old syntax
|
||||
if (aWidth != 0
|
||||
|| aHeight != 0)
|
||||
{
|
||||
std::cout << "Error: wrong syntax at " << theArgVec[anArgIter] << "\n";
|
||||
return 1;
|
||||
}
|
||||
else if (++anArgIter >= theArgNb)
|
||||
{
|
||||
std::cout << "Error: height value is expected right after width\n";
|
||||
return 1;
|
||||
}
|
||||
aWidth = Draw::Atoi (theArgVec[anArgIter - 1]);
|
||||
aHeight = Draw::Atoi (theArgVec[anArgIter]);
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << "Error: unknown argument '" << theArgVec[anArgIter] << "'\n";
|
||||
@ -878,33 +936,82 @@ static Standard_Integer VDump (Draw_Interpretor& theDI,
|
||||
|
||||
if (aWidth <= 0 || aHeight <= 0)
|
||||
{
|
||||
if (aStereoOpts != V3d_SDO_MONO)
|
||||
{
|
||||
aView->Window()->Size (aWidth, aHeight);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!aView->Dump (aFilePath, aBufferType))
|
||||
{
|
||||
theDI << "Fail: view dump failed!\n";
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
aView->Window()->Size (aWidth, aHeight);
|
||||
}
|
||||
|
||||
Image_AlienPixMap aPixMap;
|
||||
if (!aView->ToPixMap (aPixMap, aWidth, aHeight, aBufferType, Standard_True, aStereoOpts))
|
||||
|
||||
bool isBigEndian = Image_PixMap::IsBigEndianHost();
|
||||
Image_PixMap::ImgFormat aFormat = Image_PixMap::ImgUNKNOWN;
|
||||
switch (aBufferType)
|
||||
{
|
||||
theDI << "Fail: view dump failed!\n";
|
||||
return 0;
|
||||
case Graphic3d_BT_RGB: aFormat = isBigEndian ? Image_PixMap::ImgRGB : Image_PixMap::ImgBGR; break;
|
||||
case Graphic3d_BT_RGBA: aFormat = isBigEndian ? Image_PixMap::ImgRGBA : Image_PixMap::ImgBGRA; break;
|
||||
case Graphic3d_BT_Depth: aFormat = Image_PixMap::ImgGrayF; break;
|
||||
}
|
||||
|
||||
if (aPixMap.SizeX() != Standard_Size(aWidth)
|
||||
|| aPixMap.SizeY() != Standard_Size(aHeight))
|
||||
switch (aStereoPair)
|
||||
{
|
||||
theDI << "Fail: dumped dimensions " << (Standard_Integer )aPixMap.SizeX() << "x" << (Standard_Integer )aPixMap.SizeY()
|
||||
<< " are lesser than requested " << aWidth << "x" << aHeight << "\n";
|
||||
case ViewerTest_SP_Single:
|
||||
{
|
||||
if (!aView->ToPixMap (aPixMap, aWidth, aHeight, aBufferType, Standard_True, aStereoOpts))
|
||||
{
|
||||
theDI << "Fail: view dump failed!\n";
|
||||
return 0;
|
||||
}
|
||||
else if (aPixMap.SizeX() != Standard_Size(aWidth)
|
||||
|| aPixMap.SizeY() != Standard_Size(aHeight))
|
||||
{
|
||||
theDI << "Fail: dumped dimensions " << (Standard_Integer )aPixMap.SizeX() << "x" << (Standard_Integer )aPixMap.SizeY()
|
||||
<< " are lesser than requested " << aWidth << "x" << aHeight << "\n";
|
||||
}
|
||||
break;
|
||||
}
|
||||
case ViewerTest_SP_SideBySide:
|
||||
{
|
||||
if (!aPixMap.InitZero (aFormat, aWidth * 2, aHeight))
|
||||
{
|
||||
theDI << "Fail: not enough memory for image allocation!\n";
|
||||
return 0;
|
||||
}
|
||||
|
||||
Image_PixMap aPixMapL, aPixMapR;
|
||||
aPixMapL.InitWrapper (aPixMap.Format(), aPixMap.ChangeData(),
|
||||
aWidth, aHeight, aPixMap.SizeRowBytes());
|
||||
aPixMapR.InitWrapper (aPixMap.Format(), aPixMap.ChangeData() + aPixMap.SizePixelBytes() * aWidth,
|
||||
aWidth, aHeight, aPixMap.SizeRowBytes());
|
||||
if (!aView->ToPixMap (aPixMapL, aWidth, aHeight, aBufferType, Standard_True, V3d_SDO_LEFT_EYE)
|
||||
|| !aView->ToPixMap (aPixMapR, aWidth, aHeight, aBufferType, Standard_True, V3d_SDO_RIGHT_EYE)
|
||||
)
|
||||
{
|
||||
theDI << "Fail: view dump failed!\n";
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case ViewerTest_SP_OverUnder:
|
||||
{
|
||||
if (!aPixMap.InitZero (aFormat, aWidth, aHeight * 2))
|
||||
{
|
||||
theDI << "Fail: not enough memory for image allocation!\n";
|
||||
return 0;
|
||||
}
|
||||
|
||||
Image_PixMap aPixMapL, aPixMapR;
|
||||
aPixMapL.InitWrapper (aFormat, aPixMap.ChangeData(),
|
||||
aWidth, aHeight, aPixMap.SizeRowBytes());
|
||||
aPixMapR.InitWrapper (aFormat, aPixMap.ChangeData() + aPixMap.SizeRowBytes() * aHeight,
|
||||
aWidth, aHeight, aPixMap.SizeRowBytes());
|
||||
if (!aView->ToPixMap (aPixMapL, aWidth, aHeight, aBufferType, Standard_True, V3d_SDO_LEFT_EYE)
|
||||
|| !aView->ToPixMap (aPixMapR, aWidth, aHeight, aBufferType, Standard_True, V3d_SDO_RIGHT_EYE))
|
||||
{
|
||||
theDI << "Fail: view dump failed!\n";
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!aPixMap.Save (aFilePath))
|
||||
{
|
||||
theDI << "Fail: image can not be saved!\n";
|
||||
@ -912,7 +1019,6 @@ static Standard_Integer VDump (Draw_Interpretor& theDI,
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
//==============================================================================
|
||||
//function : Displays,Erase...
|
||||
//purpose :
|
||||
@ -5348,16 +5454,16 @@ void ViewerTest::Commands(Draw_Interpretor& theCommands)
|
||||
"Lists all objects displayed in 3D viewer",
|
||||
__FILE__,VDir,group);
|
||||
|
||||
#ifdef HAVE_FREEIMAGE
|
||||
#define DUMP_FORMATS "{png|bmp|jpg|gif}"
|
||||
#else
|
||||
#define DUMP_FORMATS "{ppm}"
|
||||
#endif
|
||||
theCommands.Add("vdump",
|
||||
#ifdef HAVE_FREEIMAGE
|
||||
"vdump <filename>.{png|bmp|jpg|gif} [rgb|rgba|depth=rgb] [mono|left|right=mono]"
|
||||
"\n\t\t: [width Width=0 height Height=0]"
|
||||
"\n\t\t: Dumps content of the active view into PNG, BMP, JPEG or GIF file",
|
||||
#else
|
||||
"vdump <filename>.{ppm} [rgb|rgba|depth=rgb] [mono|left|right=mono]"
|
||||
"\n\t\t: [width Width=0 height Height=0]"
|
||||
"\n\t\t: Dumps content of the active view into PPM image file",
|
||||
#endif
|
||||
"vdump <filename>." DUMP_FORMATS " [-width Width -height Height]"
|
||||
"\n\t\t: [-buffer rgb|rgba|depth=rgb]"
|
||||
"\n\t\t: [-stereo mono|left|right|blend|sideBySide|overUnder=mono]"
|
||||
"\n\t\t: Dumps content of the active view into image file",
|
||||
__FILE__,VDump,group);
|
||||
|
||||
theCommands.Add("vsub", "vsub 0/1 (off/on) [obj] : Subintensity(on/off) of selected objects",
|
||||
|
@ -1512,6 +1512,24 @@ void VT_ProcessKeyPress (const char* buf_ret)
|
||||
{
|
||||
ViewerTest::GetAISContext()->HilightPreviousDetected(ViewerTest::CurrentView());
|
||||
}
|
||||
else if (!strcasecmp (buf_ret, "/"))
|
||||
{
|
||||
Handle(Graphic3d_Camera) aCamera = aView->Camera();
|
||||
if (aCamera->IsStereo())
|
||||
{
|
||||
aCamera->SetIOD (aCamera->GetIODType(), aCamera->IOD() - 0.01);
|
||||
aView->Redraw();
|
||||
}
|
||||
}
|
||||
else if (!strcasecmp (buf_ret, "*"))
|
||||
{
|
||||
Handle(Graphic3d_Camera) aCamera = aView->Camera();
|
||||
if (aCamera->IsStereo())
|
||||
{
|
||||
aCamera->SetIOD (aCamera->GetIODType(), aCamera->IOD() + 0.01);
|
||||
aView->Redraw();
|
||||
}
|
||||
}
|
||||
else if (*buf_ret == THE_KEY_DELETE)
|
||||
{
|
||||
Handle(AIS_InteractiveContext) aCtx = ViewerTest::GetAISContext();
|
||||
@ -1983,8 +2001,12 @@ static LRESULT WINAPI ViewerWindowProc( HWND hwnd,
|
||||
LPARAM lParam )
|
||||
{
|
||||
static int Up = 1;
|
||||
const Handle(V3d_View)& aView = ViewerTest::CurrentView();
|
||||
if (aView.IsNull())
|
||||
{
|
||||
return DefWindowProc( hwnd, Msg, wParam, lParam );
|
||||
}
|
||||
|
||||
if ( !ViewerTest::CurrentView().IsNull() ) {
|
||||
PAINTSTRUCT ps;
|
||||
|
||||
switch( Msg ) {
|
||||
@ -1997,6 +2019,20 @@ static LRESULT WINAPI ViewerWindowProc( HWND hwnd,
|
||||
case WM_SIZE:
|
||||
VT_ProcessConfigure();
|
||||
break;
|
||||
case WM_MOVE:
|
||||
case WM_MOVING:
|
||||
case WM_SIZING:
|
||||
switch (aView->RenderingParams().StereoMode)
|
||||
{
|
||||
case Graphic3d_StereoMode_RowInterlaced:
|
||||
case Graphic3d_StereoMode_ColumnInterlaced:
|
||||
case Graphic3d_StereoMode_ChessBoard:
|
||||
VT_ProcessConfigure(); // track window moves to reverse stereo pair
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case WM_KEYDOWN:
|
||||
if ((wParam != VK_SHIFT) && (wParam != VK_CONTROL))
|
||||
@ -2018,6 +2054,15 @@ static LRESULT WINAPI ViewerWindowProc( HWND hwnd,
|
||||
{
|
||||
c[0] = '.';
|
||||
}
|
||||
else if (wParam == VK_DIVIDE)
|
||||
{
|
||||
c[0] = '/';
|
||||
}
|
||||
// dot
|
||||
else if (wParam == VK_MULTIPLY)
|
||||
{
|
||||
c[0] = '*';
|
||||
}
|
||||
VT_ProcessKeyPress (c);
|
||||
}
|
||||
break;
|
||||
@ -2059,6 +2104,29 @@ static LRESULT WINAPI ViewerWindowProc( HWND hwnd,
|
||||
}
|
||||
break;
|
||||
|
||||
case WM_MOUSEWHEEL:
|
||||
{
|
||||
int aDelta = GET_WHEEL_DELTA_WPARAM (wParam);
|
||||
if (wParam & MK_CONTROL)
|
||||
{
|
||||
if (aView->Camera()->IsStereo())
|
||||
{
|
||||
Standard_Real aFocus = aView->Camera()->ZFocus() + (aDelta > 0 ? 0.05 : -0.05);
|
||||
if (aFocus > 0.2
|
||||
&& aFocus < 2.0)
|
||||
{
|
||||
aView->Camera()->SetZFocus (aView->Camera()->ZFocusType(), aFocus);
|
||||
aView->Redraw();
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
aView->Zoom (0, 0, aDelta / 40, aDelta / 40);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case WM_MOUSEMOVE:
|
||||
{
|
||||
//cout << "\t WM_MOUSEMOVE" << endl;
|
||||
@ -2120,9 +2188,6 @@ static LRESULT WINAPI ViewerWindowProc( HWND hwnd,
|
||||
return( DefWindowProc( hwnd, Msg, wParam, lParam ));
|
||||
}
|
||||
return 0L;
|
||||
}
|
||||
|
||||
return DefWindowProc( hwnd, Msg, wParam, lParam );
|
||||
}
|
||||
|
||||
|
||||
@ -5413,7 +5478,9 @@ static int VCaps (Draw_Interpretor& theDI,
|
||||
theDI << "Sprites: " << (aCaps->pntSpritesDisable ? "0" : "1") << "\n";
|
||||
theDI << "SoftMode:" << (aCaps->contextNoAccel ? "1" : "0") << "\n";
|
||||
theDI << "FFP: " << (aCaps->ffpEnable ? "1" : "0") << "\n";
|
||||
theDI << "VSync: " << aCaps->swapInterval << "\n";
|
||||
theDI << "Compatible:" << (aCaps->contextCompatible ? "1" : "0") << "\n";
|
||||
theDI << "Stereo: " << (aCaps->contextStereo ? "1" : "0") << "\n";
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -5427,6 +5494,17 @@ static int VCaps (Draw_Interpretor& theDI,
|
||||
{
|
||||
continue;
|
||||
}
|
||||
else if (anArgCase == "-vsync"
|
||||
|| anArgCase == "-swapinterval")
|
||||
{
|
||||
Standard_Boolean toEnable = Standard_True;
|
||||
if (++anArgIter < theArgNb
|
||||
&& !parseOnOff (theArgVec[anArgIter], toEnable))
|
||||
{
|
||||
--anArgIter;
|
||||
}
|
||||
aCaps->swapInterval = toEnable;
|
||||
}
|
||||
else if (anArgCase == "-ffp")
|
||||
{
|
||||
Standard_Boolean toEnable = Standard_True;
|
||||
@ -5511,6 +5589,17 @@ static int VCaps (Draw_Interpretor& theDI,
|
||||
aCaps->ffpEnable = Standard_False;
|
||||
}
|
||||
}
|
||||
else if (anArgCase == "-stereo"
|
||||
|| anArgCase == "-quadbuffer")
|
||||
{
|
||||
Standard_Boolean toEnable = Standard_True;
|
||||
if (++anArgIter < theArgNb
|
||||
&& !parseOnOff (theArgVec[anArgIter], toEnable))
|
||||
{
|
||||
--anArgIter;
|
||||
}
|
||||
aCaps->contextStereo = toEnable;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << "Error: unknown argument '" << anArg << "'\n";
|
||||
@ -7301,6 +7390,94 @@ static int VCamera (Draw_Interpretor& theDI,
|
||||
return 0;
|
||||
}
|
||||
|
||||
//! Parse stereo output mode
|
||||
inline Standard_Boolean parseStereoMode (Standard_CString theArg,
|
||||
Graphic3d_StereoMode& theMode)
|
||||
{
|
||||
TCollection_AsciiString aFlag (theArg);
|
||||
aFlag.LowerCase();
|
||||
if (aFlag == "quadbuffer")
|
||||
{
|
||||
theMode = Graphic3d_StereoMode_QuadBuffer;
|
||||
}
|
||||
else if (aFlag == "anaglyph")
|
||||
{
|
||||
theMode = Graphic3d_StereoMode_Anaglyph;
|
||||
}
|
||||
else if (aFlag == "row"
|
||||
|| aFlag == "rowinterlaced")
|
||||
{
|
||||
theMode = Graphic3d_StereoMode_RowInterlaced;
|
||||
}
|
||||
else if (aFlag == "col"
|
||||
|| aFlag == "colinterlaced"
|
||||
|| aFlag == "columninterlaced")
|
||||
{
|
||||
theMode = Graphic3d_StereoMode_ColumnInterlaced;
|
||||
}
|
||||
else if (aFlag == "chess"
|
||||
|| aFlag == "chessboard")
|
||||
{
|
||||
theMode = Graphic3d_StereoMode_ChessBoard;
|
||||
}
|
||||
else if (aFlag == "sbs"
|
||||
|| aFlag == "sidebyside")
|
||||
{
|
||||
theMode = Graphic3d_StereoMode_SideBySide;
|
||||
}
|
||||
else if (aFlag == "ou"
|
||||
|| aFlag == "overunder")
|
||||
{
|
||||
theMode = Graphic3d_StereoMode_OverUnder;
|
||||
}
|
||||
else if (aFlag == "pageflip"
|
||||
|| aFlag == "softpageflip")
|
||||
{
|
||||
theMode = Graphic3d_StereoMode_SoftPageFlip;
|
||||
}
|
||||
else
|
||||
{
|
||||
return Standard_False;
|
||||
}
|
||||
return Standard_True;
|
||||
}
|
||||
|
||||
//! Parse anaglyph filter
|
||||
inline Standard_Boolean parseAnaglyphFilter (Standard_CString theArg,
|
||||
Graphic3d_RenderingParams::Anaglyph& theFilter)
|
||||
{
|
||||
TCollection_AsciiString aFlag (theArg);
|
||||
aFlag.LowerCase();
|
||||
if (aFlag == "redcyansimple")
|
||||
{
|
||||
theFilter = Graphic3d_RenderingParams::Anaglyph_RedCyan_Simple;
|
||||
}
|
||||
else if (aFlag == "redcyan"
|
||||
|| aFlag == "redcyanoptimized")
|
||||
{
|
||||
theFilter = Graphic3d_RenderingParams::Anaglyph_RedCyan_Optimized;
|
||||
}
|
||||
else if (aFlag == "yellowbluesimple")
|
||||
{
|
||||
theFilter = Graphic3d_RenderingParams::Anaglyph_YellowBlue_Simple;
|
||||
}
|
||||
else if (aFlag == "yellowblue"
|
||||
|| aFlag == "yellowblueoptimized")
|
||||
{
|
||||
theFilter = Graphic3d_RenderingParams::Anaglyph_YellowBlue_Optimized;
|
||||
}
|
||||
else if (aFlag == "greenmagenta"
|
||||
|| aFlag == "greenmagentasimple")
|
||||
{
|
||||
theFilter = Graphic3d_RenderingParams::Anaglyph_GreenMagenta_Simple;
|
||||
}
|
||||
else
|
||||
{
|
||||
return Standard_False;
|
||||
}
|
||||
return Standard_True;
|
||||
}
|
||||
|
||||
//==============================================================================
|
||||
//function : VStereo
|
||||
//purpose :
|
||||
@ -7310,12 +7487,12 @@ static int VStereo (Draw_Interpretor& theDI,
|
||||
Standard_Integer theArgNb,
|
||||
const char** theArgVec)
|
||||
{
|
||||
Handle(V3d_View) aView = ViewerTest::CurrentView();
|
||||
if (theArgNb < 2)
|
||||
{
|
||||
Handle(V3d_View) aView = ViewerTest::CurrentView();
|
||||
if (aView.IsNull())
|
||||
{
|
||||
std::cerr << "No active view. Please call vinit.\n";
|
||||
std::cout << "Error: no active viewer!\n";
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -7324,7 +7501,130 @@ static int VStereo (Draw_Interpretor& theDI,
|
||||
return 0;
|
||||
}
|
||||
|
||||
ViewerTest_myDefaultCaps.contextStereo = Draw::Atoi (theArgVec[1]) != 0;
|
||||
Handle(Graphic3d_Camera) aCamera;
|
||||
Graphic3d_RenderingParams* aParams = NULL;
|
||||
Graphic3d_StereoMode aMode = Graphic3d_StereoMode_QuadBuffer;
|
||||
if (!aView.IsNull())
|
||||
{
|
||||
aParams = &aView->ChangeRenderingParams();
|
||||
aMode = aParams->StereoMode;
|
||||
aCamera = aView->Camera();
|
||||
}
|
||||
|
||||
ViewerTest_AutoUpdater anUpdateTool (ViewerTest::GetAISContext(), aView);
|
||||
for (Standard_Integer anArgIter = 1; anArgIter < theArgNb; ++anArgIter)
|
||||
{
|
||||
Standard_CString anArg = theArgVec[anArgIter];
|
||||
TCollection_AsciiString aFlag (anArg);
|
||||
aFlag.LowerCase();
|
||||
if (anUpdateTool.parseRedrawMode (aFlag))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
else if (aFlag == "0"
|
||||
|| aFlag == "off")
|
||||
{
|
||||
if (++anArgIter < theArgNb)
|
||||
{
|
||||
std::cout << "Error: wrong number of arguments!\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (!aCamera.IsNull()
|
||||
&& aCamera->ProjectionType() == Graphic3d_Camera::Projection_Stereo)
|
||||
{
|
||||
aCamera->SetProjectionType (Graphic3d_Camera::Projection_Perspective);
|
||||
}
|
||||
ViewerTest_myDefaultCaps.contextStereo = Standard_False;
|
||||
return 0;
|
||||
}
|
||||
else if (aFlag == "1"
|
||||
|| aFlag == "on")
|
||||
{
|
||||
if (++anArgIter < theArgNb)
|
||||
{
|
||||
std::cout << "Error: wrong number of arguments!\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (!aCamera.IsNull())
|
||||
{
|
||||
aCamera->SetProjectionType (Graphic3d_Camera::Projection_Stereo);
|
||||
}
|
||||
ViewerTest_myDefaultCaps.contextStereo = Standard_True;
|
||||
return 0;
|
||||
}
|
||||
else if (aFlag == "-reverse"
|
||||
|| aFlag == "-reversed"
|
||||
|| aFlag == "-swap")
|
||||
{
|
||||
Standard_Boolean toEnable = Standard_True;
|
||||
if (++anArgIter < theArgNb
|
||||
&& !parseOnOff (theArgVec[anArgIter], toEnable))
|
||||
{
|
||||
--anArgIter;
|
||||
}
|
||||
aParams->ToReverseStereo = toEnable;
|
||||
}
|
||||
else if (aFlag == "-noreverse"
|
||||
|| aFlag == "-noswap")
|
||||
{
|
||||
Standard_Boolean toDisable = Standard_True;
|
||||
if (++anArgIter < theArgNb
|
||||
&& !parseOnOff (theArgVec[anArgIter], toDisable))
|
||||
{
|
||||
--anArgIter;
|
||||
}
|
||||
aParams->ToReverseStereo = !toDisable;
|
||||
}
|
||||
else if (aFlag == "-mode"
|
||||
|| aFlag == "-stereomode")
|
||||
{
|
||||
if (++anArgIter >= theArgNb
|
||||
|| !parseStereoMode (theArgVec[anArgIter], aMode))
|
||||
{
|
||||
std::cout << "Error: syntax error at '" << anArg << "'\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (aMode == Graphic3d_StereoMode_QuadBuffer)
|
||||
{
|
||||
ViewerTest_myDefaultCaps.contextStereo = Standard_True;
|
||||
}
|
||||
}
|
||||
else if (aFlag == "-anaglyph"
|
||||
|| aFlag == "-anaglyphfilter")
|
||||
{
|
||||
Graphic3d_RenderingParams::Anaglyph aFilter = Graphic3d_RenderingParams::Anaglyph_RedCyan_Simple;
|
||||
if (++anArgIter >= theArgNb
|
||||
|| !parseAnaglyphFilter (theArgVec[anArgIter], aFilter))
|
||||
{
|
||||
std::cout << "Error: syntax error at '" << anArg << "'\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
aMode = Graphic3d_StereoMode_Anaglyph;
|
||||
aParams->AnaglyphFilter = aFilter;
|
||||
}
|
||||
else if (parseStereoMode (anArg, aMode)) // short syntax
|
||||
{
|
||||
if (aMode == Graphic3d_StereoMode_QuadBuffer)
|
||||
{
|
||||
ViewerTest_myDefaultCaps.contextStereo = Standard_True;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << "Error: syntax error at '" << anArg << "'\n";
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
if (!aView.IsNull())
|
||||
{
|
||||
aParams->StereoMode = aMode;
|
||||
aCamera->SetProjectionType (Graphic3d_Camera::Projection_Stereo);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -8761,11 +9061,27 @@ void ViewerTest::ViewerCommands(Draw_Interpretor& theCommands)
|
||||
"vvbo [{0|1}] : turn VBO usage On/Off; affects only newly displayed objects",
|
||||
__FILE__, VVbo, group);
|
||||
theCommands.Add ("vstereo",
|
||||
"\nvstereo [{0|1}] : turn stereo usage On/Off; affects only newly displayed objects",
|
||||
"vstereo [0|1] [-mode Mode] [-reverse {0|1}]"
|
||||
"\n\t\t: [-anaglyph Filter]"
|
||||
"\n\t\t: Control stereo output mode. Available modes for -mode:"
|
||||
"\n\t\t: quadBuffer - OpenGL QuadBuffer stereo,"
|
||||
"\n\t\t: requires driver support."
|
||||
"\n\t\t: Should be called BEFORE vinit!"
|
||||
"\n\t\t: anaglyph - Anaglyph glasses"
|
||||
"\n\t\t: rowInterlaced - row-interlaced display"
|
||||
"\n\t\t: columnInterlaced - column-interlaced display"
|
||||
"\n\t\t: chessBoard - chess-board output"
|
||||
"\n\t\t: sideBySide - horizontal pair"
|
||||
"\n\t\t: overUnder - vertical pair"
|
||||
"\n\t\t: Available Anaglyph filters for -anaglyph:"
|
||||
"\n\t\t: redCyan, redCyanSimple, yellowBlue, yellowBlueSimple,"
|
||||
"\n\t\t: greenMagentaSimple",
|
||||
__FILE__, VStereo, group);
|
||||
theCommands.Add ("vcaps",
|
||||
"vcaps [-vbo {0|1}] [-sprites {0|1}] [-ffp {0|1}]"
|
||||
"\n\t\t: [-compatibleContext {0|1}]"
|
||||
"\n\t\t: [-vsync {0|1}]"
|
||||
"\n\t\t: [-quadBuffer {0|1}] [-stereo {0|1}]"
|
||||
"\n\t\t: [-softMode {0|1}] [-noupdate|-update]"
|
||||
"\n\t\t: Modify particular graphic driver options:"
|
||||
"\n\t\t: FFP - use fixed-function pipeline instead of"
|
||||
@ -8774,9 +9090,11 @@ void ViewerTest::ViewerCommands(Draw_Interpretor& theCommands)
|
||||
"\n\t\t: VBO - use Vertex Buffer Object (copy vertex"
|
||||
"\n\t\t: arrays to GPU memory)"
|
||||
"\n\t\t: sprite - use textured sprites instead of bitmaps"
|
||||
"\n\t\t: vsync - switch VSync on or off"
|
||||
"\n\t\t: Context creation options:"
|
||||
"\n\t\t: softMode - software OpenGL implementation"
|
||||
"\n\t\t: compatibleProfile - backward-compatible profile"
|
||||
"\n\t\t: quadbuffer - QuadBuffer"
|
||||
"\n\t\t: Unlike vrenderparams, these parameters control alternative"
|
||||
"\n\t\t: rendering paths producing the same visual result when"
|
||||
"\n\t\t: possible."
|
||||
|
@ -109,10 +109,13 @@ void Visual3d_View::SetWindow (const Handle(Aspect_Window)& theWindow)
|
||||
MyCView.DefWindow.XWindow = theWindow->NativeHandle();
|
||||
MyCView.DefWindow.XParentWindow = theWindow->NativeParentHandle();
|
||||
|
||||
Standard_Integer Width, Height;
|
||||
theWindow->Size (Width, Height);
|
||||
MyCView.DefWindow.dx = Width;
|
||||
MyCView.DefWindow.dy = Height;
|
||||
Standard_Integer aWidth = 0, aHeight = 0, aLeft = 0, aTop = 0;
|
||||
theWindow->Position (aLeft, aTop, aWidth, aHeight);
|
||||
theWindow->Size (aWidth, aHeight);
|
||||
MyCView.DefWindow.left = aLeft;
|
||||
MyCView.DefWindow.top = aTop;
|
||||
MyCView.DefWindow.dx = aWidth;
|
||||
MyCView.DefWindow.dy = aHeight;
|
||||
|
||||
Standard_Real R, G, B;
|
||||
MyBackground = MyWindow->Background ();
|
||||
@ -270,7 +273,11 @@ void Visual3d_View::SetRatio()
|
||||
const Aspect_TypeOfUpdate anUpdateMode = myViewManager->UpdateMode();
|
||||
myViewManager->SetUpdateMode (Aspect_TOU_WAIT);
|
||||
|
||||
Standard_Integer aWidth, aHeight;
|
||||
Standard_Integer aWidth = 0, aHeight = 0, aLeft = 0, aTop = 0;
|
||||
MyWindow->Position (aLeft, aTop, aWidth, aHeight);
|
||||
MyCView.DefWindow.left = aLeft;
|
||||
MyCView.DefWindow.top = aTop;
|
||||
|
||||
MyWindow->Size (aWidth, aHeight);
|
||||
if (aWidth > 0 && aHeight > 0)
|
||||
{
|
||||
|
@ -16,8 +16,8 @@ vinit
|
||||
vsetdispmode 1
|
||||
vdisplay b
|
||||
vfit
|
||||
vdump ${imagedir}/texture_409.png rgb 409 409
|
||||
vdump ${imagedir}/texture_412.png rgb 412 412
|
||||
vdump ${imagedir}/texture_409.png -buffer rgb -width 409 -height 409
|
||||
vdump ${imagedir}/texture_412.png -buffer rgb -width 412 -height 412
|
||||
|
||||
# texture loaded correctly
|
||||
vtexture b ${imagedir}/texture_412.png
|
||||
|
@ -15,16 +15,16 @@ vcamera -fov 45 -iodType relative -iod 0.05 -zfocustype relative -zfocus 1.0
|
||||
vcamera -ortho
|
||||
vfit
|
||||
set aTitle "ortho"
|
||||
vdump $imagedir/${casename}_${aTitle}.png rgb 512 512
|
||||
vdump $imagedir/${casename}_${aTitle}.png -buffer rgb -width 512 -height 512
|
||||
vcamera -persp
|
||||
vfit
|
||||
set aTitle "persp"
|
||||
vdump $imagedir/${casename}_${aTitle}.png rgb 512 512
|
||||
vdump $imagedir/${casename}_${aTitle}.png -buffer rgb -width 512 -height 512
|
||||
vcamera -stereo
|
||||
set aTitle "stereoR"
|
||||
vdump $imagedir/${casename}_${aTitle}.png rgb 512 512 R
|
||||
vdump $imagedir/${casename}_${aTitle}.png -buffer rgb -width 512 -height 512 -stereo R
|
||||
set aTitle "stereoL"
|
||||
vdump $imagedir/${casename}_${aTitle}.png rgb 512 512 L
|
||||
vdump $imagedir/${casename}_${aTitle}.png -buffer rgb -width 512 -height 512 -stereo L
|
||||
|
||||
# test context stereo mode swicthing
|
||||
# if not supported by hardware it must not crash
|
||||
@ -35,4 +35,4 @@ vdisplay b
|
||||
vcamera -stereo
|
||||
vfit
|
||||
set aTitle "afterSwitch"
|
||||
vdump $imagedir/${casename}_${aTitle}.png rgb 512 512 R
|
||||
vdump $imagedir/${casename}_${aTitle}.png -buffer rgb -width 512 -height 512 -stereo R
|
||||
|
33
tests/v3d/glsl/stereo
Normal file
33
tests/v3d/glsl/stereo
Normal file
@ -0,0 +1,33 @@
|
||||
puts "========"
|
||||
puts "Stereo output modes"
|
||||
puts "========"
|
||||
|
||||
restore [locate_data_file occ/fuse.brep] f
|
||||
vinit View1
|
||||
vclear
|
||||
vsetdispmode 1
|
||||
vaxo
|
||||
vdisplay f
|
||||
vfit
|
||||
vrotate -0.5 0.0 0.0
|
||||
|
||||
vstereo -mode anaglyph
|
||||
vfit
|
||||
vdump $::imagedir/${::casename}_anaglyph.png -stereo blend
|
||||
|
||||
vstereo -mode columnInterlaced
|
||||
vdump $::imagedir/${::casename}_col.png -stereo blend
|
||||
|
||||
vstereo -mode chessBoard
|
||||
vdump $::imagedir/${::casename}_chess.png -stereo blend
|
||||
|
||||
vstereo -mode rowInterlaced
|
||||
vdump $::imagedir/${::casename}_row.png -stereo blend
|
||||
|
||||
vstereo -mode sideBySide
|
||||
vdump $::imagedir/${::casename}_sbs_anamorph.png -stereo blend
|
||||
|
||||
vstereo -mode overUnder
|
||||
vdump $::imagedir/${::casename}_overunder_anamorph.png -stereo blend
|
||||
|
||||
vdump $::imagedir/${::casename}_sbs.png -stereo sbs
|
Loading…
x
Reference in New Issue
Block a user