// Created on: 1998-09-01 // Created by: Robert COUBLANC // Copyright (c) 1998-1999 Matra Datavision // Copyright (c) 1999-2014 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 #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #ifdef _WIN32 #undef DrawText #endif #include #if defined(_WIN32) #include #include #elif defined(__APPLE__) && !defined(MACOSX_USE_GLX) #include #else #include #include /* contains some dangerous #defines such as Status, True etc. */ #include #include #endif // Auxiliary definitions static const char THE_KEY_DELETE = 127; static const char THE_KEY_ESCAPE = 27; //============================================================================== // VIEWER GLOBAL VARIABLES //============================================================================== Standard_IMPORT Standard_Boolean Draw_VirtualWindows; Standard_IMPORT Standard_Boolean Draw_Interprete (const char* theCommand); Standard_EXPORT int ViewerMainLoop(Standard_Integer , const char** argv); extern ViewerTest_DoubleMapOfInteractiveAndName& GetMapOfAIS(); extern int VErase (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec); #if defined(_WIN32) static Handle(WNT_Window)& VT_GetWindow() { static Handle(WNT_Window) WNTWin; return WNTWin; } #elif defined(__APPLE__) && !defined(MACOSX_USE_GLX) static Handle(Cocoa_Window)& VT_GetWindow() { static Handle(Cocoa_Window) aWindow; return aWindow; } extern void ViewerTest_SetCocoaEventManagerView (const Handle(Cocoa_Window)& theWindow); extern void SetCocoaWindowTitle (const Handle(Cocoa_Window)& theWindow, Standard_CString theTitle); extern void GetCocoaScreenResolution (Standard_Integer& theWidth, Standard_Integer& theHeight); #else static Handle(Xw_Window)& VT_GetWindow(){ static Handle(Xw_Window) XWWin; return XWWin; } static void VProcessEvents(ClientData,int); #endif static Handle(Aspect_DisplayConnection)& GetDisplayConnection() { static Handle(Aspect_DisplayConnection) aDisplayConnection; return aDisplayConnection; } static void SetDisplayConnection (const Handle(Aspect_DisplayConnection)& theDisplayConnection) { GetDisplayConnection() = theDisplayConnection; } #if defined(_WIN32) || (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) Aspect_Handle GetWindowHandle(const Handle(Aspect_Window)& theWindow) { Aspect_Handle aWindowHandle = (Aspect_Handle)NULL; #if defined(_WIN32) const Handle (WNT_Window) aWindow = Handle(WNT_Window)::DownCast (theWindow); if (!aWindow.IsNull()) return aWindow->HWindow(); #elif (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) const Handle (Xw_Window) aWindow = Handle(Xw_Window)::DownCast (theWindow); if (!aWindow.IsNull()) return aWindow->XWindow(); #endif return aWindowHandle; } #endif //! Setting additional flag to store 2D mode of the View to avoid scene rotation by mouse/key events class ViewerTest_V3dView : public V3d_View { DEFINE_STANDARD_RTTI_INLINE(ViewerTest_V3dView, V3d_View) public: //! Initializes the view. ViewerTest_V3dView (const Handle(V3d_Viewer)& theViewer, const V3d_TypeOfView theType = V3d_ORTHOGRAPHIC, bool theIs2dMode = false) : V3d_View (theViewer, theType), myIs2dMode (theIs2dMode) {} //! Initializes the view by copying. ViewerTest_V3dView (const Handle(V3d_Viewer)& theViewer, const Handle(V3d_View)& theView) : V3d_View (theViewer, theView), myIs2dMode (false) { if (Handle(ViewerTest_V3dView) aV3dView = Handle(ViewerTest_V3dView)::DownCast (theView)) { myIs2dMode = aV3dView->IsViewIn2DMode(); } } //! Returns true if 2D mode is set for the view bool IsViewIn2DMode() const { return myIs2dMode; } //! Sets 2D mode for the view void SetView2DMode (bool the2dMode) { myIs2dMode = the2dMode; } public: //! Returns true if active view in 2D mode. static bool IsCurrentViewIn2DMode() { if (Handle(ViewerTest_V3dView) aV3dView = Handle(ViewerTest_V3dView)::DownCast (ViewerTest::CurrentView())) { return aV3dView->IsViewIn2DMode(); } return false; } //! Set if active view in 2D mode. static void SetCurrentView2DMode (bool theIs2d) { if (Handle(ViewerTest_V3dView) aV3dView = Handle(ViewerTest_V3dView)::DownCast (ViewerTest::CurrentView())) { aV3dView->SetView2DMode (theIs2d); } } private: Standard_Boolean myIs2dMode; //!< 2D mode flag }; NCollection_DoubleMap ViewerTest_myViews; static NCollection_DoubleMap ViewerTest_myContexts; static NCollection_DoubleMap ViewerTest_myDrivers; static OpenGl_Caps ViewerTest_myDefaultCaps; static void OSWindowSetup(); static struct { Quantity_Color FlatColor; Quantity_Color GradientColor1; Quantity_Color GradientColor2; Aspect_GradientFillMethod FillMethod; } ViewerTest_DefaultBackground = { Quantity_NOC_BLACK, Quantity_NOC_BLACK, Quantity_NOC_BLACK, Aspect_GFM_NONE }; //============================================================================== // EVENT GLOBAL VARIABLES //============================================================================== static int Start_Rot = 0; Standard_Boolean HasHlrOnBeforeRotation = Standard_False; int X_Motion = 0; // Current cursor position int Y_Motion = 0; int X_ButtonPress = 0; // Last ButtonPress position int Y_ButtonPress = 0; Standard_Boolean IsDragged = Standard_False; Standard_Boolean DragFirst = Standard_False; Standard_Boolean TheIsAnimating = Standard_False; Standard_Boolean Draw_ToExitOnCloseView = Standard_False; Standard_Boolean Draw_ToCloseViewOnEsc = Standard_False; Standard_EXPORT const Handle(AIS_RubberBand)& GetRubberBand() { static Handle(AIS_RubberBand) aBand; if (aBand.IsNull()) { aBand = new AIS_RubberBand (Quantity_NOC_LIGHTBLUE, Aspect_TOL_SOLID, Quantity_NOC_LIGHTBLUE, 0.4, 1.0); aBand->SetDisplayMode (0); } return aBand; } typedef NCollection_Map ViewerTest_MapOfAISManipulators; Standard_EXPORT ViewerTest_MapOfAISManipulators& GetMapOfAISManipulators() { static ViewerTest_MapOfAISManipulators aMap; return aMap; } Standard_EXPORT Handle(AIS_Manipulator) GetActiveAISManipulator() { ViewerTest_MapOfAISManipulators::Iterator anIt (GetMapOfAISManipulators()); for (; anIt.More(); anIt.Next()) { if (anIt.Value()->HasActiveMode()) { return anIt.Value(); } } return NULL; } //============================================================================== #ifdef _WIN32 static LRESULT WINAPI ViewerWindowProc( HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam ); static LRESULT WINAPI AdvViewerWindowProc( HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam ); #endif //============================================================================== //function : WClass //purpose : //============================================================================== const Handle(Standard_Transient)& ViewerTest::WClass() { static Handle(Standard_Transient) theWClass; #if defined(_WIN32) if (theWClass.IsNull()) { theWClass = new WNT_WClass ("GW3D_Class", (Standard_Address )AdvViewerWindowProc, CS_VREDRAW | CS_HREDRAW, 0, 0, ::LoadCursor (NULL, IDC_ARROW)); } #endif return theWClass; } //============================================================================== //function : CreateName //purpose : Create numerical name for new object in theMap //============================================================================== template TCollection_AsciiString CreateName (const NCollection_DoubleMap & theObjectMap, const TCollection_AsciiString& theDefaultString) { if (theObjectMap.IsEmpty()) return theDefaultString + TCollection_AsciiString(1); Standard_Integer aNextKey = 1; Standard_Boolean isFound = Standard_False; while (!isFound) { TCollection_AsciiString aStringKey = theDefaultString + TCollection_AsciiString(aNextKey); // Look for objects with default names if (theObjectMap.IsBound1(aStringKey)) { aNextKey++; } else isFound = Standard_True; } return theDefaultString + TCollection_AsciiString(aNextKey); } //============================================================================== //structure : ViewerTest_Names //purpose : Allow to operate with full view name: driverName/viewerName/viewName //============================================================================== struct ViewerTest_Names { private: TCollection_AsciiString myDriverName; TCollection_AsciiString myViewerName; TCollection_AsciiString myViewName; public: const TCollection_AsciiString& GetDriverName () const { return myDriverName; } void SetDriverName (const TCollection_AsciiString& theDriverName) { myDriverName = theDriverName; } const TCollection_AsciiString& GetViewerName () const { return myViewerName; } void SetViewerName (const TCollection_AsciiString& theViewerName) { myViewerName = theViewerName; } const TCollection_AsciiString& GetViewName () const { return myViewName; } void SetViewName (const TCollection_AsciiString& theViewName) { myViewName = theViewName; } //=========================================================================== //function : Constructor for ViewerTest_Names //purpose : Get view, viewer, driver names from custom string //=========================================================================== ViewerTest_Names (const TCollection_AsciiString& theInputString) { TCollection_AsciiString aName(theInputString); if (theInputString.IsEmpty()) { // Get current configuration if (ViewerTest_myDrivers.IsEmpty()) myDriverName = CreateName (ViewerTest_myDrivers, TCollection_AsciiString("Driver")); else myDriverName = ViewerTest_myDrivers.Find2 (ViewerTest::GetAISContext()->CurrentViewer()->Driver()); if(ViewerTest_myContexts.IsEmpty()) { myViewerName = CreateName (ViewerTest_myContexts, TCollection_AsciiString (myDriverName + "/Viewer")); } else { myViewerName = ViewerTest_myContexts.Find2 (ViewerTest::GetAISContext()); } myViewName = CreateName (ViewerTest_myViews, TCollection_AsciiString(myViewerName + "/View")); } else { // There is at least view name Standard_Integer aParserNumber = 0; for (Standard_Integer i = 0; i < 3; ++i) { Standard_Integer aParserPos = aName.SearchFromEnd("/"); if(aParserPos != -1) { aParserNumber++; aName.Split(aParserPos-1); } else break; } if (aParserNumber == 0) { // Only view name if (!ViewerTest::GetAISContext().IsNull()) { myDriverName = ViewerTest_myDrivers.Find2 (ViewerTest::GetAISContext()->CurrentViewer()->Driver()); myViewerName = ViewerTest_myContexts.Find2 (ViewerTest::GetAISContext()); } else { // There is no opened contexts here, need to create names for viewer and driver myDriverName = CreateName (ViewerTest_myDrivers, TCollection_AsciiString("Driver")); myViewerName = CreateName (ViewerTest_myContexts, TCollection_AsciiString (myDriverName + "/Viewer")); } myViewName = TCollection_AsciiString(myViewerName + "/" + theInputString); } else if (aParserNumber == 1) { // Here is viewerName/viewName if (!ViewerTest::GetAISContext().IsNull()) myDriverName = ViewerTest_myDrivers.Find2 (ViewerTest::GetAISContext()->CurrentViewer()->Driver()); else { // There is no opened contexts here, need to create name for driver myDriverName = CreateName (ViewerTest_myDrivers, TCollection_AsciiString("Driver")); } myViewerName = TCollection_AsciiString(myDriverName + "/" + aName); myViewName = TCollection_AsciiString(myDriverName + "/" + theInputString); } else { //Here is driverName/viewerName/viewName myDriverName = TCollection_AsciiString(aName); TCollection_AsciiString aViewerName(theInputString); aViewerName.Split(aViewerName.SearchFromEnd("/") - 1); myViewerName = TCollection_AsciiString(aViewerName); myViewName = TCollection_AsciiString(theInputString); } } } }; //============================================================================== //function : FindContextByView //purpose : Find AIS_InteractiveContext by View //============================================================================== Handle(AIS_InteractiveContext) FindContextByView (const Handle(V3d_View)& theView) { Handle(AIS_InteractiveContext) anAISContext; for (NCollection_DoubleMap::Iterator anIter (ViewerTest_myContexts); anIter.More(); anIter.Next()) { if (anIter.Value()->CurrentViewer() == theView->Viewer()) return anIter.Key2(); } return anAISContext; } //============================================================================== //function : SetWindowTitle //purpose : Set window title //============================================================================== void SetWindowTitle (const Handle(Aspect_Window)& theWindow, Standard_CString theTitle) { #if defined(_WIN32) const TCollection_ExtendedString theTitleW (theTitle); SetWindowTextW ((HWND )Handle(WNT_Window)::DownCast(theWindow)->HWindow(), theTitleW.ToWideString()); #elif defined(__APPLE__) && !defined(MACOSX_USE_GLX) SetCocoaWindowTitle (Handle(Cocoa_Window)::DownCast(theWindow), theTitle); #else if(GetDisplayConnection()->GetDisplay()) { Window aWindow = Handle(Xw_Window)::DownCast(theWindow)->XWindow(); XStoreName (GetDisplayConnection()->GetDisplay(), aWindow , theTitle); } #endif } //============================================================================== //function : IsWindowOverlapped //purpose : Check if theWindow overlapp another view //============================================================================== Standard_Boolean IsWindowOverlapped (const Standard_Integer thePxLeft, const Standard_Integer thePxTop, const Standard_Integer thePxRight, const Standard_Integer thePxBottom, TCollection_AsciiString& theViewId) { for(NCollection_DoubleMap ::Iterator anIter(ViewerTest_myViews); anIter.More(); anIter.Next()) { Standard_Integer aTop = 0, aLeft = 0, aRight = 0, aBottom = 0; anIter.Value()->Window()->Position(aLeft, aTop, aRight, aBottom); if ((thePxLeft >= aLeft && thePxLeft <= aRight && thePxTop >= aTop && thePxTop <= aBottom) || (thePxLeft >= aLeft && thePxLeft <= aRight && thePxBottom >= aTop && thePxBottom <= aBottom) || (thePxRight >= aLeft && thePxRight <= aRight && thePxTop >= aTop && thePxTop <= aBottom) || (thePxRight >= aLeft && thePxRight <= aRight && thePxBottom >= aTop && thePxBottom <= aBottom)) { theViewId = anIter.Key1(); return Standard_True; } } return Standard_False; } // Workaround: to create and delete non-orthographic views outside ViewerTest void ViewerTest::RemoveViewName (const TCollection_AsciiString& theName) { ViewerTest_myViews.UnBind1 (theName); } void ViewerTest::InitViewName (const TCollection_AsciiString& theName, const Handle(V3d_View)& theView) { ViewerTest_myViews.Bind (theName, theView); } TCollection_AsciiString ViewerTest::GetCurrentViewName () { return ViewerTest_myViews.Find2( ViewerTest::CurrentView()); } //============================================================================== //function : ViewerInit //purpose : Create the window viewer and initialize all the global variable //============================================================================== TCollection_AsciiString ViewerTest::ViewerInit (const Standard_Integer thePxLeft, const Standard_Integer thePxTop, const Standard_Integer thePxWidth, const Standard_Integer thePxHeight, const TCollection_AsciiString& theViewName, const TCollection_AsciiString& theDisplayName, const Handle(V3d_View)& theViewToClone) { // Default position and dimension of the viewer window. // Note that left top corner is set to be sufficiently small to have // window fit in the small screens (actual for remote desktops, see #23003). // The position corresponds to the window's client area, thus some // gap is added for window frame to be visible. Standard_Integer aPxLeft = 20; Standard_Integer aPxTop = 40; Standard_Integer aPxWidth = 409; Standard_Integer aPxHeight = 409; Standard_Boolean toCreateViewer = Standard_False; if (!theViewToClone.IsNull()) { theViewToClone->Window()->Size (aPxWidth, aPxHeight); } Handle(OpenGl_GraphicDriver) aGraphicDriver; ViewerTest_Names aViewNames(theViewName); if (ViewerTest_myViews.IsBound1 (aViewNames.GetViewName ())) aViewNames.SetViewName (aViewNames.GetViewerName() + "/" + CreateName(ViewerTest_myViews, "View")); if (thePxLeft != 0) aPxLeft = thePxLeft; if (thePxTop != 0) aPxTop = thePxTop; if (thePxWidth != 0) aPxWidth = thePxWidth; if (thePxHeight != 0) aPxHeight = thePxHeight; // Get graphic driver (create it or get from another view) if (!ViewerTest_myDrivers.IsBound1 (aViewNames.GetDriverName())) { // Get connection string #if !defined(_WIN32) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) TCollection_AsciiString aDisplayName(theDisplayName); if (!aDisplayName.IsEmpty()) SetDisplayConnection (new Aspect_DisplayConnection ()); else SetDisplayConnection (new Aspect_DisplayConnection (aDisplayName)); #else (void)theDisplayName; // avoid warning on unused argument SetDisplayConnection (new Aspect_DisplayConnection ()); #endif if (Draw_VirtualWindows) { // don't waste the time waiting for VSync when window is not displayed on the screen ViewerTest_myDefaultCaps.swapInterval = 0; // alternatively we can disable buffer swap at all, but this might be inappropriate for testing //ViewerTest_myDefaultCaps.buffersNoSwap = true; } aGraphicDriver = new OpenGl_GraphicDriver (GetDisplayConnection()); aGraphicDriver->ChangeOptions() = ViewerTest_myDefaultCaps; ViewerTest_myDrivers.Bind (aViewNames.GetDriverName(), aGraphicDriver); toCreateViewer = Standard_True; } else { aGraphicDriver = Handle(OpenGl_GraphicDriver)::DownCast (ViewerTest_myDrivers.Find1 (aViewNames.GetDriverName())); } //Dispose the window if input parameters are default if (!ViewerTest_myViews.IsEmpty() && thePxLeft == 0 && thePxTop == 0) { Standard_Integer aTop = 0, aLeft = 0, aRight = 0, aBottom = 0, aScreenWidth = 0, aScreenHeight = 0; // Get screen resolution #if defined(_WIN32) || defined(__WIN32__) RECT aWindowSize; GetClientRect(GetDesktopWindow(), &aWindowSize); aScreenHeight = aWindowSize.bottom; aScreenWidth = aWindowSize.right; #elif defined(__APPLE__) && !defined(MACOSX_USE_GLX) GetCocoaScreenResolution (aScreenWidth, aScreenHeight); #else Screen *aScreen = DefaultScreenOfDisplay(GetDisplayConnection()->GetDisplay()); aScreenWidth = WidthOfScreen(aScreen); aScreenHeight = HeightOfScreen(aScreen); #endif TCollection_AsciiString anOverlappedViewId(""); while (IsWindowOverlapped (aPxLeft, aPxTop, aPxLeft + aPxWidth, aPxTop + aPxHeight, anOverlappedViewId)) { ViewerTest_myViews.Find1(anOverlappedViewId)->Window()->Position (aLeft, aTop, aRight, aBottom); if (IsWindowOverlapped (aRight + 20, aPxTop, aRight + 20 + aPxWidth, aPxTop + aPxHeight, anOverlappedViewId) && aRight + 2*aPxWidth + 40 > aScreenWidth) { if (aBottom + aPxHeight + 40 > aScreenHeight) { aPxLeft = 20; aPxTop = 40; break; } aPxLeft = 20; aPxTop = aBottom + 40; } else aPxLeft = aRight + 20; } } // Get viewer name TCollection_AsciiString aTitle("3D View - "); aTitle = aTitle + aViewNames.GetViewName() + "(*)"; // Change name of current active window if (!ViewerTest::CurrentView().IsNull()) { TCollection_AsciiString anActiveWindowTitle("3D View - "); anActiveWindowTitle = anActiveWindowTitle + ViewerTest_myViews.Find2 (ViewerTest::CurrentView()); SetWindowTitle (ViewerTest::CurrentView()->Window(), anActiveWindowTitle.ToCString()); } // Create viewer Handle(V3d_Viewer) a3DViewer; // If it's the single view, we first look for empty context if (ViewerTest_myViews.IsEmpty() && !ViewerTest_myContexts.IsEmpty()) { NCollection_DoubleMap ::Iterator anIter(ViewerTest_myContexts); if (anIter.More()) ViewerTest::SetAISContext (anIter.Value()); a3DViewer = ViewerTest::GetAISContext()->CurrentViewer(); } else if (ViewerTest_myContexts.IsBound1(aViewNames.GetViewerName())) { ViewerTest::SetAISContext(ViewerTest_myContexts.Find1(aViewNames.GetViewerName())); a3DViewer = ViewerTest::GetAISContext()->CurrentViewer(); } else if (a3DViewer.IsNull()) { toCreateViewer = Standard_True; a3DViewer = new V3d_Viewer(aGraphicDriver); a3DViewer->SetDefaultBackgroundColor (ViewerTest_DefaultBackground.FlatColor); a3DViewer->SetDefaultBgGradientColors (ViewerTest_DefaultBackground.GradientColor1, ViewerTest_DefaultBackground.GradientColor2, ViewerTest_DefaultBackground.FillMethod); } // AIS context setup if (ViewerTest::GetAISContext().IsNull() || !(ViewerTest_myContexts.IsBound1(aViewNames.GetViewerName()))) { Handle(AIS_InteractiveContext) aContext = new AIS_InteractiveContext (a3DViewer); ViewerTest::SetAISContext (aContext); ViewerTest_myContexts.Bind (aViewNames.GetViewerName(), ViewerTest::GetAISContext()); } else { ViewerTest::ResetEventManager(); } // Create window #if defined(_WIN32) VT_GetWindow() = new WNT_Window (aTitle.ToCString(), Handle(WNT_WClass)::DownCast (WClass()), Draw_VirtualWindows ? WS_POPUP : WS_OVERLAPPEDWINDOW, aPxLeft, aPxTop, aPxWidth, aPxHeight, Quantity_NOC_BLACK); #elif defined(__APPLE__) && !defined(MACOSX_USE_GLX) VT_GetWindow() = new Cocoa_Window (aTitle.ToCString(), aPxLeft, aPxTop, aPxWidth, aPxHeight); ViewerTest_SetCocoaEventManagerView (VT_GetWindow()); #else VT_GetWindow() = new Xw_Window (aGraphicDriver->GetDisplayConnection(), aTitle.ToCString(), aPxLeft, aPxTop, aPxWidth, aPxHeight); #endif VT_GetWindow()->SetVirtual (Draw_VirtualWindows); // View setup Handle(V3d_View) aView; if (!theViewToClone.IsNull()) { aView = new ViewerTest_V3dView (a3DViewer, theViewToClone); } else { aView = new ViewerTest_V3dView (a3DViewer, a3DViewer->DefaultTypeOfView()); } aView->SetWindow (VT_GetWindow()); ViewerTest::GetAISContext()->RedrawImmediate (a3DViewer); ViewerTest::CurrentView(aView); ViewerTest_myViews.Bind (aViewNames.GetViewName(), aView); // Setup for X11 or NT OSWindowSetup(); // Set parameters for V3d_View and V3d_Viewer const Handle (V3d_View) aV3dView = ViewerTest::CurrentView(); aV3dView->SetComputedMode(Standard_False); a3DViewer->SetDefaultBackgroundColor(Quantity_NOC_BLACK); if (toCreateViewer) { a3DViewer->SetDefaultLights(); a3DViewer->SetLightOn(); } #if !defined(_WIN32) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) #if TCL_MAJOR_VERSION < 8 Tk_CreateFileHandler((void*)XConnectionNumber(GetDisplayConnection()->GetDisplay()), TK_READABLE, VProcessEvents, (ClientData) VT_GetWindow()->XWindow() ); #else Tk_CreateFileHandler(XConnectionNumber(GetDisplayConnection()->GetDisplay()), TK_READABLE, VProcessEvents, (ClientData) VT_GetWindow()->XWindow() ); #endif #endif VT_GetWindow()->Map(); // Set the handle of created view in the event manager ViewerTest::ResetEventManager(); ViewerTest::CurrentView()->Redraw(); aView.Nullify(); a3DViewer.Nullify(); return aViewNames.GetViewName(); } //============================================================================== //function : RedrawAllViews //purpose : Redraw all created views //============================================================================== void ViewerTest::RedrawAllViews() { NCollection_DoubleMap::Iterator aViewIt(ViewerTest_myViews); for (; aViewIt.More(); aViewIt.Next()) { const Handle(V3d_View)& aView = aViewIt.Key2(); aView->Redraw(); } } //============================================================================== //function : Vinit //purpose : Create the window viewer and initialize all the global variable // Use Tk_CreateFileHandler on UNIX to catch the X11 Viewer event //============================================================================== static int VInit (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { TCollection_AsciiString aViewName, aDisplayName; Standard_Integer aPxLeft = 0, aPxTop = 0, aPxWidth = 0, aPxHeight = 0; Handle(V3d_View) aCopyFrom; TCollection_AsciiString aName, aValue; int is2dMode = -1; for (Standard_Integer anArgIt = 1; anArgIt < theArgsNb; ++anArgIt) { const TCollection_AsciiString anArg = theArgVec[anArgIt]; TCollection_AsciiString anArgCase = anArg; anArgCase.LowerCase(); if (anArgIt + 1 < theArgsNb && anArgCase == "-name") { aViewName = theArgVec[++anArgIt]; } else if (anArgIt + 1 < theArgsNb && (anArgCase == "-left" || anArgCase == "-l")) { aPxLeft = Draw::Atoi (theArgVec[++anArgIt]); } else if (anArgIt + 1 < theArgsNb && (anArgCase == "-top" || anArgCase == "-t")) { aPxTop = Draw::Atoi (theArgVec[++anArgIt]); } else if (anArgIt + 1 < theArgsNb && (anArgCase == "-width" || anArgCase == "-w")) { aPxWidth = Draw::Atoi (theArgVec[++anArgIt]); } else if (anArgIt + 1 < theArgsNb && (anArgCase == "-height" || anArgCase == "-h")) { aPxHeight = Draw::Atoi (theArgVec[++anArgIt]); } else if (anArgCase == "-exitonclose") { Draw_ToExitOnCloseView = true; if (anArgIt + 1 < theArgsNb && ViewerTest::ParseOnOff (theArgVec[anArgIt + 1], Draw_ToExitOnCloseView)) { ++anArgIt; } } else if (anArgCase == "-closeonescape" || anArgCase == "-closeonesc") { Draw_ToCloseViewOnEsc = true; if (anArgIt + 1 < theArgsNb && ViewerTest::ParseOnOff (theArgVec[anArgIt + 1], Draw_ToCloseViewOnEsc)) { ++anArgIt; } } else if (anArgCase == "-2d_mode" || anArgCase == "-2dmode" || anArgCase == "-2d") { bool toEnable = true; if (anArgIt + 1 < theArgsNb && ViewerTest::ParseOnOff (theArgVec[anArgIt + 1], toEnable)) { ++anArgIt; } is2dMode = toEnable ? 1 : 0; } else if (anArgIt + 1 < theArgsNb && (anArgCase == "-disp" || anArgCase == "-display")) { aDisplayName = theArgVec[++anArgIt]; } else if (!ViewerTest::CurrentView().IsNull() && aCopyFrom.IsNull() && (anArgCase == "-copy" || anArgCase == "-clone" || anArgCase == "-cloneactive" || anArgCase == "-cloneactiveview")) { aCopyFrom = ViewerTest::CurrentView(); } // old syntax else if (ViewerTest::SplitParameter (anArg, aName, aValue)) { aName.LowerCase(); if (aName == "name") { aViewName = aValue; } else if (aName == "l" || aName == "left") { aPxLeft = aValue.IntegerValue(); } else if (aName == "t" || aName == "top") { aPxTop = aValue.IntegerValue(); } else if (aName == "disp" || aName == "display") { aDisplayName = aValue; } else if (aName == "w" || aName == "width") { aPxWidth = aValue.IntegerValue(); } else if (aName == "h" || aName == "height") { aPxHeight = aValue.IntegerValue(); } else { std::cout << "Syntax error: unknown argument " << anArg << ".\n"; return 1; } } else if (aViewName.IsEmpty()) { aViewName = anArg; } else { std::cout << "Syntax error: unknown argument " << anArg << ".\n"; return 1; } } #if defined(_WIN32) || (defined(__APPLE__) && !defined(MACOSX_USE_GLX)) if (!aDisplayName.IsEmpty()) { aDisplayName.Clear(); std::cout << "Warning: display parameter will be ignored.\n"; } #endif ViewerTest_Names aViewNames (aViewName); if (ViewerTest_myViews.IsBound1 (aViewNames.GetViewName())) { TCollection_AsciiString aCommand = TCollection_AsciiString ("vactivate ") + aViewNames.GetViewName(); theDi.Eval (aCommand.ToCString()); if (is2dMode != -1) { ViewerTest_V3dView::SetCurrentView2DMode (is2dMode == 1); } return 0; } TCollection_AsciiString aViewId = ViewerTest::ViewerInit (aPxLeft, aPxTop, aPxWidth, aPxHeight, aViewName, aDisplayName, aCopyFrom); if (is2dMode != -1) { ViewerTest_V3dView::SetCurrentView2DMode (is2dMode == 1); } theDi << aViewId; return 0; } //! Parse HLR algo type. static Standard_Boolean parseHlrAlgoType (const char* theName, Prs3d_TypeOfHLR& theType) { TCollection_AsciiString aName (theName); aName.LowerCase(); if (aName == "polyalgo") { theType = Prs3d_TOH_PolyAlgo; } else if (aName == "algo") { theType = Prs3d_TOH_Algo; } else { return Standard_False; } return Standard_True; } //============================================================================== //function : VHLR //purpose : hidden lines removal algorithm //============================================================================== static int VHLR (Draw_Interpretor& di, Standard_Integer argc, const char** argv) { const Handle(V3d_View) aView = ViewerTest::CurrentView(); const Handle(AIS_InteractiveContext) aCtx = ViewerTest::GetAISContext(); if (aView.IsNull()) { std::cerr << "Error: No opened viewer!\n"; return 1; } Standard_Boolean hasHlrOnArg = Standard_False; Standard_Boolean hasShowHiddenArg = Standard_False; Standard_Boolean isHLROn = Standard_False; Standard_Boolean toShowHidden = aCtx->DefaultDrawer()->DrawHiddenLine(); Prs3d_TypeOfHLR aTypeOfHLR = Prs3d_TOH_NotSet; ViewerTest_AutoUpdater anUpdateTool (Handle(AIS_InteractiveContext)(), aView); for (Standard_Integer anArgIter = 1; anArgIter < argc; ++anArgIter) { TCollection_AsciiString anArg (argv[anArgIter]); anArg.LowerCase(); if (anUpdateTool.parseRedrawMode (anArg)) { continue; } else if (anArg == "-showhidden" && anArgIter + 1 < argc && ViewerTest::ParseOnOff (argv[anArgIter + 1], toShowHidden)) { ++anArgIter; hasShowHiddenArg = Standard_True; continue; } else if ((anArg == "-type" || anArg == "-algo" || anArg == "-algotype") && anArgIter + 1 < argc && parseHlrAlgoType (argv[anArgIter + 1], aTypeOfHLR)) { ++anArgIter; continue; } else if (!hasHlrOnArg && ViewerTest::ParseOnOff (argv[anArgIter], isHLROn)) { hasHlrOnArg = Standard_True; continue; } // old syntax else if (!hasShowHiddenArg && ViewerTest::ParseOnOff(argv[anArgIter], toShowHidden)) { hasShowHiddenArg = Standard_True; continue; } else { std::cout << "Syntax error at '" << argv[anArgIter] << "'\n"; return 1; } } if (!hasHlrOnArg) { di << "HLR: " << aView->ComputedMode() << "\n"; di << "HiddenLine: " << aCtx->DefaultDrawer()->DrawHiddenLine() << "\n"; di << "HlrAlgo: "; switch (aCtx->DefaultDrawer()->TypeOfHLR()) { case Prs3d_TOH_NotSet: di << "NotSet\n"; break; case Prs3d_TOH_PolyAlgo: di << "PolyAlgo\n"; break; case Prs3d_TOH_Algo: di << "Algo\n"; break; } anUpdateTool.Invalidate(); return 0; } Standard_Boolean toRecompute = Standard_False; if (aTypeOfHLR != Prs3d_TOH_NotSet && aTypeOfHLR != aCtx->DefaultDrawer()->TypeOfHLR()) { toRecompute = Standard_True; aCtx->DefaultDrawer()->SetTypeOfHLR (aTypeOfHLR); } if (toShowHidden != aCtx->DefaultDrawer()->DrawHiddenLine()) { toRecompute = Standard_True; if (toShowHidden) { aCtx->DefaultDrawer()->EnableDrawHiddenLine(); } else { aCtx->DefaultDrawer()->DisableDrawHiddenLine(); } } // redisplay shapes if (aView->ComputedMode() && isHLROn && toRecompute) { AIS_ListOfInteractive aListOfShapes; aCtx->DisplayedObjects (aListOfShapes); for (AIS_ListIteratorOfListOfInteractive anIter (aListOfShapes); anIter.More(); anIter.Next()) { if (Handle(AIS_Shape) aShape = Handle(AIS_Shape)::DownCast(anIter.Value())) { aCtx->Redisplay (aShape, Standard_False); } } } aView->SetComputedMode (isHLROn); return 0; } //============================================================================== //function : VHLRType //purpose : change type of using HLR algorithm //============================================================================== static int VHLRType (Draw_Interpretor& , Standard_Integer argc, const char** argv) { const Handle(V3d_View) aView = ViewerTest::CurrentView(); const Handle(AIS_InteractiveContext) aCtx = ViewerTest::GetAISContext(); if (aView.IsNull()) { std::cerr << "Error: No opened viewer!\n"; return 1; } Prs3d_TypeOfHLR aTypeOfHLR = Prs3d_TOH_NotSet; ViewerTest_AutoUpdater anUpdateTool (Handle(AIS_InteractiveContext)(), aView); AIS_ListOfInteractive aListOfShapes; for (Standard_Integer anArgIter = 1; anArgIter < argc; ++anArgIter) { TCollection_AsciiString anArg (argv[anArgIter]); anArg.LowerCase(); if (anUpdateTool.parseRedrawMode (anArg)) { continue; } else if ((anArg == "-type" || anArg == "-algo" || anArg == "-algotype") && anArgIter + 1 < argc && parseHlrAlgoType (argv[anArgIter + 1], aTypeOfHLR)) { ++anArgIter; continue; } // old syntax else if (aTypeOfHLR == Prs3d_TOH_NotSet && parseHlrAlgoType (argv[anArgIter], aTypeOfHLR)) { continue; } else { ViewerTest_DoubleMapOfInteractiveAndName& aMap = GetMapOfAIS(); TCollection_AsciiString aName (argv[anArgIter]); if (!aMap.IsBound2 (aName)) { std::cout << "Syntax error: Wrong shape name '" << aName << "'.\n"; return 1; } Handle(AIS_Shape) aShape = Handle(AIS_Shape)::DownCast (aMap.Find2 (aName)); if (aShape.IsNull()) { std::cout << "Syntax error: '" << aName << "' is not a shape presentation.\n"; return 1; } aListOfShapes.Append (aShape); continue; } } if (aTypeOfHLR == Prs3d_TOH_NotSet) { std::cout << "Syntax error: wrong number of arguments!\n"; return 1; } const Standard_Boolean isGlobal = aListOfShapes.IsEmpty(); if (isGlobal) { aCtx->DisplayedObjects (aListOfShapes); aCtx->DefaultDrawer()->SetTypeOfHLR (aTypeOfHLR); } for (AIS_ListIteratorOfListOfInteractive anIter(aListOfShapes); anIter.More(); anIter.Next()) { Handle(AIS_Shape) aShape = Handle(AIS_Shape)::DownCast(anIter.Value()); if (aShape.IsNull()) { continue; } const bool toUpdateShape = aShape->TypeOfHLR() != aTypeOfHLR && aView->ComputedMode(); if (!isGlobal || aShape->TypeOfHLR() != aTypeOfHLR) { aShape->SetTypeOfHLR (aTypeOfHLR); } if (toUpdateShape) { aCtx->Redisplay (aShape, Standard_False); } } return 0; } //============================================================================== //function : FindViewIdByWindowHandle //purpose : Find theView Id in the map of views by window handle //============================================================================== #if defined(_WIN32) || defined(__WIN32__) || (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) TCollection_AsciiString FindViewIdByWindowHandle(const Aspect_Handle theWindowHandle) { for (NCollection_DoubleMap::Iterator anIter(ViewerTest_myViews); anIter.More(); anIter.Next()) { Aspect_Handle aWindowHandle = GetWindowHandle(anIter.Value()->Window()); if (aWindowHandle == theWindowHandle) return anIter.Key1(); } return TCollection_AsciiString(""); } #endif //============================================================================== //function : ActivateView //purpose : Make the view active //============================================================================== void ActivateView (const TCollection_AsciiString& theViewName) { const Handle(V3d_View) aView = ViewerTest_myViews.Find1(theViewName); if (!aView.IsNull()) { Handle(AIS_InteractiveContext) anAISContext = FindContextByView(aView); if (!anAISContext.IsNull()) { if (!ViewerTest::CurrentView().IsNull()) { TCollection_AsciiString aTitle("3D View - "); aTitle = aTitle + ViewerTest_myViews.Find2 (ViewerTest::CurrentView()); SetWindowTitle (ViewerTest::CurrentView()->Window(), aTitle.ToCString()); } ViewerTest::CurrentView (aView); ViewerTest::SetAISContext (anAISContext); TCollection_AsciiString aTitle = TCollection_AsciiString("3D View - ") + theViewName + "(*)"; SetWindowTitle (ViewerTest::CurrentView()->Window(), aTitle.ToCString()); #if defined(_WIN32) VT_GetWindow() = Handle(WNT_Window)::DownCast(ViewerTest::CurrentView()->Window()); #elif defined(__APPLE__) && !defined(MACOSX_USE_GLX) VT_GetWindow() = Handle(Cocoa_Window)::DownCast(ViewerTest::CurrentView()->Window()); #else VT_GetWindow() = Handle(Xw_Window)::DownCast(ViewerTest::CurrentView()->Window()); #endif SetDisplayConnection(ViewerTest::CurrentView()->Viewer()->Driver()->GetDisplayConnection()); ViewerTest::CurrentView()->Redraw(); } } } //============================================================================== //function : RemoveView //purpose : //============================================================================== void ViewerTest::RemoveView (const Handle(V3d_View)& theView, const Standard_Boolean theToRemoveContext) { if (!ViewerTest_myViews.IsBound2 (theView)) { return; } const TCollection_AsciiString aViewName = ViewerTest_myViews.Find2 (theView); RemoveView (aViewName, theToRemoveContext); } //============================================================================== //function : RemoveView //purpose : Close and remove view from display, clear maps if neccessary //============================================================================== void ViewerTest::RemoveView (const TCollection_AsciiString& theViewName, const Standard_Boolean isContextRemoved) { if (!ViewerTest_myViews.IsBound1(theViewName)) { cout << "Wrong view name\n"; return; } // Activate another view if it's active now if (ViewerTest_myViews.Find1(theViewName) == ViewerTest::CurrentView()) { if (ViewerTest_myViews.Extent() > 1) { TCollection_AsciiString aNewViewName; for (NCollection_DoubleMap ::Iterator anIter (ViewerTest_myViews); anIter.More(); anIter.Next()) { if (anIter.Key1() != theViewName) { aNewViewName = anIter.Key1(); break; } } ActivateView (aNewViewName); } else { Handle(V3d_View) anEmptyView; #if defined(_WIN32) || defined(__WIN32__) Handle(WNT_Window) anEmptyWindow; #elif defined(__APPLE__) && !defined(MACOSX_USE_GLX) Handle(Cocoa_Window) anEmptyWindow; #else Handle(Xw_Window) anEmptyWindow; #endif VT_GetWindow() = anEmptyWindow; ViewerTest::CurrentView (anEmptyView); if (isContextRemoved) { Handle(AIS_InteractiveContext) anEmptyContext; ViewerTest::SetAISContext(anEmptyContext); } } } // Delete view Handle(V3d_View) aView = ViewerTest_myViews.Find1(theViewName); Handle(AIS_InteractiveContext) aCurrentContext = FindContextByView(aView); // Remove view resources ViewerTest_myViews.UnBind1(theViewName); aView->Window()->Unmap(); aView->Remove(); #if !defined(_WIN32) && !defined(__WIN32__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) XFlush (GetDisplayConnection()->GetDisplay()); #endif // Keep context opened only if the closed view is last to avoid // unused empty contexts if (!aCurrentContext.IsNull()) { // Check if there are more difined views in the viewer aCurrentContext->CurrentViewer()->InitDefinedViews(); if ((isContextRemoved || ViewerTest_myContexts.Size() != 1) && !aCurrentContext->CurrentViewer()->MoreDefinedViews()) { // Remove driver if there is no viewers that use it Standard_Boolean isRemoveDriver = Standard_True; for(NCollection_DoubleMap::Iterator anIter(ViewerTest_myContexts); anIter.More(); anIter.Next()) { if (aCurrentContext != anIter.Key2() && aCurrentContext->CurrentViewer()->Driver() == anIter.Value()->CurrentViewer()->Driver()) { isRemoveDriver = Standard_False; break; } } aCurrentContext->RemoveAll (Standard_False); if(isRemoveDriver) { ViewerTest_myDrivers.UnBind2 (aCurrentContext->CurrentViewer()->Driver()); #if !defined(_WIN32) && !defined(__WIN32__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) #if TCL_MAJOR_VERSION < 8 Tk_DeleteFileHandler((void*)XConnectionNumber(aCurrentContext->CurrentViewer()->Driver()->GetDisplayConnection()->GetDisplay())); #else Tk_DeleteFileHandler(XConnectionNumber(aCurrentContext->CurrentViewer()->Driver()->GetDisplayConnection()->GetDisplay())); #endif #endif } ViewerTest_myContexts.UnBind2(aCurrentContext); } } cout << "3D View - " << theViewName << " was deleted.\n"; if (Draw_ToExitOnCloseView) { Draw_Interprete ("exit"); } } //============================================================================== //function : VClose //purpose : Remove the view defined by its name //============================================================================== static int VClose (Draw_Interpretor& /*theDi*/, Standard_Integer theArgsNb, const char** theArgVec) { NCollection_List aViewList; if (theArgsNb > 1) { TCollection_AsciiString anArg (theArgVec[1]); anArg.UpperCase(); if (anArg.IsEqual ("ALL") || anArg.IsEqual ("*")) { for (NCollection_DoubleMap::Iterator anIter (ViewerTest_myViews); anIter.More(); anIter.Next()) { aViewList.Append (anIter.Key1()); } if (aViewList.IsEmpty()) { std::cout << "No view to close\n"; return 0; } } else { ViewerTest_Names aViewName (theArgVec[1]); if (!ViewerTest_myViews.IsBound1 (aViewName.GetViewName())) { std::cerr << "The view with name '" << theArgVec[1] << "' does not exist\n"; return 1; } aViewList.Append (aViewName.GetViewName()); } } else { // close active view if (ViewerTest::CurrentView().IsNull()) { std::cerr << "No active view!\n"; return 1; } aViewList.Append (ViewerTest_myViews.Find2 (ViewerTest::CurrentView())); } Standard_Boolean toRemoveContext = (theArgsNb != 3 || Draw::Atoi (theArgVec[2]) != 1); for (NCollection_List::Iterator anIter(aViewList); anIter.More(); anIter.Next()) { ViewerTest::RemoveView (anIter.Value(), toRemoveContext); } return 0; } //============================================================================== //function : VActivate //purpose : Activate the view defined by its ID //============================================================================== static int VActivate (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { if (theArgsNb > 2) { theDi << theArgVec[0] << ": wrong number of command arguments.\n" << "Usage: " << theArgVec[0] << " ViewID\n"; return 1; } if(theArgsNb == 1) { theDi.Eval("vviewlist"); return 0; } TCollection_AsciiString aNameString(theArgVec[1]); if ( strcasecmp( aNameString.ToCString(), "NONE" ) == 0 ) { TCollection_AsciiString aTitle("3D View - "); aTitle = aTitle + ViewerTest_myViews.Find2(ViewerTest::CurrentView()); SetWindowTitle (ViewerTest::CurrentView()->Window(), aTitle.ToCString()); Handle(V3d_View) anEmptyView; #if defined(_WIN32) || defined(__WIN32__) Handle(WNT_Window) anEmptyWindow; #elif defined(__APPLE__) && !defined(MACOSX_USE_GLX) Handle(Cocoa_Window) anEmptyWindow; #else Handle(Xw_Window) anEmptyWindow; #endif VT_GetWindow() = anEmptyWindow; ViewerTest::CurrentView (anEmptyView); ViewerTest::ResetEventManager(); theDi << theArgVec[0] << ": all views are inactive\n"; return 0; } ViewerTest_Names aViewNames(aNameString); // Check if this view exists in the viewer with the driver if (!ViewerTest_myViews.IsBound1(aViewNames.GetViewName())) { theDi << "Wrong view name\n"; return 1; } // Check if it is active already if (ViewerTest::CurrentView() == ViewerTest_myViews.Find1(aViewNames.GetViewName())) { theDi << theArgVec[0] << ": the view is active already\n"; return 0; } ActivateView (aViewNames.GetViewName()); return 0; } //============================================================================== //function : VViewList //purpose : Print current list of views per viewer and graphic driver ID // shared between viewers //============================================================================== static int VViewList (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { if (theArgsNb > 2) { theDi << theArgVec[0] << ": Wrong number of command arguments\n" << "Usage: " << theArgVec[0] << " name"; return 1; } if (ViewerTest_myContexts.Size() < 1) return 0; Standard_Boolean isTreeView = (( theArgsNb==1 ) || ( strcasecmp( theArgVec[1], "long" ) != 0 )); if (isTreeView) { theDi << theArgVec[0] <<":\n"; } for (NCollection_DoubleMap ::Iterator aDriverIter (ViewerTest_myDrivers); aDriverIter.More(); aDriverIter.Next()) { if (isTreeView) theDi << aDriverIter.Key1() << ":\n"; for (NCollection_DoubleMap ::Iterator aContextIter(ViewerTest_myContexts); aContextIter.More(); aContextIter.Next()) { if (aContextIter.Key1().Search(aDriverIter.Key1()) != -1) { if (isTreeView) { TCollection_AsciiString aContextName(aContextIter.Key1()); theDi << " " << aContextName.Split(aDriverIter.Key1().Length() + 1) << ":\n"; } for (NCollection_DoubleMap ::Iterator aViewIter (ViewerTest_myViews); aViewIter.More(); aViewIter.Next()) { if (aViewIter.Key1().Search(aContextIter.Key1()) != -1) { TCollection_AsciiString aViewName(aViewIter.Key1()); if (isTreeView) { if (aViewIter.Value() == ViewerTest::CurrentView()) theDi << " " << aViewName.Split(aContextIter.Key1().Length() + 1) << "(*)\n"; else theDi << " " << aViewName.Split(aContextIter.Key1().Length() + 1) << "\n"; } else { theDi << aViewName << " "; } } } } } } return 0; } //============================================================================== //function : VT_ProcessKeyPress //purpose : Handle KeyPress event from a CString //============================================================================== void VT_ProcessKeyPress (const char* buf_ret) { //cout << "KeyPress" << endl; const Handle(V3d_View) aView = ViewerTest::CurrentView(); // Letter in alphabetic order if (!strcasecmp (buf_ret, "A") && !ViewerTest_V3dView::IsCurrentViewIn2DMode()) { // AXO aView->SetProj(V3d_XposYnegZpos); } else if (!strcasecmp (buf_ret, "D") && !ViewerTest_V3dView::IsCurrentViewIn2DMode()) { // Reset aView->Reset(); } else if (!strcasecmp (buf_ret, "F")) { if (ViewerTest::GetAISContext()->NbSelected() > 0) { ViewerTest::GetAISContext()->FitSelected (aView); } else { // FitAll aView->FitAll(); } } else if (!strcasecmp (buf_ret, "H")) { // HLR std::cout << "HLR" << std::endl; aView->SetComputedMode (!aView->ComputedMode()); aView->Redraw(); } else if (!strcasecmp (buf_ret, "P")) { // Type of HLR Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if (aContext->DefaultDrawer()->TypeOfHLR() == Prs3d_TOH_Algo) aContext->DefaultDrawer()->SetTypeOfHLR(Prs3d_TOH_PolyAlgo); else aContext->DefaultDrawer()->SetTypeOfHLR(Prs3d_TOH_Algo); if (aContext->NbSelected()==0) { AIS_ListOfInteractive aListOfShapes; aContext->DisplayedObjects(aListOfShapes); for (AIS_ListIteratorOfListOfInteractive anIter(aListOfShapes); anIter.More(); anIter.Next()) { Handle(AIS_Shape) aShape = Handle(AIS_Shape)::DownCast(anIter.Value()); if (aShape.IsNull()) continue; if (aShape->TypeOfHLR() == Prs3d_TOH_PolyAlgo) aShape->SetTypeOfHLR (Prs3d_TOH_Algo); else aShape->SetTypeOfHLR (Prs3d_TOH_PolyAlgo); aContext->Redisplay (aShape, Standard_False); } } else { for (aContext->InitSelected();aContext->MoreSelected();aContext->NextSelected()) { Handle(AIS_Shape) aShape = Handle(AIS_Shape)::DownCast(aContext->SelectedInteractive()); if (aShape.IsNull()) continue; if(aShape->TypeOfHLR() == Prs3d_TOH_PolyAlgo) aShape->SetTypeOfHLR (Prs3d_TOH_Algo); else aShape->SetTypeOfHLR (Prs3d_TOH_PolyAlgo); aContext->Redisplay (aShape, Standard_False); } } aContext->UpdateCurrentViewer(); } else if (!strcasecmp (buf_ret, "S")) { std::cout << "setup Shaded display mode" << std::endl; Handle(AIS_InteractiveContext) Ctx = ViewerTest::GetAISContext(); if(Ctx->NbSelected()==0) Ctx->SetDisplayMode (AIS_Shaded, Standard_True); else{ for(Ctx->InitSelected();Ctx->MoreSelected();Ctx->NextSelected()) Ctx->SetDisplayMode(Ctx->SelectedInteractive(),1,Standard_False); Ctx->UpdateCurrentViewer(); } } else if (!strcasecmp (buf_ret, "U")) { // Unset display mode std::cout << "reset display mode to defaults" << std::endl; Handle(AIS_InteractiveContext) Ctx = ViewerTest::GetAISContext(); if(Ctx->NbSelected()==0) Ctx->SetDisplayMode (AIS_WireFrame, Standard_True); else{ for(Ctx->InitSelected();Ctx->MoreSelected();Ctx->NextSelected()) Ctx->UnsetDisplayMode(Ctx->SelectedInteractive(),Standard_False); Ctx->UpdateCurrentViewer(); } } else if (!strcasecmp (buf_ret, "T") && !ViewerTest_V3dView::IsCurrentViewIn2DMode()) { // Top aView->SetProj(V3d_Zpos); } else if (!strcasecmp (buf_ret, "B") && !ViewerTest_V3dView::IsCurrentViewIn2DMode()) { // Bottom aView->SetProj(V3d_Zneg); } else if (!strcasecmp (buf_ret, "L") && !ViewerTest_V3dView::IsCurrentViewIn2DMode()) { // Left aView->SetProj(V3d_Xneg); } else if (!strcasecmp (buf_ret, "R") && !ViewerTest_V3dView::IsCurrentViewIn2DMode()) { // Right aView->SetProj(V3d_Xpos); } else if (!strcasecmp (buf_ret, "W")) { std::cout << "setup WireFrame display mode" << std::endl; Handle(AIS_InteractiveContext) Ctx = ViewerTest::GetAISContext(); if(Ctx->NbSelected()==0) Ctx->SetDisplayMode (AIS_WireFrame, Standard_True); else{ for(Ctx->InitSelected();Ctx->MoreSelected();Ctx->NextSelected()) Ctx->SetDisplayMode(Ctx->SelectedInteractive(),0,Standard_False); Ctx->UpdateCurrentViewer(); } } else if (!strcasecmp (buf_ret, ",")) { ViewerTest::GetAISContext()->HilightNextDetected(ViewerTest::CurrentView()); } else if (!strcasecmp (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(); if (!aCtx.IsNull() && aCtx->NbSelected() > 0) { Draw_Interprete ("verase"); } } else if (*buf_ret == THE_KEY_ESCAPE) { Handle(AIS_InteractiveContext) aCtx = ViewerTest::GetAISContext(); if (!aCtx.IsNull() && Draw_ToCloseViewOnEsc) { Draw_Interprete (Draw_ToExitOnCloseView ? "exit" : "vclose"); } } else { // Number const Standard_Integer aSelMode = Draw::Atoi(buf_ret); if (aSelMode >= 0 && aSelMode <= 7) { bool toEnable = true; if (const Handle(AIS_InteractiveContext) aCtx = ViewerTest::GetAISContext()) { AIS_ListOfInteractive aPrsList; aCtx->DisplayedObjects (aPrsList); for (AIS_ListOfInteractive::Iterator aPrsIter (aPrsList); aPrsIter.More() && toEnable; aPrsIter.Next()) { TColStd_ListOfInteger aModes; aCtx->ActivatedModes (aPrsIter.Value(), aModes); for (TColStd_ListOfInteger::Iterator aModeIter (aModes); aModeIter.More() && toEnable; aModeIter.Next()) { if (aModeIter.Value() == aSelMode) { toEnable = false; } } } } TCollection_AsciiString aCmd = TCollection_AsciiString ("vselmode ") + aSelMode + (toEnable ? " 1" : " 0"); Draw_Interprete (aCmd.ToCString()); } } } //============================================================================== //function : VT_ProcessExpose //purpose : Redraw the View on an Expose Event //============================================================================== void VT_ProcessExpose() { Handle(V3d_View) aView3d = ViewerTest::CurrentView(); if (!aView3d.IsNull()) { aView3d->Redraw(); } } //============================================================================== //function : VT_ProcessConfigure //purpose : Resize the View on an Configure Event //============================================================================== void VT_ProcessConfigure() { Handle(V3d_View) aView3d = ViewerTest::CurrentView(); if (aView3d.IsNull()) { return; } aView3d->MustBeResized(); aView3d->Update(); aView3d->Redraw(); } //============================================================================== //function : VT_ProcessButton1Press //purpose : Picking //============================================================================== Standard_Boolean VT_ProcessButton1Press (Standard_Integer , const char** theArgVec, Standard_Boolean theToPick, Standard_Boolean theIsShift) { if (TheIsAnimating) { TheIsAnimating = Standard_False; return Standard_False; } if (theToPick) { Standard_Real X, Y, Z; ViewerTest::CurrentView()->Convert (X_Motion, Y_Motion, X, Y, Z); Draw::Set (theArgVec[1], X); Draw::Set (theArgVec[2], Y); Draw::Set (theArgVec[3], Z); } if (theIsShift) { ViewerTest::CurrentEventManager()->ShiftSelect(); } else { ViewerTest::CurrentEventManager()->Select(); } return Standard_False; } //============================================================================== //function : VT_ProcessButton1Release //purpose : End selecting //============================================================================== void VT_ProcessButton1Release (Standard_Boolean theIsShift) { if (IsDragged) { IsDragged = Standard_False; Handle(ViewerTest_EventManager) EM = ViewerTest::CurrentEventManager(); if (theIsShift) { EM->ShiftSelect (X_ButtonPress, Y_ButtonPress, X_Motion, Y_Motion); } else { EM->Select (X_ButtonPress, Y_ButtonPress, X_Motion, Y_Motion); } } } //============================================================================== //function : VT_ProcessButton3Press //purpose : Start Rotation //============================================================================== void VT_ProcessButton3Press() { if (ViewerTest_V3dView::IsCurrentViewIn2DMode()) { return; } Start_Rot = 1; HasHlrOnBeforeRotation = ViewerTest::CurrentView()->ComputedMode(); if (HasHlrOnBeforeRotation) { ViewerTest::CurrentView()->SetComputedMode (Standard_False); } ViewerTest::CurrentView()->StartRotation( X_ButtonPress, Y_ButtonPress ); } //============================================================================== //function : VT_ProcessButton3Release //purpose : End rotation //============================================================================== void VT_ProcessButton3Release() { if (Start_Rot) { Start_Rot = 0; if (HasHlrOnBeforeRotation) { HasHlrOnBeforeRotation = Standard_False; ViewerTest::CurrentView()->SetComputedMode (Standard_True); ViewerTest::CurrentView()->Redraw(); } } } //============================================================================== //function : ProcessControlButton1Motion //purpose : Zoom //============================================================================== #if defined(_WIN32) || ! defined(__APPLE__) || defined(MACOSX_USE_GLX) static void ProcessControlButton1Motion() { ViewerTest::CurrentView()->Zoom( X_ButtonPress, Y_ButtonPress, X_Motion, Y_Motion); X_ButtonPress = X_Motion; Y_ButtonPress = Y_Motion; } #endif //============================================================================== //function : VT_ProcessControlButton2Motion //purpose : Panning //============================================================================== void VT_ProcessControlButton2Motion() { Standard_Integer aDx = X_Motion - X_ButtonPress; Standard_Integer aDy = Y_Motion - Y_ButtonPress; aDy = -aDy; // Xwindow Y axis is from top to Bottom ViewerTest::CurrentView()->Pan (aDx, aDy); X_ButtonPress = X_Motion; Y_ButtonPress = Y_Motion; } //============================================================================== //function : VT_ProcessControlButton3Motion //purpose : Rotation //============================================================================== void VT_ProcessControlButton3Motion() { if (Start_Rot) { ViewerTest::CurrentView()->Rotation (X_Motion, Y_Motion); } } //============================================================================== //function : VT_ProcessMotion //purpose : //============================================================================== void VT_ProcessMotion() { //pre-hilights detected objects at mouse position Handle(ViewerTest_EventManager) EM = ViewerTest::CurrentEventManager(); EM->MoveTo(X_Motion, Y_Motion); } void ViewerTest::GetMousePosition(Standard_Integer& Xpix,Standard_Integer& Ypix) { Xpix = X_Motion;Ypix=Y_Motion; } //============================================================================== //function : ViewProject: implements VAxo, VTop, VLeft, ... //purpose : Switches to an axonometric, top, left and other views //============================================================================== static int ViewProject(Draw_Interpretor& di, const V3d_TypeOfOrientation ori) { if ( ViewerTest::CurrentView().IsNull() ) { di<<"Call vinit before this command, please\n"; return 1; } ViewerTest::CurrentView()->SetProj(ori); return 0; } //============================================================================== //function : VAxo //purpose : Switch to an Axonometric view //Draw arg : No args //============================================================================== static int VAxo(Draw_Interpretor& di, Standard_Integer , const char** ) { return ViewProject(di, V3d_XposYnegZpos); } //============================================================================== //function : VTop //purpose : Switch to a Top View //Draw arg : No args //============================================================================== static int VTop(Draw_Interpretor& di, Standard_Integer , const char** ) { return ViewProject(di, V3d_Zpos); } //============================================================================== //function : VBottom //purpose : Switch to a Bottom View //Draw arg : No args //============================================================================== static int VBottom(Draw_Interpretor& di, Standard_Integer , const char** ) { return ViewProject(di, V3d_Zneg); } //============================================================================== //function : VLeft //purpose : Switch to a Left View //Draw arg : No args //============================================================================== static int VLeft(Draw_Interpretor& di, Standard_Integer , const char** ) { return ViewProject(di, V3d_Xneg); } //============================================================================== //function : VRight //purpose : Switch to a Right View //Draw arg : No args //============================================================================== static int VRight(Draw_Interpretor& di, Standard_Integer , const char** ) { return ViewProject(di, V3d_Xpos); } //============================================================================== //function : VFront //purpose : Switch to a Front View //Draw arg : No args //============================================================================== static int VFront(Draw_Interpretor& di, Standard_Integer , const char** ) { return ViewProject(di, V3d_Yneg); } //============================================================================== //function : VBack //purpose : Switch to a Back View //Draw arg : No args //============================================================================== static int VBack(Draw_Interpretor& di, Standard_Integer , const char** ) { return ViewProject(di, V3d_Ypos); } //============================================================================== //function : VHelp //purpose : Dsiplay help on viewer Keyboead and mouse commands //Draw arg : No args //============================================================================== static int VHelp(Draw_Interpretor& di, Standard_Integer , const char** ) { di << "Q : Quit the application\n"; di << "=========================\n"; di << "F : FitAll\n"; di << "T : TopView\n"; di << "B : BottomView\n"; di << "R : RightView\n"; di << "L : LeftView\n"; di << "A : AxonometricView\n"; di << "D : ResetView\n"; di << "=========================\n"; di << "S : Shading\n"; di << "W : Wireframe\n"; di << "H : HidelLineRemoval\n"; di << "U : Unset display mode\n"; di << "Delete : Remove selection from viewer\n"; di << "=========================\n"; di << "Selection mode \n"; di << "0 : Shape\n"; di << "1 : Vertex\n"; di << "2 : Edge\n"; di << "3 : Wire\n"; di << "4 : Face\n"; di << "5 : Shell\n"; di << "6 : Solid\n"; di << "7 : Compound\n"; di << "=========================\n"; di << "Z : Switch Z clipping On/Off\n"; di << ", : Hilight next detected\n"; di << ". : Hilight previous detected\n"; return 0; } #ifdef _WIN32 static Standard_Boolean Ppick = 0; static Standard_Integer Pargc = 0; static const char** Pargv = NULL; static LRESULT WINAPI AdvViewerWindowProc( HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam ) { if (!ViewerTest_myViews.IsEmpty()) { WPARAM fwKeys = wParam; switch( Msg ) { case WM_CLOSE: { // Delete view from map of views ViewerTest::RemoveView(FindViewIdByWindowHandle(hwnd)); return 0; } break; case WM_ACTIVATE: if(LOWORD(wParam) == WA_CLICKACTIVE || LOWORD(wParam) == WA_ACTIVE || ViewerTest::CurrentView().IsNull()) { // Activate inactive window if(GetWindowHandle(VT_GetWindow()) != hwnd) { ActivateView (FindViewIdByWindowHandle(hwnd)); } } break; case WM_LBUTTONUP: if (IsDragged && !DragFirst) { if (!GetActiveAISManipulator().IsNull()) { GetActiveAISManipulator()->StopTransform(); ViewerTest::GetAISContext()->ClearSelected (Standard_True); } if (ViewerTest::GetAISContext()->IsDisplayed (GetRubberBand())) { ViewerTest::GetAISContext()->Remove (GetRubberBand(), Standard_False); ViewerTest::GetAISContext()->CurrentViewer()->RedrawImmediate(); } VT_ProcessButton1Release ((fwKeys & MK_SHIFT) != 0); } IsDragged = Standard_False; return ViewerWindowProc( hwnd, Msg, wParam, lParam ); case WM_RBUTTONUP: if (IsDragged && !DragFirst) { if (!GetActiveAISManipulator().IsNull()) { GetActiveAISManipulator()->StopTransform (Standard_False); ViewerTest::GetAISContext()->ClearSelected (Standard_True); } IsDragged = Standard_False; } return ViewerWindowProc (hwnd, Msg, wParam, lParam); case WM_LBUTTONDOWN: if (!GetActiveAISManipulator().IsNull()) { IsDragged = ( fwKeys == MK_LBUTTON ); } else { IsDragged = ( fwKeys == MK_LBUTTON || fwKeys == ( MK_LBUTTON | MK_SHIFT ) ); } if (IsDragged) { DragFirst = Standard_True; X_ButtonPress = LOWORD(lParam); Y_ButtonPress = HIWORD(lParam); } return ViewerWindowProc( hwnd, Msg, wParam, lParam ); case WM_MOUSEMOVE: if (IsDragged) { X_Motion = LOWORD (lParam); Y_Motion = HIWORD (lParam); if (!GetActiveAISManipulator().IsNull()) { if (DragFirst) { GetActiveAISManipulator()->StartTransform (X_ButtonPress, Y_ButtonPress, ViewerTest::CurrentView()); } else { GetActiveAISManipulator()->Transform (X_Motion, Y_Motion, ViewerTest::CurrentView()); ViewerTest::GetAISContext()->CurrentViewer()->Redraw(); } } else { bool toRedraw = false; if (!DragFirst && ViewerTest::GetAISContext()->IsDisplayed (GetRubberBand())) { ViewerTest::GetAISContext()->Remove (GetRubberBand(), Standard_False); toRedraw = true; } RECT aRect; if (GetClientRect (hwnd, &aRect)) { int aHeight = aRect.bottom - aRect.top; GetRubberBand()->SetRectangle (X_ButtonPress, aHeight - Y_ButtonPress, X_Motion, aHeight - Y_Motion); ViewerTest::GetAISContext()->Display (GetRubberBand(), 0, -1, Standard_False, Standard_True, AIS_DS_Displayed); toRedraw = true; } if (toRedraw) { ViewerTest::GetAISContext()->CurrentViewer()->RedrawImmediate(); } } DragFirst = Standard_False; } else return ViewerWindowProc( hwnd, Msg, wParam, lParam ); break; default: return ViewerWindowProc( hwnd, Msg, wParam, lParam ); } return 0; } return ViewerWindowProc( hwnd, Msg, wParam, lParam ); } static LRESULT WINAPI ViewerWindowProc( HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam ) { static int Up = 1; const Handle(V3d_View)& aView = ViewerTest::CurrentView(); if (aView.IsNull()) { return DefWindowProcW (hwnd, Msg, wParam, lParam); } PAINTSTRUCT ps; switch( Msg ) { case WM_PAINT: BeginPaint(hwnd, &ps); EndPaint(hwnd, &ps); VT_ProcessExpose(); break; 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)) { char c[2]; c[0] = (char) wParam; c[1] = '\0'; if (wParam == VK_DELETE) { c[0] = THE_KEY_DELETE; } else if (wParam == VK_ESCAPE) { c[0] = THE_KEY_ESCAPE; } // comma else if (wParam == VK_OEM_COMMA) { c[0] = ','; } // dot else if (wParam == VK_OEM_PERIOD) { c[0] = '.'; } else if (wParam == VK_DIVIDE) { c[0] = '/'; } // dot else if (wParam == VK_MULTIPLY) { c[0] = '*'; } VT_ProcessKeyPress (c); } break; case WM_LBUTTONUP: case WM_MBUTTONUP: case WM_RBUTTONUP: Up = 1; VT_ProcessButton3Release(); break; case WM_LBUTTONDOWN: case WM_MBUTTONDOWN: case WM_RBUTTONDOWN: { WPARAM fwKeys = wParam; Up = 0; X_ButtonPress = LOWORD(lParam); Y_ButtonPress = HIWORD(lParam); if (Msg == WM_LBUTTONDOWN) { if ((fwKeys & MK_CONTROL) != 0) { Ppick = VT_ProcessButton1Press (Pargc, Pargv, Ppick, (fwKeys & MK_SHIFT) != 0); } else { VT_ProcessButton1Press (Pargc, Pargv, Ppick, (fwKeys & MK_SHIFT) != 0); } } else if (Msg == WM_RBUTTONDOWN) { // Start rotation VT_ProcessButton3Press(); } } 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; WPARAM fwKeys = wParam; X_Motion = LOWORD(lParam); Y_Motion = HIWORD(lParam); if ( Up && (fwKeys & ( MK_LBUTTON|MK_MBUTTON|MK_RBUTTON )) != 0 ) { Up = 0; X_ButtonPress = LOWORD(lParam); Y_ButtonPress = HIWORD(lParam); if ((fwKeys & MK_RBUTTON) != 0) { // Start rotation VT_ProcessButton3Press(); } } if ((fwKeys & MK_CONTROL) != 0) { if ((fwKeys & MK_LBUTTON) != 0) { ProcessControlButton1Motion(); } else if ((fwKeys & MK_MBUTTON) != 0 || ((fwKeys & MK_LBUTTON) != 0 && (fwKeys & MK_RBUTTON) != 0)) { VT_ProcessControlButton2Motion(); } else if ((fwKeys & MK_RBUTTON) != 0) { VT_ProcessControlButton3Motion(); } } else if (GetWindowHandle (VT_GetWindow()) == hwnd) { VT_ProcessMotion(); } } break; default: return DefWindowProcW (hwnd, Msg, wParam, lParam); } return 0L; } //============================================================================== //function : ViewerMainLoop //purpose : Get a Event on the view and dispatch it //============================================================================== int ViewerMainLoop(Standard_Integer argc, const char** argv) { Ppick = (argc > 0)? 1 : 0; Pargc = argc; Pargv = argv; if ( Ppick ) { MSG msg; msg.wParam = 1; cout << "Start picking" << endl; while ( Ppick == 1 ) { // Wait for a VT_ProcessButton1Press() to toggle pick to 1 or 0 if (GetMessageW (&msg, NULL, 0, 0)) { TranslateMessage (&msg); DispatchMessageW (&msg); } } cout << "Picking done" << endl; } return Ppick; } #elif !defined(__APPLE__) || defined(MACOSX_USE_GLX) int min( int a, int b ) { if( ab ) return a; else return b; } int ViewerMainLoop(Standard_Integer argc, const char** argv) { static XEvent aReport; Standard_Boolean pick = argc > 0; Display *aDisplay = GetDisplayConnection()->GetDisplay(); XNextEvent (aDisplay, &aReport); // Handle event for the chosen display connection switch (aReport.type) { case ClientMessage: { if((Atom)aReport.xclient.data.l[0] == GetDisplayConnection()->GetAtom(Aspect_XA_DELETE_WINDOW)) { // Close the window ViewerTest::RemoveView(FindViewIdByWindowHandle (aReport.xclient.window)); } } return 0; case FocusIn: { // Activate inactive view Window aWindow = GetWindowHandle(VT_GetWindow()); if(aWindow != aReport.xfocus.window) { ActivateView (FindViewIdByWindowHandle (aReport.xfocus.window)); } } break; case Expose: { VT_ProcessExpose(); } break; case ConfigureNotify: { VT_ProcessConfigure(); } break; case KeyPress: { KeySym ks_ret ; char buf_ret[11] ; int ret_len ; XComposeStatus status_in_out; ret_len = XLookupString( ( XKeyEvent *)&aReport , (char *) buf_ret , 10 , &ks_ret , &status_in_out ) ; buf_ret[ret_len] = '\0' ; if (ret_len) { VT_ProcessKeyPress (buf_ret); } } break; case ButtonPress: { X_ButtonPress = aReport.xbutton.x; Y_ButtonPress = aReport.xbutton.y; if (aReport.xbutton.button == Button1) { if (aReport.xbutton.state & ControlMask) { pick = VT_ProcessButton1Press (argc, argv, pick, (aReport.xbutton.state & ShiftMask)); } else { IsDragged = Standard_True; DragFirst = Standard_True; } } else if (aReport.xbutton.button == Button3) { // Start rotation VT_ProcessButton3Press(); } } break; case ButtonRelease: { if( IsDragged ) { if( !DragFirst ) { if (ViewerTest::GetAISContext()->IsDisplayed (GetRubberBand())) { ViewerTest::GetAISContext()->Remove (GetRubberBand(), Standard_False); ViewerTest::GetAISContext()->CurrentViewer()->RedrawImmediate(); } } Handle( AIS_InteractiveContext ) aContext = ViewerTest::GetAISContext(); if( aContext.IsNull() ) { cout << "The context is null. Please use vinit before createmesh" << endl; return 0; } Standard_Boolean ShiftPressed = ( aReport.xbutton.state & ShiftMask ); if( aReport.xbutton.button==1 ) if( DragFirst ) if( ShiftPressed ) { aContext->ShiftSelect (Standard_True); } else { aContext->Select (Standard_True); } else if( ShiftPressed ) { aContext->ShiftSelect(Min(X_ButtonPress, X_Motion), Min(Y_ButtonPress, Y_Motion), Max(X_ButtonPress, X_Motion), Max(Y_ButtonPress, Y_Motion), ViewerTest::CurrentView(), Standard_True); } else { aContext->Select(Min(X_ButtonPress, X_Motion), Min(Y_ButtonPress, Y_Motion), Max(X_ButtonPress, X_Motion), Max(Y_ButtonPress, Y_Motion), ViewerTest::CurrentView(), Standard_True); } else VT_ProcessButton3Release(); IsDragged = Standard_False; } else VT_ProcessButton3Release(); } break; case MotionNotify: { if (GetWindowHandle (VT_GetWindow()) != aReport.xmotion.window) { break; } if( IsDragged ) { if( !DragFirst ) { if (ViewerTest::GetAISContext()->IsDisplayed (GetRubberBand())) { ViewerTest::GetAISContext()->Remove (GetRubberBand(), Standard_False); } } X_Motion = aReport.xmotion.x; Y_Motion = aReport.xmotion.y; DragFirst = Standard_False; Window aWindow = GetWindowHandle(VT_GetWindow()); Window aRoot; int anX, anY; unsigned int aWidth, aHeight, aBorderWidth, aDepth; XGetGeometry (aDisplay, aWindow, &aRoot, &anX, &anY, &aWidth, &aHeight, &aBorderWidth, &aDepth); GetRubberBand()->SetRectangle (X_ButtonPress, aHeight - Y_ButtonPress, X_Motion, aHeight - Y_Motion); ViewerTest::GetAISContext()->Display (GetRubberBand(), 0, -1, Standard_False, Standard_True, AIS_DS_Displayed); ViewerTest::GetAISContext()->CurrentViewer()->RedrawImmediate(); } else { X_Motion = aReport.xmotion.x; Y_Motion = aReport.xmotion.y; // remove all the ButtonMotionMaskr while( XCheckMaskEvent( aDisplay, ButtonMotionMask, &aReport) ) ; if ( aReport.xmotion.state & ControlMask ) { if ( aReport.xmotion.state & Button1Mask ) { ProcessControlButton1Motion(); } else if ( aReport.xmotion.state & Button2Mask ) { VT_ProcessControlButton2Motion(); } else if ( aReport.xmotion.state & Button3Mask ) { VT_ProcessControlButton3Motion(); } } else { VT_ProcessMotion(); } } } break; } return pick; } //============================================================================== //function : VProcessEvents //purpose : call by Tk_CreateFileHandler() to be able to manage the // event in the Viewer window //============================================================================== static void VProcessEvents(ClientData,int) { NCollection_Vector anEventNumbers; // Get number of messages from every display for (NCollection_DoubleMap ::Iterator anIter (ViewerTest_myDrivers); anIter.More(); anIter.Next()) { anEventNumbers.Append(XPending (anIter.Key2()->GetDisplayConnection()->GetDisplay())); } // Handle events for every display int anEventIter = 0; for (NCollection_DoubleMap ::Iterator anIter (ViewerTest_myDrivers); anIter.More(); anIter.Next(), anEventIter++) { for (int i = 0; i < anEventNumbers.Value(anEventIter) && XPending (anIter.Key2()->GetDisplayConnection()->GetDisplay()) > 0; ++i) { SetDisplayConnection (anIter.Key2()->GetDisplayConnection()); int anEventResult = ViewerMainLoop( 0, NULL); // If window is closed or context was not found finish current event processing loop if (!anEventResult) return; } } SetDisplayConnection (ViewerTest::GetAISContext()->CurrentViewer()->Driver()->GetDisplayConnection()); } #endif //============================================================================== //function : OSWindowSetup //purpose : Setup for the X11 window to be able to cath the event //============================================================================== static void OSWindowSetup() { #if !defined(_WIN32) && !defined(__WIN32__) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) // X11 Window window = VT_GetWindow()->XWindow(); SetDisplayConnection (ViewerTest::CurrentView()->Viewer()->Driver()->GetDisplayConnection()); Display *aDisplay = GetDisplayConnection()->GetDisplay(); XSynchronize(aDisplay, 1); // X11 : For keyboard on SUN XWMHints wmhints; wmhints.flags = InputHint; wmhints.input = 1; XSetWMHints( aDisplay, window, &wmhints); XSelectInput( aDisplay, window, ExposureMask | KeyPressMask | ButtonPressMask | ButtonReleaseMask | StructureNotifyMask | PointerMotionMask | Button1MotionMask | Button2MotionMask | Button3MotionMask | FocusChangeMask ); Atom aDeleteWindowAtom = GetDisplayConnection()->GetAtom(Aspect_XA_DELETE_WINDOW); XSetWMProtocols(aDisplay, window, &aDeleteWindowAtom, 1); XSynchronize(aDisplay, 0); #else // _WIN32 #endif } //============================================================================== //function : VFit //purpose : //============================================================================== static int VFit (Draw_Interpretor& /*theDi*/, Standard_Integer theArgNb, const char** theArgv) { const Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cout << "Error: no active viewer!\n"; return 1; } Standard_Boolean toFit = Standard_True; ViewerTest_AutoUpdater anUpdateTool (Handle(AIS_InteractiveContext)(), aView); for (Standard_Integer anArgIter = 1; anArgIter < theArgNb; ++anArgIter) { TCollection_AsciiString anArg (theArgv[anArgIter]); anArg.LowerCase(); if (anUpdateTool.parseRedrawMode (anArg)) { continue; } else if (anArg == "-selected") { ViewerTest::GetAISContext()->FitSelected (aView, 0.01, Standard_False); toFit = Standard_False; } else { std::cout << "Syntax error at '" << anArg << "'\n"; } } if (toFit) { aView->FitAll (0.01, Standard_False); } return 0; } //======================================================================= //function : VFitArea //purpose : Fit view to show area located between two points // : given in world 2D or 3D coordinates. //======================================================================= static int VFitArea (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cerr << theArgVec[0] << "Error: No active view.\n"; return 1; } // Parse arguments. gp_Pnt aWorldPnt1 (0.0, 0.0, 0.0); gp_Pnt aWorldPnt2 (0.0, 0.0, 0.0); if (theArgNb == 5) { aWorldPnt1.SetX (Draw::Atof (theArgVec[1])); aWorldPnt1.SetY (Draw::Atof (theArgVec[2])); aWorldPnt2.SetX (Draw::Atof (theArgVec[3])); aWorldPnt2.SetY (Draw::Atof (theArgVec[4])); } else if (theArgNb == 7) { aWorldPnt1.SetX (Draw::Atof (theArgVec[1])); aWorldPnt1.SetY (Draw::Atof (theArgVec[2])); aWorldPnt1.SetZ (Draw::Atof (theArgVec[3])); aWorldPnt2.SetX (Draw::Atof (theArgVec[4])); aWorldPnt2.SetY (Draw::Atof (theArgVec[5])); aWorldPnt2.SetZ (Draw::Atof (theArgVec[6])); } else { std::cerr << theArgVec[0] << "Error: Invalid number of arguments.\n"; theDI.PrintHelp(theArgVec[0]); return 1; } // Convert model coordinates to view space Handle(Graphic3d_Camera) aCamera = aView->Camera(); gp_Pnt aViewPnt1 = aCamera->ConvertWorld2View (aWorldPnt1); gp_Pnt aViewPnt2 = aCamera->ConvertWorld2View (aWorldPnt2); // Determine fit area gp_Pnt2d aMinCorner (Min (aViewPnt1.X(), aViewPnt2.X()), Min (aViewPnt1.Y(), aViewPnt2.Y())); gp_Pnt2d aMaxCorner (Max (aViewPnt1.X(), aViewPnt2.X()), Max (aViewPnt1.Y(), aViewPnt2.Y())); Standard_Real aDiagonal = aMinCorner.Distance (aMaxCorner); if (aDiagonal < Precision::Confusion()) { std::cerr << theArgVec[0] << "Error: view area is too small.\n"; return 1; } aView->FitAll (aMinCorner.X(), aMinCorner.Y(), aMaxCorner.X(), aMaxCorner.Y()); return 0; } //============================================================================== //function : VZFit //purpose : ZFitall, no DRAW arguments //Draw arg : No args //============================================================================== static int VZFit (Draw_Interpretor& /*theDi*/, Standard_Integer theArgsNb, const char** theArgVec) { const Handle(V3d_View)& aCurrentView = ViewerTest::CurrentView(); if (aCurrentView.IsNull()) { std::cout << theArgVec[0] << ": Call vinit before this command, please.\n"; return 1; } if (theArgsNb == 1) { aCurrentView->ZFitAll(); aCurrentView->Redraw(); return 0; } Standard_Real aScale = 1.0; if (theArgsNb >= 2) { aScale = Draw::Atoi (theArgVec[1]); } aCurrentView->ZFitAll (aScale); aCurrentView->Redraw(); return 0; } //============================================================================== //function : VRepaint //purpose : //============================================================================== static int VRepaint (Draw_Interpretor& , Standard_Integer theArgNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cout << "Error: no active viewer!\n"; return 1; } Standard_Boolean isImmediateUpdate = Standard_False; for (Standard_Integer anArgIter = 1; anArgIter < theArgNb; ++anArgIter) { TCollection_AsciiString anArg (theArgVec[anArgIter]); anArg.LowerCase(); if (anArg == "-immediate") { isImmediateUpdate = Standard_True; if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], isImmediateUpdate)) { ++anArgIter; } } else { std::cout << "Syntax error at '" << anArg << "'\n"; } } if (isImmediateUpdate) { aView->RedrawImmediate(); } else { aView->Redraw(); } return 0; } //============================================================================== //function : VClear //purpose : Remove all the object from the viewer //Draw arg : No args //============================================================================== static int VClear(Draw_Interpretor& , Standard_Integer , const char** ) { Handle(V3d_View) V = ViewerTest::CurrentView(); if(!V.IsNull()) ViewerTest::Clear(); return 0; } //============================================================================== //function : VPick //purpose : //============================================================================== static int VPick(Draw_Interpretor& di, Standard_Integer argc, const char** argv) { if (ViewerTest::CurrentView().IsNull() ) return 1; if ( argc < 4 ) { di << argv[0] << "Invalid number of arguments\n"; return 1; } while (ViewerMainLoop( argc, argv)) { } return 0; } //============================================================================== //function : VSetBg //purpose : Load image as background //============================================================================== static int VSetBg(Draw_Interpretor& di, Standard_Integer argc, const char** argv) { if (argc < 2 || argc > 3) { di << "Usage : " << argv[0] << " imagefile [filltype] : Load image as background\n"; di << "filltype can be one of CENTERED, TILED, STRETCH, NONE\n"; return 1; } Handle(AIS_InteractiveContext) AISContext = ViewerTest::GetAISContext(); if(AISContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } Aspect_FillMethod aFillType = Aspect_FM_CENTERED; if (argc == 3) { const char* szType = argv[2]; if (strcmp(szType, "NONE" ) == 0) aFillType = Aspect_FM_NONE; else if (strcmp(szType, "CENTERED") == 0) aFillType = Aspect_FM_CENTERED; else if (strcmp(szType, "TILED" ) == 0) aFillType = Aspect_FM_TILED; else if (strcmp(szType, "STRETCH" ) == 0) aFillType = Aspect_FM_STRETCH; else { di << "Wrong fill type : " << szType << "\n"; di << "Must be one of CENTERED, TILED, STRETCH, NONE\n"; return 1; } } Handle(V3d_View) V3dView = ViewerTest::CurrentView(); V3dView->SetBackgroundImage(argv[1], aFillType, Standard_True); return 0; } //============================================================================== //function : VSetBgMode //purpose : Change background image fill type //============================================================================== static int VSetBgMode(Draw_Interpretor& di, Standard_Integer argc, const char** argv) { if (argc != 2) { di << "Usage : " << argv[0] << " filltype : Change background image mode\n"; di << "filltype must be one of CENTERED, TILED, STRETCH, NONE\n"; return 1; } Handle(AIS_InteractiveContext) AISContext = ViewerTest::GetAISContext(); if(AISContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } Aspect_FillMethod aFillType = Aspect_FM_NONE; const char* szType = argv[1]; if (strcmp(szType, "NONE" ) == 0) aFillType = Aspect_FM_NONE; else if (strcmp(szType, "CENTERED") == 0) aFillType = Aspect_FM_CENTERED; else if (strcmp(szType, "TILED" ) == 0) aFillType = Aspect_FM_TILED; else if (strcmp(szType, "STRETCH" ) == 0) aFillType = Aspect_FM_STRETCH; else { di << "Wrong fill type : " << szType << "\n"; di << "Must be one of CENTERED, TILED, STRETCH, NONE\n"; return 1; } Handle(V3d_View) V3dView = ViewerTest::CurrentView(); V3dView->SetBgImageStyle(aFillType, Standard_True); return 0; } //============================================================================== //function : VSetGradientBg //purpose : Mount gradient background //============================================================================== static int VSetGradientBg(Draw_Interpretor& di, Standard_Integer argc, const char** argv) { if (argc != 8 ) { di << "Usage : " << argv[0] << " R1 G1 B1 R2 G2 B2 Type : Mount gradient background\n"; di << "R1,G1,B1,R2,G2,B2 = [0..255]\n"; di << "Type must be one of 0 = NONE, 1 = HOR, 2 = VER, 3 = DIAG1, 4 = DIAG2\n"; di << " 5 = CORNER1, 6 = CORNER2, 7 = CORNER3, 8 = CORNER4\n"; return 1; } Handle(AIS_InteractiveContext) AISContext = ViewerTest::GetAISContext(); if(AISContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } if (argc == 8) { Standard_Real R1 = Draw::Atof(argv[1])/255.; Standard_Real G1 = Draw::Atof(argv[2])/255.; Standard_Real B1 = Draw::Atof(argv[3])/255.; Quantity_Color aColor1(R1,G1,B1,Quantity_TOC_RGB); Standard_Real R2 = Draw::Atof(argv[4])/255.; Standard_Real G2 = Draw::Atof(argv[5])/255.; Standard_Real B2 = Draw::Atof(argv[6])/255.; Quantity_Color aColor2(R2,G2,B2,Quantity_TOC_RGB); int aType = Draw::Atoi(argv[7]); if( aType < 0 || aType > 8 ) { di << "Wrong fill type \n"; di << "Must be one of 0 = NONE, 1 = HOR, 2 = VER, 3 = DIAG1, 4 = DIAG2\n"; di << " 5 = CORNER1, 6 = CORNER2, 7 = CORNER3, 8 = CORNER4\n"; return 1; } Aspect_GradientFillMethod aMethod = Aspect_GradientFillMethod(aType); Handle(V3d_View) V3dView = ViewerTest::CurrentView(); V3dView->SetBgGradientColors( aColor1, aColor2, aMethod, 1); } return 0; } //============================================================================== //function : VSetGradientBgMode //purpose : Change gradient background fill style //============================================================================== static int VSetGradientBgMode(Draw_Interpretor& di, Standard_Integer argc, const char** argv) { if (argc != 2 ) { di << "Usage : " << argv[0] << " Type : Change gradient background fill type\n"; di << "Type must be one of 0 = NONE, 1 = HOR, 2 = VER, 3 = DIAG1, 4 = DIAG2\n"; di << " 5 = CORNER1, 6 = CORNER2, 7 = CORNER3, 8 = CORNER4\n"; return 1; } Handle(AIS_InteractiveContext) AISContext = ViewerTest::GetAISContext(); if(AISContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } if (argc == 2) { int aType = Draw::Atoi(argv[1]); if( aType < 0 || aType > 8 ) { di << "Wrong fill type \n"; di << "Must be one of 0 = NONE, 1 = HOR, 2 = VER, 3 = DIAG1, 4 = DIAG2\n"; di << " 5 = CORNER1, 6 = CORNER2, 7 = CORNER3, 8 = CORNER4\n"; return 1; } Aspect_GradientFillMethod aMethod = Aspect_GradientFillMethod(aType); Handle(V3d_View) V3dView = ViewerTest::CurrentView(); V3dView->SetBgGradientStyle( aMethod, 1 ); } return 0; } //============================================================================== //function : VSetColorBg //purpose : Set color background //============================================================================== static int VSetColorBg(Draw_Interpretor& di, Standard_Integer argc, const char** argv) { if (argc != 4 ) { di << "Usage : " << argv[0] << " R G B : Set color background\n"; di << "R,G,B = [0..255]\n"; return 1; } Handle(AIS_InteractiveContext) AISContext = ViewerTest::GetAISContext(); if(AISContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } if (argc == 4) { Standard_Real R = Draw::Atof(argv[1])/255.; Standard_Real G = Draw::Atof(argv[2])/255.; Standard_Real B = Draw::Atof(argv[3])/255.; Quantity_Color aColor(R,G,B,Quantity_TOC_RGB); Handle(V3d_View) V3dView = ViewerTest::CurrentView(); V3dView->SetBackgroundColor( aColor ); V3dView->Update(); } return 0; } //============================================================================== //function : VSetDefaultBg //purpose : Set default viewer background fill color //============================================================================== static int VSetDefaultBg (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { if (theArgNb != 4 && theArgNb != 8) { std::cout << "Error: wrong syntax! See usage:\n"; theDI.PrintHelp (theArgVec[0]); return 1; } ViewerTest_DefaultBackground.FillMethod = theArgNb == 4 ? Aspect_GFM_NONE : (Aspect_GradientFillMethod) Draw::Atoi (theArgVec[7]); if (theArgNb == 4) { Standard_Real R = Draw::Atof (theArgVec[1]) / 255.; Standard_Real G = Draw::Atof (theArgVec[2]) / 255.; Standard_Real B = Draw::Atof (theArgVec[3]) / 255.; ViewerTest_DefaultBackground.FlatColor.SetValues (R, G, B, Quantity_TOC_RGB); } else { Standard_Real R1 = Draw::Atof (theArgVec[1]) / 255.; Standard_Real G1 = Draw::Atof (theArgVec[2]) / 255.; Standard_Real B1 = Draw::Atof (theArgVec[3]) / 255.; ViewerTest_DefaultBackground.GradientColor1.SetValues (R1, G1, B1, Quantity_TOC_RGB); Standard_Real R2 = Draw::Atof (theArgVec[4]) / 255.; Standard_Real G2 = Draw::Atof (theArgVec[5]) / 255.; Standard_Real B2 = Draw::Atof (theArgVec[6]) / 255.; ViewerTest_DefaultBackground.GradientColor2.SetValues (R2, G2, B2, Quantity_TOC_RGB); } for (NCollection_DoubleMap::Iterator anIter (ViewerTest_myContexts); anIter.More(); anIter.Next()) { const Handle(V3d_Viewer)& aViewer = anIter.Value()->CurrentViewer(); aViewer->SetDefaultBackgroundColor (ViewerTest_DefaultBackground.FlatColor); aViewer->SetDefaultBgGradientColors (ViewerTest_DefaultBackground.GradientColor1, ViewerTest_DefaultBackground.GradientColor2, ViewerTest_DefaultBackground.FillMethod); } return 0; } //============================================================================== //function : VScale //purpose : View Scaling //============================================================================== static int VScale(Draw_Interpretor& di, Standard_Integer argc, const char** argv) { Handle(V3d_View) V3dView = ViewerTest::CurrentView(); if ( V3dView.IsNull() ) return 1; if ( argc != 4 ) { di << argv[0] << "Invalid number of arguments\n"; return 1; } V3dView->SetAxialScale( Draw::Atof(argv[1]), Draw::Atof(argv[2]), Draw::Atof(argv[3]) ); return 0; } //============================================================================== //function : VZBuffTrihedron //purpose : //============================================================================== static int VZBuffTrihedron (Draw_Interpretor& /*theDI*/, Standard_Integer theArgNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cout << "Error: no active viewer!\n"; return 1; } ViewerTest_AutoUpdater anUpdateTool (ViewerTest::GetAISContext(), aView); Aspect_TypeOfTriedronPosition aPosition = Aspect_TOTP_LEFT_LOWER; V3d_TypeOfVisualization aVisType = V3d_ZBUFFER; Quantity_Color aLabelsColor = Quantity_NOC_WHITE; Quantity_Color anArrowColorX = Quantity_NOC_RED; Quantity_Color anArrowColorY = Quantity_NOC_GREEN; Quantity_Color anArrowColorZ = Quantity_NOC_BLUE1; Standard_Real aScale = 0.1; Standard_Real aSizeRatio = 0.8; Standard_Real anArrowDiam = 0.05; Standard_Integer aNbFacets = 12; 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 == "-on") { continue; } else if (aFlag == "-off") { aView->TriedronErase(); return 0; } else if (aFlag == "-pos" || aFlag == "-position" || aFlag == "-corner") { if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } TCollection_AsciiString aPosName (theArgVec[anArgIter]); aPosName.LowerCase(); if (aPosName == "center") { aPosition = Aspect_TOTP_CENTER; } else if (aPosName == "left_lower" || aPosName == "lower_left" || aPosName == "leftlower" || aPosName == "lowerleft") { aPosition = Aspect_TOTP_LEFT_LOWER; } else if (aPosName == "left_upper" || aPosName == "upper_left" || aPosName == "leftupper" || aPosName == "upperleft") { aPosition = Aspect_TOTP_LEFT_UPPER; } else if (aPosName == "right_lower" || aPosName == "lower_right" || aPosName == "rightlower" || aPosName == "lowerright") { aPosition = Aspect_TOTP_RIGHT_LOWER; } else if (aPosName == "right_upper" || aPosName == "upper_right" || aPosName == "rightupper" || aPosName == "upperright") { aPosition = Aspect_TOTP_RIGHT_UPPER; } else { std::cerr << "Error: wrong syntax at '" << anArg << "' - unknown position '" << aPosName << "'\n"; return 1; } } else if (aFlag == "-type") { if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } TCollection_AsciiString aTypeName (theArgVec[anArgIter]); aTypeName.LowerCase(); if (aTypeName == "wireframe" || aTypeName == "wire") { aVisType = V3d_WIREFRAME; } else if (aTypeName == "zbuffer" || aTypeName == "shaded") { aVisType = V3d_ZBUFFER; } else { std::cerr << "Error: wrong syntax at '" << anArg << "' - unknown type '" << aTypeName << "'\n"; } } else if (aFlag == "-scale") { if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } aScale = Draw::Atof (theArgVec[anArgIter]); } else if (aFlag == "-size" || aFlag == "-sizeratio") { if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } aSizeRatio = Draw::Atof (theArgVec[anArgIter]); } else if (aFlag == "-arrowdiam" || aFlag == "-arrowdiameter") { if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } anArrowDiam = Draw::Atof (theArgVec[anArgIter]); } else if (aFlag == "-nbfacets") { if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } aNbFacets = Draw::Atoi (theArgVec[anArgIter]); } else if (aFlag == "-colorlabel" || aFlag == "-colorlabels") { Standard_Integer aNbParsed = ViewerTest::ParseColor (theArgNb - anArgIter - 1, theArgVec + anArgIter + 1, aLabelsColor); if (aNbParsed == 0) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } anArgIter += aNbParsed; } else if (aFlag == "-colorarrowx") { Standard_Integer aNbParsed = ViewerTest::ParseColor (theArgNb - anArgIter - 1, theArgVec + anArgIter + 1, anArrowColorX); if (aNbParsed == 0) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } anArgIter += aNbParsed; } else if (aFlag == "-colorarrowy") { Standard_Integer aNbParsed = ViewerTest::ParseColor (theArgNb - anArgIter - 1, theArgVec + anArgIter + 1, anArrowColorY); if (aNbParsed == 0) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } anArgIter += aNbParsed; } else if (aFlag == "-colorarrowz") { Standard_Integer aNbParsed = ViewerTest::ParseColor (theArgNb - anArgIter - 1, theArgVec + anArgIter + 1, anArrowColorZ); if (aNbParsed == 0) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } anArgIter += aNbParsed; } else { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } } aView->ZBufferTriedronSetup (anArrowColorX.Name(), anArrowColorY.Name(), anArrowColorZ.Name(), aSizeRatio, anArrowDiam, aNbFacets); aView->TriedronDisplay (aPosition, aLabelsColor.Name(), aScale, aVisType); aView->ZFitAll(); return 0; } //============================================================================== //function : VRotate //purpose : Camera Rotating //============================================================================== static int VRotate (Draw_Interpretor& /*theDi*/, Standard_Integer theArgNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cout << "No active view!\n"; return 1; } Standard_Boolean hasFlags = Standard_False; for (Standard_Integer anArgIter = 1; anArgIter < theArgNb; ++anArgIter) { Standard_CString anArg (theArgVec[anArgIter]); TCollection_AsciiString aFlag (anArg); aFlag.LowerCase(); if (aFlag == "-mousestart" || aFlag == "-mousefrom") { hasFlags = Standard_True; if (anArgIter + 2 >= theArgNb) { std::cout << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } Standard_Integer anX = Draw::Atoi (theArgVec[++anArgIter]); Standard_Integer anY = Draw::Atoi (theArgVec[++anArgIter]); aView->StartRotation (anX, anY); } else if (aFlag == "-mousemove") { hasFlags = Standard_True; if (anArgIter + 2 >= theArgNb) { std::cout << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } Standard_Integer anX = Draw::Atoi (theArgVec[++anArgIter]); Standard_Integer anY = Draw::Atoi (theArgVec[++anArgIter]); aView->Rotation (anX, anY); } else if (theArgNb != 4 && theArgNb != 7) { std::cout << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } } if (hasFlags) { return 0; } else if (theArgNb == 4) { Standard_Real anAX = Draw::Atof (theArgVec[1]); Standard_Real anAY = Draw::Atof (theArgVec[2]); Standard_Real anAZ = Draw::Atof (theArgVec[3]); aView->Rotate (anAX, anAY, anAZ); return 0; } else if (theArgNb == 7) { Standard_Real anAX = Draw::Atof (theArgVec[1]); Standard_Real anAY = Draw::Atof (theArgVec[2]); Standard_Real anAZ = Draw::Atof (theArgVec[3]); Standard_Real anX = Draw::Atof (theArgVec[4]); Standard_Real anY = Draw::Atof (theArgVec[5]); Standard_Real anZ = Draw::Atof (theArgVec[6]); aView->Rotate (anAX, anAY, anAZ, anX, anY, anZ); return 0; } std::cout << "Error: Invalid number of arguments\n"; return 1; } //============================================================================== //function : VZoom //purpose : View zoom in / out (relative to current zoom) //============================================================================== static int VZoom( Draw_Interpretor& di, Standard_Integer argc, const char** argv ) { Handle(V3d_View) V3dView = ViewerTest::CurrentView(); if ( V3dView.IsNull() ) { return 1; } if ( argc == 2 ) { Standard_Real coef = Draw::Atof(argv[1]); if ( coef <= 0.0 ) { di << argv[1] << "Invalid value\n"; return 1; } V3dView->SetZoom( Draw::Atof(argv[1]) ); return 0; } else { di << argv[0] << " Invalid number of arguments\n"; return 1; } } //============================================================================== //function : VPan //purpose : View panning (in pixels) //============================================================================== static int VPan( Draw_Interpretor& di, Standard_Integer argc, const char** argv ) { Handle(V3d_View) V3dView = ViewerTest::CurrentView(); if ( V3dView.IsNull() ) return 1; if ( argc == 3 ) { V3dView->Pan( Draw::Atoi(argv[1]), Draw::Atoi(argv[2]) ); return 0; } else { di << argv[0] << " Invalid number of arguments\n"; return 1; } } //============================================================================== //function : VPlace //purpose : Place the point (in pixels) at the center of the window //============================================================================== static int VPlace (Draw_Interpretor& /*theDi*/, Standard_Integer theArgNb, const char** theArgs) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cerr << theArgs[0] << "Error: no active view." << std::endl; return 1; } if (theArgNb != 3) { std::cerr << theArgs[0] << "Error: invalid number of arguments." << std::endl; return 1; } aView->Place (Draw::Atoi (theArgs[1]), Draw::Atoi (theArgs[2]), aView->Scale()); return 0; } static int VColorScale (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aContext.IsNull()) { std::cout << "Error: no active view!\n"; return 1; } if (theArgNb <= 1) { std::cout << "Error: wrong syntax at command '" << theArgVec[0] << "'!\n"; return 1; } Handle(AIS_ColorScale) aColorScale; if (GetMapOfAIS().IsBound2 (theArgVec[1])) { // find existing object aColorScale = Handle(AIS_ColorScale)::DownCast (GetMapOfAIS().Find2 (theArgVec[1])); if (aColorScale.IsNull()) { std::cout << "Error: object '" << theArgVec[1] << "'is already defined and is not a color scale!\n"; return 1; } } if (theArgNb <= 2) { if (aColorScale.IsNull()) { std::cout << "Syntax error: colorscale with a given name does not exist.\n"; return 1; } theDI << "Color scale parameters for '"<< theArgVec[1] << "':\n" << "Min range: " << aColorScale->GetMin() << "\n" << "Max range: " << aColorScale->GetMax() << "\n" << "Number of intervals: " << aColorScale->GetNumberOfIntervals() << "\n" << "Text height: " << aColorScale->GetTextHeight() << "\n" << "Color scale position: " << aColorScale->GetXPosition() << " " << aColorScale->GetYPosition() << "\n" << "Color scale title: " << aColorScale->GetTitle() << "\n" << "Label position: "; switch (aColorScale->GetLabelPosition()) { case Aspect_TOCSP_NONE: theDI << "None\n"; break; case Aspect_TOCSP_LEFT: theDI << "Left\n"; break; case Aspect_TOCSP_RIGHT: theDI << "Right\n"; break; case Aspect_TOCSP_CENTER: theDI << "Center\n"; break; } return 0; } if (aColorScale.IsNull()) { aColorScale = new AIS_ColorScale(); aColorScale->SetZLayer (Graphic3d_ZLayerId_TopOSD); aContext->SetTransformPersistence (aColorScale, new Graphic3d_TransformPers (Graphic3d_TMF_2d, Aspect_TOTP_LEFT_LOWER)); } ViewerTest_AutoUpdater anUpdateTool (aContext, aView); for (Standard_Integer anArgIter = 2; anArgIter < theArgNb; ++anArgIter) { Standard_CString anArg = theArgVec[anArgIter]; TCollection_AsciiString aFlag (anArg); aFlag.LowerCase(); if (anUpdateTool.parseRedrawMode (aFlag)) { continue; } else if (aFlag == "-range") { if (anArgIter + 3 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } const TCollection_AsciiString aRangeMin (theArgVec[++anArgIter]); const TCollection_AsciiString aRangeMax (theArgVec[++anArgIter]); const TCollection_AsciiString aNbIntervals (theArgVec[++anArgIter]); if (!aRangeMin.IsRealValue() || !aRangeMax.IsRealValue()) { std::cout << "Error: the range values should be real!\n"; return 1; } else if (!aNbIntervals.IsIntegerValue()) { std::cout << "Error: the number of intervals should be integer!\n"; return 1; } aColorScale->SetRange (aRangeMin.RealValue(), aRangeMax.RealValue()); aColorScale->SetNumberOfIntervals (aNbIntervals.IntegerValue()); } else if (aFlag == "-font") { if (anArgIter + 1 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } TCollection_AsciiString aFontArg(theArgVec[anArgIter + 1]); if (!aFontArg.IsIntegerValue()) { std::cout << "Error: HeightFont value should be integer!\n"; return 1; } aColorScale->SetTextHeight (aFontArg.IntegerValue()); anArgIter += 1; } else if (aFlag == "-textpos") { if (anArgIter + 1 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } TCollection_AsciiString aTextPosArg(theArgVec[++anArgIter]); aTextPosArg.LowerCase(); Aspect_TypeOfColorScalePosition aLabPosition = Aspect_TOCSP_NONE; if (aTextPosArg == "none") { aLabPosition = Aspect_TOCSP_NONE; } else if (aTextPosArg == "left") { aLabPosition = Aspect_TOCSP_LEFT; } else if (aTextPosArg == "right") { aLabPosition = Aspect_TOCSP_RIGHT; } else if (aTextPosArg == "center") { aLabPosition = Aspect_TOCSP_CENTER; } else { std::cout << "Error: unknown position '" << aTextPosArg << "'!\n"; return 1; } aColorScale->SetLabelPosition (aLabPosition); } else if (aFlag == "-logarithmic" || aFlag == "-log") { if (anArgIter + 1 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } Standard_Boolean IsLog; if (!ViewerTest::ParseOnOff(theArgVec[++anArgIter], IsLog)) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } aColorScale->SetLogarithmic (IsLog); } else if (aFlag == "-huerange" || aFlag == "-hue") { if (anArgIter + 2 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } const Standard_Real aHueMin = Draw::Atof (theArgVec[++anArgIter]); const Standard_Real aHueMax = Draw::Atof (theArgVec[++anArgIter]); aColorScale->SetHueRange (aHueMin, aHueMax); } else if (aFlag == "-colorrange") { Quantity_Color aColorMin, aColorMax; Standard_Integer aNbParsed1 = ViewerTest::ParseColor (theArgNb - (anArgIter + 1), theArgVec + (anArgIter + 1), aColorMin); anArgIter += aNbParsed1; Standard_Integer aNbParsed2 = ViewerTest::ParseColor (theArgNb - (anArgIter + 1), theArgVec + (anArgIter + 1), aColorMax); anArgIter += aNbParsed2; if (aNbParsed1 == 0 || aNbParsed2 == 0) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } aColorScale->SetColorRange (aColorMin, aColorMax); } else if (aFlag == "-reversed" || aFlag == "-inverted" || aFlag == "-topdown" || aFlag == "-bottomup") { Standard_Boolean toEnable = Standard_True; if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff(theArgVec[anArgIter + 1], toEnable)) { ++anArgIter; } aColorScale->SetReversed ((aFlag == "-topdown") ? !toEnable : toEnable); } else if (aFlag == "-smooth" || aFlag == "-smoothtransition") { Standard_Boolean toEnable = Standard_True; if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], toEnable)) { ++anArgIter; } aColorScale->SetSmoothTransition (toEnable); } else if (aFlag == "-xy") { if (anArgIter + 2 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } const TCollection_AsciiString anX (theArgVec[++anArgIter]); const TCollection_AsciiString anY (theArgVec[++anArgIter]); if (!anX.IsIntegerValue() || !anY.IsIntegerValue()) { std::cout << "Error: coordinates should be integer values!\n"; return 1; } aColorScale->SetPosition (anX.IntegerValue(), anY.IntegerValue()); } else if (aFlag == "-width" || aFlag == "-w" || aFlag == "-breadth") { if (anArgIter + 1 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } const TCollection_AsciiString aBreadth (theArgVec[++anArgIter]); if (!aBreadth.IsIntegerValue()) { std::cout << "Error: a width should be an integer value!\n"; return 1; } aColorScale->SetBreadth (aBreadth.IntegerValue()); } else if (aFlag == "-height" || aFlag == "-h") { if (anArgIter + 1 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } const TCollection_AsciiString aHeight (theArgVec[++anArgIter]); if (!aHeight.IsIntegerValue()) { std::cout << "Error: a width should be an integer value!\n"; return 1; } aColorScale->SetHeight (aHeight.IntegerValue()); } else if (aFlag == "-color") { if (aColorScale->GetColorType() != Aspect_TOCSD_USER) { std::cout << "Error: wrong color type! Call -colors before to set user-specified colors!\n"; return 1; } else if (anArgIter + 2 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } const TCollection_AsciiString anInd (theArgVec[++anArgIter]); if (!anInd.IsIntegerValue()) { std::cout << "Error: Index value should be integer!\n"; return 1; } const Standard_Integer anIndex = anInd.IntegerValue(); if (anIndex <= 0 || anIndex > aColorScale->GetNumberOfIntervals()) { std::cout << "Error: Index value should be within range 1.." << aColorScale->GetNumberOfIntervals() <<"!\n"; return 1; } Quantity_Color aColor; Standard_Integer aNbParsed = ViewerTest::ParseColor (theArgNb - (anArgIter + 1), theArgVec + (anArgIter + 1), aColor); if (aNbParsed == 0) { std::cerr << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } aColorScale->SetIntervalColor (aColor, anIndex); aColorScale->SetColorType (Aspect_TOCSD_USER); anArgIter += aNbParsed; } else if (aFlag == "-label") { if (aColorScale->GetColorType() != Aspect_TOCSD_USER) { std::cout << "Error: wrong label type! Call -labels before to set user-specified labels!\n"; return 1; } else if (anArgIter + 2 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } Standard_Integer anIndex = Draw::Atoi (theArgVec[anArgIter + 1]); if (anIndex <= 0 || anIndex > aColorScale->GetNumberOfIntervals() + 1) { std::cout << "Error: Index value should be within range 1.." << aColorScale->GetNumberOfIntervals() + 1 <<"!\n"; return 1; } TCollection_ExtendedString aText (theArgVec[anArgIter + 2]); aColorScale->SetLabel (aText, anIndex); aColorScale->SetLabelType (Aspect_TOCSD_USER); anArgIter += 2; } else if (aFlag == "-labelat" || aFlag == "-labat" || aFlag == "-labelatborder" || aFlag == "-labatborder" || aFlag == "-labelatcenter" || aFlag == "-labatcenter") { Standard_Boolean toEnable = Standard_True; if (aFlag == "-labelat" || aFlag == "-labat") { Standard_Integer aLabAtBorder = -1; if (++anArgIter >= theArgNb) { TCollection_AsciiString anAtBorder (theArgVec[anArgIter]); anAtBorder.LowerCase(); if (anAtBorder == "border") { aLabAtBorder = 1; } else if (anAtBorder == "center") { aLabAtBorder = 0; } } if (aLabAtBorder == -1) { std::cout << "Syntax error at argument '" << anArg << "'!\n"; return 1; } toEnable = (aLabAtBorder == 1); } else if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], toEnable)) { ++anArgIter; } aColorScale->SetLabelAtBorder (aFlag == "-labelatcenter" || aFlag == "-labatcenter" ? !toEnable : toEnable); } else if (aFlag == "-colors") { Aspect_SequenceOfColor aSeq; for (;;) { Quantity_Color aColor; Standard_Integer aNbParsed = ViewerTest::ParseColor (theArgNb - (anArgIter + 1), theArgVec + (anArgIter + 1), aColor); if (aNbParsed == 0) { break; } anArgIter += aNbParsed; aSeq.Append (aColor); } if (aSeq.Length() != aColorScale->GetNumberOfIntervals()) { std::cout << "Error: not enough arguments! You should provide color names or RGB color values for every interval of the " << aColorScale->GetNumberOfIntervals() << " intervals\n"; return 1; } aColorScale->SetColors (aSeq); aColorScale->SetColorType (Aspect_TOCSD_USER); } else if (aFlag == "-labels" || aFlag == "-freelabels") { if (anArgIter + 1 >= theArgNb) { std::cout << "Syntax error at argument '" << anArg << "'!\n"; return 1; } Standard_Integer aNbLabels = aColorScale->IsLabelAtBorder() ? aColorScale->GetNumberOfIntervals() + 1 : aColorScale->GetNumberOfIntervals(); if (aFlag == "-freelabels") { ++anArgIter; aNbLabels = Draw::Atoi (theArgVec[anArgIter]); } if (anArgIter + aNbLabels >= theArgNb) { std::cout << "Error: not enough arguments! " << aNbLabels << " text labels are expected.\n"; return 1; } TColStd_SequenceOfExtendedString aSeq; for (Standard_Integer aLabelIter = 0; aLabelIter < aNbLabels; ++aLabelIter) { aSeq.Append (TCollection_ExtendedString (theArgVec[++anArgIter])); } aColorScale->SetLabels (aSeq); aColorScale->SetLabelType (Aspect_TOCSD_USER); } else if (aFlag == "-title") { if (anArgIter + 1 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } Standard_Boolean isTwoArgs = Standard_False; if (anArgIter + 2 < theArgNb) { TCollection_AsciiString aSecondArg (theArgVec[anArgIter + 2]); aSecondArg.LowerCase(); Standard_DISABLE_DEPRECATION_WARNINGS if (aSecondArg == "none") { aColorScale->SetTitlePosition (Aspect_TOCSP_NONE); isTwoArgs = Standard_True; } else if (aSecondArg == "left") { aColorScale->SetTitlePosition (Aspect_TOCSP_LEFT); isTwoArgs = Standard_True; } else if (aSecondArg == "right") { aColorScale->SetTitlePosition (Aspect_TOCSP_RIGHT); isTwoArgs = Standard_True; } else if (aSecondArg == "center") { aColorScale->SetTitlePosition (Aspect_TOCSP_CENTER); isTwoArgs = Standard_True; } Standard_ENABLE_DEPRECATION_WARNINGS } aColorScale->SetTitle (theArgVec[anArgIter + 1]); if (isTwoArgs) { anArgIter += 1; } anArgIter += 1; } else if (aFlag == "-demoversion" || aFlag == "-demo") { aColorScale->SetPosition (0, 0); aColorScale->SetTextHeight (16); aColorScale->SetRange (0.0, 100.0); aColorScale->SetNumberOfIntervals (10); aColorScale->SetBreadth (0); aColorScale->SetHeight (0); aColorScale->SetLabelPosition (Aspect_TOCSP_RIGHT); aColorScale->SetColorType (Aspect_TOCSD_AUTO); aColorScale->SetLabelType (Aspect_TOCSD_AUTO); } else if (aFlag == "-findcolor") { if (anArgIter + 1 >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'!\n"; return 1; } TCollection_AsciiString anArg1 (theArgVec[++anArgIter]); if (!anArg1.IsRealValue()) { std::cout << "Error: the value should be real!\n"; return 1; } Quantity_Color aColor; aColorScale->FindColor (anArg1.RealValue(), aColor); theDI << Quantity_Color::StringName (aColor.Name()); return 0; } else { std::cout << "Error: wrong syntax at " << anArg << " - unknown argument!\n"; return 1; } } Standard_Integer aWinWidth = 0, aWinHeight = 0; aView->Window()->Size (aWinWidth, aWinHeight); if (aColorScale->GetBreadth() == 0) { aColorScale->SetBreadth (aWinWidth); } if (aColorScale->GetHeight() == 0) { aColorScale->SetHeight (aWinHeight); } aColorScale->SetToUpdate(); ViewerTest::Display (theArgVec[1], aColorScale, Standard_False, Standard_True); return 0; } //============================================================================== //function : VGraduatedTrihedron //purpose : Displays or hides a graduated trihedron //============================================================================== static Standard_Boolean GetColor (const TCollection_AsciiString& theValue, Quantity_Color& theColor) { Quantity_NameOfColor aColorName; TCollection_AsciiString aVal = theValue; aVal.UpperCase(); if (!Quantity_Color::ColorFromName (aVal.ToCString(), aColorName)) { return Standard_False; } theColor = Quantity_Color (aColorName); return Standard_True; } static int VGraduatedTrihedron (Draw_Interpretor& /*theDi*/, Standard_Integer theArgNum, const char** theArgs) { if (theArgNum < 2) { std::cout << theArgs[0] << " error: wrong number of parameters. Type 'help" << theArgs[0] <<"' for more information.\n"; return 1; //TCL_ERROR } NCollection_DataMap aMapOfArgs; TCollection_AsciiString aParseKey; for (Standard_Integer anArgIt = 1; anArgIt < theArgNum; ++anArgIt) { TCollection_AsciiString anArg (theArgs [anArgIt]); if (anArg.Value (1) == '-' && !anArg.IsRealValue()) { aParseKey = anArg; aParseKey.Remove (1); aParseKey.LowerCase(); aMapOfArgs.Bind (aParseKey, new TColStd_HSequenceOfAsciiString); continue; } if (aParseKey.IsEmpty()) { continue; } aMapOfArgs(aParseKey)->Append (anArg); } // Check parameters for (NCollection_DataMap::Iterator aMapIt (aMapOfArgs); aMapIt.More(); aMapIt.Next()) { const TCollection_AsciiString& aKey = aMapIt.Key(); const Handle(TColStd_HSequenceOfAsciiString)& anArgs = aMapIt.Value(); // Bool key, without arguments if ((aKey.IsEqual ("on") || aKey.IsEqual ("off")) && anArgs->IsEmpty()) { continue; } // One argument if ( (aKey.IsEqual ("xname") || aKey.IsEqual ("yname") || aKey.IsEqual ("zname")) && anArgs->Length() == 1) { continue; } // On/off arguments if ((aKey.IsEqual ("xdrawname") || aKey.IsEqual ("ydrawname") || aKey.IsEqual ("zdrawname") || aKey.IsEqual ("xdrawticks") || aKey.IsEqual ("ydrawticks") || aKey.IsEqual ("zdrawticks") || aKey.IsEqual ("xdrawvalues") || aKey.IsEqual ("ydrawvalues") || aKey.IsEqual ("zdrawvalues") || aKey.IsEqual ("drawgrid") || aKey.IsEqual ("drawaxes")) && anArgs->Length() == 1 && (anArgs->Value(1).IsEqual ("on") || anArgs->Value(1).IsEqual ("off"))) { continue; } // One string argument if ( (aKey.IsEqual ("xnamecolor") || aKey.IsEqual ("ynamecolor") || aKey.IsEqual ("znamecolor") || aKey.IsEqual ("xcolor") || aKey.IsEqual ("ycolor") || aKey.IsEqual ("zcolor")) && anArgs->Length() == 1 && !anArgs->Value(1).IsIntegerValue() && !anArgs->Value(1).IsRealValue()) { continue; } // One integer argument if ( (aKey.IsEqual ("xticks") || aKey.IsEqual ("yticks") || aKey.IsEqual ("zticks") || aKey.IsEqual ("xticklength") || aKey.IsEqual ("yticklength") || aKey.IsEqual ("zticklength") || aKey.IsEqual ("xnameoffset") || aKey.IsEqual ("ynameoffset") || aKey.IsEqual ("znameoffset") || aKey.IsEqual ("xvaluesoffset") || aKey.IsEqual ("yvaluesoffset") || aKey.IsEqual ("zvaluesoffset")) && anArgs->Length() == 1 && anArgs->Value(1).IsIntegerValue()) { continue; } // One real argument if ( aKey.IsEqual ("arrowlength") && anArgs->Length() == 1 && (anArgs->Value(1).IsIntegerValue() || anArgs->Value(1).IsRealValue())) { continue; } // Two string arguments if ( (aKey.IsEqual ("namefont") || aKey.IsEqual ("valuesfont")) && anArgs->Length() == 1 && !anArgs->Value(1).IsIntegerValue() && !anArgs->Value(1).IsRealValue()) { continue; } TCollection_AsciiString aLowerKey; aLowerKey = "-"; aLowerKey += aKey; aLowerKey.LowerCase(); std::cout << theArgs[0] << ": " << aLowerKey << " is unknown option, or the arguments are unacceptable.\n"; std::cout << "Type help for more information.\n"; return 1; } Handle(AIS_InteractiveContext) anAISContext = ViewerTest::GetAISContext(); if (anAISContext.IsNull()) { std::cout << theArgs[0] << ": please use 'vinit' command to initialize view.\n"; return 1; } Standard_Boolean toDisplay = Standard_True; Quantity_Color aColor; Graphic3d_GraduatedTrihedron aTrihedronData; // Process parameters Handle(TColStd_HSequenceOfAsciiString) aValues; if (aMapOfArgs.Find ("off", aValues)) { toDisplay = Standard_False; } // AXES NAMES if (aMapOfArgs.Find ("xname", aValues)) { aTrihedronData.ChangeXAxisAspect().SetName (aValues->Value(1)); } if (aMapOfArgs.Find ("yname", aValues)) { aTrihedronData.ChangeYAxisAspect().SetName (aValues->Value(1)); } if (aMapOfArgs.Find ("zname", aValues)) { aTrihedronData.ChangeZAxisAspect().SetName (aValues->Value(1)); } if (aMapOfArgs.Find ("xdrawname", aValues)) { aTrihedronData.ChangeXAxisAspect().SetDrawName (aValues->Value(1).IsEqual ("on")); } if (aMapOfArgs.Find ("ydrawname", aValues)) { aTrihedronData.ChangeYAxisAspect().SetDrawName (aValues->Value(1).IsEqual ("on")); } if (aMapOfArgs.Find ("zdrawname", aValues)) { aTrihedronData.ChangeZAxisAspect().SetDrawName (aValues->Value(1).IsEqual ("on")); } if (aMapOfArgs.Find ("xnameoffset", aValues)) { aTrihedronData.ChangeXAxisAspect().SetNameOffset (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("ynameoffset", aValues)) { aTrihedronData.ChangeYAxisAspect().SetNameOffset (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("znameoffset", aValues)) { aTrihedronData.ChangeZAxisAspect().SetNameOffset (aValues->Value(1).IntegerValue()); } // COLORS if (aMapOfArgs.Find ("xnamecolor", aValues)) { if (!GetColor (aValues->Value(1), aColor)) { std::cout << theArgs[0] << "error: -xnamecolor wrong color name.\n"; return 1; } aTrihedronData.ChangeXAxisAspect().SetNameColor (aColor); } if (aMapOfArgs.Find ("ynamecolor", aValues)) { if (!GetColor (aValues->Value(1), aColor)) { std::cout << theArgs[0] << "error: -ynamecolor wrong color name.\n"; return 1; } aTrihedronData.ChangeYAxisAspect().SetNameColor (aColor); } if (aMapOfArgs.Find ("znamecolor", aValues)) { if (!GetColor (aValues->Value(1), aColor)) { std::cout << theArgs[0] << "error: -znamecolor wrong color name.\n"; return 1; } aTrihedronData.ChangeZAxisAspect().SetNameColor (aColor); } if (aMapOfArgs.Find ("xcolor", aValues)) { if (!GetColor (aValues->Value(1), aColor)) { std::cout << theArgs[0] << "error: -xcolor wrong color name.\n"; return 1; } aTrihedronData.ChangeXAxisAspect().SetColor (aColor); } if (aMapOfArgs.Find ("ycolor", aValues)) { if (!GetColor (aValues->Value(1), aColor)) { std::cout << theArgs[0] << "error: -ycolor wrong color name.\n"; return 1; } aTrihedronData.ChangeYAxisAspect().SetColor (aColor); } if (aMapOfArgs.Find ("zcolor", aValues)) { if (!GetColor (aValues->Value(1), aColor)) { std::cout << theArgs[0] << "error: -zcolor wrong color name.\n"; return 1; } aTrihedronData.ChangeZAxisAspect().SetColor (aColor); } // TICKMARKS if (aMapOfArgs.Find ("xticks", aValues)) { aTrihedronData.ChangeXAxisAspect().SetTickmarksNumber (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("yticks", aValues)) { aTrihedronData.ChangeYAxisAspect().SetTickmarksNumber (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("zticks", aValues)) { aTrihedronData.ChangeZAxisAspect().SetTickmarksNumber (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("xticklength", aValues)) { aTrihedronData.ChangeXAxisAspect().SetTickmarksLength (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("yticklength", aValues)) { aTrihedronData.ChangeYAxisAspect().SetTickmarksLength (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("zticklength", aValues)) { aTrihedronData.ChangeZAxisAspect().SetTickmarksLength (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("xdrawticks", aValues)) { aTrihedronData.ChangeXAxisAspect().SetDrawTickmarks (aValues->Value(1).IsEqual ("on")); } if (aMapOfArgs.Find ("ydrawticks", aValues)) { aTrihedronData.ChangeYAxisAspect().SetDrawTickmarks (aValues->Value(1).IsEqual ("on")); } if (aMapOfArgs.Find ("zdrawticks", aValues)) { aTrihedronData.ChangeZAxisAspect().SetDrawTickmarks (aValues->Value(1).IsEqual ("on")); } // VALUES if (aMapOfArgs.Find ("xdrawvalues", aValues)) { aTrihedronData.ChangeXAxisAspect().SetDrawValues (aValues->Value(1).IsEqual ("on")); } if (aMapOfArgs.Find ("ydrawvalues", aValues)) { aTrihedronData.ChangeYAxisAspect().SetDrawValues (aValues->Value(1).IsEqual ("on")); } if (aMapOfArgs.Find ("zdrawvalues", aValues)) { aTrihedronData.ChangeZAxisAspect().SetDrawValues (aValues->Value(1).IsEqual ("on")); } if (aMapOfArgs.Find ("xvaluesoffset", aValues)) { aTrihedronData.ChangeXAxisAspect().SetValuesOffset (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("yvaluesoffset", aValues)) { aTrihedronData.ChangeYAxisAspect().SetValuesOffset (aValues->Value(1).IntegerValue()); } if (aMapOfArgs.Find ("zvaluesoffset", aValues)) { aTrihedronData.ChangeZAxisAspect().SetValuesOffset (aValues->Value(1).IntegerValue()); } // ARROWS if (aMapOfArgs.Find ("arrowlength", aValues)) { aTrihedronData.SetArrowsLength ((Standard_ShortReal) aValues->Value(1).RealValue()); } // FONTS if (aMapOfArgs.Find ("namefont", aValues)) { aTrihedronData.SetNamesFont (aValues->Value(1)); } if (aMapOfArgs.Find ("valuesfont", aValues)) { aTrihedronData.SetValuesFont (aValues->Value(1)); } if (aMapOfArgs.Find ("drawgrid", aValues)) { aTrihedronData.SetDrawGrid (aValues->Value(1).IsEqual ("on")); } if (aMapOfArgs.Find ("drawaxes", aValues)) { aTrihedronData.SetDrawAxes (aValues->Value(1).IsEqual ("on")); } // The final step: display of erase trihedron if (toDisplay) { ViewerTest::CurrentView()->GraduatedTrihedronDisplay (aTrihedronData); } else { ViewerTest::CurrentView()->GraduatedTrihedronErase(); } ViewerTest::GetAISContext()->UpdateCurrentViewer(); ViewerTest::CurrentView()->Redraw(); return 0; } //============================================================================== //function : VTile //purpose : //============================================================================== static int VTile (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cerr << "Error: no active viewer.\n"; return 1; } Graphic3d_CameraTile aTile = aView->Camera()->Tile(); if (theArgNb < 2) { theDI << "Total size: " << aTile.TotalSize.x() << " " << aTile.TotalSize.y() << "\n" << "Tile size: " << aTile.TileSize.x() << " " << aTile.TileSize.y() << "\n" << "Lower left: " << aTile.Offset.x() << " " << aTile.Offset.y() << "\n"; return 0; } aView->Window()->Size (aTile.TileSize.x(), aTile.TileSize.y()); for (Standard_Integer anArgIter = 1; anArgIter < theArgNb; ++anArgIter) { TCollection_AsciiString anArg (theArgVec[anArgIter]); anArg.LowerCase(); if (anArg == "-lowerleft" || anArg == "-upperleft") { if (anArgIter + 3 < theArgNb) { std::cerr << "Syntax error at '" << theArgVec[anArgIter] << "'.\n"; return 1; } aTile.IsTopDown = (anArg == "-upperleft") == Standard_True; aTile.Offset.x() = Draw::Atoi (theArgVec[anArgIter + 1]); aTile.Offset.y() = Draw::Atoi (theArgVec[anArgIter + 2]); } else if (anArg == "-total" || anArg == "-totalsize" || anArg == "-viewsize") { if (anArgIter + 3 < theArgNb) { std::cerr << "Syntax error at '" << theArgVec[anArgIter] << "'.\n"; return 1; } aTile.TotalSize.x() = Draw::Atoi (theArgVec[anArgIter + 1]); aTile.TotalSize.y() = Draw::Atoi (theArgVec[anArgIter + 2]); if (aTile.TotalSize.x() < 1 || aTile.TotalSize.y() < 1) { std::cerr << "Error: total size is incorrect.\n"; return 1; } } else if (anArg == "-tilesize") { if (anArgIter + 3 < theArgNb) { std::cerr << "Syntax error at '" << theArgVec[anArgIter] << "'.\n"; return 1; } aTile.TileSize.x() = Draw::Atoi (theArgVec[anArgIter + 1]); aTile.TileSize.y() = Draw::Atoi (theArgVec[anArgIter + 2]); if (aTile.TileSize.x() < 1 || aTile.TileSize.y() < 1) { std::cerr << "Error: tile size is incorrect.\n"; return 1; } } else if (anArg == "-unset") { aView->Camera()->SetTile (Graphic3d_CameraTile()); aView->Redraw(); return 0; } } if (aTile.TileSize.x() < 1 || aTile.TileSize.y() < 1) { std::cerr << "Error: tile size is undefined.\n"; return 1; } else if (aTile.TotalSize.x() < 1 || aTile.TotalSize.y() < 1) { std::cerr << "Error: total size is undefined.\n"; return 1; } aView->Camera()->SetTile (aTile); aView->Redraw(); return 0; } //! Format ZLayer ID. inline const char* formZLayerId (const Standard_Integer theLayerId) { switch (theLayerId) { case Graphic3d_ZLayerId_UNKNOWN: return "[INVALID]"; case Graphic3d_ZLayerId_Default: return "[DEFAULT]"; case Graphic3d_ZLayerId_Top: return "[TOP]"; case Graphic3d_ZLayerId_Topmost: return "[TOPMOST]"; case Graphic3d_ZLayerId_TopOSD: return "[OVERLAY]"; case Graphic3d_ZLayerId_BotOSD: return "[UNDERLAY]"; } return ""; } //! Print the ZLayer information. inline void printZLayerInfo (Draw_Interpretor& theDI, const Graphic3d_ZLayerSettings& theLayer) { if (!theLayer.Name().IsEmpty()) { theDI << " Name: " << theLayer.Name() << "\n"; } if (theLayer.IsImmediate()) { theDI << " Immediate: TRUE\n"; } theDI << " Origin: " << theLayer.Origin().X() << " " << theLayer.Origin().Y() << " " << theLayer.Origin().Z() << "\n"; theDI << " Culling distance: " << theLayer.CullingDistance() << "\n"; theDI << " Culling size: " << theLayer.CullingSize() << "\n"; theDI << " Depth test: " << (theLayer.ToEnableDepthTest() ? "enabled" : "disabled") << "\n"; theDI << " Depth write: " << (theLayer.ToEnableDepthWrite() ? "enabled" : "disabled") << "\n"; theDI << " Depth buffer clearing: " << (theLayer.ToClearDepth() ? "enabled" : "disabled") << "\n"; if (theLayer.PolygonOffset().Mode != Aspect_POM_None) { theDI << " Depth offset: " << theLayer.PolygonOffset().Factor << " " << theLayer.PolygonOffset().Units << "\n"; } } //============================================================================== //function : VZLayer //purpose : Test z layer operations for v3d viewer //============================================================================== static int VZLayer (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { Handle(AIS_InteractiveContext) aContextAIS = ViewerTest::GetAISContext(); if (aContextAIS.IsNull()) { std::cout << "No active viewer!\n"; return 1; } const Handle(V3d_Viewer)& aViewer = aContextAIS->CurrentViewer(); if (theArgNb < 2) { TColStd_SequenceOfInteger aLayers; aViewer->GetAllZLayers (aLayers); for (TColStd_SequenceOfInteger::Iterator aLayeriter (aLayers); aLayeriter.More(); aLayeriter.Next()) { theDI << "ZLayer " << aLayeriter.Value() << " " << formZLayerId (aLayeriter.Value()) << "\n"; Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayeriter.Value()); printZLayerInfo (theDI, aSettings); } return 1; } Standard_Integer anArgIter = 1; Standard_Integer aLayerId = Graphic3d_ZLayerId_UNKNOWN; ViewerTest_AutoUpdater anUpdateTool (aContextAIS, ViewerTest::CurrentView()); if (anUpdateTool.parseRedrawMode (theArgVec[anArgIter])) { ++anArgIter; } TCollection_AsciiString aFirstArg (theArgVec[anArgIter]); if (aFirstArg.IsIntegerValue()) { ++anArgIter; aLayerId = aFirstArg.IntegerValue(); } else { aFirstArg.LowerCase(); if (aFirstArg == "default" || aFirstArg == "def") { aLayerId = Graphic3d_ZLayerId_Default; ++anArgIter; } else if (aFirstArg == "top") { aLayerId = Graphic3d_ZLayerId_Top; ++anArgIter; } else if (aFirstArg == "topmost") { aLayerId = Graphic3d_ZLayerId_Topmost; ++anArgIter; } else if (aFirstArg == "overlay" || aFirstArg == "toposd") { aLayerId = Graphic3d_ZLayerId_TopOSD; ++anArgIter; } else if (aFirstArg == "underlay" || aFirstArg == "botosd") { aLayerId = Graphic3d_ZLayerId_BotOSD; ++anArgIter; } else { TColStd_SequenceOfInteger aLayers; aViewer->GetAllZLayers (aLayers); for (TColStd_SequenceOfInteger::Iterator aLayeriter (aLayers); aLayeriter.More(); aLayeriter.Next()) { Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayeriter.Value()); if (TCollection_AsciiString::IsSameString (aSettings.Name(), aFirstArg, Standard_False)) { aLayerId = aLayeriter.Value(); ++anArgIter; break; } } } } for (; anArgIter < theArgNb; ++anArgIter) { // perform operation TCollection_AsciiString anArg (theArgVec[anArgIter]); anArg.LowerCase(); if (anUpdateTool.parseRedrawMode (anArg)) { // } else if (anArg == "-add" || anArg == "add") { aLayerId = Graphic3d_ZLayerId_UNKNOWN; if (!aViewer->AddZLayer (aLayerId)) { std::cout << "Error: can not add a new z layer!\n"; return 0; } theDI << aLayerId; } else if (anArg == "-del" || anArg == "-delete" || anArg == "del") { if (aLayerId == Graphic3d_ZLayerId_UNKNOWN) { if (++anArgIter >= theArgNb) { std::cout << "Syntax error: id of z layer to remove is missing\n"; return 1; } aLayerId = Draw::Atoi (theArgVec[anArgIter]); } if (aLayerId == Graphic3d_ZLayerId_UNKNOWN || aLayerId == Graphic3d_ZLayerId_Default || aLayerId == Graphic3d_ZLayerId_Top || aLayerId == Graphic3d_ZLayerId_Topmost || aLayerId == Graphic3d_ZLayerId_TopOSD || aLayerId == Graphic3d_ZLayerId_BotOSD) { std::cout << "Syntax error: standard Z layer can not be removed\n"; return 1; } // move all object displayed in removing layer to default layer for (ViewerTest_DoubleMapIteratorOfDoubleMapOfInteractiveAndName anObjIter (GetMapOfAIS()); anObjIter.More(); anObjIter.Next()) { Handle(PrsMgr_PresentableObject) aPrs = Handle(PrsMgr_PresentableObject)::DownCast (anObjIter.Key1()); if (aPrs.IsNull() || aPrs->ZLayer() != aLayerId) { continue; } aPrs->SetZLayer (Graphic3d_ZLayerId_Default); } if (!aViewer->RemoveZLayer (aLayerId)) { std::cout << "Z layer can not be removed!\n"; } else { theDI << aLayerId << " "; } } else if (anArg == "-get" || anArg == "get") { TColStd_SequenceOfInteger aLayers; aViewer->GetAllZLayers (aLayers); for (TColStd_SequenceOfInteger::Iterator aLayeriter (aLayers); aLayeriter.More(); aLayeriter.Next()) { theDI << aLayeriter.Value() << " "; } theDI << "\n"; } else if (anArg == "-name") { if (aLayerId == Graphic3d_ZLayerId_UNKNOWN) { std::cout << "Syntax error: id of Z layer is missing\n"; return 1; } if (++anArgIter >= theArgNb) { std::cout << "Syntax error: name is missing\n"; return 1; } Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayerId); aSettings.SetName (theArgVec[anArgIter]); aViewer->SetZLayerSettings (aLayerId, aSettings); } else if (anArg == "-origin") { if (aLayerId == Graphic3d_ZLayerId_UNKNOWN) { std::cout << "Syntax error: id of Z layer is missing\n"; return 1; } if (anArgIter + 2 >= theArgNb) { std::cout << "Syntax error: origin coordinates are missing\n"; return 1; } Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayerId); gp_XYZ anOrigin; anOrigin.SetX (Draw::Atof (theArgVec[anArgIter + 1])); anOrigin.SetY (Draw::Atof (theArgVec[anArgIter + 2])); anOrigin.SetZ (0.0); if (anArgIter + 3 < theArgNb) { anOrigin.SetZ (Draw::Atof (theArgVec[anArgIter + 3])); anArgIter += 3; } else { anArgIter += 2; } aSettings.SetOrigin (anOrigin); aViewer->SetZLayerSettings (aLayerId, aSettings); } else if (aLayerId != Graphic3d_ZLayerId_UNKNOWN && anArgIter + 1 < theArgNb && (anArg == "-cullingdistance" || anArg == "-cullingdist" || anArg == "-culldistance" || anArg == "-culldist" || anArg == "-distcull" || anArg == "-distculling" || anArg == "-distanceculling")) { Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayerId); const Standard_Real aDist = Draw::Atof (theArgVec[++anArgIter]); aSettings.SetCullingDistance (aDist); aViewer->SetZLayerSettings (aLayerId, aSettings); } else if (aLayerId != Graphic3d_ZLayerId_UNKNOWN && anArgIter + 1 < theArgNb && (anArg == "-cullingsize" || anArg == "-cullsize" || anArg == "-sizecull" || anArg == "-sizeculling")) { Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayerId); const Standard_Real aSize = Draw::Atof (theArgVec[++anArgIter]); aSettings.SetCullingSize (aSize); aViewer->SetZLayerSettings (aLayerId, aSettings); } else if (anArg == "-settings" || anArg == "settings") { if (aLayerId == Graphic3d_ZLayerId_UNKNOWN) { if (++anArgIter >= theArgNb) { std::cout << "Syntax error: id of Z layer is missing\n"; return 1; } aLayerId = Draw::Atoi (theArgVec[anArgIter]); } Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayerId); printZLayerInfo (theDI, aSettings); } else if (anArg == "-enable" || anArg == "enable" || anArg == "-disable" || anArg == "disable") { const Standard_Boolean toEnable = anArg == "-enable" || anArg == "enable"; if (++anArgIter >= theArgNb) { std::cout << "Syntax error: option name is missing\n"; return 1; } TCollection_AsciiString aSubOp (theArgVec[anArgIter]); aSubOp.LowerCase(); if (aLayerId == Graphic3d_ZLayerId_UNKNOWN) { if (++anArgIter >= theArgNb) { std::cout << "Syntax error: id of Z layer is missing\n"; return 1; } aLayerId = Draw::Atoi (theArgVec[anArgIter]); } Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayerId); if (aSubOp == "depthtest" || aSubOp == "test") { aSettings.SetEnableDepthTest (toEnable); } else if (aSubOp == "depthwrite" || aSubOp == "write") { aSettings.SetEnableDepthWrite (toEnable); } else if (aSubOp == "depthclear" || aSubOp == "clear") { aSettings.SetClearDepth (toEnable); } else if (aSubOp == "depthoffset" || aSubOp == "offset") { Graphic3d_PolygonOffset aParams; aParams.Mode = toEnable ? Aspect_POM_Fill : Aspect_POM_None; if (toEnable) { if (anArgIter + 2 >= theArgNb) { std::cout << "Syntax error: factor and units values for depth offset are missing\n"; return 1; } aParams.Factor = static_cast (Draw::Atof (theArgVec[++anArgIter])); aParams.Units = static_cast (Draw::Atof (theArgVec[++anArgIter])); } aSettings.SetPolygonOffset (aParams); } else if (aSubOp == "positiveoffset" || aSubOp == "poffset") { if (toEnable) { aSettings.SetDepthOffsetPositive(); } else { aSettings.SetPolygonOffset (Graphic3d_PolygonOffset()); } } else if (aSubOp == "negativeoffset" || aSubOp == "noffset") { if (toEnable) { aSettings.SetDepthOffsetNegative(); } else { aSettings.SetPolygonOffset(Graphic3d_PolygonOffset()); } } else if (aSubOp == "textureenv") { aSettings.SetEnvironmentTexture (toEnable); } aViewer->SetZLayerSettings (aLayerId, aSettings); } else { std::cout << "Syntax error: unknown option " << theArgVec[anArgIter] << "\n"; return 1; } } return 0; } // The interactive presentation of 2d layer item // for "vlayerline" command it provides a presentation of // line with user-defined linewidth, linetype and transparency. class V3d_LineItem : public AIS_InteractiveObject { public: // CASCADE RTTI DEFINE_STANDARD_RTTI_INLINE(V3d_LineItem,AIS_InteractiveObject) // constructor Standard_EXPORT V3d_LineItem(Standard_Real X1, Standard_Real Y1, Standard_Real X2, Standard_Real Y2, Aspect_TypeOfLine theType = Aspect_TOL_SOLID, Standard_Real theWidth = 0.5, Standard_Real theTransp = 1.0); private: void Compute (const Handle(PrsMgr_PresentationManager3d)& thePresentationManager, const Handle(Prs3d_Presentation)& thePresentation, const Standard_Integer theMode) Standard_OVERRIDE; void ComputeSelection (const Handle(SelectMgr_Selection)& /*aSelection*/, const Standard_Integer /*aMode*/) Standard_OVERRIDE {} private: Standard_Real myX1, myY1, myX2, myY2; Aspect_TypeOfLine myType; Standard_Real myWidth; }; // default constructor for line item V3d_LineItem::V3d_LineItem(Standard_Real X1, Standard_Real Y1, Standard_Real X2, Standard_Real Y2, Aspect_TypeOfLine theType, Standard_Real theWidth, Standard_Real theTransp) : myX1(X1), myY1(Y1), myX2(X2), myY2(Y2), myType(theType), myWidth(theWidth) { SetTransparency (1-theTransp); } // render line void V3d_LineItem::Compute (const Handle(PrsMgr_PresentationManager3d)& /*thePresentationManager*/, const Handle(Prs3d_Presentation)& thePresentation, const Standard_Integer /*theMode*/) { thePresentation->Clear(); Quantity_Color aColor (1.0, 0, 0, Quantity_TOC_RGB); Standard_Integer aWidth, aHeight; ViewerTest::CurrentView()->Window()->Size (aWidth, aHeight); Handle (Graphic3d_Group) aGroup = Prs3d_Root::CurrentGroup (thePresentation); Handle(Graphic3d_ArrayOfPolylines) aPrim = new Graphic3d_ArrayOfPolylines(5); aPrim->AddVertex(myX1, aHeight-myY1, 0.); aPrim->AddVertex(myX2, aHeight-myY2, 0.); Handle(Prs3d_LineAspect) anAspect = new Prs3d_LineAspect (aColor, (Aspect_TypeOfLine)myType, myWidth); aGroup->SetPrimitivesAspect (anAspect->Aspect()); aGroup->AddPrimitiveArray (aPrim); } //============================================================================= //function : VLayerLine //purpose : Draws line in the v3d view layer with given attributes: linetype, // : linewidth, transparency coefficient //============================================================================ static int VLayerLine(Draw_Interpretor& di, Standard_Integer argc, const char** argv) { // get the active view Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { di << "Call vinit before!\n"; return 1; } else if (argc < 5) { di << "Use: " << argv[0]; di << " x1 y1 x2 y2 [linewidth = 0.5] [linetype = 0] [transparency = 1]\n"; di << " linetype : { 0 | 1 | 2 | 3 } \n"; di << " 0 - solid \n"; di << " 1 - dashed \n"; di << " 2 - dot \n"; di << " 3 - dashdot\n"; di << " transparency : { 0.0 - 1.0 } \n"; di << " 0.0 - transparent\n"; di << " 1.0 - visible \n"; return 1; } Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); // get the input params Standard_Real X1 = Draw::Atof(argv[1]); Standard_Real Y1 = Draw::Atof(argv[2]); Standard_Real X2 = Draw::Atof(argv[3]); Standard_Real Y2 = Draw::Atof(argv[4]); Standard_Real aWidth = 0.5; Standard_Real aTransparency = 1.0; // has width if (argc > 5) aWidth = Draw::Atof(argv[5]); // select appropriate line type Aspect_TypeOfLine aLineType = Aspect_TOL_SOLID; if (argc > 6 && !ViewerTest::ParseLineType (argv[6], aLineType)) { std::cout << "Syntax error: unknown line type '" << argv[6] << "'\n"; return 1; } // has transparency if (argc > 7) { aTransparency = Draw::Atof(argv[7]); if (aTransparency < 0 || aTransparency > 1.0) aTransparency = 1.0; } static Handle (V3d_LineItem) aLine; if (!aLine.IsNull()) { aContext->Erase (aLine, Standard_False); } aLine = new V3d_LineItem (X1, Y1, X2, Y2, aLineType, aWidth, aTransparency); aContext->SetTransformPersistence (aLine, new Graphic3d_TransformPers (Graphic3d_TMF_2d, Aspect_TOTP_LEFT_LOWER)); aLine->SetZLayer (Graphic3d_ZLayerId_TopOSD); aLine->SetToUpdate(); aContext->Display (aLine, Standard_True); return 0; } //============================================================================== //function : VGrid //purpose : //============================================================================== static int VGrid (Draw_Interpretor& /*theDI*/, Standard_Integer theArgNb, const char** theArgVec) { // get the active view Handle(V3d_View) aView = ViewerTest::CurrentView(); Handle(V3d_Viewer) aViewer = ViewerTest::GetViewerFromContext(); if (aView.IsNull() || aViewer.IsNull()) { std::cerr << "No active view. Please call vinit.\n"; return 1; } Aspect_GridType aType = aViewer->GridType(); Aspect_GridDrawMode aMode = aViewer->GridDrawMode(); ViewerTest_AutoUpdater anUpdateTool (ViewerTest::GetAISContext(), aView); Standard_Integer anIter = 1; for (; anIter < theArgNb; ++anIter) { const char* aValue = theArgVec[anIter]; if (anUpdateTool.parseRedrawMode (aValue)) { continue; } else if (*aValue == 'r') { aType = Aspect_GT_Rectangular; } else if (*aValue == 'c') { aType = Aspect_GT_Circular; } else if (*aValue == 'l') { aMode = Aspect_GDM_Lines; } else if (*aValue == 'p') { aMode = Aspect_GDM_Points; } else if (strcmp (aValue, "off" ) == 0) { aViewer->DeactivateGrid(); return 0; } else { break; } } Standard_Integer aTail = (theArgNb - anIter); if (aTail == 0) { aViewer->ActivateGrid (aType, aMode); return 0; } else if (aTail != 2 && aTail != 5) { std::cerr << "Incorrect arguments number! Usage:\n" << "vgrid [off] [Mode={r|c}] [Type={l|p}] [OriginX OriginY [StepX/StepRadius StepY/DivNb RotAngle]]\n"; return 1; } Standard_Real anOriginX, anOriginY, aRotAngle; if (aType == Aspect_GT_Rectangular) { Standard_Real aRStepX, aRStepY; aViewer->RectangularGridValues (anOriginX, anOriginY, aRStepX, aRStepY, aRotAngle); anOriginX = Draw::Atof (theArgVec[anIter++]); anOriginY = Draw::Atof (theArgVec[anIter++]); if (aTail == 5) { aRStepX = Draw::Atof (theArgVec[anIter++]); aRStepY = Draw::Atof (theArgVec[anIter++]); aRotAngle = Draw::Atof (theArgVec[anIter++]); } aViewer->SetRectangularGridValues (anOriginX, anOriginY, aRStepX, aRStepY, aRotAngle); aViewer->ActivateGrid (aType, aMode); } else if (aType == Aspect_GT_Circular) { Standard_Real aRadiusStep; Standard_Integer aDivisionNumber; aViewer->CircularGridValues (anOriginX, anOriginY, aRadiusStep, aDivisionNumber, aRotAngle); anOriginX = Draw::Atof (theArgVec[anIter++]); anOriginY = Draw::Atof (theArgVec[anIter++]); if (aTail == 5) { aRadiusStep = Draw::Atof (theArgVec[anIter++]); aDivisionNumber = Draw::Atoi (theArgVec[anIter++]); aRotAngle = Draw::Atof (theArgVec[anIter++]); } aViewer->SetCircularGridValues (anOriginX, anOriginY, aRadiusStep, aDivisionNumber, aRotAngle); aViewer->ActivateGrid (aType, aMode); } return 0; } //============================================================================== //function : VPriviledgedPlane //purpose : //============================================================================== static int VPriviledgedPlane (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { if (theArgNb != 1 && theArgNb != 7 && theArgNb != 10) { std::cerr << "Error: wrong number of arguments! See usage:\n"; theDI.PrintHelp (theArgVec[0]); return 1; } // get the active viewer Handle(V3d_Viewer) aViewer = ViewerTest::GetViewerFromContext(); if (aViewer.IsNull()) { std::cerr << "Error: no active viewer. Please call vinit.\n"; return 1; } if (theArgNb == 1) { gp_Ax3 aPriviledgedPlane = aViewer->PrivilegedPlane(); const gp_Pnt& anOrig = aPriviledgedPlane.Location(); const gp_Dir& aNorm = aPriviledgedPlane.Direction(); const gp_Dir& aXDir = aPriviledgedPlane.XDirection(); theDI << "Origin: " << anOrig.X() << " " << anOrig.Y() << " " << anOrig.Z() << " " << "Normal: " << aNorm.X() << " " << aNorm.Y() << " " << aNorm.Z() << " " << "X-dir: " << aXDir.X() << " " << aXDir.Y() << " " << aXDir.Z() << "\n"; return 0; } Standard_Integer anArgIdx = 1; Standard_Real anOrigX = Draw::Atof (theArgVec[anArgIdx++]); Standard_Real anOrigY = Draw::Atof (theArgVec[anArgIdx++]); Standard_Real anOrigZ = Draw::Atof (theArgVec[anArgIdx++]); Standard_Real aNormX = Draw::Atof (theArgVec[anArgIdx++]); Standard_Real aNormY = Draw::Atof (theArgVec[anArgIdx++]); Standard_Real aNormZ = Draw::Atof (theArgVec[anArgIdx++]); gp_Ax3 aPriviledgedPlane; gp_Pnt anOrig (anOrigX, anOrigY, anOrigZ); gp_Dir aNorm (aNormX, aNormY, aNormZ); if (theArgNb > 7) { Standard_Real aXDirX = Draw::Atof (theArgVec[anArgIdx++]); Standard_Real aXDirY = Draw::Atof (theArgVec[anArgIdx++]); Standard_Real aXDirZ = Draw::Atof (theArgVec[anArgIdx++]); gp_Dir aXDir (aXDirX, aXDirY, aXDirZ); aPriviledgedPlane = gp_Ax3 (anOrig, aNorm, aXDir); } else { aPriviledgedPlane = gp_Ax3 (anOrig, aNorm); } aViewer->SetPrivilegedPlane (aPriviledgedPlane); return 0; } //============================================================================== //function : VConvert //purpose : //============================================================================== static int VConvert (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { // get the active view Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cerr << "Error: no active view. Please call vinit.\n"; return 1; } enum { Model, Ray, View, Window, Grid } aMode = Model; // access coordinate arguments TColStd_SequenceOfReal aCoord; Standard_Integer anArgIdx = 1; for (; anArgIdx < 4 && anArgIdx < theArgNb; ++anArgIdx) { TCollection_AsciiString anArg (theArgVec[anArgIdx]); if (!anArg.IsRealValue()) { break; } aCoord.Append (anArg.RealValue()); } // non-numeric argument too early if (aCoord.IsEmpty()) { std::cerr << "Error: wrong number of arguments! See usage:\n"; theDI.PrintHelp (theArgVec[0]); return 1; } // collect all other arguments and options for (; anArgIdx < theArgNb; ++anArgIdx) { TCollection_AsciiString anArg (theArgVec[anArgIdx]); anArg.LowerCase(); if (anArg == "window") aMode = Window; else if (anArg == "view") aMode = View; else if (anArg == "grid") aMode = Grid; else if (anArg == "ray") aMode = Ray; else { std::cerr << "Error: wrong argument " << anArg << "! See usage:\n"; theDI.PrintHelp (theArgVec[0]); return 1; } } // complete input checks if ((aCoord.Length() == 1 && theArgNb > 3) || (aCoord.Length() == 2 && theArgNb > 4) || (aCoord.Length() == 3 && theArgNb > 5)) { std::cerr << "Error: wrong number of arguments! See usage:\n"; theDI.PrintHelp (theArgVec[0]); return 1; } Standard_Real aXYZ[6] = {0.0, 0.0, 0.0, 0.0, 0.0, 0.0}; Standard_Integer aXYp[2] = {0, 0}; // convert one-dimensional coordinate if (aCoord.Length() == 1) { switch (aMode) { case View : theDI << "View Vv: " << aView->Convert ((Standard_Integer)aCoord (1)); return 0; case Window : theDI << "Window Vp: " << aView->Convert (aCoord (1)); return 0; default: std::cerr << "Error: wrong arguments! See usage:\n"; theDI.PrintHelp (theArgVec[0]); return 1; } } // convert 2D coordinates from projection or view reference space if (aCoord.Length() == 2) { switch (aMode) { case Model : aView->Convert ((Standard_Integer) aCoord (1), (Standard_Integer) aCoord (2), aXYZ[0], aXYZ[1], aXYZ[2]); theDI << "Model X,Y,Z: " << aXYZ[0] << " " << aXYZ[1] << " " << aXYZ[2] << "\n"; return 0; case View : aView->Convert ((Standard_Integer) aCoord (1), (Standard_Integer) aCoord (2), aXYZ[0], aXYZ[1]); theDI << "View Xv,Yv: " << aXYZ[0] << " " << aXYZ[1] << "\n"; return 0; case Window : aView->Convert (aCoord (1), aCoord (2), aXYp[0], aXYp[1]); theDI << "Window Xp,Yp: " << aXYp[0] << " " << aXYp[1] << "\n"; return 0; case Grid : aView->Convert ((Standard_Integer) aCoord (1), (Standard_Integer) aCoord (2), aXYZ[0], aXYZ[1], aXYZ[2]); aView->ConvertToGrid (aXYZ[0], aXYZ[1], aXYZ[2], aXYZ[3], aXYZ[4], aXYZ[5]); theDI << "Model X,Y,Z: " << aXYZ[3] << " " << aXYZ[4] << " " << aXYZ[5] << "\n"; return 0; case Ray : aView->ConvertWithProj ((Standard_Integer) aCoord (1), (Standard_Integer) aCoord (2), aXYZ[0], aXYZ[1], aXYZ[2], aXYZ[3], aXYZ[4], aXYZ[5]); theDI << "Model DX,DY,DZ: " << aXYZ[3] << " " << aXYZ[4] << " " << aXYZ[5] << "\n"; return 0; default: std::cerr << "Error: wrong arguments! See usage:\n"; theDI.PrintHelp (theArgVec[0]); return 1; } } // convert 3D coordinates from view reference space else if (aCoord.Length() == 3) { switch (aMode) { case Window : aView->Convert (aCoord (1), aCoord (2), aCoord (3), aXYp[0], aXYp[1]); theDI << "Window Xp,Yp: " << aXYp[0] << " " << aXYp[1] << "\n"; return 0; case Grid : aView->ConvertToGrid (aCoord (1), aCoord (2), aCoord (3), aXYZ[0], aXYZ[1], aXYZ[2]); theDI << "Model X,Y,Z: " << aXYZ[0] << " " << aXYZ[1] << " " << aXYZ[2] << "\n"; return 0; default: std::cerr << "Error: wrong arguments! See usage:\n"; theDI.PrintHelp (theArgVec[0]); return 1; } } return 0; } //============================================================================== //function : VFps //purpose : //============================================================================== static int VFps (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { // get the active view Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cerr << "No active view. Please call vinit.\n"; return 1; } Standard_Integer aFramesNb = (theArgNb > 1) ? Draw::Atoi(theArgVec[1]) : 100; if (aFramesNb <= 0) { std::cerr << "Incorrect arguments!\n"; return 1; } // the time is meaningless for first call // due to async OpenGl rendering aView->Redraw(); // redraw view in loop to estimate average values OSD_Timer aTimer; aTimer.Start(); for (Standard_Integer anInter = 0; anInter < aFramesNb; ++anInter) { aView->Redraw(); } aTimer.Stop(); Standard_Real aCpu; const Standard_Real aTime = aTimer.ElapsedTime(); aTimer.OSD_Chronometer::Show (aCpu); const Standard_Real aFpsAver = Standard_Real(aFramesNb) / aTime; const Standard_Real aCpuAver = aCpu / Standard_Real(aFramesNb); // return statistics theDI << "FPS: " << aFpsAver << "\n" << "CPU: " << (1000.0 * aCpuAver) << " msec\n"; // compute additional statistics in ray-tracing mode Graphic3d_RenderingParams& aParams = aView->ChangeRenderingParams(); if (aParams.Method == Graphic3d_RM_RAYTRACING) { Standard_Integer aSizeX; Standard_Integer aSizeY; aView->Window()->Size (aSizeX, aSizeY); // 1 shadow ray and 1 secondary ray pew each bounce const Standard_Real aMRays = aSizeX * aSizeY * aFpsAver * aParams.RaytracingDepth * 2 / 1.0e6f; theDI << "MRays/sec (upper bound): " << aMRays << "\n"; } return 0; } //============================================================================== //function : VGlDebug //purpose : //============================================================================== static int VGlDebug (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { Handle(OpenGl_GraphicDriver) aDriver; Handle(V3d_View) aView = ViewerTest::CurrentView(); if (!aView.IsNull()) { aDriver = Handle(OpenGl_GraphicDriver)::DownCast (aView->Viewer()->Driver()); } OpenGl_Caps* aDefCaps = &ViewerTest_myDefaultCaps; OpenGl_Caps* aCaps = !aDriver.IsNull() ? &aDriver->ChangeOptions() : NULL; if (theArgNb < 2) { TCollection_AsciiString aDebActive, aSyncActive; if (aCaps == NULL) { aCaps = aDefCaps; } else { Standard_Boolean isActive = OpenGl_Context::CheckExtension ((const char* )::glGetString (GL_EXTENSIONS), "GL_ARB_debug_output"); aDebActive = isActive ? " (active)" : " (inactive)"; if (isActive) { // GL_DEBUG_OUTPUT_SYNCHRONOUS_ARB aSyncActive = ::glIsEnabled (0x8242) == GL_TRUE ? " (active)" : " (inactive)"; } } theDI << "debug: " << (aCaps->contextDebug ? "1" : "0") << aDebActive << "\n" << "sync: " << (aCaps->contextSyncDebug ? "1" : "0") << aSyncActive << "\n" << "glslWarn:" << (aCaps->glslWarnings ? "1" : "0") << "\n" << "extraMsg:" << (aCaps->suppressExtraMsg ? "0" : "1") << "\n"; return 0; } for (Standard_Integer anArgIter = 1; anArgIter < theArgNb; ++anArgIter) { Standard_CString anArg = theArgVec[anArgIter]; TCollection_AsciiString anArgCase (anArg); anArgCase.LowerCase(); Standard_Boolean toEnableDebug = Standard_True; if (anArgCase == "-glsl" || anArgCase == "-glslwarn" || anArgCase == "-glslwarns" || anArgCase == "-glslwarnings") { Standard_Boolean toShowWarns = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toShowWarns)) { --anArgIter; } aDefCaps->glslWarnings = toShowWarns; if (aCaps != NULL) { aCaps->glslWarnings = toShowWarns; } } else if (anArgCase == "-extra" || anArgCase == "-extramsg" || anArgCase == "-extramessages") { Standard_Boolean toShow = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toShow)) { --anArgIter; } aDefCaps->suppressExtraMsg = !toShow; if (aCaps != NULL) { aCaps->suppressExtraMsg = !toShow; } } else if (anArgCase == "-noextra" || anArgCase == "-noextramsg" || anArgCase == "-noextramessages") { Standard_Boolean toSuppress = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toSuppress)) { --anArgIter; } aDefCaps->suppressExtraMsg = toSuppress; if (aCaps != NULL) { aCaps->suppressExtraMsg = toSuppress; } } else if (anArgCase == "-sync") { Standard_Boolean toSync = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toSync)) { --anArgIter; } aDefCaps->contextSyncDebug = toSync; if (toSync) { aDefCaps->contextDebug = Standard_True; } } else if (anArgCase == "-debug") { if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnableDebug)) { --anArgIter; } aDefCaps->contextDebug = toEnableDebug; } else if (ViewerTest::ParseOnOff (anArg, toEnableDebug) && (anArgIter + 1 == theArgNb)) { // simple alias to turn on almost everything aDefCaps->contextDebug = toEnableDebug; aDefCaps->contextSyncDebug = toEnableDebug; aDefCaps->glslWarnings = toEnableDebug; } else { std::cout << "Error: wrong syntax at '" << anArg << "'\n"; return 1; } } return 0; } //============================================================================== //function : VVbo //purpose : //============================================================================== static int VVbo (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { const Standard_Boolean toSet = (theArgNb > 1); const Standard_Boolean toUseVbo = toSet ? (Draw::Atoi (theArgVec[1]) == 0) : 1; if (toSet) { ViewerTest_myDefaultCaps.vboDisable = toUseVbo; } // get the context Handle(AIS_InteractiveContext) aContextAIS = ViewerTest::GetAISContext(); if (aContextAIS.IsNull()) { if (!toSet) { std::cerr << "No active view!\n"; } return 1; } Handle(OpenGl_GraphicDriver) aDriver = Handle(OpenGl_GraphicDriver)::DownCast (aContextAIS->CurrentViewer()->Driver()); if (!aDriver.IsNull()) { if (!toSet) { theDI << (aDriver->Options().vboDisable ? "0" : "1") << "\n"; } else { aDriver->ChangeOptions().vboDisable = toUseVbo; } } return 0; } //============================================================================== //function : VCaps //purpose : //============================================================================== static int VCaps (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { OpenGl_Caps* aCaps = &ViewerTest_myDefaultCaps; Handle(OpenGl_GraphicDriver) aDriver; Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if (!aContext.IsNull()) { aDriver = Handle(OpenGl_GraphicDriver)::DownCast (aContext->CurrentViewer()->Driver()); aCaps = &aDriver->ChangeOptions(); } if (theArgNb < 2) { theDI << "VBO: " << (aCaps->vboDisable ? "0" : "1") << "\n"; 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"; theDI << "WinBuffer: " << (aCaps->useSystemBuffer ? "1" : "0") << "\n"; return 0; } ViewerTest_AutoUpdater anUpdateTool (aContext, ViewerTest::CurrentView()); for (Standard_Integer anArgIter = 1; anArgIter < theArgNb; ++anArgIter) { Standard_CString anArg = theArgVec[anArgIter]; TCollection_AsciiString anArgCase (anArg); anArgCase.LowerCase(); if (anUpdateTool.parseRedrawMode (anArg)) { continue; } else if (anArgCase == "-vsync" || anArgCase == "-swapinterval") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->swapInterval = toEnable; } else if (anArgCase == "-ffp") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->ffpEnable = toEnable; } else if (anArgCase == "-vbo") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->vboDisable = !toEnable; } else if (anArgCase == "-sprite" || anArgCase == "-sprites") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->pntSpritesDisable = !toEnable; } else if (anArgCase == "-softmode") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->contextNoAccel = toEnable; } else if (anArgCase == "-winbuffer" || anArgCase == "-windowbuffer" || anArgCase == "-usewinbuffer" || anArgCase == "-usewindowbuffer" || anArgCase == "-usesystembuffer") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->useSystemBuffer = toEnable; } else if (anArgCase == "-accel" || anArgCase == "-acceleration") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->contextNoAccel = !toEnable; } else if (anArgCase == "-compat" || anArgCase == "-compatprofile" || anArgCase == "-compatible" || anArgCase == "-compatibleprofile") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->contextCompatible = toEnable; if (!aCaps->contextCompatible) { aCaps->ffpEnable = Standard_False; } } else if (anArgCase == "-core" || anArgCase == "-coreprofile") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->contextCompatible = !toEnable; if (!aCaps->contextCompatible) { aCaps->ffpEnable = Standard_False; } } else if (anArgCase == "-stereo" || anArgCase == "-quadbuffer") { Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aCaps->contextStereo = toEnable; } else { std::cout << "Error: unknown argument '" << anArg << "'\n"; return 1; } } if (aCaps != &ViewerTest_myDefaultCaps) { ViewerTest_myDefaultCaps = *aCaps; } return 0; } //============================================================================== //function : VMemGpu //purpose : //============================================================================== static int VMemGpu (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { // get the context Handle(AIS_InteractiveContext) aContextAIS = ViewerTest::GetAISContext(); if (aContextAIS.IsNull()) { std::cerr << "No active view. Please call vinit.\n"; return 1; } Handle(Graphic3d_GraphicDriver) aDriver = aContextAIS->CurrentViewer()->Driver(); if (aDriver.IsNull()) { std::cerr << "Graphic driver not available.\n"; return 1; } Standard_Size aFreeBytes = 0; TCollection_AsciiString anInfo; if (!aDriver->MemoryInfo (aFreeBytes, anInfo)) { std::cerr << "Information not available.\n"; return 1; } if (theArgNb > 1 && *theArgVec[1] == 'f') { theDI << Standard_Real (aFreeBytes); } else { theDI << anInfo; } return 0; } // ============================================================================== // function : VReadPixel // purpose : // ============================================================================== static int VReadPixel (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { // get the active view Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cerr << "No active view. Please call vinit.\n"; return 1; } else if (theArgNb < 3) { std::cerr << "Usage : " << theArgVec[0] << " xPixel yPixel [{rgb|rgba|depth|hls|rgbf|rgbaf}=rgba] [name]\n"; return 1; } Image_Format aFormat = Image_Format_RGBA; Graphic3d_BufferType aBufferType = Graphic3d_BT_RGBA; Standard_Integer aWidth, aHeight; aView->Window()->Size (aWidth, aHeight); const Standard_Integer anX = Draw::Atoi (theArgVec[1]); const Standard_Integer anY = Draw::Atoi (theArgVec[2]); if (anX < 0 || anX >= aWidth || anY < 0 || anY > aHeight) { std::cerr << "Pixel coordinates (" << anX << "; " << anY << ") are out of view (" << aWidth << " x " << aHeight << ")\n"; return 1; } Standard_Boolean toShowName = Standard_False; Standard_Boolean toShowHls = Standard_False; for (Standard_Integer anIter = 3; anIter < theArgNb; ++anIter) { TCollection_AsciiString aParam (theArgVec[anIter]); aParam.LowerCase(); if (aParam == "rgb") { aFormat = Image_Format_RGB; aBufferType = Graphic3d_BT_RGB; } else if (aParam == "hls") { aFormat = Image_Format_RGB; aBufferType = Graphic3d_BT_RGB; toShowHls = Standard_True; } else if (aParam == "rgbf") { aFormat = Image_Format_RGBF; aBufferType = Graphic3d_BT_RGB; } else if (aParam == "rgba") { aFormat = Image_Format_RGBA; aBufferType = Graphic3d_BT_RGBA; } else if (aParam == "rgbaf") { aFormat = Image_Format_RGBAF; aBufferType = Graphic3d_BT_RGBA; } else if (aParam == "depth") { aFormat = Image_Format_GrayF; aBufferType = Graphic3d_BT_Depth; } else if (aParam == "name") { toShowName = Standard_True; } } Image_PixMap anImage; if (!anImage.InitTrash (aFormat, aWidth, aHeight)) { std::cerr << "Image allocation failed\n"; return 1; } else if (!aView->ToPixMap (anImage, aWidth, aHeight, aBufferType)) { std::cerr << "Image dump failed\n"; return 1; } // redirect possible warning messages that could have been added by ToPixMap // into the Tcl interpretor (via DefaultMessenger) to cout, so that they do not // contaminate result of the command Standard_CString aWarnLog = theDI.Result(); if (aWarnLog != NULL && aWarnLog[0] != '\0') { std::cout << aWarnLog << std::endl; } theDI.Reset(); Quantity_ColorRGBA aColor = anImage.PixelColor (anX, anY); if (toShowName) { if (aBufferType == Graphic3d_BT_RGBA) { theDI << Quantity_Color::StringName (aColor.GetRGB().Name()) << " " << aColor.Alpha(); } else { theDI << Quantity_Color::StringName (aColor.GetRGB().Name()); } } else { switch (aBufferType) { default: case Graphic3d_BT_RGB: { if (toShowHls) { theDI << aColor.GetRGB().Hue() << " " << aColor.GetRGB().Light() << " " << aColor.GetRGB().Saturation(); } else { theDI << aColor.GetRGB().Red() << " " << aColor.GetRGB().Green() << " " << aColor.GetRGB().Blue(); } break; } case Graphic3d_BT_RGBA: { theDI << aColor.GetRGB().Red() << " " << aColor.GetRGB().Green() << " " << aColor.GetRGB().Blue() << " " << aColor.Alpha(); break; } case Graphic3d_BT_Depth: { theDI << aColor.GetRGB().Red(); break; } } } return 0; } //! Auxiliary presentation for an image plane. class ViewerTest_ImagePrs : public AIS_InteractiveObject { public: //! Main constructor. ViewerTest_ImagePrs (const Handle(Image_PixMap)& theImage, const Standard_Real theWidth, const Standard_Real theHeight, const TCollection_AsciiString& theLabel) : myLabel (theLabel), myWidth (theWidth), myHeight(theHeight) { SetDisplayMode (0); SetHilightMode (1); myDynHilightDrawer->SetZLayer (Graphic3d_ZLayerId_Topmost); { myDrawer->SetShadingAspect (new Prs3d_ShadingAspect()); const Handle(Graphic3d_AspectFillArea3d)& aFillAspect = myDrawer->ShadingAspect()->Aspect(); Graphic3d_MaterialAspect aMat; aMat.SetMaterialType (Graphic3d_MATERIAL_PHYSIC); aMat.SetAmbient (1.0); aMat.SetDiffuse (1.0); aMat.SetSpecular (1.0); aMat.SetEmissive (1.0); aMat.SetReflectionModeOn (Graphic3d_TOR_AMBIENT); aMat.SetReflectionModeOn (Graphic3d_TOR_DIFFUSE); aMat.SetReflectionModeOn (Graphic3d_TOR_SPECULAR); aMat.SetReflectionModeOn (Graphic3d_TOR_EMISSION); aMat.SetAmbientColor (Quantity_Color (0.0, 0.0, 0.0, Quantity_TOC_RGB)); aMat.SetDiffuseColor (Quantity_Color (1.0, 1.0, 1.0, Quantity_TOC_RGB)); aMat.SetSpecularColor (Quantity_Color (0.0, 0.0, 0.0, Quantity_TOC_RGB)); aMat.SetEmissiveColor (Quantity_Color (0.0, 0.0, 0.0, Quantity_TOC_RGB)); aFillAspect->SetFrontMaterial (aMat); aFillAspect->SetTextureMap (new Graphic3d_Texture2Dmanual (theImage)); aFillAspect->SetTextureMapOn(); } { Handle(Prs3d_TextAspect) aTextAspect = new Prs3d_TextAspect(); aTextAspect->SetHorizontalJustification (Graphic3d_HTA_CENTER); aTextAspect->SetVerticalJustification (Graphic3d_VTA_CENTER); myDrawer->SetTextAspect (aTextAspect); } { const gp_Dir aNorm (0.0, 0.0, 1.0); myTris = new Graphic3d_ArrayOfTriangles (4, 6, true, false, true); myTris->AddVertex (gp_Pnt(-myWidth * 0.5, -myHeight * 0.5, 0.0), aNorm, gp_Pnt2d (0.0, 0.0)); myTris->AddVertex (gp_Pnt( myWidth * 0.5, -myHeight * 0.5, 0.0), aNorm, gp_Pnt2d (1.0, 0.0)); myTris->AddVertex (gp_Pnt(-myWidth * 0.5, myHeight * 0.5, 0.0), aNorm, gp_Pnt2d (0.0, 1.0)); myTris->AddVertex (gp_Pnt( myWidth * 0.5, myHeight * 0.5, 0.0), aNorm, gp_Pnt2d (1.0, 1.0)); myTris->AddEdge (1); myTris->AddEdge (2); myTris->AddEdge (3); myTris->AddEdge (3); myTris->AddEdge (2); myTris->AddEdge (4); myRect = new Graphic3d_ArrayOfPolylines (4); myRect->AddVertex (myTris->Vertice (1)); myRect->AddVertex (myTris->Vertice (3)); myRect->AddVertex (myTris->Vertice (4)); myRect->AddVertex (myTris->Vertice (2)); } } //! Returns TRUE for accepted display modes. virtual Standard_Boolean AcceptDisplayMode (const Standard_Integer theMode) const Standard_OVERRIDE { return theMode == 0 || theMode == 1; } //! Compute presentation. virtual void Compute (const Handle(PrsMgr_PresentationManager3d)& , const Handle(Prs3d_Presentation)& thePrs, const Standard_Integer theMode) Standard_OVERRIDE { switch (theMode) { case 0: { Handle(Graphic3d_Group) aGroup = thePrs->NewGroup(); aGroup->AddPrimitiveArray (myTris); aGroup->SetGroupPrimitivesAspect (myDrawer->ShadingAspect()->Aspect()); aGroup->AddPrimitiveArray (myRect); aGroup->SetGroupPrimitivesAspect (myDrawer->LineAspect()->Aspect()); return; } case 1: { Prs3d_Text::Draw (thePrs->NewGroup(), myDrawer->TextAspect(), myLabel, gp_Pnt(0.0, 0.0, 0.0)); Handle(Graphic3d_Group) aGroup = thePrs->NewGroup(); aGroup->AddPrimitiveArray (myRect); aGroup->SetGroupPrimitivesAspect (myDrawer->LineAspect()->Aspect()); return; } } } //! Compute selection. virtual void ComputeSelection (const Handle(SelectMgr_Selection)& theSel, const Standard_Integer theMode) Standard_OVERRIDE { if (theMode == 0) { Handle(SelectMgr_EntityOwner) anEntityOwner = new SelectMgr_EntityOwner (this, 5); Handle(Select3D_SensitivePrimitiveArray) aSensitive = new Select3D_SensitivePrimitiveArray (anEntityOwner); aSensitive->InitTriangulation (myTris->Attributes(), myTris->Indices(), TopLoc_Location()); theSel->Add (aSensitive); } } private: Handle(Graphic3d_ArrayOfTriangles) myTris; Handle(Graphic3d_ArrayOfPolylines) myRect; TCollection_AsciiString myLabel; Standard_Real myWidth; Standard_Real myHeight; }; //============================================================================== //function : VDiffImage //purpose : The draw-command compares two images. //============================================================================== static int VDiffImage (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { if (theArgNb < 3) { std::cout << "Syntax error: not enough arguments.\n"; return 1; } Standard_Integer anArgIter = 1; TCollection_AsciiString anImgPathRef (theArgVec[anArgIter++]); TCollection_AsciiString anImgPathNew (theArgVec[anArgIter++]); TCollection_AsciiString aDiffImagePath; Standard_Real aTolColor = -1.0; Standard_Integer toBlackWhite = -1; Standard_Integer isBorderFilterOn = -1; Standard_Boolean isOldSyntax = Standard_False; TCollection_AsciiString aViewName, aPrsNameRef, aPrsNameNew, aPrsNameDiff; for (; anArgIter < theArgNb; ++anArgIter) { TCollection_AsciiString anArg (theArgVec[anArgIter]); anArg.LowerCase(); if (anArgIter + 1 < theArgNb && (anArg == "-toleranceofcolor" || anArg == "-tolerancecolor" || anArg == "-tolerance" || anArg == "-toler")) { aTolColor = Atof (theArgVec[++anArgIter]); if (aTolColor < 0.0 || aTolColor > 1.0) { std::cout << "Syntax error at '" << anArg << " " << theArgVec[anArgIter] << "'\n"; return 1; } } else if (anArg == "-blackwhite") { Standard_Boolean toEnable = Standard_True; if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], toEnable)) { ++anArgIter; } toBlackWhite = toEnable ? 1 : 0; } else if (anArg == "-borderfilter") { Standard_Boolean toEnable = Standard_True; if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], toEnable)) { ++anArgIter; } isBorderFilterOn = toEnable ? 1 : 0; } else if (anArg == "-exitonclose") { Draw_ToExitOnCloseView = true; if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], Draw_ToExitOnCloseView)) { ++anArgIter; } } else if (anArg == "-closeonescape" || anArg == "-closeonesc") { Draw_ToCloseViewOnEsc = true; if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], Draw_ToCloseViewOnEsc)) { ++anArgIter; } } else if (anArgIter + 3 < theArgNb && anArg == "-display") { aViewName = theArgVec[++anArgIter]; aPrsNameRef = theArgVec[++anArgIter]; aPrsNameNew = theArgVec[++anArgIter]; if (anArgIter + 1 < theArgNb && *theArgVec[anArgIter + 1] != '-') { aPrsNameDiff = theArgVec[++anArgIter]; } } else if (aTolColor < 0.0 && anArg.IsRealValue()) { isOldSyntax = Standard_True; aTolColor = anArg.RealValue(); if (aTolColor < 0.0 || aTolColor > 1.0) { std::cout << "Syntax error at '" << anArg << " " << theArgVec[anArgIter] << "'\n"; return 1; } } else if (isOldSyntax && toBlackWhite == -1 && (anArg == "0" || anArg == "1")) { toBlackWhite = anArg == "1" ? 1 : 0; } else if (isOldSyntax && isBorderFilterOn == -1 && (anArg == "0" || anArg == "1")) { isBorderFilterOn = anArg == "1" ? 1 : 0; } else if (aDiffImagePath.IsEmpty()) { aDiffImagePath = theArgVec[anArgIter]; } else { std::cout << "Syntax error at '" << theArgVec[anArgIter] << "'\n"; return 1; } } Handle(Image_AlienPixMap) anImgRef = new Image_AlienPixMap(); Handle(Image_AlienPixMap) anImgNew = new Image_AlienPixMap(); if (!anImgRef->Load (anImgPathRef)) { std::cout << "Error: image file '" << anImgPathRef << "' cannot be read\n"; return 1; } if (!anImgNew->Load (anImgPathNew)) { std::cout << "Error: image file '" << anImgPathNew << "' cannot be read\n"; return 1; } // compare the images Image_Diff aComparer; Standard_Integer aDiffColorsNb = -1; if (aComparer.Init (anImgRef, anImgNew, toBlackWhite == 1)) { aComparer.SetColorTolerance (aTolColor >= 0.0 ? aTolColor : 0.0); aComparer.SetBorderFilterOn (isBorderFilterOn == 1); aDiffColorsNb = aComparer.Compare(); theDI << aDiffColorsNb << "\n"; } // save image of difference Handle(Image_AlienPixMap) aDiff; if (aDiffColorsNb > 0 && (!aDiffImagePath.IsEmpty() || !aPrsNameDiff.IsEmpty())) { aDiff = new Image_AlienPixMap(); if (!aDiff->InitTrash (Image_Format_Gray, anImgRef->SizeX(), anImgRef->SizeY())) { std::cout << "Error: cannot allocate memory for diff image " << anImgRef->SizeX() << "x" << anImgRef->SizeY() << "\n"; return 1; } aComparer.SaveDiffImage (*aDiff); if (!aDiffImagePath.IsEmpty() && !aDiff->Save (aDiffImagePath)) { std::cout << "Error: diff image file '" << aDiffImagePath << "' cannot be written\n"; return 1; } } if (aViewName.IsEmpty()) { return 0; } ViewerTest_Names aViewNames (aViewName); if (ViewerTest_myViews.IsBound1 (aViewNames.GetViewName())) { TCollection_AsciiString aCommand = TCollection_AsciiString ("vclose ") + aViewNames.GetViewName(); theDI.Eval (aCommand.ToCString()); } Standard_Integer aPxLeft = 0; Standard_Integer aPxTop = 0; Standard_Integer aWinSizeX = int(anImgRef->SizeX() * 2); Standard_Integer aWinSizeY = !aDiff.IsNull() && !aPrsNameDiff.IsEmpty() ? int(anImgRef->SizeY() * 2) : int(anImgRef->SizeY()); TCollection_AsciiString aDisplayName; TCollection_AsciiString aViewId = ViewerTest::ViewerInit (aPxLeft, aPxTop, aWinSizeX, aWinSizeY, aViewName, aDisplayName); Standard_Real aRatio = anImgRef->Ratio(); Standard_Real aSizeX = 1.0; Standard_Real aSizeY = aSizeX / aRatio; { OSD_Path aPath (anImgPathRef); TCollection_AsciiString aLabelRef; if (!aPath.Name().IsEmpty()) { aLabelRef = aPath.Name() + aPath.Extension(); } aLabelRef += TCollection_AsciiString() + "\n" + int(anImgRef->SizeX()) + "x" + int(anImgRef->SizeY()); Handle(ViewerTest_ImagePrs) anImgRefPrs = new ViewerTest_ImagePrs (anImgRef, aSizeX, aSizeY, aLabelRef); gp_Trsf aTrsfRef; aTrsfRef.SetTranslationPart (gp_Vec (-aSizeX * 0.5, 0.0, 0.0)); anImgRefPrs->SetLocalTransformation (aTrsfRef); ViewerTest::Display (aPrsNameRef, anImgRefPrs, false, true); } { OSD_Path aPath (anImgPathNew); TCollection_AsciiString aLabelNew; if (!aPath.Name().IsEmpty()) { aLabelNew = aPath.Name() + aPath.Extension(); } aLabelNew += TCollection_AsciiString() + "\n" + int(anImgNew->SizeX()) + "x" + int(anImgNew->SizeY()); Handle(ViewerTest_ImagePrs) anImgNewPrs = new ViewerTest_ImagePrs (anImgNew, aSizeX, aSizeY, aLabelNew); gp_Trsf aTrsfRef; aTrsfRef.SetTranslationPart (gp_Vec (aSizeX * 0.5, 0.0, 0.0)); anImgNewPrs->SetLocalTransformation (aTrsfRef); ViewerTest::Display (aPrsNameNew, anImgNewPrs, false, true); } Handle(ViewerTest_ImagePrs) anImgDiffPrs; if (!aDiff.IsNull()) { anImgDiffPrs = new ViewerTest_ImagePrs (aDiff, aSizeX, aSizeY, TCollection_AsciiString() + "Difference: " + aDiffColorsNb + " pixels"); gp_Trsf aTrsfDiff; aTrsfDiff.SetTranslationPart (gp_Vec (0.0, -aSizeY, 0.0)); anImgDiffPrs->SetLocalTransformation (aTrsfDiff); } if (!aPrsNameDiff.IsEmpty()) { ViewerTest::Display (aPrsNameDiff, anImgDiffPrs, false, true); } ViewerTest::CurrentView()->SetProj (V3d_Zpos); ViewerTest::CurrentView()->FitAll(); return 0; } //======================================================================= //function : VSelect //purpose : Emulates different types of selection by mouse: // 1) single click selection // 2) selection with rectangle having corners at pixel positions (x1,y1) and (x2,y2) // 3) selection with polygon having corners at // pixel positions (x1,y1),...,(xn,yn) // 4) any of these selections with shift button pressed //======================================================================= static Standard_Integer VSelect (Draw_Interpretor& di, Standard_Integer argc, const char ** argv) { if(argc < 3) { di << "Usage : " << argv[0] << " x1 y1 [x2 y2 [... xn yn]] [shift_selection = 1|0]\n"; return 1; } Handle(AIS_InteractiveContext) myAIScontext = ViewerTest::GetAISContext(); if(myAIScontext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } const Standard_Boolean isShiftSelection = (argc > 3 && !(argc % 2) && (atoi (argv[argc - 1]) == 1)); Standard_Integer aCoordsNb = isShiftSelection ? argc - 2 : argc - 1; TCollection_AsciiString anArg; anArg = isShiftSelection ? argv[argc - 3] : argv[argc - 2]; anArg.LowerCase(); if (anArg == "-allowoverlap") { Standard_Boolean isValidated = isShiftSelection ? argc == 8 : argc == 7; if (!isValidated) { di << "Wrong number of arguments! -allowoverlap key is applied only for rectangle selection"; return 1; } Standard_Integer isToAllow = isShiftSelection ? Draw::Atoi(argv[argc - 2]) : Draw::Atoi(argv[argc - 1]); myAIScontext->MainSelector()->AllowOverlapDetection (isToAllow != 0); aCoordsNb -= 2; } Handle(ViewerTest_EventManager) aCurrentEventManager = ViewerTest::CurrentEventManager(); aCurrentEventManager->MoveTo(atoi(argv[1]),atoi(argv[2])); if(aCoordsNb == 2) { if(isShiftSelection) aCurrentEventManager->ShiftSelect(); else aCurrentEventManager->Select(); } else if(aCoordsNb == 4) { if(isShiftSelection) aCurrentEventManager->ShiftSelect (atoi (argv[1]), atoi (argv[2]), atoi (argv[3]), atoi (argv[4]), Standard_False); else aCurrentEventManager->Select (atoi (argv[1]), atoi (argv[2]), atoi (argv[3]), atoi (argv[4]), Standard_False); } else { TColgp_Array1OfPnt2d aPolyline (1,aCoordsNb / 2); for(Standard_Integer i=1;i<=aCoordsNb / 2;++i) aPolyline.SetValue(i,gp_Pnt2d(atoi(argv[2*i-1]),atoi(argv[2*i]))); if(isShiftSelection) aCurrentEventManager->ShiftSelect(aPolyline); else aCurrentEventManager->Select(aPolyline); } return 0; } //======================================================================= //function : VMoveTo //purpose : Emulates cursor movement to defined pixel position //======================================================================= static Standard_Integer VMoveTo (Draw_Interpretor& , Standard_Integer theNbArgs, const char** theArgVec) { const Handle(AIS_InteractiveContext)& aContext = ViewerTest::GetAISContext(); const Handle(V3d_View)& aView = ViewerTest::CurrentView(); if (aContext.IsNull()) { std::cout << "Error: no active View\n"; return 1; } Graphic3d_Vec2i aMousePos (IntegerLast(), IntegerLast()); for (Standard_Integer anArgIter = 1; anArgIter < theNbArgs; ++anArgIter) { TCollection_AsciiString anArgStr (theArgVec[anArgIter]); anArgStr.LowerCase(); if (anArgStr == "-reset" || anArgStr == "-clear") { if (anArgIter + 1 < theNbArgs) { std::cout << "Syntax error at '" << theArgVec[anArgIter + 1] << "'\n"; return 1; } const Standard_Boolean toEchoGrid = aContext->CurrentViewer()->Grid()->IsActive() && aContext->CurrentViewer()->GridEcho(); if (toEchoGrid) { aContext->CurrentViewer()->HideGridEcho (aView); } if (aContext->ClearDetected() || toEchoGrid) { aContext->CurrentViewer()->RedrawImmediate(); } return 0; } else if (aMousePos.x() == IntegerLast() && anArgStr.IsIntegerValue()) { aMousePos.x() = anArgStr.IntegerValue(); } else if (aMousePos.y() == IntegerLast() && anArgStr.IsIntegerValue()) { aMousePos.y() = anArgStr.IntegerValue(); } else { std::cout << "Syntax error at '" << theArgVec[anArgIter] << "'\n"; return 1; } } if (aMousePos.x() == IntegerLast() || aMousePos.y() == IntegerLast()) { std::cout << "Syntax error: wrong number of arguments\n"; return 1; } ViewerTest::CurrentEventManager()->MoveTo (aMousePos.x(), aMousePos.y()); return 0; } namespace { //! Global map storing all animations registered in ViewerTest. static NCollection_DataMap ViewerTest_AnimationTimelineMap; //! The animation calling the Draw Harness command. class ViewerTest_AnimationProc : public AIS_Animation { public: //! Main constructor. ViewerTest_AnimationProc (const TCollection_AsciiString& theAnimationName, Draw_Interpretor* theDI, const TCollection_AsciiString& theCommand) : AIS_Animation (theAnimationName), myDrawInter(theDI), myCommand (theCommand) { // } protected: //! Evaluate the command. virtual void update (const AIS_AnimationProgress& theProgress) Standard_OVERRIDE { TCollection_AsciiString aCmd = myCommand; replace (aCmd, "%pts", TCollection_AsciiString(theProgress.Pts)); replace (aCmd, "%localpts", TCollection_AsciiString(theProgress.LocalPts)); replace (aCmd, "%ptslocal", TCollection_AsciiString(theProgress.LocalPts)); replace (aCmd, "%normalized", TCollection_AsciiString(theProgress.LocalNormalized)); replace (aCmd, "%localnormalized", TCollection_AsciiString(theProgress.LocalNormalized)); myDrawInter->Eval (aCmd.ToCString()); } //! Find the keyword in the command and replace it with value. //! @return the position of the keyword to pass value void replace (TCollection_AsciiString& theCmd, const TCollection_AsciiString& theKey, const TCollection_AsciiString& theVal) { TCollection_AsciiString aCmd (theCmd); aCmd.LowerCase(); const Standard_Integer aPos = aCmd.Search (theKey); if (aPos == -1) { return; } TCollection_AsciiString aPart1, aPart2; Standard_Integer aPart1To = aPos - 1; if (aPart1To >= 1 && aPart1To <= theCmd.Length()) { aPart1 = theCmd.SubString (1, aPart1To); } Standard_Integer aPart2From = aPos + theKey.Length(); if (aPart2From >= 1 && aPart2From <= theCmd.Length()) { aPart2 = theCmd.SubString (aPart2From, theCmd.Length()); } theCmd = aPart1 + theVal + aPart2; } protected: Draw_Interpretor* myDrawInter; TCollection_AsciiString myCommand; }; //! Replace the animation with the new one. static void replaceAnimation (const Handle(AIS_Animation)& theParentAnimation, Handle(AIS_Animation)& theAnimation, const Handle(AIS_Animation)& theAnimationNew) { theAnimationNew->CopyFrom (theAnimation); if (!theParentAnimation.IsNull()) { theParentAnimation->Replace (theAnimation, theAnimationNew); } else { ViewerTest_AnimationTimelineMap.UnBind (theAnimationNew->Name()); ViewerTest_AnimationTimelineMap.Bind (theAnimationNew->Name(), theAnimationNew); } theAnimation = theAnimationNew; } //! Parse the point. static Standard_Boolean parseXYZ (const char** theArgVec, gp_XYZ& thePnt) { const TCollection_AsciiString anXYZ[3] = { theArgVec[0], theArgVec[1], theArgVec[2] }; if (!anXYZ[0].IsRealValue() || !anXYZ[1].IsRealValue() || !anXYZ[2].IsRealValue()) { return Standard_False; } thePnt.SetCoord (anXYZ[0].RealValue(), anXYZ[1].RealValue(), anXYZ[2].RealValue()); return Standard_True; } //! Parse the quaternion. static Standard_Boolean parseQuaternion (const char** theArgVec, gp_Quaternion& theQRot) { const TCollection_AsciiString anXYZW[4] = {theArgVec[0], theArgVec[1], theArgVec[2], theArgVec[3]}; if (!anXYZW[0].IsRealValue() || !anXYZW[1].IsRealValue() || !anXYZW[2].IsRealValue() || !anXYZW[3].IsRealValue()) { return Standard_False; } theQRot.Set (anXYZW[0].RealValue(), anXYZW[1].RealValue(), anXYZW[2].RealValue(), anXYZW[3].RealValue()); return Standard_True; } //! Auxiliary class for flipping image upside-down. class ImageFlipper { public: //! Empty constructor. ImageFlipper() : myTmp (NCollection_BaseAllocator::CommonBaseAllocator()) {} //! Perform flipping. Standard_Boolean FlipY (Image_PixMap& theImage) { if (theImage.IsEmpty() || theImage.SizeX() == 0 || theImage.SizeY() == 0) { return Standard_False; } const Standard_Size aRowSize = theImage.SizeRowBytes(); if (myTmp.Size() < aRowSize && !myTmp.Allocate (aRowSize)) { return Standard_False; } // for odd height middle row should be left as is Standard_Size aNbRowsHalf = theImage.SizeY() / 2; for (Standard_Size aRowT = 0, aRowB = theImage.SizeY() - 1; aRowT < aNbRowsHalf; ++aRowT, --aRowB) { Standard_Byte* aTop = theImage.ChangeRow (aRowT); Standard_Byte* aBot = theImage.ChangeRow (aRowB); memcpy (myTmp.ChangeData(), aTop, aRowSize); memcpy (aTop, aBot, aRowSize); memcpy (aBot, myTmp.Data(), aRowSize); } return Standard_True; } private: NCollection_Buffer myTmp; }; } //================================================================================================= //function : VViewParams //purpose : Gets or sets AIS View characteristics //================================================================================================= static int VViewParams (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cout << theArgVec[0] << ": please initialize or activate view.\n"; return 1; } Standard_Boolean toSetProj = Standard_False; Standard_Boolean toSetUp = Standard_False; Standard_Boolean toSetAt = Standard_False; Standard_Boolean toSetEye = Standard_False; Standard_Boolean toSetScale = Standard_False; Standard_Boolean toSetSize = Standard_False; Standard_Boolean toSetCenter2d = Standard_False; Standard_Real aViewScale = aView->Scale(); Standard_Real aViewSize = 1.0; Graphic3d_Vec2i aCenter2d; gp_XYZ aViewProj, aViewUp, aViewAt, aViewEye; aView->Proj (aViewProj.ChangeCoord (1), aViewProj.ChangeCoord (2), aViewProj.ChangeCoord (3)); aView->Up (aViewUp .ChangeCoord (1), aViewUp .ChangeCoord (2), aViewUp .ChangeCoord (3)); aView->At (aViewAt .ChangeCoord (1), aViewAt .ChangeCoord (2), aViewAt .ChangeCoord (3)); aView->Eye (aViewEye .ChangeCoord (1), aViewEye .ChangeCoord (2), aViewEye .ChangeCoord (3)); if (theArgsNb == 1) { // print all of the available view parameters char aText[4096]; Sprintf (aText, "Scale: %g\n" "Proj: %12g %12g %12g\n" "Up: %12g %12g %12g\n" "At: %12g %12g %12g\n" "Eye: %12g %12g %12g\n", aViewScale, aViewProj.X(), aViewProj.Y(), aViewProj.Z(), aViewUp.X(), aViewUp.Y(), aViewUp.Z(), aViewAt.X(), aViewAt.Y(), aViewAt.Z(), aViewEye.X(), aViewEye.Y(), aViewEye.Z()); theDi << aText; return 0; } ViewerTest_AutoUpdater anUpdateTool (ViewerTest::GetAISContext(), aView); for (Standard_Integer anArgIter = 1; anArgIter < theArgsNb; ++anArgIter) { TCollection_AsciiString anArg (theArgVec[anArgIter]); anArg.LowerCase(); if (anUpdateTool.parseRedrawMode (anArg)) { continue; } else if (anArg == "-cmd" || anArg == "-command" || anArg == "-args") { char aText[4096]; Sprintf (aText, "-scale %g " "-proj %g %g %g " "-up %g %g %g " "-at %g %g %g\n", aViewScale, aViewProj.X(), aViewProj.Y(), aViewProj.Z(), aViewUp.X(), aViewUp.Y(), aViewUp.Z(), aViewAt.X(), aViewAt.Y(), aViewAt.Z()); theDi << aText; } else if (anArg == "-scale" || anArg == "-size") { if (anArgIter + 1 < theArgsNb && *theArgVec[anArgIter + 1] != '-') { const TCollection_AsciiString aValueArg (theArgVec[anArgIter + 1]); if (aValueArg.IsRealValue()) { ++anArgIter; if (anArg == "-scale") { toSetScale = Standard_True; aViewScale = aValueArg.RealValue(); } else if (anArg == "-size") { toSetSize = Standard_True; aViewSize = aValueArg.RealValue(); } continue; } } if (anArg == "-scale") { theDi << "Scale: " << aView->Scale() << "\n"; } else if (anArg == "-size") { Graphic3d_Vec2d aSizeXY; aView->Size (aSizeXY.x(), aSizeXY.y()); theDi << "Size: " << aSizeXY.x() << " " << aSizeXY.y() << "\n"; } } else if (anArg == "-eye" || anArg == "-at" || anArg == "-up" || anArg == "-proj") { if (anArgIter + 3 < theArgsNb) { gp_XYZ anXYZ; if (parseXYZ (theArgVec + anArgIter + 1, anXYZ)) { anArgIter += 3; if (anArg == "-eye") { toSetEye = Standard_True; aViewEye = anXYZ; } else if (anArg == "-at") { toSetAt = Standard_True; aViewAt = anXYZ; } else if (anArg == "-up") { toSetUp = Standard_True; aViewUp = anXYZ; } else if (anArg == "-proj") { toSetProj = Standard_True; aViewProj = anXYZ; } continue; } } if (anArg == "-eye") { theDi << "Eye: " << aViewEye.X() << " " << aViewEye.Y() << " " << aViewEye.Z() << "\n"; } else if (anArg == "-at") { theDi << "At: " << aViewAt.X() << " " << aViewAt.Y() << " " << aViewAt.Z() << "\n"; } else if (anArg == "-up") { theDi << "Up: " << aViewUp.X() << " " << aViewUp.Y() << " " << aViewUp.Z() << "\n"; } else if (anArg == "-proj") { theDi << "Proj: " << aViewProj.X() << " " << aViewProj.Y() << " " << aViewProj.Z() << "\n"; } } else if (anArg == "-center") { if (anArgIter + 2 < theArgsNb) { const TCollection_AsciiString anX (theArgVec[anArgIter + 1]); const TCollection_AsciiString anY (theArgVec[anArgIter + 2]); if (anX.IsIntegerValue() && anY.IsIntegerValue()) { toSetCenter2d = Standard_True; aCenter2d = Graphic3d_Vec2i (anX.IntegerValue(), anY.IntegerValue()); } } } else { std::cout << "Syntax error at '" << anArg << "'\n"; return 1; } } // change view parameters in proper order if (toSetScale) { aView->SetScale (aViewScale); } if (toSetSize) { aView->SetSize (aViewSize); } if (toSetEye) { aView->SetEye (aViewEye.X(), aViewEye.Y(), aViewEye.Z()); } if (toSetAt) { aView->SetAt (aViewAt.X(), aViewAt.Y(), aViewAt.Z()); } if (toSetProj) { aView->SetProj (aViewProj.X(), aViewProj.Y(), aViewProj.Z()); } if (toSetUp) { aView->SetUp (aViewUp.X(), aViewUp.Y(), aViewUp.Z()); } if (toSetCenter2d) { aView->SetCenter (aCenter2d.x(), aCenter2d.y()); } return 0; } //============================================================================== //function : V2DMode //purpose : //============================================================================== static Standard_Integer V2DMode (Draw_Interpretor&, Standard_Integer theArgsNb, const char** theArgVec) { bool is2dMode = true; Handle(ViewerTest_V3dView) aV3dView = Handle(ViewerTest_V3dView)::DownCast (ViewerTest::CurrentView()); if (aV3dView.IsNull()) { std::cout << "Error: no active view.\n"; return 1; } for (Standard_Integer anArgIt = 1; anArgIt < theArgsNb; ++anArgIt) { const TCollection_AsciiString anArg = theArgVec[anArgIt]; TCollection_AsciiString anArgCase = anArg; anArgCase.LowerCase(); if (anArgIt + 1 < theArgsNb && anArgCase == "-name") { ViewerTest_Names aViewNames (theArgVec[++anArgIt]); TCollection_AsciiString aViewName = aViewNames.GetViewName(); if (!ViewerTest_myViews.IsBound1 (aViewName)) { std::cout << "Syntax error: unknown view '" << theArgVec[anArgIt - 1] << "'.\n"; return 1; } aV3dView = Handle(ViewerTest_V3dView)::DownCast (ViewerTest_myViews.Find1 (aViewName)); } else if (anArgCase == "-mode") { if (anArgIt + 1 < theArgsNb && ViewerTest::ParseOnOff (theArgVec[anArgIt + 1], is2dMode)) { ++anArgIt; } } else if (ViewerTest::ParseOnOff (theArgVec[anArgIt], is2dMode)) { // } else { std::cout << "Syntax error: unknown argument " << anArg << ".\n"; return 1; } } aV3dView->SetView2DMode (is2dMode); return 0; } //============================================================================== //function : VAnimation //purpose : //============================================================================== static Standard_Integer VAnimation (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { Handle(AIS_InteractiveContext) aCtx = ViewerTest::GetAISContext(); if (theArgNb < 2) { for (NCollection_DataMap::Iterator anAnimIter (ViewerTest_AnimationTimelineMap); anAnimIter.More(); anAnimIter.Next()) { theDI << anAnimIter.Key() << " " << anAnimIter.Value()->Duration() << " sec\n"; } return 0; } if (aCtx.IsNull()) { std::cout << "Error: no active view\n"; return 1; } Standard_Integer anArgIter = 1; TCollection_AsciiString aNameArg (theArgVec[anArgIter++]); if (aNameArg.IsEmpty()) { std::cout << "Syntax error: animation name is not defined.\n"; return 1; } TCollection_AsciiString aNameArgLower = aNameArg; aNameArgLower.LowerCase(); if (aNameArgLower == "-reset" || aNameArgLower == "-clear") { ViewerTest_AnimationTimelineMap.Clear(); return 0; } else if (aNameArg.Value (1) == '-') { std::cout << "Syntax error: invalid animation name '" << aNameArg << "'.\n"; return 1; } const char* aNameSplitter = "/"; Standard_Integer aSplitPos = aNameArg.Search (aNameSplitter); if (aSplitPos == -1) { aNameSplitter = "."; aSplitPos = aNameArg.Search (aNameSplitter); } // find existing or create a new animation by specified name within syntax "parent.child". Handle(AIS_Animation) aRootAnimation, aParentAnimation, anAnimation; for (; !aNameArg.IsEmpty();) { TCollection_AsciiString aNameParent; if (aSplitPos != -1) { if (aSplitPos == aNameArg.Length()) { std::cout << "Syntax error: animation name is not defined.\n"; return 1; } aNameParent = aNameArg.SubString ( 1, aSplitPos - 1); aNameArg = aNameArg.SubString (aSplitPos + 1, aNameArg.Length()); aSplitPos = aNameArg.Search (aNameSplitter); } else { aNameParent = aNameArg; aNameArg.Clear(); } if (anAnimation.IsNull()) { if (!ViewerTest_AnimationTimelineMap.Find (aNameParent, anAnimation)) { anAnimation = new AIS_Animation (aNameParent); ViewerTest_AnimationTimelineMap.Bind (aNameParent, anAnimation); } aRootAnimation = anAnimation; } else { aParentAnimation = anAnimation; anAnimation = aParentAnimation->Find (aNameParent); if (anAnimation.IsNull()) { anAnimation = new AIS_Animation (aNameParent); aParentAnimation->Add (anAnimation); } } } if (anArgIter >= theArgNb) { // just print the list of children for (NCollection_Sequence::Iterator anAnimIter (anAnimation->Children()); anAnimIter.More(); anAnimIter.Next()) { theDI << anAnimIter.Value()->Name() << " " << anAnimIter.Value()->Duration() << " sec\n"; } return 0; } // animation parameters Standard_Boolean toPlay = Standard_False; Standard_Real aPlaySpeed = 1.0; Standard_Real aPlayStartTime = anAnimation->StartPts(); Standard_Real aPlayDuration = anAnimation->Duration(); Standard_Boolean isFreeCamera = Standard_False; Standard_Boolean isLockLoop = Standard_False; // video recording parameters TCollection_AsciiString aRecFile; Image_VideoParams aRecParams; Handle(V3d_View) aView = ViewerTest::CurrentView(); for (; anArgIter < theArgNb; ++anArgIter) { TCollection_AsciiString anArg (theArgVec[anArgIter]); anArg.LowerCase(); // general options if (anArg == "-reset" || anArg == "-clear") { anAnimation->Clear(); } else if (anArg == "-remove" || anArg == "-del" || anArg == "-delete") { if (!aParentAnimation.IsNull()) { ViewerTest_AnimationTimelineMap.UnBind (anAnimation->Name()); } else { aParentAnimation->Remove (anAnimation); } } // playback options else if (anArg == "-play") { toPlay = Standard_True; if (++anArgIter < theArgNb) { if (*theArgVec[anArgIter] == '-') { --anArgIter; continue; } aPlayStartTime = Draw::Atof (theArgVec[anArgIter]); if (++anArgIter < theArgNb) { if (*theArgVec[anArgIter] == '-') { --anArgIter; continue; } aPlayDuration = Draw::Atof (theArgVec[anArgIter]); } } } else if (anArg == "-resume") { toPlay = Standard_True; aPlayStartTime = anAnimation->ElapsedTime(); if (++anArgIter < theArgNb) { if (*theArgVec[anArgIter] == '-') { --anArgIter; continue; } aPlayDuration = Draw::Atof (theArgVec[anArgIter]); } } else if (anArg == "-playspeed" || anArg == "-speed") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } aPlaySpeed = Draw::Atof (theArgVec[anArgIter]); } else if (anArg == "-lock" || anArg == "-lockloop" || anArg == "-playlockloop") { isLockLoop = Standard_True; } else if (anArg == "-freecamera" || anArg == "-playfreecamera" || anArg == "-freelook") { isFreeCamera = Standard_True; } // video recodring options else if (anArg == "-rec" || anArg == "-record") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } aRecFile = theArgVec[anArgIter]; if (aRecParams.FpsNum <= 0) { aRecParams.FpsNum = 24; } if (anArgIter + 2 < theArgNb && *theArgVec[anArgIter + 1] != '-' && *theArgVec[anArgIter + 2] != '-') { TCollection_AsciiString aWidthArg (theArgVec[anArgIter + 1]); TCollection_AsciiString aHeightArg (theArgVec[anArgIter + 2]); if (aWidthArg .IsIntegerValue() && aHeightArg.IsIntegerValue()) { aRecParams.Width = aWidthArg .IntegerValue(); aRecParams.Height = aHeightArg.IntegerValue(); anArgIter += 2; } } } else if (anArg == "-fps") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } TCollection_AsciiString aFpsArg (theArgVec[anArgIter]); Standard_Integer aSplitIndex = aFpsArg.FirstLocationInSet ("/", 1, aFpsArg.Length()); if (aSplitIndex == 0) { aRecParams.FpsNum = aFpsArg.IntegerValue(); } else { const TCollection_AsciiString aDenStr = aFpsArg.Split (aSplitIndex); aFpsArg.Split (aFpsArg.Length() - 1); const TCollection_AsciiString aNumStr = aFpsArg; aRecParams.FpsNum = aNumStr.IntegerValue(); aRecParams.FpsDen = aDenStr.IntegerValue(); if (aRecParams.FpsDen < 1) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } } } else if (anArg == "-format") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } aRecParams.Format = theArgVec[anArgIter]; } else if (anArg == "-pix_fmt" || anArg == "-pixfmt" || anArg == "-pixelformat") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } aRecParams.PixelFormat = theArgVec[anArgIter]; } else if (anArg == "-codec" || anArg == "-vcodec" || anArg == "-videocodec") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } aRecParams.VideoCodec = theArgVec[anArgIter]; } else if (anArg == "-crf" || anArg == "-preset" || anArg == "-qp") { const TCollection_AsciiString aParamName = anArg.SubString (2, anArg.Length()); if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } aRecParams.VideoCodecParams.Bind (aParamName, theArgVec[anArgIter]); } // animation definition options else if (anArg == "-start" || anArg == "-starttime" || anArg == "-startpts") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } anAnimation->SetStartPts (Draw::Atof (theArgVec[anArgIter])); aRootAnimation->UpdateTotalDuration(); } else if (anArg == "-end" || anArg == "-endtime" || anArg == "-endpts") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } anAnimation->SetOwnDuration (Draw::Atof (theArgVec[anArgIter]) - anAnimation->StartPts()); aRootAnimation->UpdateTotalDuration(); } else if (anArg == "-dur" || anArg == "-duration") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } anAnimation->SetOwnDuration (Draw::Atof (theArgVec[anArgIter])); aRootAnimation->UpdateTotalDuration(); } else if (anArg == "-command" || anArg == "-cmd" || anArg == "-invoke" || anArg == "-eval" || anArg == "-proc") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } Handle(ViewerTest_AnimationProc) aCmdAnimation = new ViewerTest_AnimationProc (anAnimation->Name(), &theDI, theArgVec[anArgIter]); replaceAnimation (aParentAnimation, anAnimation, aCmdAnimation); } else if (anArg == "-objecttrsf" || anArg == "-objectransformation" || anArg == "-objtransformation" || anArg == "-objtrsf" || anArg == "-object" || anArg == "-obj") { if (++anArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } TCollection_AsciiString anObjName (theArgVec[anArgIter]); const ViewerTest_DoubleMapOfInteractiveAndName& aMapOfAIS = GetMapOfAIS(); if (!aMapOfAIS.IsBound2 (anObjName)) { std::cout << "Syntax error: wrong object name at " << anArg << "\n"; return 1; } Handle(AIS_InteractiveObject) anObject = Handle(AIS_InteractiveObject)::DownCast (aMapOfAIS.Find2 (anObjName)); gp_Trsf aTrsfs [2] = { anObject->LocalTransformation(), anObject->LocalTransformation() }; gp_Quaternion aRotQuats[2] = { aTrsfs[0].GetRotation(), aTrsfs[1].GetRotation() }; gp_XYZ aLocPnts [2] = { aTrsfs[0].TranslationPart(), aTrsfs[1].TranslationPart() }; Standard_Real aScales [2] = { aTrsfs[0].ScaleFactor(), aTrsfs[1].ScaleFactor() }; Standard_Boolean isTrsfSet = Standard_False; Standard_Integer aTrsfArgIter = anArgIter + 1; for (; aTrsfArgIter < theArgNb; ++aTrsfArgIter) { TCollection_AsciiString aTrsfArg (theArgVec[aTrsfArgIter]); aTrsfArg.LowerCase(); const Standard_Integer anIndex = aTrsfArg.EndsWith ("1") ? 0 : 1; if (aTrsfArg.StartsWith ("-rotation") || aTrsfArg.StartsWith ("-rot")) { isTrsfSet = Standard_True; if (aTrsfArgIter + 4 >= theArgNb || !parseQuaternion (theArgVec + aTrsfArgIter + 1, aRotQuats[anIndex])) { std::cout << "Syntax error at " << aTrsfArg << ".\n"; return 1; } aTrsfArgIter += 4; } else if (aTrsfArg.StartsWith ("-location") || aTrsfArg.StartsWith ("-loc")) { isTrsfSet = Standard_True; if (aTrsfArgIter + 3 >= theArgNb || !parseXYZ (theArgVec + aTrsfArgIter + 1, aLocPnts[anIndex])) { std::cout << "Syntax error at " << aTrsfArg << ".\n"; return 1; } aTrsfArgIter += 3; } else if (aTrsfArg.StartsWith ("-scale")) { isTrsfSet = Standard_True; if (++aTrsfArgIter >= theArgNb) { std::cout << "Syntax error at " << aTrsfArg << ".\n"; return 1; } const TCollection_AsciiString aScaleStr (theArgVec[aTrsfArgIter]); if (!aScaleStr.IsRealValue()) { std::cout << "Syntax error at " << aTrsfArg << ".\n"; return 1; } aScales[anIndex] = aScaleStr.RealValue(); } else { anArgIter = aTrsfArgIter - 1; break; } } if (!isTrsfSet) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } else if (aTrsfArgIter >= theArgNb) { anArgIter = theArgNb; } aTrsfs[0].SetRotation (aRotQuats[0]); aTrsfs[1].SetRotation (aRotQuats[1]); aTrsfs[0].SetTranslationPart (aLocPnts[0]); aTrsfs[1].SetTranslationPart (aLocPnts[1]); aTrsfs[0].SetScaleFactor (aScales[0]); aTrsfs[1].SetScaleFactor (aScales[1]); Handle(AIS_AnimationObject) anObjAnimation = new AIS_AnimationObject (anAnimation->Name(), aCtx, anObject, aTrsfs[0], aTrsfs[1]); replaceAnimation (aParentAnimation, anAnimation, anObjAnimation); } else if (anArg == "-viewtrsf" || anArg == "-view") { Handle(AIS_AnimationCamera) aCamAnimation = Handle(AIS_AnimationCamera)::DownCast (anAnimation); if (aCamAnimation.IsNull()) { aCamAnimation = new AIS_AnimationCamera (anAnimation->Name(), aView); replaceAnimation (aParentAnimation, anAnimation, aCamAnimation); } Handle(Graphic3d_Camera) aCams[2] = { new Graphic3d_Camera (aCamAnimation->View()->Camera()), new Graphic3d_Camera (aCamAnimation->View()->Camera()) }; Standard_Boolean isTrsfSet = Standard_False; Standard_Integer aViewArgIter = anArgIter + 1; for (; aViewArgIter < theArgNb; ++aViewArgIter) { TCollection_AsciiString aViewArg (theArgVec[aViewArgIter]); aViewArg.LowerCase(); const Standard_Integer anIndex = aViewArg.EndsWith("1") ? 0 : 1; if (aViewArg.StartsWith ("-scale")) { isTrsfSet = Standard_True; if (++aViewArgIter >= theArgNb) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } const TCollection_AsciiString aScaleStr (theArgVec[aViewArgIter]); if (!aScaleStr.IsRealValue()) { std::cout << "Syntax error at " << aViewArg << ".\n"; return 1; } Standard_Real aScale = aScaleStr.RealValue(); aScale = aCamAnimation->View()->DefaultCamera()->Scale() / aScale; aCams[anIndex]->SetScale (aScale); } else if (aViewArg.StartsWith ("-eye") || aViewArg.StartsWith ("-center") || aViewArg.StartsWith ("-at") || aViewArg.StartsWith ("-up")) { isTrsfSet = Standard_True; gp_XYZ anXYZ; if (aViewArgIter + 3 >= theArgNb || !parseXYZ (theArgVec + aViewArgIter + 1, anXYZ)) { std::cout << "Syntax error at " << aViewArg << ".\n"; return 1; } aViewArgIter += 3; if (aViewArg.StartsWith ("-eye")) { aCams[anIndex]->SetEye (anXYZ); } else if (aViewArg.StartsWith ("-center") || aViewArg.StartsWith ("-at")) { aCams[anIndex]->SetCenter (anXYZ); } else if (aViewArg.StartsWith ("-up")) { aCams[anIndex]->SetUp (anXYZ); } } else { anArgIter = aViewArgIter - 1; break; } } if (!isTrsfSet) { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } else if (aViewArgIter >= theArgNb) { anArgIter = theArgNb; } aCamAnimation->SetCameraStart(aCams[0]); aCamAnimation->SetCameraEnd (aCams[1]); } else { std::cout << "Syntax error at " << anArg << ".\n"; return 1; } } if (!toPlay && aRecFile.IsEmpty()) { return 0; } // Start animation timeline and process frame updating. TheIsAnimating = Standard_True; const Standard_Boolean wasImmediateUpdate = aView->SetImmediateUpdate (Standard_False); Handle(Graphic3d_Camera) aCameraBack = new Graphic3d_Camera (aView->Camera()); anAnimation->StartTimer (aPlayStartTime, aPlaySpeed, Standard_True, aPlayDuration <= 0.0); if (isFreeCamera) { aView->Camera()->Copy (aCameraBack); } const Standard_Real anUpperPts = aPlayStartTime + aPlayDuration; if (aRecParams.FpsNum <= 0) { while (!anAnimation->IsStopped()) { aCameraBack->Copy (aView->Camera()); const Standard_Real aPts = anAnimation->UpdateTimer(); if (isFreeCamera) { aView->Camera()->Copy (aCameraBack); } if (aPts >= anUpperPts) { anAnimation->Pause(); break; } if (aView->IsInvalidated()) { aView->Redraw(); } else { aView->RedrawImmediate(); } if (!isLockLoop) { // handle user events theDI.Eval ("after 1 set waiter 1"); theDI.Eval ("vwait waiter"); } if (!TheIsAnimating) { anAnimation->Pause(); theDI << aPts; break; } } if (aView->IsInvalidated()) { aView->Redraw(); } else { aView->RedrawImmediate(); } } else { OSD_Timer aPerfTimer; aPerfTimer.Start(); Handle(Image_VideoRecorder) aRecorder; ImageFlipper aFlipper; Handle(Draw_ProgressIndicator) aProgress; if (!aRecFile.IsEmpty()) { if (aRecParams.Width <= 0 || aRecParams.Height <= 0) { aView->Window()->Size (aRecParams.Width, aRecParams.Height); } aRecorder = new Image_VideoRecorder(); if (!aRecorder->Open (aRecFile.ToCString(), aRecParams)) { std::cout << "Error: failed to open video file for recording\n"; return 0; } aProgress = new Draw_ProgressIndicator (theDI, 1); } // Manage frame-rated animation here Standard_Real aPts = aPlayStartTime; int64_t aNbFrames = 0; Message_ProgressSentry aPSentry (aProgress, "Video recording, sec", 0, Max (1, Standard_Integer(aPlayDuration / aPlaySpeed)), 1); Standard_Integer aSecondsProgress = 0; for (; aPts <= anUpperPts && aPSentry.More();) { const Standard_Real aRecPts = aPlaySpeed * ((Standard_Real(aRecParams.FpsDen) / Standard_Real(aRecParams.FpsNum)) * Standard_Real(aNbFrames)); aPts = aPlayStartTime + aRecPts; ++aNbFrames; if (!anAnimation->Update (aPts)) { break; } if (!aRecorder.IsNull()) { V3d_ImageDumpOptions aDumpParams; aDumpParams.Width = aRecParams.Width; aDumpParams.Height = aRecParams.Height; aDumpParams.BufferType = Graphic3d_BT_RGBA; aDumpParams.StereoOptions = V3d_SDO_MONO; aDumpParams.ToAdjustAspect = Standard_True; if (!aView->ToPixMap (aRecorder->ChangeFrame(), aDumpParams)) { std::cout << "Error: view dump is failed!\n"; return 0; } aFlipper.FlipY (aRecorder->ChangeFrame()); if (!aRecorder->PushFrame()) { return 0; } } else { aView->Redraw(); } while (aSecondsProgress < Standard_Integer(aRecPts / aPlaySpeed)) { aPSentry.Next(); ++aSecondsProgress; } } aPerfTimer.Stop(); anAnimation->Stop(); const Standard_Real aRecFps = Standard_Real(aNbFrames) / aPerfTimer.ElapsedTime(); theDI << "Average FPS: " << aRecFps << "\n" << "Nb. Frames: " << Standard_Real(aNbFrames); aView->Redraw(); } aView->SetImmediateUpdate (wasImmediateUpdate); TheIsAnimating = Standard_False; return 0; } //======================================================================= //function : VChangeSelected //purpose : Adds the shape to selection or remove one from it //======================================================================= static Standard_Integer VChangeSelected (Draw_Interpretor& di, Standard_Integer argc, const char ** argv) { if(argc != 2) { di<<"Usage : " << argv[0] << " shape \n"; return 1; } //get AIS_Shape: Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); ViewerTest_DoubleMapOfInteractiveAndName& aMap = GetMapOfAIS(); TCollection_AsciiString aName(argv[1]); Handle(AIS_InteractiveObject) anAISObject; if(!aMap.IsBound2(aName)) { di<<"Use 'vdisplay' before"; return 1; } else { anAISObject = Handle(AIS_InteractiveObject)::DownCast(aMap.Find2(aName)); if(anAISObject.IsNull()){ di<<"No interactive object \n"; return 1; } aContext->AddOrRemoveSelected(anAISObject, Standard_True); } return 0; } //======================================================================= //function : VNbSelected //purpose : Returns number of selected objects //======================================================================= static Standard_Integer VNbSelected (Draw_Interpretor& di, Standard_Integer argc, const char ** argv) { if(argc != 1) { di << "Usage : " << argv[0] << "\n"; return 1; } Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if(aContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } di << aContext->NbSelected() << "\n"; return 0; } //======================================================================= //function : VPurgeDisplay //purpose : Switches altialiasing on or off //======================================================================= static Standard_Integer VPurgeDisplay (Draw_Interpretor& di, Standard_Integer argc, const char ** argv) { if (argc > 1) { di << "Usage : " << argv[0] << "\n"; return 1; } Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if (aContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } di << aContext->PurgeDisplay() << "\n"; return 0; } //======================================================================= //function : VSetViewSize //purpose : //======================================================================= static Standard_Integer VSetViewSize (Draw_Interpretor& di, Standard_Integer argc, const char ** argv) { Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if(aContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } if(argc != 2) { di<<"Usage : " << argv[0] << " Size\n"; return 1; } Standard_Real aSize = Draw::Atof (argv[1]); if (aSize <= 0.) { di<<"Bad Size value : " << aSize << "\n"; return 1; } Handle(V3d_View) aView = ViewerTest::CurrentView(); aView->SetSize(aSize); return 0; } //======================================================================= //function : VMoveView //purpose : //======================================================================= static Standard_Integer VMoveView (Draw_Interpretor& di, Standard_Integer argc, const char ** argv) { Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if(aContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } if(argc < 4 || argc > 5) { di<<"Usage : " << argv[0] << " Dx Dy Dz [Start = 1|0]\n"; return 1; } Standard_Real Dx = Draw::Atof (argv[1]); Standard_Real Dy = Draw::Atof (argv[2]); Standard_Real Dz = Draw::Atof (argv[3]); Standard_Boolean aStart = Standard_True; if (argc == 5) { aStart = (Draw::Atoi (argv[4]) > 0); } Handle(V3d_View) aView = ViewerTest::CurrentView(); aView->Move(Dx,Dy,Dz,aStart); return 0; } //======================================================================= //function : VTranslateView //purpose : //======================================================================= static Standard_Integer VTranslateView (Draw_Interpretor& di, Standard_Integer argc, const char ** argv) { Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if(aContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } if(argc < 4 || argc > 5) { di<<"Usage : " << argv[0] << " Dx Dy Dz [Start = 1|0]\n"; return 1; } Standard_Real Dx = Draw::Atof (argv[1]); Standard_Real Dy = Draw::Atof (argv[2]); Standard_Real Dz = Draw::Atof (argv[3]); Standard_Boolean aStart = Standard_True; if (argc == 5) { aStart = (Draw::Atoi (argv[4]) > 0); } Handle(V3d_View) aView = ViewerTest::CurrentView(); aView->Translate(Dx,Dy,Dz,aStart); return 0; } //======================================================================= //function : VTurnView //purpose : //======================================================================= static Standard_Integer VTurnView (Draw_Interpretor& di, Standard_Integer argc, const char ** argv) { Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if(aContext.IsNull()) { di << "use 'vinit' command before " << argv[0] << "\n"; return 1; } if(argc < 4 || argc > 5){ di<<"Usage : " << argv[0] << " Ax Ay Az [Start = 1|0]\n"; return 1; } Standard_Real Ax = Draw::Atof (argv[1]); Standard_Real Ay = Draw::Atof (argv[2]); Standard_Real Az = Draw::Atof (argv[3]); Standard_Boolean aStart = Standard_True; if (argc == 5) { aStart = (Draw::Atoi (argv[4]) > 0); } Handle(V3d_View) aView = ViewerTest::CurrentView(); aView->Turn(Ax,Ay,Az,aStart); return 0; } //============================================================================== //function : VTextureEnv //purpose : ENables or disables environment mapping //============================================================================== class OCC_TextureEnv : public Graphic3d_TextureEnv { public: OCC_TextureEnv(const Standard_CString FileName); OCC_TextureEnv(const Graphic3d_NameOfTextureEnv aName); void SetTextureParameters(const Standard_Boolean theRepeatFlag, const Standard_Boolean theModulateFlag, const Graphic3d_TypeOfTextureFilter theFilter, const Standard_ShortReal theXScale, const Standard_ShortReal theYScale, const Standard_ShortReal theXShift, const Standard_ShortReal theYShift, const Standard_ShortReal theAngle); DEFINE_STANDARD_RTTI_INLINE(OCC_TextureEnv,Graphic3d_TextureEnv) }; DEFINE_STANDARD_HANDLE(OCC_TextureEnv, Graphic3d_TextureEnv) OCC_TextureEnv::OCC_TextureEnv(const Standard_CString theFileName) : Graphic3d_TextureEnv(theFileName) { } OCC_TextureEnv::OCC_TextureEnv(const Graphic3d_NameOfTextureEnv theTexId) : Graphic3d_TextureEnv(theTexId) { } void OCC_TextureEnv::SetTextureParameters(const Standard_Boolean theRepeatFlag, const Standard_Boolean theModulateFlag, const Graphic3d_TypeOfTextureFilter theFilter, const Standard_ShortReal theXScale, const Standard_ShortReal theYScale, const Standard_ShortReal theXShift, const Standard_ShortReal theYShift, const Standard_ShortReal theAngle) { myParams->SetRepeat (theRepeatFlag); myParams->SetModulate (theModulateFlag); myParams->SetFilter (theFilter); myParams->SetScale (Graphic3d_Vec2(theXScale, theYScale)); myParams->SetTranslation(Graphic3d_Vec2(theXShift, theYShift)); myParams->SetRotation (theAngle); } static int VTextureEnv (Draw_Interpretor& /*theDI*/, Standard_Integer theArgNb, const char** theArgVec) { // get the active view Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cerr << "No active view. Please call vinit.\n"; return 1; } // Checking the input arguments Standard_Boolean anEnableFlag = Standard_False; Standard_Boolean isOk = theArgNb >= 2; if (isOk) { TCollection_AsciiString anEnableOpt(theArgVec[1]); anEnableFlag = anEnableOpt.IsEqual("on"); isOk = anEnableFlag || anEnableOpt.IsEqual("off"); } if (anEnableFlag) { isOk = (theArgNb == 3 || theArgNb == 11); if (isOk) { TCollection_AsciiString aTextureOpt(theArgVec[2]); isOk = (!aTextureOpt.IsIntegerValue() || (aTextureOpt.IntegerValue() >= 0 && aTextureOpt.IntegerValue() < Graphic3d_NOT_ENV_UNKNOWN)); if (isOk && theArgNb == 11) { TCollection_AsciiString aRepeatOpt (theArgVec[3]), aModulateOpt(theArgVec[4]), aFilterOpt (theArgVec[5]), aSScaleOpt (theArgVec[6]), aTScaleOpt (theArgVec[7]), aSTransOpt (theArgVec[8]), aTTransOpt (theArgVec[9]), anAngleOpt (theArgVec[10]); isOk = ((aRepeatOpt. IsEqual("repeat") || aRepeatOpt. IsEqual("clamp")) && (aModulateOpt.IsEqual("modulate") || aModulateOpt.IsEqual("decal")) && (aFilterOpt. IsEqual("nearest") || aFilterOpt. IsEqual("bilinear") || aFilterOpt.IsEqual("trilinear")) && aSScaleOpt.IsRealValue() && aTScaleOpt.IsRealValue() && aSTransOpt.IsRealValue() && aTTransOpt.IsRealValue() && anAngleOpt.IsRealValue()); } } } if (!isOk) { std::cerr << "Usage :" << std::endl; std::cerr << theArgVec[0] << " off" << std::endl; std::cerr << theArgVec[0] << " on {index_of_std_texture(0..7)|texture_file_name} [{clamp|repeat} {decal|modulate} {nearest|bilinear|trilinear} scale_s scale_t translation_s translation_t rotation_degrees]" << std::endl; return 1; } if (anEnableFlag) { TCollection_AsciiString aTextureOpt(theArgVec[2]); Handle(OCC_TextureEnv) aTexEnv = aTextureOpt.IsIntegerValue() ? new OCC_TextureEnv((Graphic3d_NameOfTextureEnv)aTextureOpt.IntegerValue()) : new OCC_TextureEnv(theArgVec[2]); if (theArgNb == 11) { TCollection_AsciiString aRepeatOpt(theArgVec[3]), aModulateOpt(theArgVec[4]), aFilterOpt(theArgVec[5]); aTexEnv->SetTextureParameters( aRepeatOpt. IsEqual("repeat"), aModulateOpt.IsEqual("modulate"), aFilterOpt. IsEqual("nearest") ? Graphic3d_TOTF_NEAREST : aFilterOpt.IsEqual("bilinear") ? Graphic3d_TOTF_BILINEAR : Graphic3d_TOTF_TRILINEAR, (Standard_ShortReal)Draw::Atof(theArgVec[6]), (Standard_ShortReal)Draw::Atof(theArgVec[7]), (Standard_ShortReal)Draw::Atof(theArgVec[8]), (Standard_ShortReal)Draw::Atof(theArgVec[9]), (Standard_ShortReal)Draw::Atof(theArgVec[10]) ); } aView->SetTextureEnv(aTexEnv); } else // Disabling environment mapping { Handle(Graphic3d_TextureEnv) aTexture; aView->SetTextureEnv(aTexture); // Passing null handle to clear the texture data } aView->Redraw(); return 0; } namespace { typedef NCollection_DataMap MapOfPlanes; //! Remove registered clipping plane from all views and objects. static void removePlane (MapOfPlanes& theRegPlanes, const TCollection_AsciiString& theName) { Handle(Graphic3d_ClipPlane) aClipPlane; if (!theRegPlanes.Find (theName, aClipPlane)) { std::cout << "Warning: no such plane.\n"; return; } theRegPlanes.UnBind (theName); for (ViewerTest_DoubleMapIteratorOfDoubleMapOfInteractiveAndName anIObjIt (GetMapOfAIS()); anIObjIt.More(); anIObjIt.Next()) { Handle(PrsMgr_PresentableObject) aPrs = Handle(PrsMgr_PresentableObject)::DownCast (anIObjIt.Key1()); aPrs->RemoveClipPlane (aClipPlane); } for (NCollection_DoubleMap::Iterator aViewIt(ViewerTest_myViews); aViewIt.More(); aViewIt.Next()) { const Handle(V3d_View)& aView = aViewIt.Key2(); aView->RemoveClipPlane(aClipPlane); } ViewerTest::RedrawAllViews(); } } //=============================================================================================== //function : VClipPlane //purpose : //=============================================================================================== static int VClipPlane (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { // use short-cut for created clip planes map of created (or "registered by name") clip planes static MapOfPlanes aRegPlanes; if (theArgsNb < 2) { for (MapOfPlanes::Iterator aPlaneIter (aRegPlanes); aPlaneIter.More(); aPlaneIter.Next()) { theDi << aPlaneIter.Key() << " "; } return 0; } TCollection_AsciiString aCommand (theArgVec[1]); aCommand.LowerCase(); const Handle(V3d_View)& anActiveView = ViewerTest::CurrentView(); if (anActiveView.IsNull()) { std::cout << "Error: no active view.\n"; return 1; } // print maximum number of planes for current viewer if (aCommand == "-maxplanes" || aCommand == "maxplanes") { theDi << anActiveView->Viewer()->Driver()->InquirePlaneLimit() << " plane slots provided by driver.\n"; return 0; } // create / delete plane instance if (aCommand == "-create" || aCommand == "create" || aCommand == "-delete" || aCommand == "delete" || aCommand == "-clone" || aCommand == "clone") { if (theArgsNb < 3) { std::cout << "Syntax error: plane name is required.\n"; return 1; } Standard_Boolean toCreate = aCommand == "-create" || aCommand == "create"; Standard_Boolean toClone = aCommand == "-clone" || aCommand == "clone"; Standard_Boolean toDelete = aCommand == "-delete" || aCommand == "delete"; TCollection_AsciiString aPlane (theArgVec[2]); if (toCreate) { if (aRegPlanes.IsBound (aPlane)) { std::cout << "Warning: existing plane has been overridden.\n"; toDelete = true; } else { aRegPlanes.Bind (aPlane, new Graphic3d_ClipPlane()); return 0; } } else if (toClone) // toClone { if (!aRegPlanes.IsBound (aPlane)) { std::cout << "Error: no such plane.\n"; return 1; } else if (theArgsNb < 4) { std::cout << "Syntax error: enter name for new plane.\n"; return 1; } TCollection_AsciiString aClone (theArgVec[3]); if (aRegPlanes.IsBound (aClone)) { std::cout << "Error: plane name is in use.\n"; return 1; } const Handle(Graphic3d_ClipPlane)& aClipPlane = aRegPlanes.Find (aPlane); aRegPlanes.Bind (aClone, aClipPlane->Clone()); return 0; } if (toDelete) { if (aPlane == "ALL" || aPlane == "all" || aPlane == "*") { for (MapOfPlanes::Iterator aPlaneIter (aRegPlanes); aPlaneIter.More();) { aPlane = aPlaneIter.Key(); removePlane (aRegPlanes, aPlane); aPlaneIter = MapOfPlanes::Iterator (aRegPlanes); } } else { removePlane (aRegPlanes, aPlane); } } if (toCreate) { aRegPlanes.Bind (aPlane, new Graphic3d_ClipPlane()); } return 0; } // set / unset plane command if (aCommand == "set" || aCommand == "unset") { if (theArgsNb < 5) { std::cout << "Syntax error: need more arguments.\n"; return 1; } // redirect to new syntax NCollection_Array1 anArgVec (1, theArgsNb - 1); anArgVec.SetValue (1, theArgVec[0]); anArgVec.SetValue (2, theArgVec[2]); anArgVec.SetValue (3, aCommand == "set" ? "-set" : "-unset"); for (Standard_Integer anIt = 4; anIt < theArgsNb; ++anIt) { anArgVec.SetValue (anIt, theArgVec[anIt]); } return VClipPlane (theDi, anArgVec.Length(), &anArgVec.ChangeFirst()); } // change plane command TCollection_AsciiString aPlaneName; Handle(Graphic3d_ClipPlane) aClipPlane; Standard_Integer anArgIter = 0; if (aCommand == "-change" || aCommand == "change") { // old syntax support if (theArgsNb < 3) { std::cout << "Syntax error: need more arguments.\n"; return 1; } anArgIter = 3; aPlaneName = theArgVec[2]; if (!aRegPlanes.Find (aPlaneName, aClipPlane)) { std::cout << "Error: no such plane '" << aPlaneName << "'.\n"; return 1; } } else if (aRegPlanes.Find (theArgVec[1], aClipPlane)) { anArgIter = 2; aPlaneName = theArgVec[1]; } else { anArgIter = 2; aPlaneName = theArgVec[1]; aClipPlane = new Graphic3d_ClipPlane(); aRegPlanes.Bind (aPlaneName, aClipPlane); theDi << "Created new plane " << aPlaneName << ".\n"; } if (theArgsNb - anArgIter < 1) { std::cout << "Syntax error: need more arguments.\n"; return 1; } for (; anArgIter < theArgsNb; ++anArgIter) { const char** aChangeArgs = theArgVec + anArgIter; Standard_Integer aNbChangeArgs = theArgsNb - anArgIter; TCollection_AsciiString aChangeArg (aChangeArgs[0]); aChangeArg.LowerCase(); Standard_Boolean toEnable = Standard_True; if (ViewerTest::ParseOnOff (aChangeArgs[0], toEnable)) { aClipPlane->SetOn (toEnable); } else if (aChangeArg.StartsWith ("-equation") || aChangeArg.StartsWith ("equation")) { if (aNbChangeArgs < 5) { std::cout << "Syntax error: need more arguments.\n"; return 1; } Standard_Integer aSubIndex = 1; Standard_Integer aPrefixLen = 8 + (aChangeArg.Value (1) == '-' ? 1 : 0); if (aPrefixLen < aChangeArg.Length()) { TCollection_AsciiString aSubStr = aChangeArg.SubString (aPrefixLen + 1, aChangeArg.Length()); if (!aSubStr.IsIntegerValue() || aSubStr.IntegerValue() <= 0) { std::cout << "Syntax error: unknown argument '" << aChangeArg << "'.\n"; return 1; } aSubIndex = aSubStr.IntegerValue(); } Standard_Real aCoeffA = Draw::Atof (aChangeArgs[1]); Standard_Real aCoeffB = Draw::Atof (aChangeArgs[2]); Standard_Real aCoeffC = Draw::Atof (aChangeArgs[3]); Standard_Real aCoeffD = Draw::Atof (aChangeArgs[4]); Handle(Graphic3d_ClipPlane) aSubPln = aClipPlane; for (Standard_Integer aSubPlaneIter = 1; aSubPlaneIter < aSubIndex; ++aSubPlaneIter) { if (aSubPln->ChainNextPlane().IsNull()) { aSubPln->SetChainNextPlane (new Graphic3d_ClipPlane (*aSubPln)); } aSubPln = aSubPln->ChainNextPlane(); } aSubPln->SetChainNextPlane (Handle(Graphic3d_ClipPlane)()); aSubPln->SetEquation (gp_Pln (aCoeffA, aCoeffB, aCoeffC, aCoeffD)); anArgIter += 4; } else if ((aChangeArg == "-boxinterior" || aChangeArg == "-boxint" || aChangeArg == "-box") && aNbChangeArgs >= 7) { Graphic3d_BndBox3d aBndBox; aBndBox.Add (Graphic3d_Vec3d (Draw::Atof (aChangeArgs[1]), Draw::Atof (aChangeArgs[2]), Draw::Atof (aChangeArgs[3]))); aBndBox.Add (Graphic3d_Vec3d (Draw::Atof (aChangeArgs[4]), Draw::Atof (aChangeArgs[5]), Draw::Atof (aChangeArgs[6]))); anArgIter += 6; Standard_Integer aNbSubPlanes = 6; const Graphic3d_Vec3d aDirArray[6] = { Graphic3d_Vec3d (-1, 0, 0), Graphic3d_Vec3d ( 1, 0, 0), Graphic3d_Vec3d ( 0,-1, 0), Graphic3d_Vec3d ( 0, 1, 0), Graphic3d_Vec3d ( 0, 0,-1), Graphic3d_Vec3d ( 0, 0, 1), }; Handle(Graphic3d_ClipPlane) aSubPln = aClipPlane; for (Standard_Integer aSubPlaneIter = 0; aSubPlaneIter < aNbSubPlanes; ++aSubPlaneIter) { const Graphic3d_Vec3d& aDir = aDirArray[aSubPlaneIter]; const Standard_Real aW = -aDir.Dot ((aSubPlaneIter % 2 == 1) ? aBndBox.CornerMax() : aBndBox.CornerMin()); aSubPln->SetEquation (gp_Pln (aDir.x(), aDir.y(), aDir.z(), aW)); if (aSubPlaneIter + 1 == aNbSubPlanes) { aSubPln->SetChainNextPlane (Handle(Graphic3d_ClipPlane)()); } else { aSubPln->SetChainNextPlane (new Graphic3d_ClipPlane (*aSubPln)); } aSubPln = aSubPln->ChainNextPlane(); } } else if (aChangeArg == "-capping" || aChangeArg == "capping") { if (aNbChangeArgs < 2) { std::cout << "Syntax error: need more arguments.\n"; return 1; } if (ViewerTest::ParseOnOff (aChangeArgs[1], toEnable)) { aClipPlane->SetCapping (toEnable); anArgIter += 1; } else { // just skip otherwise (old syntax) } } else if (aChangeArg == "-useobjectmaterial" || aChangeArg == "-useobjectmat" || aChangeArg == "-useobjmat" || aChangeArg == "-useobjmaterial") { if (aNbChangeArgs < 2) { std::cout << "Syntax error: need more arguments.\n"; return 1; } if (ViewerTest::ParseOnOff (aChangeArgs[1], toEnable)) { aClipPlane->SetUseObjectMaterial (toEnable == Standard_True); anArgIter += 1; } } else if (aChangeArg == "-useobjecttexture" || aChangeArg == "-useobjecttex" || aChangeArg == "-useobjtexture" || aChangeArg == "-useobjtex") { if (aNbChangeArgs < 2) { std::cout << "Syntax error: need more arguments.\n"; return 1; } if (ViewerTest::ParseOnOff (aChangeArgs[1], toEnable)) { aClipPlane->SetUseObjectTexture (toEnable == Standard_True); anArgIter += 1; } } else if (aChangeArg == "-useobjectshader" || aChangeArg == "-useobjshader") { if (aNbChangeArgs < 2) { std::cout << "Syntax error: need more arguments.\n"; return 1; } if (ViewerTest::ParseOnOff (aChangeArgs[1], toEnable)) { aClipPlane->SetUseObjectShader (toEnable == Standard_True); anArgIter += 1; } } else if (aChangeArg == "-color" || aChangeArg == "color") { Quantity_Color aColor; Standard_Integer aNbParsed = ViewerTest::ParseColor (aNbChangeArgs - 1, aChangeArgs + 1, aColor); if (aNbParsed == 0) { std::cout << "Syntax error: need more arguments.\n"; return 1; } Graphic3d_MaterialAspect aMat = aClipPlane->CappingMaterial(); aMat.SetAmbientColor (aColor); aMat.SetDiffuseColor (aColor); aClipPlane->SetCappingMaterial (aMat); anArgIter += aNbParsed; } else if (aChangeArg == "-texname" || aChangeArg == "texname") { if (aNbChangeArgs < 2) { std::cout << "Syntax error: need more arguments.\n"; return 1; } TCollection_AsciiString aTextureName (aChangeArgs[1]); Handle(Graphic3d_Texture2Dmanual) aTexture = new Graphic3d_Texture2Dmanual(aTextureName); if (!aTexture->IsDone()) { aClipPlane->SetCappingTexture (NULL); } else { aTexture->EnableModulate(); aTexture->EnableRepeat(); aClipPlane->SetCappingTexture (aTexture); } anArgIter += 1; } else if (aChangeArg == "-texscale" || aChangeArg == "texscale") { if (aClipPlane->CappingTexture().IsNull()) { std::cout << "Error: no texture is set.\n"; return 1; } if (aNbChangeArgs < 3) { std::cout << "Syntax error: need more arguments.\n"; return 1; } Standard_ShortReal aSx = (Standard_ShortReal)Draw::Atof (aChangeArgs[1]); Standard_ShortReal aSy = (Standard_ShortReal)Draw::Atof (aChangeArgs[2]); aClipPlane->CappingTexture()->GetParams()->SetScale (Graphic3d_Vec2 (aSx, aSy)); anArgIter += 2; } else if (aChangeArg == "-texorigin" || aChangeArg == "texorigin") // texture origin { if (aClipPlane->CappingTexture().IsNull()) { std::cout << "Error: no texture is set.\n"; return 1; } if (aNbChangeArgs < 3) { std::cout << "Syntax error: need more arguments.\n"; return 1; } Standard_ShortReal aTx = (Standard_ShortReal)Draw::Atof (aChangeArgs[1]); Standard_ShortReal aTy = (Standard_ShortReal)Draw::Atof (aChangeArgs[2]); aClipPlane->CappingTexture()->GetParams()->SetTranslation (Graphic3d_Vec2 (aTx, aTy)); anArgIter += 2; } else if (aChangeArg == "-texrotate" || aChangeArg == "texrotate") // texture rotation { if (aClipPlane->CappingTexture().IsNull()) { std::cout << "Error: no texture is set.\n"; return 1; } if (aNbChangeArgs < 2) { std::cout << "Syntax error: need more arguments.\n"; return 1; } Standard_ShortReal aRot = (Standard_ShortReal)Draw::Atof (aChangeArgs[1]); aClipPlane->CappingTexture()->GetParams()->SetRotation (aRot); anArgIter += 1; } else if (aChangeArg == "-hatch" || aChangeArg == "hatch") { if (aNbChangeArgs < 2) { std::cout << "Syntax error: need more arguments.\n"; return 1; } TCollection_AsciiString aHatchStr (aChangeArgs[1]); aHatchStr.LowerCase(); if (aHatchStr == "on") { aClipPlane->SetCappingHatchOn(); } else if (aHatchStr == "off") { aClipPlane->SetCappingHatchOff(); } else { aClipPlane->SetCappingHatch ((Aspect_HatchStyle)Draw::Atoi (aChangeArgs[1])); } anArgIter += 1; } else if (aChangeArg == "-delete" || aChangeArg == "delete") { removePlane (aRegPlanes, aPlaneName); return 0; } else if (aChangeArg == "-set" || aChangeArg == "-unset" || aChangeArg == "-setoverrideglobal") { // set / unset plane command const Standard_Boolean toSet = aChangeArg.StartsWith ("-set"); const Standard_Boolean toOverrideGlobal = aChangeArg == "-setoverrideglobal"; Standard_Integer anIt = 1; for (; anIt < aNbChangeArgs; ++anIt) { TCollection_AsciiString anEntityName (aChangeArgs[anIt]); if (anEntityName.IsEmpty() || anEntityName.Value (1) == '-') { break; } else if (!toOverrideGlobal && ViewerTest_myViews.IsBound1 (anEntityName)) { Handle(V3d_View) aView = ViewerTest_myViews.Find1 (anEntityName); if (toSet) { aView->AddClipPlane (aClipPlane); } else { aView->RemoveClipPlane (aClipPlane); } continue; } else if (GetMapOfAIS().IsBound2 (anEntityName)) { Handle(AIS_InteractiveObject) aIObj = Handle(AIS_InteractiveObject)::DownCast (GetMapOfAIS().Find2 (anEntityName)); if (toSet) { aIObj->AddClipPlane (aClipPlane); } else { aIObj->RemoveClipPlane (aClipPlane); } if (!aIObj->ClipPlanes().IsNull()) { aIObj->ClipPlanes()->SetOverrideGlobal (toOverrideGlobal); } } else { std::cout << "Error: object/view '" << anEntityName << "' is not found!\n"; return 1; } } if (anIt == 1) { // apply to active view if (toSet) { anActiveView->AddClipPlane (aClipPlane); } else { anActiveView->RemoveClipPlane (aClipPlane); } } else { anArgIter = anArgIter + anIt - 1; } } else { std::cout << "Syntax error: unknown argument '" << aChangeArg << "'.\n"; return 1; } } ViewerTest::RedrawAllViews(); return 0; } //=============================================================================================== //function : VZRange //purpose : //=============================================================================================== static int VZRange (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { const Handle(V3d_View)& aCurrentView = ViewerTest::CurrentView(); if (aCurrentView.IsNull()) { std::cout << theArgVec[0] << ": Call vinit before this command, please.\n"; return 1; } Handle(Graphic3d_Camera) aCamera = aCurrentView->Camera(); if (theArgsNb < 2) { theDi << "ZNear: " << aCamera->ZNear() << "\n"; theDi << "ZFar: " << aCamera->ZFar() << "\n"; return 0; } if (theArgsNb == 3) { Standard_Real aNewZNear = Draw::Atof (theArgVec[1]); Standard_Real aNewZFar = Draw::Atof (theArgVec[2]); if (aNewZNear >= aNewZFar) { std::cout << theArgVec[0] << ": invalid arguments: znear should be less than zfar.\n"; return 1; } if (!aCamera->IsOrthographic() && (aNewZNear <= 0.0 || aNewZFar <= 0.0)) { std::cout << theArgVec[0] << ": invalid arguments: "; std::cout << "znear, zfar should be positive for perspective camera.\n"; return 1; } aCamera->SetZRange (aNewZNear, aNewZFar); } else { std::cout << theArgVec[0] << ": wrong command arguments. Type help for more information.\n"; return 1; } aCurrentView->Redraw(); return 0; } //=============================================================================================== //function : VAutoZFit //purpose : //=============================================================================================== static int VAutoZFit (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { const Handle(V3d_View)& aCurrentView = ViewerTest::CurrentView(); if (aCurrentView.IsNull()) { std::cout << theArgVec[0] << ": Call vinit before this command, please.\n"; return 1; } Standard_Real aScale = aCurrentView->AutoZFitScaleFactor(); if (theArgsNb > 3) { std::cout << theArgVec[0] << ": wrong command arguments. Type help for more information.\n"; return 1; } if (theArgsNb < 2) { theDi << "Auto z-fit mode: \n" << "On: " << (aCurrentView->AutoZFitMode() ? "enabled" : "disabled") << "\n" << "Scale: " << aScale << "\n"; return 0; } Standard_Boolean isOn = Draw::Atoi (theArgVec[1]) == 1; if (theArgsNb >= 3) { aScale = Draw::Atoi (theArgVec[2]); } aCurrentView->SetAutoZFitMode (isOn, aScale); aCurrentView->AutoZFit(); aCurrentView->Redraw(); return 0; } //! Auxiliary function to print projection type inline const char* projTypeName (Graphic3d_Camera::Projection theProjType) { switch (theProjType) { case Graphic3d_Camera::Projection_Orthographic: return "orthographic"; case Graphic3d_Camera::Projection_Perspective: return "perspective"; case Graphic3d_Camera::Projection_Stereo: return "stereoscopic"; case Graphic3d_Camera::Projection_MonoLeftEye: return "monoLeftEye"; case Graphic3d_Camera::Projection_MonoRightEye: return "monoRightEye"; } return "UNKNOWN"; } //=============================================================================================== //function : VCamera //purpose : //=============================================================================================== static int VCamera (Draw_Interpretor& theDI, Standard_Integer theArgsNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cout << "Error: no active view.\n"; return 1; } Handle(Graphic3d_Camera) aCamera = aView->Camera(); if (theArgsNb < 2) { theDI << "ProjType: " << projTypeName (aCamera->ProjectionType()) << "\n"; theDI << "FOVy: " << aCamera->FOVy() << "\n"; theDI << "Distance: " << aCamera->Distance() << "\n"; theDI << "IOD: " << aCamera->IOD() << "\n"; theDI << "IODType: " << (aCamera->GetIODType() == Graphic3d_Camera::IODType_Absolute ? "absolute" : "relative") << "\n"; theDI << "ZFocus: " << aCamera->ZFocus() << "\n"; theDI << "ZFocusType: " << (aCamera->ZFocusType() == Graphic3d_Camera::FocusType_Absolute ? "absolute" : "relative") << "\n"; return 0; } for (Standard_Integer anArgIter = 1; anArgIter < theArgsNb; ++anArgIter) { Standard_CString anArg = theArgVec[anArgIter]; TCollection_AsciiString anArgCase (anArg); anArgCase.LowerCase(); if (anArgCase == "-proj" || anArgCase == "-projection" || anArgCase == "-projtype" || anArgCase == "-projectiontype") { theDI << projTypeName (aCamera->ProjectionType()) << " "; } else if (anArgCase == "-ortho" || anArgCase == "-orthographic") { aCamera->SetProjectionType (Graphic3d_Camera::Projection_Orthographic); } else if (anArgCase == "-persp" || anArgCase == "-perspective" || anArgCase == "-perspmono" || anArgCase == "-perspectivemono" || anArgCase == "-mono") { aCamera->SetProjectionType (Graphic3d_Camera::Projection_Perspective); } else if (anArgCase == "-stereo" || anArgCase == "-stereoscopic" || anArgCase == "-perspstereo" || anArgCase == "-perspectivestereo") { aCamera->SetProjectionType (Graphic3d_Camera::Projection_Stereo); } else if (anArgCase == "-left" || anArgCase == "-lefteye" || anArgCase == "-monoleft" || anArgCase == "-monolefteye" || anArgCase == "-perpsleft" || anArgCase == "-perpslefteye") { aCamera->SetProjectionType (Graphic3d_Camera::Projection_MonoLeftEye); } else if (anArgCase == "-right" || anArgCase == "-righteye" || anArgCase == "-monoright" || anArgCase == "-monorighteye" || anArgCase == "-perpsright") { aCamera->SetProjectionType (Graphic3d_Camera::Projection_MonoRightEye); } else if (anArgCase == "-dist" || anArgCase == "-distance") { Standard_CString anArgValue = (anArgIter + 1 < theArgsNb) ? theArgVec[anArgIter + 1] : NULL; if (anArgValue != NULL && *anArgValue != '-') { ++anArgIter; aCamera->SetDistance (Draw::Atof (anArgValue)); continue; } theDI << aCamera->Distance() << " "; } else if (anArgCase == "-iod") { Standard_CString anArgValue = (anArgIter + 1 < theArgsNb) ? theArgVec[anArgIter + 1] : NULL; if (anArgValue != NULL && *anArgValue != '-') { ++anArgIter; aCamera->SetIOD (aCamera->GetIODType(), Draw::Atof (anArgValue)); continue; } theDI << aCamera->IOD() << " "; } else if (anArgCase == "-iodtype") { Standard_CString anArgValue = (anArgIter + 1 < theArgsNb) ? theArgVec[anArgIter + 1] : ""; TCollection_AsciiString anValueCase (anArgValue); anValueCase.LowerCase(); if (anValueCase == "abs" || anValueCase == "absolute") { ++anArgIter; aCamera->SetIOD (Graphic3d_Camera::IODType_Absolute, aCamera->IOD()); continue; } else if (anValueCase == "rel" || anValueCase == "relative") { ++anArgIter; aCamera->SetIOD (Graphic3d_Camera::IODType_Relative, aCamera->IOD()); continue; } else if (*anArgValue != '-') { std::cout << "Error: unknown IOD type '" << anArgValue << "'\n"; return 1; } switch (aCamera->GetIODType()) { case Graphic3d_Camera::IODType_Absolute: theDI << "absolute "; break; case Graphic3d_Camera::IODType_Relative: theDI << "relative "; break; } } else if (anArgCase == "-zfocus") { Standard_CString anArgValue = (anArgIter + 1 < theArgsNb) ? theArgVec[anArgIter + 1] : NULL; if (anArgValue != NULL && *anArgValue != '-') { ++anArgIter; aCamera->SetZFocus (aCamera->ZFocusType(), Draw::Atof (anArgValue)); continue; } theDI << aCamera->ZFocus() << " "; } else if (anArgCase == "-zfocustype") { Standard_CString anArgValue = (anArgIter + 1 < theArgsNb) ? theArgVec[anArgIter + 1] : ""; TCollection_AsciiString anValueCase (anArgValue); anValueCase.LowerCase(); if (anValueCase == "abs" || anValueCase == "absolute") { ++anArgIter; aCamera->SetZFocus (Graphic3d_Camera::FocusType_Absolute, aCamera->ZFocus()); continue; } else if (anValueCase == "rel" || anValueCase == "relative") { ++anArgIter; aCamera->SetZFocus (Graphic3d_Camera::FocusType_Relative, aCamera->ZFocus()); continue; } else if (*anArgValue != '-') { std::cout << "Error: unknown ZFocus type '" << anArgValue << "'\n"; return 1; } switch (aCamera->ZFocusType()) { case Graphic3d_Camera::FocusType_Absolute: theDI << "absolute "; break; case Graphic3d_Camera::FocusType_Relative: theDI << "relative "; break; } } else if (anArgCase == "-fov" || anArgCase == "-fovy") { Standard_CString anArgValue = (anArgIter + 1 < theArgsNb) ? theArgVec[anArgIter + 1] : NULL; if (anArgValue != NULL && *anArgValue != '-') { ++anArgIter; aCamera->SetFOVy (Draw::Atof (anArgValue)); continue; } theDI << aCamera->FOVy() << " "; } else { std::cout << "Error: unknown argument '" << anArg << "'\n"; return 1; } } aView->AutoZFit(); aView->Redraw(); 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 : //============================================================================== static int VStereo (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (theArgNb < 2) { if (aView.IsNull()) { std::cout << "Error: no active viewer!\n"; return 0; } Standard_Boolean isActive = ViewerTest_myDefaultCaps.contextStereo; theDI << "Stereo " << (isActive ? "ON" : "OFF") << "\n"; if (isActive) { TCollection_AsciiString aMode; switch (aView->RenderingParams().StereoMode) { case Graphic3d_StereoMode_QuadBuffer : aMode = "quadBuffer"; break; case Graphic3d_StereoMode_RowInterlaced : aMode = "rowInterlaced"; break; case Graphic3d_StereoMode_ColumnInterlaced : aMode = "columnInterlaced"; break; case Graphic3d_StereoMode_ChessBoard : aMode = "chessBoard"; break; case Graphic3d_StereoMode_SideBySide : aMode = "sideBySide"; break; case Graphic3d_StereoMode_OverUnder : aMode = "overUnder"; break; case Graphic3d_StereoMode_SoftPageFlip : aMode = "softpageflip"; break; case Graphic3d_StereoMode_Anaglyph : aMode = "anaglyph"; switch (aView->RenderingParams().AnaglyphFilter) { case Graphic3d_RenderingParams::Anaglyph_RedCyan_Simple : aMode.AssignCat (" (redCyanSimple)"); break; case Graphic3d_RenderingParams::Anaglyph_RedCyan_Optimized : aMode.AssignCat (" (redCyan)"); break; case Graphic3d_RenderingParams::Anaglyph_YellowBlue_Simple : aMode.AssignCat (" (yellowBlueSimple)"); break; case Graphic3d_RenderingParams::Anaglyph_YellowBlue_Optimized: aMode.AssignCat (" (yellowBlue)"); break; case Graphic3d_RenderingParams::Anaglyph_GreenMagenta_Simple : aMode.AssignCat (" (greenMagentaSimple)"); break; default: break; } default: break; } theDI << "Mode " << aMode << "\n"; } return 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 && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams->ToReverseStereo = toEnable; } else if (aFlag == "-noreverse" || aFlag == "-noswap") { Standard_Boolean toDisable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::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; } //=============================================================================================== //function : VDefaults //purpose : //=============================================================================================== static int VDefaults (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { const Handle(AIS_InteractiveContext)& aCtx = ViewerTest::GetAISContext(); if (aCtx.IsNull()) { std::cerr << "No active viewer!\n"; return 1; } Handle(Prs3d_Drawer) aDefParams = aCtx->DefaultDrawer(); if (theArgsNb < 2) { if (aDefParams->TypeOfDeflection() == Aspect_TOD_RELATIVE) { theDi << "DeflType: relative\n" << "DeviationCoeff: " << aDefParams->DeviationCoefficient() << "\n"; } else { theDi << "DeflType: absolute\n" << "AbsoluteDeflection: " << aDefParams->MaximalChordialDeviation() << "\n"; } theDi << "AngularDeflection: " << (180.0 * aDefParams->HLRAngle() / M_PI) << "\n"; theDi << "AutoTriangulation: " << (aDefParams->IsAutoTriangulation() ? "on" : "off") << "\n"; return 0; } for (Standard_Integer anArgIter = 1; anArgIter < theArgsNb; ++anArgIter) { TCollection_AsciiString anArg (theArgVec[anArgIter]); anArg.UpperCase(); if (anArg == "-ABSDEFL" || anArg == "-ABSOLUTEDEFLECTION" || anArg == "-DEFL" || anArg == "-DEFLECTION") { if (++anArgIter >= theArgsNb) { std::cout << "Error: wrong syntax at " << anArg << "\n"; return 1; } aDefParams->SetTypeOfDeflection (Aspect_TOD_ABSOLUTE); aDefParams->SetMaximalChordialDeviation (Draw::Atof (theArgVec[anArgIter])); } else if (anArg == "-RELDEFL" || anArg == "-RELATIVEDEFLECTION" || anArg == "-DEVCOEFF" || anArg == "-DEVIATIONCOEFF" || anArg == "-DEVIATIONCOEFFICIENT") { if (++anArgIter >= theArgsNb) { std::cout << "Error: wrong syntax at " << anArg << "\n"; return 1; } aDefParams->SetTypeOfDeflection (Aspect_TOD_RELATIVE); aDefParams->SetDeviationCoefficient (Draw::Atof (theArgVec[anArgIter])); } else if (anArg == "-ANGDEFL" || anArg == "-ANGULARDEFL" || anArg == "-ANGULARDEFLECTION") { if (++anArgIter >= theArgsNb) { std::cout << "Error: wrong syntax at " << anArg << "\n"; return 1; } // currently HLRDeviationAngle is used instead of DeviationAngle in most places aDefParams->SetHLRAngle (M_PI * Draw::Atof (theArgVec[anArgIter]) / 180.0); } else if (anArg == "-AUTOTR" || anArg == "-AUTOTRIANG" || anArg == "-AUTOTRIANGULATION") { if (++anArgIter >= theArgsNb) { std::cout << "Error: wrong syntax at " << anArg << "\n"; return 1; } TCollection_AsciiString aValue (theArgVec[anArgIter]); aValue.LowerCase(); if (aValue == "on" || aValue == "1") { aDefParams->SetAutoTriangulation (Standard_True); } else if (aValue == "off" || aValue == "0") { aDefParams->SetAutoTriangulation (Standard_False); } } else { std::cerr << "Warning, unknown argument '" << anArg.ToCString() << "'\n"; } } return 0; } //! Auxiliary method inline void addLight (const Handle(V3d_Light)& theLightNew, const Graphic3d_ZLayerId theLayer, const Standard_Boolean theIsGlobal) { if (theLightNew.IsNull()) { return; } Handle(V3d_Viewer) aViewer = ViewerTest::GetViewerFromContext(); if (theLayer == Graphic3d_ZLayerId_UNKNOWN) { aViewer->AddLight (theLightNew); if (theIsGlobal) { aViewer->SetLightOn (theLightNew); } else { ViewerTest::CurrentView()->SetLightOn (theLightNew); } } else { Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (theLayer); if (aSettings.Lights().IsNull()) { aSettings.SetLights (new Graphic3d_LightSet()); } aSettings.Lights()->Add (theLightNew); aViewer->SetZLayerSettings (theLayer, aSettings); } } //! Auxiliary method inline Standard_Integer getLightId (const TCollection_AsciiString& theArgNext) { TCollection_AsciiString anArgNextCase (theArgNext); anArgNextCase.UpperCase(); if (anArgNextCase.Length() > 5 && anArgNextCase.SubString (1, 5).IsEqual ("LIGHT")) { return theArgNext.SubString (6, theArgNext.Length()).IntegerValue(); } else { return theArgNext.IntegerValue(); } } //=============================================================================================== //function : VLight //purpose : //=============================================================================================== static int VLight (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); Handle(V3d_Viewer) aViewer = ViewerTest::GetViewerFromContext(); if (aView.IsNull() || aViewer.IsNull()) { std::cerr << "No active viewer!\n"; return 1; } Standard_Real anXYZ[3] = {}; Standard_Real anAtten[2] = {}; if (theArgsNb < 2) { // print lights info Standard_Integer aLightId = 0; for (V3d_ListOfLightIterator aLightIter (aView->ActiveLightIterator()); aLightIter.More(); aLightIter.Next(), ++aLightId) { Handle(V3d_Light) aLight = aLightIter.Value(); const Quantity_Color aColor = aLight->Color(); theDi << "Light #" << aLightId << (!aLight->Name().IsEmpty() ? (TCollection_AsciiString(" ") + aLight->Name()) : "") << " [" << aLight->GetId() << "]" << "\n"; switch (aLight->Type()) { case V3d_AMBIENT: { theDi << " Type: Ambient\n"; theDi << " Intensity: " << aLight->Intensity() << "\n"; break; } case V3d_DIRECTIONAL: { theDi << " Type: Directional\n"; theDi << " Intensity: " << aLight->Intensity() << "\n"; theDi << " Headlight: " << (aLight->Headlight() ? "TRUE" : "FALSE") << "\n"; theDi << " Smoothness: " << aLight->Smoothness() << "\n"; aLight->Direction (anXYZ[0], anXYZ[1], anXYZ[2]); theDi << " Direction: " << anXYZ[0] << ", " << anXYZ[1] << ", " << anXYZ[2] << "\n"; break; } case V3d_POSITIONAL: { theDi << " Type: Positional\n"; theDi << " Intensity: " << aLight->Intensity() << "\n"; theDi << " Headlight: " << (aLight->Headlight() ? "TRUE" : "FALSE") << "\n"; theDi << " Smoothness: " << aLight->Smoothness() << "\n"; aLight->Position (anXYZ[0], anXYZ[1], anXYZ[2]); theDi << " Position: " << anXYZ[0] << ", " << anXYZ[1] << ", " << anXYZ[2] << "\n"; aLight->Attenuation (anAtten[0], anAtten[1]); theDi << " Atten.: " << anAtten[0] << " " << anAtten[1] << "\n"; break; } case V3d_SPOT: { theDi << " Type: Spot\n"; theDi << " Intensity: " << aLight->Intensity() << "\n"; theDi << " Headlight: " << (aLight->Headlight() ? "TRUE" : "FALSE") << "\n"; aLight->Position (anXYZ[0], anXYZ[1], anXYZ[2]); theDi << " Position: " << anXYZ[0] << ", " << anXYZ[1] << ", " << anXYZ[2] << "\n"; aLight->Direction (anXYZ[0], anXYZ[1], anXYZ[2]); theDi << " Direction: " << anXYZ[0] << ", " << anXYZ[1] << ", " << anXYZ[2] << "\n"; aLight->Attenuation (anAtten[0], anAtten[1]); theDi << " Atten.: " << anAtten[0] << " " << anAtten[1] << "\n"; theDi << " Angle: " << (aLight->Angle() * 180.0 / M_PI) << "\n"; theDi << " Exponent: " << aLight->Concentration() << "\n"; break; } default: { theDi << " Type: UNKNOWN\n"; break; } } theDi << " Color: " << aColor.Red() << ", " << aColor.Green() << ", " << aColor.Blue() << " [" << Quantity_Color::StringName (aColor.Name()) << "]\n"; } } Handle(V3d_Light) aLightNew; Handle(V3d_Light) aLightOld; Graphic3d_ZLayerId aLayer = Graphic3d_ZLayerId_UNKNOWN; Standard_Boolean isGlobal = Standard_True; Standard_Boolean toCreate = Standard_False; ViewerTest_AutoUpdater anUpdateTool (ViewerTest::GetAISContext(), aView); for (Standard_Integer anArgIt = 1; anArgIt < theArgsNb; ++anArgIt) { Handle(V3d_Light) aLightCurr = aLightNew.IsNull() ? aLightOld : aLightNew; TCollection_AsciiString aName, aValue; const TCollection_AsciiString anArg (theArgVec[anArgIt]); TCollection_AsciiString anArgCase (anArg); anArgCase.UpperCase(); if (anUpdateTool.parseRedrawMode (anArg)) { continue; } if (anArgCase.IsEqual ("NEW") || anArgCase.IsEqual ("ADD") || anArgCase.IsEqual ("CREATE") || anArgCase.IsEqual ("-NEW") || anArgCase.IsEqual ("-ADD") || anArgCase.IsEqual ("-CREATE")) { toCreate = Standard_True; } else if (anArgCase.IsEqual ("-LAYER") || anArgCase.IsEqual ("-ZLAYER")) { if (++anArgIt >= theArgsNb) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } TCollection_AsciiString aValStr (theArgVec[anArgIt]); aValStr.LowerCase(); if (aValStr == "default" || aValStr == "def") { aLayer = Graphic3d_ZLayerId_Default; } else if (aValStr == "top") { aLayer = Graphic3d_ZLayerId_Top; } else if (aValStr == "topmost") { aLayer = Graphic3d_ZLayerId_Topmost; } else if (aValStr == "toposd" || aValStr == "osd") { aLayer = Graphic3d_ZLayerId_TopOSD; } else if (aValStr == "botosd" || aValStr == "bottom") { aLayer = Graphic3d_ZLayerId_BotOSD; } else if (aValStr.IsIntegerValue()) { aLayer = Draw::Atoi (theArgVec[anArgIt]); } else { std::cout << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } } else if (anArgCase.IsEqual ("GLOB") || anArgCase.IsEqual ("GLOBAL") || anArgCase.IsEqual ("-GLOB") || anArgCase.IsEqual ("-GLOBAL")) { isGlobal = Standard_True; } else if (anArgCase.IsEqual ("LOC") || anArgCase.IsEqual ("LOCAL") || anArgCase.IsEqual ("-LOC") || anArgCase.IsEqual ("-LOCAL")) { isGlobal = Standard_False; } else if (anArgCase.IsEqual ("DEF") || anArgCase.IsEqual ("DEFAULTS") || anArgCase.IsEqual ("-DEF") || anArgCase.IsEqual ("-DEFAULTS")) { toCreate = Standard_False; aViewer->SetDefaultLights(); } else if (anArgCase.IsEqual ("CLR") || anArgCase.IsEqual ("CLEAR") || anArgCase.IsEqual ("-CLR") || anArgCase.IsEqual ("-CLEAR")) { toCreate = Standard_False; TColStd_SequenceOfInteger aLayers; aViewer->GetAllZLayers (aLayers); for (TColStd_SequenceOfInteger::Iterator aLayeriter (aLayers); aLayeriter.More(); aLayeriter.Next()) { if (aLayeriter.Value() == aLayer || aLayer == Graphic3d_ZLayerId_UNKNOWN) { Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayeriter.Value()); aSettings.SetLights (Handle(Graphic3d_LightSet)()); aViewer->SetZLayerSettings (aLayeriter.Value(), aSettings); if (aLayer != Graphic3d_ZLayerId_UNKNOWN) { break; } } } if (aLayer == Graphic3d_ZLayerId_UNKNOWN) { for (V3d_ListOfLightIterator aLightIter (aView->ActiveLightIterator()); aLightIter.More();) { Handle(V3d_Light) aLight = aLightIter.Value(); aViewer->DelLight (aLight); aLightIter = aView->ActiveLightIterator(); } } } else if (anArgCase.IsEqual ("AMB") || anArgCase.IsEqual ("AMBIENT") || anArgCase.IsEqual ("AMBLIGHT")) { if (!toCreate) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } addLight (aLightNew, aLayer, isGlobal); toCreate = Standard_False; aLightNew = new V3d_AmbientLight(); } else if (anArgCase.IsEqual ("DIRECTIONAL") || anArgCase.IsEqual ("DIRLIGHT")) { if (!toCreate) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } addLight (aLightNew, aLayer, isGlobal); toCreate = Standard_False; aLightNew = new V3d_DirectionalLight(); } else if (anArgCase.IsEqual ("SPOT") || anArgCase.IsEqual ("SPOTLIGHT")) { if (!toCreate) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } addLight (aLightNew, aLayer, isGlobal); toCreate = Standard_False; aLightNew = new V3d_SpotLight (gp_Pnt (0.0, 0.0, 0.0)); } else if (anArgCase.IsEqual ("POSLIGHT") || anArgCase.IsEqual ("POSITIONAL")) { if (!toCreate) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } addLight (aLightNew, aLayer, isGlobal); toCreate = Standard_False; aLightNew = new V3d_PositionalLight (gp_Pnt (0.0, 0.0, 0.0)); } else if (anArgCase.IsEqual ("CHANGE") || anArgCase.IsEqual ("-CHANGE")) { if (++anArgIt >= theArgsNb) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } addLight (aLightNew, aLayer, isGlobal); aLightNew.Nullify(); const Standard_Integer aLightId = getLightId (theArgVec[anArgIt]); Standard_Integer aLightIt = 0; for (V3d_ListOfLightIterator aLightIter (aView->ActiveLightIterator()); aLightIter.More(); aLightIter.Next(), ++aLightIt) { if (aLightIt == aLightId) { aLightOld = aLightIter.Value(); break; } } if (aLightOld.IsNull()) { std::cerr << "Light " << theArgVec[anArgIt] << " is undefined!\n"; return 1; } } else if (anArgCase.IsEqual ("DEL") || anArgCase.IsEqual ("DELETE") || anArgCase.IsEqual ("-DEL") || anArgCase.IsEqual ("-DELETE")) { Handle(V3d_Light) aLightDel; if (++anArgIt >= theArgsNb) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } const TCollection_AsciiString anArgNext (theArgVec[anArgIt]); const Standard_Integer aLightDelId = getLightId (theArgVec[anArgIt]); Standard_Integer aLightIt = 0; for (V3d_ListOfLightIterator aLightIter (aView->ActiveLightIterator()); aLightIter.More(); aLightIter.Next(), ++aLightIt) { aLightDel = aLightIter.Value(); if (aLightIt == aLightDelId) { break; } } if (aLightDel.IsNull()) { continue; } TColStd_SequenceOfInteger aLayers; aViewer->GetAllZLayers (aLayers); for (TColStd_SequenceOfInteger::Iterator aLayeriter (aLayers); aLayeriter.More(); aLayeriter.Next()) { if (aLayeriter.Value() == aLayer || aLayer == Graphic3d_ZLayerId_UNKNOWN) { Graphic3d_ZLayerSettings aSettings = aViewer->ZLayerSettings (aLayeriter.Value()); if (!aSettings.Lights().IsNull()) { aSettings.Lights()->Remove (aLightDel); if (aSettings.Lights()->IsEmpty()) { aSettings.SetLights (Handle(Graphic3d_LightSet)()); } } aViewer->SetZLayerSettings (aLayeriter.Value(), aSettings); if (aLayer != Graphic3d_ZLayerId_UNKNOWN) { break; } } } if (aLayer == Graphic3d_ZLayerId_UNKNOWN) { aViewer->DelLight (aLightDel); } } else if (anArgCase.IsEqual ("COLOR") || anArgCase.IsEqual ("COLOUR") || anArgCase.IsEqual ("-COLOR") || anArgCase.IsEqual ("-COLOUR")) { if (++anArgIt >= theArgsNb || aLightCurr.IsNull()) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } TCollection_AsciiString anArgNext (theArgVec[anArgIt]); anArgNext.UpperCase(); const Quantity_Color aColor = ViewerTest::GetColorFromName (anArgNext.ToCString()); aLightCurr->SetColor (aColor); } else if (anArgCase.IsEqual ("POS") || anArgCase.IsEqual ("POSITION") || anArgCase.IsEqual ("-POS") || anArgCase.IsEqual ("-POSITION")) { if ((anArgIt + 3) >= theArgsNb || aLightCurr.IsNull() || (aLightCurr->Type() != Graphic3d_TOLS_POSITIONAL && aLightCurr->Type() != Graphic3d_TOLS_SPOT)) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } anXYZ[0] = Atof (theArgVec[++anArgIt]); anXYZ[1] = Atof (theArgVec[++anArgIt]); anXYZ[2] = Atof (theArgVec[++anArgIt]); aLightCurr->SetPosition (anXYZ[0], anXYZ[1], anXYZ[2]); } else if (anArgCase.IsEqual ("DIR") || anArgCase.IsEqual ("DIRECTION") || anArgCase.IsEqual ("-DIR") || anArgCase.IsEqual ("-DIRECTION")) { if ((anArgIt + 3) >= theArgsNb || aLightCurr.IsNull() || (aLightCurr->Type() != Graphic3d_TOLS_DIRECTIONAL && aLightCurr->Type() != Graphic3d_TOLS_SPOT)) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } anXYZ[0] = Atof (theArgVec[++anArgIt]); anXYZ[1] = Atof (theArgVec[++anArgIt]); anXYZ[2] = Atof (theArgVec[++anArgIt]); aLightCurr->SetDirection (anXYZ[0], anXYZ[1], anXYZ[2]); } else if (anArgCase.IsEqual ("SM") || anArgCase.IsEqual ("SMOOTHNESS") || anArgCase.IsEqual ("-SM") || anArgCase.IsEqual ("-SMOOTHNESS")) { if (++anArgIt >= theArgsNb || aLightCurr.IsNull()) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } Standard_ShortReal aSmoothness = (Standard_ShortReal )Atof (theArgVec[anArgIt]); if (Abs (aSmoothness) <= ShortRealEpsilon()) { aLightCurr->SetIntensity (1.f); } else if (Abs (aLightCurr->Smoothness()) <= ShortRealEpsilon()) { aLightCurr->SetIntensity ((aSmoothness * aSmoothness) / 3.f); } else { Standard_ShortReal aSmoothnessRatio = static_cast (aSmoothness / aLightCurr->Smoothness()); aLightCurr->SetIntensity (aLightCurr->Intensity() / (aSmoothnessRatio * aSmoothnessRatio)); } if (aLightCurr->Type() == Graphic3d_TOLS_POSITIONAL) { aLightCurr->SetSmoothRadius (aSmoothness); } else if (aLightCurr->Type() == Graphic3d_TOLS_DIRECTIONAL) { aLightCurr->SetSmoothAngle (aSmoothness); } } else if (anArgCase.IsEqual ("INT") || anArgCase.IsEqual ("INTENSITY") || anArgCase.IsEqual ("-INT") || anArgCase.IsEqual ("-INTENSITY")) { if (++anArgIt >= theArgsNb || aLightCurr.IsNull()) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } Standard_ShortReal aIntensity = (Standard_ShortReal )Atof (theArgVec[anArgIt]); aLightCurr->SetIntensity (aIntensity); } else if (anArgCase.IsEqual ("ANG") || anArgCase.IsEqual ("ANGLE") || anArgCase.IsEqual ("-ANG") || anArgCase.IsEqual ("-ANGLE")) { if (++anArgIt >= theArgsNb || aLightCurr.IsNull() || aLightCurr->Type() != Graphic3d_TOLS_SPOT) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } Standard_ShortReal anAngle = (Standard_ShortReal )Atof (theArgVec[anArgIt]); aLightCurr->SetAngle (Standard_ShortReal (anAngle / 180.0 * M_PI)); } else if (anArgCase.IsEqual ("CONSTATTEN") || anArgCase.IsEqual ("CONSTATTENUATION") || anArgCase.IsEqual ("-CONSTATTEN") || anArgCase.IsEqual ("-CONSTATTENUATION")) { if (++anArgIt >= theArgsNb || aLightCurr.IsNull() || (aLightCurr->Type() != Graphic3d_TOLS_POSITIONAL && aLightCurr->Type() != Graphic3d_TOLS_SPOT)) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } aLightCurr->Attenuation (anAtten[0], anAtten[1]); anAtten[0] = Atof (theArgVec[anArgIt]); aLightCurr->SetAttenuation ((Standard_ShortReal )anAtten[0], (Standard_ShortReal )anAtten[1]); } else if (anArgCase.IsEqual ("LINATTEN") || anArgCase.IsEqual ("LINEARATTEN") || anArgCase.IsEqual ("LINEARATTENUATION") || anArgCase.IsEqual ("-LINATTEN") || anArgCase.IsEqual ("-LINEARATTEN") || anArgCase.IsEqual ("-LINEARATTENUATION")) { if (++anArgIt >= theArgsNb || aLightCurr.IsNull() || (aLightCurr->Type() != Graphic3d_TOLS_POSITIONAL && aLightCurr->Type() != Graphic3d_TOLS_SPOT)) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } aLightCurr->Attenuation (anAtten[0], anAtten[1]); anAtten[1] = Atof (theArgVec[anArgIt]); aLightCurr->SetAttenuation ((Standard_ShortReal )anAtten[0], (Standard_ShortReal )anAtten[1]); } else if (anArgCase.IsEqual ("EXP") || anArgCase.IsEqual ("EXPONENT") || anArgCase.IsEqual ("SPOTEXP") || anArgCase.IsEqual ("SPOTEXPONENT") || anArgCase.IsEqual ("-EXP") || anArgCase.IsEqual ("-EXPONENT") || anArgCase.IsEqual ("-SPOTEXP") || anArgCase.IsEqual ("-SPOTEXPONENT")) { if (++anArgIt >= theArgsNb || aLightCurr.IsNull() || aLightCurr->Type() != Graphic3d_TOLS_SPOT) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } aLightCurr->SetConcentration ((Standard_ShortReal )Atof (theArgVec[anArgIt])); } else if (anArgCase.IsEqual ("HEAD") || anArgCase.IsEqual ("HEADLIGHT") || anArgCase.IsEqual ("-HEAD") || anArgCase.IsEqual ("-HEADLIGHT")) { if (aLightCurr.IsNull() || aLightCurr->Type() == Graphic3d_TOLS_AMBIENT) { std::cerr << "Wrong syntax at argument '" << anArg << "'!\n"; return 1; } Standard_Boolean isHeadLight = Standard_True; if (anArgIt + 1 < theArgsNb && ViewerTest::ParseOnOff (theArgVec[anArgIt + 1], isHeadLight)) { ++anArgIt; } aLightCurr->SetHeadlight (isHeadLight); } else { std::cerr << "Warning: unknown argument '" << anArg << "'\n"; } } addLight (aLightNew, aLayer, isGlobal); return 0; } //! Read Graphic3d_RenderingParams::PerfCounters flag. static Standard_Boolean parsePerfStatsFlag (const TCollection_AsciiString& theValue, Standard_Boolean& theToReset, Graphic3d_RenderingParams::PerfCounters& theFlagsRem, Graphic3d_RenderingParams::PerfCounters& theFlagsAdd) { Graphic3d_RenderingParams::PerfCounters aFlag = Graphic3d_RenderingParams::PerfCounters_NONE; TCollection_AsciiString aVal = theValue; Standard_Boolean toReverse = Standard_False; if (aVal == "none") { theToReset = Standard_True; return Standard_True; } else if (aVal.StartsWith ("-")) { toReverse = Standard_True; aVal = aVal.SubString (2, aVal.Length()); } else if (aVal.StartsWith ("no")) { toReverse = Standard_True; aVal = aVal.SubString (3, aVal.Length()); } else if (aVal.StartsWith ("+")) { aVal = aVal.SubString (2, aVal.Length()); } else { theToReset = Standard_True; } if ( aVal == "fps" || aVal == "framerate") aFlag = Graphic3d_RenderingParams::PerfCounters_FrameRate; else if (aVal == "cpu") aFlag = Graphic3d_RenderingParams::PerfCounters_CPU; else if (aVal == "layers") aFlag = Graphic3d_RenderingParams::PerfCounters_Layers; else if (aVal == "structs" || aVal == "structures" || aVal == "objects") aFlag = Graphic3d_RenderingParams::PerfCounters_Structures; else if (aVal == "groups") aFlag = Graphic3d_RenderingParams::PerfCounters_Groups; else if (aVal == "arrays") aFlag = Graphic3d_RenderingParams::PerfCounters_GroupArrays; else if (aVal == "tris" || aVal == "triangles") aFlag = Graphic3d_RenderingParams::PerfCounters_Triangles; else if (aVal == "pnts" || aVal == "points") aFlag = Graphic3d_RenderingParams::PerfCounters_Points; else if (aVal == "mem" || aVal == "gpumem" || aVal == "estimmem") aFlag = Graphic3d_RenderingParams::PerfCounters_EstimMem; else if (aVal == "basic") aFlag = Graphic3d_RenderingParams::PerfCounters_Basic; else if (aVal == "extended" || aVal == "verbose" || aVal == "extra") aFlag = Graphic3d_RenderingParams::PerfCounters_Extended; else { return Standard_False; } if (toReverse) { theFlagsRem = Graphic3d_RenderingParams::PerfCounters(theFlagsRem | aFlag); } else { theFlagsAdd = Graphic3d_RenderingParams::PerfCounters(theFlagsAdd | aFlag); } return Standard_True; } //! Read Graphic3d_RenderingParams::PerfCounters flags. static Standard_Boolean convertToPerfStatsFlags (const TCollection_AsciiString& theValue, Graphic3d_RenderingParams::PerfCounters& theFlags) { TCollection_AsciiString aValue = theValue; Graphic3d_RenderingParams::PerfCounters aFlagsRem = Graphic3d_RenderingParams::PerfCounters_NONE; Graphic3d_RenderingParams::PerfCounters aFlagsAdd = Graphic3d_RenderingParams::PerfCounters_NONE; Standard_Boolean toReset = Standard_False; for (;;) { Standard_Integer aSplitPos = aValue.Search ("|"); if (aSplitPos <= 0) { if (!parsePerfStatsFlag (aValue, toReset, aFlagsRem, aFlagsAdd)) { return Standard_False; } if (toReset) { theFlags = Graphic3d_RenderingParams::PerfCounters_NONE; } theFlags = Graphic3d_RenderingParams::PerfCounters(theFlags | aFlagsAdd); theFlags = Graphic3d_RenderingParams::PerfCounters(theFlags & ~aFlagsRem); return Standard_True; } if (aSplitPos > 1) { TCollection_AsciiString aSubValue = aValue.SubString (1, aSplitPos - 1); if (!parsePerfStatsFlag (aSubValue, toReset, aFlagsRem, aFlagsAdd)) { return Standard_False; } } aValue = aValue.SubString (aSplitPos + 1, aValue.Length()); } } //======================================================================= //function : VRenderParams //purpose : Enables/disables rendering features //======================================================================= static Standard_Integer VRenderParams (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cerr << "Error: no active viewer!\n"; return 1; } Graphic3d_RenderingParams& aParams = aView->ChangeRenderingParams(); TCollection_AsciiString aCmdName (theArgVec[0]); aCmdName.LowerCase(); if (aCmdName == "vraytrace") { if (theArgNb == 1) { theDI << (aParams.Method == Graphic3d_RM_RAYTRACING ? "on" : "off") << " "; return 0; } else if (theArgNb == 2) { TCollection_AsciiString aValue (theArgVec[1]); aValue.LowerCase(); if (aValue == "on" || aValue == "1") { aParams.Method = Graphic3d_RM_RAYTRACING; aView->Redraw(); return 0; } else if (aValue == "off" || aValue == "0") { aParams.Method = Graphic3d_RM_RASTERIZATION; aView->Redraw(); return 0; } else { std::cout << "Error: unknown argument '" << theArgVec[1] << "'\n"; return 1; } } else { std::cout << "Error: wrong number of arguments\n"; return 1; } } if (theArgNb < 2) { theDI << "renderMode: "; switch (aParams.Method) { case Graphic3d_RM_RASTERIZATION: theDI << "rasterization "; break; case Graphic3d_RM_RAYTRACING: theDI << "raytrace "; break; } theDI << "\n"; theDI << "transparency: "; switch (aParams.TransparencyMethod) { case Graphic3d_RTM_BLEND_UNORDERED: theDI << "Basic blended transparency with non-commuting operator "; break; case Graphic3d_RTM_BLEND_OIT: theDI << "Weighted Blended Order-Independent Transparency, depth weight factor: " << TCollection_AsciiString (aParams.OitDepthFactor); break; } theDI << "\n"; theDI << "msaa: " << aParams.NbMsaaSamples << "\n"; theDI << "rendScale: " << aParams.RenderResolutionScale << "\n"; theDI << "rayDepth: " << aParams.RaytracingDepth << "\n"; theDI << "fsaa: " << (aParams.IsAntialiasingEnabled ? "on" : "off") << "\n"; theDI << "shadows: " << (aParams.IsShadowEnabled ? "on" : "off") << "\n"; theDI << "reflections: " << (aParams.IsReflectionEnabled ? "on" : "off") << "\n"; theDI << "gleam: " << (aParams.IsTransparentShadowEnabled ? "on" : "off") << "\n"; theDI << "GI: " << (aParams.IsGlobalIlluminationEnabled ? "on" : "off") << "\n"; theDI << "blocked RNG: " << (aParams.CoherentPathTracingMode ? "on" : "off") << "\n"; theDI << "iss: " << (aParams.AdaptiveScreenSampling ? "on" : "off") << "\n"; theDI << "iss debug: " << (aParams.ShowSamplingTiles ? "on" : "off") << "\n"; theDI << "two-sided BSDF: " << (aParams.TwoSidedBsdfModels ? "on" : "off") << "\n"; theDI << "max radiance: " << aParams.RadianceClampingValue << "\n"; theDI << "nb tiles (iss): " << aParams.NbRayTracingTiles << "\n"; theDI << "shadingModel: "; switch (aView->ShadingModel()) { case Graphic3d_TOSM_DEFAULT: theDI << "default"; break; case Graphic3d_TOSM_UNLIT: theDI << "unlit"; break; case Graphic3d_TOSM_FACET: theDI << "flat"; break; case Graphic3d_TOSM_VERTEX: theDI << "gouraud"; break; case Graphic3d_TOSM_FRAGMENT: theDI << "phong"; break; } { theDI << "perfCounters:"; if ((aParams.CollectedStats & Graphic3d_RenderingParams::PerfCounters_FrameRate) != 0) { theDI << " fps"; } if ((aParams.CollectedStats & Graphic3d_RenderingParams::PerfCounters_CPU) != 0) { theDI << " cpu"; } if ((aParams.CollectedStats & Graphic3d_RenderingParams::PerfCounters_Structures) != 0) { theDI << " structs"; } if ((aParams.CollectedStats & Graphic3d_RenderingParams::PerfCounters_Groups) != 0) { theDI << " groups"; } if ((aParams.CollectedStats & Graphic3d_RenderingParams::PerfCounters_GroupArrays) != 0) { theDI << " arrays"; } if ((aParams.CollectedStats & Graphic3d_RenderingParams::PerfCounters_Triangles) != 0) { theDI << " tris"; } if ((aParams.CollectedStats & Graphic3d_RenderingParams::PerfCounters_Points) != 0) { theDI << " pnts"; } if ((aParams.CollectedStats & Graphic3d_RenderingParams::PerfCounters_EstimMem) != 0) { theDI << " gpumem"; } if (aParams.CollectedStats == Graphic3d_RenderingParams::PerfCounters_NONE) { theDI << " none"; } theDI << "\n"; } theDI << "depth pre-pass: " << (aParams.ToEnableDepthPrepass ? "on" : "off") << "\n"; theDI << "alpha to coverage: " << (aParams.ToEnableAlphaToCoverage ? "on" : "off") << "\n"; theDI << "\n"; return 0; } Standard_Boolean toPrint = Standard_False; 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 == "-echo" || aFlag == "-print") { toPrint = Standard_True; anUpdateTool.Invalidate(); } else if (aFlag == "-mode" || aFlag == "-rendermode" || aFlag == "-render_mode") { if (toPrint) { switch (aParams.Method) { case Graphic3d_RM_RASTERIZATION: theDI << "rasterization "; break; case Graphic3d_RM_RAYTRACING: theDI << "ray-tracing "; break; } continue; } else { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } } else if (aFlag == "-ray" || aFlag == "-raytrace") { if (toPrint) { theDI << (aParams.Method == Graphic3d_RM_RAYTRACING ? "true" : "false") << " "; continue; } aParams.Method = Graphic3d_RM_RAYTRACING; } else if (aFlag == "-rast" || aFlag == "-raster" || aFlag == "-rasterization") { if (toPrint) { theDI << (aParams.Method == Graphic3d_RM_RASTERIZATION ? "true" : "false") << " "; continue; } aParams.Method = Graphic3d_RM_RASTERIZATION; } else if (aFlag == "-msaa") { if (toPrint) { theDI << aParams.NbMsaaSamples << " "; continue; } else if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } const Standard_Integer aNbSamples = Draw::Atoi (theArgVec[anArgIter]); if (aNbSamples < 0) { std::cerr << "Error: invalid number of MSAA samples " << aNbSamples << ".\n"; return 1; } else { aParams.NbMsaaSamples = aNbSamples; } } else if (aFlag == "-oit") { if (toPrint) { if (aParams.TransparencyMethod == Graphic3d_RTM_BLEND_OIT) { theDI << "on, depth weight factor: " << TCollection_AsciiString (aParams.OitDepthFactor) << " "; } else { theDI << "off" << " "; } continue; } else if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } TCollection_AsciiString aParam = theArgVec[anArgIter]; aParam.LowerCase(); if (aParam.IsRealValue()) { const Standard_ShortReal aWeight = (Standard_ShortReal) Draw::Atof (theArgVec[anArgIter]); if (aWeight < 0.f || aWeight > 1.f) { std::cerr << "Error: invalid value of Weighted Order-Independent Transparency depth weight factor " << aWeight << ". Should be within range [0.0; 1.0]\n"; return 1; } aParams.TransparencyMethod = Graphic3d_RTM_BLEND_OIT; aParams.OitDepthFactor = aWeight; } else if (aParam == "off") { aParams.TransparencyMethod = Graphic3d_RTM_BLEND_UNORDERED; } else { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } } else if (aFlag == "-depthprepass") { if (toPrint) { theDI << (aParams.ToEnableDepthPrepass ? "on " : "off "); continue; } aParams.ToEnableDepthPrepass = Standard_True; if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], aParams.ToEnableDepthPrepass)) { ++anArgIter; } } else if (aFlag == "-samplealphatocoverage" || aFlag == "-alphatocoverage") { if (toPrint) { theDI << (aParams.ToEnableAlphaToCoverage ? "on " : "off "); continue; } aParams.ToEnableAlphaToCoverage = Standard_True; if (anArgIter + 1 < theArgNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], aParams.ToEnableAlphaToCoverage)) { ++anArgIter; } } else if (aFlag == "-rendscale" || aFlag == "-renderscale" || aFlag == "-renderresolutionscale") { if (toPrint) { theDI << aParams.RenderResolutionScale << " "; continue; } else if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } const Standard_Real aScale = Draw::Atof (theArgVec[anArgIter]); if (aScale < 0.01) { std::cerr << "Error: invalid rendering resolution scale " << aScale << ".\n"; return 1; } else { aParams.RenderResolutionScale = Standard_ShortReal(aScale); } } else if (aFlag == "-raydepth" || aFlag == "-ray_depth") { if (toPrint) { theDI << aParams.RaytracingDepth << " "; continue; } else if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } const Standard_Integer aDepth = Draw::Atoi (theArgVec[anArgIter]); // We allow RaytracingDepth be more than 10 in case of GI enabled if (aDepth < 1 || (aDepth > 10 && !aParams.IsGlobalIlluminationEnabled)) { std::cerr << "Error: invalid ray-tracing depth " << aDepth << ". Should be within range [1; 10]\n"; return 1; } else { aParams.RaytracingDepth = aDepth; } } else if (aFlag == "-shad" || aFlag == "-shadows") { if (toPrint) { theDI << (aParams.IsShadowEnabled ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.IsShadowEnabled = toEnable; } else if (aFlag == "-refl" || aFlag == "-reflections") { if (toPrint) { theDI << (aParams.IsReflectionEnabled ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.IsReflectionEnabled = toEnable; } else if (aFlag == "-fsaa") { if (toPrint) { theDI << (aParams.IsAntialiasingEnabled ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.IsAntialiasingEnabled = toEnable; } else if (aFlag == "-gleam") { if (toPrint) { theDI << (aParams.IsTransparentShadowEnabled ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.IsTransparentShadowEnabled = toEnable; } else if (aFlag == "-gi") { if (toPrint) { theDI << (aParams.IsGlobalIlluminationEnabled ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.IsGlobalIlluminationEnabled = toEnable; if (!toEnable) { aParams.RaytracingDepth = Min (aParams.RaytracingDepth, 10); } } else if (aFlag == "-blockedrng" || aFlag == "-brng") { if (toPrint) { theDI << (aParams.CoherentPathTracingMode ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.CoherentPathTracingMode = toEnable; } else if (aFlag == "-maxrad") { if (toPrint) { theDI << aParams.RadianceClampingValue << " "; continue; } else if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } const TCollection_AsciiString aMaxRadStr = theArgVec[anArgIter]; if (!aMaxRadStr.IsRealValue()) { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } const Standard_Real aMaxRadiance = aMaxRadStr.RealValue(); if (aMaxRadiance <= 0.0) { std::cerr << "Error: invalid radiance clamping value " << aMaxRadiance << ".\n"; return 1; } else { aParams.RadianceClampingValue = static_cast (aMaxRadiance); } } else if (aFlag == "-iss") { if (toPrint) { theDI << (aParams.AdaptiveScreenSampling ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.AdaptiveScreenSampling = toEnable; } else if (aFlag == "-issd") { if (toPrint) { theDI << (aParams.ShowSamplingTiles ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.ShowSamplingTiles = toEnable; } else if (aFlag == "-nbtiles") { if (toPrint) { theDI << aParams.NbRayTracingTiles << " "; continue; } else if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } const Standard_Integer aNbTiles = Draw::Atoi (theArgVec[anArgIter]); if (aNbTiles < 64) { std::cerr << "Error: invalid number of ISS tiles " << aNbTiles << ".\n"; std::cerr << "Specify value in range [64, 1024].\n"; return 1; } else { aParams.NbRayTracingTiles = aNbTiles; } } else if (aFlag == "-env") { if (toPrint) { theDI << (aParams.UseEnvironmentMapBackground ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.UseEnvironmentMapBackground = toEnable; } else if (aFlag == "-twoside") { if (toPrint) { theDI << (aParams.TwoSidedBsdfModels ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.TwoSidedBsdfModels = toEnable; } else if (aFlag == "-shademodel" || aFlag == "-shadingmodel" || aFlag == "-shading") { if (toPrint) { switch (aView->ShadingModel()) { case Graphic3d_TOSM_DEFAULT: theDI << "default"; break; case Graphic3d_TOSM_UNLIT: theDI << "unlit "; break; case Graphic3d_TOSM_FACET: theDI << "flat "; break; case Graphic3d_TOSM_VERTEX: theDI << "gouraud "; break; case Graphic3d_TOSM_FRAGMENT: theDI << "phong "; break; } continue; } if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; } Graphic3d_TypeOfShadingModel aModel = Graphic3d_TOSM_DEFAULT; if (ViewerTest::ParseShadingModel (theArgVec[anArgIter], aModel) && aModel != Graphic3d_TOSM_DEFAULT) { aView->SetShadingModel (aModel); } else { std::cout << "Error: unknown shading model '" << theArgVec[anArgIter] << "'\n"; return 1; } } else if (aFlag == "-resolution") { if (++anArgIter >= theArgNb) { std::cerr << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } TCollection_AsciiString aResolution (theArgVec[anArgIter]); if (aResolution.IsIntegerValue()) { aView->ChangeRenderingParams().Resolution = static_cast (Draw::Atoi (aResolution.ToCString())); } else { std::cout << "Error: wrong syntax at argument'" << anArg << "'.\n"; return 1; } } else if (aFlag == "-rebuildglsl" || aFlag == "-rebuild") { if (toPrint) { theDI << (aParams.RebuildRayTracingShaders ? "on" : "off") << " "; continue; } Standard_Boolean toEnable = Standard_True; if (++anArgIter < theArgNb && !ViewerTest::ParseOnOff (theArgVec[anArgIter], toEnable)) { --anArgIter; } aParams.RebuildRayTracingShaders = toEnable; } else if (aFlag == "-focal") { if (++anArgIter >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } TCollection_AsciiString aParam (theArgVec[anArgIter]); if (aParam.IsRealValue()) { float aFocalDist = static_cast (aParam.RealValue()); if (aFocalDist < 0) { std::cout << "Error: parameter can't be negative at argument '" << anArg << "'.\n"; return 1; } aView->ChangeRenderingParams().CameraFocalPlaneDist = aFocalDist; } else { std::cout << "Error: wrong syntax at argument'" << anArg << "'.\n"; return 1; } } else if (aFlag == "-aperture") { if (++anArgIter >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } TCollection_AsciiString aParam(theArgVec[anArgIter]); if (aParam.IsRealValue()) { float aApertureSize = static_cast (aParam.RealValue()); if (aApertureSize < 0) { std::cout << "Error: parameter can't be negative at argument '" << anArg << "'.\n"; return 1; } aView->ChangeRenderingParams().CameraApertureRadius = aApertureSize; } else { std::cout << "Error: wrong syntax at argument'" << anArg << "'.\n"; return 1; } } else if (aFlag == "-exposure") { if (++anArgIter >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } TCollection_AsciiString anExposure (theArgVec[anArgIter]); if (anExposure.IsRealValue()) { aView->ChangeRenderingParams().Exposure = static_cast (anExposure.RealValue()); } else { std::cout << "Error: wrong syntax at argument'" << anArg << "'.\n"; return 1; } } else if (aFlag == "-whitepoint") { if (++anArgIter >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } TCollection_AsciiString aWhitePoint (theArgVec[anArgIter]); if (aWhitePoint.IsRealValue()) { aView->ChangeRenderingParams().WhitePoint = static_cast (aWhitePoint.RealValue()); } else { std::cout << "Error: wrong syntax at argument'" << anArg << "'.\n"; return 1; } } else if (aFlag == "-tonemapping") { if (++anArgIter >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } TCollection_AsciiString aMode (theArgVec[anArgIter]); aMode.LowerCase(); if (aMode == "disabled") { aView->ChangeRenderingParams().ToneMappingMethod = Graphic3d_ToneMappingMethod_Disabled; } else if (aMode == "filmic") { aView->ChangeRenderingParams().ToneMappingMethod = Graphic3d_ToneMappingMethod_Filmic; } else { std::cout << "Error: wrong syntax at argument'" << anArg << "'.\n"; return 1; } } else if (aFlag == "-performancestats" || aFlag == "-performancecounters" || aFlag == "-perfstats" || aFlag == "-perfcounters" || aFlag == "-stats") { if (++anArgIter >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } TCollection_AsciiString aFlagsStr (theArgVec[anArgIter]); aFlagsStr.LowerCase(); Graphic3d_RenderingParams::PerfCounters aFlags = aView->ChangeRenderingParams().CollectedStats; if (!convertToPerfStatsFlags (aFlagsStr, aFlags)) { std::cout << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } aView->ChangeRenderingParams().CollectedStats = aFlags; aView->ChangeRenderingParams().ToShowStats = aFlags != Graphic3d_RenderingParams::PerfCounters_NONE; } else if (aFlag == "-perfupdateinterval" || aFlag == "-statsupdateinterval") { if (++anArgIter >= theArgNb) { std::cout << "Error: wrong syntax at argument '" << anArg << "'\n"; return 1; } aView->ChangeRenderingParams().StatsUpdateInterval = (Standard_ShortReal )Draw::Atof (theArgVec[anArgIter]); } else { std::cout << "Error: wrong syntax, unknown flag '" << anArg << "'\n"; return 1; } } return 0; } //======================================================================= //function : VProgressiveMode //purpose : //======================================================================= #if defined(_WIN32) static Standard_Integer VProgressiveMode (Draw_Interpretor& /*theDI*/, Standard_Integer /*theNbArgs*/, const char** /*theArgs*/) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cerr << "Error: no active viewer!\n"; return 1; } std::cout << "Press Enter or Escape key to exit progressive rendering mode" << std::endl; for (;;) { aView->Redraw(); Standard_Boolean toExit = Standard_False; MSG aMsg; while (PeekMessageW (&aMsg, NULL, 0, 0, PM_REMOVE)) { if (aMsg.message == WM_KEYDOWN && (aMsg.wParam == 0x0d || aMsg.wParam == 0x1b)) { toExit = Standard_True; } TranslateMessage (&aMsg); DispatchMessageW (&aMsg); } if (toExit) { break; } } return 0; } #endif //======================================================================= //function : VFrustumCulling //purpose : enables/disables view volume's culling. //======================================================================= static int VFrustumCulling (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); if (aView.IsNull()) { std::cout << theArgVec[0] << " Error: Use 'vinit' command before\n"; return 1; } if (theArgNb < 2) { theDI << (aView->IsCullingEnabled() ? "on" : "off"); return 0; } else if (theArgNb != 2) { std::cout << theArgVec[0] << " Syntax error: Specify the mode\n"; return 1; } TCollection_AsciiString aModeStr (theArgVec[1]); aModeStr.LowerCase(); Standard_Boolean toEnable = 0; if (aModeStr == "on") { toEnable = 1; } else if (aModeStr == "off") { toEnable = 0; } else { toEnable = Draw::Atoi (theArgVec[1]) != 0; } aView->SetFrustumCulling (toEnable); aView->Redraw(); return 0; } //======================================================================= //function : VHighlightSelected //purpose : //======================================================================= static int VHighlightSelected (Draw_Interpretor& theDI, Standard_Integer theArgNb, const char** theArgVec) { if (ViewerTest::GetAISContext().IsNull()) { std::cout << theArgVec[0] << " error : Context is not created. Please call vinit before.\n"; return 1; } const Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if (theArgNb < 2) { theDI << (aContext->ToHilightSelected() ? "on" : "off"); return 0; } if (theArgNb != 2) { std::cout << theArgVec[0] << " error : wrong number of parameters." << "Type 'help" << theArgVec[0] << "' for more information."; return 1; } // Parse parameter TCollection_AsciiString aMode (theArgVec[1]); aMode.LowerCase(); Standard_Boolean toEnable = Standard_False; if (aMode.IsEqual ("on")) { toEnable = Standard_True; } else if (aMode.IsEqual ("off")) { toEnable = Standard_False; } else { toEnable = Draw::Atoi (theArgVec[1]) != 0; } if (toEnable != aContext->ToHilightSelected()) { aContext->SetToHilightSelected (toEnable); // Move cursor to null position and back to process updating of detection // and highlighting of selected object immediatly. Standard_Integer aPixX = 0; Standard_Integer aPixY = 0; const Handle(ViewerTest_EventManager)& anEventManager = ViewerTest::CurrentEventManager(); anEventManager->GetCurrentPosition (aPixX, aPixY); anEventManager->MoveTo (0, 0); anEventManager->MoveTo (aPixX, aPixY); } return 0; } //======================================================================= //function : VXRotate //purpose : //======================================================================= static Standard_Integer VXRotate (Draw_Interpretor& di, Standard_Integer argc, const char ** argv) { Handle(AIS_InteractiveContext) aContext = ViewerTest::GetAISContext(); if (aContext.IsNull()) { di << argv[0] << "ERROR : use 'vinit' command before \n"; return 1; } if (argc != 3) { di << "ERROR : Usage : " << argv[0] << " name angle\n"; return 1; } TCollection_AsciiString aName (argv[1]); Standard_Real anAngle = Draw::Atof (argv[2]); // find object ViewerTest_DoubleMapOfInteractiveAndName& aMap = GetMapOfAIS(); Handle(AIS_InteractiveObject) anIObj; if (!aMap.IsBound2 (aName) ) { di << "Use 'vdisplay' before\n"; return 1; } else { anIObj = Handle(AIS_InteractiveObject)::DownCast (aMap.Find2 (aName)); gp_Trsf aTransform; aTransform.SetRotation (gp_Ax1 (gp_Pnt (0.0, 0.0, 0.0), gp_Vec (1.0, 0.0, 0.0)), anAngle); aTransform.SetTranslationPart (anIObj->LocalTransformation().TranslationPart()); aContext->SetLocation (anIObj, aTransform); aContext->UpdateCurrentViewer(); } return 0; } //=============================================================================================== //class : ViewerTest_AISManipulator //purpose : Proxy class maintaining automated registry map to enlist existing AIS_Manipulator instances //=============================================================================================== DEFINE_STANDARD_HANDLE (ViewerTest_AISManipulator, AIS_Manipulator) class ViewerTest_AISManipulator : public AIS_Manipulator { public: ViewerTest_AISManipulator() : AIS_Manipulator() { GetMapOfAISManipulators().Add (this); } virtual ~ViewerTest_AISManipulator() { GetMapOfAISManipulators().Remove (this); } DEFINE_STANDARD_RTTIEXT(ViewerTest_AISManipulator, AIS_Manipulator) }; IMPLEMENT_STANDARD_HANDLE (ViewerTest_AISManipulator, AIS_Manipulator) IMPLEMENT_STANDARD_RTTIEXT(ViewerTest_AISManipulator, AIS_Manipulator) //=============================================================================================== //function : VManipulator //purpose : //=============================================================================================== static int VManipulator (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { Handle(V3d_View) aView = ViewerTest::CurrentView(); Handle(V3d_Viewer) aViewer = ViewerTest::GetViewerFromContext(); ViewerTest::GetAISContext()->MainSelector()->SetPickClosest (Standard_False); if (aView.IsNull() || aViewer.IsNull()) { std::cerr << "No active viewer!\n"; return 1; } ViewerTest_AutoUpdater anUpdateTool (ViewerTest::GetAISContext(), ViewerTest::CurrentView()); Standard_Integer anArgIter = 1; for (; anArgIter < theArgsNb; ++anArgIter) { anUpdateTool.parseRedrawMode (theArgVec[anArgIter]); } ViewerTest_CmdParser aCmd; aCmd.AddDescription ("Manages manipulator for interactive objects:"); aCmd.AddOption ("attach", "... object - attach manipulator to an object"); aCmd.AddOption ("adjustPosition", "... {0|1} - adjust position when attaching"); aCmd.AddOption ("adjustSize", "... {0|1} - adjust size when attaching "); aCmd.AddOption ("enableModes", "... {0|1} - enable modes when attaching "); aCmd.AddOption ("detach", "... - detach manipulator"); aCmd.AddOption ("startTransform", "... mouse_x mouse_y - invoke start transformation"); aCmd.AddOption ("transform", "... mouse_x mouse_y - invoke transformation"); aCmd.AddOption ("stopTransform", "... [abort] - invoke stop transformation"); aCmd.AddOption ("move", "... x y z - move object"); aCmd.AddOption ("rotate", "... x y z dx dy dz angle - rotate object"); aCmd.AddOption ("scale", "... factor - scale object"); aCmd.AddOption ("autoActivate", "... {0|1} - set activation on detection"); aCmd.AddOption ("followTranslation", "... {0|1} - set following translation transform"); aCmd.AddOption ("followRotation", "... {0|1} - set following rotation transform"); aCmd.AddOption ("gap", "... value - set gap between sub-parts"); aCmd.AddOption ("part", "... axis mode {0|1} - set visual part"); aCmd.AddOption ("pos", "... x y z [nx ny nz [xx xy xz]] - set position of manipulator"); aCmd.AddOption ("size", "... size - set size of manipulator"); aCmd.AddOption ("zoomable", "... {0|1} - set zoom persistence"); aCmd.Parse (theArgsNb, theArgVec); if (aCmd.HasOption ("help")) { theDi.PrintHelp (theArgVec[0]); return 0; } ViewerTest_DoubleMapOfInteractiveAndName& aMapAIS = GetMapOfAIS(); TCollection_AsciiString aName (aCmd.Arg ("", 0).c_str()); if (aName.IsEmpty()) { std::cerr << theArgVec[0] << " error: please specify AIS manipulator's name as the first argument.\n"; return 1; } // ---------------------------------- // detach existing manipulator object // ---------------------------------- if (aCmd.HasOption ("detach")) { if (!aMapAIS.IsBound2 (aName)) { std::cerr << theArgVec[0] << " error: could not find \"" << aName << "\" AIS object.\n"; return 1; } Handle(AIS_Manipulator) aManipulator = Handle(AIS_Manipulator)::DownCast (aMapAIS.Find2 (aName)); if (aManipulator.IsNull()) { std::cerr << theArgVec[0] << " error: \"" << aName << "\" is not an AIS manipulator.\n"; return 1; } aManipulator->Detach(); aMapAIS.UnBind2 (aName); ViewerTest::GetAISContext()->Remove (aManipulator, Standard_True); return 0; } // ----------------------------------------------- // find or create manipulator if it does not exist // ----------------------------------------------- Handle(AIS_Manipulator) aManipulator; if (!aMapAIS.IsBound2 (aName)) { std::cout << theArgVec[0] << ": AIS object \"" << aName << "\" has been created.\n"; aManipulator = new ViewerTest_AISManipulator(); aMapAIS.Bind (aManipulator, aName); } else { aManipulator = Handle(AIS_Manipulator)::DownCast (aMapAIS.Find2 (aName)); if (aManipulator.IsNull()) { std::cerr << theArgVec[0] << " error: \"" << aName << "\" is not an AIS manipulator.\n"; return 1; } } // ----------------------------------------- // change properties of manipulator instance // ----------------------------------------- if (aCmd.HasOption ("autoActivate", 1, Standard_True)) { aManipulator->SetModeActivationOnDetection (aCmd.ArgBool ("autoActivate")); } if (aCmd.HasOption ("followTranslation", 1, Standard_True)) { aManipulator->ChangeTransformBehavior().SetFollowTranslation (aCmd.ArgBool ("followTranslation")); } if (aCmd.HasOption ("followRotation", 1, Standard_True)) { aManipulator->ChangeTransformBehavior().SetFollowRotation (aCmd.ArgBool ("followRotation")); } if (aCmd.HasOption ("gap", 1, Standard_True)) { aManipulator->SetGap (aCmd.ArgFloat ("gap")); } if (aCmd.HasOption ("part", 3, Standard_True)) { Standard_Integer anAxis = aCmd.ArgInt ("part", 0); Standard_Integer aMode = aCmd.ArgInt ("part", 1); Standard_Boolean aOnOff = aCmd.ArgBool ("part", 2); if (aMode < 1 || aMode > 3) { std::cerr << theArgVec[0] << " error: mode value should be in range [1, 3].\n"; return 1; } aManipulator->SetPart (anAxis, static_cast (aMode), aOnOff); } if (aCmd.HasOption ("pos", 3, Standard_True)) { gp_Pnt aLocation = aCmd.ArgPnt ("pos", 0); gp_Dir aVDir = aCmd.HasOption ("pos", 6) ? gp_Dir (aCmd.ArgVec ("pos", 3)) : aManipulator->Position().Direction(); gp_Dir aXDir = aCmd.HasOption ("pos", 9) ? gp_Dir (aCmd.ArgVec ("pos", 6)) : aManipulator->Position().XDirection(); aManipulator->SetPosition (gp_Ax2 (aLocation, aVDir, aXDir)); } if (aCmd.HasOption ("size", 1, Standard_True)) { aManipulator->SetSize (aCmd.ArgFloat ("size")); } if (aCmd.HasOption ("zoomable", 1, Standard_True)) { aManipulator->SetZoomPersistence (!aCmd.ArgBool ("zoomable")); if (ViewerTest::GetAISContext()->IsDisplayed (aManipulator)) { ViewerTest::GetAISContext()->Remove (aManipulator, Standard_False); ViewerTest::GetAISContext()->Display (aManipulator, Standard_False); } } // --------------------------------------------------- // attach, detach or access manipulator from an object // --------------------------------------------------- if (aCmd.HasOption ("attach")) { // Find an object and attach manipulator to it if (!aCmd.HasOption ("attach", 1, Standard_True)) { return 1; } TCollection_AsciiString anObjName (aCmd.Arg ("attach", 0).c_str()); if (!aMapAIS.IsBound2 (anObjName)) { std::cerr << theArgVec[0] << " error: AIS object \"" << anObjName << "\" does not exist.\n"; return 1; } Handle(AIS_InteractiveObject) anObject = Handle(AIS_InteractiveObject)::DownCast (aMapAIS.Find2 (anObjName)); ViewerTest_MapOfAISManipulators::Iterator anIt (GetMapOfAISManipulators()); for (; anIt.More(); anIt.Next()) { if (anIt.Value()->IsAttached() && anIt.Value()->Object() == anObject) { std::cerr << theArgVec[0] << " error: AIS object \"" << anObjName << "\" already has manipulator.\n"; return 1; } } AIS_Manipulator::OptionsForAttach anOptions; if (aCmd.HasOption ("adjustPosition", 1, Standard_True)) { anOptions.SetAdjustPosition (aCmd.ArgBool ("adjustPosition")); } if (aCmd.HasOption ("adjustSize", 1, Standard_True)) { anOptions.SetAdjustSize (aCmd.ArgBool ("adjustSize")); } if (aCmd.HasOption ("enableModes", 1, Standard_True)) { anOptions.SetEnableModes (aCmd.ArgBool ("enableModes")); } aManipulator->Attach (anObject, anOptions); } // -------------------------------------- // apply transformation using manipulator // -------------------------------------- if (aCmd.HasOption ("startTransform", 2, Standard_True)) { aManipulator->StartTransform (aCmd.ArgInt ("startTransform", 0), aCmd.ArgInt ("startTransform", 1), ViewerTest::CurrentView()); } if (aCmd.HasOption ("transform", 2, Standard_True)) { aManipulator->Transform (aCmd.ArgInt ("transform", 0), aCmd.ArgInt ("transform", 1), ViewerTest::CurrentView()); } if (aCmd.HasOption ("stopTransform")) { Standard_Boolean toApply = !aCmd.HasOption ("stopTransform", 1) || (aCmd.Arg ("stopTransform", 0) != "abort"); aManipulator->StopTransform (toApply); } gp_Trsf aT; if (aCmd.HasOption ("move", 3, Standard_True)) { aT.SetTranslationPart (aCmd.ArgVec ("move")); } if (aCmd.HasOption ("rotate", 7, Standard_True)) { aT.SetRotation (gp_Ax1 (aCmd.ArgPnt ("rotate", 0), aCmd.ArgVec ("rotate", 3)), aCmd.ArgDouble ("rotate", 6)); } if (aCmd.HasOption ("scale", 1)) { aT.SetScale (gp_Pnt(), aCmd.ArgDouble("scale")); } if (aT.Form() != gp_Identity) { aManipulator->Transform (aT); } ViewerTest::GetAISContext()->Redisplay (aManipulator, Standard_True); return 0; } //=============================================================================================== //function : VSelectionProperties //purpose : //=============================================================================================== static int VSelectionProperties (Draw_Interpretor& theDi, Standard_Integer theArgsNb, const char** theArgVec) { const Handle(AIS_InteractiveContext)& aCtx = ViewerTest::GetAISContext(); if (aCtx.IsNull()) { std::cerr << "No active viewer!\n"; return 1; } Standard_Boolean toPrint = theArgsNb == 1; Standard_Boolean toRedraw = Standard_False; Standard_Integer anArgIter = 1; Prs3d_TypeOfHighlight aType = Prs3d_TypeOfHighlight_None; if (anArgIter < theArgsNb) { TCollection_AsciiString anArgFirst (theArgVec[anArgIter]); anArgFirst.LowerCase(); ++anArgIter; if (anArgFirst == "dynhighlight" || anArgFirst == "dynhilight" || anArgFirst == "dynamichighlight" || anArgFirst == "dynamichilight") { aType = Prs3d_TypeOfHighlight_Dynamic; } else if (anArgFirst == "localdynhighlight" || anArgFirst == "localdynhilight" || anArgFirst == "localdynamichighlight" || anArgFirst == "localdynamichilight") { aType = Prs3d_TypeOfHighlight_LocalDynamic; } else if (anArgFirst == "selhighlight" || anArgFirst == "selhilight" || anArgFirst == "selectedhighlight" || anArgFirst == "selectedhilight") { aType = Prs3d_TypeOfHighlight_Selected; } else if (anArgFirst == "localselhighlight" || anArgFirst == "localselhilight" || anArgFirst == "localselectedhighlight" || anArgFirst == "localselectedhilight") { aType = Prs3d_TypeOfHighlight_LocalSelected; } else { --anArgIter; } } for (; anArgIter < theArgsNb; ++anArgIter) { TCollection_AsciiString anArg (theArgVec[anArgIter]); anArg.LowerCase(); if (anArg == "-help") { theDi.PrintHelp (theArgVec[0]); return 0; } else if (anArg == "-print") { toPrint = Standard_True; } else if (anArg == "-autoactivate") { Standard_Boolean toEnable = Standard_True; if (anArgIter + 1 < theArgsNb && ViewerTest::ParseOnOff (theArgVec[anArgIter + 1], toEnable)) { ++anArgIter; } aCtx->SetAutoActivateSelection (toEnable); } else if (anArg == "-pickstrategy" || anArg == "-pickingstrategy") { if (++anArgIter >= theArgsNb) { std::cout << "Syntax error: type of highlighting is undefined\n"; return 1; } SelectMgr_PickingStrategy aStrategy = SelectMgr_PickingStrategy_FirstAcceptable; TCollection_AsciiString aVal (theArgVec[anArgIter]); aVal.LowerCase(); if (aVal == "first" || aVal == "firstaccepted" || aVal == "firstacceptable") { aStrategy = SelectMgr_PickingStrategy_FirstAcceptable; } else if (aVal == "topmost" || aVal == "onlyTopmost") { aStrategy = SelectMgr_PickingStrategy_OnlyTopmost; } else { std::cout << "Syntax error: unknwon picking strategy '" << aVal << "'\n"; return 1; } aCtx->SetPickingStrategy (aStrategy); } else if (anArg == "-pixtol" && anArgIter + 1 < theArgsNb) { aCtx->SetPixelTolerance (Draw::Atoi (theArgVec[++anArgIter])); } else if ((anArg == "-mode" || anArg == "-dispmode") && anArgIter + 1 < theArgsNb) { if (aType == Prs3d_TypeOfHighlight_None) { std::cout << "Syntax error: type of highlighting is undefined\n"; return 1; } const Standard_Integer aDispMode = Draw::Atoi (theArgVec[++anArgIter]); const Handle(Prs3d_Drawer)& aStyle = aCtx->HighlightStyle (aType); aStyle->SetDisplayMode (aDispMode); toRedraw = Standard_True; } else if (anArg == "-layer" && anArgIter + 1 < theArgsNb) { if (aType == Prs3d_TypeOfHighlight_None) { std::cout << "Syntax error: type of highlighting is undefined\n"; return 1; } const Standard_Integer aNewLayer = Draw::Atoi (theArgVec[++anArgIter]); if (aNewLayer != Graphic3d_ZLayerId_UNKNOWN) { TColStd_SequenceOfInteger aLayers; aCtx->CurrentViewer()->GetAllZLayers (aLayers); if (std::find (aLayers.begin(), aLayers.end(), aNewLayer) == aLayers.end()) { std::cout << "Syntax error: Layer " << aNewLayer << " is undefined\n"; return 1; } } const Handle(Prs3d_Drawer)& aStyle = aCtx->HighlightStyle (aType); aStyle->SetZLayer (aNewLayer); toRedraw = Standard_True; } else if (anArg == "-hicolor" || anArg == "-selcolor" || anArg == "-color") { if (anArg.StartsWith ("-hi")) { aType = Prs3d_TypeOfHighlight_Dynamic; } else if (anArg.StartsWith ("-sel")) { aType = Prs3d_TypeOfHighlight_Selected; } else if (aType == Prs3d_TypeOfHighlight_None) { std::cout << "Syntax error: type of highlighting is undefined\n"; return 1; } Quantity_Color aColor; Standard_Integer aNbParsed = ViewerTest::ParseColor (theArgsNb - anArgIter - 1, theArgVec + anArgIter + 1, aColor); if (aNbParsed == 0) { std::cout << "Syntax error: need more arguments.\n"; return 1; } anArgIter += aNbParsed; const Handle(Prs3d_Drawer)& aStyle = aCtx->HighlightStyle (aType); aStyle->SetColor (aColor); toRedraw = Standard_True; } else if ((anArg == "-transp" || anArg == "-transparency" || anArg == "-hitransp" || anArg == "-seltransp" || anArg == "-hitransplocal" || anArg == "-seltransplocal") && anArgIter + 1 < theArgsNb) { if (anArg.StartsWith ("-hi")) { aType = Prs3d_TypeOfHighlight_Dynamic; } else if (anArg.StartsWith ("-sel")) { aType = Prs3d_TypeOfHighlight_Selected; } else if (aType == Prs3d_TypeOfHighlight_None) { std::cout << "Syntax error: type of highlighting is undefined\n"; return 1; } const Standard_Real aTransp = Draw::Atof (theArgVec[++anArgIter]); const Handle(Prs3d_Drawer)& aStyle = aCtx->HighlightStyle (aType); aStyle->SetTransparency ((Standard_ShortReal )aTransp); toRedraw = Standard_True; } else if ((anArg == "-mat" || anArg == "-material") && anArgIter + 1 < theArgsNb) { if (aType == Prs3d_TypeOfHighlight_None) { std::cout << "Syntax error: type of highlighting is undefined\n"; return 1; } const Handle(Prs3d_Drawer)& aStyle = aCtx->HighlightStyle (aType); Graphic3d_NameOfMaterial aMatName = Graphic3d_MaterialAspect::MaterialFromName (theArgVec[anArgIter + 1]); if (aMatName != Graphic3d_NOM_DEFAULT) { ++anArgIter; Handle(Graphic3d_AspectFillArea3d) anAspect = new Graphic3d_AspectFillArea3d(); *anAspect = *aCtx->DefaultDrawer()->ShadingAspect()->Aspect(); Graphic3d_MaterialAspect aMat (aMatName); aMat.SetColor (aStyle->Color()); aMat.SetTransparency (aStyle->Transparency()); anAspect->SetFrontMaterial (aMat); anAspect->SetInteriorColor (aStyle->Color()); aStyle->SetBasicFillAreaAspect (anAspect); } else { aStyle->SetBasicFillAreaAspect (Handle(Graphic3d_AspectFillArea3d)()); } toRedraw = Standard_True; } else { std::cout << "Syntax error at '" << theArgVec[anArgIter] << "'\n"; } } if (toPrint) { const Handle(Prs3d_Drawer)& aHiStyle = aCtx->HighlightStyle(); const Handle(Prs3d_Drawer)& aSelStyle = aCtx->SelectionStyle(); theDi << "Auto-activation : " << (aCtx->GetAutoActivateSelection() ? "On" : "Off") << "\n"; theDi << "Selection pixel tolerance : " << aCtx->MainSelector()->PixelTolerance() << "\n"; theDi << "Selection color : " << Quantity_Color::StringName (aSelStyle->Color().Name()) << "\n"; theDi << "Dynamic highlight color : " << Quantity_Color::StringName (aHiStyle->Color().Name()) << "\n"; theDi << "Selection transparency : " << aSelStyle->Transparency() << "\n"; theDi << "Dynamic highlight transparency : " << aHiStyle->Transparency() << "\n"; theDi << "Selection mode : " << aSelStyle->DisplayMode() << "\n"; theDi << "Dynamic highlight mode : " << aHiStyle->DisplayMode() << "\n"; theDi << "Selection layer : " << aSelStyle->ZLayer() << "\n"; theDi << "Dynamic layer : " << aHiStyle->ZLayer() << "\n"; } if (aCtx->NbSelected() != 0 && toRedraw) { aCtx->HilightSelected (Standard_True); } return 0; } //=============================================================================================== //function : VDumpSelectionImage //purpose : //=============================================================================================== static int VDumpSelectionImage (Draw_Interpretor& /*theDi*/, Standard_Integer theArgsNb, const char** theArgVec) { if (theArgsNb < 2) { std::cout << "Syntax error: wrong number arguments for '" << theArgVec[0] << "'\n"; return 1; } const Handle(AIS_InteractiveContext)& aContext = ViewerTest::GetAISContext(); if (aContext.IsNull()) { std::cout << "Error: no active view.\n"; return 1; } TCollection_AsciiString aFile; StdSelect_TypeOfSelectionImage aType = StdSelect_TypeOfSelectionImage_NormalizedDepth; Image_Format anImgFormat = Image_Format_BGR; Standard_Integer aPickedIndex = 1; for (Standard_Integer anArgIter = 1; anArgIter < theArgsNb; ++anArgIter) { TCollection_AsciiString aParam (theArgVec[anArgIter]); aParam.LowerCase(); if (aParam == "-type") { if (++anArgIter >= theArgsNb) { std::cout << "Syntax error: wrong number parameters of flag '-depth'.\n"; return 1; } TCollection_AsciiString aValue (theArgVec[anArgIter]); aValue.LowerCase(); if (aValue == "depth" || aValue == "normdepth" || aValue == "normalizeddepth") { aType = StdSelect_TypeOfSelectionImage_NormalizedDepth; anImgFormat = Image_Format_GrayF; } if (aValue == "depthinverted" || aValue == "normdepthinverted" || aValue == "normalizeddepthinverted" || aValue == "inverted") { aType = StdSelect_TypeOfSelectionImage_NormalizedDepthInverted; anImgFormat = Image_Format_GrayF; } else if (aValue == "unnormdepth" || aValue == "unnormalizeddepth") { aType = StdSelect_TypeOfSelectionImage_UnnormalizedDepth; anImgFormat = Image_Format_GrayF; } else if (aValue == "objectcolor" || aValue == "object" || aValue == "color") { aType = StdSelect_TypeOfSelectionImage_ColoredDetectedObject; } else if (aValue == "entitycolor" || aValue == "entity") { aType = StdSelect_TypeOfSelectionImage_ColoredEntity; } else if (aValue == "ownercolor" || aValue == "owner") { aType = StdSelect_TypeOfSelectionImage_ColoredOwner; } else if (aValue == "selectionmodecolor" || aValue == "selectionmode" || aValue == "selmodecolor" || aValue == "selmode") { aType = StdSelect_TypeOfSelectionImage_ColoredSelectionMode; } } else if (aParam == "-picked" || aParam == "-pickeddepth" || aParam == "-pickedindex") { if (++anArgIter >= theArgsNb) { std::cout << "Syntax error: wrong number parameters at '" << aParam << "'.\n"; return 1; } aPickedIndex = Draw::Atoi (theArgVec[anArgIter]); } else if (aFile.IsEmpty()) { aFile = theArgVec[anArgIter]; } else { std::cout << "Syntax error: unknown argument '" << theArgVec[anArgIter] << "'.\n"; return 1; } } if (aFile.IsEmpty()) { std::cout << "Syntax error: image file name is missing.\n"; return 1; } const Handle(V3d_View)& aView = ViewerTest::CurrentView(); Standard_Integer aWidth = 0, aHeight = 0; aView->Window()->Size (aWidth, aHeight); Image_AlienPixMap aPixMap; if (!aPixMap.InitZero (anImgFormat, aWidth, aHeight)) { std::cout << "Error: can't allocate image.\n"; return 1; } if (!aContext->MainSelector()->ToPixMap (aPixMap, aView, aType, aPickedIndex)) { std::cout << "Error: can't generate selection image.\n"; return 1; } if (!aPixMap.Save (aFile)) { std::cout << "Error: can't save selection image.\n"; return 0; } return 0; } //======================================================================= //function : ViewerCommands //purpose : //======================================================================= void ViewerTest::ViewerCommands(Draw_Interpretor& theCommands) { const char *group = "ZeViewer"; theCommands.Add("vinit", "vinit [-name viewName] [-left leftPx] [-top topPx] [-width widthPx] [-height heightPx]" "\n\t\t: [-exitOnClose] [-closeOnEscape] [-cloneActive] [-2d_mode {on|off}=off]" #if !defined(_WIN32) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) "\n\t\t: [-display displayName]" #endif "\n\t\t: Creates new View window with specified name viewName." "\n\t\t: By default the new view is created in the viewer and in" "\n\t\t: graphic driver shared with active view." "\n\t\t: -name {driverName/viewerName/viewName | viewerName/viewName | viewName}" "\n\t\t: If driverName isn't specified the driver will be shared with active view." "\n\t\t: If viewerName isn't specified the viewer will be shared with active view." #if !defined(_WIN32) && (!defined(__APPLE__) || defined(MACOSX_USE_GLX)) "\n\t\t: -display HostName.DisplayNumber[:ScreenNumber]" "\n\t\t: Display name will be used within creation of graphic driver, when specified." #endif "\n\t\t: -left, -top pixel position of left top corner of the window." "\n\t\t: -width, -height width and heigth of window respectively." "\n\t\t: -cloneActive floag to copy camera and dimensions of active view." "\n\t\t: -exitOnClose when specified, closing the view will exit application." "\n\t\t: -closeOnEscape when specified, view will be closed on pressing Escape." "\n\t\t: -2d_mode when on, view will not react on rotate scene events" "\n\t\t: Additional commands for operations with views: vclose, vactivate, vviewlist.", __FILE__,VInit,group); theCommands.Add("vclose" , "[view_id [keep_context=0|1]]\n" "or vclose ALL - to remove all created views\n" " - removes view(viewer window) defined by its view_id.\n" " - keep_context: by default 0; if 1 and the last view is deleted" " the current context is not removed.", __FILE__,VClose,group); theCommands.Add("vactivate" , "view_id" " - activates view(viewer window) defined by its view_id", __FILE__,VActivate,group); theCommands.Add("vviewlist", "vviewlist [format={tree, long}]" " - prints current list of views per viewer and graphic_driver ID shared between viewers" " - format: format of result output, if tree the output is a tree view;" "otherwise it's a list of full view names. By default format = tree", __FILE__,VViewList,group); theCommands.Add("vhelp" , "vhelp : display help on the viewer commands", __FILE__,VHelp,group); theCommands.Add("vtop" , "vtop or : Top view. Orientation +X+Y" , __FILE__,VTop,group); theCommands.Add("vbottom" , "vbottom : Bottom view. Orientation +X-Y" , __FILE__,VBottom,group); theCommands.Add("vleft" , "vleft : Left view. Orientation -Y+Z" , __FILE__,VLeft,group); theCommands.Add("vright" , "vright : Right view. Orientation +Y+Z" , __FILE__,VRight,group); theCommands.Add("vaxo" , " vaxo or : Axonometric view. Orientation +X-Y+Z", __FILE__,VAxo,group); theCommands.Add("vfront" , "vfront : Front view. Orientation +X+Z" , __FILE__,VFront,group); theCommands.Add("vback" , "vback : Back view. Orientation -X+Z" , __FILE__,VBack,group); theCommands.Add("vpick" , "vpick : vpick X Y Z [shape subshape] ( all variables as string )", VPick,group); theCommands.Add("vfit", "vfit or [-selected] [-noupdate]" "\n\t\t: [-selected] fits the scene according to bounding box of currently selected objects", __FILE__,VFit,group); theCommands.Add ("vfitarea", "vfitarea x1 y1 x2 y2" "\n\t\t: vfitarea x1 y1 z1 x2 y2 z2" "\n\t\t: Fit view to show area located between two points" "\n\t\t: given in world 2D or 3D corrdinates.", __FILE__, VFitArea, group); theCommands.Add ("vzfit", "vzfit [scale]\n" " Matches Z near, Z far view volume planes to the displayed objects.\n" " \"scale\" - specifies factor to scale computed z range.\n", __FILE__, VZFit, group); theCommands.Add("vrepaint", "vrepaint [-immediate]" "\n\t\t: force redraw", __FILE__,VRepaint,group); theCommands.Add("vclear", "vclear : vclear" "\n\t\t: remove all the object from the viewer", __FILE__,VClear,group); theCommands.Add("vsetbg", "vsetbg : vsetbg imagefile [filltype] : Load image as background", __FILE__,VSetBg,group); theCommands.Add("vsetbgmode", "vsetbgmode : vsetbgmode filltype : Change background image fill type", __FILE__,VSetBgMode,group); theCommands.Add("vsetgradientbg", "vsetgradientbg : vsetgradientbg r1 g1 b1 r2 g2 b2 filltype : Mount gradient background", __FILE__,VSetGradientBg,group); theCommands.Add("vsetgrbgmode", "vsetgrbgmode : vsetgrbgmode filltype : Change gradient background fill type", __FILE__,VSetGradientBgMode,group); theCommands.Add("vsetcolorbg", "vsetcolorbg : vsetcolorbg r g b : Set background color", __FILE__,VSetColorBg,group); theCommands.Add("vsetdefaultbg", "vsetdefaultbg r g b\n" "\n\t\t: vsetdefaultbg r1 g1 b1 r2 g2 b2 fillmode" "\n\t\t: Set default viewer background fill color (flat/gradient).", __FILE__,VSetDefaultBg,group); theCommands.Add("vscale", "vscale : vscale X Y Z", __FILE__,VScale,group); theCommands.Add("vzbufftrihedron", "vzbufftrihedron [{-on|-off}=-on] [-type {wireframe|zbuffer}=zbuffer]" "\n\t\t: [-position center|left_lower|left_upper|right_lower|right_upper]" "\n\t\t: [-scale value=0.1] [-size value=0.8] [-arrowDiam value=0.05]" "\n\t\t: [-colorArrowX color=RED] [-colorArrowY color=GREEN] [-colorArrowZ color=BLUE]" "\n\t\t: [-nbfacets value=12] [-colorLabels color=WHITE]" "\n\t\t: Displays a trihedron", __FILE__,VZBuffTrihedron,group); theCommands.Add("vrotate", "vrotate [[-mouseStart X Y] [-mouseMove X Y]]|[AX AY AZ [X Y Z]]" "\n : Option -mouseStart starts rotation according to the mouse position" "\n : Option -mouseMove continues rotation with angle computed" "\n : from last and new mouse position." "\n : vrotate AX AY AZ [X Y Z]", __FILE__,VRotate,group); theCommands.Add("vzoom", "vzoom : vzoom coef", __FILE__,VZoom,group); theCommands.Add("vpan", "vpan : vpan dx dy", __FILE__,VPan,group); theCommands.Add("vcolorscale", "vcolorscale name [-noupdate|-update] [-demo]" "\n\t\t: [-range RangeMin=0 RangeMax=1 NbIntervals=10]" "\n\t\t: [-font HeightFont=20]" "\n\t\t: [-logarithmic {on|off}=off] [-reversed {on|off}=off]" "\n\t\t: [-smoothTransition {on|off}=off]" "\n\t\t: [-hueRange MinAngle=230 MaxAngle=0]" "\n\t\t: [-colorRange MinColor=BLUE1 MaxColor=RED]" "\n\t\t: [-textpos {left|right|center|none}=right]" "\n\t\t: [-labelAtBorder {on|off}=on]" "\n\t\t: [-colors Color1 Color2 ...] [-color Index Color]" "\n\t\t: [-labels Label1 Label2 ...] [-label Index Label]" "\n\t\t: [-freeLabels NbOfLabels Label1 Label2 ...]" "\n\t\t: [-xy Left=0 Bottom=0]" "\n\t\t: -demo - displays a color scale with demonstratio values" "\n\t\t: -colors - set colors for all intervals" "\n\t\t: -color - set color for specific interval" "\n\t\t: -textpos - horizontal label position relative to color scale bar" "\n\t\t: -labelAtBorder - vertical label position relative to color interval;" "\n\t\t: at border means the value inbetween neighbor intervals," "\n\t\t: at center means the center value within current interval" "\n\t\t: -labels - set labels for all intervals" "\n\t\t: -freeLabels - same as -labels but does not require" "\n\t\t: matching the number of intervals" "\n\t\t: -label - set label for specific interval" "\n\t\t: -title - set title" "\n\t\t: -reversed - setup smooth color transition between intervals" "\n\t\t: -smoothTransition - swap colorscale direction" "\n\t\t: -hueRange - set hue angles corresponding to minimum and maximum values" __FILE__, VColorScale, group); theCommands.Add("vgraduatedtrihedron", "vgraduatedtrihedron : -on/-off [-xname Name] [-yname Name] [-zname Name] [-arrowlength Value]\n" "\t[-namefont Name] [-valuesfont Name]\n" "\t[-xdrawname on/off] [-ydrawname on/off] [-zdrawname on/off]\n" "\t[-xnameoffset IntVal] [-ynameoffset IntVal] [-znameoffset IntVal]" "\t[-xnamecolor Color] [-ynamecolor Color] [-znamecolor Color]\n" "\t[-xdrawvalues on/off] [-ydrawvalues on/off] [-zdrawvalues on/off]\n" "\t[-xvaluesoffset IntVal] [-yvaluesoffset IntVal] [-zvaluesoffset IntVal]" "\t[-xcolor Color] [-ycolor Color] [-zcolor Color]\n" "\t[-xdrawticks on/off] [-ydrawticks on/off] [-zdrawticks on/off]\n" "\t[-xticks Number] [-yticks Number] [-zticks Number]\n" "\t[-xticklength IntVal] [-yticklength IntVal] [-zticklength IntVal]\n" "\t[-drawgrid on/off] [-drawaxes on/off]\n" " - Displays or erases graduated trihedron" " - xname, yname, zname - names of axes, default: X, Y, Z\n" " - namefont - font of axes names. Default: Arial\n" " - xnameoffset, ynameoffset, znameoffset - offset of name from values or tickmarks or axis. Default: 30\n" " - xnamecolor, ynamecolor, znamecolor - colors of axes names\n" " - xvaluesoffset, yvaluesoffset, zvaluesoffset - offset of values from tickmarks or axis. Default: 10\n" " - valuesfont - font of axes values. Default: Arial\n" " - xcolor, ycolor, zcolor - color of axis and values\n" " - xticks, yticks, xzicks - number of tickmark on axes. Default: 5\n" " - xticklength, yticklength, xzicklength - length of tickmark on axes. Default: 10\n", __FILE__,VGraduatedTrihedron,group); theCommands.Add("vtile" , "vtile [-totalSize W H] [-lowerLeft X Y] [-upperLeft X Y] [-tileSize W H]" "\n\t\t: Setup view to draw a tile (a part of virtual bigger viewport)." "\n\t\t: -totalSize the size of virtual bigger viewport" "\n\t\t: -tileSize tile size (the view size will be used if omitted)" "\n\t\t: -lowerLeft tile offset as lower left corner" "\n\t\t: -upperLeft tile offset as upper left corner", __FILE__, VTile, group); theCommands.Add("vzlayer", "vzlayer [layerId]" "\n\t\t: [-add|-delete|-get|-settings]" "\n\t\t: [-origin X Y Z] [-cullDist Distance] [-cullSize Size]" "\n\t\t: [-enable|-disable {depthTest|depthWrite|depthClear|depthoffset}]" "\n\t\t: [-enable|-disable {positiveOffset|negativeOffset|textureenv}]" "\n\t\t: ZLayer list management:" "\n\t\t: -add add new z layer to viewer and print its id" "\n\t\t: -delete delete z layer" "\n\t\t: -get print sequence of z layers" "\n\t\t: -settings print status of z layer settings" "\n\t\t: -disable disables given setting" "\n\t\t: -enable enables given setting", __FILE__,VZLayer,group); theCommands.Add("vlayerline", "vlayerline : vlayerline x1 y1 x2 y2 [linewidth=0.5] [linetype=0] [transparency=1.0]", __FILE__,VLayerLine,group); theCommands.Add ("vgrid", "vgrid [off] [Mode={r|c}] [Type={l|p}] [OriginX OriginY [StepX/StepRadius StepY/DivNb RotAngle]]" " : Mode - rectangular or circular" " : Type - lines or points", __FILE__, VGrid, group); theCommands.Add ("vpriviledgedplane", "vpriviledgedplane [Ox Oy Oz Nx Ny Nz [Xx Xy Xz]]" "\n\t\t: Ox, Oy, Oz - plane origin" "\n\t\t: Nx, Ny, Nz - plane normal direction" "\n\t\t: Xx, Xy, Xz - plane x-reference axis direction" "\n\t\t: Sets or prints viewer's priviledged plane geometry.", __FILE__, VPriviledgedPlane, group); theCommands.Add ("vconvert", "vconvert v [Mode={window|view}]" "\n\t\t: vconvert x y [Mode={window|view|grid|ray}]" "\n\t\t: vconvert x y z [Mode={window|grid}]" "\n\t\t: window - convert to window coordinates, pixels" "\n\t\t: view - convert to view projection plane" "\n\t\t: grid - convert to model coordinates, given on grid" "\n\t\t: ray - convert projection ray to model coordiantes" "\n\t\t: - vconvert v window : convert view to window;" "\n\t\t: - vconvert v view : convert window to view;" "\n\t\t: - vconvert x y window : convert view to window;" "\n\t\t: - vconvert x y view : convert window to view;" "\n\t\t: - vconvert x y : convert window to model;" "\n\t\t: - vconvert x y grid : convert window to model using grid;" "\n\t\t: - vconvert x y ray : convert window projection line to model;" "\n\t\t: - vconvert x y z window : convert model to window;" "\n\t\t: - vconvert x y z grid : convert view to model using grid;" "\n\t\t: Converts the given coordinates to window/view/model space.", __FILE__, VConvert, group); theCommands.Add ("vfps", "vfps [framesNb=100] : estimate average frame rate for active view", __FILE__, VFps, group); theCommands.Add ("vgldebug", "vgldebug [-sync {0|1}] [-debug {0|1}] [-glslWarn {0|1}]" "\n\t\t: [-extraMsg {0|1}] [{0|1}]" "\n\t\t: Request debug GL context. Should be called BEFORE vinit." "\n\t\t: Debug context can be requested only on Windows" "\n\t\t: with GL_ARB_debug_output extension implemented by GL driver!" "\n\t\t: -sync - request synchronized debug GL context" "\n\t\t: -glslWarn - log GLSL compiler/linker warnings," "\n\t\t: which are suppressed by default," "\n\t\t: -extraMsg - log extra diagnostic messages from GL context," "\n\t\t: which are suppressed by default", __FILE__, VGlDebug, group); theCommands.Add ("vvbo", "vvbo [{0|1}] : turn VBO usage On/Off; affects only newly displayed objects", __FILE__, VVbo, group); theCommands.Add ("vstereo", "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: [-compatibleProfile {0|1}]" "\n\t\t: [-vsync {0|1}] [-useWinBuffer {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" "\n\t\t: built-in GLSL programs" "\n\t\t: (requires compatible profile)" "\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: winBuffer - allow using window buffer for rendering" "\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." "\n\t\t: Command is intended for testing old hardware compatibility.", __FILE__, VCaps, group); theCommands.Add ("vmemgpu", "vmemgpu [f]: print system-dependent GPU memory information if available;" " with f option returns free memory in bytes", __FILE__, VMemGpu, group); theCommands.Add ("vreadpixel", "vreadpixel xPixel yPixel [{rgb|rgba|depth|hls|rgbf|rgbaf}=rgba] [name]" " : Read pixel value for active view", __FILE__, VReadPixel, group); theCommands.Add("diffimage", "diffimage imageFile1 imageFile2 [diffImageFile]" "\n\t\t: [-toleranceOfColor {0..1}=0] [-blackWhite {on|off}=off] [-borderFilter {on|off}=off]" "\n\t\t: [-display viewName prsName1 prsName2 prsNameDiff] [-exitOnClose] [-closeOnEscape]" "\n\t\t: Compare two images by content and generate difference image." "\n\t\t: When -exitOnClose is specified, closing the view will exit application." "\n\t\t: When -closeOnEscape is specified, view will be closed on pressing Escape.", __FILE__, VDiffImage, group); theCommands.Add ("vselect", "vselect x1 y1 [x2 y2 [x3 y3 ... xn yn]] [-allowoverlap 0|1] [shift_selection = 0|1]\n" "- emulates different types of selection:\n" "- 1) single click selection\n" "- 2) selection with rectangle having corners at pixel positions (x1,y1) and (x2,y2)\n" "- 3) selection with polygon having corners in pixel positions (x1,y1), (x2,y2),...,(xn,yn)\n" "- 4) -allowoverlap manages overlap and inclusion detection in rectangular selection.\n" " If the flag is set to 1, both sensitives that were included completely and overlapped partially by defined rectangle will be detected,\n" " otherwise algorithm will chose only fully included sensitives. Default behavior is to detect only full inclusion. " " (partial inclusion - overlap - is not allowed by default)\n" "- 5) any of these selections with shift button pressed", __FILE__, VSelect, group); theCommands.Add ("vmoveto", "vmoveto [x y] [-reset]" "\n\t\t: Emulates cursor movement to pixel position (x,y)." "\n\t\t: -reset resets current highlighting", __FILE__, VMoveTo, group); theCommands.Add ("vviewparams", "vviewparams [-args] [-scale [s]]" "\n\t\t: [-eye [x y z]] [-at [x y z]] [-up [x y z]]" "\n\t\t: [-proj [x y z]] [-center x y] [-size sx]" "\n\t\t: Manage current view parameters or prints all" "\n\t\t: current values when called without argument." "\n\t\t: -scale [s] prints or sets viewport relative scale" "\n\t\t: -eye [x y z] prints or sets eye location" "\n\t\t: -at [x y z] prints or sets center of look" "\n\t\t: -up [x y z] prints or sets direction of up vector" "\n\t\t: -proj [x y z] prints or sets direction of look" "\n\t\t: -center x y sets location of center of the screen in pixels" "\n\t\t: -size [sx] prints viewport projection width and height sizes" "\n\t\t: or changes the size of its maximum dimension" "\n\t\t: -args prints vviewparams arguments for restoring current view", __FILE__, VViewParams, group); theCommands.Add("v2dmode", "v2dmode [-name viewName] [-mode {-on|-off}=-on]" "\n\t\t: name - name of existing view, if not defined, the active view is changed" "\n\t\t: mode - switches On/Off rotation mode" "\n\t\t: Set 2D mode of the active viewer manipulating. The following mouse and key actions are disabled:" "\n\t\t: - rotation of the view by 3rd mouse button with Ctrl active" "\n\t\t: - set view projection using key buttons: A/D/T/B/L/R for AXO, Reset, Top, Bottom, Left, Right" "\n\t\t: View camera position might be changed only by commands.", __FILE__, V2DMode, group); theCommands.Add("vanimation", "Alias for vanim", __FILE__, VAnimation, group); theCommands.Add("vanim", "List existing animations:" "\n\t\t: vanim" "\n\t\t: Animation playback:" "\n\t\t: vanim name -play|-resume [playFrom [playDuration]]" "\n\t\t: [-speed Coeff] [-freeLook] [-lockLoop]" "\n\t\t: -speed playback speed (1.0 is normal speed)" "\n\t\t: -freeLook skip camera animations" "\n\t\t: -lockLoop disable any interactions" "\n\t\t:" "\n\t\t: Animation definition:" "\n\t\t: vanim Name/sub/name [-clear] [-delete]" "\n\t\t: [start TimeSec] [duration TimeSec]" "\n\t\t:" "\n\t\t: Animation name defined in path-style (anim/name or anim.name)" "\n\t\t: specifies nested animations." "\n\t\t: There is no syntax to explicitly add new animation," "\n\t\t: and all non-existing animations within the name will be" "\n\t\t: implicitly created on first use (including parents)." "\n\t\t:" "\n\t\t: Each animation might define the SINGLE action (see below)," "\n\t\t: like camera transition, object transformation or custom callback." "\n\t\t: Child animations can be used for defining concurrent actions." "\n\t\t:" "\n\t\t: Camera animation:" "\n\t\t: vanim name -view [-eye1 X Y Z] [-eye2 X Y Z]" "\n\t\t: [-at1 X Y Z] [-at2 X Y Z]" "\n\t\t: [-up1 X Y Z] [-up2 X Y Z]" "\n\t\t: [-scale1 Scale] [-scale2 Scale]" "\n\t\t: -eyeX camera Eye positions pair (start and end)" "\n\t\t: -atX camera Center positions pair" "\n\t\t: -upX camera Up directions pair" "\n\t\t: -scaleX camera Scale factors pair" "\n\t\t: Object animation:" "\n\t\t: vanim name -object [-loc1 X Y Z] [-loc2 X Y Z]" "\n\t\t: [-rot1 QX QY QZ QW] [-rot2 QX QY QZ QW]" "\n\t\t: [-scale1 Scale] [-scale2 Scale]" "\n\t\t: -locX object Location points pair (translation)" "\n\t\t: -rotX object Orientations pair (quaternions)" "\n\t\t: -scaleX object Scale factors pair (quaternions)" "\n\t\t: Custom callback:" "\n\t\t: vanim name -invoke \"Command Arg1 Arg2 %Pts %LocalPts %Normalized ArgN\"" "\n\t\t: %Pts overall animation presentation timestamp" "\n\t\t: %LocalPts local animation timestamp" "\n\t\t: %Normalized local animation normalized value in range 0..1" "\n\t\t:" "\n\t\t: Video recording:" "\n\t\t: vanim name -record FileName [Width Height] [-fps FrameRate=24]" "\n\t\t: [-format Format] [-vcodec Codec] [-pix_fmt PixelFormat]" "\n\t\t: [-crf Value] [-preset Preset]" "\n\t\t: -fps video framerate" "\n\t\t: -format file format, container (matroska, etc.)" "\n\t\t: -vcodec video codec identifier (ffv1, mjpeg, etc.)" "\n\t\t: -pix_fmt image pixel format (yuv420p, rgb24, etc.)" "\n\t\t: -crf constant rate factor (specific to codec)" "\n\t\t: -preset codec parameters preset (specific to codec)" __FILE__, VAnimation, group); theCommands.Add("vchangeselected", "vchangeselected shape" "- adds to shape to selection or remove one from it", __FILE__, VChangeSelected, group); theCommands.Add ("vnbselected", "vnbselected" "\n\t\t: Returns number of selected objects", __FILE__, VNbSelected, group); theCommands.Add ("vcamera", "vcamera [-ortho] [-projtype]" "\n\t\t: [-persp]" "\n\t\t: [-fovy [Angle]] [-distance [Distance]]" "\n\t\t: [-stereo] [-leftEye] [-rightEye]" "\n\t\t: [-iod [Distance]] [-iodType [absolute|relative]]" "\n\t\t: [-zfocus [Value]] [-zfocusType [absolute|relative]]" "\n\t\t: Manage camera parameters." "\n\t\t: Prints current value when option called without argument." "\n\t\t: Orthographic camera:" "\n\t\t: -ortho activate orthographic projection" "\n\t\t: Perspective camera:" "\n\t\t: -persp activate perspective projection (mono)" "\n\t\t: -fovy field of view in y axis, in degrees" "\n\t\t: -distance distance of eye from camera center" "\n\t\t: Stereoscopic camera:" "\n\t\t: -stereo perspective projection (stereo)" "\n\t\t: -leftEye perspective projection (left eye)" "\n\t\t: -rightEye perspective projection (right eye)" "\n\t\t: -iod intraocular distance value" "\n\t\t: -iodType distance type, absolute or relative" "\n\t\t: -zfocus stereographic focus value" "\n\t\t: -zfocusType focus type, absolute or relative", __FILE__, VCamera, group); theCommands.Add ("vautozfit", "command to enable or disable automatic z-range adjusting\n" "- vautozfit [on={1|0}] [scale]\n" " Prints or changes parameters of automatic z-fit mode:\n" " \"on\" - turns automatic z-fit on or off\n" " \"scale\" - specifies factor to scale computed z range.\n", __FILE__, VAutoZFit, group); theCommands.Add ("vzrange", "command to manually access znear and zfar values\n" " vzrange - without parameters shows current values\n" " vzrange [znear] [zfar] - applies provided values to view", __FILE__,VZRange, group); theCommands.Add ("vpurgedisplay", "vpurgedisplay" "- removes structures which don't belong to objects displayed in neutral point", __FILE__, VPurgeDisplay, group); theCommands.Add("vsetviewsize", "vsetviewsize size", __FILE__,VSetViewSize,group); theCommands.Add("vmoveview", "vmoveview Dx Dy Dz [Start = 1|0]", __FILE__,VMoveView,group); theCommands.Add("vtranslateview", "vtranslateview Dx Dy Dz [Start = 1|0)]", __FILE__,VTranslateView,group); theCommands.Add("vturnview", "vturnview Ax Ay Az [Start = 1|0]", __FILE__,VTurnView,group); theCommands.Add("vtextureenv", "Enables or disables environment mapping in the 3D view, loading the texture from the given standard " "or user-defined file and optionally applying texture mapping parameters\n" " Usage:\n" " vtextureenv off - disables environment mapping\n" " vtextureenv on {std_texture|texture_file_name} [rep mod flt ss st ts tt rot] - enables environment mapping\n" " std_texture = (0..7)\n" " rep = {clamp|repeat}\n" " mod = {decal|modulate}\n" " flt = {nearest|bilinear|trilinear}\n" " ss, st - scale factors for s and t texture coordinates\n" " ts, tt - translation for s and t texture coordinates\n" " rot - texture rotation angle in degrees", __FILE__, VTextureEnv, group); theCommands.Add("vhlr", "vhlr {on|off} [-showHidden={1|0}] [-algoType={algo|polyAlgo}] [-noupdate]" "\n\t\t: Hidden Line Removal algorithm." "\n\t\t: -showHidden if set ON, hidden lines are drawn as dotted ones" "\n\t\t: -algoType type of HLR algorithm.\n", __FILE__,VHLR,group); theCommands.Add("vhlrtype", "vhlrtype {algo|polyAlgo} [shape_1 ... shape_n] [-noupdate]" "\n\t\t: Changes the type of HLR algorithm using for shapes:" "\n\t\t: 'algo' - exact HLR algorithm is applied" "\n\t\t: 'polyAlgo' - polygonal HLR algorithm is applied" "\n\t\t: If shapes are not given - option is applied to all shapes in the view", __FILE__,VHLRType,group); theCommands.Add("vclipplane", "vclipplane planeName [{0|1}]" "\n\t\t: [-equation1 A B C D]" "\n\t\t: [-equation2 A B C D]" "\n\t\t: [-boxInterior MinX MinY MinZ MaxX MaxY MaxZ]" "\n\t\t: [-set|-unset|-setOverrideGlobal [objects|views]]" "\n\t\t: [-maxPlanes]" "\n\t\t: [-capping {0|1}]" "\n\t\t: [-color R G B] [-hatch {on|off|ID}]" "\n\t\t: [-texName Texture] [-texScale SX SY] [-texOrigin TX TY]" "\n\t\t: [-texRotate Angle]" "\n\t\t: [-useObjMaterial {0|1}] [-useObjTexture {0|1}]" "\n\t\t: [-useObjShader {0|1}]" "\n\t\t: Clipping planes management:" "\n\t\t: -maxPlanes print plane limit for view" "\n\t\t: -delete delete plane with given name" "\n\t\t: {off|on|0|1} turn clipping on/off" "\n\t\t: -set|-unset set/unset plane for Object or View list;" "\n\t\t: applied to active View when list is omitted" "\n\t\t: -equation A B C D change plane equation" "\n\t\t: -clone SourcePlane NewPlane clone the plane definition." "\n\t\t: Capping options:" "\n\t\t: -capping {off|on|0|1} turn capping on/off" "\n\t\t: -color R G B set capping color" "\n\t\t: -texName Texture set capping texture" "\n\t\t: -texScale SX SY set capping tex scale" "\n\t\t: -texOrigin TX TY set capping tex origin" "\n\t\t: -texRotate Angle set capping tex rotation" "\n\t\t: -hatch {on|off|ID} set capping hatching mask" "\n\t\t: -useObjMaterial {off|on|0|1} use material of clipped object" "\n\t\t: -useObjTexture {off|on|0|1} use texture of clipped object" "\n\t\t: -useObjShader {off|on|0|1} use shader program of object", __FILE__, VClipPlane, group); theCommands.Add("vdefaults", "vdefaults [-absDefl value]" "\n\t\t: [-devCoeff value]" "\n\t\t: [-angDefl value]" "\n\t\t: [-autoTriang {off/on | 0/1}]" , __FILE__, VDefaults, group); theCommands.Add("vlight", "tool to manage light sources, without arguments shows list of lights." "\n Main commands: " "\n '-clear' to clear lights" "\n '-{def}aults' to load deafault lights" "\n '-add' to add any light source" "\n where is one of {amb}ient|directional|{spot}light|positional" "\n 'change' to edit light source with specified lightId" "\n\n In addition to 'add' and 'change' commands you can use light parameters:" "\n -layer Id" "\n -{pos}ition X Y Z" "\n -{dir}ection X Y Z (for directional light or for spotlight)" "\n -color colorName" "\n -{head}light 0|1" "\n -{sm}oothness value" "\n -{int}ensity value" "\n -{constAtten}uation value" "\n -{linearAtten}uation value" "\n -angle angleDeg" "\n -{spotexp}onent value" "\n -local|-global" "\n\n example: vlight -add positional -head 1 -pos 0 1 1 -color red" "\n example: vlight -change 0 -direction 0 -1 0 -linearAttenuation 0.2", __FILE__, VLight, group); theCommands.Add("vraytrace", "vraytrace [0|1]" "\n\t\t: Turns on/off ray-tracing renderer." "\n\t\t: 'vraytrace 0' alias for 'vrenderparams -raster'." "\n\t\t: 'vraytrace 1' alias for 'vrenderparams -rayTrace'.", __FILE__, VRenderParams, group); theCommands.Add("vrenderparams", "\n Manages rendering parameters: " "\n '-raster' Disables GPU ray-tracing" "\n '-msaa 0..4' Specifies number of samples for MSAA" "\n '-oit off|0.0-1.0' Enables/disables OIT and sets depth weight factor" "\n '-depthPrePass on|off' Enables/disables depth pre-pass" "\n '-alphatocoverage on|off' Enables/disables alpha to coverage (needs MSAA)" "\n '-rendScale value Rendering resolution scale factor" "\n '-rayTrace' Enables GPU ray-tracing" "\n '-rayDepth 0..10' Defines maximum ray-tracing depth" "\n '-shadows on|off' Enables/disables shadows rendering" "\n '-reflections on|off' Enables/disables specular reflections" "\n '-fsaa on|off' Enables/disables adaptive anti-aliasing" "\n '-gleam on|off' Enables/disables transparency shadow effects" "\n '-gi on|off' Enables/disables global illumination effects" "\n '-brng on|off' Enables/disables blocked RNG (fast coherent PT)" "\n '-env on|off' Enables/disables environment map background" "\n '-twoside on|off' Enables/disables two-sided BSDF models (PT mode)" "\n '-iss on|off' Enables/disables adaptive screen sampling (PT mode)" "\n '-issd on|off' Shows screen sampling distribution in ISS mode" "\n '-maxrad > 0.0' Value used for clamping radiance estimation (PT mode)" "\n '-nbtiles 64..1024' Specifies number of screen tiles in ISS mode" "\n '-rebuildGlsl on|off' Rebuild Ray-Tracing GLSL programs (for debugging)" "\n '-shadingModel model' Controls shading model from enumeration" "\n color, flat, gouraud, phong" "\n '-resolution value' Sets a new pixels density (PPI), defines scaling factor for parameters like text size" "\n '-aperture >= 0.0' Aperture size of perspective camera for depth-of-field effect (0 disables DOF)" "\n '-focal >= 0.0' Focal distance of perspective camera for depth-of-field effect" "\n '-exposure value' Exposure value for tone mapping (0.0 value disables the effect)" "\n '-whitepoint value' White point value for filmic tone mapping" "\n '-tonemapping mode' Tone mapping mode (disabled, filmic)" "\n '-perfCounters none|fps|cpu|layers|structures|groups|arrays|triagles|points|gpuMem|basic|extended|nofps'" "\n Show/hide performance counters (flags can be combined)" "\n '-perfUpdateInterval nbSeconds' Performance counters update interval" "\n Unlike vcaps, these parameters dramatically change visual properties." "\n Command is intended to control presentation quality depending on" "\n hardware capabilities and performance.", __FILE__, VRenderParams, group); theCommands.Add("vfrustumculling", "vfrustumculling [toEnable]: enables/disables objects clipping", __FILE__,VFrustumCulling,group); theCommands.Add("vhighlightselected", "vhighlightselected [0|1] or vhighlightselected [on|off]: enables/disables highlighting of selected objects.\n" "Without arguments it shows if highlighting of selected objects is enabled now.", __FILE__,VHighlightSelected,group); theCommands.Add ("vplace", "vplace dx dy" "\n\t\t: Places the point (in pixels) at the center of the window", __FILE__, VPlace, group); theCommands.Add("vxrotate", "vxrotate", __FILE__,VXRotate,group); theCommands.Add("vmanipulator", "\n vmanipulator Name [-attach AISObject | -detach | ...]" "\n tool to create and manage AIS manipulators." "\n Options: " "\n '-attach AISObject' attach manipulator to AISObject" "\n '-adjustPosition {0|1}' adjust position when attaching" "\n '-adjustSize {0|1}' adjust size when attaching" "\n '-enableModes {0|1}' enable modes when attaching" "\n '-detach' detach manipulator" "\n '-startTransform mouse_x mouse_y' - invoke start of transformation" "\n '-transform mouse_x mouse_y' - invoke transformation" "\n '-stopTransform [abort]' - invoke stop of transformation" "\n '-move x y z' - move attached object" "\n '-rotate x y z dx dy dz angle' - rotate attached object" "\n '-scale factor' - scale attached object" "\n '-autoActivate {0|1}' - set activation on detection" "\n '-followTranslation {0|1}' - set following translation transform" "\n '-followRotation {0|1}' - set following rotation transform" "\n '-gap value' - set gap between sub-parts" "\n '-part axis mode {0|1}' - set visual part" "\n '-pos x y z [nx ny nz [xx xy xz]' - set position of manipulator" "\n '-size value' - set size of manipulator" "\n '-zoomable {0|1}' - set zoom persistence", __FILE__, VManipulator, group); theCommands.Add("vselprops", "\n vselprops [dynHighlight|localDynHighlight|selHighlight|localSelHighlight] [options]" "\n Customizes selection and dynamic highlight parameters for the whole interactive context:" "\n -autoActivate {0|1} : disables|enables default computation and activation of global selection mode" "\n -pickStrategy {first|topmost} : defines picking strategy" "\n 'first' to pick first acceptable (default)" "\n 'topmost' to pick only topmost (and nothing, if topmost is rejected by filters)" "\n -pixTol value : sets up pixel tolerance" "\n -dispMode dispMode : sets display mode for highlighting" "\n -layer ZLayer : sets ZLayer for highlighting" "\n -color {name|r g b} : sets highlight color" "\n -transp value : sets transparency coefficient for highlight" "\n -material material : sets highlight material" "\n -print : prints current state of all mentioned parameters", __FILE__, VSelectionProperties, group); theCommands.Add ("vseldump", "vseldump file -type {depth|unnormDepth|object|owner|selMode|entity}=depth -pickedIndex Index=1" "\n\t\t: Generate an image based on detection results:" "\n\t\t: depth normalized depth values" "\n\t\t: unnormDepth unnormalized depth values" "\n\t\t: object color of detected object" "\n\t\t: owner color of detected owner" "\n\t\t: selMode color of selection mode" "\n\t\t: entity color of etected entity", __FILE__, VDumpSelectionImage, group); #if defined(_WIN32) theCommands.Add("vprogressive", "vprogressive", __FILE__, VProgressiveMode, group); #endif }