kdecore Library API Documentation

kconfigdialogmanager.cpp

00001 /*
00002  *  This file is part of the KDE libraries
00003  *  Copyright (C) 2003 Benjamin C Meyer (ben+kdelibs at meyerhome dot net)
00004  *  Copyright (C) 2003 Waldo Bastian <bastian@kde.org>
00005  *
00006  *  This library is free software; you can redistribute it and/or
00007  *  modify it under the terms of the GNU Library General Public
00008  *  License as published by the Free Software Foundation; either
00009  *  version 2 of the License, or (at your option) any later version.
00010  *
00011  *  This library is distributed in the hope that it will be useful,
00012  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00013  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014  *  Library General Public License for more details.
00015  *
00016  *  You should have received a copy of the GNU Library General Public License
00017  *  along with this library; see the file COPYING.LIB.  If not, write to
00018  *  the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00019  *  Boston, MA 02111-1307, USA.
00020  */
00021 
00022 #include "kconfigdialogmanager.h"
00023 
00024 #include <qlabel.h>
00025 #include <qobjectlist.h>
00026 #include <qbuttongroup.h>
00027 #include <qcombobox.h>
00028 #include <qsqlpropertymap.h>
00029 #include <qmetaobject.h>
00030 
00031 #include <kapplication.h>
00032 #include <kconfigskeleton.h>
00033 #include <kdebug.h>
00034 #include <kglobal.h>
00035 
00036 #include <assert.h>
00037 
00038 class KConfigDialogManager::Private {
00039 
00040 public:
00041   Private() { }
00042 
00043 public:
00044   QDict<QWidget> knownWidget;
00045   QDict<QWidget> buddyWidget;
00046 };
00047 
00048 KConfigDialogManager::KConfigDialogManager(QWidget *parent, KConfigSkeleton *conf, const char *name)
00049  : QObject(parent, name), m_conf(conf), m_dialog(parent) 
00050 {
00051   d = new Private();
00052   
00053   kapp->installKDEPropertyMap();
00054   propertyMap = QSqlPropertyMap::defaultMap();
00055   
00056   init(true);
00057 }
00058 
00059 KConfigDialogManager::~KConfigDialogManager()
00060 {
00061   delete d;
00062 }
00063 
00064 void KConfigDialogManager::init(bool trackChanges)
00065 {
00066   if(trackChanges)
00067   {
00068     // QT
00069     changedMap.insert("QButton", SIGNAL(stateChanged(int)));
00070     changedMap.insert("QCheckBox", SIGNAL(stateChanged(int)));
00071     changedMap.insert("QPushButton", SIGNAL(stateChanged(int)));
00072     changedMap.insert("QRadioButton", SIGNAL(stateChanged(int)));
00073     changedMap.insert("QButtonGroup", SIGNAL(clicked(int)));
00074     changedMap.insert("QComboBox", SIGNAL(activated (int)));
00075     //qsqlproperty map doesn't store the text, but the value!
00076     //changedMap.insert("QComboBox", SIGNAL(textChanged(const QString &)));
00077     changedMap.insert("QDateEdit", SIGNAL(valueChanged(const QDate &)));
00078     changedMap.insert("QDateTimeEdit", SIGNAL(valueChanged(const QDateTime &)));
00079     changedMap.insert("QDial", SIGNAL(valueChanged (int)));
00080     changedMap.insert("QLineEdit", SIGNAL(textChanged(const QString &)));
00081     changedMap.insert("QSlider", SIGNAL(valueChanged(int)));
00082     changedMap.insert("QSpinBox", SIGNAL(valueChanged(int)));
00083     changedMap.insert("QTimeEdit", SIGNAL(valueChanged(const QTime &)));
00084     changedMap.insert("QTextEdit", SIGNAL(textChanged()));
00085     changedMap.insert("QTextBrowser", SIGNAL(sourceChanged(const QString &)));
00086     changedMap.insert("QMultiLineEdit", SIGNAL(textChanged()));
00087     changedMap.insert("QListBox", SIGNAL(selectionChanged()));
00088     changedMap.insert("QTabWidget", SIGNAL(currentChanged(QWidget *)));
00089 
00090     // KDE
00091     changedMap.insert( "KComboBox", SIGNAL(activated (int)));
00092     changedMap.insert( "KFontCombo", SIGNAL(activated (int)));
00093     changedMap.insert( "KFontRequester", SIGNAL(fontSelected(const QFont &)));
00094     changedMap.insert( "KFontChooser",  SIGNAL(fontSelected(const QFont &)));
00095     changedMap.insert( "KHistoryCombo", SIGNAL(activated (int)));
00096 
00097     changedMap.insert( "KColorButton", SIGNAL(changed(const QColor &)));
00098     changedMap.insert( "KDatePicker", SIGNAL(dateSelected (QDate)));
00099     changedMap.insert( "KEditListBox", SIGNAL(changed()));
00100     changedMap.insert( "KListBox", SIGNAL(selectionChanged()));
00101     changedMap.insert( "KLineEdit", SIGNAL(textChanged(const QString &)));
00102     changedMap.insert( "KPasswordEdit", SIGNAL(textChanged(const QString &)));
00103     changedMap.insert( "KRestrictedLine", SIGNAL(textChanged(const QString &)));
00104     changedMap.insert( "KTextBrowser", SIGNAL(sourceChanged(const QString &)));
00105     changedMap.insert( "KTextEdit", SIGNAL(textChanged()));
00106     changedMap.insert( "KURLRequester",  SIGNAL(textChanged (const QString& )));
00107     changedMap.insert( "KIntNumInput", SIGNAL(valueChanged (int)));
00108     changedMap.insert( "KIntSpinBox", SIGNAL(valueChanged (int)));
00109     changedMap.insert( "KDoubleNumInput", SIGNAL(valueChanged (double)));
00110   }
00111 
00112   // Go through all of the children of the widgets and find all known widgets
00113   (void) parseChildren(m_dialog, trackChanges);
00114 }
00115 
00116 void KConfigDialogManager::addWidget(QWidget *widget)
00117 {
00118   (void) parseChildren(widget, true);
00119 }
00120 
00121 void KConfigDialogManager::setupWidget(QWidget *widget, KConfigSkeletonItem *item)
00122 {
00123   QVariant minValue = item->minValue();
00124   if (minValue.isValid())
00125   {
00126     if (widget->metaObject()->findProperty("minValue", true) != -1)
00127        widget->setProperty("minValue", minValue);
00128   }
00129   QVariant maxValue = item->maxValue();
00130   if (maxValue.isValid())
00131   {
00132     if (widget->metaObject()->findProperty("maxValue", true) != -1)
00133        widget->setProperty("maxValue", maxValue);
00134   }
00135 }
00136 
00137 bool KConfigDialogManager::parseChildren(const QWidget *widget, bool trackChanges)
00138 {
00139   bool valueChanged = false;
00140   const QObjectList *listOfChildren = widget->children();
00141   if(!listOfChildren)
00142     return valueChanged;
00143 
00144   QObject *object;
00145   for( QPtrListIterator<QObject> it( *listOfChildren );
00146        (object = it.current()); ++it )
00147   {
00148     if(!object->isWidgetType())
00149       continue; // Skip non-widgets
00150 
00151     QWidget *childWidget = (QWidget *)object;
00152 
00153     const char *widgetName = childWidget->name(0);
00154     bool bParseChildren = true;
00155     
00156     if (widgetName && (strncmp(widgetName, "kcfg_", 5) == 0))
00157     {
00158       // This is one of our widgets!
00159       QString configId = widgetName+5;
00160       KConfigSkeletonItem *item = m_conf->findItem(configId);
00161       if (item)
00162       {
00163         d->knownWidget.insert(configId, childWidget);
00164 
00165         setupWidget(childWidget, item);
00166 
00167         QMap<QString, QCString>::const_iterator changedIt = changedMap.find(childWidget->className());
00168         if (changedIt == changedMap.end())
00169         {
00170           kdWarning(178) << "Don't know how to monitor widget '" << childWidget->className() << "' for changes!" << endl;
00171         }
00172         else
00173         {
00174           connect(childWidget, *changedIt,
00175                   this, SIGNAL(widgetModified()));
00176 
00177           QButtonGroup *bg = dynamic_cast<QButtonGroup *>(childWidget);
00178           if (!bg)
00179             bParseChildren = false;
00180 
00181           QComboBox *cb = dynamic_cast<QComboBox *>(childWidget);
00182           if (cb && cb->editable())
00183             connect(cb, SIGNAL(textChanged(const QString &)),
00184                     this, SIGNAL(widgetModified()));
00185         }
00186       }
00187       else
00188       {
00189         kdWarning(178) << "A widget named '" << widgetName << "' was found but there is no setting named '" << configId << "'" << endl;
00190         assert(false);
00191       }
00192     }
00193     else if (childWidget->inherits("QLabel"))
00194     {
00195       QLabel *label = static_cast<QLabel *>(childWidget);
00196       QWidget *buddy = label->buddy();
00197       if (!buddy)
00198         continue;
00199       const char *buddyName = buddy->name(0);
00200       if (buddyName && (strncmp(buddyName, "kcfg_", 5) == 0))
00201       {
00202         // This is one of our widgets!
00203         QString configId = buddyName+5;
00204         d->buddyWidget.insert(configId, childWidget);
00205       }
00206     }
00207     else if (widgetName)
00208     {
00209       QMap<QString, QCString>::const_iterator changedIt = changedMap.find(childWidget->className());
00210       if (changedIt != changedMap.end())
00211         kdDebug(178) << "Widget '" << widgetName << "' (" << childWidget->className() << ") remains unmanaged." << endl;
00212     }
00213     
00214     if(bParseChildren)
00215     {
00216       // this widget is not known as something we can store.
00217       // Maybe we can store one of its children.
00218       valueChanged |= parseChildren(childWidget, trackChanges);
00219     }
00220   }
00221   return valueChanged;
00222 }
00223 
00224 void KConfigDialogManager::updateWidgets()
00225 {
00226   bool bSignalsBlocked = signalsBlocked();
00227   blockSignals(true);
00228 
00229   QWidget *widget;
00230   for( QDictIterator<QWidget> it( d->knownWidget );
00231        (widget = it.current()); ++it )
00232   {
00233      KConfigSkeletonItem *item = m_conf->findItem(it.currentKey());
00234      if (!item)
00235      {
00236         kdWarning(178) << "The setting '" << it.currentKey() << "' has disappeared!" << endl;
00237         continue;
00238      }
00239 
00240      QVariant p = item->property();
00241      if (p != property(widget))
00242      {
00243         setProperty(widget, p);
00244      }
00245      if (item->isImmutable())
00246      {
00247         widget->setEnabled(false);
00248         QWidget *buddy = d->buddyWidget.find(it.currentKey());
00249         if (buddy)
00250            buddy->setEnabled(false);
00251      }
00252   }
00253   blockSignals(bSignalsBlocked);
00254 }
00255 
00256 void KConfigDialogManager::updateWidgetsDefault()
00257 {
00258   bool bUseDefaults = m_conf->useDefaults(true);
00259   updateWidgets();
00260   m_conf->useDefaults(bUseDefaults);
00261 }
00262 
00263 void KConfigDialogManager::updateSettings()
00264 {
00265   bool changed = false;
00266 
00267   QWidget *widget;
00268   for( QDictIterator<QWidget> it( d->knownWidget );
00269        (widget = it.current()); ++it )
00270   {
00271      KConfigSkeletonItem *item = m_conf->findItem(it.currentKey());
00272      if (!item)
00273      {
00274         kdWarning(178) << "The setting '" << it.currentKey() << "' has disappeared!" << endl;
00275         continue;
00276      }
00277 
00278      QVariant p = property(widget);
00279      if (p != item->property())
00280      {
00281         item->setProperty(p);
00282         changed = true;
00283      }
00284   }
00285   if (changed)
00286   {
00287      m_conf->writeConfig();
00288      emit settingsChanged();
00289   }
00290 }
00291 
00292 void KConfigDialogManager::setProperty(QWidget *w, const QVariant &v)
00293 {
00294   QButtonGroup *bg = dynamic_cast<QButtonGroup *>(w);
00295   if (bg)
00296   {
00297     bg->setButton(v.toInt());
00298     return;
00299   }
00300 
00301   QComboBox *cb = dynamic_cast<QComboBox *>(w);
00302   if (cb && cb->editable())
00303   {
00304     cb->setCurrentText(v.toString());
00305     return;
00306   }
00307 
00308   propertyMap->setProperty(w, v);
00309 }
00310 
00311 QVariant KConfigDialogManager::property(QWidget *w)
00312 {
00313   QButtonGroup *bg = dynamic_cast<QButtonGroup *>(w);
00314   if (bg)
00315     return QVariant(bg->selectedId());
00316 
00317   QComboBox *cb = dynamic_cast<QComboBox *>(w);
00318   if (cb && cb->editable())
00319       return QVariant(cb->currentText());
00320 
00321   return propertyMap->property(w);
00322 }
00323 
00324 bool KConfigDialogManager::hasChanged()
00325 {
00326 
00327   QWidget *widget;
00328   for( QDictIterator<QWidget> it( d->knownWidget );
00329        (widget = it.current()); ++it )
00330   {
00331      KConfigSkeletonItem *item = m_conf->findItem(it.currentKey());
00332      if (!item)
00333      {
00334         kdWarning(178) << "The setting '" << it.currentKey() << "' has disappeared!" << endl;
00335         continue;
00336      }
00337 
00338      QVariant p = property(widget);
00339      if (p != item->property())
00340      {
00341 //      kdDebug(178) << "Widget for '" << it.currentKey() << "' has changed." << endl;
00342         return true;
00343      }
00344   }
00345   return false;
00346 }
00347 
00348 bool KConfigDialogManager::isDefault()
00349 {
00350   bool bUseDefaults = m_conf->useDefaults(true);
00351   bool result = !hasChanged();
00352   m_conf->useDefaults(bUseDefaults);
00353   return result;
00354 }
00355 
00356 #include "kconfigdialogmanager.moc"
00357 
KDE Logo
This file is part of the documentation for kdecore Library Version 3.2.2.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Tue Feb 14 09:16:05 2006 by doxygen 1.3.6 written by Dimitri van Heesch, © 1997-2003