2013-04-17 23:09:55 -04:00
// Copyright 2013 Dolphin Emulator Project
// Licensed under GPLv2
// Refer to the license.txt file included.
2008-12-08 04:46:09 +00:00
2014-02-10 13:54:46 -05:00
# pragma once
2008-12-08 04:46:09 +00:00
2014-02-20 04:11:52 +01:00
# include <cstring>
2014-06-24 12:28:02 -05:00
# include <list>
2013-09-06 19:56:19 +02:00
# include <map>
2014-02-17 05:18:15 -05:00
# include <string>
2010-06-03 18:05:08 +00:00
# include <vector>
2010-06-03 04:55:39 +00:00
2014-02-20 04:11:52 +01:00
# include "Common/CommonTypes.h"
2014-02-17 05:18:15 -05:00
# include "Common/StringUtil.h"
2008-12-08 04:46:09 +00:00
2013-09-06 19:56:19 +02:00
struct CaseInsensitiveStringCompare
{
bool operator ( ) ( const std : : string & a , const std : : string & b ) const
{
return strcasecmp ( a . c_str ( ) , b . c_str ( ) ) < 0 ;
}
} ;
2010-06-03 18:05:08 +00:00
class IniFile
2010-06-03 04:55:39 +00:00
{
public :
2010-06-04 19:56:34 +00:00
class Section
{
2010-06-05 05:30:23 +00:00
friend class IniFile ;
2010-06-04 19:56:34 +00:00
2010-06-05 05:30:23 +00:00
public :
Section ( ) { }
Section ( const std : : string & _name ) : name ( _name ) { }
2010-06-04 19:56:34 +00:00
2014-02-08 18:50:37 +13:00
bool Exists ( const std : : string & key ) const ;
bool Delete ( const std : : string & key ) ;
2010-06-04 19:56:34 +00:00
2014-02-08 18:50:37 +13:00
void Set ( const std : : string & key , const std : : string & newValue ) ;
void Set ( const std : : string & key , const std : : string & newValue , const std : : string & defaultValue ) ;
2010-06-05 05:30:23 +00:00
2014-02-16 23:51:41 -05:00
bool Get ( const std : : string & key , std : : string * value , const std : : string & defaultValue = NULL_STRING ) ;
2010-06-04 19:56:34 +00:00
2014-02-08 18:50:37 +13:00
void Set ( const std : : string & key , u32 newValue ) {
Set ( key , StringFromFormat ( " 0x%08x " , newValue ) ) ;
2010-06-04 19:56:34 +00:00
}
2014-02-08 18:50:37 +13:00
void Set ( const std : : string & key , float newValue ) {
Set ( key , StringFromFormat ( " %f " , newValue ) ) ;
2010-06-04 19:56:34 +00:00
}
2014-02-08 18:50:37 +13:00
void Set ( const std : : string & key , const float newValue , const float defaultValue ) ;
void Set ( const std : : string & key , double newValue ) {
Set ( key , StringFromFormat ( " %f " , newValue ) ) ;
2010-06-04 19:56:34 +00:00
}
2013-10-29 01:23:17 -04:00
2014-02-08 18:50:37 +13:00
void Set ( const std : : string & key , int newValue , int defaultValue ) ;
void Set ( const std : : string & key , int newValue ) {
Set ( key , StringFromInt ( newValue ) ) ;
2010-06-04 19:56:34 +00:00
}
2013-10-29 01:23:17 -04:00
2014-02-08 18:50:37 +13:00
void Set ( const std : : string & key , bool newValue , bool defaultValue ) ;
void Set ( const std : : string & key , bool newValue ) {
Set ( key , StringFromBool ( newValue ) ) ;
2010-06-04 19:56:34 +00:00
}
2014-02-08 18:50:37 +13:00
void Set ( const std : : string & key , const std : : vector < std : : string > & newValues ) ;
2010-06-04 19:56:34 +00:00
2014-02-08 18:50:37 +13:00
bool Get ( const std : : string & key , int * value , int defaultValue = 0 ) ;
bool Get ( const std : : string & key , u32 * value , u32 defaultValue = 0 ) ;
bool Get ( const std : : string & key , bool * value , bool defaultValue = false ) ;
bool Get ( const std : : string & key , float * value , float defaultValue = false ) ;
bool Get ( const std : : string & key , double * value , double defaultValue = false ) ;
2014-03-15 03:29:53 +01:00
bool Get ( const std : : string & key , std : : vector < std : : string > * values ) ;
2010-06-04 19:56:34 +00:00
bool operator < ( const Section & other ) const {
return name < other . name ;
}
2010-06-05 05:30:23 +00:00
protected :
std : : string name ;
2013-09-06 19:56:19 +02:00
std : : vector < std : : string > keys_order ;
std : : map < std : : string , std : : string , CaseInsensitiveStringCompare > values ;
std : : vector < std : : string > lines ;
2010-06-05 05:30:23 +00:00
} ;
2010-06-03 04:55:39 +00:00
2013-09-06 19:56:19 +02:00
/**
* Loads sections and keys.
* @param filename filename of the ini file which should be loaded
* @param keep_current_data If true, "extends" the currently loaded list of sections and keys with the loaded data (and replaces existing entries). If false, existing data will be erased.
* @warning Using any other operations than "Get*" and "Exists" is untested and will behave unexpectedly
* @todo This really is just a hack to support having two levels of gameinis (defaults and user-specified) and should eventually be replaced with a less stupid system.
*/
2014-02-08 18:50:37 +13:00
bool Load ( const std : : string & filename , bool keep_current_data = false ) ;
2013-09-06 19:56:19 +02:00
2014-02-08 18:50:37 +13:00
bool Save ( const std : : string & filename ) ;
2010-06-03 04:55:39 +00:00
2010-06-04 19:56:34 +00:00
// Returns true if key exists in section
2014-02-08 18:50:37 +13:00
bool Exists ( const std : : string & sectionName , const std : : string & key ) const ;
2010-06-03 18:05:08 +00:00
2014-02-08 18:50:37 +13:00
template < typename T > bool GetIfExists ( const std : : string & sectionName , const std : : string & key , T value )
2011-02-13 22:36:12 +00:00
{
if ( Exists ( sectionName , key ) )
2014-06-16 01:12:43 -04:00
return GetOrCreateSection ( sectionName ) - > Get ( key , value ) ;
2011-02-13 22:36:12 +00:00
return false ;
}
2014-03-15 03:29:53 +01:00
bool GetKeys ( const std : : string & sectionName , std : : vector < std : : string > * keys ) const ;
2010-06-04 19:56:34 +00:00
2014-03-15 03:29:53 +01:00
void SetLines ( const std : : string & sectionName , const std : : vector < std : : string > & lines ) ;
bool GetLines ( const std : : string & sectionName , std : : vector < std : : string > * lines , const bool remove_comments = true ) const ;
2010-06-03 18:05:08 +00:00
2014-02-08 18:50:37 +13:00
bool DeleteKey ( const std : : string & sectionName , const std : : string & key ) ;
bool DeleteSection ( const std : : string & sectionName ) ;
2010-06-03 18:05:08 +00:00
void SortSections ( ) ;
2014-02-08 18:50:37 +13:00
Section * GetOrCreateSection ( const std : : string & section ) ;
2010-06-03 18:05:08 +00:00
private :
2014-06-24 12:28:02 -05:00
std : : list < Section > sections ;
2010-06-03 18:05:08 +00:00
2014-02-08 18:50:37 +13:00
const Section * GetSection ( const std : : string & section ) const ;
Section * GetSection ( const std : : string & section ) ;
std : : string * GetLine ( const std : : string & section , const std : : string & key ) ;
void CreateSection ( const std : : string & section ) ;
2014-03-29 11:05:44 +01:00
2014-02-08 18:50:37 +13:00
static const std : : string & NULL_STRING ;
2008-12-08 04:46:09 +00:00
} ;