summaryrefslogtreecommitdiff
path: root/gameui/OptionsSubAudio.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'gameui/OptionsSubAudio.cpp')
-rw-r--r--gameui/OptionsSubAudio.cpp432
1 files changed, 432 insertions, 0 deletions
diff --git a/gameui/OptionsSubAudio.cpp b/gameui/OptionsSubAudio.cpp
new file mode 100644
index 0000000..9a4d6ae
--- /dev/null
+++ b/gameui/OptionsSubAudio.cpp
@@ -0,0 +1,432 @@
+//========= Copyright Valve Corporation, All rights reserved. ============//
+//
+// Purpose:
+//
+//=============================================================================//
+
+#include "OptionsSubAudio.h"
+
+#include "cvarslider.h"
+#include "EngineInterface.h"
+#include "ModInfo.h"
+#include "vgui_controls/ComboBox.h"
+#include "vgui_controls/QueryBox.h"
+#include "CvarToggleCheckButton.h"
+#include "tier1/KeyValues.h"
+#include "tier1/convar.h"
+#include <vgui/IInput.h>
+#include <steam/steam_api.h>
+#include <tier1/strtools.h>
+
+
+// memdbgon must be the last include file in a .cpp file!!!
+#include "tier0/memdbgon.h"
+
+using namespace vgui;
+
+// This member is static so that the updated audio language can be referenced during shutdown
+char* COptionsSubAudio::m_pchUpdatedAudioLanguage = (char*)GetLanguageShortName( k_Lang_English );
+
+enum SoundQuality_e
+{
+ SOUNDQUALITY_LOW,
+ SOUNDQUALITY_MEDIUM,
+ SOUNDQUALITY_HIGH,
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: Constructor
+//-----------------------------------------------------------------------------
+COptionsSubAudio::COptionsSubAudio(vgui::Panel *parent) : PropertyPage(parent, NULL)
+{
+ m_pSFXSlider = new CCvarSlider( this, "SFXSlider", "#GameUI_SoundEffectVolume", 0.0f, 1.0f, "volume" );
+ m_pMusicSlider = new CCvarSlider( this, "MusicSlider", "#GameUI_MusicVolume", 0.0f, 1.0f, "Snd_MusicVolume" );
+
+ m_pCloseCaptionCombo = new ComboBox( this, "CloseCaptionCheck", 6, false );
+ m_pCloseCaptionCombo->AddItem( "#GameUI_NoClosedCaptions", NULL );
+ m_pCloseCaptionCombo->AddItem( "#GameUI_SubtitlesAndSoundEffects", NULL );
+ m_pCloseCaptionCombo->AddItem( "#GameUI_Subtitles", NULL );
+
+ m_pSoundQualityCombo = new ComboBox( this, "SoundQuality", 6, false );
+ m_pSoundQualityCombo->AddItem( "#GameUI_High", new KeyValues("SoundQuality", "quality", SOUNDQUALITY_HIGH) );
+ m_pSoundQualityCombo->AddItem( "#GameUI_Medium", new KeyValues("SoundQuality", "quality", SOUNDQUALITY_MEDIUM) );
+ m_pSoundQualityCombo->AddItem( "#GameUI_Low", new KeyValues("SoundQuality", "quality", SOUNDQUALITY_LOW) );
+
+ m_pSpeakerSetupCombo = new ComboBox( this, "SpeakerSetup", 6, false );
+#ifndef POSIX
+ m_pSpeakerSetupCombo->AddItem( "#GameUI_Headphones", new KeyValues("SpeakerSetup", "speakers", 0) );
+#endif
+ m_pSpeakerSetupCombo->AddItem( "#GameUI_2Speakers", new KeyValues("SpeakerSetup", "speakers", 2) );
+#ifndef POSIX
+ m_pSpeakerSetupCombo->AddItem( "#GameUI_4Speakers", new KeyValues("SpeakerSetup", "speakers", 4) );
+ m_pSpeakerSetupCombo->AddItem( "#GameUI_5Speakers", new KeyValues("SpeakerSetup", "speakers", 5) );
+ m_pSpeakerSetupCombo->AddItem( "#GameUI_7Speakers", new KeyValues("SpeakerSetup", "speakers", 7) );
+#endif
+ m_pSpokenLanguageCombo = new ComboBox (this, "AudioSpokenLanguage", 6, false );
+
+ m_pSoundMuteLoseFocusCheckButton = new CCvarToggleCheckButton( this, "snd_mute_losefocus", "#GameUI_SndMuteLoseFocus", "snd_mute_losefocus" );
+
+ LoadControlSettings("Resource\\OptionsSubAudio.res");
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Destructor
+//-----------------------------------------------------------------------------
+COptionsSubAudio::~COptionsSubAudio()
+{
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Reloads data
+//-----------------------------------------------------------------------------
+void COptionsSubAudio::OnResetData()
+{
+ m_bRequireRestart = false;
+ m_pSFXSlider->Reset();
+ m_pMusicSlider->Reset();
+
+
+ // reset the combo boxes
+
+ // close captions
+ ConVarRef closecaption("closecaption");
+ ConVarRef cc_subtitles("cc_subtitles");
+ if (closecaption.GetBool())
+ {
+ if (cc_subtitles.GetBool())
+ {
+ m_pCloseCaptionCombo->ActivateItem(2);
+ }
+ else
+ {
+ m_pCloseCaptionCombo->ActivateItem(1);
+ }
+ }
+ else
+ {
+ m_pCloseCaptionCombo->ActivateItem(0);
+ }
+
+ // speakers
+ ConVarRef snd_surround_speakers("Snd_Surround_Speakers");
+ int speakers = snd_surround_speakers.GetInt();
+
+#ifdef POSIX
+ // On Posix there is no headphone option, so we upgrade to 2 speakers if Snd_Surround_Speakers == 0
+ if ( speakers == 0 )
+ speakers = 2;
+#endif
+
+ // if Snd_Surround_Speakers is -1, then upgrade to 2 speakers
+ if ( speakers < 0 )
+ speakers = 2;
+
+ {for (int itemID = 0; itemID < m_pSpeakerSetupCombo->GetItemCount(); itemID++)
+ {
+ KeyValues *kv = m_pSpeakerSetupCombo->GetItemUserData( itemID );
+ if (kv && kv->GetInt( "speakers" ) == speakers)
+ {
+ m_pSpeakerSetupCombo->ActivateItem( itemID );
+ break;
+ }
+ }}
+
+ // sound quality is made up from several cvars
+ ConVarRef Snd_PitchQuality("Snd_PitchQuality");
+ ConVarRef dsp_slow_cpu("dsp_slow_cpu");
+ int quality = SOUNDQUALITY_LOW;
+ if (dsp_slow_cpu.GetBool() == false)
+ {
+ quality = SOUNDQUALITY_MEDIUM;
+ }
+ if (Snd_PitchQuality.GetBool())
+ {
+ quality = SOUNDQUALITY_HIGH;
+ }
+ // find the item in the list and activate it
+ {for (int itemID = 0; itemID < m_pSoundQualityCombo->GetItemCount(); itemID++)
+ {
+ KeyValues *kv = m_pSoundQualityCombo->GetItemUserData(itemID);
+ if (kv && kv->GetInt("quality") == quality)
+ {
+ m_pSoundQualityCombo->ActivateItem(itemID);
+ }
+ }}
+
+ //
+ // Audio Languages
+ //
+ char szCurrentLanguage[50];
+ char szAvailableLanguages[512];
+ szCurrentLanguage[0] = 0;
+ szAvailableLanguages[0] = 0;
+
+ // Fallback to current engine language
+ engine->GetUILanguage( szCurrentLanguage, sizeof( szCurrentLanguage ));
+
+ // In a Steam environment we get the current language
+#if !defined( NO_STEAM )
+ // When Steam isn't running we can't get the language info...
+ if ( steamapicontext->SteamApps() )
+ {
+ Q_strncpy( szCurrentLanguage, steamapicontext->SteamApps()->GetCurrentGameLanguage(), sizeof(szCurrentLanguage) );
+ Q_strncpy( szAvailableLanguages, steamapicontext->SteamApps()->GetAvailableGameLanguages(), sizeof(szAvailableLanguages) );
+ }
+#endif
+
+ // Get the spoken language and store it for comparison purposes
+ m_nCurrentAudioLanguage = PchLanguageToELanguage( szCurrentLanguage );
+
+ // Check to see if we have a list of languages from Steam
+ if ( V_strlen( szAvailableLanguages ) )
+ {
+ // Populate the combo box with each available language
+ CUtlVector<char*> languagesList;
+ V_SplitString( szAvailableLanguages, ",", languagesList );
+
+ for ( int i=0; i < languagesList.Count(); i++ )
+ {
+ const ELanguage languageCode = PchLanguageToELanguage( languagesList[i] );
+ m_pSpokenLanguageCombo->AddItem( GetLanguageVGUILocalization( languageCode ), new KeyValues ("Audio Languages", "language", languageCode) );
+ }
+
+ languagesList.PurgeAndDeleteElements();
+ }
+ else
+ {
+ // Add the current language to the combo
+ m_pSpokenLanguageCombo->AddItem( GetLanguageVGUILocalization( m_nCurrentAudioLanguage ), new KeyValues ("Audio Languages", "language", m_nCurrentAudioLanguage) );
+ }
+
+ // Activate the current language in the combo
+ {for (int itemID = 0; itemID < m_pSpokenLanguageCombo->GetItemCount(); itemID++)
+ {
+ KeyValues *kv = m_pSpokenLanguageCombo->GetItemUserData( itemID );
+ if ( kv && kv->GetInt( "language" ) == m_nCurrentAudioLanguage )
+ {
+ m_pSpokenLanguageCombo->ActivateItem( itemID );
+ break;
+ }
+ }}
+
+ m_pSoundMuteLoseFocusCheckButton->Reset();
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Applies changes
+//-----------------------------------------------------------------------------
+void COptionsSubAudio::OnApplyChanges()
+{
+ m_pSFXSlider->ApplyChanges();
+ m_pMusicSlider->ApplyChanges();
+
+ // set the cvars appropriately
+ // Tracker 28933: Note we can't do this because closecaption is marked
+ // FCVAR_USERINFO and it won't get sent to server is we direct set it, we
+ // need to pass it along to the engine parser!!!
+ // ConVar *closecaption = (ConVar *)cvar->FindVar("closecaption");
+ int closecaption_value = 0;
+
+ ConVarRef cc_subtitles( "cc_subtitles" );
+ switch (m_pCloseCaptionCombo->GetActiveItem())
+ {
+ default:
+ case 0:
+ closecaption_value = 0;
+ cc_subtitles.SetValue( 0 );
+ break;
+ case 1:
+ closecaption_value = 1;
+ cc_subtitles.SetValue( 0 );
+ break;
+ case 2:
+ closecaption_value = 1;
+ cc_subtitles.SetValue( 1 );
+ break;
+ }
+
+ // Stuff the close caption change to the console so that it can be
+ // sent to the server (FCVAR_USERINFO) so that you don't have to restart
+ // the level for the change to take effect.
+ char cmd[ 64 ];
+ Q_snprintf( cmd, sizeof( cmd ), "closecaption %i\n", closecaption_value );
+ engine->ClientCmd_Unrestricted( cmd );
+
+ ConVarRef snd_surround_speakers( "Snd_Surround_Speakers" );
+ int speakers = m_pSpeakerSetupCombo->GetActiveItemUserData()->GetInt( "speakers" );
+ snd_surround_speakers.SetValue( speakers );
+
+ // quality
+ ConVarRef Snd_PitchQuality( "Snd_PitchQuality" );
+ ConVarRef dsp_slow_cpu( "dsp_slow_cpu" );
+ int quality = m_pSoundQualityCombo->GetActiveItemUserData()->GetInt( "quality" );
+ switch ( quality )
+ {
+ case SOUNDQUALITY_LOW:
+ dsp_slow_cpu.SetValue(true);
+ Snd_PitchQuality.SetValue(false);
+ break;
+ case SOUNDQUALITY_MEDIUM:
+ dsp_slow_cpu.SetValue(false);
+ Snd_PitchQuality.SetValue(false);
+ break;
+ default:
+ Assert("Undefined sound quality setting.");
+ case SOUNDQUALITY_HIGH:
+ dsp_slow_cpu.SetValue(false);
+ Snd_PitchQuality.SetValue(true);
+ break;
+ };
+
+ // headphones at high quality get enhanced stereo turned on
+ ConVarRef dsp_enhance_stereo( "dsp_enhance_stereo" );
+ if (speakers == 0 && quality == SOUNDQUALITY_HIGH)
+ {
+ dsp_enhance_stereo.SetValue( 1 );
+ }
+ else
+ {
+ dsp_enhance_stereo.SetValue( 0 );
+ }
+
+ // Audio spoken language
+ KeyValues *kv = m_pSpokenLanguageCombo->GetItemUserData( m_pSpokenLanguageCombo->GetActiveItem() );
+ const ELanguage nUpdatedAudioLanguage = (ELanguage)( kv ? kv->GetInt( "language" ) : k_Lang_English );
+
+ if ( nUpdatedAudioLanguage != m_nCurrentAudioLanguage )
+ {
+ // Store new language in static member so that it can be accessed during shutdown when this instance is gone
+ m_pchUpdatedAudioLanguage = (char *) GetLanguageShortName( nUpdatedAudioLanguage );
+
+ // Inform user that they need to restart in order change language at this time
+ QueryBox *qb = new QueryBox( "#GameUI_ChangeLanguageRestart_Title", "#GameUI_ChangeLanguageRestart_Info", GetParent()->GetParent()->GetParent() );
+ if (qb != NULL)
+ {
+ qb->SetOKCommand( new KeyValues( "Command", "command", "RestartWithNewLanguage" ) );
+ qb->SetOKButtonText( "#GameUI_ChangeLanguageRestart_OkButton" );
+ qb->SetCancelButtonText( "#GameUI_ChangeLanguageRestart_CancelButton" );
+ qb->AddActionSignalTarget( GetParent()->GetParent()->GetParent() );
+ qb->DoModal();
+ }
+ }
+
+ m_pSoundMuteLoseFocusCheckButton->ApplyChanges();
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Called on controls changing, enables the Apply button
+//-----------------------------------------------------------------------------
+void COptionsSubAudio::OnControlModified()
+{
+ PostActionSignal(new KeyValues("ApplyButtonEnable"));
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: returns true if the engine needs to be restarted
+//-----------------------------------------------------------------------------
+bool COptionsSubAudio::RequiresRestart()
+{
+ // nothing in audio requires a restart like now
+ return false;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+void COptionsSubAudio::OnCommand( const char *command )
+{
+ if ( !stricmp( command, "TestSpeakers" ) )
+ {
+ // ask them if they REALLY want to test the speakers if they're in a game already.
+ if (engine->IsConnected())
+ {
+ QueryBox *qb = new QueryBox("#GameUI_TestSpeakersWarning_Title", "#GameUI_TestSpeakersWarning_Info" );
+ if (qb != NULL)
+ {
+ qb->SetOKCommand(new KeyValues("RunTestSpeakers"));
+ qb->SetOKButtonText("#GameUI_TestSpeakersWarning_OkButton");
+ qb->SetCancelButtonText("#GameUI_TestSpeakersWarning_CancelButton");
+ qb->AddActionSignalTarget( this );
+ qb->DoModal();
+ }
+ else
+ {
+ // couldn't create the warning dialog for some reason, so just test the speakers.
+ RunTestSpeakers();
+ }
+ }
+ else
+ {
+ // player isn't connected to a game so there's no reason to warn them about being disconnected.
+ // create the command to execute
+ RunTestSpeakers();
+ }
+ }
+ else if ( !stricmp( command, "ShowThirdPartyAudioCredits" ) )
+ {
+ OpenThirdPartySoundCreditsDialog();
+ }
+
+ BaseClass::OnCommand( command );
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Run the test speakers map.
+//-----------------------------------------------------------------------------
+void COptionsSubAudio::RunTestSpeakers()
+{
+ engine->ClientCmd_Unrestricted( "disconnect\nwait\nwait\nsv_lan 1\nsetmaster enable\nmaxplayers 1\n\nhostname \"Speaker Test\"\nprogress_enable\nmap test_speakers\n" );
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: third-party audio credits dialog
+//-----------------------------------------------------------------------------
+class COptionsSubAudioThirdPartyCreditsDlg : public vgui::Frame
+{
+ DECLARE_CLASS_SIMPLE( COptionsSubAudioThirdPartyCreditsDlg, vgui::Frame );
+public:
+ COptionsSubAudioThirdPartyCreditsDlg( vgui::VPANEL hParent ) : BaseClass( NULL, NULL )
+ {
+ // parent is ignored, since we want look like we're steal focus from the parent (we'll become modal below)
+
+ SetTitle("#GameUI_ThirdPartyAudio_Title", true);
+ SetSize( 500, 200 );
+ LoadControlSettings( "resource/OptionsSubAudioThirdPartyDlg.res" );
+ MoveToCenterOfScreen();
+ SetSizeable( false );
+ SetDeleteSelfOnClose( true );
+ }
+
+ virtual void Activate()
+ {
+ BaseClass::Activate();
+
+ input()->SetAppModalSurface(GetVPanel());
+ }
+
+ void OnKeyCodeTyped(KeyCode code)
+ {
+ // force ourselves to be closed if the escape key it pressed
+ if (code == KEY_ESCAPE)
+ {
+ Close();
+ }
+ else
+ {
+ BaseClass::OnKeyCodeTyped(code);
+ }
+ }
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Open third party audio credits dialog
+//-----------------------------------------------------------------------------
+void COptionsSubAudio::OpenThirdPartySoundCreditsDialog()
+{
+ if (!m_OptionsSubAudioThirdPartyCreditsDlg.Get())
+ {
+ m_OptionsSubAudioThirdPartyCreditsDlg = new COptionsSubAudioThirdPartyCreditsDlg(GetVParent());
+ }
+ m_OptionsSubAudioThirdPartyCreditsDlg->Activate();
+}