@ -4,9 +4,43 @@
# include <components/config/launchersettings.hpp>
# include <QFileDialog>
# include <QCompleter>
# include <QProxyStyle>
# include <components/contentselector/view/contentselector.hpp>
# include <components/contentselector/model/esmfile.hpp>
# include <cmath>
class HorizontalTextWestTabStyle : public QProxyStyle
{
public :
QSize sizeFromContents ( ContentsType type , const QStyleOption * option , const QSize & size , const QWidget * widget ) const
{
QSize s = QProxyStyle : : sizeFromContents ( type , option , size , widget ) ;
if ( type = = QStyle : : CT_TabBarTab )
{
s . transpose ( ) ;
s . setHeight ( s . height ( ) + 20 ) ;
}
return s ;
}
void drawControl ( ControlElement element , const QStyleOption * option , QPainter * painter , const QWidget * widget ) const
{
if ( element = = CE_TabBarTabLabel )
{
if ( const QStyleOptionTab * tab = qstyleoption_cast < const QStyleOptionTab * > ( option ) )
{
QStyleOptionTab opt ( * tab ) ;
opt . shape = QTabBar : : RoundedNorth ;
QProxyStyle : : drawControl ( element , & opt , painter , widget ) ;
return ;
}
}
QProxyStyle : : drawControl ( element , option , painter , widget ) ;
}
} ;
Launcher : : AdvancedPage : : AdvancedPage ( Files : : ConfigurationManager & cfg ,
Config : : GameSettings & gameSettings ,
Settings : : Manager & engineSettings , QWidget * parent )
@ -19,6 +53,7 @@ Launcher::AdvancedPage::AdvancedPage(Files::ConfigurationManager &cfg,
setupUi ( this ) ;
loadSettings ( ) ;
AdvancedTabWidget - > tabBar ( ) - > setStyle ( new HorizontalTextWestTabStyle ) ;
mCellNameCompleter . setModel ( & mCellNameCompleterModel ) ;
startDefaultCharacterAtField - > setCompleter ( & mCellNameCompleter ) ;
}
@ -55,142 +90,222 @@ void Launcher::AdvancedPage::on_runScriptAfterStartupBrowseButton_clicked()
runScriptAfterStartupField - > setText ( path ) ;
}
namespace
{
constexpr double CellSizeInUnits = 8192 ;
double convertToCells ( double unitRadius )
{
return std : : round ( ( unitRadius / 0.93 + 1024 ) / CellSizeInUnits ) ;
}
double convertToUnits ( double CellGridRadius )
{
return ( CellSizeInUnits * CellGridRadius - 1024 ) * 0.93 ;
}
}
bool Launcher : : AdvancedPage : : loadSettings ( )
{
// Game mechanics
{
loadSettingBool ( toggleSneakCheckBox , " toggle sneak " , " Input " ) ;
loadSettingBool ( canLootDuringDeathAnimationCheckBox , " can loot during death animation " , " Game " ) ;
loadSettingBool ( followersAttackOnSightCheckBox , " followers attack on sight " , " Game " ) ;
loadSettingBool ( rebalanceSoulGemValuesCheckBox , " rebalance soul gem values " , " Game " ) ;
loadSettingBool ( enchantedWeaponsMagicalCheckBox , " enchanted weapons are magical " , " Game " ) ;
loadSettingBool ( permanentBarterDispositionChangeCheckBox , " barter disposition change is permanent " , " Game " ) ;
loadSettingBool ( classicReflectedAbsorbSpellsCheckBox , " classic reflected absorb spells behavior " , " Game " ) ;
loadSettingBool ( requireAppropriateAmmunitionCheckBox , " only appropriate ammunition bypasses resistance " , " Game " ) ;
loadSettingBool ( uncappedDamageFatigueCheckBox , " uncapped damage fatigue " , " Game " ) ;
loadSettingBool ( normaliseRaceSpeedCheckBox , " normalise race speed " , " Game " ) ;
int unarmedFactorsStrengthIndex = mEngineSettings . getInt ( " strength influences hand to hand " , " Game " ) ;
if ( unarmedFactorsStrengthIndex > = 0 & & unarmedFactorsStrengthIndex < = 2 )
unarmedFactorsStrengthComboBox - > setCurrentIndex ( unarmedFactorsStrengthIndex ) ;
loadSettingBool ( stealingFromKnockedOutCheckBox , " always allow stealing from knocked out actors " , " Game " ) ;
}
// Visuals
{
loadSettingBool ( bumpMapLocalLightingCheckBox , " apply lighting to environment maps " , " Shaders " ) ;
loadSettingBool ( magicItemAnimationsCheckBox , " use magic item animations " , " Game " ) ;
connect ( animSourcesCheckBox , SIGNAL ( toggled ( bool ) ) , this , SLOT ( slotAnimSourcesToggled ( bool ) ) ) ;
loadSettingBool ( animSourcesCheckBox , " use additional anim sources " , " Game " ) ;
if ( animSourcesCheckBox - > checkState ( ) )
{
loadSettingBool ( weaponSheathingCheckBox , " weapon sheathing " , " Game " ) ;
loadSettingBool ( shieldSheathingCheckBox , " shield sheathing " , " Game " ) ;
}
loadSettingBool ( viewOverShoulderCheckBox , " view over shoulder " , " Camera " ) ;
loadSettingBool ( turnToMovementDirectionCheckBox , " turn to movement direction " , " Game " ) ;
const bool distantTerrain = mEngineSettings . getBool ( " distant terrain " , " Terrain " ) ;
const bool objectPaging = mEngineSettings . getBool ( " object paging " , " Terrain " ) ;
if ( distantTerrain & & objectPaging ) {
distantLandCheckBox - > setCheckState ( Qt : : Checked ) ;
}
loadSettingBool ( activeGridObjectPagingCheckBox , " object paging active grid " , " Terrain " ) ;
viewingDistanceComboBox - > setValue ( convertToCells ( mEngineSettings . getInt ( " viewing distance " , " Camera " ) ) ) ;
}
// Interface Changes
{
loadSettingBool ( showEffectDurationCheckBox , " show effect duration " , " Game " ) ;
loadSettingBool ( showEnchantChanceCheckBox , " show enchant chance " , " Game " ) ;
loadSettingBool ( showMeleeInfoCheckBox , " show melee info " , " Game " ) ;
loadSettingBool ( showProjectileDamageCheckBox , " show projectile damage " , " Game " ) ;
loadSettingBool ( changeDialogTopicsCheckBox , " color topic enable " , " GUI " ) ;
int showOwnedIndex = mEngineSettings . getInt ( " show owned " , " Game " ) ;
// Match the index with the option (only 0, 1, 2, or 3 are valid). Will default to 0 if invalid.
if ( showOwnedIndex > = 0 & & showOwnedIndex < = 3 )
showOwnedComboBox - > setCurrentIndex ( showOwnedIndex ) ;
}
// Bug fixes
{
loadSettingBool ( preventMerchantEquippingCheckBox , " prevent merchant equipping " , " Game " ) ;
loadSettingBool ( trainersTrainingSkillsBasedOnBaseSkillCheckBox , " trainers training skills based on base skill " , " Game " ) ;
}
// Miscellaneous
{
// Saves
loadSettingBool ( timePlayedCheckbox , " timeplayed " , " Saves " ) ;
maximumQuicksavesComboBox - > setValue ( mEngineSettings . getInt ( " max quicksaves " , " Saves " ) ) ;
// Other Settings
QString screenshotFormatString = QString : : fromStdString ( mEngineSettings . getString ( " screenshot format " , " General " ) ) . toUpper ( ) ;
if ( screenshotFormatComboBox - > findText ( screenshotFormatString ) = = - 1 )
screenshotFormatComboBox - > addItem ( screenshotFormatString ) ;
screenshotFormatComboBox - > setCurrentIndex ( screenshotFormatComboBox - > findText ( screenshotFormatString ) ) ;
}
// Testing
bool skipMenu = mGameSettings . value ( " skip-menu " ) . toInt ( ) = = 1 ;
if ( skipMenu ) {
skipMenuCheckBox - > setCheckState ( Qt : : Checked ) ;
}
startDefaultCharacterAtLabel - > setEnabled ( skipMenu ) ;
startDefaultCharacterAtField - > setEnabled ( skipMenu ) ;
startDefaultCharacterAtField - > setText ( mGameSettings . value ( " start " ) ) ;
runScriptAfterStartupField - > setText ( mGameSettings . value ( " script-run " ) ) ;
// Game Settings
loadSettingBool ( canLootDuringDeathAnimationCheckBox , " can loot during death animation " , " Game " ) ;
loadSettingBool ( followersAttackOnSightCheckBox , " followers attack on sight " , " Game " ) ;
loadSettingBool ( preventMerchantEquippingCheckBox , " prevent merchant equipping " , " Game " ) ;
loadSettingBool ( classicReflectedAbsorbSpellsCheckBox , " classic reflected absorb spells behavior " , " Game " ) ;
loadSettingBool ( rebalanceSoulGemValuesCheckBox , " rebalance soul gem values " , " Game " ) ;
loadSettingBool ( enchantedWeaponsMagicalCheckBox , " enchanted weapons are magical " , " Game " ) ;
loadSettingBool ( permanentBarterDispositionChangeCheckBox , " barter disposition change is permanent " , " Game " ) ;
int unarmedFactorsStrengthIndex = mEngineSettings . getInt ( " strength influences hand to hand " , " Game " ) ;
if ( unarmedFactorsStrengthIndex > = 0 & & unarmedFactorsStrengthIndex < = 2 )
unarmedFactorsStrengthComboBox - > setCurrentIndex ( unarmedFactorsStrengthIndex ) ;
loadSettingBool ( requireAppropriateAmmunitionCheckBox , " only appropriate ammunition bypasses resistance " , " Game " ) ;
loadSettingBool ( magicItemAnimationsCheckBox , " use magic item animations " , " Game " ) ;
loadSettingBool ( normaliseRaceSpeedCheckBox , " normalise race speed " , " Game " ) ;
connect ( animSourcesCheckBox , SIGNAL ( toggled ( bool ) ) , this , SLOT ( slotAnimSourcesToggled ( bool ) ) ) ;
loadSettingBool ( animSourcesCheckBox , " use additional anim sources " , " Game " ) ;
if ( animSourcesCheckBox - > checkState ( ) )
{
loadSettingBool ( weaponSheathingCheckBox , " weapon sheathing " , " Game " ) ;
loadSettingBool ( shieldSheathingCheckBox , " shield sheathing " , " Game " ) ;
}
loadSettingBool ( uncappedDamageFatigueCheckBox , " uncapped damage fatigue " , " Game " ) ;
loadSettingBool ( trainersTrainingSkillsBasedOnBaseSkillCheckBox , " trainers training skills based on base skill " , " Game " ) ;
// Input Settings
loadSettingBool ( grabCursorCheckBox , " grab cursor " , " Input " ) ;
loadSettingBool ( toggleSneakCheckBox , " toggle sneak " , " Input " ) ;
// Saves Settings
loadSettingBool ( timePlayedCheckbox , " timeplayed " , " Saves " ) ;
maximumQuicksavesComboBox - > setValue ( mEngineSettings . getInt ( " max quicksaves " , " Saves " ) ) ;
// User Interface Settings
loadSettingBool ( showEffectDurationCheckBox , " show effect duration " , " Game " ) ;
loadSettingBool ( showEnchantChanceCheckBox , " show enchant chance " , " Game " ) ;
loadSettingBool ( showMeleeInfoCheckBox , " show melee info " , " Game " ) ;
loadSettingBool ( showProjectileDamageCheckBox , " show projectile damage " , " Game " ) ;
loadSettingBool ( changeDialogTopicsCheckBox , " color topic enable " , " GUI " ) ;
int showOwnedIndex = mEngineSettings . getInt ( " show owned " , " Game " ) ;
// Match the index with the option (only 0, 1, 2, or 3 are valid). Will default to 0 if invalid.
if ( showOwnedIndex > = 0 & & showOwnedIndex < = 3 )
showOwnedComboBox - > setCurrentIndex ( showOwnedIndex ) ;
// Other Settings
QString screenshotFormatString = QString : : fromStdString ( mEngineSettings . getString ( " screenshot format " , " General " ) ) . toUpper ( ) ;
if ( screenshotFormatComboBox - > findText ( screenshotFormatString ) = = - 1 )
screenshotFormatComboBox - > addItem ( screenshotFormatString ) ;
screenshotFormatComboBox - > setCurrentIndex ( screenshotFormatComboBox - > findText ( screenshotFormatString ) ) ;
{
loadSettingBool ( grabCursorCheckBox , " grab cursor " , " Input " ) ;
bool skipMenu = mGameSettings . value ( " skip-menu " ) . toInt ( ) = = 1 ;
if ( skipMenu )
{
skipMenuCheckBox - > setCheckState ( Qt : : Checked ) ;
}
startDefaultCharacterAtLabel - > setEnabled ( skipMenu ) ;
startDefaultCharacterAtField - > setEnabled ( skipMenu ) ;
startDefaultCharacterAtField - > setText ( mGameSettings . value ( " start " ) ) ;
runScriptAfterStartupField - > setText ( mGameSettings . value ( " script-run " ) ) ;
}
return true ;
}
void Launcher : : AdvancedPage : : saveSettings ( )
{
// Ensure we only set the new settings if they changed. This is to avoid cluttering the
// user settings file (which by definition should only contain settings the user has touched)
// Game mechanics
{
saveSettingBool ( toggleSneakCheckBox , " toggle sneak " , " Input " ) ;
saveSettingBool ( canLootDuringDeathAnimationCheckBox , " can loot during death animation " , " Game " ) ;
saveSettingBool ( followersAttackOnSightCheckBox , " followers attack on sight " , " Game " ) ;
saveSettingBool ( rebalanceSoulGemValuesCheckBox , " rebalance soul gem values " , " Game " ) ;
saveSettingBool ( enchantedWeaponsMagicalCheckBox , " enchanted weapons are magical " , " Game " ) ;
saveSettingBool ( permanentBarterDispositionChangeCheckBox , " barter disposition change is permanent " , " Game " ) ;
saveSettingBool ( classicReflectedAbsorbSpellsCheckBox , " classic reflected absorb spells behavior " , " Game " ) ;
saveSettingBool ( requireAppropriateAmmunitionCheckBox , " only appropriate ammunition bypasses resistance " , " Game " ) ;
saveSettingBool ( uncappedDamageFatigueCheckBox , " uncapped damage fatigue " , " Game " ) ;
saveSettingBool ( normaliseRaceSpeedCheckBox , " normalise race speed " , " Game " ) ;
int unarmedFactorsStrengthIndex = unarmedFactorsStrengthComboBox - > currentIndex ( ) ;
if ( unarmedFactorsStrengthIndex ! = mEngineSettings . getInt ( " strength influences hand to hand " , " Game " ) )
mEngineSettings . setInt ( " strength influences hand to hand " , " Game " , unarmedFactorsStrengthIndex ) ;
saveSettingBool ( stealingFromKnockedOutCheckBox , " always allow stealing from knocked out actors " , " Game " ) ;
}
// Visuals
{
saveSettingBool ( bumpMapLocalLightingCheckBox , " apply lighting to environment maps " , " Shaders " ) ;
saveSettingBool ( magicItemAnimationsCheckBox , " use magic item animations " , " Game " ) ;
saveSettingBool ( animSourcesCheckBox , " use additional anim sources " , " Game " ) ;
saveSettingBool ( weaponSheathingCheckBox , " weapon sheathing " , " Game " ) ;
saveSettingBool ( shieldSheathingCheckBox , " shield sheathing " , " Game " ) ;
saveSettingBool ( viewOverShoulderCheckBox , " view over shoulder " , " Camera " ) ;
saveSettingBool ( turnToMovementDirectionCheckBox , " turn to movement direction " , " Game " ) ;
const bool distantTerrain = mEngineSettings . getBool ( " distant terrain " , " Terrain " ) ;
const bool objectPaging = mEngineSettings . getBool ( " object paging " , " Terrain " ) ;
const bool wantDistantLand = distantLandCheckBox - > checkState ( ) ;
if ( wantDistantLand ! = ( distantTerrain & & objectPaging ) ) {
mEngineSettings . setBool ( " distant terrain " , " Terrain " , wantDistantLand ) ;
mEngineSettings . setBool ( " object paging " , " Terrain " , wantDistantLand ) ;
}
saveSettingBool ( activeGridObjectPagingCheckBox , " object paging active grid " , " Terrain " ) ;
double viewingDistance = viewingDistanceComboBox - > value ( ) ;
if ( viewingDistance ! = convertToCells ( mEngineSettings . getInt ( " viewing distance " , " Camera " ) ) )
{
mEngineSettings . setInt ( " viewing distance " , " Camera " , convertToUnits ( viewingDistance ) ) ;
}
}
// Interface Changes
{
saveSettingBool ( showEffectDurationCheckBox , " show effect duration " , " Game " ) ;
saveSettingBool ( showEnchantChanceCheckBox , " show enchant chance " , " Game " ) ;
saveSettingBool ( showMeleeInfoCheckBox , " show melee info " , " Game " ) ;
saveSettingBool ( showProjectileDamageCheckBox , " show projectile damage " , " Game " ) ;
saveSettingBool ( changeDialogTopicsCheckBox , " color topic enable " , " GUI " ) ;
int showOwnedCurrentIndex = showOwnedComboBox - > currentIndex ( ) ;
if ( showOwnedCurrentIndex ! = mEngineSettings . getInt ( " show owned " , " Game " ) )
mEngineSettings . setInt ( " show owned " , " Game " , showOwnedCurrentIndex ) ;
}
// Bug fixes
{
saveSettingBool ( preventMerchantEquippingCheckBox , " prevent merchant equipping " , " Game " ) ;
saveSettingBool ( trainersTrainingSkillsBasedOnBaseSkillCheckBox , " trainers training skills based on base skill " , " Game " ) ;
}
// Miscellaneous
{
// Saves Settings
saveSettingBool ( timePlayedCheckbox , " timeplayed " , " Saves " ) ;
int maximumQuicksaves = maximumQuicksavesComboBox - > value ( ) ;
if ( maximumQuicksaves ! = mEngineSettings . getInt ( " max quicksaves " , " Saves " ) )
{
mEngineSettings . setInt ( " max quicksaves " , " Saves " , maximumQuicksaves ) ;
}
// Other Settings
std : : string screenshotFormatString = screenshotFormatComboBox - > currentText ( ) . toLower ( ) . toStdString ( ) ;
if ( screenshotFormatString ! = mEngineSettings . getString ( " screenshot format " , " General " ) )
mEngineSettings . setString ( " screenshot format " , " General " , screenshotFormatString ) ;
}
// Testing
int skipMenu = skipMenuCheckBox - > checkState ( ) = = Qt : : Checked ;
if ( skipMenu ! = mGameSettings . value ( " skip-menu " ) . toInt ( ) )
mGameSettings . setValue ( " skip-menu " , QString : : number ( skipMenu ) ) ;
QString startCell = startDefaultCharacterAtField - > text ( ) ;
if ( startCell ! = mGameSettings . value ( " start " ) ) {
mGameSettings . setValue ( " start " , startCell ) ;
}
QString scriptRun = runScriptAfterStartupField - > text ( ) ;
if ( scriptRun ! = mGameSettings . value ( " script-run " ) )
mGameSettings . setValue ( " script-run " , scriptRun ) ;
// Game Settings
saveSettingBool ( canLootDuringDeathAnimationCheckBox , " can loot during death animation " , " Game " ) ;
saveSettingBool ( followersAttackOnSightCheckBox , " followers attack on sight " , " Game " ) ;
saveSettingBool ( preventMerchantEquippingCheckBox , " prevent merchant equipping " , " Game " ) ;
saveSettingBool ( rebalanceSoulGemValuesCheckBox , " rebalance soul gem values " , " Game " ) ;
saveSettingBool ( classicReflectedAbsorbSpellsCheckBox , " classic reflected absorb spells behavior " , " Game " ) ;
saveSettingBool ( enchantedWeaponsMagicalCheckBox , " enchanted weapons are magical " , " Game " ) ;
saveSettingBool ( permanentBarterDispositionChangeCheckBox , " barter disposition change is permanent " , " Game " ) ;
int unarmedFactorsStrengthIndex = unarmedFactorsStrengthComboBox - > currentIndex ( ) ;
if ( unarmedFactorsStrengthIndex ! = mEngineSettings . getInt ( " strength influences hand to hand " , " Game " ) )
mEngineSettings . setInt ( " strength influences hand to hand " , " Game " , unarmedFactorsStrengthIndex ) ;
saveSettingBool ( requireAppropriateAmmunitionCheckBox , " only appropriate ammunition bypasses resistance " , " Game " ) ;
saveSettingBool ( magicItemAnimationsCheckBox , " use magic item animations " , " Game " ) ;
saveSettingBool ( normaliseRaceSpeedCheckBox , " normalise race speed " , " Game " ) ;
saveSettingBool ( animSourcesCheckBox , " use additional anim sources " , " Game " ) ;
saveSettingBool ( weaponSheathingCheckBox , " weapon sheathing " , " Game " ) ;
saveSettingBool ( shieldSheathingCheckBox , " shield sheathing " , " Game " ) ;
saveSettingBool ( uncappedDamageFatigueCheckBox , " uncapped damage fatigue " , " Game " ) ;
saveSettingBool ( trainersTrainingSkillsBasedOnBaseSkillCheckBox , " trainers training skills based on base skill " , " Game " ) ;
// Input Settings
saveSettingBool ( grabCursorCheckBox , " grab cursor " , " Input " ) ;
saveSettingBool ( toggleSneakCheckBox , " toggle sneak " , " Input " ) ;
// Saves Settings
saveSettingBool ( timePlayedCheckbox , " timeplayed " , " Saves " ) ;
int maximumQuicksaves = maximumQuicksavesComboBox - > value ( ) ;
if ( maximumQuicksaves ! = mEngineSettings . getInt ( " max quicksaves " , " Saves " ) ) {
mEngineSettings . setInt ( " max quicksaves " , " Saves " , maximumQuicksaves ) ;
}
// User Interface Settings
saveSettingBool ( showEffectDurationCheckBox , " show effect duration " , " Game " ) ;
saveSettingBool ( showEnchantChanceCheckBox , " show enchant chance " , " Game " ) ;
saveSettingBool ( showMeleeInfoCheckBox , " show melee info " , " Game " ) ;
saveSettingBool ( showProjectileDamageCheckBox , " show projectile damage " , " Game " ) ;
saveSettingBool ( changeDialogTopicsCheckBox , " color topic enable " , " GUI " ) ;
int showOwnedCurrentIndex = showOwnedComboBox - > currentIndex ( ) ;
if ( showOwnedCurrentIndex ! = mEngineSettings . getInt ( " show owned " , " Game " ) )
mEngineSettings . setInt ( " show owned " , " Game " , showOwnedCurrentIndex ) ;
// Other Settings
std : : string screenshotFormatString = screenshotFormatComboBox - > currentText ( ) . toLower ( ) . toStdString ( ) ;
if ( screenshotFormatString ! = mEngineSettings . getString ( " screenshot format " , " General " ) )
mEngineSettings . setString ( " screenshot format " , " General " , screenshotFormatString ) ;
{
saveSettingBool ( grabCursorCheckBox , " grab cursor " , " Input " ) ;
int skipMenu = skipMenuCheckBox - > checkState ( ) = = Qt : : Checked ;
if ( skipMenu ! = mGameSettings . value ( " skip-menu " ) . toInt ( ) )
mGameSettings . setValue ( " skip-menu " , QString : : number ( skipMenu ) ) ;
QString startCell = startDefaultCharacterAtField - > text ( ) ;
if ( startCell ! = mGameSettings . value ( " start " ) )
{
mGameSettings . setValue ( " start " , startCell ) ;
}
QString scriptRun = runScriptAfterStartupField - > text ( ) ;
if ( scriptRun ! = mGameSettings . value ( " script-run " ) )
mGameSettings . setValue ( " script-run " , scriptRun ) ;
}
}
void Launcher : : AdvancedPage : : loadSettingBool ( QCheckBox * checkbox , const std : : string & setting , const std : : string & group ) {
void Launcher : : AdvancedPage : : loadSettingBool ( QCheckBox * checkbox , const std : : string & setting , const std : : string & group )
{
if ( mEngineSettings . getBool ( setting , group ) )
checkbox - > setCheckState ( Qt : : Checked ) ;
}
void Launcher : : AdvancedPage : : saveSettingBool ( QCheckBox * checkbox , const std : : string & setting , const std : : string & group ) {
void Launcher : : AdvancedPage : : saveSettingBool ( QCheckBox * checkbox , const std : : string & setting , const std : : string & group )
{
bool cValue = checkbox - > checkState ( ) ;
if ( cValue ! = mEngineSettings . getBool ( setting , group ) )
mEngineSettings . setBool ( setting , group , cValue ) ;