kdeui Library API Documentation

kselect.cpp

00001 /* This file is part of the KDE libraries
00002     Copyright (C) 1997 Martin Jones (mjones@kde.org)
00003 
00004     This library is free software; you can redistribute it and/or
00005     modify it under the terms of the GNU Library General Public
00006     License as published by the Free Software Foundation; either
00007     version 2 of the License, or (at your option) any later version.
00008 
00009     This library is distributed in the hope that it will be useful,
00010     but WITHOUT ANY WARRANTY; without even the implied warranty of
00011     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00012     Library General Public License for more details.
00013 
00014     You should have received a copy of the GNU Library General Public License
00015     along with this library; see the file COPYING.LIB.  If not, write to
00016     the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00017     Boston, MA 02111-1307, USA.
00018 */
00019 
00020 #include <qimage.h>
00021 #include <qpainter.h>
00022 #include <qdrawutil.h>
00023 #include <kimageeffect.h>
00024 #include "kselect.h"
00025 
00026 #define STORE_W 8
00027 #define STORE_W2 STORE_W * 2
00028 
00029 //-----------------------------------------------------------------------------
00030 /*
00031  * 2D value selector.
00032  * The contents of the selector are drawn by derived class.
00033  */
00034 
00035 KXYSelector::KXYSelector( QWidget *parent, const char *name )
00036         : QWidget( parent, name )
00037 {
00038         xPos = 0;
00039         yPos = 0;
00040         minX = 0;
00041         minY = 0;
00042         maxX = 100;
00043         maxY = 100;
00044         store.setOptimization( QPixmap::BestOptim );
00045         store.resize( STORE_W2, STORE_W2 );
00046 }
00047 
00048 
00049 KXYSelector::~KXYSelector()
00050 {}
00051 
00052 
00053 void KXYSelector::setRange( int _minX, int _minY, int _maxX, int _maxY )
00054 {
00055         px = 2;
00056         py = 2;
00057         minX = _minX;
00058         minY = _minY;
00059         maxX = _maxX;
00060         maxY = _maxY;
00061 }
00062 
00063 void KXYSelector::setValues( int _xPos, int _yPos )
00064 {
00065         xPos = _xPos;
00066         yPos = _yPos;
00067 
00068         if ( xPos > maxX )
00069                 xPos = maxX;
00070         else if ( xPos < minX )
00071                 xPos = minX;
00072         
00073         if ( yPos > maxY )
00074                 yPos = maxY;
00075         else if ( yPos < minY )
00076                 yPos = minY;
00077 
00078         int xp = 2 + (width() - 4) * xPos / (maxX - minX);
00079         int yp = height() - 2 - (height() - 4) * yPos / (maxY - minY);
00080 
00081         setPosition( xp, yp );
00082 }
00083 
00084 QRect KXYSelector::contentsRect() const
00085 {
00086         return QRect( 2, 2, width()-4, height()-4 );
00087 }
00088 
00089 void KXYSelector::paintEvent( QPaintEvent *ev )
00090 {
00091         QRect cursorRect( px - STORE_W, py - STORE_W, STORE_W2, STORE_W2);
00092         QRect paintRect = ev->rect();
00093 
00094         QPainter painter;
00095         painter.begin( this );
00096 
00097         QBrush brush;
00098         qDrawShadePanel( &painter, 0, 0, width(), height(), colorGroup(),
00099                         TRUE, 2, &brush );
00100 
00101         drawContents( &painter );
00102         if (paintRect.contains(cursorRect))
00103         {
00104            bitBlt( &store, 0, 0, this, px - STORE_W, py - STORE_W,
00105                 STORE_W2, STORE_W2, CopyROP );
00106            drawCursor( &painter, px, py );
00107         }
00108         else if (paintRect.intersects(cursorRect))
00109         {
00110            repaint( cursorRect, false);
00111         }
00112 
00113         painter.end();
00114 }
00115 
00116 void KXYSelector::mousePressEvent( QMouseEvent *e )
00117 {
00118         setPosition( e->pos().x() - 2, e->pos().y() - 2 );
00119 
00120         emit valueChanged( xPos, yPos );
00121 }
00122 
00123 void KXYSelector::mouseMoveEvent( QMouseEvent *e )
00124 {
00125         setPosition( e->pos().x() - 2, e->pos().y() - 2 );
00126 
00127         emit valueChanged( xPos, yPos );
00128 }
00129 
00130 void KXYSelector::setPosition( int xp, int yp )
00131 {
00132         if ( xp < 2 )
00133                 xp = 2;
00134         else if ( xp > width() - 2 )
00135                 xp = width() - 2;
00136 
00137         if ( yp < 2 )
00138                 yp = 2;
00139         else if ( yp > height() - 2 )
00140                 yp = height() - 2;
00141 
00142         QPainter painter;
00143         painter.begin( this );
00144 
00145         bitBlt( this, px - STORE_W, py - STORE_W, &store, 0, 0,
00146                         STORE_W2, STORE_W2, CopyROP );
00147         bitBlt( &store, 0, 0, this, xp - STORE_W, yp - STORE_W,
00148                         STORE_W2, STORE_W2, CopyROP );
00149         drawCursor( &painter, xp, yp );
00150         px = xp;
00151         py = yp;
00152 
00153         painter.end();
00154 
00155         xPos = ( (maxX-minX) * (xp-2) ) / ( width()-4 );
00156         yPos = maxY - ( ( (maxY-minY) * (yp-2) ) / ( height()-4 ) );
00157         
00158         if ( xPos > maxX )
00159                 xPos = maxX;
00160         else if ( xPos < minX )
00161                 xPos = minX;
00162         
00163         if ( yPos > maxY )
00164                 yPos = maxY;
00165         else if ( yPos < minY )
00166                 yPos = minY;
00167 }
00168 
00169 void KXYSelector::drawContents( QPainter * )
00170 {}
00171 
00172 
00173 void KXYSelector::drawCursor( QPainter *p, int xp, int yp )
00174 {
00175         p->setPen( QPen( white ) );
00176 
00177         p->drawLine( xp - 6, yp - 6, xp - 2, yp - 2 );
00178         p->drawLine( xp - 6, yp + 6, xp - 2, yp + 2 );
00179         p->drawLine( xp + 6, yp - 6, xp + 2, yp - 2 );
00180         p->drawLine( xp + 6, yp + 6, xp + 2, yp + 2 );
00181 }
00182 
00183 //-----------------------------------------------------------------------------
00184 /*
00185  * 1D value selector with contents drawn by derived class.
00186  * See KColorDialog for example.
00187  */
00188 
00189 
00190 KSelector::KSelector( QWidget *parent, const char *name )
00191         : QWidget( parent, name ), QRangeControl()
00192 {
00193         _orientation = Horizontal;
00194         _indent = TRUE;
00195 }
00196 
00197 KSelector::KSelector( Orientation o, QWidget *parent, const char *name )
00198         : QWidget( parent, name ), QRangeControl()
00199 {
00200         _orientation = o;
00201         _indent = TRUE;
00202 }
00203 
00204 
00205 KSelector::~KSelector()
00206 {}
00207 
00208 
00209 QRect KSelector::contentsRect() const
00210 {
00211         if ( orientation() == Vertical )
00212                 return QRect( 2, 5, width()-9, height()-10 );
00213         else
00214                 return QRect( 5, 2, width()-10, height()-9 );
00215 }
00216 
00217 void KSelector::paintEvent( QPaintEvent * )
00218 {
00219         QPainter painter;
00220 
00221         painter.begin( this );
00222 
00223         drawContents( &painter );
00224 
00225         QBrush brush;
00226 
00227         if ( indent() )
00228         {
00229                 if ( orientation() == Vertical )
00230                         qDrawShadePanel( &painter, 0, 3, width()-5, height()-6,
00231                                 colorGroup(), TRUE, 2, &brush );
00232                 else
00233                         qDrawShadePanel( &painter, 3, 0, width()-6, height()-5,
00234                                 colorGroup(), TRUE, 2, &brush );
00235         }
00236 
00237         QPoint pos = calcArrowPos( value() );
00238         drawArrow( &painter, TRUE, pos );   
00239 
00240         painter.end();
00241 }
00242 
00243 void KSelector::mousePressEvent( QMouseEvent *e )
00244 {
00245         moveArrow( e->pos() );
00246 }
00247 
00248 void KSelector::mouseMoveEvent( QMouseEvent *e )
00249 {
00250         moveArrow( e->pos() );
00251 }
00252 
00253 void KSelector::valueChange()
00254 {
00255         QPainter painter;
00256         QPoint pos;
00257 
00258         painter.begin( this );
00259 
00260         pos = calcArrowPos( prevValue() );
00261         drawArrow( &painter, FALSE, pos );   
00262 
00263         pos = calcArrowPos( value() );
00264         drawArrow( &painter, TRUE, pos );   
00265 
00266         painter.end();
00267 }
00268 
00269 void KSelector::moveArrow( const QPoint &pos )
00270 {
00271         int val;
00272 
00273         if ( orientation() == Vertical )
00274                 val = ( maxValue() - minValue() ) * (height()-pos.y()-3)
00275                                 / (height()-10) + minValue();
00276         else
00277                 val = ( maxValue() - minValue() ) * (width()-pos.x()-3)
00278                                 / (width()-10) + minValue();
00279 
00280         if ( val > maxValue() )
00281                 val = maxValue();
00282         if ( val < minValue() )
00283                 val = minValue();
00284 
00285         emit valueChanged( val );
00286         setValue( val );
00287 }
00288 
00289 QPoint KSelector::calcArrowPos( int val )
00290 {
00291         QPoint p;
00292 
00293         if ( orientation() == Vertical )
00294         {
00295                 p.setY( height() - ( (height()-10) * val
00296                                 / ( maxValue() - minValue() ) + 5 ) );
00297                 p.setX( width() - 5 );
00298         }
00299         else
00300         {
00301                 p.setX( width() - ( (width()-10) * val
00302                                 / ( maxValue() - minValue() ) + 5 ) );
00303                 p.setY( height() - 5 );
00304         }
00305 
00306         return p;
00307 }
00308 
00309 void KSelector::drawContents( QPainter * )
00310 {}
00311 
00312 void KSelector::drawArrow( QPainter *painter, bool show, const QPoint &pos )
00313 {
00314   if ( show )
00315   {
00316     QPointArray array(3);
00317 
00318     painter->setPen( QPen() );
00319     painter->setBrush( QBrush( colorGroup().buttonText() ) );
00320     if ( orientation() == Vertical )
00321     {
00322       array.setPoint( 0, pos.x()+0, pos.y()+0 );
00323       array.setPoint( 1, pos.x()+5, pos.y()+5 );
00324       array.setPoint( 2, pos.x()+5, pos.y()-5 );
00325     }
00326     else
00327     {
00328       array.setPoint( 0, pos.x()+0, pos.y()+0 );
00329       array.setPoint( 1, pos.x()+5, pos.y()+5 );
00330       array.setPoint( 2, pos.x()-5, pos.y()+5 );
00331     }
00332 
00333     painter->drawPolygon( array );
00334   } 
00335   else 
00336   {
00337     if ( orientation() == Vertical )
00338     {
00339        repaint(pos.x(), pos.y()-5, 6, 11, true);
00340     }
00341     else
00342     {
00343        repaint(pos.x()-5, pos.y(), 11, 6, true);
00344     }
00345   }
00346 }
00347 
00348 //----------------------------------------------------------------------------
00349 
00350 KGradientSelector::KGradientSelector( QWidget *parent, const char *name )
00351     : KSelector( parent, name )
00352 {
00353     init();
00354 }
00355 
00356 
00357 KGradientSelector::KGradientSelector( Orientation o, QWidget *parent,
00358                 const char *name )
00359         : KSelector( o, parent, name )
00360 {
00361     init();
00362 }
00363 
00364 
00365 KGradientSelector::~KGradientSelector()
00366 {}
00367 
00368 
00369 void KGradientSelector::init()
00370 {
00371     color1.setRgb( 0, 0, 0 );
00372     color2.setRgb( 255, 255, 255 );
00373     
00374     text1 = text2 = "";
00375 }
00376 
00377 
00378 void KGradientSelector::drawContents( QPainter *painter )
00379 {
00380         QImage image( contentsRect().width(), contentsRect().height(), 32 );
00381 
00382         QColor col;
00383         float scale;
00384 
00385         int redDiff   = color2.red() - color1.red();
00386         int greenDiff = color2.green() - color1.green();
00387         int blueDiff  = color2.blue() - color1.blue();
00388 
00389         if ( orientation() == Vertical )
00390         {
00391                 for ( int y = 0; y < image.height(); y++ )
00392                 {
00393                         scale = 1.0 * y / image.height();
00394                         col.setRgb( color1.red() + int(redDiff*scale),
00395                                                 color1.green() + int(greenDiff*scale),
00396                                                 color1.blue() + int(blueDiff*scale) );
00397 
00398                         unsigned int *p = (uint *) image.scanLine( y );
00399                         for ( int x = 0; x < image.width(); x++ )
00400                                 *p++ = col.rgb();
00401                 }
00402         }
00403         else
00404         {
00405                 unsigned int *p = (uint *) image.scanLine( 0 );
00406 
00407                 for ( int x = 0; x < image.width(); x++ )
00408                 {
00409                         scale = 1.0 * x / image.width();
00410                         col.setRgb( color1.red() + int(redDiff*scale),
00411                                                 color1.green() + int(greenDiff*scale),
00412                                                 color1.blue() + int(blueDiff*scale) );
00413                         *p++ = col.rgb();
00414                 }
00415 
00416                 for ( int y = 1; y < image.height(); y++ )
00417                         memcpy( image.scanLine( y ), image.scanLine( y - 1),
00418                                  sizeof( unsigned int ) * image.width() );
00419         }
00420 
00421         QColor ditherPalette[8];
00422 
00423         for ( int s = 0; s < 8; s++ )
00424                 ditherPalette[s].setRgb( color1.red() + redDiff * s / 8,
00425                                                                 color1.green() + greenDiff * s / 8,
00426                                                                 color1.blue() + blueDiff * s / 8 );
00427 
00428         KImageEffect::dither( image, ditherPalette, 8 );
00429 
00430         QPixmap p;
00431         p.convertFromImage( image );
00432 
00433         painter->drawPixmap( contentsRect().x(), contentsRect().y(), p );
00434 
00435         if ( orientation() == Vertical )
00436         {
00437                 int yPos = contentsRect().top() + painter->fontMetrics().ascent() + 2;
00438                 int xPos = contentsRect().left() + (contentsRect().width() -
00439                          painter->fontMetrics().width( text2 )) / 2;
00440                 QPen pen( color2 );
00441                 painter->setPen( pen );
00442                 painter->drawText( xPos, yPos, text2 );
00443 
00444                 yPos = contentsRect().bottom() - painter->fontMetrics().descent() - 2;
00445                 xPos = contentsRect().left() + (contentsRect().width() - 
00446                         painter->fontMetrics().width( text1 )) / 2;
00447                 pen.setColor( color1 );
00448                 painter->setPen( pen );
00449                 painter->drawText( xPos, yPos, text1 );
00450         }
00451         else
00452         {
00453                 int yPos = contentsRect().bottom()-painter->fontMetrics().descent()-2;
00454 
00455                 QPen pen( color2 );
00456                 painter->setPen( pen );
00457                 painter->drawText( contentsRect().left() + 2, yPos, text1 );
00458 
00459                 pen.setColor( color1 );
00460                 painter->setPen( pen );
00461                 painter->drawText( contentsRect().right() -
00462                          painter->fontMetrics().width( text2 ) - 2, yPos, text2 );
00463         }
00464 }
00465 
00466 //-----------------------------------------------------------------------------
00467 
00468 void KXYSelector::virtual_hook( int, void* )
00469 { /*BASE::virtual_hook( id, data );*/ }
00470 
00471 void KSelector::virtual_hook( int, void* )
00472 { /*BASE::virtual_hook( id, data );*/ }
00473 
00474 void KGradientSelector::virtual_hook( int id, void* data )
00475 { KSelector::virtual_hook( id, data ); }
00476 
00477 #include "kselect.moc"
00478 
KDE Logo
This file is part of the documentation for kdelibs Version 3.1.5.
Documentation copyright © 1996-2002 the KDE developers.
Generated on Wed Jan 28 12:57:39 2004 by doxygen 1.3.4 written by Dimitri van Heesch, © 1997-2001