Improved handling of directory for user configuration files to work even if $HOME/.config
does not exist, and moved handling of files and directories from user_config to file_manager. git-svn-id: svn+ssh://svn.code.sf.net/p/supertuxkart/code/main/trunk@4467 178a84e3-b1eb-0310-8ba1-8eac791a3b58
This commit is contained in:
parent
def4c22a2b
commit
037069a257
@ -22,7 +22,6 @@
|
||||
#define HEADER_SFX_HPP
|
||||
|
||||
#include "audio/sfx_manager.hpp"
|
||||
#include "config/user_config.hpp"
|
||||
|
||||
class Vec3;
|
||||
|
||||
|
@ -1,34 +1,42 @@
|
||||
|
||||
#include "config/player.hpp"
|
||||
|
||||
#include "karts/player_kart.hpp"
|
||||
#include "race/race_manager.hpp"
|
||||
#include "modes/world.hpp"
|
||||
#include "race/race_manager.hpp"
|
||||
|
||||
ActivePlayer::ActivePlayer(PlayerProfile* player, InputDevice *device)
|
||||
{
|
||||
m_player = player;
|
||||
m_device = NULL;
|
||||
setDevice(device);
|
||||
}
|
||||
} // ActivePlayer
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
ActivePlayer::~ActivePlayer()
|
||||
{
|
||||
setDevice(NULL);
|
||||
}
|
||||
} // ~ActivePlayer
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
PlayerProfile* ActivePlayer::getProfile()
|
||||
{
|
||||
return m_player;
|
||||
}
|
||||
} // getProfile
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
void ActivePlayer::setPlayerProfile(PlayerProfile* player)
|
||||
{
|
||||
m_player = player;
|
||||
}
|
||||
} // setPlayerProfile
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
InputDevice* ActivePlayer::getDevice() const
|
||||
{
|
||||
return m_device;
|
||||
}
|
||||
} // getDevice
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
void ActivePlayer::setDevice(InputDevice* device)
|
||||
{
|
||||
// unset player from previous device he was assigned to, if any
|
||||
@ -38,8 +46,9 @@ void ActivePlayer::setDevice(InputDevice* device)
|
||||
|
||||
// inform the devce of its new owner
|
||||
if (device != NULL) device->setPlayer(this);
|
||||
}
|
||||
} // setDevice
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
PlayerKart* ActivePlayer::getKart()
|
||||
{
|
||||
const int amount = RaceManager::getWorld()->getCurrentNumLocalPlayers();
|
||||
@ -53,4 +62,4 @@ PlayerKart* ActivePlayer::getKart()
|
||||
|
||||
std::cout << "ActivePlayer::getKart() failed to find player named " << m_player->getName() << std::endl;
|
||||
return NULL;
|
||||
}
|
||||
} // getKart
|
||||
|
@ -20,23 +20,15 @@
|
||||
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdexcept>
|
||||
#include <sstream>
|
||||
//#include <stdio.h>
|
||||
//#include <stdexcept>
|
||||
//#include <sstream>
|
||||
#include <string>
|
||||
#include <stdlib.h>
|
||||
#include <fstream>
|
||||
#include <vector>
|
||||
#include "utils/ptr_vector.hpp"
|
||||
|
||||
// for mkdir:
|
||||
#if !defined(WIN32) || defined(__CYGWIN__)
|
||||
# include <sys/stat.h>
|
||||
# include <sys/types.h>
|
||||
#else
|
||||
# include <direct.h>
|
||||
#endif
|
||||
|
||||
class UserConfigParam;
|
||||
static ptr_vector<UserConfigParam, REF> all_params;
|
||||
|
||||
@ -331,24 +323,15 @@ UserConfig *user_config;
|
||||
|
||||
UserConfig::UserConfig()
|
||||
{
|
||||
setDefaults();
|
||||
m_filename = "supertuxkart.cfg";
|
||||
m_warning = "";
|
||||
//m_blacklist_res.clear();
|
||||
if(!loadConfig() || UserConfigParams::m_all_players.size() == 0)
|
||||
{
|
||||
addDefaultPlayer();
|
||||
}
|
||||
} // UserConfig
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
UserConfig::UserConfig(const std::string& filename)
|
||||
{
|
||||
setDefaults();
|
||||
if(!loadConfig(filename) || UserConfigParams::m_all_players.size() == 0)
|
||||
{
|
||||
addDefaultPlayer();
|
||||
}
|
||||
} // UserConfig
|
||||
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
UserConfig::~UserConfig()
|
||||
{
|
||||
@ -373,86 +356,10 @@ void UserConfig::addDefaultPlayer()
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
/**
|
||||
* Load default values for options
|
||||
*/
|
||||
void UserConfig::setDefaults()
|
||||
{
|
||||
#ifdef WIN32
|
||||
m_filename = file_manager->getLogFile("supertuxkart.cfg");
|
||||
#else
|
||||
m_filename = file_manager->getLogFile("config");
|
||||
#endif
|
||||
|
||||
m_warning = "";
|
||||
//m_blacklist_res.clear();
|
||||
|
||||
} // setDefaults
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
/**
|
||||
* load default configuration file for this platform
|
||||
*/
|
||||
/** Load configuration values from file. */
|
||||
bool UserConfig::loadConfig()
|
||||
{
|
||||
return loadConfig(m_filename);
|
||||
} // loadConfig
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
/**
|
||||
* Checks for existance of the STK configuration directory. If the
|
||||
* directory does not exist, it will be created. Return values:
|
||||
* 1: config dir exists
|
||||
* 2: does not exist, but was created
|
||||
* 0: does not exist, and could not be created.
|
||||
*/
|
||||
int UserConfig::CheckAndCreateDir()
|
||||
{
|
||||
// the standard C/C++ libraries don't include anything allowing to check
|
||||
// for directory existance. I work around this by checking if trying to
|
||||
// check for the config file (first reading, then writing)
|
||||
|
||||
const std::string filename = file_manager->getHomeDir() + "/config";
|
||||
|
||||
std::ofstream test(filename.c_str(), std::ios::in);
|
||||
|
||||
if(test.fail() || !test.is_open())
|
||||
{
|
||||
std::ofstream test2(filename.c_str(), std::ios::out);
|
||||
|
||||
if(test2.fail() || !test2.is_open())
|
||||
{
|
||||
int bError;
|
||||
#if defined(WIN32) && !defined(__CYGWIN__)
|
||||
bError = _mkdir(file_manager->getHomeDir().c_str() ) != 0;
|
||||
#else
|
||||
bError = mkdir(file_manager->getHomeDir().c_str(), 0755) != 0;
|
||||
#endif
|
||||
if(bError)
|
||||
{
|
||||
fprintf(stderr, "Couldn't create '%s', config files will not be saved.\n",
|
||||
file_manager->getHomeDir().c_str());
|
||||
return 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("Config directory '%s' successfully created.\n", file_manager->getHomeDir().c_str());
|
||||
return 2;
|
||||
}
|
||||
}
|
||||
if(test2.is_open()) test2.close();
|
||||
|
||||
}
|
||||
if(test.is_open()) test.close();
|
||||
return 1;
|
||||
|
||||
} // CheckAndCreateDir
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
/** Load configuration values from file. */
|
||||
bool UserConfig::loadConfig(const std::string& filename)
|
||||
{
|
||||
|
||||
const std::string filename = file_manager->getConfigDir()+"/"+m_filename;
|
||||
XMLNode* root = file_manager->createXMLTree(filename);
|
||||
if(!root || root->getName() != "stkconfig")
|
||||
{
|
||||
@ -530,26 +437,23 @@ bool UserConfig::loadConfig(const std::string& filename)
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
/** Write settings to config file. */
|
||||
void UserConfig::saveConfig(const std::string& filepath)
|
||||
void UserConfig::saveConfig()
|
||||
{
|
||||
const int DIR_EXIST = CheckAndCreateDir();
|
||||
// Check if the config directory exists (again, since it was already checked
|
||||
// when reading the config file - this is done in case that the problem was
|
||||
// fixed while tuxkart is running). If the directory does not exist and
|
||||
// can not be created, an error message was already printed to stderr,
|
||||
// and we can exit here without any further messages.
|
||||
if (DIR_EXIST == 0)
|
||||
const std::string dir = file_manager->getConfigDir();
|
||||
if(dir=="")
|
||||
{
|
||||
std::cerr << "User config firectory does not exist, cannot save config file!\n";
|
||||
return;
|
||||
}
|
||||
|
||||
const std::string filename = dir + "/" + m_filename;
|
||||
|
||||
std::ofstream configfile;
|
||||
configfile.open (filepath.c_str());
|
||||
configfile.open (filename.c_str());
|
||||
|
||||
if(!configfile.is_open())
|
||||
{
|
||||
std::cerr << "Failed to open " << filepath.c_str() << " for writing, user config won't be saved\n";
|
||||
std::cerr << "Failed to open " << filename.c_str() << " for writing, user config won't be saved\n";
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -285,30 +285,22 @@ class UserConfig
|
||||
private:
|
||||
|
||||
/** Filename of the user config file. */
|
||||
std::string m_filename;
|
||||
|
||||
void addDefaultPlayer ();
|
||||
|
||||
public:
|
||||
|
||||
std::string m_filename;
|
||||
irr::core::stringw m_warning;
|
||||
int CheckAndCreateDir();
|
||||
|
||||
UserConfig();
|
||||
UserConfig(const std::string& filename);
|
||||
~UserConfig();
|
||||
void setDefaults();
|
||||
|
||||
void addDefaultPlayer();
|
||||
public:
|
||||
UserConfig();
|
||||
~UserConfig();
|
||||
|
||||
bool loadConfig();
|
||||
bool loadConfig(const std::string& filename);
|
||||
void saveConfig() { saveConfig(m_filename); }
|
||||
void saveConfig(const std::string& filename);
|
||||
void saveConfig();
|
||||
|
||||
const irr::core::stringw& getWarning() { return m_warning; }
|
||||
void resetWarning() { m_warning=""; }
|
||||
void setWarning(irr::core::stringw& warning) { m_warning=warning; }
|
||||
|
||||
};
|
||||
}; // UserConfig
|
||||
|
||||
|
||||
extern UserConfig *user_config;
|
||||
|
@ -297,7 +297,7 @@ InputDevice* DeviceManager::getLatestUsedDevice()
|
||||
// -----------------------------------------------------------------------------
|
||||
bool DeviceManager::deserialize()
|
||||
{
|
||||
static std::string filepath = file_manager->getHomeDir() + "/input.config";
|
||||
static std::string filepath = file_manager->getConfigDir() + "/input.config";
|
||||
|
||||
printf("Deserializing input.config...\n");
|
||||
|
||||
@ -394,8 +394,7 @@ bool DeviceManager::deserialize()
|
||||
// -----------------------------------------------------------------------------
|
||||
void DeviceManager::serialize()
|
||||
{
|
||||
static std::string filepath = file_manager->getHomeDir() + "/input.config";
|
||||
user_config->CheckAndCreateDir();
|
||||
static std::string filepath = file_manager->getConfigDir() + "/input.config";
|
||||
printf("Serializing input.config...\n");
|
||||
|
||||
|
||||
|
@ -20,11 +20,22 @@
|
||||
|
||||
#include "io/file_manager.hpp"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdexcept>
|
||||
#include <sstream>
|
||||
#include <sys/stat.h>
|
||||
#include <iostream>
|
||||
#include <string>
|
||||
|
||||
// For mkdir
|
||||
#if !defined(WIN32) || defined(__CYGWIN__)
|
||||
# include <sys/stat.h>
|
||||
# include <sys/types.h>
|
||||
#else
|
||||
# include <direct.h>
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef WIN32
|
||||
# include <io.h>
|
||||
# include <stdio.h>
|
||||
@ -36,7 +47,6 @@
|
||||
# include <unistd.h>
|
||||
#endif
|
||||
|
||||
#define CONFIGDIR "supertuxkart"
|
||||
|
||||
#include "irrlicht.h"
|
||||
#include "btBulletDynamicsCommon.h"
|
||||
@ -142,7 +152,7 @@ FileManager::FileManager(char *argv[])
|
||||
// after the filemanager (to get the path to the tranlsations from it)
|
||||
fprintf(stderr, "Data files will be fetched from: '%s'\n",
|
||||
m_root_dir.c_str() );
|
||||
|
||||
checkAndCreateConfigDir();
|
||||
} // FileManager
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
@ -349,53 +359,107 @@ std::string FileManager::getItemFile(const std::string& fname) const
|
||||
} // getConfigFile
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
std::string FileManager::getHomeDir() const
|
||||
/** If the directory specified in path does not exist, it is created.
|
||||
* /params path Directory to test.
|
||||
* /return True if the directory exists or could be created, false otherwise.
|
||||
*/
|
||||
bool FileManager::checkAndCreateDirectory(const std::string &path)
|
||||
{
|
||||
io::path p=m_file_system->getWorkingDirectory();
|
||||
// irrlicht apparently returns true for files and directory
|
||||
// (using access/_access internally):
|
||||
if(m_file_system->existFile(io::path(path.c_str())))
|
||||
return true;
|
||||
|
||||
// Otherwise try to create the directory:
|
||||
#if defined(WIN32) && !defined(__CYGWIN__)
|
||||
bool error = _mkdir(path.c_str()) != 0;
|
||||
#else
|
||||
bool error = mkdir(path.c_str(), 0755) != 0;
|
||||
#endif
|
||||
return !error;
|
||||
} // checkAndCreateDirectory
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
/** Checks if the config directory exists, and it not, tries to create it. */
|
||||
void FileManager::checkAndCreateConfigDir()
|
||||
{
|
||||
std::string DIRNAME;
|
||||
#ifdef WIN32
|
||||
// Try to use the APPDATA directory to store config files and highscore
|
||||
// lists. If not defined, used the current directory.
|
||||
std::ostringstream s;
|
||||
if(getenv("APPDATA")!=NULL)
|
||||
{
|
||||
s<<getenv("APPDATA")<<"/"<<CONFIGDIR<<"/";
|
||||
DIRNAME=s.str();
|
||||
m_config_dir = getenv("APPDATA");
|
||||
if(!checkAndCreateDirectory(m_config_dir))
|
||||
{
|
||||
fprintf(stderr, "Can't create config dir '%s', falling back to '.'.\n",
|
||||
m_config_dir.c_str());
|
||||
m_config_dir = ".";
|
||||
}
|
||||
}
|
||||
else DIRNAME=".";
|
||||
#endif
|
||||
#ifdef linux
|
||||
// Use new standards for config directory
|
||||
if (getenv("XDG_CONFIG_HOME")!=NULL){
|
||||
DIRNAME = getenv("XDG_CONFIG_HOME");
|
||||
}else if (getenv("HOME")!=NULL){
|
||||
DIRNAME = getenv("HOME");
|
||||
DIRNAME += "/.config";
|
||||
}else{
|
||||
std::cerr << "No home directory, this should NOT happen!\n";
|
||||
// This is what was here before, it looks rather questionable.
|
||||
DIRNAME=".";
|
||||
}
|
||||
DIRNAME += "/";
|
||||
DIRNAME += CONFIGDIR;
|
||||
#endif
|
||||
#ifdef __APPLE__
|
||||
if (getenv("HOME")!=NULL){
|
||||
DIRNAME = getenv("HOME");
|
||||
}else{
|
||||
else
|
||||
m_config_dir = ".";
|
||||
#else
|
||||
# ifdef __APPLE__
|
||||
if (getenv("HOME")!=NULL)
|
||||
{
|
||||
m_config_dir = getenv("HOME");
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cerr << "No home directory, this should NOT happen!\n";
|
||||
// Fall back to system-wide app data (rather than user-specific data), but should not happen anyway.
|
||||
DIRNAME = "";
|
||||
m_config_dir = "";
|
||||
}
|
||||
DIRNAME += "/Library/Application Support/";
|
||||
DIRNAME += CONFIGDIR;
|
||||
m_config_dir += "/Library/Application Support/";
|
||||
# else
|
||||
// Remaining unix variants. Use the new standards for config directory
|
||||
// i.e. either XDG_CONFIG_HOME or $HOME/.config
|
||||
if (getenv("XDG_CONFIG_HOME")!=NULL){
|
||||
m_config_dir = getenv("XDG_CONFIG_HOME");
|
||||
}
|
||||
else if (!getenv("HOME"))
|
||||
{
|
||||
std::cerr << "No home directory, this should NOT happen - trying '.' for config files!\n";
|
||||
m_config_dir = ".";
|
||||
}
|
||||
else
|
||||
{
|
||||
m_config_dir = getenv("HOME");
|
||||
m_config_dir += "/.config";
|
||||
if(!checkAndCreateDirectory(m_config_dir))
|
||||
{
|
||||
// If $HOME/.config can not be created:
|
||||
fprintf(stderr, "Can't create dir '%s', falling back to use '%s'.\n",
|
||||
m_config_dir.c_str(), getenv("HOME"));
|
||||
m_config_dir = getenv("HOME");
|
||||
}
|
||||
}
|
||||
# endif
|
||||
#endif
|
||||
return DIRNAME;
|
||||
} // getHomeDir
|
||||
const std::string CONFIGDIR("supertuxkart");
|
||||
|
||||
m_config_dir += "/";
|
||||
m_config_dir += CONFIGDIR;
|
||||
if(!checkAndCreateDirectory(m_config_dir))
|
||||
{
|
||||
fprintf(stderr, "Can not create config dir '%s', falling back to '.'.\n",
|
||||
m_config_dir.c_str());
|
||||
m_config_dir = ".";
|
||||
}
|
||||
return;
|
||||
} // checkAndCreateConfigDir
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
std::string FileManager::getConfigDir() const
|
||||
{
|
||||
return m_config_dir;
|
||||
} // getConfigDir
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
std::string FileManager::getLogFile(const std::string& fname) const
|
||||
{
|
||||
return getHomeDir()+"/"+fname;
|
||||
return getConfigDir()+"/"+fname;
|
||||
} // getLogFile
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
@ -419,14 +483,14 @@ std::string FileManager::getFontFile(const std::string& fname) const
|
||||
//-----------------------------------------------------------------------------
|
||||
std::string FileManager::getHighscoreFile(const std::string& fname) const
|
||||
{
|
||||
return getHomeDir()+"/"+fname;
|
||||
return getConfigDir()+"/"+fname;
|
||||
} // getHighscoreFile
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
/** Returns the full path of the challenge file. */
|
||||
std::string FileManager::getChallengeFile(const std::string &fname) const
|
||||
{
|
||||
return getHomeDir()+"/"+fname;
|
||||
return getConfigDir()+"/"+fname;
|
||||
} // getChallengeFile
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
@ -40,6 +40,9 @@ private:
|
||||
IrrlichtDevice *m_device;
|
||||
|
||||
bool m_is_full_path;
|
||||
/** Directory where user config files are stored. */
|
||||
std::string m_config_dir;
|
||||
/** Root data directory. */
|
||||
std::string m_root_dir;
|
||||
std::vector<std::string> m_texture_search_path,
|
||||
m_model_search_path,
|
||||
@ -50,8 +53,9 @@ private:
|
||||
const;
|
||||
void makePath (std::string& path, const std::string& dir,
|
||||
const std::string& fname) const;
|
||||
io::path createAbsoluteFilename(const std::string &f);
|
||||
|
||||
bool checkAndCreateDirectory(const std::string &path);
|
||||
io::path createAbsoluteFilename(const std::string &f);
|
||||
void checkAndCreateConfigDir();
|
||||
public:
|
||||
FileManager(char *argv[]);
|
||||
~FileManager();
|
||||
@ -60,7 +64,7 @@ public:
|
||||
io::IXMLReader *createXMLReader(const std::string &filename);
|
||||
XMLNode *createXMLTree(const std::string &filename);
|
||||
|
||||
std::string getHomeDir () const;
|
||||
std::string getConfigDir () const;
|
||||
std::string getKartDir () const;
|
||||
std::string getDataDir () const;
|
||||
std::string getItemsDir () const;
|
||||
|
Loading…
x
Reference in New Issue
Block a user