diff options
Diffstat (limited to 'common/vgui')
| -rw-r--r-- | common/vgui/vgui_basebudgetpanel.cpp | 443 | ||||
| -rw-r--r-- | common/vgui/vgui_basebudgetpanel.h | 145 | ||||
| -rw-r--r-- | common/vgui/vgui_budgetbargraphpanel.cpp | 252 | ||||
| -rw-r--r-- | common/vgui/vgui_budgetbargraphpanel.h | 43 | ||||
| -rw-r--r-- | common/vgui/vgui_budgethistorypanel.cpp | 136 | ||||
| -rw-r--r-- | common/vgui/vgui_budgethistorypanel.h | 48 | ||||
| -rw-r--r-- | common/vgui/vgui_budgetpanelshared.cpp | 263 | ||||
| -rw-r--r-- | common/vgui/vgui_budgetpanelshared.h | 71 |
8 files changed, 1401 insertions, 0 deletions
diff --git a/common/vgui/vgui_basebudgetpanel.cpp b/common/vgui/vgui_basebudgetpanel.cpp new file mode 100644 index 0000000..3a2f639 --- /dev/null +++ b/common/vgui/vgui_basebudgetpanel.cpp @@ -0,0 +1,443 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//=============================================================================// + +#include "vgui_basebudgetpanel.h" +#include "vgui_controls/Label.h" + +// memdbgon must be the last include file in a .cpp file!!! +#include "tier0/memdbgon.h" + +CBaseBudgetPanel::CBaseBudgetPanel( vgui::Panel *pParent, const char *pElementName ) + : vgui::Panel( pParent, pElementName ) +{ + m_BudgetHistoryOffset = 0; + + SetProportional( false ); + SetKeyBoardInputEnabled( false ); + SetMouseInputEnabled( false ); + SetVisible( true ); + + // set the scheme before any child control is created + vgui::HScheme scheme = vgui::scheme()->LoadSchemeFromFile("resource/SourceScheme.res", "Client"); + SetScheme( scheme ); + + m_pBudgetHistoryPanel = NULL; + m_pBudgetBarGraphPanel = NULL; + SetZPos( 1001 ); + + m_bDedicated = false; +} + + +CBaseBudgetPanel::~CBaseBudgetPanel() +{ +} + + +float CBaseBudgetPanel::GetBudgetGroupPercent( float value ) +{ + if ( m_ConfigData.m_flBarGraphRange == 0.0f ) + return 1.0f; + return value / m_ConfigData.m_flBarGraphRange; +} + + +const double *CBaseBudgetPanel::GetBudgetGroupData( int &nGroups, int &nSamplesPerGroup, int &nSampleOffset ) const +{ + nGroups = m_ConfigData.m_BudgetGroupInfo.Count(); + nSamplesPerGroup = BUDGET_HISTORY_COUNT; + nSampleOffset = m_BudgetHistoryOffset; + if( m_BudgetGroupTimes.Count() == 0 ) + { + return NULL; + } + else + { + return &m_BudgetGroupTimes[0].m_Time[0]; + } +} + + +void CBaseBudgetPanel::ClearTimesForAllGroupsForThisFrame( void ) +{ + int i; + for( i = 0; i < m_ConfigData.m_BudgetGroupInfo.Count(); i++ ) + { + m_BudgetGroupTimes[i].m_Time[m_BudgetHistoryOffset] = 0.0; + } +} + +void CBaseBudgetPanel::ClearAllTimesForGroup( int groupID ) +{ + int i; + for( i = 0; i < BUDGET_HISTORY_COUNT; i++ ) + { + m_BudgetGroupTimes[groupID].m_Time[i] = 0.0; + } +} + + +void CBaseBudgetPanel::OnConfigDataChanged( const CBudgetPanelConfigData &data ) +{ + int oldNumGroups = m_ConfigData.m_BudgetGroupInfo.Count(); + + // Copy in the config data and rebuild everything. + Rebuild( data ); + + if ( m_ConfigData.m_BudgetGroupInfo.Count() > m_BudgetGroupTimes.Count() ) + { + m_BudgetGroupTimes.EnsureCount( m_ConfigData.m_BudgetGroupInfo.Count() ); + for ( int i = oldNumGroups; i < m_ConfigData.m_BudgetGroupInfo.Count(); i++ ) + { + ClearAllTimesForGroup( i ); + } + } + else + { + m_BudgetGroupTimes.SetSize( m_ConfigData.m_BudgetGroupInfo.Count() ); + for ( int i = 0; i < m_BudgetGroupTimes.Count(); i++ ) + { + ClearAllTimesForGroup( i ); + } + } + + InvalidateLayout( false, true ); +} + + +void CBaseBudgetPanel::ResetAll() +{ + m_ConfigData.m_BudgetGroupInfo.Purge(); + + for ( int i=0; i < m_GraphLabels.Count(); i++ ) + m_GraphLabels[i]->MarkForDeletion(); + m_GraphLabels.Purge(); + + for ( int i=0; i < m_TimeLabels.Count(); i++ ) + m_TimeLabels[i]->MarkForDeletion(); + m_TimeLabels.Purge(); +} + + +void CBaseBudgetPanel::Rebuild( const CBudgetPanelConfigData &data ) +{ + int oldNumBudgetGroups = m_ConfigData.m_BudgetGroupInfo.Count(); + int oldNumHistoryLabels = m_ConfigData.m_HistoryLabelValues.Count(); + + int oldNumTimeLabels = m_TimeLabels.Count(); + + // Copy the new config in. + m_ConfigData = data; + + int nParentWidth, nParentHeight; + GetParent()->GetSize( nParentWidth, nParentHeight ); + if ( m_ConfigData.m_Width > nParentWidth ) + { + m_ConfigData.m_Width = nParentWidth; + } + if ( m_ConfigData.m_Height > nParentHeight ) + { + m_ConfigData.m_Height = nParentHeight; + } + if ( m_ConfigData.m_xCoord + m_ConfigData.m_Width > nParentWidth ) + { + m_ConfigData.m_xCoord = nParentWidth - m_ConfigData.m_Width; + } + if ( m_ConfigData.m_yCoord + m_ConfigData.m_Height > nParentHeight ) + { + m_ConfigData.m_yCoord = nParentHeight - m_ConfigData.m_Height; + } + + // Recreate the history and bar graph panels. + if( m_pBudgetHistoryPanel ) + { + m_pBudgetHistoryPanel->MarkForDeletion(); + } + m_pBudgetHistoryPanel = new CBudgetHistoryPanel( this, "FrametimeHistory" ); + + if( m_pBudgetBarGraphPanel ) + { + m_pBudgetBarGraphPanel->MarkForDeletion(); + } + m_pBudgetBarGraphPanel = new CBudgetBarGraphPanel( this, "BudgetBarGraph" ); + + // Create any new labels we need. + int i; + + if ( m_ConfigData.m_BudgetGroupInfo.Count() > m_GraphLabels.Count() ) + { + m_GraphLabels.EnsureCount( m_ConfigData.m_BudgetGroupInfo.Count() ); + for( i = oldNumBudgetGroups; i < m_ConfigData.m_BudgetGroupInfo.Count(); i++ ) + { + const char *pBudgetGroupName = m_ConfigData.m_BudgetGroupInfo[i].m_Name.String(); + m_GraphLabels[i] = new vgui::Label( this, pBudgetGroupName, pBudgetGroupName ); + } + } + else + { + while ( m_GraphLabels.Count() > m_ConfigData.m_BudgetGroupInfo.Count() ) + { + m_GraphLabels[m_GraphLabels.Count()-1]->MarkForDeletion(); + m_GraphLabels.Remove( m_GraphLabels.Count()-1 ); + } + } + Assert( m_GraphLabels.Count() == m_ConfigData.m_BudgetGroupInfo.Count() ); + + + // Create new history labels. + if ( m_ConfigData.m_HistoryLabelValues.Count() > m_HistoryLabels.Count() ) + { + m_HistoryLabels.EnsureCount( m_ConfigData.m_HistoryLabelValues.Count() ); + for ( i=oldNumHistoryLabels; i < m_HistoryLabels.Count(); i++ ) + { + m_HistoryLabels[i] = new vgui::Label( this, "history label", "history label" ); + } + } + else + { + while ( m_HistoryLabels.Count() > m_ConfigData.m_HistoryLabelValues.Count() ) + { + m_HistoryLabels[m_HistoryLabels.Count()-1]->MarkForDeletion(); + m_HistoryLabels.Remove( m_HistoryLabels.Count()-1 ); + } + } + SetHistoryLabelText(); + + + // Note: the time lines still use milliseconds for the computations about where to draw them, + // but each BudgetGroupDataType_t has its own scale. + int nTimeLabels = m_ConfigData.m_flBarGraphRange + data.m_flTimeLabelInterval; + if ( data.m_flTimeLabelInterval != 0.0f ) + { + nTimeLabels /= data.m_flTimeLabelInterval; + } + + if ( nTimeLabels > m_TimeLabels.Count() ) + { + m_TimeLabels.EnsureCount( nTimeLabels ); + for( i = oldNumTimeLabels; i < m_TimeLabels.Count(); i++ ) + { + char name[1024]; + Q_snprintf( name, sizeof( name ), "time_label_%d", i ); + m_TimeLabels[i] = new vgui::Label( this, name, "TEXT NOT SET YET" ); + } + } + else + { + while ( m_TimeLabels.Count() > nTimeLabels ) + { + m_TimeLabels[m_TimeLabels.Count()-1]->MarkForDeletion(); + m_TimeLabels.Remove( m_TimeLabels.Count()-1 ); + } + } + + SetTimeLabelText(); +} + +void CBaseBudgetPanel::UpdateWindowGeometry() +{ + if( m_ConfigData.m_Width > BUDGET_HISTORY_COUNT ) + { + m_ConfigData.m_Width = BUDGET_HISTORY_COUNT; + } + + SetPos( m_ConfigData.m_xCoord, m_ConfigData.m_yCoord ); + SetSize( m_ConfigData.m_Width, m_ConfigData.m_Height ); +} + +void CBaseBudgetPanel::PerformLayout() +{ + if ( !m_pBudgetHistoryPanel || !m_pBudgetBarGraphPanel ) + return; + + + int maxFPSLabelWidth = 0; + int i; + for( i = 0; i < m_HistoryLabels.Count(); i++ ) + { + int labelWidth, labelHeight; + m_HistoryLabels[i]->GetContentSize( labelWidth, labelHeight ); + if( labelWidth > maxFPSLabelWidth ) + { + maxFPSLabelWidth = labelWidth; + } + } + + m_pBudgetHistoryPanel->SetRange( 0, m_ConfigData.m_flHistoryRange ); + + + float bottomOfHistoryPercentage = m_ConfigData.m_flBottomOfHistoryFraction; + UpdateWindowGeometry(); + int x, y, totalWidth, totalHeight; + int totalHeightMinusTimeLabels; + GetPos( x, y ); + GetSize( totalWidth, totalHeight ); + + int maxTimeLabelHeight = 0; + for( i = 0; i < m_TimeLabels.Count(); i++ ) + { + int labelWidth, labelHeight; + m_TimeLabels[i]->GetContentSize( labelWidth, labelHeight ); + maxTimeLabelHeight = max( maxTimeLabelHeight, labelHeight ); + } + + totalHeightMinusTimeLabels = totalHeight - maxTimeLabelHeight; + + m_pBudgetHistoryPanel->SetPos( 0, 0 ); + int budgetHistoryHeight = totalHeightMinusTimeLabels * bottomOfHistoryPercentage; + m_pBudgetHistoryPanel->SetSize( totalWidth - maxFPSLabelWidth, + budgetHistoryHeight ); + + int maxLabelWidth = 0; + for( i = 0; i < m_GraphLabels.Count(); i++ ) + { + int width, height; + m_GraphLabels[i]->GetContentSize( width, height ); + if( maxLabelWidth < width ) + { + maxLabelWidth = width; + } + } + + m_pBudgetBarGraphPanel->SetPos( maxLabelWidth, + totalHeightMinusTimeLabels * bottomOfHistoryPercentage ); + m_pBudgetBarGraphPanel->SetSize( totalWidth - maxLabelWidth, + totalHeightMinusTimeLabels * ( 1 - bottomOfHistoryPercentage ) ); + + for( i = 0; i < m_GraphLabels.Count(); i++ ) + { + m_GraphLabels[i]->SetPos( 0, + ( bottomOfHistoryPercentage * totalHeightMinusTimeLabels ) + + ( i * totalHeightMinusTimeLabels * + ( 1 - bottomOfHistoryPercentage ) ) / m_ConfigData.m_BudgetGroupInfo.Count() ); + // fudge height by 1 for rounding + m_GraphLabels[i]->SetSize( maxLabelWidth, 1 + ( totalHeightMinusTimeLabels * + ( 1 - bottomOfHistoryPercentage ) ) / m_ConfigData.m_BudgetGroupInfo.Count() ); + m_GraphLabels[i]->SetContentAlignment( vgui::Label::a_east ); + } + + // Note: the time lines still use milliseconds for the computations about where to draw them, + // but each BudgetGroupDataType_t has its own scale. + float fRange = m_ConfigData.m_flBarGraphRange; + for( i = 0; i < m_TimeLabels.Count(); i++ ) + { + int labelWidth, labelHeight; + m_TimeLabels[i]->GetContentSize( labelWidth, labelHeight ); + x = maxLabelWidth + ( i * m_ConfigData.m_flTimeLabelInterval ) / fRange * ( totalWidth - maxLabelWidth ); + + m_TimeLabels[i]->SetPos( x - ( labelWidth * 0.5 ), totalHeight - labelHeight ); + m_TimeLabels[i]->SetSize( labelWidth, labelHeight ); + m_TimeLabels[i]->SetContentAlignment( vgui::Label::a_east ); + } + + + // position the fps labels + fRange = m_ConfigData.m_flHistoryRange; + for( i = 0; i < m_HistoryLabels.Count(); i++ ) + { + int labelWidth, labelHeight; + m_HistoryLabels[i]->GetContentSize( labelWidth, labelHeight ); + y = (fRange != 0) ? budgetHistoryHeight * m_ConfigData.m_HistoryLabelValues[i] / ( float )fRange : 0.0f; + int top = ( int )( budgetHistoryHeight - y - 1 - labelHeight * 0.5f ); + m_HistoryLabels[i]->SetPos( totalWidth - maxFPSLabelWidth, top ); + m_HistoryLabels[i]->SetSize( labelWidth, labelHeight ); + m_HistoryLabels[i]->SetContentAlignment( vgui::Label::a_east ); + } +} + +void CBaseBudgetPanel::ApplySchemeSettings( vgui::IScheme *pScheme ) +{ + BaseClass::ApplySchemeSettings( pScheme ); + + int i; + for( i = 0; i < m_ConfigData.m_BudgetGroupInfo.Count(); i++ ) + { + m_GraphLabels[i]->SetFgColor( m_ConfigData.m_BudgetGroupInfo[i].m_Color ); + m_GraphLabels[i]->SetBgColor( Color( 0, 0, 0, 255 ) ); + m_GraphLabels[i]->SetPaintBackgroundEnabled( false ); + m_GraphLabels[i]->SetFont( pScheme->GetFont( "BudgetLabel", IsProportional() ) ); + if ( m_bDedicated ) + { + m_GraphLabels[i]->SetBgColor( pScheme->GetColor( "ControlBG", Color( 0, 0, 0, 255 ) ) ); + } + } + + for( i = 0; i < m_TimeLabels.Count(); i++ ) + { + int red, green, blue, alpha; + red = green = blue = alpha = 255; + m_TimeLabels[i]->SetFgColor( Color( red, green, blue, alpha ) ); + m_TimeLabels[i]->SetBgColor( Color( 0, 0, 0, 255 ) ); + m_TimeLabels[i]->SetPaintBackgroundEnabled( false ); + m_TimeLabels[i]->SetFont( pScheme->GetFont( "BudgetLabel", IsProportional() ) ); + if ( m_bDedicated ) + { + m_TimeLabels[i]->SetBgColor( pScheme->GetColor( "ControlBG", Color( 0, 0, 0, 255 ) ) ); + } + } + + for( i = 0; i < m_HistoryLabels.Count(); i++ ) + { + int red, green, blue, alpha; + red = green = blue = alpha = 255; + m_HistoryLabels[i]->SetFgColor( Color( red, green, blue, alpha ) ); + m_HistoryLabels[i]->SetBgColor( Color( 0, 0, 0, 255 ) ); + m_HistoryLabels[i]->SetPaintBackgroundEnabled( false ); + m_HistoryLabels[i]->SetFont( pScheme->GetFont( "BudgetLabel", IsProportional() ) ); + if ( m_bDedicated ) + { + m_HistoryLabels[i]->SetBgColor( pScheme->GetColor( "ControlBG", Color( 0, 0, 0, 255 ) ) ); + } + } + + m_hFont = pScheme->GetFont( "DefaultFixed" ); + + if ( m_bDedicated ) + { + SetBgColor( pScheme->GetColor( "ControlBG", Color( 0, 0, 0, 255 ) ) ); + } + SetPaintBackgroundEnabled( true ); +} + +void CBaseBudgetPanel::PaintBackground() +{ + if ( m_bDedicated ) + { + m_pBudgetBarGraphPanel->SetBgColor( GetBgColor() ); + } + else + { + SetBgColor( Color( 0, 0, 0, m_ConfigData.m_flBackgroundAlpha ) ); + } + BaseClass::PaintBackground(); +} + +void CBaseBudgetPanel::Paint() +{ + m_pBudgetHistoryPanel->SetData( &m_BudgetGroupTimes[0].m_Time[0], GetNumCachedBudgetGroups(), BUDGET_HISTORY_COUNT, m_BudgetHistoryOffset ); + BaseClass::Paint(); +} + +void CBaseBudgetPanel::MarkForFullRepaint() +{ + Repaint(); + m_pBudgetHistoryPanel->Repaint(); + m_pBudgetBarGraphPanel->Repaint(); +} + + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void CBaseBudgetPanel::GetGraphLabelScreenSpaceTopAndBottom( int id, int &top, int &bottom ) +{ + int x = 0; + int y = 0; + m_GraphLabels[id]->LocalToScreen( x, y ); + top = y; + bottom = top + m_GraphLabels[id]->GetTall(); +} + diff --git a/common/vgui/vgui_basebudgetpanel.h b/common/vgui/vgui_basebudgetpanel.h new file mode 100644 index 0000000..27115bc --- /dev/null +++ b/common/vgui/vgui_basebudgetpanel.h @@ -0,0 +1,145 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//=============================================================================// + +#ifndef VGUI_BASEBUDGETPANEL_H +#define VGUI_BASEBUDGETPANEL_H + +#ifdef _WIN32 +#pragma once +#endif + + +#include <vgui_controls/Frame.h> +#include <vgui/IScheme.h> +#include "vgui_budgethistorypanel.h" +#include "vgui_budgetbargraphpanel.h" +#include "utlsymbol.h" +//#include "hudelement.h" + + +#define BUDGET_HISTORY_COUNT 1024 + +class CBudgetGroupInfo +{ +public: + CUtlSymbol m_Name; + Color m_Color; +}; + +// Derived classes supply this configuration data with OnConfigDataChanged. +class CBudgetPanelConfigData +{ +public: + // NOTE: nothing can ever be removed from this list once you've called + // OnConfigDataChanged. Elements can only be added to it. + CUtlVector<CBudgetGroupInfo> m_BudgetGroupInfo; + + float m_flHistoryRange; + float m_flBottomOfHistoryFraction; + CUtlVector<float> m_HistoryLabelValues; // A label will be placed at each of these values. + + // How much range the bar graph represents. + float m_flBarGraphRange; + + // Controls how many labels are shown. + float m_flTimeLabelInterval; + int m_nLinesPerTimeLabel; // How many vertical lines per time label? + + // How translucent is the background. + float m_flBackgroundAlpha; + + // Where to position it on the screen. + int m_xCoord; + int m_yCoord; + int m_Width; + int m_Height; +}; + + +class CBaseBudgetPanel : public vgui::Panel +{ + typedef vgui::Panel BaseClass; + +public: + CBaseBudgetPanel( vgui::Panel *pParent, const char *pElementName ); + ~CBaseBudgetPanel(); + + // This should be called when starting up and whenever this data changes. + void OnConfigDataChanged( const CBudgetPanelConfigData &data ); + + // Call this to reset everything. + virtual void ResetAll(); + + // The derived class should implement this and set the text in the time labels. + virtual void SetTimeLabelText() {} + virtual void SetHistoryLabelText() {} + + virtual void ApplySchemeSettings( vgui::IScheme *pScheme ); + virtual void Paint(); + virtual void PaintBackground(); + virtual void PerformLayout(); + void MarkAsDedicatedServer() { m_bDedicated = true; } // plays nicer as part of a vgui window setup + bool IsDedicated() const { return m_bDedicated; } + + const double *GetBudgetGroupData( int &nGroups, int &nSamplesPerGroup, int &nSampleOffset ) const; + + void GetGraphLabelScreenSpaceTopAndBottom( int id, int &top, int &bottom ); + + // What percentage is the specified value of the (bargraph) range? + float GetBudgetGroupPercent( float value ); + + // Get the current config data. + const CBudgetPanelConfigData& GetConfigData() const; + + // Returns the number of budget groups in the last OnConfigDataChanged call. + int GetNumCachedBudgetGroups() const; + + // (Used by dedicated server, mark everything for a repaint). + void MarkForFullRepaint(); + +protected: + void UpdateWindowGeometry(); + void ClearTimesForAllGroupsForThisFrame( void ); + void ClearAllTimesForGroup( int groupID ); + void Rebuild( const CBudgetPanelConfigData &data ); + +protected: + int m_BudgetHistoryOffset; + + // This defines all the positioning, label names, etc. + CBudgetPanelConfigData m_ConfigData; + + CUtlVector<vgui::Label *> m_GraphLabels; + CUtlVector<vgui::Label *> m_TimeLabels; + CUtlVector<vgui::Label *> m_HistoryLabels; + + CBudgetHistoryPanel *m_pBudgetHistoryPanel; + CBudgetBarGraphPanel *m_pBudgetBarGraphPanel; + + struct BudgetGroupTimeData_t + { + double m_Time[BUDGET_HISTORY_COUNT]; + }; + CUtlVector<BudgetGroupTimeData_t> m_BudgetGroupTimes; // [m_CachedNumBudgetGroups][BUDGET_HISTORY_COUNT] + int m_CachedNumTimeLabels; + vgui::HFont m_hFont; + + bool m_bDedicated; +}; + + +inline const CBudgetPanelConfigData& CBaseBudgetPanel::GetConfigData() const +{ + return m_ConfigData; +} + +inline int CBaseBudgetPanel::GetNumCachedBudgetGroups() const +{ + return m_ConfigData.m_BudgetGroupInfo.Count(); +} + + +#endif // VGUI_BASEBUDGETPANEL_H diff --git a/common/vgui/vgui_budgetbargraphpanel.cpp b/common/vgui/vgui_budgetbargraphpanel.cpp new file mode 100644 index 0000000..2db8fad --- /dev/null +++ b/common/vgui/vgui_budgetbargraphpanel.cpp @@ -0,0 +1,252 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//=============================================================================// + +#include "vgui_budgetbargraphpanel.h" +#include "vgui_basebudgetpanel.h" +#include <vgui/ISurface.h> +#include "vgui_controls/Label.h" +#include "convar.h" + +// memdbgon must be the last include file in a .cpp file!!! +#include "tier0/memdbgon.h" + +ConVar budget_bargraph_background_alpha( "budget_bargraph_background_alpha", "128", FCVAR_ARCHIVE, "how translucent the budget panel is" ); + +ConVar budget_peaks_window( "budget_peaks_window", "30", FCVAR_ARCHIVE, "number of frames to look at when figuring out peak frametimes" ); +ConVar budget_averages_window( "budget_averages_window", "30", FCVAR_ARCHIVE, "number of frames to look at when figuring out average frametimes" ); +ConVar budget_show_peaks( "budget_show_peaks", "1", FCVAR_ARCHIVE, "enable/disable peaks in the budget panel" ); +ConVar budget_show_averages( "budget_show_averages", "0", FCVAR_ARCHIVE, "enable/disable averages in the budget panel" ); + + +CBudgetBarGraphPanel::CBudgetBarGraphPanel( CBaseBudgetPanel *pParent, const char *pPanelName ) : + BaseClass( pParent, pPanelName ) +{ + m_pBudgetPanel = pParent; + + SetProportional( false ); + SetKeyBoardInputEnabled( false ); + SetMouseInputEnabled( false ); + SetVisible( true ); + + SetPaintBackgroundEnabled( true ); + SetBgColor( Color( 255, 0, 0, budget_bargraph_background_alpha.GetInt() ) ); +} + +CBudgetBarGraphPanel::~CBudgetBarGraphPanel() +{ +} + +void CBudgetBarGraphPanel::GetBudgetGroupTopAndBottom( int id, int &top, int &bottom ) +{ + // Ask where the corresponding graph label is. + m_pBudgetPanel->GetGraphLabelScreenSpaceTopAndBottom( id, top, bottom ); + int tall = bottom - top; + + int x = 0; + ScreenToLocal( x, top ); + + bottom = top + tall; +} + +void CBudgetBarGraphPanel::DrawBarAtIndex( int id, float percent ) +{ + int panelWidth, panelHeight; + GetSize( panelWidth, panelHeight ); + + int top, bottom; + GetBudgetGroupTopAndBottom( id, top, bottom ); + + int left = 0; + int right = panelWidth * percent; + + int red, green, blue, alpha; + m_pBudgetPanel->GetConfigData().m_BudgetGroupInfo[id].m_Color.GetColor( red, green, blue, alpha ); + + // DrawFilledRect is panel relative + vgui::surface()->DrawSetColor( 0, 0, 0, alpha ); + vgui::surface()->DrawFilledRect( left, top, right+2, bottom ); + + vgui::surface()->DrawSetColor( 255, 255, 255, alpha ); + vgui::surface()->DrawFilledRect( left, top+1, right+1, bottom-1 ); + + vgui::surface()->DrawSetColor( red, green, blue, alpha ); + vgui::surface()->DrawFilledRect( left, top+2, right, bottom-2 ); +} + +void CBudgetBarGraphPanel::DrawTickAtIndex( int id, float percent, int red, int green, int blue, int alpha ) +{ + if( percent > 1.0f ) + { + percent = 1.0f; + } + int panelWidth, panelHeight; + GetSize( panelWidth, panelHeight ); + + int top, bottom; + GetBudgetGroupTopAndBottom( id, top, bottom ); + + int right = ( int )( panelWidth * percent + 1.0f ); + int left = right - 2; + + // DrawFilledRect is panel relative + vgui::surface()->DrawSetColor( 0, 0, 0, alpha ); + vgui::surface()->DrawFilledRect( left-2, top, right+2, bottom ); + + vgui::surface()->DrawSetColor( 255, 255, 255, alpha ); + vgui::surface()->DrawFilledRect( left-1, top+1, right+1, bottom-1 ); + + vgui::surface()->DrawSetColor( red, green, blue, alpha ); + vgui::surface()->DrawFilledRect( left, top+2, right, bottom-2 ); +} + +void CBudgetBarGraphPanel::DrawTimeLines( void ) +{ + int panelWidth, panelHeight; + GetSize( panelWidth, panelHeight ); + int i; + int left, right, top, bottom; + top = 0; + bottom = panelHeight; + + const CBudgetPanelConfigData &config = m_pBudgetPanel->GetConfigData(); + + float flValueInterval = config.m_flTimeLabelInterval; + if ( config.m_nLinesPerTimeLabel != 0.0f ) + { + flValueInterval = config.m_flTimeLabelInterval / config.m_nLinesPerTimeLabel; + } + + int nTotalLines = config.m_flBarGraphRange; + if ( flValueInterval != 0.0f ) + { + nTotalLines /= flValueInterval; + } + nTotalLines += 2; + + for( i = 0; i < nTotalLines; i++ ) + { + int alpha; + if( i % (config.m_nLinesPerTimeLabel*2) == 0 ) + { + alpha = 150; + } + else if( i % config.m_nLinesPerTimeLabel == 0 ) + { + alpha = 100; + } + else + { + alpha = 50; + } + + float flTemp = ( config.m_flBarGraphRange != 0.0f ) ? ( flValueInterval / config.m_flBarGraphRange ) : flValueInterval; + left = -0.5f + panelWidth * ( float )( i * flTemp ); + right = left + 1; + + vgui::surface()->DrawSetColor( 0, 0, 0, alpha ); + vgui::surface()->DrawFilledRect( left-1, top, right+1, bottom ); + + vgui::surface()->DrawSetColor( 255, 255, 255, alpha ); + vgui::surface()->DrawFilledRect( left, top+1, right, bottom-1 ); + } +} + +void CBudgetBarGraphPanel::DrawInstantaneous() +{ + int nGroups, nSamplesPerGroup, nSampleOffset; + const double *pBudgetGroupTimes = m_pBudgetPanel->GetBudgetGroupData( nGroups, nSamplesPerGroup, nSampleOffset ); + if( !pBudgetGroupTimes ) + { + return; + } + + int i; + for( i = 0; i < nGroups; i++ ) + { + float percent = m_pBudgetPanel->GetBudgetGroupPercent( pBudgetGroupTimes[nSamplesPerGroup * i + nSampleOffset] ); + DrawBarAtIndex( i, percent ); + } +} + +void CBudgetBarGraphPanel::DrawPeaks() +{ + int nGroups, nSamplesPerGroup, nSampleOffset; + const double *pBudgetGroupTimes = m_pBudgetPanel->GetBudgetGroupData( nGroups, nSamplesPerGroup, nSampleOffset ); + if( !pBudgetGroupTimes ) + { + return; + } + int numSamples = budget_peaks_window.GetInt(); + int i; + for( i = 0; i < nGroups; i++ ) + { + double max = 0; + int j; + for( j = 0; j < numSamples; j++ ) + { + double tmp; + int offset = ( nSampleOffset - j + BUDGET_HISTORY_COUNT ) % BUDGET_HISTORY_COUNT; + tmp = pBudgetGroupTimes[i * nSamplesPerGroup + offset]; + if( tmp > max ) + { + max = tmp; + } + } + float percent = m_pBudgetPanel->GetBudgetGroupPercent( max ); + DrawTickAtIndex( i, percent, 255, 0, 0, 255 ); + } +} + +void CBudgetBarGraphPanel::DrawAverages() +{ + int nGroups, nSamplesPerGroup, nSampleOffset; + const double *pBudgetGroupTimes = m_pBudgetPanel->GetBudgetGroupData( nGroups, nSamplesPerGroup, nSampleOffset ); + if( !pBudgetGroupTimes ) + { + return; + } + int numSamples = budget_averages_window.GetInt(); + int i; + for( i = 0; i < nGroups; i++ ) + { + int red, green, blue, alpha; + m_pBudgetPanel->GetConfigData().m_BudgetGroupInfo[i].m_Color.GetColor( red, green, blue, alpha ); + + double sum = 0; + int j; + for( j = 0; j < numSamples; j++ ) + { + int offset = ( nSampleOffset - j + BUDGET_HISTORY_COUNT ) % BUDGET_HISTORY_COUNT; + sum += pBudgetGroupTimes[i * nSamplesPerGroup + offset]; + } + sum *= ( 1.0f / numSamples ); + float percent = m_pBudgetPanel->GetBudgetGroupPercent( sum ); + DrawTickAtIndex( i, percent, red, green, blue, alpha ); + } +} + +void CBudgetBarGraphPanel::Paint( void ) +{ + int width, height; + GetSize( width, height ); + + if ( !m_pBudgetPanel->IsDedicated() ) + { + SetBgColor( Color( 255, 0, 0, budget_bargraph_background_alpha.GetInt() ) ); + } + + DrawTimeLines(); + DrawInstantaneous(); + if( budget_show_peaks.GetBool() ) + { + DrawPeaks(); + } + if( budget_show_averages.GetBool() ) + { + DrawAverages(); + } +} + diff --git a/common/vgui/vgui_budgetbargraphpanel.h b/common/vgui/vgui_budgetbargraphpanel.h new file mode 100644 index 0000000..ef9da30 --- /dev/null +++ b/common/vgui/vgui_budgetbargraphpanel.h @@ -0,0 +1,43 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//=============================================================================// + +#ifndef VGUI_BUDGETBARGRAPHPANEL_H +#define VGUI_BUDGETBARGRAPHPANEL_H +#ifdef _WIN32 +#pragma once +#endif + +#include <vgui_controls/Frame.h> + + +class CBaseBudgetPanel; + + +class CBudgetBarGraphPanel : public vgui::Panel +{ + typedef vgui::Panel BaseClass; + +public: + CBudgetBarGraphPanel( CBaseBudgetPanel *pParent, const char *pPanelName ); + ~CBudgetBarGraphPanel(); + virtual void Paint( void ); + +private: + + void DrawInstantaneous(); + void DrawPeaks(); + void DrawAverages(); + void DrawTimeLines( void ); + void GetBudgetGroupTopAndBottom( int id, int &top, int &bottom ); + void DrawBarAtIndex( int id, float percent ); + void DrawTickAtIndex( int id, float percent, int red, int green, int blue, int alpha ); + +private: + + CBaseBudgetPanel *m_pBudgetPanel; +}; + +#endif // VGUI_BUDGETBARGRAPHPANEL_H diff --git a/common/vgui/vgui_budgethistorypanel.cpp b/common/vgui/vgui_budgethistorypanel.cpp new file mode 100644 index 0000000..e9b42fd --- /dev/null +++ b/common/vgui/vgui_budgethistorypanel.cpp @@ -0,0 +1,136 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//=============================================================================// + +#include "vgui_basebudgetpanel.h" +#include "vgui_budgethistorypanel.h" +#include <vgui/ISurface.h> +#include "tier0/vprof.h" +#include "convar.h" + +// memdbgon must be the last include file in a .cpp file!!! +#include "tier0/memdbgon.h" + +ConVar budget_show_history( "budget_show_history", "1", FCVAR_ARCHIVE, "turn history graph off and on. . good to turn off on low end" ); +ConVar budget_history_numsamplesvisible( "budget_history_numsamplesvisible", "100", FCVAR_ARCHIVE, "number of samples to draw in the budget history window. The lower the better as far as rendering overhead of the budget panel" ); + +CBudgetHistoryPanel::CBudgetHistoryPanel( CBaseBudgetPanel *pParent, const char *pPanelName ) : + BaseClass( pParent, pPanelName ) +{ + m_pBudgetPanel = pParent; + + m_nSamplesPerGroup = 0; + SetProportional( false ); + SetKeyBoardInputEnabled( false ); + SetMouseInputEnabled( false ); + SetVisible( true ); + SetPaintBackgroundEnabled( false ); + SetBgColor( Color( 0, 0, 0, 255 ) ); + + // For some reason, vgui::Frame likes to set the minimum size to (128,66) and we may want to get smaller. + SetMinimumSize( 0, 0 ); +} + +CBudgetHistoryPanel::~CBudgetHistoryPanel() +{ +} + +void CBudgetHistoryPanel::Paint() +{ + if( m_nSamplesPerGroup == 0 ) + { + // SetData hasn't been called yet. + return; + } + if( !budget_show_history.GetBool() ) + { + return; + } + + int width, height; + GetSize( width, height ); + + int startID = m_nSampleOffset - width; + while( startID < 0 ) + { + startID += m_nSamplesPerGroup; + } + int endID = startID + width; + int numSamplesVisible = budget_history_numsamplesvisible.GetInt(); + int xOffset = 0; + if( endID - startID > numSamplesVisible ) + { + xOffset = ( endID - numSamplesVisible ) - startID; + startID = endID - numSamplesVisible; + } + static CUtlVector<vgui::IntRect> s_Rects; + static CUtlVector<float> s_CurrentHeight; + s_Rects.EnsureCount( ( endID - startID ) ); + s_CurrentHeight.EnsureCount( endID - startID ); + memset( &s_CurrentHeight[0], 0, sizeof( float ) * ( endID - startID ) ); + int j; + float ooRangeMaxMinusMin = 1.0f / ( m_fRangeMax - m_fRangeMin ); + for( j = 0; j < m_nGroups; j++ ) + { + int i; + for( i = startID; i < endID; i++ ) + { + int sampleOffset = i % m_nSamplesPerGroup; + int left = i - startID + xOffset; + int right = left + 1; + float &curHeight = s_CurrentHeight[i - startID]; + int bottom = ( curHeight - m_fRangeMin ) * ooRangeMaxMinusMin * height; + curHeight += m_pData[sampleOffset + m_nSamplesPerGroup * j]; + int top = ( curHeight - m_fRangeMin ) * ooRangeMaxMinusMin * height; + bottom = height - bottom - 1; + top = height - top - 1; + vgui::IntRect& rect = s_Rects[( i - startID )]; + rect.x0 = left; + rect.x1 = right; + rect.y0 = top; + rect.y1 = bottom; + } + + int red, green, blue, alpha; + m_pBudgetPanel->GetConfigData().m_BudgetGroupInfo[j].m_Color.GetColor( red, green, blue, alpha ); + + vgui::surface()->DrawSetColor( red, green, blue, alpha ); + vgui::surface()->DrawFilledRectArray( &s_Rects[0], endID - startID ); + } + + for ( int i=0; i < m_pBudgetPanel->GetConfigData().m_HistoryLabelValues.Count(); i++ ) + { + DrawBudgetLine( m_pBudgetPanel->GetConfigData().m_HistoryLabelValues[i] ); + } +} + +// Only call this from Paint!!!!! +void CBudgetHistoryPanel::DrawBudgetLine( float val ) +{ + int width, height; + GetSize( width, height ); + double y = ( val - m_fRangeMin ) * ( 1.0f / ( m_fRangeMax - m_fRangeMin ) ) * height; + int bottom = ( int )( height - y - 1 + .5 ); + int top = ( int )( height - y - 1 - .5 ); + vgui::surface()->DrawSetColor( 0, 0, 0, 255 ); + vgui::surface()->DrawFilledRect( 0, top-1, width, bottom+1 ); + vgui::surface()->DrawSetColor( 255, 255, 255, 255 ); + vgui::surface()->DrawFilledRect( 0, top, width, bottom ); +} + + +void CBudgetHistoryPanel::SetData( double *pData, int nGroups, int nSamplesPerGroup, int nSampleOffset ) +{ + m_pData = pData; + m_nGroups = nGroups; + m_nSamplesPerGroup = nSamplesPerGroup; + m_nSampleOffset = nSampleOffset; +} + +void CBudgetHistoryPanel::SetRange( float fMin, float fMax ) +{ + m_fRangeMin = fMin; + m_fRangeMax = fMax; +} diff --git a/common/vgui/vgui_budgethistorypanel.h b/common/vgui/vgui_budgethistorypanel.h new file mode 100644 index 0000000..0436362 --- /dev/null +++ b/common/vgui/vgui_budgethistorypanel.h @@ -0,0 +1,48 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//=============================================================================// + +#ifndef VGUI_BudgetHistoryPanel_H +#define VGUI_BudgetHistoryPanel_H +#ifdef _WIN32 +#pragma once +#endif + +#include <vgui_controls/Frame.h> + +class CBaseBudgetPanel; + +class CBudgetHistoryPanel : public vgui::Panel +{ + typedef vgui::Panel BaseClass; + +public: + CBudgetHistoryPanel( CBaseBudgetPanel *pParent, const char *pPanelName ); + ~CBudgetHistoryPanel(); + void SetData( double *pData, int numCategories, int numItems, int offsetIntoData ); + void SetRange( float fMin, float fMax ); + + +protected: + + void Paint(); + +private: + + void DrawBudgetLine( float val ); + +private: + + CBaseBudgetPanel *m_pBudgetPanel; + + double *m_pData; + int m_nGroups; + int m_nSamplesPerGroup; + int m_nSampleOffset; + float m_fRangeMin; + float m_fRangeMax; +}; + +#endif // VGUI_BudgetHistoryPanel_H diff --git a/common/vgui/vgui_budgetpanelshared.cpp b/common/vgui/vgui_budgetpanelshared.cpp new file mode 100644 index 0000000..0cc075a --- /dev/null +++ b/common/vgui/vgui_budgetpanelshared.cpp @@ -0,0 +1,263 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//=============================================================================// + +#include "vgui_budgetpanelshared.h" +#include "vgui/IVGui.h" +#include "vgui/ILocalize.h" +#include "vgui/ISurface.h" +#include "vgui_controls/Label.h" +#include "ivprofexport.h" +#include "convar.h" +#include "mathlib/mathlib.h" + +// NOTE: This has to be the last file included! +#include "tier0/memdbgon.h" + + +#ifdef VPROF_ENABLED + +#ifdef BUDGET_ADMIN_SERVER + #define BUDGET_CVAR_CALLBACK NULL +#else + #define BUDGET_CVAR_CALLBACK PanelGeometryChangedCallBack +#endif + + +// Global ConVars. +ConVar budget_history_range_ms( "budget_history_range_ms", "66.666666667", FCVAR_ARCHIVE, "budget history range in milliseconds", BUDGET_CVAR_CALLBACK ); +ConVar budget_panel_bottom_of_history_fraction( "budget_panel_bottom_of_history_fraction", ".25", FCVAR_ARCHIVE, "number between 0 and 1", BUDGET_CVAR_CALLBACK ); +ConVar budget_bargraph_range_ms( "budget_bargraph_range_ms", "16.6666666667", FCVAR_ARCHIVE, "budget bargraph range in milliseconds", BUDGET_CVAR_CALLBACK ); +ConVar budget_background_alpha( "budget_background_alpha", "128", FCVAR_ARCHIVE, "how translucent the budget panel is" ); + +ConVar budget_panel_x( "budget_panel_x", "0", FCVAR_ARCHIVE, "number of pixels from the left side of the game screen to draw the budget panel", BUDGET_CVAR_CALLBACK ); +ConVar budget_panel_y( "budget_panel_y", "50", FCVAR_ARCHIVE, "number of pixels from the top side of the game screen to draw the budget panel", BUDGET_CVAR_CALLBACK ); +ConVar budget_panel_width( "budget_panel_width", "512", FCVAR_ARCHIVE, "width in pixels of the budget panel", BUDGET_CVAR_CALLBACK ); +ConVar budget_panel_height( "budget_panel_height", "384", FCVAR_ARCHIVE, "height in pixels of the budget panel", BUDGET_CVAR_CALLBACK ); + + +static CUtlVector<IVProfExport::CExportedBudgetGroupInfo> g_TempBudgetGroupSpace; + + +double CBudgetPanelShared::g_fFrameTimeLessBudget = 0; +double CBudgetPanelShared::g_fFrameRate = 0; + +static CFastTimer g_TimerLessBudget; +static CBudgetPanelShared *g_pBudgetPanelShared = NULL; +extern IVProfExport *g_pVProfExport; + + +void PanelGeometryChangedCallBack( IConVar *var, const char *pOldString, float flOldValue ) +{ + // screw it . . rebuild the whole damn thing. + // GetBudgetPanel()->InvalidateLayout(); + if ( g_pBudgetPanelShared ) + { + g_pBudgetPanelShared->SendConfigDataToBase(); + } +} + + +// -------------------------------------------------------------------------------------------------------------------- // +// CBudgetPanelShared implementation. +// -------------------------------------------------------------------------------------------------------------------- // + +CBudgetPanelShared::CBudgetPanelShared( vgui::Panel *pParent, const char *pElementName, int budgetFlagsFilter ) + : BaseClass( pParent, pElementName ) +{ + Assert( !g_pBudgetPanelShared ); + g_pBudgetPanelShared = this; + + if ( g_pVProfExport ) + g_pVProfExport->SetBudgetFlagsFilter( budgetFlagsFilter ); + + SendConfigDataToBase(); + SetZPos( 1001 ); + SetVisible( false ); + vgui::ivgui()->AddTickSignal( GetVPanel() ); + SetPostChildPaintEnabled( true ); // so we can turn vprof back on +} + + +CBudgetPanelShared::~CBudgetPanelShared() +{ + Assert( g_pBudgetPanelShared == this ); + g_pBudgetPanelShared = NULL; +} + + +void CBudgetPanelShared::OnNumBudgetGroupsChanged() +{ + SendConfigDataToBase(); +} + + +void CBudgetPanelShared::SetupCustomConfigData( CBudgetPanelConfigData &data ) +{ + data.m_xCoord = budget_panel_x.GetInt(); + data.m_yCoord = budget_panel_y.GetInt(); + data.m_Width = budget_panel_width.GetInt(); + data.m_Height = budget_panel_height.GetInt(); +} + + +void CBudgetPanelShared::SendConfigDataToBase() +{ + // Setup all the data. + CBudgetPanelConfigData data; + + // Copy the budget group names in. + int nGroups = 0; + if ( g_pVProfExport ) + { + nGroups = g_pVProfExport->GetNumBudgetGroups(); + + // Make sure we have space to store the results. + if ( g_TempBudgetGroupSpace.Count() < nGroups ) + g_TempBudgetGroupSpace.SetSize( nGroups ); + + g_pVProfExport->GetBudgetGroupInfos( g_TempBudgetGroupSpace.Base() ); + } + + data.m_BudgetGroupInfo.SetSize( nGroups ); + for ( int i=0; i < nGroups; i++ ) + { + data.m_BudgetGroupInfo[i].m_Name = g_TempBudgetGroupSpace[i].m_pName; + data.m_BudgetGroupInfo[i].m_Color = g_TempBudgetGroupSpace[i].m_Color; + } + + data.m_HistoryLabelValues.AddToTail( 1000.0 / 20 ); + data.m_HistoryLabelValues.AddToTail( 1000.0 / 30 ); + data.m_HistoryLabelValues.AddToTail( 1000.0 / 60 ); + + // Copy all the cvars in. + data.m_flHistoryRange = budget_history_range_ms.GetFloat(); + data.m_flBottomOfHistoryFraction = budget_panel_bottom_of_history_fraction.GetFloat(); + + data.m_flBarGraphRange = budget_bargraph_range_ms.GetFloat(); + data.m_flTimeLabelInterval = 5; + data.m_nLinesPerTimeLabel = 5; + + data.m_flBackgroundAlpha = budget_background_alpha.GetFloat(); + + SetupCustomConfigData( data ); + + // Send the config data to the base class. + OnConfigDataChanged( data ); +} + + +void CBudgetPanelShared::DrawColoredText( + vgui::HFont font, + int x, int y, + int r, int g, int b, int a, + const char *pText, + ... ) +{ + char msg[4096]; + va_list marker; + va_start( marker, pText ); + _vsnprintf( msg, sizeof( msg ), pText, marker ); + va_end( marker ); + + wchar_t unicodeStr[4096]; + int nChars = g_pVGuiLocalize->ConvertANSIToUnicode( msg, unicodeStr, sizeof( unicodeStr ) ); + + vgui::surface()->DrawSetTextFont( font ); + vgui::surface()->DrawSetTextColor( r, g, b, a ); + vgui::surface()->DrawSetTextPos( x, y ); + vgui::surface()->DrawPrintText( unicodeStr, nChars ); +} + + +void CBudgetPanelShared::PaintBackground() +{ + if ( g_pVProfExport ) + g_pVProfExport->PauseProfile(); + + BaseClass::PaintBackground(); +} + + +void CBudgetPanelShared::Paint() +{ + if( m_BudgetGroupTimes.Count() == 0 ) + { + return; + } + + static bool TimerInitialized = false; + if( !TimerInitialized ) + { + g_TimerLessBudget.Start(); + TimerInitialized=true; + } + + g_TimerLessBudget.End(); + + BaseClass::Paint(); + + g_fFrameTimeLessBudget = ( g_TimerLessBudget.GetDuration().GetSeconds() ); + g_fFrameRate = 1.0 / g_fFrameTimeLessBudget; +} + +void CBudgetPanelShared::PostChildPaint() +{ + g_TimerLessBudget.Start(); + + if ( g_pVProfExport ) + g_pVProfExport->ResumeProfile(); +} + +void CBudgetPanelShared::SnapshotVProfHistory( float filteredtime ) +{ + m_BudgetHistoryOffset = ( m_BudgetHistoryOffset + 1 ) % BUDGET_HISTORY_COUNT; + ClearTimesForAllGroupsForThisFrame(); + + if ( g_pVProfExport ) + { + if ( GetNumCachedBudgetGroups() != g_pVProfExport->GetNumBudgetGroups() ) + { + SendConfigDataToBase(); + } + + float times[IVProfExport::MAX_BUDGETGROUP_TIMES]; + g_pVProfExport->GetBudgetGroupTimes( times ); + + for ( int groupID=0; groupID < GetNumCachedBudgetGroups(); groupID++ ) + { + float dt = times[groupID]; + // Hack: add filtered time into unnaccounted group... + if ( groupID == VPROF_BUDGET_GROUP_ID_UNACCOUNTED ) + { + dt += 1000.0f * filteredtime; + } + m_BudgetGroupTimes[groupID].m_Time[m_BudgetHistoryOffset] = dt; + } + } +} + + +void CBudgetPanelShared::SetTimeLabelText() +{ + for ( int i=0; i < m_TimeLabels.Count(); i++ ) + { + char text[512]; + Q_snprintf( text, sizeof( text ), "%dms", (int)( i * GetConfigData().m_flTimeLabelInterval ) ); + m_TimeLabels[i]->SetText( text ); + } +} + + +void CBudgetPanelShared::SetHistoryLabelText() +{ + Assert( m_HistoryLabels.Count() == 3 ); + m_HistoryLabels[0]->SetText( "20 fps (50 ms)" ); + m_HistoryLabels[1]->SetText( "30 fps (33 1/3 ms)" ); + m_HistoryLabels[2]->SetText( "60 fps (16 2/3 ms)" ); +} + + +#endif // VPROF_ENABLED diff --git a/common/vgui/vgui_budgetpanelshared.h b/common/vgui/vgui_budgetpanelshared.h new file mode 100644 index 0000000..5713604 --- /dev/null +++ b/common/vgui/vgui_budgetpanelshared.h @@ -0,0 +1,71 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//===========================================================================// + +#ifndef VGUI_BUDGETPANELSHARED_H +#define VGUI_BUDGETPANELSHARED_H + +#ifdef _WIN32 +#pragma once +#endif + + +#include "vgui_basebudgetpanel.h" + + +class IConVar; + + +// Shared between the engine and dedicated server. +class CBudgetPanelShared : public CBaseBudgetPanel +{ + typedef CBaseBudgetPanel BaseClass; + +public: + + // budgetFlagsFilter is a combination of BUDGETFLAG_ defines that filters out which budget groups we are interested in. + CBudgetPanelShared( vgui::Panel *pParent, const char *pElementName, int budgetFlagsFilter ); + ~CBudgetPanelShared(); + + // Override this to set the window position. + virtual void SetupCustomConfigData( CBudgetPanelConfigData &data ); + + virtual void SetTimeLabelText(); + virtual void SetHistoryLabelText(); + + virtual void PaintBackground(); + virtual void Paint( void ); + virtual void PostChildPaint(); + + virtual void SnapshotVProfHistory( float filteredtime ); + + // Command handlers + void OnNumBudgetGroupsChanged( void ); + + void SendConfigDataToBase(); + + +public: + + static double g_fFrameTimeLessBudget; + static double g_fFrameRate; + + +private: + + void DrawColoredText( + vgui::HFont font, + int x, int y, + int r, int g, int b, int a, + PRINTF_FORMAT_STRING const char *pText, + ... ) FMTFUNCTION( 9, 10 ); +}; + + +// CVars that change the layout can hook this. +void PanelGeometryChangedCallBack( IConVar *var, const char *pOldString, float flOldValue ); + + +#endif // VGUI_BUDGETPANELSHARED_H |