add more spacing
[personal-kdebase.git] / workspace / ksysguard / gui / SensorDisplayLib / SensorLogger.cc
blob5138ba11f9c8138a05a4c635e98800744eb844d6
1 /*
2 KSysGuard, the KDE System Guard
4 Copyright (c) 2001 Tobias Koenig <tokoe@kde.org>
6 This program is free software; you can redistribute it and/or
7 modify it under the terms of the GNU General Public
8 License as published by the Free Software Foundation; either
9 version 2 of the License, or (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
22 #include <QtCore/QAbstractTableModel>
23 #include <QtCore/QDate>
24 #include <QtCore/QFile>
25 #include <QtCore/QTextStream>
26 #include <QtGui/QContextMenuEvent>
27 #include <QtGui/QHeaderView>
28 #include <QtGui/QMenu>
29 #include <QtGui/QTreeView>
30 #include <QtGui/QHBoxLayout>
31 #include <QtXml/QDomNodeList>
32 #include <QtXml/QDomDocument>
33 #include <QtXml/QDomElement>
35 #include <kapplication.h>
36 #include <kiconloader.h>
37 #include <klocale.h>
38 #include <knotification.h>
39 #include <ksgrd/SensorManager.h>
40 #include <kdebug.h>
41 #include "StyleEngine.h"
43 #include "SensorLoggerDlg.h"
44 #include "SensorLoggerSettings.h"
45 #include "SensorLogger.h"
47 #define NONE -1
49 LogSensorView::LogSensorView( QWidget *parent )
50 : QTreeView( parent )
54 void LogSensorView::contextMenuEvent( QContextMenuEvent *event )
56 const QModelIndex index = indexAt( event->pos() );
58 emit contextMenuRequest( index, viewport()->mapToGlobal( event->pos() ) );
61 class LogSensorModel : public QAbstractTableModel
63 public:
64 LogSensorModel( QObject *parent = 0 )
65 : QAbstractTableModel( parent )
69 virtual int columnCount( const QModelIndex &parent = QModelIndex() ) const
71 Q_UNUSED( parent );
73 return 5;
76 virtual int rowCount( const QModelIndex &parent = QModelIndex() ) const
78 Q_UNUSED( parent );
80 return mSensors.count();
83 virtual QVariant data( const QModelIndex &index, int role = Qt::DisplayRole ) const
85 if ( !index.isValid() )
86 return QVariant();
88 if ( index.row() >= mSensors.count() || index.row() < 0 )
89 return QVariant();
91 LogSensor *sensor = mSensors[ index.row() ];
93 if ( role == Qt::DisplayRole ) {
94 switch ( index.column() ) {
95 case 1:
96 return sensor->timerInterval();
97 break;
98 case 2:
99 return sensor->sensorName();
100 break;
101 case 3:
102 return sensor->hostName();
103 break;
104 case 4:
105 return sensor->fileName();
106 break;
108 } else if ( role == Qt::DecorationRole ) {
109 static QPixmap runningPixmap = KIconLoader::global()->loadIcon( "running", KIconLoader::Small, KIconLoader::SizeSmall );
110 static QPixmap waitingPixmap = KIconLoader::global()->loadIcon( "waiting", KIconLoader::Small, KIconLoader::SizeSmall );
112 if ( index.column() == 0 ) {
113 if ( sensor->isLogging() )
114 return runningPixmap;
115 else
116 return waitingPixmap;
118 } else if ( role == Qt::ForegroundRole ) {
119 if ( sensor->limitReached() )
120 return mAlarmColor;
121 else
122 return mForegroundColor;
123 } else if ( role == Qt::BackgroundRole ) {
124 return mBackgroundColor;
127 return QVariant();
130 virtual QVariant headerData( int section, Qt::Orientation orientation, int role = Qt::DisplayRole ) const
132 if ( orientation == Qt::Vertical )
133 return QVariant();
135 if ( role == Qt::DisplayRole ) {
136 switch ( section ) {
137 case 0:
138 return i18n("Logging");
139 break;
140 case 1:
141 return i18n("Timer Interval");
142 break;
143 case 2:
144 return i18n("Sensor Name");
145 break;
146 case 3:
147 return i18n("Host Name");
148 break;
149 case 4:
150 return i18n("Log File");
151 break;
152 default:
153 return QVariant();
157 return QVariant();
160 void addSensor( LogSensor *sensor )
162 mSensors.append( sensor );
164 connect( sensor, SIGNAL( changed() ), this, SIGNAL( layoutChanged() ) );
166 emit layoutChanged();
169 void removeSensor( LogSensor *sensor )
171 delete mSensors.takeAt( mSensors.indexOf( sensor ) );
173 emit layoutChanged();
176 LogSensor* sensor( const QModelIndex &index ) const
178 if ( !index.isValid() || index.row() >= mSensors.count() || index.row() < 0 )
179 return 0;
181 return mSensors[ index.row() ];
184 void clear()
186 qDeleteAll( mSensors );
187 mSensors.clear();
190 const QList<LogSensor*> sensors() const
192 return mSensors;
195 void setForegroundColor( const QColor &color ) { mForegroundColor = color; }
196 QColor foregroundColor() const { return mForegroundColor; }
198 void setBackgroundColor( const QColor &color ) { mBackgroundColor = color; }
199 QColor backgroundColor() const { return mBackgroundColor; }
201 void setAlarmColor( const QColor &color ) { mAlarmColor = color; }
202 QColor alarmColor() const { return mAlarmColor; }
204 private:
206 QColor mForegroundColor;
207 QColor mBackgroundColor;
208 QColor mAlarmColor;
210 QList<LogSensor*> mSensors;
213 LogSensor::LogSensor( QObject *parent )
214 : QObject( parent ),
215 mTimerID( NONE ),
216 mLowerLimitActive( false ),
217 mUpperLimitActive( 0 ),
218 mLowerLimit( 0 ),
219 mUpperLimit( 0 ),
220 mLimitReached( false )
224 LogSensor::~LogSensor()
228 void LogSensor::setHostName( const QString& name )
230 mHostName = name;
233 QString LogSensor::hostName() const
235 return mHostName;
238 void LogSensor::setSensorName( const QString& name )
240 mSensorName = name;
243 QString LogSensor::sensorName() const
245 return mSensorName;
248 void LogSensor::setFileName( const QString& name )
250 mFileName = name;
253 QString LogSensor::fileName() const
255 return mFileName;
258 void LogSensor::setUpperLimitActive( bool value )
260 mUpperLimitActive = value;
263 bool LogSensor::upperLimitActive() const
265 return mUpperLimitActive;
268 void LogSensor::setLowerLimitActive( bool value )
270 mLowerLimitActive = value;
273 bool LogSensor::lowerLimitActive() const
275 return mLowerLimitActive;
278 void LogSensor::setUpperLimit( double value )
280 mUpperLimit = value;
283 double LogSensor::upperLimit() const
285 return mUpperLimit;
288 void LogSensor::setLowerLimit( double value )
290 mLowerLimit = value;
293 double LogSensor::lowerLimit() const
295 return mLowerLimit;
298 void LogSensor::setTimerInterval( int interval )
300 mTimerInterval = interval;
302 if ( mTimerID != NONE ) {
303 timerOff();
304 timerOn();
308 int LogSensor::timerInterval() const
310 return mTimerInterval;
313 bool LogSensor::isLogging() const
315 return mTimerID != NONE;
318 bool LogSensor::limitReached() const
320 return mLimitReached;
323 void LogSensor::timerOff()
325 if ( mTimerID > 0 )
326 killTimer( mTimerID );
327 mTimerID = NONE;
330 void LogSensor::timerOn()
332 mTimerID = startTimer( mTimerInterval * 1000 );
335 void LogSensor::startLogging()
337 timerOn();
340 void LogSensor::stopLogging()
342 timerOff();
345 void LogSensor::timerTick( )
347 KSGRD::SensorMgr->sendRequest( mHostName, mSensorName, (KSGRD::SensorClient*) this, 42 );
350 void LogSensor::answerReceived( int id, const QList<QByteArray>& answer ) //virtual
352 QFile mLogFile( mFileName );
354 if ( !mLogFile.open( QIODevice::ReadWrite | QIODevice::Append ) ) {
355 stopLogging();
356 return;
359 switch ( id ) {
360 case 42: {
361 QTextStream stream( &mLogFile );
362 double value = 0;
363 if ( !answer.isEmpty() )
364 value = answer[ 0 ].toDouble();
366 if ( mLowerLimitActive && value < mLowerLimit ) {
367 timerOff();
368 mLimitReached = true;
370 // send notification
371 KNotification::event( "sensor_alarm", QString( "sensor '%1' at '%2' reached lower limit" )
372 .arg( mSensorName ).arg( mHostName), QPixmap(), 0 );
374 timerOn();
375 } else if ( mUpperLimitActive && value > mUpperLimit ) {
376 timerOff();
377 mLimitReached = true;
379 // send notification
380 KNotification::event( "sensor_alarm", QString( "sensor '%1' at '%2' reached upper limit" )
381 .arg( mSensorName).arg( mHostName), QPixmap(), 0 );
383 timerOn();
384 } else {
385 mLimitReached = false;
388 const QDate date = QDateTime::currentDateTime().date();
389 const QTime time = QDateTime::currentDateTime().time();
391 stream << QString( "%1 %2 %3 %4 %5: %6\n" ).arg( date.shortMonthName( date.month() ) )
392 .arg( date.day() ).arg( time.toString() )
393 .arg( mHostName).arg( mSensorName ).arg( value );
397 emit changed();
399 mLogFile.close();
402 SensorLogger::SensorLogger( QWidget *parent, const QString& title, SharedSettings *workSheetSettings )
403 : KSGRD::SensorDisplay( parent, title, workSheetSettings )
405 mModel = new LogSensorModel( this );
406 mModel->setForegroundColor( KSGRD::Style->firstForegroundColor() );
407 mModel->setBackgroundColor( KSGRD::Style->backgroundColor() );
408 mModel->setAlarmColor( KSGRD::Style->alarmColor() );
410 QLayout *layout = new QHBoxLayout(this);
411 mView = new LogSensorView( this );
412 layout->addWidget(mView);
413 setLayout(layout);
415 mView->setContextMenuPolicy( Qt::CustomContextMenu );
416 connect(mView, SIGNAL(customContextMenuRequested(const QPoint&)), SLOT(showContextMenu(const QPoint &)));
418 mView->header()->setStretchLastSection( true );
419 mView->setRootIsDecorated( false );
420 mView->setItemsExpandable( false );
421 mView->setModel( mModel );
422 setPlotterWidget( mView );
424 connect( mView, SIGNAL( contextMenuRequest( const QModelIndex&, const QPoint& ) ),
425 this, SLOT( contextMenuRequest( const QModelIndex&, const QPoint& ) ) );
427 QPalette palette = mView->palette();
428 palette.setColor( QPalette::Base, KSGRD::Style->backgroundColor() );
429 mView->setPalette( palette );
431 setTitle( i18n( "Sensor Logger" ) );
432 setMinimumSize( 50, 25 );
435 SensorLogger::~SensorLogger(void)
439 bool SensorLogger::addSensor( const QString& hostName, const QString& sensorName, const QString& sensorType, const QString& )
441 if ( sensorType != "integer" && sensorType != "float" )
442 return false;
444 SensorLoggerDlg dlg( this );
446 if ( dlg.exec() ) {
447 if ( !dlg.fileName().isEmpty() ) {
448 LogSensor *sensor = new LogSensor( mModel );
450 sensor->setHostName( hostName );
451 sensor->setSensorName( sensorName );
452 sensor->setFileName( dlg.fileName() );
453 sensor->setTimerInterval( dlg.timerInterval() );
454 sensor->setLowerLimitActive( dlg.lowerLimitActive() );
455 sensor->setUpperLimitActive( dlg.upperLimitActive() );
456 sensor->setLowerLimit( dlg.lowerLimit() );
457 sensor->setUpperLimit( dlg.upperLimit() );
459 mModel->addSensor( sensor );
463 return true;
466 bool SensorLogger::editSensor( LogSensor* sensor )
468 SensorLoggerDlg dlg( this );
470 dlg.setFileName( sensor->fileName() );
471 dlg.setTimerInterval( sensor->timerInterval() );
472 dlg.setLowerLimitActive( sensor->lowerLimitActive() );
473 dlg.setLowerLimit( sensor->lowerLimit() );
474 dlg.setUpperLimitActive( sensor->upperLimitActive() );
475 dlg.setUpperLimit( sensor->upperLimit() );
477 if ( dlg.exec() ) {
478 if ( !dlg.fileName().isEmpty() ) {
479 sensor->setFileName( dlg.fileName() );
480 sensor->setTimerInterval( dlg.timerInterval() );
481 sensor->setLowerLimitActive( dlg.lowerLimitActive() );
482 sensor->setUpperLimitActive( dlg.upperLimitActive() );
483 sensor->setLowerLimit( dlg.lowerLimit() );
484 sensor->setUpperLimit( dlg.upperLimit() );
488 return true;
491 void SensorLogger::configureSettings()
493 SensorLoggerSettings dlg( this );
495 dlg.setTitle( title() );
496 dlg.setForegroundColor( mModel->foregroundColor() );
497 dlg.setBackgroundColor( mModel->backgroundColor() );
498 dlg.setAlarmColor( mModel->alarmColor() );
500 if ( dlg.exec() ) {
501 setTitle( dlg.title() );
503 mModel->setForegroundColor( dlg.foregroundColor() );
504 mModel->setBackgroundColor( dlg.backgroundColor() );
505 mModel->setAlarmColor( dlg.alarmColor() );
507 QPalette palette = mView->palette();
508 palette.setColor( QPalette::Base, dlg.backgroundColor() );
509 mView->setPalette( palette );
513 void SensorLogger::applyStyle()
515 mModel->setForegroundColor( KSGRD::Style->firstForegroundColor() );
516 mModel->setBackgroundColor( KSGRD::Style->backgroundColor() );
517 mModel->setAlarmColor( KSGRD::Style->alarmColor() );
519 QPalette palette = mView->palette();
520 palette.setColor( QPalette::Base, KSGRD::Style->backgroundColor() );
521 mView->setPalette( palette );
524 bool SensorLogger::restoreSettings( QDomElement& element )
526 mModel->setForegroundColor( restoreColor( element, "textColor", Qt::green) );
527 mModel->setBackgroundColor( restoreColor( element, "backgroundColor", Qt::black ) );
528 mModel->setAlarmColor( restoreColor( element, "alarmColor", Qt::red ) );
530 mModel->clear();
532 QDomNodeList dnList = element.elementsByTagName( "logsensors" );
533 for ( int i = 0; i < dnList.count(); i++ ) {
534 QDomElement element = dnList.item( i ).toElement();
535 LogSensor* sensor = new LogSensor( mModel );
537 sensor->setHostName( element.attribute("hostName") );
538 sensor->setSensorName( element.attribute("sensorName") );
539 sensor->setFileName( element.attribute("fileName") );
540 sensor->setTimerInterval( element.attribute("timerInterval").toInt() );
541 sensor->setLowerLimitActive( element.attribute("lowerLimitActive").toInt() );
542 sensor->setLowerLimit( element.attribute("lowerLimit").toDouble() );
543 sensor->setUpperLimitActive( element.attribute("upperLimitActive").toInt() );
544 sensor->setUpperLimit( element.attribute("upperLimit").toDouble() );
546 mModel->addSensor( sensor );
549 SensorDisplay::restoreSettings( element );
551 QPalette palette = mView->palette();
552 palette.setColor( QPalette::Base, mModel->backgroundColor() );
553 mView->setPalette( palette );
555 return true;
558 bool SensorLogger::saveSettings( QDomDocument& doc, QDomElement& element )
560 saveColor( element, "textColor", mModel->foregroundColor() );
561 saveColor( element, "backgroundColor", mModel->backgroundColor() );
562 saveColor( element, "alarmColor", mModel->alarmColor() );
564 const QList<LogSensor*> sensors = mModel->sensors();
565 for ( int i = 0; i < sensors.count(); ++i ) {
566 LogSensor *sensor = sensors[ i ];
567 QDomElement log = doc.createElement( "logsensors" );
568 log.setAttribute("sensorName", sensor->sensorName());
569 log.setAttribute("hostName", sensor->hostName());
570 log.setAttribute("fileName", sensor->fileName());
571 log.setAttribute("timerInterval", sensor->timerInterval());
572 log.setAttribute("lowerLimitActive", QString("%1").arg(sensor->lowerLimitActive()));
573 log.setAttribute("lowerLimit", QString("%1").arg(sensor->lowerLimit()));
574 log.setAttribute("upperLimitActive", QString("%1").arg(sensor->upperLimitActive()));
575 log.setAttribute("upperLimit", QString("%1").arg(sensor->upperLimit()));
577 element.appendChild( log );
580 SensorDisplay::saveSettings( doc, element );
582 return true;
585 void SensorLogger::answerReceived( int, const QList<QByteArray>& ) //virtual
587 // we do not use this, since all answers are received by the LogSensors
590 void SensorLogger::contextMenuRequest( const QModelIndex &index, const QPoint &point )
592 LogSensor *sensor = mModel->sensor( index );
594 QMenu pm;
596 QAction *action = 0;
597 if (hasSettingsDialog()) {
598 action = pm.addAction(i18n("&Properties"));
599 action->setData( 1 );
601 if(!mSharedSettings->locked) {
603 action = pm.addAction(i18n("&Remove Display"));
604 action->setData( 2 );
606 pm.addSeparator();
608 action = pm.addAction(i18n("&Remove Sensor"));
609 action->setData( 3 );
610 if ( !sensor )
611 action->setEnabled( false );
613 action = pm.addAction(i18n("&Edit Sensor..."));
614 action->setData( 4 );
615 if ( !sensor )
616 action->setEnabled( false );
619 if ( sensor ) {
620 if ( sensor->isLogging() ) {
621 action = pm.addAction(i18n("St&op Logging"));
622 action->setData( 6 );
623 } else {
624 action = pm.addAction(i18n("S&tart Logging"));
625 action->setData( 5 );
629 action = pm.exec( point );
630 if ( !action )
631 return;
633 switch (action->data().toInt())
635 case 1:
636 configureSettings();
637 break;
638 case 2: {
639 KSGRD::SensorDisplay::DeleteEvent *ev = new KSGRD::SensorDisplay::DeleteEvent( this );
640 kapp->postEvent(parent(), ev);
641 break;
643 case 3:
644 if ( sensor )
645 mModel->removeSensor( sensor );
646 break;
647 case 4:
648 if ( sensor )
649 editSensor( sensor );
650 break;
651 case 5:
652 if ( sensor )
653 sensor->startLogging();
654 break;
655 case 6:
656 if ( sensor )
657 sensor->stopLogging();
658 break;
662 #include "SensorLogger.moc"