kalarm/lib

colourcombo.cpp

00001 /*
00002  *  colourcombo.cpp  -  colour selection combo box
00003  *  Program:  kalarm
00004  *  Copyright (c) 2001 - 2003, 2005 by David Jarvie <software@astrojar.org.uk>
00005  *
00006  *  Some code taken from kdelibs/kdeui/kcolorcombo.cpp in the KDE libraries:
00007  *  Copyright (C) 1997 Martin Jones (mjones@kde.org)
00008  *
00009  *  This program is free software; you can redistribute it and/or modify
00010  *  it under the terms of the GNU General Public License as published by
00011  *  the Free Software Foundation; either version 2 of the License, or
00012  *  (at your option) any later version.
00013  *
00014  *  This program is distributed in the hope that it will be useful,
00015  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00016  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
00017  *  GNU General Public License for more details.
00018  *
00019  *  You should have received a copy of the GNU General Public License along
00020  *  with this program; if not, write to the Free Software Foundation, Inc.,
00021  *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
00022  */
00023 
00024 #include <tqpainter.h>
00025 
00026 #include <klocale.h>
00027 #include <kcolordialog.h>
00028 
00029 #include "preferences.h"
00030 #include "colourcombo.moc"
00031 
00032 
00033 ColourCombo::ColourCombo(TQWidget* parent, const char* name, const TQColor& defaultColour)
00034     : TQComboBox(parent, name),
00035       mColourList(Preferences::messageColours()),
00036       mSelectedColour(defaultColour),
00037       mCustomColour(255, 255, 255),
00038       mReadOnly(false),
00039       mDisabled(false)
00040 {
00041     addColours();
00042     connect(this, TQT_SIGNAL(activated(int)), TQT_SLOT(slotActivated(int)));
00043     connect(this, TQT_SIGNAL(highlighted(int)), TQT_SLOT(slotHighlighted(int)));
00044     Preferences::connect(TQT_SIGNAL(preferencesChanged()), this, TQT_SLOT(slotPreferencesChanged()));
00045 }
00046 
00047 void ColourCombo::setColour(const TQColor& colour)
00048 {
00049     mSelectedColour = colour;
00050     addColours();
00051 }
00052 
00053 /******************************************************************************
00054 *  Set a new colour selection.
00055 */
00056 void ColourCombo::setColours(const ColourList& colours)
00057 {
00058     mColourList = colours;
00059     if (mSelectedColour != mCustomColour
00060     &&  !mColourList.contains(mSelectedColour))
00061     {
00062         // The current colour has been deleted
00063         mSelectedColour = mColourList.count() ? mColourList.first() : mCustomColour;
00064     }
00065     addColours();
00066 }
00067 
00068 /******************************************************************************
00069 *  Called when the user changes the preference settings.
00070 *  If the colour list has changed, update the colours displayed.
00071 */
00072 void ColourCombo::slotPreferencesChanged()
00073 {
00074     const ColourList& prefColours = Preferences::messageColours();
00075     if (prefColours != mColourList)
00076         setColours(prefColours);      // update the display with the new colours
00077 }
00078 
00079 /******************************************************************************
00080 *  Enable or disable the control.
00081 *  If it is disabled, its colour is set to the dialog background colour.
00082 */
00083 void ColourCombo::setEnabled(bool enable)
00084 {
00085     if (enable  &&  mDisabled)
00086     {
00087         mDisabled = false;
00088         setColour(mSelectedColour);
00089     }
00090     else if (!enable  &&  !mDisabled)
00091     {
00092         mSelectedColour = color();
00093         int end = count();
00094         if (end > 1)
00095         {
00096             // Add a dialog background colour item
00097             TQPixmap pm = *pixmap(1);
00098             pm.fill(paletteBackgroundColor());
00099             insertItem(pm);
00100             setCurrentItem(end);
00101         }
00102         mDisabled = true;
00103     }
00104     TQComboBox::setEnabled(enable);
00105 }
00106 
00107 void ColourCombo::slotActivated(int index)
00108 {
00109     if (index)
00110         mSelectedColour = mColourList[index - 1];
00111     else
00112     {
00113         if (KColorDialog::getColor(mCustomColour, this) == TQDialog::Accepted)
00114         {
00115             TQRect rect;
00116             drawCustomItem(rect, false);
00117         }
00118         mSelectedColour = mCustomColour;
00119     }
00120     emit activated(mSelectedColour);
00121 }
00122 
00123 void ColourCombo::slotHighlighted(int index)
00124 {
00125     mSelectedColour = index ? mColourList[index - 1] : mCustomColour;
00126     emit highlighted(mSelectedColour);
00127 }
00128 
00129 /******************************************************************************
00130 *  Initialise the items in the combo box to one for each colour in the list.
00131 */
00132 void ColourCombo::addColours()
00133 {
00134     clear();
00135 
00136     for (ColourList::const_iterator it = mColourList.begin();  ;  ++it)
00137     {
00138         if (it == mColourList.end())
00139         {
00140             mCustomColour = mSelectedColour;
00141             break;
00142         }
00143         if (mSelectedColour == *it)
00144             break;
00145     }
00146 
00147     TQRect rect;
00148     drawCustomItem(rect, true);
00149 
00150     TQPainter painter;
00151     TQPixmap pixmap(rect.width(), rect.height());
00152     int i = 1;
00153     for (ColourList::const_iterator it = mColourList.begin();  it != mColourList.end();  ++i, ++it)
00154     {
00155         painter.begin(&pixmap);
00156         TQBrush brush(*it);
00157         painter.fillRect(rect, brush);
00158         painter.end();
00159 
00160         insertItem(pixmap);
00161         pixmap.detach();
00162 
00163         if (*it == mSelectedColour.rgb())
00164             setCurrentItem(i);
00165     }
00166 }
00167 
00168 void ColourCombo::drawCustomItem(TQRect& rect, bool insert)
00169 {
00170     TQPen pen;
00171     if (qGray(mCustomColour.rgb()) < 128)
00172         pen.setColor(Qt::white);
00173     else
00174         pen.setColor(Qt::black);
00175 
00176     TQPainter painter;
00177     TQFontMetrics fm = TQFontMetrics(painter.font());
00178     rect.setRect(0, 0, width(), fm.height() + 4);
00179     TQPixmap pixmap(rect.width(), rect.height());
00180 
00181     painter.begin(&pixmap);
00182     TQBrush brush(mCustomColour);
00183     painter.fillRect(rect, brush);
00184     painter.setPen(pen);
00185     painter.drawText(2, fm.ascent() + 2, i18n("Custom..."));
00186     painter.end();
00187 
00188     if (insert)
00189         insertItem(pixmap);
00190     else
00191         changeItem(pixmap, 0);
00192     pixmap.detach();
00193 }
00194 
00195 void ColourCombo::setReadOnly(bool ro)
00196 {
00197     mReadOnly = ro;
00198 }
00199 
00200 void ColourCombo::resizeEvent(TQResizeEvent* re)
00201 {
00202     TQComboBox::resizeEvent(re);
00203     addColours();
00204 }
00205 
00206 void ColourCombo::mousePressEvent(TQMouseEvent* e)
00207 {
00208     if (mReadOnly)
00209     {
00210         // Swallow up the event if it's the left button
00211         if (e->button() == Qt::LeftButton)
00212             return;
00213     }
00214     TQComboBox::mousePressEvent(e);
00215 }
00216 
00217 void ColourCombo::mouseReleaseEvent(TQMouseEvent* e)
00218 {
00219     if (!mReadOnly)
00220         TQComboBox::mouseReleaseEvent(e);
00221 }
00222 
00223 void ColourCombo::mouseMoveEvent(TQMouseEvent* e)
00224 {
00225     if (!mReadOnly)
00226         TQComboBox::mouseMoveEvent(e);
00227 }
00228 
00229 void ColourCombo::keyPressEvent(TQKeyEvent* e)
00230 {
00231     if (!mReadOnly  ||  e->key() == Qt::Key_Escape)
00232         TQComboBox::keyPressEvent(e);
00233 }
00234 
00235 void ColourCombo::keyReleaseEvent(TQKeyEvent* e)
00236 {
00237     if (!mReadOnly)
00238         TQComboBox::keyReleaseEvent(e);
00239 }