Make ping timeouts and auto-WHO configurable
authorManuel Nickschas <sputnick@quassel-irc.org>
Tue, 21 Jul 2009 22:33:58 +0000 (00:33 +0200)
committerManuel Nickschas <sputnick@quassel-irc.org>
Tue, 21 Jul 2009 22:33:58 +0000 (00:33 +0200)
A new [Core]NetworkConfig object allows configuring global network parameters. This adds
a new settingspage (Misc -> Connection) that allows configuring the dreaded "active ping timeouts" that
hit some people, and also auto-WHO (tracking users' away status) can now be disabled or modified.

18 files changed:
src/client/client.cpp
src/client/client.h
src/common/CMakeLists.txt
src/common/networkconfig.cpp [new file with mode: 0644]
src/common/networkconfig.h [new file with mode: 0644]
src/core/CMakeLists.txt
src/core/core.h
src/core/corenetwork.cpp
src/core/corenetwork.h
src/core/corenetworkconfig.cpp [new file with mode: 0644]
src/core/corenetworkconfig.h [new file with mode: 0644]
src/core/coresession.cpp
src/core/coresession.h
src/qtui/mainwin.cpp
src/qtui/settingspages/connectionsettingspage.cpp [new file with mode: 0644]
src/qtui/settingspages/connectionsettingspage.h [new file with mode: 0644]
src/qtui/settingspages/connectionsettingspage.ui [new file with mode: 0644]
src/qtui/settingspages/settingspages.inc

index 733ba54..c25f193 100644 (file)
@@ -39,6 +39,7 @@
 #include "message.h"
 #include "messagemodel.h"
 #include "network.h"
+#include "networkconfig.h"
 #include "networkmodel.h"
 #include "quassel.h"
 #include "signalproxy.h"
@@ -89,6 +90,7 @@ Client::Client(QObject *parent)
     _bufferViewOverlay(new BufferViewOverlay(this)),
     _ircListHelper(new ClientIrcListHelper(this)),
     _inputHandler(0),
+    _networkConfig(0),
     _messageModel(0),
     _messageProcessor(0),
     _connectedToCore(false),
@@ -329,6 +331,11 @@ void Client::setSyncedToCore() {
   connect(aliasManager(), SIGNAL(initDone()), SLOT(sendBufferedUserInput()));
   signalProxy()->synchronize(aliasManager());
 
+  // create NetworkConfig
+  Q_ASSERT(!_networkConfig);
+  _networkConfig = new NetworkConfig("GlobalNetworkConfig", this);
+  signalProxy()->synchronize(networkConfig());
+
   // trigger backlog request once all active bufferviews are initialized
   connect(bufferViewOverlay(), SIGNAL(initDone()), this, SLOT(requestInitialBacklog()));
 
@@ -417,6 +424,10 @@ void Client::disconnectedFromCore() {
   }
   Q_ASSERT(_identities.isEmpty());
 
+  if(_networkConfig) {
+    _networkConfig->deleteLater();
+    _networkConfig = 0;
+  }
 }
 
 /*** ***/
index 4787731..57c4909 100644 (file)
@@ -51,6 +51,7 @@ class ClientSyncer;
 class ClientUserInputHandler;
 class IrcUser;
 class IrcChannel;
+class NetworkConfig;
 class SignalProxy;
 struct NetworkInfo;
 
@@ -110,6 +111,7 @@ public:
   static inline ClientBufferViewManager *bufferViewManager() { return instance()->_bufferViewManager; }
   static inline BufferViewOverlay *bufferViewOverlay() { return instance()->_bufferViewOverlay; }
   static inline ClientUserInputHandler *inputHandler() { return instance()->_inputHandler; }
+  static inline NetworkConfig *networkConfig() { return instance()->_networkConfig; }
 
   static AccountId currentCoreAccount();
 
@@ -215,6 +217,7 @@ private:
   BufferViewOverlay *_bufferViewOverlay;
   ClientIrcListHelper *_ircListHelper;
   ClientUserInputHandler *_inputHandler;
+  NetworkConfig *_networkConfig;
 
   MessageModel *_messageModel;
   AbstractMessageProcessor *_messageProcessor;
index fae257d..7c883a9 100644 (file)
@@ -18,6 +18,7 @@ set(SOURCES
     logger.cpp
     message.cpp
     network.cpp
+    networkconfig.cpp
     quassel.cpp
     settings.cpp
     signalproxy.cpp
@@ -43,6 +44,7 @@ set(MOC_HDRS
     irclisthelper.h
     ircuser.h
     network.h
+    networkconfig.h
     settings.h
     signalproxy.h
     syncableobject.h)
diff --git a/src/common/networkconfig.cpp b/src/common/networkconfig.cpp
new file mode 100644 (file)
index 0000000..dea582e
--- /dev/null
@@ -0,0 +1,90 @@
+/***************************************************************************
+ *   Copyright (C) 2005-09 by the Quassel Project                          *
+ *   devel@quassel-irc.org                                                 *
+ *                                                                         *
+ *   This program is free software; you can redistribute it and/or modify  *
+ *   it under the terms of the GNU General Public License as published by  *
+ *   the Free Software Foundation; either version 2 of the License, or     *
+ *   (at your option) version 3.                                           *
+ *                                                                         *
+ *   This program is distributed in the hope that it will be useful,       *
+ *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
+ *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
+ *   GNU General Public License for more details.                          *
+ *                                                                         *
+ *   You should have received a copy of the GNU General Public License     *
+ *   along with this program; if not, write to the                         *
+ *   Free Software Foundation, Inc.,                                       *
+ *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
+ ***************************************************************************/
+
+#include "networkconfig.h"
+
+NetworkConfig::NetworkConfig(const QString &objectName, QObject *parent)
+: SyncableObject(objectName, parent),
+  _pingTimeoutEnabled(true),
+  _pingInterval(30),
+  _maxPingCount(6),
+  _autoWhoEnabled(true),
+  _autoWhoInterval(90),
+  _autoWhoNickLimit(200),
+  _autoWhoDelay(5)
+{
+
+}
+
+void NetworkConfig::setPingTimeoutEnabled(bool enabled) {
+  if(_pingTimeoutEnabled == enabled)
+    return;
+
+  _pingTimeoutEnabled = enabled;
+  emit pingTimeoutEnabledSet(enabled);
+}
+
+void NetworkConfig::setPingInterval(int interval) {
+  if(_pingInterval == interval)
+    return;
+
+  _pingInterval = interval;
+  emit pingIntervalSet(interval);
+}
+
+void NetworkConfig::setMaxPingCount(int count) {
+  if(_maxPingCount == count)
+    return;
+
+  _maxPingCount = count;
+  emit maxPingCountSet(count);
+}
+
+void NetworkConfig::setAutoWhoEnabled(bool enabled) {
+  if(_autoWhoEnabled == enabled)
+    return;
+
+  _autoWhoEnabled = enabled;
+  emit autoWhoEnabledSet(enabled);
+}
+
+void NetworkConfig::setAutoWhoInterval(int interval) {
+  if(_autoWhoInterval == interval)
+    return;
+
+  _autoWhoInterval = interval;
+  emit autoWhoIntervalSet(interval);
+}
+
+void NetworkConfig::setAutoWhoNickLimit(int nickLimit) {
+  if(_autoWhoNickLimit == nickLimit)
+    return;
+
+  _autoWhoNickLimit = nickLimit;
+  emit autoWhoNickLimitSet(nickLimit);
+}
+
+void NetworkConfig::setAutoWhoDelay(int delay) {
+  if(_autoWhoDelay == delay)
+    return;
+
+  _autoWhoDelay = delay;
+  emit autoWhoDelaySet(delay);
+}
diff --git a/src/common/networkconfig.h b/src/common/networkconfig.h
new file mode 100644 (file)
index 0000000..8f61363
--- /dev/null
@@ -0,0 +1,98 @@
+/***************************************************************************
+ *   Copyright (C) 2005-09 by the Quassel Project                          *
+ *   devel@quassel-irc.org                                                 *
+ *                                                                         *
+ *   This program is free software; you can redistribute it and/or modify  *
+ *   it under the terms of the GNU General Public License as published by  *
+ *   the Free Software Foundation; either version 2 of the License, or     *
+ *   (at your option) version 3.                                           *
+ *                                                                         *
+ *   This program is distributed in the hope that it will be useful,       *
+ *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
+ *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
+ *   GNU General Public License for more details.                          *
+ *                                                                         *
+ *   You should have received a copy of the GNU General Public License     *
+ *   along with this program; if not, write to the                         *
+ *   Free Software Foundation, Inc.,                                       *
+ *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
+ ***************************************************************************/
+
+#ifndef NETWORKCONFIG_H_
+#define NETWORKCONFIG_H_
+
+#include "syncableobject.h"
+
+class NetworkConfig : public SyncableObject {
+  Q_OBJECT
+  Q_PROPERTY(bool pingTimeoutEnabled READ pingTimeoutEnabled WRITE setPingTimeoutEnabled)
+  Q_PROPERTY(int pingInterval READ pingInterval WRITE setPingInterval)
+  Q_PROPERTY(int maxPingCount READ maxPingCount WRITE setMaxPingCount)
+  Q_PROPERTY(bool autoWhoEnabled READ autoWhoEnabled WRITE setAutoWhoEnabled)
+  Q_PROPERTY(int autoWhoInterval READ autoWhoInterval WRITE setAutoWhoInterval)
+  Q_PROPERTY(int autoWhoNickLimit READ autoWhoNickLimit WRITE setAutoWhoNickLimit)
+  Q_PROPERTY(int autoWhoDelay READ autoWhoDelay WRITE setAutoWhoDelay)
+
+public:
+  NetworkConfig(const QString &objectName = "GlobalNetworkConfig", QObject *parent = 0);
+
+  inline virtual const QMetaObject *syncMetaObject() const { return &staticMetaObject; }
+
+public slots:
+  inline bool pingTimeoutEnabled() const { return _pingTimeoutEnabled; }
+  void setPingTimeoutEnabled(bool);
+  virtual inline void requestSetPingTimeoutEnabled(bool b) { emit setPingTimeoutEnabledRequested(b); }
+
+  inline int pingInterval() const { return _pingInterval; }
+  void setPingInterval(int);
+  virtual inline void requestSetPingInterval(int i) { emit setPingIntervalRequested(i); }
+
+  inline int maxPingCount() const { return _maxPingCount; }
+  void setMaxPingCount(int);
+  virtual inline void requestSetMaxPingCount(int i) { emit setMaxPingCountRequested(i); }
+
+  inline bool autoWhoEnabled() const { return _autoWhoEnabled; }
+  void setAutoWhoEnabled(bool);
+  virtual inline void requestSetAutoWhoEnabled(bool b) { emit setAutoWhoEnabledRequested(b); }
+
+  inline int autoWhoInterval() const { return _autoWhoInterval; }
+  void setAutoWhoInterval(int);
+  virtual inline void requestSetAutoWhoInterval(int i) { emit setAutoWhoIntervalRequested(i); }
+
+  inline int autoWhoNickLimit() const { return _autoWhoNickLimit; }
+  void setAutoWhoNickLimit(int);
+  virtual inline void requestSetAutoWhoNickLimit(int i) { emit setAutoWhoNickLimitRequested(i); }
+
+  inline int autoWhoDelay() const { return _autoWhoDelay; }
+  void setAutoWhoDelay(int);
+  virtual inline void requestSetAutoWhoDelay(int i) { emit setAutoWhoDelayRequested(i); }
+
+signals:
+  void pingTimeoutEnabledSet(bool);
+  void pingIntervalSet(int);
+  void maxPingCountSet(int);
+  void autoWhoEnabledSet(bool);
+  void autoWhoIntervalSet(int);
+  void autoWhoNickLimitSet(int);
+  void autoWhoDelaySet(int);
+
+  void setPingTimeoutEnabledRequested(bool);
+  void setPingIntervalRequested(int);
+  void setMaxPingCountRequested(int);
+  void setAutoWhoEnabledRequested(bool);
+  void setAutoWhoIntervalRequested(int);
+  void setAutoWhoNickLimitRequested(int);
+  void setAutoWhoDelayRequested(int);
+
+private:
+  bool _pingTimeoutEnabled;
+  int _pingInterval;
+  int _maxPingCount;
+
+  bool _autoWhoEnabled;
+  int _autoWhoInterval;
+  int _autoWhoNickLimit;
+  int _autoWhoDelay;
+};
+
+#endif
index 1713760..3ec5df2 100644 (file)
@@ -21,6 +21,7 @@ set(SOURCES
     coreircchannel.cpp
     coreirclisthelper.cpp
     corenetwork.cpp
+    corenetworkconfig.cpp
     coresession.cpp
     coresettings.cpp
     coreusersettings.cpp
@@ -47,6 +48,7 @@ set(MOC_HDRS
     coreircchannel.h
     coreirclisthelper.h
     corenetwork.h
+    corenetworkconfig.h
     coresession.h
     ctcphandler.h
     ircserverhandler.h
index c1f397a..49910a9 100644 (file)
@@ -75,11 +75,11 @@ public:
   /**
    * \param userId       The users Id
    * \param settingName  The Name of the Setting
-   * \param default      Value to return in case it's unset.
+   * \param defaultValue Value to return in case it's unset.
    * \return the Value of the Setting or the default value if it is unset.
    */
-  static inline QVariant getUserSetting(UserId userId, const QString &settingName, const QVariant &data = QVariant()) {
-    return instance()->_storage->getUserSetting(userId, settingName, data);
+  static inline QVariant getUserSetting(UserId userId, const QString &settingName, const QVariant &defaultValue = QVariant()) {
+    return instance()->_storage->getUserSetting(userId, settingName, defaultValue);
   }
 
   /* Identity handling */
index 81c92cb..21415ae 100644 (file)
@@ -23,6 +23,7 @@
 #include "core.h"
 #include "coresession.h"
 #include "coreidentity.h"
+#include "corenetworkconfig.h"
 
 #include "ircserverhandler.h"
 #include "userinputhandler.h"
@@ -41,37 +42,36 @@ CoreNetwork::CoreNetwork(const NetworkId &networkid, CoreSession *session)
     _lastUsedServerIndex(0),
 
     _lastPingTime(0),
-    _maxPingCount(3),
-    _pingCount(0),
-
-    // TODO make autowho configurable (possibly per-network)
-    _autoWhoEnabled(true),
-    _autoWhoInterval(90),
-    _autoWhoNickLimit(0), // unlimited
-    _autoWhoDelay(5)
+    _pingCount(0)
+
 {
   _autoReconnectTimer.setSingleShot(true);
   _socketCloseTimer.setSingleShot(true);
   connect(&_socketCloseTimer, SIGNAL(timeout()), this, SLOT(socketCloseTimeout()));
 
-  _pingTimer.setInterval(30000);
+  setPingInterval(networkConfig()->pingInterval());
   connect(&_pingTimer, SIGNAL(timeout()), this, SLOT(sendPing()));
 
-  _autoWhoTimer.setInterval(_autoWhoDelay * 1000);
-  _autoWhoCycleTimer.setInterval(_autoWhoInterval * 1000);
+  setAutoWhoDelay(networkConfig()->autoWhoDelay());
+  setAutoWhoInterval(networkConfig()->autoWhoInterval());
 
   QHash<QString, QString> channels = coreSession()->persistentChannels(networkId());
   foreach(QString chan, channels.keys()) {
     _channelKeys[chan.toLower()] = channels[chan];
   }
 
+  connect(networkConfig(), SIGNAL(pingTimeoutEnabledSet(bool)), SLOT(enablePingTimeout(bool)));
+  connect(networkConfig(), SIGNAL(pingIntervalSet(int)), SLOT(setPingInterval(int)));
+  connect(networkConfig(), SIGNAL(autoWhoEnabledSet(bool)), SLOT(setAutoWhoEnabled(bool)));
+  connect(networkConfig(), SIGNAL(autoWhoIntervalSet(int)), SLOT(setAutoWhoInterval(int)));
+  connect(networkConfig(), SIGNAL(autoWhoDelaySet(int)), SLOT(setAutoWhoDelay(int)));
+
   connect(&_autoReconnectTimer, SIGNAL(timeout()), this, SLOT(doAutoReconnect()));
   connect(&_autoWhoTimer, SIGNAL(timeout()), this, SLOT(sendAutoWho()));
   connect(&_autoWhoCycleTimer, SIGNAL(timeout()), this, SLOT(startAutoWhoCycle()));
   connect(&_tokenBucketTimer, SIGNAL(timeout()), this, SLOT(fillBucketAndProcessQueue()));
   connect(this, SIGNAL(connectRequested()), this, SLOT(connectToIrc()));
 
-
   connect(&socket, SIGNAL(connected()), this, SLOT(socketInitialized()));
   connect(&socket, SIGNAL(disconnected()), this, SLOT(socketDisconnected()));
   connect(&socket, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(socketError(QAbstractSocket::SocketError)));
@@ -432,7 +432,7 @@ void CoreNetwork::networkInitialized() {
 
   enablePingTimeout();
 
-  if(_autoWhoEnabled) {
+  if(networkConfig()->autoWhoEnabled()) {
     _autoWhoCycleTimer.start();
     _autoWhoTimer.start();
     startAutoWhoCycle();  // FIXME wait for autojoin to be completed
@@ -531,11 +531,11 @@ void CoreNetwork::sendPing() {
     qDebug() << "UserId:" << userId() << "Network:" << networkName() << "missed" << _pingCount << "pings."
             << "BA:" << socket.bytesAvailable() << "BTW:" << socket.bytesToWrite();
   }
-  if(_pingCount >= _maxPingCount && now - _lastPingTime <= (uint)(_pingTimer.interval() / 1000) + 1) {
+  if((int)_pingCount >= networkConfig()->maxPingCount() && now - _lastPingTime <= (uint)(_pingTimer.interval() / 1000) + 1) {
     // the second check compares the actual elapsed time since the last ping and the pingTimer interval
     // if the interval is shorter then the actual elapsed time it means that this thread was somehow blocked
     // and unable to even handle a ping answer. So we ignore those misses.
-    disconnectFromIrc(false, QString("No Ping reply in %1 seconds.").arg(_maxPingCount * _pingTimer.interval() / 1000), true /* withReconnect */);
+    disconnectFromIrc(false, QString("No Ping reply in %1 seconds.").arg(_pingCount * _pingTimer.interval() / 1000), true /* withReconnect */);
   } else {
     _lastPingTime = now;
     _pingCount++;
@@ -543,9 +543,14 @@ void CoreNetwork::sendPing() {
   }
 }
 
-void CoreNetwork::enablePingTimeout() {
-  resetPingTimeout();
-  _pingTimer.start();
+void CoreNetwork::enablePingTimeout(bool enable) {
+  if(!enable)
+    disablePingTimeout();
+  else {
+    resetPingTimeout();
+    if(networkConfig()->pingTimeoutEnabled())
+      _pingTimer.start();
+  }
 }
 
 void CoreNetwork::disablePingTimeout() {
@@ -553,6 +558,37 @@ void CoreNetwork::disablePingTimeout() {
   resetPingTimeout();
 }
 
+void CoreNetwork::setPingInterval(int interval) {
+  _pingTimer.setInterval(interval * 1000);
+}
+
+/******** AutoWHO ********/
+
+void CoreNetwork::startAutoWhoCycle() {
+  if(!_autoWhoQueue.isEmpty()) {
+    _autoWhoCycleTimer.stop();
+    return;
+  }
+  _autoWhoQueue = channels();
+}
+
+void CoreNetwork::setAutoWhoDelay(int delay) {
+  _autoWhoTimer.setInterval(delay * 1000);
+}
+
+void CoreNetwork::setAutoWhoInterval(int interval) {
+  _autoWhoCycleTimer.setInterval(interval * 1000);
+}
+
+void CoreNetwork::setAutoWhoEnabled(bool enabled) {
+  if(enabled && isConnected() && !_autoWhoTimer.isActive())
+    _autoWhoTimer.start();
+  else if(!enabled) {
+    _autoWhoTimer.stop();
+    _autoWhoCycleTimer.stop();
+  }
+}
+
 void CoreNetwork::sendAutoWho() {
   // Don't send autowho if there are still some pending
   if(_autoWhoPending.count())
@@ -562,24 +598,17 @@ void CoreNetwork::sendAutoWho() {
     QString chan = _autoWhoQueue.takeFirst();
     IrcChannel *ircchan = ircChannel(chan);
     if(!ircchan) continue;
-    if(_autoWhoNickLimit > 0 && ircchan->ircUsers().count() > _autoWhoNickLimit) continue;
+    if(networkConfig()->autoWhoNickLimit() > 0 && ircchan->ircUsers().count() >= networkConfig()->autoWhoNickLimit())
+      continue;
     _autoWhoPending[chan]++;
     putRawLine("WHO " + serverEncode(chan));
-    if(_autoWhoQueue.isEmpty() && _autoWhoEnabled && !_autoWhoCycleTimer.isActive()) {
-      // Timer was stopped, means a new cycle is due immediately
-      _autoWhoCycleTimer.start();
-      startAutoWhoCycle();
-    }
     break;
   }
-}
-
-void CoreNetwork::startAutoWhoCycle() {
-  if(!_autoWhoQueue.isEmpty()) {
-    _autoWhoCycleTimer.stop();
-    return;
+  if(_autoWhoQueue.isEmpty() && networkConfig()->autoWhoEnabled() && !_autoWhoCycleTimer.isActive()) {
+    // Timer was stopped, means a new cycle is due immediately
+    _autoWhoCycleTimer.start();
+    startAutoWhoCycle();
   }
-  _autoWhoQueue = channels();
 }
 
 #ifdef HAVE_SSL
index d7ebd44..d263f3f 100644 (file)
@@ -50,6 +50,7 @@ public:
 
   inline CoreIdentity *identityPtr() const { return coreSession()->identity(identity()); }
   inline CoreSession *coreSession() const { return _coreSession; }
+  inline CoreNetworkConfig *networkConfig() const { return coreSession()->networkConfig(); }
 
   inline IrcServerHandler *ircServerHandler() const { return _ircServerHandler; }
   inline UserInputHandler *userInputHandler() const { return _userInputHandler; }
@@ -90,6 +91,8 @@ public slots:
   virtual void setAutoReconnectInterval(quint32);
   virtual void setAutoReconnectRetries(quint16);
 
+  void setPingInterval(int interval);
+
   void connectToIrc(bool reconnecting = false);
   void disconnectFromIrc(bool requested = true, const QString &reason = QString(), bool withReconnect = false);
 
@@ -102,6 +105,10 @@ public slots:
   void addChannelKey(const QString &channel, const QString &key);
   void removeChannelKey(const QString &channel);
 
+  void setAutoWhoEnabled(bool enabled);
+  void setAutoWhoInterval(int interval);
+  void setAutoWhoDelay(int delay);
+
   bool setAutoWhoDone(const QString &channel);
 
   Server usedServer() const;
@@ -138,7 +145,7 @@ private slots:
   void restoreUserModes();
   void doAutoReconnect();
   void sendPing();
-  void enablePingTimeout();
+  void enablePingTimeout(bool enable = true);
   void disablePingTimeout();
   void sendAutoWho();
   void startAutoWhoCycle();
@@ -182,15 +189,10 @@ private:
 
   QTimer _pingTimer;
   uint _lastPingTime;
-  uint _maxPingCount;
   uint _pingCount;
 
-  bool _autoWhoEnabled;
   QStringList _autoWhoQueue;
   QHash<QString, int> _autoWhoPending;
-  int _autoWhoInterval;
-  int _autoWhoNickLimit;
-  int _autoWhoDelay;
   QTimer _autoWhoTimer, _autoWhoCycleTimer;
 
   QTimer _tokenBucketTimer;
diff --git a/src/core/corenetworkconfig.cpp b/src/core/corenetworkconfig.cpp
new file mode 100644 (file)
index 0000000..1ea76f2
--- /dev/null
@@ -0,0 +1,46 @@
+/***************************************************************************
+ *   Copyright (C) 2005-09 by the Quassel Project                          *
+ *   devel@quassel-irc.org                                                 *
+ *                                                                         *
+ *   This program is free software; you can redistribute it and/or modify  *
+ *   it under the terms of the GNU General Public License as published by  *
+ *   the Free Software Foundation; either version 2 of the License, or     *
+ *   (at your option) version 3.                                           *
+ *                                                                         *
+ *   This program is distributed in the hope that it will be useful,       *
+ *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
+ *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
+ *   GNU General Public License for more details.                          *
+ *                                                                         *
+ *   You should have received a copy of the GNU General Public License     *
+ *   along with this program; if not, write to the                         *
+ *   Free Software Foundation, Inc.,                                       *
+ *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
+ ***************************************************************************/
+
+#include "core.h"
+#include "coresession.h"
+#include "corenetworkconfig.h"
+
+CoreNetworkConfig::CoreNetworkConfig(const QString& objectName, CoreSession* session)
+  : NetworkConfig(objectName, session)
+{
+  setAllowClientUpdates(true);
+
+  if(!session) {
+    qWarning() << Q_FUNC_INFO << "No CoreSession set, cannot load network configuration!";
+    return;
+  }
+
+  fromVariantMap(Core::getUserSetting(session->user(), objectName).toMap());
+}
+
+void CoreNetworkConfig::save() {
+  CoreSession *session = qobject_cast<CoreSession *>(parent());
+  if(!session) {
+    qWarning() << Q_FUNC_INFO << "No CoreSession set, cannot save network configuration!";
+    return;
+  }
+
+  Core::setUserSetting(session->user(), objectName(), toVariantMap());
+}
diff --git a/src/core/corenetworkconfig.h b/src/core/corenetworkconfig.h
new file mode 100644 (file)
index 0000000..4f26531
--- /dev/null
@@ -0,0 +1,48 @@
+/***************************************************************************
+ *   Copyright (C) 2005-09 by the Quassel Project                          *
+ *   devel@quassel-irc.org                                                 *
+ *                                                                         *
+ *   This program is free software; you can redistribute it and/or modify  *
+ *   it under the terms of the GNU General Public License as published by  *
+ *   the Free Software Foundation; either version 2 of the License, or     *
+ *   (at your option) version 3.                                           *
+ *                                                                         *
+ *   This program is distributed in the hope that it will be useful,       *
+ *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
+ *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
+ *   GNU General Public License for more details.                          *
+ *                                                                         *
+ *   You should have received a copy of the GNU General Public License     *
+ *   along with this program; if not, write to the                         *
+ *   Free Software Foundation, Inc.,                                       *
+ *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
+ ***************************************************************************/
+
+#ifndef CORENETWORKCONFIG_H_
+#define CORENETWORKCONFIG_H_
+
+#include "networkconfig.h"
+
+class CoreSession;
+
+class CoreNetworkConfig : public NetworkConfig {
+  Q_OBJECT
+
+public:
+  CoreNetworkConfig(const QString &objectName, CoreSession *parent);
+
+  inline virtual const QMetaObject *syncMetaObject() const { return &NetworkConfig::staticMetaObject; }
+
+  void save();
+
+public slots:
+  virtual inline void requestSetPingTimeoutEnabled(bool enabled) { setPingTimeoutEnabled(enabled); }
+  virtual inline void requestSetPingInterval(int interval) { setPingInterval(interval); }
+  virtual inline void requestSetMaxPingCount(int count) { setMaxPingCount(count); }
+  virtual inline void requestSetAutoWhoEnabled(bool enabled) { setAutoWhoEnabled(enabled); }
+  virtual inline void requestSetAutoWhoInterval(int interval) { setAutoWhoInterval(interval); }
+  virtual inline void requestSetAutoWhoNickLimit(int nickLimit) { setAutoWhoNickLimit(nickLimit); }
+  virtual inline void requestSetAutoWhoDelay(int delay) { setAutoWhoDelay(delay); }
+};
+
+#endif
index 9f21056..0c62171 100644 (file)
@@ -28,6 +28,7 @@
 #include "corebacklogmanager.h"
 #include "corebufferviewmanager.h"
 #include "coreirclisthelper.h"
+#include "corenetworkconfig.h"
 #include "storage.h"
 
 #include "coreidentity.h"
@@ -53,6 +54,7 @@ CoreSession::CoreSession(UserId uid, bool restoreState, QObject *parent)
     _backlogManager(new CoreBacklogManager(this)),
     _bufferViewManager(new CoreBufferViewManager(_signalProxy, this)),
     _ircListHelper(new CoreIrcListHelper(this)),
+    _networkConfig(new CoreNetworkConfig("GlobalNetworkConfig", this)),
     _coreInfo(this),
     scriptEngine(new QScriptEngine(this)),
     _processMessages(false)
@@ -87,6 +89,7 @@ CoreSession::CoreSession(UserId uid, bool restoreState, QObject *parent)
   p->synchronize(&aliasManager());
   p->synchronize(_backlogManager);
   p->synchronize(ircListHelper());
+  p->synchronize(networkConfig());
   p->synchronize(&_coreInfo);
 
   // Restore session state
@@ -148,6 +151,7 @@ void CoreSession::loadSettings() {
 void CoreSession::saveSessionState() const {
   _bufferSyncer->storeDirtyIds();
   _bufferViewManager->saveBufferViews();
+  _networkConfig->save();
 }
 
 void CoreSession::restoreSessionState() {
index 48d83f8..e2ccf9e 100644 (file)
@@ -33,6 +33,7 @@ class CoreBacklogManager;
 class CoreBufferSyncer;
 class CoreBufferViewManager;
 class CoreIrcListHelper;
+class CoreNetworkConfig;
 class Identity;
 class CoreIdentity;
 class NetworkConnection;
@@ -52,8 +53,9 @@ public:
   QList<BufferInfo> buffers() const;
   inline UserId user() const { return _user; }
   CoreNetwork *network(NetworkId) const;
-  NetworkConnection *networkConnection(NetworkId) const;
   CoreIdentity *identity(IdentityId) const;
+  inline CoreNetworkConfig *networkConfig() const { return _networkConfig; }
+  NetworkConnection *networkConnection(NetworkId) const;
 
   QVariant sessionState();
 
@@ -167,6 +169,7 @@ private:
   CoreBacklogManager *_backlogManager;
   CoreBufferViewManager *_bufferViewManager;
   CoreIrcListHelper *_ircListHelper;
+  CoreNetworkConfig *_networkConfig;
   CoreCoreInfo _coreInfo;
 
   QScriptEngine *scriptEngine;
index b6f4dc8..f405388 100644 (file)
@@ -98,6 +98,7 @@
 #include "settingspages/bufferviewsettingspage.h"
 #include "settingspages/chatmonitorsettingspage.h"
 #include "settingspages/colorsettingspage.h"
+#include "settingspages/connectionsettingspage.h"
 #include "settingspages/generalsettingspage.h"
 #include "settingspages/highlightsettingspage.h"
 #include "settingspages/identitiessettingspage.h"
@@ -812,6 +813,7 @@ void MainWin::showSettingsDlg() {
 
   //Category: Misc
   dlg->registerSettingsPage(new GeneralSettingsPage(dlg));
+  dlg->registerSettingsPage(new ConnectionSettingsPage(dlg));
   dlg->registerSettingsPage(new IdentitiesSettingsPage(dlg));
   dlg->registerSettingsPage(new NetworksSettingsPage(dlg));
   dlg->registerSettingsPage(new AliasesSettingsPage(dlg));
diff --git a/src/qtui/settingspages/connectionsettingspage.cpp b/src/qtui/settingspages/connectionsettingspage.cpp
new file mode 100644 (file)
index 0000000..7bdac2d
--- /dev/null
@@ -0,0 +1,104 @@
+/***************************************************************************
+ *   Copyright (C) 2005-09 by the Quassel Project                          *
+ *   devel@quassel-irc.org                                                 *
+ *                                                                         *
+ *   This program is free software; you can redistribute it and/or modify  *
+ *   it under the terms of the GNU General Public License as published by  *
+ *   the Free Software Foundation; either version 2 of the License, or     *
+ *   (at your option) any later version.                                   *
+ *                                                                         *
+ *   This program is distributed in the hope that it will be useful,       *
+ *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
+ *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
+ *   GNU General Public License for more details.                          *
+ *                                                                         *
+ *   You should have received a copy of the GNU General Public License     *
+ *   along with this program; if not, write to the                         *
+ *   Free Software Foundation, Inc.,                                       *
+ *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
+ ***************************************************************************/
+
+#include "connectionsettingspage.h"
+
+#include "client.h"
+#include "networkconfig.h"
+
+ConnectionSettingsPage::ConnectionSettingsPage(QWidget *parent)
+  : SettingsPage(tr("Misc"), tr("Connection"), parent) {
+
+  ui.setupUi(this);
+  initAutoWidgets();
+
+  connect(Client::instance(), SIGNAL(connected()), this, SLOT(clientConnected()));
+  connect(Client::instance(), SIGNAL(disconnected()), this, SLOT(clientDisconnected()));
+
+  setEnabled(false);
+  if(Client::isConnected())
+    clientConnected();
+}
+
+void ConnectionSettingsPage::clientConnected() {
+  if(Client::networkConfig()->isInitialized())
+    initDone();
+  else
+    connect(Client::networkConfig(), SIGNAL(initDone()), SLOT(initDone()));
+}
+
+void ConnectionSettingsPage::clientDisconnected() {
+  setEnabled(false);
+  setChangedState(false);
+}
+
+void ConnectionSettingsPage::initDone() {
+  setEnabled(true);
+}
+
+bool ConnectionSettingsPage::hasDefaults() const {
+  return true;
+}
+
+QVariant ConnectionSettingsPage::loadAutoWidgetValue(const QString &widgetName) {
+  if(!isEnabled())
+    return QVariant();
+  NetworkConfig *config = Client::networkConfig();
+  if(widgetName == "pingTimeoutEnabled")
+    return config->pingTimeoutEnabled();
+  if(widgetName == "pingInterval")
+    return config->pingInterval();
+  if(widgetName == "maxPingCount")
+    return config->maxPingCount();
+  if(widgetName == "autoWhoEnabled")
+    return config->autoWhoEnabled();
+  if(widgetName == "autoWhoInterval")
+    return config->autoWhoInterval();
+  if(widgetName == "autoWhoNickLimit")
+    return config->autoWhoNickLimit();
+  if(widgetName == "autoWhoDelay")
+    return config->autoWhoDelay();
+
+  return SettingsPage::loadAutoWidgetValue(widgetName);
+}
+
+void ConnectionSettingsPage::saveAutoWidgetValue(const QString &widgetName, const QVariant &value) {
+  if(!isEnabled())
+    return;
+  NetworkConfig *config = Client::networkConfig();
+  if(widgetName == "pingTimeoutEnabled")
+    config->requestSetPingTimeoutEnabled(value.toBool());
+  else if(widgetName == "pingInterval")
+    config->requestSetPingInterval(value.toInt());
+  else if(widgetName == "maxPingCount")
+    config->requestSetMaxPingCount(value.toInt());
+  else if(widgetName == "autoWhoEnabled")
+    config->requestSetAutoWhoEnabled(value.toBool());
+  else if(widgetName == "autoWhoInterval")
+    config->requestSetAutoWhoInterval(value.toInt());
+  else if(widgetName == "autoWhoNickLimit")
+    config->requestSetAutoWhoNickLimit(value.toInt());
+  else if(widgetName == "autoWhoDelay")
+    config->requestSetAutoWhoDelay(value.toInt());
+
+  else
+    SettingsPage::saveAutoWidgetValue(widgetName, value);
+}
+
diff --git a/src/qtui/settingspages/connectionsettingspage.h b/src/qtui/settingspages/connectionsettingspage.h
new file mode 100644 (file)
index 0000000..34c5684
--- /dev/null
@@ -0,0 +1,51 @@
+/***************************************************************************
+ *   Copyright (C) 2005-09 by the Quassel Project                          *
+ *   devel@quassel-irc.org                                                 *
+ *                                                                         *
+ *   This program is free software; you can redistribute it and/or modify  *
+ *   it under the terms of the GNU General Public License as published by  *
+ *   the Free Software Foundation; either version 2 of the License, or     *
+ *   (at your option) any later version.                                   *
+ *                                                                         *
+ *   This program is distributed in the hope that it will be useful,       *
+ *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
+ *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
+ *   GNU General Public License for more details.                          *
+ *                                                                         *
+ *   You should have received a copy of the GNU General Public License     *
+ *   along with this program; if not, write to the                         *
+ *   Free Software Foundation, Inc.,                                       *
+ *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
+ ***************************************************************************/
+
+#ifndef CONNECTIONSETTINGSPAGE_H_
+#define CONNECTIONSETTINGSPAGE_H_
+
+#include "settings.h"
+#include "settingspage.h"
+
+#include "ui_connectionsettingspage.h"
+
+class ConnectionSettingsPage : public SettingsPage {
+  Q_OBJECT
+
+  public:
+    ConnectionSettingsPage(QWidget *parent = 0);
+
+    bool hasDefaults() const;
+
+  public slots:
+
+  private slots:
+    void clientConnected();
+    void clientDisconnected();
+    void initDone();
+
+  private:
+    QVariant loadAutoWidgetValue(const QString &widgetName);
+    void saveAutoWidgetValue(const QString &widgetName, const QVariant &value);
+
+    Ui::ConnectionSettingsPage ui;
+};
+
+#endif
diff --git a/src/qtui/settingspages/connectionsettingspage.ui b/src/qtui/settingspages/connectionsettingspage.ui
new file mode 100644 (file)
index 0000000..e17aded
--- /dev/null
@@ -0,0 +1,264 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>ConnectionSettingsPage</class>
+ <widget class="QWidget" name="ConnectionSettingsPage">
+  <property name="geometry">
+   <rect>
+    <x>0</x>
+    <y>0</y>
+    <width>524</width>
+    <height>402</height>
+   </rect>
+  </property>
+  <property name="windowTitle">
+   <string>Configure the IRC Connection</string>
+  </property>
+  <layout class="QVBoxLayout" name="verticalLayout_2">
+   <item>
+    <widget class="QGroupBox" name="pingTimeoutEnabled">
+     <property name="title">
+      <string>Enable Ping Timeout Detection</string>
+     </property>
+     <property name="checkable">
+      <bool>true</bool>
+     </property>
+     <property name="settingsKey" stdset="0">
+      <string/>
+     </property>
+     <property name="defaultValue" stdset="0">
+      <bool>true</bool>
+     </property>
+     <layout class="QVBoxLayout" name="verticalLayout">
+      <item>
+       <layout class="QHBoxLayout" name="horizontalLayout">
+        <item>
+         <widget class="QLabel" name="label">
+          <property name="text">
+           <string>Ping interval:</string>
+          </property>
+         </widget>
+        </item>
+        <item>
+         <widget class="QSpinBox" name="pingInterval">
+          <property name="suffix">
+           <string> seconds</string>
+          </property>
+          <property name="minimum">
+           <number>30</number>
+          </property>
+          <property name="maximum">
+           <number>9999</number>
+          </property>
+          <property name="defaultValue" stdset="0">
+           <UInt>30</UInt>
+          </property>
+          <property name="settingsKey" stdset="0">
+           <string/>
+          </property>
+         </widget>
+        </item>
+        <item>
+         <spacer name="horizontalSpacer_2">
+          <property name="orientation">
+           <enum>Qt::Horizontal</enum>
+          </property>
+          <property name="sizeHint" stdset="0">
+           <size>
+            <width>40</width>
+            <height>20</height>
+           </size>
+          </property>
+         </spacer>
+        </item>
+       </layout>
+      </item>
+      <item>
+       <layout class="QHBoxLayout" name="horizontalLayout_2">
+        <item>
+         <widget class="QLabel" name="label_2">
+          <property name="text">
+           <string>Disconnect after</string>
+          </property>
+         </widget>
+        </item>
+        <item>
+         <widget class="QSpinBox" name="maxPingCount">
+          <property name="minimum">
+           <number>2</number>
+          </property>
+          <property name="value">
+           <number>6</number>
+          </property>
+          <property name="defaultValue" stdset="0">
+           <UInt>6</UInt>
+          </property>
+          <property name="settingsKey" stdset="0">
+           <string/>
+          </property>
+         </widget>
+        </item>
+        <item>
+         <widget class="QLabel" name="label_3">
+          <property name="text">
+           <string>missed pings</string>
+          </property>
+         </widget>
+        </item>
+        <item>
+         <spacer name="horizontalSpacer">
+          <property name="orientation">
+           <enum>Qt::Horizontal</enum>
+          </property>
+          <property name="sizeHint" stdset="0">
+           <size>
+            <width>40</width>
+            <height>20</height>
+           </size>
+          </property>
+         </spacer>
+        </item>
+       </layout>
+      </item>
+     </layout>
+    </widget>
+   </item>
+   <item>
+    <widget class="QGroupBox" name="autoWhoEnabled">
+     <property name="toolTip">
+      <string>This enables periodic polling of user information using /WHO. This is mostly interesting for tracking users' away status.</string>
+     </property>
+     <property name="title">
+      <string>Enable Automatic User Information Lookup (/WHO)</string>
+     </property>
+     <property name="checkable">
+      <bool>true</bool>
+     </property>
+     <property name="settingsKey" stdset="0">
+      <string/>
+     </property>
+     <property name="defaultValue" stdset="0">
+      <bool>true</bool>
+     </property>
+     <layout class="QHBoxLayout" name="horizontalLayout_3">
+      <item>
+       <layout class="QGridLayout" name="gridLayout">
+        <item row="0" column="0">
+         <widget class="QLabel" name="label_4">
+          <property name="text">
+           <string>Update interval:</string>
+          </property>
+         </widget>
+        </item>
+        <item row="0" column="1">
+         <widget class="QSpinBox" name="autoWhoInterval">
+          <property name="suffix">
+           <string> seconds</string>
+          </property>
+          <property name="minimum">
+           <number>10</number>
+          </property>
+          <property name="maximum">
+           <number>999</number>
+          </property>
+          <property name="value">
+           <number>90</number>
+          </property>
+          <property name="settingsKey" stdset="0">
+           <string/>
+          </property>
+          <property name="defaultValue" stdset="0">
+           <UInt>90</UInt>
+          </property>
+         </widget>
+        </item>
+        <item row="1" column="0">
+         <widget class="QLabel" name="label_5">
+          <property name="text">
+           <string>Ignore channels with more than:</string>
+          </property>
+         </widget>
+        </item>
+        <item row="1" column="1">
+         <widget class="QSpinBox" name="autoWhoNickLimit">
+          <property name="suffix">
+           <string> users</string>
+          </property>
+          <property name="minimum">
+           <number>100</number>
+          </property>
+          <property name="maximum">
+           <number>9999</number>
+          </property>
+          <property name="value">
+           <number>200</number>
+          </property>
+          <property name="settingsKey" stdset="0">
+           <string/>
+          </property>
+          <property name="defaultValue" stdset="0">
+           <UInt>200</UInt>
+          </property>
+         </widget>
+        </item>
+        <item row="2" column="0">
+         <widget class="QLabel" name="label_6">
+          <property name="text">
+           <string>Minimum delay between requests:</string>
+          </property>
+         </widget>
+        </item>
+        <item row="2" column="1">
+         <widget class="QSpinBox" name="autoWhoDelay">
+          <property name="suffix">
+           <string> seconds</string>
+          </property>
+          <property name="minimum">
+           <number>3</number>
+          </property>
+          <property name="value">
+           <number>5</number>
+          </property>
+          <property name="settingsKey" stdset="0">
+           <string/>
+          </property>
+          <property name="defaultValue" stdset="0">
+           <UInt>5</UInt>
+          </property>
+         </widget>
+        </item>
+       </layout>
+      </item>
+      <item>
+       <spacer name="horizontalSpacer_3">
+        <property name="orientation">
+         <enum>Qt::Horizontal</enum>
+        </property>
+        <property name="sizeHint" stdset="0">
+         <size>
+          <width>40</width>
+          <height>20</height>
+         </size>
+        </property>
+       </spacer>
+      </item>
+     </layout>
+    </widget>
+   </item>
+   <item>
+    <spacer name="verticalSpacer">
+     <property name="orientation">
+      <enum>Qt::Vertical</enum>
+     </property>
+     <property name="sizeHint" stdset="0">
+      <size>
+       <width>20</width>
+       <height>138</height>
+      </size>
+     </property>
+    </spacer>
+   </item>
+  </layout>
+ </widget>
+ <resources/>
+ <connections/>
+</ui>
index d4ccb4d..1cbd50b 100644 (file)
@@ -1,7 +1,7 @@
 # Putting $FOO in SETTINGSPAGES automatically includes
 # $FOOsettingspage.cpp, $FOOsettingspage.h and $FOOsettingspage.ui
 
-set(SETTINGSPAGES aliases appearance backlog bufferview color chatmonitor general highlight identities networks)
+set(SETTINGSPAGES aliases appearance backlog bufferview color connection chatmonitor general highlight identities networks)
 
 # Specify additional files (e.g. for subdialogs) here!
 set(SP_SOURCES aliasesmodel.cpp identityeditwidget.cpp notificationssettingspage.cpp)