4040
4141#define DEFINE_PARTICLE_SYSTEM_NAMES
4242#include " GameClient/ParticleSys.h"
43- #include " GameClient/Shell .h"
43+ #include " GameLogic/GameLogic .h"
4444
4545
4646#define PROFILE_ERROR_LIMIT 0 .94f // fraction of profiled result needed to get a match. Allows some room for error/fluctuation.
@@ -232,14 +232,10 @@ GameLODManager::GameLODManager()
232232 m_numBenchProfiles=0 ;
233233 m_reallyLowMHz = 400 ;
234234#if defined(GENERALS_ONLINE_HIGH_FPS_SERVER)
235- m_userGraphSnapshotTaken = false ;
236- m_userShadowVolumesEnabled = true ;
237- m_userShadowDecalsEnabled = true ;
238- m_userHeatEffectsEnabled = true ;
239235 m_isQualityReduced = false ;
240- m_stableFPSDuration = 0 ;
241236 m_lowFPSSecondsCount = 0 ;
242- m_userDynamicLOD = DYNAMIC_GAME_LOD_VERY_HIGH ;
237+ m_stableFPSSecondsCount = 0 ;
238+ m_userMaxParticleCount = 0 ;
243239#endif
244240
245241 for (Int i=0 ; i<STATIC_GAME_LOD_CUSTOM ; i++)
@@ -782,50 +778,41 @@ Bool GameLODManager::didMemPass()
782778#if defined(GENERALS_ONLINE_HIGH_FPS_SERVER)
783779void GameLODManager::updateGraphicsQualityState (float averageFPS)
784780{
785- if (!m_userGraphSnapshotTaken)
786- {
787- m_userShadowVolumesEnabled = TheGlobalData->m_useShadowVolumes ;
788- m_userShadowDecalsEnabled = TheGlobalData->m_useShadowDecals ;
789- m_userHeatEffectsEnabled = TheGlobalData->m_useHeatEffects ;
790- m_userDynamicLOD = m_currentDynamicLOD;
791- m_userGraphSnapshotTaken = true ;
792- }
781+ if (!TheGameLogic || (TheGameLogic->getFrame () % LOGICFRAMES_PER_SECOND ) != 0 )
782+ return ;
793783
794- if (m_isQualityReduced && TheGameClient && TheGameClient ->getFrame () <= 1 )
784+ if (TheGameLogic-> isInShellGame () || TheGameLogic-> isInReplayGame () || (TheGameLogic ->getFrame () < LOGICFRAMES_PER_SECOND ) )
795785 {
796- TheWritableGlobalData->m_useShadowVolumes = m_userShadowVolumesEnabled;
797- TheWritableGlobalData->m_useShadowDecals = m_userShadowDecalsEnabled;
798- TheWritableGlobalData->m_useHeatEffects = m_userHeatEffectsEnabled;
799- setDynamicLODLevel (m_userDynamicLOD);
800- if (TheGameClient)
801- TheGameClient->allocateShadows ();
802- m_isQualityReduced = false ;
803- m_stableFPSDuration = 0 ;
786+ if (m_isQualityReduced)
787+ restoreQualitySettings ();
788+ return ;
804789 }
805790
806791 if (!m_isQualityReduced)
807792 {
808793 m_userShadowVolumesEnabled = TheGlobalData->m_useShadowVolumes ;
809794 m_userShadowDecalsEnabled = TheGlobalData->m_useShadowDecals ;
810795 m_userHeatEffectsEnabled = TheGlobalData->m_useHeatEffects ;
811- m_userDynamicLOD = m_currentDynamicLOD ;
796+ m_userMaxParticleCount = TheGlobalData-> m_maxParticleCount ;
812797 }
813798
814- if (averageFPS < 56 .0f )
815- m_lowFPSSecondsCount++, m_stableFPSDuration = 0 ;
816- else if (averageFPS > 57 .0f )
817- m_stableFPSDuration++, m_lowFPSSecondsCount = 0 ;
799+ // Track how many consecutive seconds FPS is below or above threshold.
800+ const float minAcceptedFPS = 58 .f ;
801+ if (averageFPS < minAcceptedFPS)
802+ {
803+ m_lowFPSSecondsCount++;
804+ m_stableFPSSecondsCount = 0 ;
805+ }
806+ else
807+ {
808+ m_stableFPSSecondsCount++;
809+ m_lowFPSSecondsCount = 0 ;
810+ }
818811
819- bool shouldReduceQuality = (m_lowFPSSecondsCount >= 2 && TheGameClient && TheGameClient->getFrame () > LOGICFRAMES_PER_SECOND * 10 && !TheShell->isShellActive ());
812+ bool isInGame = TheGameLogic->isInGame ();
813+ bool shouldReduceQuality = (m_lowFPSSecondsCount >= 2 && isInGame);
820814 if (shouldReduceQuality && !m_isQualityReduced)
821815 {
822- if (averageFPS < 56 .0f )
823- m_dynamicGameLODInfo[DYNAMIC_GAME_LOD_LOW ].m_minDynamicParticlePriority = WEAPON_TRAIL ;
824- if (averageFPS < 40 .0f )
825- m_dynamicGameLODInfo[DYNAMIC_GAME_LOD_LOW ].m_minDynamicParticlePriority = ALWAYS_RENDER ;
826-
827-
828- setDynamicLODLevel (DYNAMIC_GAME_LOD_LOW );
829816 TheGameClient->releaseShadows ();
830817 TheWritableGlobalData->m_useShadowVolumes = false ;
831818 TheWritableGlobalData->m_useShadowDecals = false ;
@@ -834,24 +821,40 @@ void GameLODManager::updateGraphicsQualityState(float averageFPS)
834821 m_lowFPSSecondsCount = 0 ;
835822 }
836823
837- // Restore to user preferences after sustained good performance
838- else if (!shouldReduceQuality && m_isQualityReduced)
824+
825+ if (m_isQualityReduced)
839826 {
840- if (m_stableFPSDuration > 15 )
841- {
842- TheWritableGlobalData->m_useShadowVolumes = m_userShadowVolumesEnabled;
843- TheWritableGlobalData->m_useShadowDecals = m_userShadowDecalsEnabled;
844- TheWritableGlobalData->m_useHeatEffects = m_userHeatEffectsEnabled;
827+ float particleReductionFactor = max (0 .f , min (1 .f , (minAcceptedFPS - averageFPS) / minAcceptedFPS * 5 .f ));
828+ int targetCount = max (100 , (int )(m_userMaxParticleCount * (1 .f - particleReductionFactor)));
829+ int current = TheGlobalData->m_maxParticleCount ;
845830
846- if (TheGameClient)
847- TheGameClient->allocateShadows ();
831+ if (targetCount < current)
832+ TheWritableGlobalData->m_maxParticleCount = max (100 , current + (int )((targetCount - current) * 0 .5f ));
833+
834+ if (!shouldReduceQuality && m_stableFPSSecondsCount > 15 )
835+ {
836+ int newCount = current + (int )((m_userMaxParticleCount - current) * 0 .3f );
837+ if (newCount >= m_userMaxParticleCount || newCount == current)
838+ restoreQualitySettings ();
839+ else
840+ TheWritableGlobalData->m_maxParticleCount = newCount;
848841
849842 DynamicGameLODLevel lod = TheGameLODManager->findDynamicLODLevel (averageFPS);
850843 TheGameLODManager->setDynamicLODLevel (lod);
851-
852- m_isQualityReduced = false ;
853- m_stableFPSDuration = 0 ;
854844 }
855845 }
856846}
847+
848+ void GameLODManager::restoreQualitySettings ()
849+ {
850+ TheWritableGlobalData->m_useShadowVolumes = m_userShadowVolumesEnabled;
851+ TheWritableGlobalData->m_useShadowDecals = m_userShadowDecalsEnabled;
852+ TheWritableGlobalData->m_useHeatEffects = m_userHeatEffectsEnabled;
853+ TheWritableGlobalData->m_maxParticleCount = m_userMaxParticleCount;
854+ m_stableFPSSecondsCount = 0 ;
855+ m_lowFPSSecondsCount = 0 ;
856+ m_isQualityReduced = false ;
857+ if (TheGameClient)
858+ TheGameClient->allocateShadows ();
859+ }
857860#endif // GENERALS_ONLINE_HIGH_FPS_SERVER
0 commit comments