Main Page | Class Hierarchy | Alphabetical List | Class List | File List | Class Members | File Members | Related Pages

# qwt_counter.cpp

    00001 /* -*- mode: C++ ; c-file-style: "stroustrup" -*- *****************************
    00002  * Qwt Widget Library
    00003  * Copyright (C) 1997   Josef Wilgen
    00004  * Copyright (C) 2002   Uwe Rathmann
    00005  *
    00006  * This library is free software; you can redistribute it and/or
    00007  * modify it under the terms of the Qwt License, Version 1.0
    00008  *****************************************************************************/
    00009
    00010 // vim: expandtab
    00011
    00012 #include <qlayout.h>
    00013 #include <qlineedit.h>
    00014 #include <qevent.h>
    00015 #include "qwt_counter.h"
    00016 #include "qwt_arrbtn.h"
    00017
    00027 QwtCounter::QwtCounter(QWidget *parent, const char *name ):
    00028     QWidget(parent,name),
    00029     d_blockKeys(FALSE),
    00030     d_keyPressed(FALSE)
    00031 {
    00032     d_increment[Button1] = 1;
    00033     d_increment[Button2] = 10;
    00034     d_increment[Button3] = 100;
    00035
    00036     QHBoxLayout *layout = new QHBoxLayout(this);
    00037     layout->setAutoAdd(TRUE);
    00038
    00039     int i;
    00040     for(i = ButtonCnt - 1; i >= 0; i--)
    00041     {
    00042         QwtArrowButton *btn =
    00043             new QwtArrowButton(i+1, Qt::DownArrow,this);
    00044         btn->setFocusPolicy(QWidget::StrongFocus);
    00045         btn->installEventFilter(this);
    00046
    00047         connect(btn, SIGNAL(released()), SLOT(btnReleased()));
    00048         connect(btn, SIGNAL(clicked()), SLOT(btnClicked()));
    00049
    00050         d_buttonDown[i] = btn;
    00051     }
    00052
    00053     d_valueEdit = new QLineEdit(this);
    00054     d_valueEdit->setReadOnly(TRUE);
    00055     d_valueEdit->setFocusPolicy(QWidget::NoFocus);
    00056
    00057     layout->setStretchFactor(d_valueEdit, 10);
    00058
    00059     for(i = 0; i < ButtonCnt; i++)
    00060     {
    00061         QwtArrowButton *btn =
    00062             new QwtArrowButton(i+1, Qt::UpArrow, this);
    00063         btn->setFocusPolicy(QWidget::StrongFocus);
    00064         btn->installEventFilter(this);
    00065
    00066         connect(btn, SIGNAL(released()), SLOT(btnReleased()));
    00067         connect(btn, SIGNAL(clicked()), SLOT(btnClicked()));
    00068
    00069         d_buttonUp[i] = btn;
    00070     }
    00071
    00072     setNumButtons(2);
    00073     setRange(0.0,1.0,0.001);
    00074     setValue(0.0);
    00075 }
    00076
    00078 bool QwtCounter::eventFilter(QObject *object, QEvent *e)
    00079 {
    00080     if ( object->inherits("QPushButton") )
    00081     {
    00082         if ( e->type() == QEvent::KeyPress )
    00083         {
    00084             if ( !((QKeyEvent *)e)->isAutoRepeat() )
    00085                 d_keyPressed = TRUE;
    00086         }
    00087
    00088         if ( e->type() == QEvent::KeyRelease )
    00089         {
    00090             if ( !((QKeyEvent *)e)->isAutoRepeat() )
    00091             {
    00092                 d_keyPressed = FALSE;
    00093
    00094                 // Unblock key events. They might be blocked
    00095                 // to interrupt auto repeat, when we changed
    00096                 // the focus to a different button.
    00097
    00098                 d_blockKeys = FALSE;
    00099             }
    00100         }
    00101     }
    00102
    00103     return QWidget::eventFilter(object, e);
    00104 }
    00105
    00115 void QwtCounter::setIncSteps(QwtCounter::Button btn, int nSteps)
    00116 {
    00117     if (( btn >= 0) && (btn < ButtonCnt))
    00118        d_increment[btn] = nSteps;
    00119 }
    00120
    00127 int QwtCounter::incSteps(QwtCounter::Button btn) const
    00128 {
    00129     if (( btn >= 0) && (btn < ButtonCnt))
    00130        return d_increment[btn];
    00131
    00132     return 0;
    00133 }
    00134
    00142 void QwtCounter::setValue(double v)
    00143 {
    00144     QwtDblRange::setValue(v);
    00145
    00146     showNum(value());
    00147     updateButtons();
    00148 }
    00149
    00153 void QwtCounter::valueChange()
    00154 {
    00155     if ( isValid() )
    00156         showNum(value());
    00157     else
    00158         d_valueEdit->setText(QString::null);
    00159
    00160     updateButtons();
    00161
    00162     if ( isValid() )
    00163         emit valueChanged(value());
    00164 }
    00165
    00174 void QwtCounter::updateButtons()
    00175 {
    00176     if ( isValid() )
    00177     {
    00178         // 1. save enabled state of the smallest down- and up-button
    00179         // 2. change enabled state on under- or over-flow
    00180         // 3. switch focus if the enabled state has changed
    00181
    00182         int oldEnabledDown = d_buttonDown[0]->isEnabled();
    00183         int oldEnabledUp = d_buttonUp[0]->isEnabled();
    00184
    00185         for ( int i = 0; i < ButtonCnt; i++ )
    00186         {
    00187             d_buttonDown[i]->setEnabled(value() > minValue());
    00188             d_buttonUp[i]->setEnabled(value() < maxValue());
    00189         }
    00190
    00191         QPushButton *focusButton = NULL;
    00192         if (oldEnabledDown && !d_buttonDown[0]->isEnabled())
    00193             focusButton = d_buttonUp[0];
    00194
    00195         if (oldEnabledUp && !d_buttonUp[0]->isEnabled())
    00196             focusButton = d_buttonDown[0];
    00197
    00198         if ( focusButton )
    00199         {
    00200             focusButton->setFocus();
    00201             if ( d_keyPressed )
    00202             {
    00203                 // Stop auto repeat until the key has been released
    00204                 d_blockKeys = TRUE;
    00205             }
    00206         }
    00207     }
    00208     else
    00209     {
    00210         for ( int i = 0; i < ButtonCnt; i++ )
    00211         {
    00212             d_buttonDown[i]->setEnabled(FALSE);
    00213             d_buttonUp[i]->setEnabled(FALSE);
    00214         }
    00215     }
    00216 }
    00217
    00222 void QwtCounter::setNumButtons(int n)
    00223 {
    00224     if ( n<0 || n>ButtonCnt )
    00225         return;
    00226
    00227     for ( int i = 0; i < ButtonCnt; i++ )
    00228     {
    00229         if ( i < n )
    00230         {
    00231             d_buttonDown[i]->show();
    00232             d_buttonUp[i]->show();
    00233         }
    00234         else
    00235         {
    00236             d_buttonDown[i]->hide();
    00237             d_buttonUp[i]->hide();
    00238         }
    00239     }
    00240
    00241     d_nButtons = n;
    00242 }
    00243
    00247 int QwtCounter::numButtons() const
    00248 {
    00249     return d_nButtons;
    00250 }
    00251
    00253 void QwtCounter::showNum(double d)
    00254 {
    00255     QString v;
    00256     v.setNum(d);
    00257
    00258     d_valueEdit->setText(v);
    00259     d_valueEdit->setCursorPosition(0);
    00260 }
    00261
    00263 void QwtCounter::btnClicked()
    00264 {
    00265     if (d_blockKeys)
    00266     {
    00267         // When we set the focus to a different button,
    00268         // auto repeat has been stopped until the key will
    00269         // be released
    00270
    00271         return;
    00272     }
    00273
    00274     for ( int i = 0; i < ButtonCnt; i++ )
    00275     {
    00276         if ( d_buttonUp[i] == sender() )
    00277             incValue(d_increment[i]);
    00278
    00279         if ( d_buttonDown[i] == sender() )
    00280             incValue(-d_increment[i]);
    00281     }
    00282 }
    00283
    00285 void QwtCounter::btnReleased()
    00286 {
    00287     emit buttonReleased(value());
    00288 }
    00289
    00296 void QwtCounter::rangeChange()
    00297 {
    00298     updateButtons();
    00299 }
    00300
    00308 void QwtCounter::fontChange(const QFont &f)
    00309 {
    00310     QWidget::fontChange( f );
    00311     d_valueEdit->setFont(font());
    00312 }
    00313
    00315 QSize QwtCounter::sizeHint() const
    00316 {
    00317     QString tmp;
    00318     QFontMetrics fm(d_valueEdit->font());
    00319
    00320     int w = fm.width(tmp.setNum(minValue()));
    00321     int w1 = fm.width(tmp.setNum(maxValue()));
    00322     if ( w1 > w )
    00323         w = w1;
    00324     w1 = fm.width(tmp.setNum(minValue() + step()));
    00325     if ( w1 > w )
    00326         w = w1;
    00327     w1 = fm.width(tmp.setNum(maxValue() - step()));
    00328     if ( w1 > w )
    00329         w = w1;
    00330
    00331     // QLineEdit::minimumSizeHint is for one char. Subtracting
    00332     // the size for the char we get all the margins, frames ...
    00333
    00334 #if QT_VERSION < 300
    00335     w += d_valueEdit->minimumSizeHint().width() - fm.maxWidth();
    00336 #else
    00337     w += 2 * d_valueEdit->frameWidth() +
    00338         d_valueEdit->fontMetrics().minRightBearing() + 3;
    00339 #endif
    00340
    00341     // Now we replace default sizeHint contribution of d_valueEdit by
    00342     // what we really need.
    00343
    00344     w += QWidget::sizeHint().width() - d_valueEdit->sizeHint().width();
    00345
    00346     return QSize(w, QWidget::sizeHint().height());
    00347 }
    00348
    00350 QSizePolicy QwtCounter::sizePolicy() const
    00351 {
    00352     QSizePolicy sp;
    00353     sp.setHorData( QSizePolicy::Preferred );
    00354     sp.setVerData( QSizePolicy::Fixed );
    00355     return sp;
    00356 }