1 /* 2 * this file is part of the oxygen gtk engine 3 * Copyright (c) 2010 Hugo Pereira Da Costa <hugo.pereira@free.fr> 4 * 5 * This library is free software; you can redistribute it and/or 6 * modify it under the terms of the GNU Lesser General Public 7 * License as published by the Free Software Foundation; either 8 * version 2 of the License, or( at your option ) any later version. 9 * 10 * This library is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 * Lesser General Public License for more details. 14 * 15 * You should have received a copy of the GNU Lesser General Public 16 * License along with this library; if not, write to the Free 17 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, 18 * MA 02110-1301, USA. 19 */ 20 21 #include "oxygengtkrc.h" 22 23 #include <gtk/gtk.h> 24 #include <algorithm> 25 #include <cassert> 26 27 namespace Oxygen 28 { 29 30 //_________________________________________________ 31 const std::string Gtk::RC::_headerSectionName = "__head__"; 32 const std::string Gtk::RC::_rootSectionName = "__root__"; 33 const std::string Gtk::RC::_defaultSectionName = "oxygen-default-internal"; 34 35 //_________________________________________________ commit(void)36 void Gtk::RC::commit( void ) 37 { 38 gtk_rc_parse_string( toString().c_str() ); 39 clear(); 40 } 41 42 //_________________________________________________ merge(const Gtk::RC & other)43 void Gtk::RC::merge( const Gtk::RC& other ) 44 { 45 46 // loop over sections in other 47 for( Section::List::const_iterator iter = other._sections.begin(); iter != other._sections.end(); ++iter ) 48 { 49 Section::List::iterator sectionIter = std::find_if( _sections.begin(), _sections.end(), Section::SameNameFTor( *iter ) ); 50 if( sectionIter == _sections.end() ) _sections.push_back( *iter ); 51 else { 52 53 assert( sectionIter->_parent == iter->_parent ); 54 sectionIter->add( iter->_content ); 55 56 } 57 58 } 59 60 return; 61 } 62 63 //_________________________________________________ addSection(const std::string & name,const std::string & parent)64 void Gtk::RC::addSection( const std::string& name, const std::string& parent ) 65 { 66 if( std::find( _sections.begin(), _sections.end(), name ) != _sections.end() ) 67 { 68 69 std::cerr << "Gtk::RC::addSection - section named " << name << " already exists" << std::endl; 70 71 } else { 72 73 _sections.push_back( Section( name, parent ) ); 74 75 } 76 77 setCurrentSection( name ); 78 79 } 80 81 //_________________________________________________ addToSection(const std::string & name,const std::string & content)82 void Gtk::RC::addToSection( const std::string& name, const std::string& content ) 83 { 84 Section::List::iterator iter( std::find( _sections.begin(), _sections.end(), name ) ); 85 if( iter == _sections.end() ) 86 { 87 std::cerr << "Gtk::RC::addToSection - unable to find section named " << name << std::endl; 88 return; 89 } 90 91 iter->add( content ); 92 } 93 94 //_________________________________________________ matchClassToSection(const std::string & content,const std::string & name)95 void Gtk::RC::matchClassToSection( const std::string& content, const std::string& name ) 96 { 97 if( std::find( _sections.begin(), _sections.end(), name ) == _sections.end() ) 98 { std::cerr << "Gtk::RC::matchClassToSection - unable to find section named " << name << std::endl; } 99 100 std::ostringstream what; 101 what << "class \"" << content << "\" style \"" << name << "\""; 102 addToRootSection( what.str() ); 103 } 104 105 //_________________________________________________ matchWidgetToSection(const std::string & content,const std::string & name)106 void Gtk::RC::matchWidgetToSection( const std::string& content, const std::string& name ) 107 { 108 if( std::find( _sections.begin(), _sections.end(), name ) == _sections.end() ) 109 { std::cerr << "Gtk::RC::matchWidgetToSection - unable to find section named " << name << std::endl; } 110 111 std::ostringstream what; 112 what << "widget \"" << content << "\" style \"" << name << "\""; 113 addToRootSection( what.str() ); 114 } 115 116 //_________________________________________________ matchWidgetClassToSection(const std::string & content,const std::string & name)117 void Gtk::RC::matchWidgetClassToSection( const std::string& content, const std::string& name ) 118 { 119 if( std::find( _sections.begin(), _sections.end(), name ) == _sections.end() ) 120 { std::cerr << "Gtk::RC::matchWidgetClassToSection - unable to find section named " << name << std::endl; } 121 122 std::ostringstream what; 123 what << "widget_class \"" << content << "\" style \"" << name << "\""; 124 addToRootSection( what.str() ); 125 } 126 127 //_________________________________________________ setCurrentSection(const std::string & name)128 void Gtk::RC::setCurrentSection( const std::string& name ) 129 { 130 if( std::find( _sections.begin(), _sections.end(), name ) == _sections.end() ) 131 { 132 133 std::cerr << "Gtk::RC::setCurrentSection - unable to find section named " << name << std::endl; 134 return; 135 136 } else { 137 138 _currentSection = name; 139 140 } 141 } 142 143 //_________________________________________________ add(const Gtk::RC::Section::ContentList & content)144 void Gtk::RC::Section::add( const Gtk::RC::Section::ContentList& content ) 145 { 146 for( ContentList::const_iterator iter = content.begin(); iter != content.end(); ++iter ) 147 { 148 if( std::find( _content.begin(), _content.end(), *iter ) == _content.end() ) 149 { _content.push_back( *iter ); } 150 } 151 } 152 153 namespace Gtk 154 { 155 //_______________________________________________________________________ operator <<(std::ostream & out,const RC::Section & section)156 std::ostream& operator << (std::ostream& out, const RC::Section& section ) 157 { 158 if( section._name == RC::_rootSectionName || section._name == RC::_headerSectionName ) 159 { 160 161 // add contents 162 for( RC::Section::ContentList::const_iterator iter = section._content.begin(); iter != section._content.end(); ++iter ) 163 { out << *iter << std::endl; } 164 165 } else { 166 167 out << "style \"" << section._name << "\""; 168 if( !section._parent.empty() ) out << " = \"" << section._parent << "\""; 169 out << std::endl; 170 out << "{" << std::endl; 171 172 // add contents 173 for( RC::Section::ContentList::const_iterator iter = section._content.begin(); iter != section._content.end(); ++iter ) 174 { out << *iter << std::endl; } 175 176 out << "}" << std::endl; 177 178 } 179 180 return out; 181 } 182 183 //_______________________________________________________________________ operator <<(std::ostream & out,const RC & rc)184 std::ostream& operator << (std::ostream& out, const RC& rc ) 185 { 186 // dump header section 187 RC::Section::List::const_iterator iter( std::find( rc._sections.begin(), rc._sections.end(), RC::_headerSectionName ) ); 188 assert( iter != rc._sections.end() ); 189 out << *iter << std::endl; 190 191 // dump all section except root 192 for( RC::Section::List::const_iterator iter = rc._sections.begin(); iter != rc._sections.end(); ++iter ) 193 { if( !(*iter == RC::_rootSectionName || *iter == RC::_headerSectionName ) ) out << *iter << std::endl; } 194 195 // dump root section 196 iter = std::find( rc._sections.begin(), rc._sections.end(), RC::_rootSectionName ); 197 assert( iter != rc._sections.end() ); 198 out << *iter << std::endl; 199 200 return out; 201 } 202 203 } 204 } 205