diff --git a/src/Graphic3d/Graphic3d_FrameStats.cxx b/src/Graphic3d/Graphic3d_FrameStats.cxx index 01e0c65f91..99fb734697 100644 --- a/src/Graphic3d/Graphic3d_FrameStats.cxx +++ b/src/Graphic3d/Graphic3d_FrameStats.cxx @@ -49,6 +49,10 @@ namespace else { theStream << theValue; + if (thePostfix == NULL) + { + theStream << " "; + } } if (thePostfix != NULL) { @@ -57,6 +61,23 @@ namespace return theStream; } + //! Format a pair of counters. + static std::ostream& formatCounterPair (std::ostream& theStream, + Standard_Integer theWidth, + const char* thePrefix, + Standard_Size theValue, + Standard_Size theImmValue, + bool theToShowImmediate) + { + formatCounter (theStream, theWidth, thePrefix, theValue, NULL); + if (theToShowImmediate) + { + formatCounter (theStream, 1, "(", theImmValue, ")"); + } + theStream << "\n"; + return theStream; + } + //! Format memory counter. static std::ostream& formatBytes (std::ostream& theStream, Standard_Integer theWidth, @@ -263,11 +284,21 @@ TCollection_AsciiString Graphic3d_FrameStats::FormatStats (Graphic3d_RenderingPa { if ((theFlags & Graphic3d_RenderingParams::PerfCounters_FrameRate) != 0) { - aBuf << "FPS: " << std::setfill(' ') << std::setw (isCompact ? aValWidth : aValWidth + 3) << std::fixed << std::setprecision (1) << aStats.FrameRate() << "\n"; + aBuf << "FPS: " << std::setfill(' ') << std::setw (isCompact ? aValWidth : aValWidth + 3) << std::fixed << std::setprecision (1) << aStats.FrameRate(); + if (aStats.ImmediateFrameRate() > 0.0) + { + aBuf << " (" << std::fixed << std::setprecision (1) << aStats.ImmediateFrameRate() << ")"; + } + aBuf << "\n"; } if ((theFlags & Graphic3d_RenderingParams::PerfCounters_CPU) != 0) { - aBuf << "CPU FPS: " << std::setfill(' ') << std::setw (isCompact ? aValWidth : aValWidth + 3) << std::fixed << std::setprecision (1) << aStats.FrameRateCpu() << "\n"; + aBuf << "CPU FPS: " << std::setfill(' ') << std::setw (isCompact ? aValWidth : aValWidth + 3) << std::fixed << std::setprecision (1) << aStats.FrameRateCpu(); + if (aStats.ImmediateFrameRateCpu() > 0.0) + { + aBuf << " (" << std::fixed << std::setprecision (1) << aStats.ImmediateFrameRateCpu() << ")"; + } + aBuf << "\n"; } } if ((theFlags & Graphic3d_RenderingParams::PerfCounters_Layers) != 0) @@ -302,6 +333,8 @@ TCollection_AsciiString Graphic3d_FrameStats::FormatStats (Graphic3d_RenderingPa formatCounter (aBuf, aValWidth + 3, "Structs: ", aStats[Graphic3d_FrameStatsCounter_NbStructs], "\n"); } } + + const bool hasImmediate = aStats[Graphic3d_FrameStatsCounter_NbLayersImmediate] != 0 || aStats.ImmediateFrameRate() > 0.0; if ((theFlags & Graphic3d_RenderingParams::PerfCounters_Groups) != 0 || (theFlags & Graphic3d_RenderingParams::PerfCounters_GroupArrays) != 0 || (theFlags & Graphic3d_RenderingParams::PerfCounters_Triangles) != 0 @@ -311,41 +344,70 @@ TCollection_AsciiString Graphic3d_FrameStats::FormatStats (Graphic3d_RenderingPa && ((theFlags & Graphic3d_RenderingParams::PerfCounters_Structures) != 0 || (theFlags & Graphic3d_RenderingParams::PerfCounters_Layers) != 0))) { - aBuf << "Rendered\n"; + if (hasImmediate) + { + aBuf << "Rendered (imm.)\n"; + } + else + { + aBuf << "Rendered\n"; + } } if (!myIsLongLineFormat && (theFlags & Graphic3d_RenderingParams::PerfCounters_Layers) != 0) { - formatCounter (aBuf, aValWidth, " Layers: ", aStats[Graphic3d_FrameStatsCounter_NbLayersNotCulled], "\n"); + formatCounterPair (aBuf, aValWidth, " Layers: ", + aStats[Graphic3d_FrameStatsCounter_NbLayersNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbLayersImmediate], hasImmediate); } if (!myIsLongLineFormat && (theFlags & Graphic3d_RenderingParams::PerfCounters_Structures) != 0) { - formatCounter (aBuf, aValWidth, " Structs: ", aStats[Graphic3d_FrameStatsCounter_NbStructsNotCulled], "\n"); + formatCounterPair (aBuf, aValWidth, " Structs: ", + aStats[Graphic3d_FrameStatsCounter_NbStructsNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbStructsImmediate], hasImmediate); } if ((theFlags & Graphic3d_RenderingParams::PerfCounters_Groups) != 0) { - formatCounter (aBuf, aValWidth, " Groups: ", aStats[Graphic3d_FrameStatsCounter_NbGroupsNotCulled], "\n"); + formatCounterPair (aBuf, aValWidth, " Groups: ", + aStats[Graphic3d_FrameStatsCounter_NbGroupsNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbGroupsImmediate], hasImmediate); } if ((theFlags & Graphic3d_RenderingParams::PerfCounters_GroupArrays) != 0) { - formatCounter (aBuf, aValWidth, " Arrays: ", aStats[Graphic3d_FrameStatsCounter_NbElemsNotCulled], "\n"); - formatCounter (aBuf, aValWidth, " [fill]: ", aStats[Graphic3d_FrameStatsCounter_NbElemsFillNotCulled], "\n"); - formatCounter (aBuf, aValWidth, " [line]: ", aStats[Graphic3d_FrameStatsCounter_NbElemsLineNotCulled], "\n"); - formatCounter (aBuf, aValWidth, " [point]: ", aStats[Graphic3d_FrameStatsCounter_NbElemsPointNotCulled], "\n"); - formatCounter (aBuf, aValWidth, " [text]: ", aStats[Graphic3d_FrameStatsCounter_NbElemsTextNotCulled], "\n"); + formatCounterPair (aBuf, aValWidth, " Arrays: ", + aStats[Graphic3d_FrameStatsCounter_NbElemsNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbElemsImmediate], hasImmediate); + formatCounterPair (aBuf, aValWidth, " [fill]: ", + aStats[Graphic3d_FrameStatsCounter_NbElemsFillNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbElemsFillImmediate], hasImmediate); + formatCounterPair (aBuf, aValWidth, " [line]: ", + aStats[Graphic3d_FrameStatsCounter_NbElemsLineNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbElemsLineImmediate], hasImmediate); + formatCounterPair (aBuf, aValWidth, " [point]: ", + aStats[Graphic3d_FrameStatsCounter_NbElemsPointNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbElemsPointImmediate], hasImmediate); + formatCounterPair (aBuf, aValWidth, " [text]: ", + aStats[Graphic3d_FrameStatsCounter_NbElemsTextNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbElemsTextImmediate], hasImmediate); } if ((theFlags & Graphic3d_RenderingParams::PerfCounters_Triangles) != 0) { - formatCounter (aBuf, aValWidth, " Triangles: ", aStats[Graphic3d_FrameStatsCounter_NbTrianglesNotCulled], "\n"); + formatCounterPair (aBuf, aValWidth, " Triangles: ", + aStats[Graphic3d_FrameStatsCounter_NbTrianglesNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbTrianglesImmediate], hasImmediate); } if ((theFlags & Graphic3d_RenderingParams::PerfCounters_Lines) != 0) { - formatCounter (aBuf, aValWidth, " Lines: ", aStats[Graphic3d_FrameStatsCounter_NbLinesNotCulled], "\n"); + formatCounterPair (aBuf, aValWidth, " Lines: ", + aStats[Graphic3d_FrameStatsCounter_NbLinesNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbLinesImmediate], hasImmediate); } if ((theFlags & Graphic3d_RenderingParams::PerfCounters_Points) != 0) { - formatCounter (aBuf, aValWidth, " Points: ", aStats[Graphic3d_FrameStatsCounter_NbPointsNotCulled], "\n"); + formatCounterPair (aBuf, aValWidth, " Points: ", + aStats[Graphic3d_FrameStatsCounter_NbPointsNotCulled], + aStats[Graphic3d_FrameStatsCounter_NbPointsImmediate], hasImmediate); } if ((theFlags & Graphic3d_RenderingParams::PerfCounters_EstimMem) != 0) { @@ -561,18 +623,33 @@ void Graphic3d_FrameStats::FrameEnd (const Handle(Graphic3d_CView)& theView, return; } + const Graphic3d_FrameStatsData& aPrevFrame = myCounters.Value (myLastFrameIndex); if (aTime > gp::Resolution()) { // update FPS myFpsTimer.Stop(); const double aCpuSec = myFpsTimer.UserTimeCPU(); - myCountersTmp[Graphic3d_FrameStatsTimer_ElapsedFrame] = aTime; myCountersTmp[Graphic3d_FrameStatsTimer_CpuFrame] = aCpuSec; - myCountersTmp.ChangeFrameRate() = double(myFpsFrameCount) / aTime; - myCountersTmp.ChangeFrameRateCpu() = aCpuSec > gp::Resolution() - ? double(myFpsFrameCount) / aCpuSec - : -1.0; + + if (theIsImmediateOnly) + { + myCountersTmp.ChangeImmediateFrameRate() = double(myFpsFrameCount) / aTime; + myCountersTmp.ChangeImmediateFrameRateCpu() = aCpuSec > gp::Resolution() + ? double(myFpsFrameCount) / aCpuSec + : -1.0; + myCountersTmp.ChangeFrameRate() = aPrevFrame.FrameRate(); + myCountersTmp.ChangeFrameRateCpu() = aPrevFrame.FrameRateCpu(); + } + else + { + myCountersTmp.ChangeImmediateFrameRate() = -1.0; + myCountersTmp.ChangeImmediateFrameRateCpu() = -1.0; + myCountersTmp.ChangeFrameRate() = double(myFpsFrameCount) / aTime; + myCountersTmp.ChangeFrameRateCpu() = aCpuSec > gp::Resolution() + ? double(myFpsFrameCount) / aCpuSec + : -1.0; + } myCountersTmp.FlushTimers (myFpsFrameCount, true); myCountersMax.FillMax (myCountersTmp); myFpsTimer.Reset(); @@ -594,6 +671,23 @@ void Graphic3d_FrameStats::FrameEnd (const Handle(Graphic3d_CView)& theView, { myLastFrameIndex = myCounters.Lower(); } + if (theIsImmediateOnly) + { + // copy rendered counters collected for immediate layers + const Standard_Integer anImmShift = Graphic3d_FrameStatsCounter_IMMEDIATE_LOWER - Graphic3d_FrameStatsCounter_RENDERED_LOWER; + Standard_STATIC_ASSERT((Graphic3d_FrameStatsCounter_RENDERED_UPPER - Graphic3d_FrameStatsCounter_RENDERED_LOWER) == (Graphic3d_FrameStatsCounter_IMMEDIATE_UPPER - Graphic3d_FrameStatsCounter_IMMEDIATE_LOWER)) + for (Standard_Integer aCntIter = Graphic3d_FrameStatsCounter_RENDERED_LOWER; aCntIter <= Graphic3d_FrameStatsCounter_RENDERED_UPPER; ++aCntIter) + { + myCountersTmp.ChangeCounterValue ((Graphic3d_FrameStatsCounter )(aCntIter + anImmShift)) = myCountersTmp.CounterValue ((Graphic3d_FrameStatsCounter )aCntIter); + } + + // copy main rendered counters from previous non-immediate frame + for (Standard_Integer aCntIter = Graphic3d_FrameStatsCounter_RENDERED_LOWER; aCntIter <= Graphic3d_FrameStatsCounter_RENDERED_UPPER; ++aCntIter) + { + myCountersTmp.ChangeCounterValue ((Graphic3d_FrameStatsCounter )aCntIter) = aPrevFrame.CounterValue ((Graphic3d_FrameStatsCounter )aCntIter); + } + myCountersTmp.ChangeCounterValue (Graphic3d_FrameStatsCounter_EstimatedBytesGeom) = aPrevFrame.CounterValue (Graphic3d_FrameStatsCounter_EstimatedBytesGeom); + } myCounters.SetValue (myLastFrameIndex, myCountersTmp); myCountersTmp.Reset(); } diff --git a/src/Graphic3d/Graphic3d_FrameStatsCounter.hxx b/src/Graphic3d/Graphic3d_FrameStatsCounter.hxx index 137cc4c2a7..b2f27a46c9 100644 --- a/src/Graphic3d/Graphic3d_FrameStatsCounter.hxx +++ b/src/Graphic3d/Graphic3d_FrameStatsCounter.hxx @@ -17,9 +17,15 @@ //! Stats counter. enum Graphic3d_FrameStatsCounter { + // overall scene counters Graphic3d_FrameStatsCounter_NbLayers = 0, //!< number of ZLayers - Graphic3d_FrameStatsCounter_NbLayersNotCulled, //!< number of not culled ZLayers Graphic3d_FrameStatsCounter_NbStructs, //!< number of defined OpenGl_Structure + Graphic3d_FrameStatsCounter_EstimatedBytesGeom, //!< estimated GPU memory used for geometry + Graphic3d_FrameStatsCounter_EstimatedBytesFbos, //!< estimated GPU memory used for FBOs + Graphic3d_FrameStatsCounter_EstimatedBytesTextures, //!< estimated GPU memory used for textures + + // rendered counters + Graphic3d_FrameStatsCounter_NbLayersNotCulled, //!< number of not culled ZLayers Graphic3d_FrameStatsCounter_NbStructsNotCulled, //!< number of not culled OpenGl_Structure Graphic3d_FrameStatsCounter_NbGroupsNotCulled, //!< number of not culled OpenGl_Group Graphic3d_FrameStatsCounter_NbElemsNotCulled, //!< number of not culled OpenGl_Element @@ -31,10 +37,29 @@ enum Graphic3d_FrameStatsCounter Graphic3d_FrameStatsCounter_NbLinesNotCulled, //!< number of not culled (as structure) line segments Graphic3d_FrameStatsCounter_NbPointsNotCulled, //!< number of not culled (as structure) points //Graphic3d_FrameStatsCounter_NbGlyphsNotCulled, //!< number glyphs, to be considered in future - Graphic3d_FrameStatsCounter_EstimatedBytesGeom, //!< estimated GPU memory used for geometry - Graphic3d_FrameStatsCounter_EstimatedBytesFbos, //!< estimated GPU memory used for FBOs - Graphic3d_FrameStatsCounter_EstimatedBytesTextures, //!< estimated GPU memory used for textures + + // immediate layer rendered counters + Graphic3d_FrameStatsCounter_NbLayersImmediate, //!< number of ZLayers in immediate layer + Graphic3d_FrameStatsCounter_NbStructsImmediate, //!< number of OpenGl_Structure in immediate layer + Graphic3d_FrameStatsCounter_NbGroupsImmediate, //!< number of OpenGl_Group in immediate layer + Graphic3d_FrameStatsCounter_NbElemsImmediate, //!< number of OpenGl_Element in immediate layer + Graphic3d_FrameStatsCounter_NbElemsFillImmediate, //!< number of OpenGl_PrimitiveArray drawing triangles in immediate layer + Graphic3d_FrameStatsCounter_NbElemsLineImmediate, //!< number of OpenGl_PrimitiveArray drawing lines in immediate layer + Graphic3d_FrameStatsCounter_NbElemsPointImmediate, //!< number of OpenGl_PrimitiveArray drawing points in immediate layer + Graphic3d_FrameStatsCounter_NbElemsTextImmediate, //!< number of OpenGl_Text in immediate layer + Graphic3d_FrameStatsCounter_NbTrianglesImmediate, //!< number of triangles in immediate layer + Graphic3d_FrameStatsCounter_NbLinesImmediate, //!< number of line segments in immediate layer + Graphic3d_FrameStatsCounter_NbPointsImmediate, //!< number of points in immediate layer +}; +enum +{ + Graphic3d_FrameStatsCounter_NB = Graphic3d_FrameStatsCounter_NbPointsImmediate + 1, + Graphic3d_FrameStatsCounter_SCENE_LOWER = Graphic3d_FrameStatsCounter_NbLayers, + Graphic3d_FrameStatsCounter_SCENE_UPPER = Graphic3d_FrameStatsCounter_EstimatedBytesTextures, + Graphic3d_FrameStatsCounter_RENDERED_LOWER = Graphic3d_FrameStatsCounter_NbLayersNotCulled, + Graphic3d_FrameStatsCounter_RENDERED_UPPER = Graphic3d_FrameStatsCounter_NbPointsNotCulled, + Graphic3d_FrameStatsCounter_IMMEDIATE_LOWER = Graphic3d_FrameStatsCounter_NbLayersImmediate, + Graphic3d_FrameStatsCounter_IMMEDIATE_UPPER = Graphic3d_FrameStatsCounter_NbPointsImmediate, }; -enum { Graphic3d_FrameStatsCounter_NB = Graphic3d_FrameStatsCounter_EstimatedBytesTextures + 1 }; #endif // _Graphic3d_FrameStatsCounter_HeaderFile diff --git a/src/Graphic3d/Graphic3d_FrameStatsData.cxx b/src/Graphic3d/Graphic3d_FrameStatsData.cxx index df50b3d652..8c46a42aee 100644 --- a/src/Graphic3d/Graphic3d_FrameStatsData.cxx +++ b/src/Graphic3d/Graphic3d_FrameStatsData.cxx @@ -19,7 +19,9 @@ // ======================================================================= Graphic3d_FrameStatsData::Graphic3d_FrameStatsData() : myFps (-1.0), - myFpsCpu (-1.0) + myFpsCpu (-1.0), + myFpsImmediate (-1.0), + myFpsCpuImmediate (-1.0) { myCounters .resize (Graphic3d_FrameStatsCounter_NB, 0); myTimers .resize (Graphic3d_FrameStatsTimer_NB, 0.0); @@ -36,6 +38,8 @@ Graphic3d_FrameStatsData& Graphic3d_FrameStatsData::operator= (const Graphic3d_F { myFps = theOther.myFps; myFpsCpu = theOther.myFpsCpu; + myFpsImmediate = theOther.myFpsImmediate; + myFpsCpuImmediate = theOther.myFpsCpuImmediate; myCounters = theOther.myCounters; myTimers = theOther.myTimers; myTimersMin = theOther.myTimersMin; @@ -51,6 +55,8 @@ void Graphic3d_FrameStatsData::Reset() { myFps = -1.0; myFpsCpu = -1.0; + myFpsImmediate = -1.0; + myFpsCpuImmediate = -1.0; myCounters .assign (myCounters.size(), 0); myTimers .assign (myTimers.size(), 0.0); myTimersMin.assign (myTimersMin.size(), RealLast()); @@ -65,6 +71,8 @@ void Graphic3d_FrameStatsData::FillMax (const Graphic3d_FrameStatsData& theOther { myFps = Max (myFps, theOther.myFps); myFpsCpu = Max (myFpsCpu, theOther.myFpsCpu); + myFpsImmediate = Max (myFpsImmediate, theOther.myFpsImmediate); + myFpsCpuImmediate = Max (myFpsCpuImmediate, theOther.myFpsCpuImmediate); for (size_t aCounterIter = 0; aCounterIter < myCounters.size(); ++aCounterIter) { myCounters[aCounterIter] = myCounters[aCounterIter] > theOther.myCounters[aCounterIter] ? myCounters[aCounterIter] : theOther.myCounters[aCounterIter]; diff --git a/src/Graphic3d/Graphic3d_FrameStatsData.hxx b/src/Graphic3d/Graphic3d_FrameStatsData.hxx index f84f34294d..27db098b66 100644 --- a/src/Graphic3d/Graphic3d_FrameStatsData.hxx +++ b/src/Graphic3d/Graphic3d_FrameStatsData.hxx @@ -40,6 +40,12 @@ public: //! while values around actual frame rate indicate rendering being limited by CPU performance (GPU is stalled in-between). Standard_Real FrameRateCpu() const { return myFpsCpu; } + //! Returns FPS for immediate redraws. + Standard_Real ImmediateFrameRate() const { return myFpsImmediate; } + + //! Returns CPU FPS for immediate redraws. + Standard_Real ImmediateFrameRateCpu() const { return myFpsCpuImmediate; } + //! Get counter value. Standard_Size CounterValue (Graphic3d_FrameStatsCounter theIndex) const { return myCounters[theIndex]; } @@ -71,6 +77,8 @@ protected: std::vector myTimersMax; //!< maximum values of timers Standard_Real myFps; //!< FPS meter (frames per seconds, elapsed time) Standard_Real myFpsCpu; //!< CPU FPS meter (frames per seconds, CPU time) + Standard_Real myFpsImmediate; //!< FPS meter for immediate redraws + Standard_Real myFpsCpuImmediate; //!< CPU FPS meter for immediate redraws }; //! Temporary data frame definition. @@ -95,6 +103,12 @@ public: //! Returns CPU FPS (frames per seconds, CPU time). Standard_Real& ChangeFrameRateCpu() { return myFpsCpu; } + //! Returns FPS for immediate redraws. + Standard_Real& ChangeImmediateFrameRate() { return myFpsImmediate; } + + //! Returns CPU FPS for immediate redraws. + Standard_Real& ChangeImmediateFrameRateCpu() { return myFpsCpuImmediate; } + //! Return a timer object for time measurements. OSD_Timer& ChangeTimer (Graphic3d_FrameStatsTimer theTimer) { return myOsdTimers[theTimer]; } diff --git a/src/OpenGl/OpenGl_FrameStats.cxx b/src/OpenGl/OpenGl_FrameStats.cxx index 9828dd411e..c751d512c9 100644 --- a/src/OpenGl/OpenGl_FrameStats.cxx +++ b/src/OpenGl/OpenGl_FrameStats.cxx @@ -61,6 +61,8 @@ bool OpenGl_FrameStats::IsFrameUpdated (Handle(OpenGl_FrameStats)& thePrev) cons else if (myLastFrameIndex == thePrev->myLastFrameIndex && Abs (aFrame.FrameRate() - thePrev->myCountersTmp.FrameRate()) <= 0.001 && Abs (aFrame.FrameRateCpu() - thePrev->myCountersTmp.FrameRateCpu()) <= 0.001 + && Abs (aFrame.ImmediateFrameRate() - thePrev->myCountersTmp.ImmediateFrameRate()) <= 0.001 + && Abs (aFrame.ImmediateFrameRateCpu() - thePrev->myCountersTmp.ImmediateFrameRateCpu()) <= 0.001 && aFrame[Graphic3d_FrameStatsCounter_NbLayers] == thePrev->myCountersTmp[Graphic3d_FrameStatsCounter_NbLayers] && aFrame[Graphic3d_FrameStatsCounter_NbLayersNotCulled] == thePrev->myCountersTmp[Graphic3d_FrameStatsCounter_NbLayersNotCulled] && aFrame[Graphic3d_FrameStatsCounter_NbStructs] == thePrev->myCountersTmp[Graphic3d_FrameStatsCounter_NbStructs]