File indexing completed on 2024-04-28 05:32:12
0001 #ifndef oxygenoption_h 0002 #define oxygenoption_h 0003 /* 0004 * this file is part of the oxygen gtk engine 0005 * SPDX-FileCopyrightText: 2010 Hugo Pereira Da Costa <hugo.pereira@free.fr> 0006 * 0007 * inspired notably from kdelibs/kdeui/color/kcolorutils.h 0008 * SPDX-FileCopyrightText: 2007 Matthew Woehlke <mw_triad@users.sourceforge.net> 0009 * SPDX-FileCopyrightText: 2007 Thomas Zander <zander@kde.org> 0010 * SPDX-FileCopyrightText: 2007 Zack Rusin <zack@kde.org> 0011 * 0012 * SPDX-License-Identifier: LGPL-2.0-or-later 0013 */ 0014 0015 #include "config.h" 0016 0017 #include <iostream> 0018 #include <set> 0019 #include <sstream> 0020 #include <string> 0021 0022 namespace Oxygen 0023 { 0024 0025 //! used to store values from kde-like rc file 0026 class Option 0027 { 0028 public: 0029 0030 //! constructor 0031 explicit Option( const std::string& tag = std::string(), const std::string& value = std::string() ): 0032 _tag(tag), 0033 _value(value) 0034 {} 0035 0036 //! destructor 0037 virtual ~Option( void ) 0038 {} 0039 0040 //! equal to operator 0041 bool operator == (const Option& other ) const 0042 { return tag() == other.tag(); } 0043 0044 //! equal to operator 0045 bool operator == (const std::string& other ) const 0046 { return tag() == other; } 0047 0048 //! less than operator 0049 bool operator < (const Option& other ) const 0050 { return tag() < other.tag(); } 0051 0052 //! tag 0053 const std::string& tag( void ) const 0054 { return _tag; } 0055 0056 //! value 0057 const std::string& value( void ) const 0058 { return _value; } 0059 0060 #if OXYGEN_DEBUG 0061 //! set filename from where option was read 0062 void setFile( const std::string& file ) 0063 { _file = file; } 0064 #endif 0065 0066 //! convert to integer 0067 int toInt( int defaultValue ) const 0068 { return toVariant<int>( defaultValue ); } 0069 0070 template< typename T> T toVariant( T = T() ) const; 0071 0072 class Set: public std::set<Option> 0073 { 0074 public: 0075 0076 //! equal to operator 0077 /*! 0078 it differs from the stl version, based on Option equal to operator 0079 in that it is more strict. This is needed to actually track option 0080 changes prior to reloading */ 0081 inline bool operator == (const Set& ) const; 0082 0083 }; 0084 0085 #if OXYGEN_DEBUG 0086 protected: 0087 const std::string& file( void ) const 0088 { return _file; } 0089 #endif 0090 0091 private: 0092 0093 //! tag 0094 std::string _tag; 0095 0096 //! value 0097 std::string _value; 0098 0099 //! file (used for debugging) 0100 std::string _file; 0101 0102 //! streamer 0103 friend std::ostream& operator << (std::ostream& out, const Option& option ) 0104 { 0105 out << option.tag() << "=" << option.value(); 0106 0107 #if OXYGEN_DEBUG 0108 if( !option.file().empty() ) 0109 { out << " (" << option.file() << ")"; } 0110 #endif 0111 0112 return out; 0113 } 0114 0115 //! streamer 0116 friend std::ostream& operator << (std::ostream& out, const Option::Set& options ) 0117 { 0118 for( Option::Set::const_iterator iter = options.begin(); iter != options.end(); ++iter ) 0119 { out << *iter << std::endl; } 0120 0121 return out; 0122 } 0123 0124 }; 0125 0126 //_______________________________________________________________________ 0127 template<typename T> T Option::toVariant( T defaultValue ) const 0128 { 0129 0130 T out; 0131 std::istringstream stream( _value ); 0132 return ( stream >> out ) ? out:defaultValue; 0133 } 0134 0135 // specialization of template to correctly handle std::string with spaces 0136 template<> std::string Option::toVariant( std::string defaultValue ) const; 0137 0138 //_______________________________________________________________________ 0139 bool Option::Set::operator == (const Option::Set& other ) const 0140 { 0141 const_iterator firstIter = begin(); 0142 const_iterator secondIter = other.begin(); 0143 for(;firstIter != end() && secondIter != other.end(); ++firstIter, ++secondIter ) 0144 { 0145 if( firstIter->_tag != secondIter->_tag || firstIter->_value != secondIter->_value ) 0146 { return false; } 0147 } 0148 0149 return firstIter == end() && secondIter == other.end(); 0150 } 0151 0152 } 0153 0154 #endif