kdeui Library API Documentation

kdatetbl.cpp

00001 /*  -*- C++ -*-
00002     This file is part of the KDE libraries
00003     Copyright (C) 1997 Tim D. Gilman (tdgilman@best.org)
00004               (C) 1998-2001 Mirko Boehm (mirko@kde.org)
00005     This library is free software; you can redistribute it and/or
00006     modify it under the terms of the GNU Library General Public
00007     License as published by the Free Software Foundation; either
00008     version 2 of the License, or (at your option) any later version.
00009 
00010     This library is distributed in the hope that it will be useful,
00011     but WITHOUT ANY WARRANTY; without even the implied warranty of
00012     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00013     Library General Public License for more details.
00014 
00015     You should have received a copy of the GNU Library General Public License
00016     along with this library; see the file COPYING.LIB.  If not, write to
00017     the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00018     Boston, MA 02111-1307, USA.
00019 */
00020 
00022 //
00023 // Copyright (C) 1997 Tim D. Gilman
00024 //           (C) 1998-2001 Mirko Boehm
00025 // Written using Qt (http://www.troll.no) for the
00026 // KDE project (http://www.kde.org)
00027 //
00028 // This is a support class for the KDatePicker class.  It just
00029 // draws the calender table without titles, but could theoretically
00030 // be used as a standalone.
00031 //
00032 // When a date is selected by the user, it emits a signal:
00033 //      dateSelected(QDate)
00034 
00035 #include <kconfig.h>
00036 #include <kglobal.h>
00037 #include <kglobalsettings.h>
00038 #include <kapplication.h>
00039 #include <kaccel.h>
00040 #include <klocale.h>
00041 #include <kdebug.h>
00042 #include <knotifyclient.h>
00043 #include <kcalendarsystem.h>
00044 #include <kshortcut.h>
00045 #include <kstdaccel.h>
00046 #include "kdatepicker.h"
00047 #include "kdatetbl.h"
00048 #include "kpopupmenu.h"
00049 #include <qdatetime.h>
00050 #include <qstring.h>
00051 #include <qpen.h>
00052 #include <qpainter.h>
00053 #include <qdialog.h>
00054 #include <qdict.h>
00055 #include <assert.h>
00056 
00057 
00058 class KDateTable::KDateTablePrivate
00059 {
00060 public:
00061    KDateTablePrivate()
00062    {
00063       popupMenuEnabled=false;
00064       useCustomColors=false;
00065    }
00066 
00067    ~KDateTablePrivate()
00068    {
00069    }
00070 
00071    bool popupMenuEnabled;
00072    bool useCustomColors;
00073 
00074    struct DatePaintingMode
00075    {
00076      QColor fgColor;
00077      QColor bgColor;
00078      BackgroundMode bgMode;
00079    };
00080    QDict <DatePaintingMode> customPaintingModes;
00081 
00082 };
00083 
00084 
00085 KDateValidator::KDateValidator(QWidget* parent, const char* name)
00086     : QValidator(parent, name)
00087 {
00088 }
00089 
00090 QValidator::State
00091 KDateValidator::validate(QString& text, int&) const
00092 {
00093   QDate temp;
00094   // ----- everything is tested in date():
00095   return date(text, temp);
00096 }
00097 
00098 QValidator::State
00099 KDateValidator::date(const QString& text, QDate& d) const
00100 {
00101   QDate tmp = KGlobal::locale()->readDate(text);
00102   if (!tmp.isNull())
00103     {
00104       d = tmp;
00105       return Acceptable;
00106     } else
00107       return Valid;
00108 }
00109 
00110 void
00111 KDateValidator::fixup( QString& ) const
00112 {
00113 
00114 }
00115 
00116 KDateTable::KDateTable(QWidget *parent, QDate date_, const char* name, WFlags f)
00117   : QGridView(parent, name, f)
00118 {
00119   d = new KDateTablePrivate;
00120   setFontSize(10);
00121   if(!date_.isValid())
00122     {
00123       kdDebug() << "KDateTable ctor: WARNING: Given date is invalid, using current date." << endl;
00124       date_=QDate::currentDate();
00125     }
00126   setFocusPolicy( QWidget::StrongFocus );
00127   setNumRows(7); // 6 weeks max + headline
00128   setNumCols(7); // 7 days a week
00129   setHScrollBarMode(AlwaysOff);
00130   setVScrollBarMode(AlwaysOff);
00131   viewport()->setEraseColor(KGlobalSettings::baseColor());
00132   setDate(date_); // this initializes firstday, numdays, numDaysPrevMonth
00133   initAccels();
00134 }
00135 
00136 KDateTable::KDateTable(QWidget *parent, const char* name, WFlags f)
00137   : QGridView(parent, name, f)
00138 {
00139   d = new KDateTablePrivate;
00140   setFontSize(10);
00141   setFocusPolicy( QWidget::StrongFocus );
00142   setNumRows(7); // 6 weeks max + headline
00143   setNumCols(7); // 7 days a week
00144   setHScrollBarMode(AlwaysOff);
00145   setVScrollBarMode(AlwaysOff);
00146   viewport()->setEraseColor(KGlobalSettings::baseColor());
00147   setDate(QDate::currentDate()); // this initializes firstday, numdays, numDaysPrevMonth
00148   initAccels();
00149 }
00150 
00151 KDateTable::~KDateTable()
00152 {
00153   delete d;
00154 }
00155 
00156 void KDateTable::initAccels()
00157 {
00158   KAccel* accel = new KAccel(this, "date table accel");
00159   accel->insert(KStdAccel::Next, this, SLOT(nextMonth()));
00160   accel->insert(KStdAccel::Prior, this, SLOT(previousMonth()));
00161   accel->insert(KStdAccel::Home, this, SLOT(beginningOfMonth()));
00162   accel->insert(KStdAccel::End, this, SLOT(endOfMonth()));
00163   accel->insert(KStdAccel::BeginningOfLine, this, SLOT(beginningOfWeek()));
00164   accel->insert(KStdAccel::EndOfLine, this, SLOT(endOfWeek()));
00165   accel->readSettings();
00166 }
00167 
00168 int KDateTable::posFromDate( const QDate &dt )
00169 {
00170   const KCalendarSystem * calendar = KGlobal::locale()->calendar();
00171   const int firstWeekDay = KGlobal::locale()->weekStartDay();
00172   int pos = calendar->day( dt );
00173   int offset = (firstday - firstWeekDay + 7) % 7;
00174   // make sure at least one day of the previous month is visible.
00175   // adjust this <1 if more days should be forced visible:
00176   if ( offset < 1 ) offset += 7;
00177   return pos + offset;
00178 }
00179 
00180 QDate KDateTable::dateFromPos( int pos )
00181 {
00182   QDate pCellDate;
00183   const KCalendarSystem * calendar = KGlobal::locale()->calendar();
00184   calendar->setYMD(pCellDate, calendar->year(date), calendar->month(date), 1);
00185 
00186   int firstWeekDay = KGlobal::locale()->weekStartDay();
00187   int offset = (firstday - firstWeekDay + 7) % 7;
00188   // make sure at least one day of the previous month is visible.
00189   // adjust this <1 if more days should be forced visible:
00190   if ( offset < 1 ) offset += 7;
00191   pCellDate = calendar->addDays( pCellDate, pos - offset );
00192   return pCellDate;
00193 }
00194 
00195 void
00196 KDateTable::paintCell(QPainter *painter, int row, int col)
00197 {
00198   const KCalendarSystem * calendar = KGlobal::locale()->calendar();
00199 
00200   QRect rect;
00201   QString text;
00202   QPen pen;
00203   int w=cellWidth();
00204   int h=cellHeight();
00205   QFont font=KGlobalSettings::generalFont();
00206   // -----
00207 
00208   if(row == 0)
00209     { // we are drawing the headline
00210       font.setBold(true);
00211       painter->setFont(font);
00212       bool normalday = true;
00213       int firstWeekDay = KGlobal::locale()->weekStartDay();
00214       int daynum = ( col+firstWeekDay < 8 ) ? col+firstWeekDay :
00215                                               col+firstWeekDay-7;
00216       if ( daynum == calendar->weekDayOfPray() ||
00217          ( daynum == 6 && calendar->calendarName() == "gregorian" ) )
00218           normalday=false;
00219 
00220             QBrush brushInvertTitle(colorGroup().base());
00221             QColor titleColor(isEnabled()?( KGlobalSettings::activeTitleColor() ):( KGlobalSettings::inactiveTitleColor() ) );
00222             QColor textColor(isEnabled()?( KGlobalSettings::activeTextColor() ):( KGlobalSettings::inactiveTextColor() ) );
00223       if (!normalday)
00224         {
00225           painter->setPen(textColor);
00226           painter->setBrush(textColor);
00227           painter->drawRect(0, 0, w, h);
00228           painter->setPen(titleColor);
00229         } else {
00230           painter->setPen(titleColor);
00231           painter->setBrush(titleColor);
00232           painter->drawRect(0, 0, w, h);
00233           painter->setPen(textColor);
00234         }
00235       painter->drawText(0, 0, w, h-1, AlignCenter,
00236                         calendar->weekDayName(daynum, true), -1, &rect);
00237       painter->setPen(colorGroup().text());
00238       painter->moveTo(0, h-1);
00239       painter->lineTo(w-1, h-1);
00240       // ----- draw the weekday:
00241     } else {
00242       bool paintRect=true;
00243       painter->setFont(font);
00244       int pos=7*(row-1)+col;
00245 
00246       QDate pCellDate = dateFromPos( pos );
00247       // First day of month
00248       text = calendar->dayString(pCellDate, true);
00249       if( calendar->month(pCellDate) != calendar->month(date) )
00250         { // we are either
00251           // ° painting a day of the previous month or
00252           // ° painting a day of the following month
00253           // TODO: don't hardcode gray here! Use a color with less contrast to the background than normal text.
00254           painter->setPen( colorGroup().mid() );
00255 //          painter->setPen(gray);
00256         } else { // paint a day of the current month
00257           if ( d->useCustomColors )
00258           {
00259             KDateTablePrivate::DatePaintingMode *mode=d->customPaintingModes[pCellDate.toString()];
00260             if (mode)
00261             {
00262               if (mode->bgMode != NoBgMode)
00263               {
00264                 QBrush oldbrush=painter->brush();
00265                 painter->setBrush( mode->bgColor );
00266                 switch(mode->bgMode)
00267                 {
00268                   case(CircleMode) : painter->drawEllipse(0,0,w,h);break;
00269                   case(RectangleMode) : painter->drawRect(0,0,w,h);break;
00270                   case(NoBgMode) : // Should never be here, but just to get one
00271                                    // less warning when compiling
00272                   default: break;
00273                 }
00274                 painter->setBrush( oldbrush );
00275                 paintRect=false;
00276               }
00277               painter->setPen( mode->fgColor );
00278             } else
00279               painter->setPen(colorGroup().text());
00280           } else //if ( firstWeekDay < 4 ) // <- this doesn' make sense at all!
00281           painter->setPen(colorGroup().text());
00282         }
00283 
00284       pen=painter->pen();
00285       int firstWeekDay=KGlobal::locale()->weekStartDay();
00286       int offset=firstday-firstWeekDay;
00287       if(offset<1)
00288         offset+=7;
00289       int d = calendar->day(date);
00290            if( (offset+d) == (pos+1))
00291         {
00292            // draw the currently selected date
00293        if (isEnabled())
00294        {
00295            painter->setPen(colorGroup().highlight());
00296            painter->setBrush(colorGroup().highlight());
00297        }
00298        else 
00299        {
00300        painter->setPen(colorGroup().text());
00301            painter->setBrush(colorGroup().text());
00302        }
00303            pen=colorGroup().highlightedText();
00304         } else {
00305           painter->setBrush(paletteBackgroundColor());
00306           painter->setPen(paletteBackgroundColor());
00307 //          painter->setBrush(colorGroup().base());
00308 //          painter->setPen(colorGroup().base());
00309         }
00310 
00311       if ( pCellDate == QDate::currentDate() )
00312       {
00313          painter->setPen(colorGroup().text());
00314       }
00315 
00316       if ( paintRect ) painter->drawRect(0, 0, w, h);
00317       painter->setPen(pen);
00318       painter->drawText(0, 0, w, h, AlignCenter, text, -1, &rect);
00319     }
00320   if(rect.width()>maxCell.width()) maxCell.setWidth(rect.width());
00321   if(rect.height()>maxCell.height()) maxCell.setHeight(rect.height());
00322 }
00323 
00324 void KDateTable::nextMonth()
00325 {
00326     const KCalendarSystem * calendar = KGlobal::locale()->calendar();
00327   setDate(calendar->addMonths( date, 1 ));
00328 }
00329 
00330 void KDateTable::previousMonth()
00331 {
00332   const KCalendarSystem * calendar = KGlobal::locale()->calendar();
00333   setDate(calendar->addMonths( date, -1 ));
00334 }
00335 
00336 void KDateTable::beginningOfMonth()
00337 {
00338   setDate(date.addDays(1 - date.day()));
00339 }
00340 
00341 void KDateTable::endOfMonth()
00342 {
00343   setDate(date.addDays(date.daysInMonth() - date.day()));
00344 }
00345 
00346 void KDateTable::beginningOfWeek()
00347 {
00348   setDate(date.addDays(1 - date.dayOfWeek()));
00349 }
00350 
00351 void KDateTable::endOfWeek()
00352 {
00353   setDate(date.addDays(7 - date.dayOfWeek()));
00354 }    
00355 
00356 void
00357 KDateTable::keyPressEvent( QKeyEvent *e )
00358 {
00359     switch( e->key() ) {
00360     case Key_Up:
00361             setDate(date.addDays(-7));
00362         break;
00363     case Key_Down:
00364             setDate(date.addDays(7));
00365         break;
00366     case Key_Left:
00367             setDate(date.addDays(-1));
00368         break;
00369     case Key_Right:
00370             setDate(date.addDays(1));
00371         break;
00372     case Key_Minus:
00373         setDate(date.addDays(-1));
00374     break;
00375     case Key_Plus:
00376         setDate(date.addDays(1));
00377     break;
00378     case Key_N:
00379         setDate(QDate::currentDate());
00380     break;
00381     case Key_Return:
00382     case Key_Enter:
00383         emit tableClicked();
00384         break;
00385     case Key_Control:
00386     case Key_Alt:
00387     case Key_Meta:
00388     case Key_Shift:
00389       // Don't beep for modifiers
00390       break;
00391     default:
00392       if (!e->state()) { // hm
00393     KNotifyClient::beep();
00394 }
00395     }
00396 }
00397 
00398 void
00399 KDateTable::viewportResizeEvent(QResizeEvent * e)
00400 {
00401   QGridView::viewportResizeEvent(e);
00402 
00403   setCellWidth(viewport()->width()/7);
00404   setCellHeight(viewport()->height()/7);
00405 }
00406 
00407 void
00408 KDateTable::setFontSize(int size)
00409 {
00410   int count;
00411   QFontMetrics metrics(fontMetrics());
00412   QRect rect;
00413   // ----- store rectangles:
00414   fontsize=size;
00415   // ----- find largest day name:
00416   maxCell.setWidth(0);
00417   maxCell.setHeight(0);
00418   for(count=0; count<7; ++count)
00419     {
00420       rect=metrics.boundingRect(KGlobal::locale()->calendar()
00421                                 ->weekDayName(count+1, true));
00422       maxCell.setWidth(QMAX(maxCell.width(), rect.width()));
00423       maxCell.setHeight(QMAX(maxCell.height(), rect.height()));
00424     }
00425   // ----- compare with a real wide number and add some space:
00426   rect=metrics.boundingRect(QString::fromLatin1("88"));
00427   maxCell.setWidth(QMAX(maxCell.width()+2, rect.width()));
00428   maxCell.setHeight(QMAX(maxCell.height()+4, rect.height()));
00429 }
00430 
00431 void
00432 KDateTable::wheelEvent ( QWheelEvent * e )
00433 {
00434     setDate(date.addMonths( -(int)(e->delta()/120)) );
00435     e->accept();
00436 }
00437 
00438 void
00439 KDateTable::contentsMousePressEvent(QMouseEvent *e)
00440 {
00441 
00442   if(e->type()!=QEvent::MouseButtonPress)
00443     { // the KDatePicker only reacts on mouse press events:
00444       return;
00445     }
00446   if(!isEnabled())
00447     {
00448       KNotifyClient::beep();
00449       return;
00450     }
00451 
00452   // -----
00453   int row, col, pos, temp;
00454   QPoint mouseCoord;
00455   // -----
00456   mouseCoord = e->pos();
00457   row=rowAt(mouseCoord.y());
00458   col=columnAt(mouseCoord.x());
00459   if(row<1 || col<0)
00460     { // the user clicked on the frame of the table
00461       return;
00462     }
00463 
00464   // Rows and columns are zero indexed.  The (row - 1) below is to avoid counting
00465   // the row with the days of the week in the calculation.
00466 
00467   // old selected date:
00468   temp = posFromDate( date );
00469   // new position and date
00470   pos = (7 * (row - 1)) + col; 
00471   QDate clickedDate = dateFromPos( pos );
00472 
00473   // set the new date. If it is in the previous or next month, the month will
00474   // automatically be changed, no need to do that manually...
00475   setDate( clickedDate );
00476 
00477   // call updateCell on the old and new selection. If setDate switched to a different 
00478   // month, these cells will be painted twice, but that's no problem.
00479   updateCell( temp/7+1, temp%7 );
00480   updateCell( row, col );
00481 
00482   emit tableClicked();
00483 
00484   if (  e->button() == Qt::RightButton && d->popupMenuEnabled )
00485   {
00486         KPopupMenu *menu = new KPopupMenu();
00487         menu->insertTitle( KGlobal::locale()->formatDate(clickedDate) );
00488         emit aboutToShowContextMenu( menu, clickedDate );
00489         menu->popup(e->globalPos());
00490   }
00491 }
00492 
00493 bool
00494 KDateTable::setDate(const QDate& date_)
00495 {
00496   bool changed=false;
00497   QDate temp;
00498   // -----
00499   if(!date_.isValid())
00500     {
00501       kdDebug() << "KDateTable::setDate: refusing to set invalid date." << endl;
00502       return false;
00503     }
00504   if(date!=date_)
00505     {
00506       emit(dateChanged(date, date_));
00507       date=date_;
00508       emit(dateChanged(date));
00509       changed=true;
00510     }
00511   const KCalendarSystem * calendar = KGlobal::locale()->calendar();
00512 
00513   calendar->setYMD(temp, calendar->year(date), calendar->month(date), 1);
00514   //temp.setYMD(date.year(), date.month(), 1);
00515   //kdDebug() << "firstDayInWeek: " << temp.toString() << endl;
00516   firstday=temp.dayOfWeek();
00517   numdays=calendar->daysInMonth(date);
00518 
00519   temp = calendar->addMonths(temp, -1);
00520   numDaysPrevMonth=calendar->daysInMonth(temp);
00521   if(changed)
00522     {
00523       repaintContents(false);
00524     }
00525   return true;
00526 }
00527 
00528 const QDate&
00529 KDateTable::getDate() const
00530 {
00531   return date;
00532 }
00533 
00534 // what are those repaintContents() good for? (pfeiffer)
00535 void KDateTable::focusInEvent( QFocusEvent *e )
00536 {
00537 //    repaintContents(false);
00538     QGridView::focusInEvent( e );
00539 }
00540 
00541 void KDateTable::focusOutEvent( QFocusEvent *e )
00542 {
00543 //    repaintContents(false);
00544     QGridView::focusOutEvent( e );
00545 }
00546 
00547 QSize
00548 KDateTable::sizeHint() const
00549 {
00550   if(maxCell.height()>0 && maxCell.width()>0)
00551     {
00552       return QSize(maxCell.width()*numCols()+2*frameWidth(),
00553              (maxCell.height()+2)*numRows()+2*frameWidth());
00554     } else {
00555       kdDebug() << "KDateTable::sizeHint: obscure failure - " << endl;
00556       return QSize(-1, -1);
00557     }
00558 }
00559 
00560 void KDateTable::setPopupMenuEnabled( bool enable )
00561 {
00562    d->popupMenuEnabled=enable;
00563 }
00564 
00565 bool KDateTable::popupMenuEnabled() const
00566 {
00567    return d->popupMenuEnabled;
00568 }
00569 
00570 void KDateTable::setCustomDatePainting(const QDate &date, const QColor &fgColor, BackgroundMode bgMode, const QColor &bgColor)
00571 {
00572     if (!fgColor.isValid())
00573     {
00574         unsetCustomDatePainting( date );
00575         return;
00576     }
00577 
00578     KDateTablePrivate::DatePaintingMode *mode=new KDateTablePrivate::DatePaintingMode;
00579     mode->bgMode=bgMode;
00580     mode->fgColor=fgColor;
00581     mode->bgColor=bgColor;
00582 
00583     d->customPaintingModes.replace( date.toString(), mode );
00584     d->useCustomColors=true;
00585     update();
00586 }
00587 
00588 void KDateTable::unsetCustomDatePainting( const QDate &date )
00589 {
00590     d->customPaintingModes.remove( date.toString() );
00591 }
00592 
00593 KDateInternalWeekSelector::KDateInternalWeekSelector
00594 (QWidget* parent, const char* name)
00595   : QLineEdit(parent, name),
00596     val(new QIntValidator(this)),
00597     result(0)
00598 {
00599   QFont font;
00600   // -----
00601   font=KGlobalSettings::generalFont();
00602   setFont(font);
00603   setFrameStyle(QFrame::NoFrame);
00604   setValidator(val);
00605   connect(this, SIGNAL(returnPressed()), SLOT(weekEnteredSlot()));
00606 }
00607 
00608 void
00609 KDateInternalWeekSelector::weekEnteredSlot()
00610 {
00611   bool ok;
00612   int week;
00613   // ----- check if this is a valid week:
00614   week=text().toInt(&ok);
00615   if(!ok)
00616     {
00617       KNotifyClient::beep();
00618       return;
00619     }
00620   result=week;
00621   emit(closeMe(1));
00622 }
00623 
00624 int
00625 KDateInternalWeekSelector::getWeek()
00626 {
00627   return result;
00628 }
00629 
00630 void
00631 KDateInternalWeekSelector::setWeek(int week)
00632 {
00633   QString temp;
00634   // -----
00635   temp.setNum(week);
00636   setText(temp);
00637 }
00638 
00639 void
00640 KDateInternalWeekSelector::setMaxWeek(int max)
00641 {
00642   val->setRange(1, max);
00643 }
00644 
00645 // ### CFM To avoid binary incompatibility.
00646 //     In future releases, remove this and replace by  a QDate
00647 //     private member, needed in KDateInternalMonthPicker::paintCell
00648 class KDateInternalMonthPicker::KDateInternalMonthPrivate {
00649 public:
00650         KDateInternalMonthPrivate (int y, int m, int d)
00651         : year(y), month(m), day(d)
00652         {};
00653         int year;
00654         int month;
00655         int day;
00656 };
00657 
00658 KDateInternalMonthPicker::~KDateInternalMonthPicker() {
00659    delete d;
00660 }
00661 
00662 KDateInternalMonthPicker::KDateInternalMonthPicker
00663 (const QDate & date, QWidget* parent, const char* name)
00664   : QGridView(parent, name),
00665     result(0) // invalid
00666 {
00667   QRect rect;
00668   QFont font;
00669   // -----
00670   activeCol = -1;
00671   activeRow = -1;
00672   font=KGlobalSettings::generalFont();
00673   setFont(font);
00674   setHScrollBarMode(AlwaysOff);
00675   setVScrollBarMode(AlwaysOff);
00676   setFrameStyle(QFrame::NoFrame);
00677   setNumCols(3);
00678   d = new KDateInternalMonthPrivate(date.year(), date.month(), date.day());
00679   // For monthsInYear != 12
00680   setNumRows( (KGlobal::locale()->calendar()->monthsInYear(date) + 2) / 3);
00681   // enable to find drawing failures:
00682   // setTableFlags(Tbl_clipCellPainting);
00683   viewport()->setEraseColor(KGlobalSettings::baseColor()); // for consistency with the datepicker
00684   // ----- find the preferred size
00685   //       (this is slow, possibly, but unfortunately it is needed here):
00686   QFontMetrics metrics(font);
00687   for(int i = 1; ; ++i)
00688     {
00689       QString str = KGlobal::locale()->calendar()->monthName(i,
00690          KGlobal::locale()->calendar()->year(date), false);
00691       if (str.isNull()) break;
00692       rect=metrics.boundingRect(str);
00693       if(max.width()<rect.width()) max.setWidth(rect.width());
00694       if(max.height()<rect.height()) max.setHeight(rect.height());
00695     }
00696 }
00697 
00698 QSize
00699 KDateInternalMonthPicker::sizeHint() const
00700 {
00701   return QSize((max.width()+6)*numCols()+2*frameWidth(),
00702          (max.height()+6)*numRows()+2*frameWidth());
00703 }
00704 
00705 int
00706 KDateInternalMonthPicker::getResult() const
00707 {
00708   return result;
00709 }
00710 
00711 void
00712 KDateInternalMonthPicker::setupPainter(QPainter *p)
00713 {
00714   p->setPen(KGlobalSettings::textColor());
00715 }
00716 
00717 void
00718 KDateInternalMonthPicker::viewportResizeEvent(QResizeEvent*)
00719 {
00720   setCellWidth(width() / numCols());
00721   setCellHeight(height() / numRows());
00722 }
00723 
00724 void
00725 KDateInternalMonthPicker::paintCell(QPainter* painter, int row, int col)
00726 {
00727   int index;
00728   QString text;
00729   // ----- find the number of the cell:
00730   index=3*row+col+1;
00731   text=KGlobal::locale()->calendar()->monthName(index,
00732     KGlobal::locale()->calendar()->year(QDate(d->year, d->month,
00733     d->day)), false);
00734   painter->drawText(0, 0, cellWidth(), cellHeight(), AlignCenter, text);
00735   if ( activeCol == col && activeRow == row )
00736       painter->drawRect( 0, 0, cellWidth(), cellHeight() );
00737 }
00738 
00739 void
00740 KDateInternalMonthPicker::contentsMousePressEvent(QMouseEvent *e)
00741 {
00742   if(!isEnabled() || e->button() != LeftButton)
00743     {
00744       KNotifyClient::beep();
00745       return;
00746     }
00747   // -----
00748   int row, col;
00749   QPoint mouseCoord;
00750   // -----
00751   mouseCoord = e->pos();
00752   row=rowAt(mouseCoord.y());
00753   col=columnAt(mouseCoord.x());
00754 
00755   if(row<0 || col<0)
00756     { // the user clicked on the frame of the table
00757       activeCol = -1;
00758       activeRow = -1;
00759     } else {
00760       activeCol = col;
00761       activeRow = row;
00762       updateCell( row, col /*, false */ );
00763   }
00764 }
00765 
00766 void
00767 KDateInternalMonthPicker::contentsMouseMoveEvent(QMouseEvent *e)
00768 {
00769   if (e->state() & LeftButton)
00770     {
00771       int row, col;
00772       QPoint mouseCoord;
00773       // -----
00774       mouseCoord = e->pos();
00775       row=rowAt(mouseCoord.y());
00776       col=columnAt(mouseCoord.x());
00777       int tmpRow = -1, tmpCol = -1;
00778       if(row<0 || col<0)
00779         { // the user clicked on the frame of the table
00780           if ( activeCol > -1 )
00781             {
00782               tmpRow = activeRow;
00783               tmpCol = activeCol;
00784             }
00785           activeCol = -1;
00786           activeRow = -1;
00787         } else {
00788           bool differentCell = (activeRow != row || activeCol != col);
00789           if ( activeCol > -1 && differentCell)
00790             {
00791               tmpRow = activeRow;
00792               tmpCol = activeCol;
00793             }
00794           if ( differentCell)
00795             {
00796               activeRow = row;
00797               activeCol = col;
00798               updateCell( row, col /*, false */ ); // mark the new active cell
00799             }
00800         }
00801       if ( tmpRow > -1 ) // repaint the former active cell
00802           updateCell( tmpRow, tmpCol /*, true */ );
00803     }
00804 }
00805 
00806 void
00807 KDateInternalMonthPicker::contentsMouseReleaseEvent(QMouseEvent *e)
00808 {
00809   if(!isEnabled())
00810     {
00811       return;
00812     }
00813   // -----
00814   int row, col, pos;
00815   QPoint mouseCoord;
00816   // -----
00817   mouseCoord = e->pos();
00818   row=rowAt(mouseCoord.y());
00819   col=columnAt(mouseCoord.x());
00820   if(row<0 || col<0)
00821     { // the user clicked on the frame of the table
00822       emit(closeMe(0));
00823     }
00824 
00825   pos=3*row+col+1;
00826   result=pos;
00827   emit(closeMe(1));
00828 }
00829 
00830 
00831 
00832 KDateInternalYearSelector::KDateInternalYearSelector
00833 (QWidget* parent, const char* name)
00834   : QLineEdit(parent, name),
00835     val(new QIntValidator(this)),
00836     result(0)
00837 {
00838   QFont font;
00839   // -----
00840   font=KGlobalSettings::generalFont();
00841   setFont(font);
00842   setFrameStyle(QFrame::NoFrame);
00843   // we have to respect the limits of QDate here, I fear:
00844   val->setRange(0, 8000);
00845   setValidator(val);
00846   connect(this, SIGNAL(returnPressed()), SLOT(yearEnteredSlot()));
00847 }
00848 
00849 void
00850 KDateInternalYearSelector::yearEnteredSlot()
00851 {
00852   bool ok;
00853   int year;
00854   QDate date;
00855   // ----- check if this is a valid year:
00856   year=text().toInt(&ok);
00857   if(!ok)
00858     {
00859       KNotifyClient::beep();
00860       return;
00861     }
00862   //date.setYMD(year, 1, 1);
00863   KGlobal::locale()->calendar()->setYMD(date, year, 1, 1);
00864   if(!date.isValid())
00865     {
00866       KNotifyClient::beep();
00867       return;
00868     }
00869   result=year;
00870   emit(closeMe(1));
00871 }
00872 
00873 int
00874 KDateInternalYearSelector::getYear()
00875 {
00876   return result;
00877 }
00878 
00879 void
00880 KDateInternalYearSelector::setYear(int year)
00881 {
00882   QString temp;
00883   // -----
00884   temp.setNum(year);
00885   setText(temp);
00886 }
00887 
00888 KPopupFrame::KPopupFrame(QWidget* parent, const char*  name)
00889   : QFrame(parent, name, WType_Popup),
00890     result(0), // rejected
00891     main(0)
00892 {
00893   setFrameStyle(QFrame::Box|QFrame::Raised);
00894   setMidLineWidth(2);
00895 }
00896 
00897 void
00898 KPopupFrame::keyPressEvent(QKeyEvent* e)
00899 {
00900   if(e->key()==Key_Escape)
00901     {
00902       result=0; // rejected
00903       qApp->exit_loop();
00904     }
00905 }
00906 
00907 void
00908 KPopupFrame::close(int r)
00909 {
00910   result=r;
00911   qApp->exit_loop();
00912 }
00913 
00914 void
00915 KPopupFrame::setMainWidget(QWidget* m)
00916 {
00917   main=m;
00918   if(main)
00919     {
00920       resize(main->width()+2*frameWidth(), main->height()+2*frameWidth());
00921     }
00922 }
00923 
00924 void
00925 KPopupFrame::resizeEvent(QResizeEvent*)
00926 {
00927   if(main)
00928     {
00929       main->setGeometry(frameWidth(), frameWidth(),
00930           width()-2*frameWidth(), height()-2*frameWidth());
00931     }
00932 }
00933 
00934 void
00935 KPopupFrame::popup(const QPoint &pos)
00936 {
00937   // Make sure the whole popup is visible.
00938   QRect d = KGlobalSettings::desktopGeometry(pos);
00939 
00940   int x = pos.x();
00941   int y = pos.y();
00942   int w = width();
00943   int h = height();
00944   if (x+w > d.x()+d.width())
00945     x = d.width() - w;
00946   if (y+h > d.y()+d.height())
00947     y = d.height() - h;
00948   if (x < d.x())
00949     x = 0;
00950   if (y < d.y())
00951     y = 0;
00952 
00953   // Pop the thingy up.
00954   move(x, y);
00955   show();
00956 }
00957 
00958 int
00959 KPopupFrame::exec(QPoint pos)
00960 {
00961   popup(pos);
00962   repaint();
00963   qApp->enter_loop();
00964   hide();
00965   return result;
00966 }
00967 
00968 int
00969 KPopupFrame::exec(int x, int y)
00970 {
00971   return exec(QPoint(x, y));
00972 }
00973 
00974 void KPopupFrame::virtual_hook( int, void* )
00975 { /*BASE::virtual_hook( id, data );*/ }
00976 
00977 void KDateTable::virtual_hook( int, void* )
00978 { /*BASE::virtual_hook( id, data );*/ }
00979 
00980 #include "kdatetbl.moc"
KDE Logo
This file is part of the documentation for kdeui Library Version 3.4.0.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Fri Jul 21 13:14:01 2006 by doxygen 1.4.0 written by Dimitri van Heesch, © 1997-2003