summaryrefslogtreecommitdiffabout
path: root/korganizer/koagendaview.cpp
Side-by-side diff
Diffstat (limited to 'korganizer/koagendaview.cpp') (more/less context) (ignore whitespace changes)
-rw-r--r--korganizer/koagendaview.cpp31
1 files changed, 28 insertions, 3 deletions
diff --git a/korganizer/koagendaview.cpp b/korganizer/koagendaview.cpp
index f811fba..488d9d4 100644
--- a/korganizer/koagendaview.cpp
+++ b/korganizer/koagendaview.cpp
@@ -1,175 +1,175 @@
/*
This file is part of KOrganizer.
Copyright (c) 2001 Cornelius Schumacher <schumacher@kde.org>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
As a special exception, permission is given to link this program
with any edition of Qt, and distribute the resulting executable,
without including the source code for Qt in the source distribution.
*/
#include <qhbox.h>
#include <qvbox.h>
#include <qlabel.h>
#include <qframe.h>
#include <qlayout.h>
#ifndef KORG_NOSPLITTER
#include <qsplitter.h>
#endif
#include <qfont.h>
#include <qfontmetrics.h>
#include <qpopupmenu.h>
#include <qtooltip.h>
#include <qpainter.h>
#include <qpushbutton.h>
#include <qapplication.h>
#include <kapplication.h>
#include <KDGanttMinimizeSplitter.h>
#include <kdebug.h>
#include <kstandarddirs.h>
#include <kiconloader.h>
#include <klocale.h>
#include <kconfig.h>
#include <kglobal.h>
#include "calendarview.h"
#include "koviewmanager.h"
#include <libkcal/calendar.h>
#include <libkcal/icaldrag.h>
#include <libkcal/dndfactory.h>
#include <kcalendarsystem.h>
#include "koglobals.h"
#ifndef KORG_NOPLUGINS
#include "kocore.h"
#endif
#include "koprefs.h"
#include "koagenda.h"
#include "koagendaitem.h"
#ifndef KORG_NOPRINTER
#include "calprinter.h"
#endif
#include "koagendaview.h"
//#include "koagendaview.moc"
//extern bool globalFlagBlockPainting;
extern int globalFlagBlockAgenda;
extern int globalFlagBlockStartup;
extern int globalFlagBlockAgendaItemPaint;
extern int globalFlagBlockAgendaItemUpdate;
extern int globalFlagBlockLabel;
using namespace KOrg;
-
+#define IDLETIMEOUT 3
TimeLabels::TimeLabels(int rows,QWidget *parent,const char *name,WFlags f) :
QScrollView(parent,name,f)
{
myPix.resize( 1, 1 );
mRows = rows;
mRedrawNeeded = true;
setMinimumHeight( 20 );
mCellHeight = KOPrefs::instance()->mHourSize*4;
enableClipper(true);
setHScrollBarMode(AlwaysOff);
setVScrollBarMode(AlwaysOff);
resizeContents(50,mRows * mCellHeight);
viewport()->setBackgroundMode( PaletteBackground );
}
void TimeLabels::setCellHeight(int height)
{
mCellHeight = height;
}
/*
Optimization so that only the "dirty" portion of the scroll view
is redrawn. Unfortunately, this is not called by default paintEvent() method.
*/
void TimeLabels::drawContents(QPainter *p,int cx, int cy, int cw, int ch)
{
cx = contentsX() + frameWidth()*2;
cw = contentsWidth() ;
// end of workaround
int cell = ((int)(cy/mCellHeight));
int y = cell * mCellHeight;
QFontMetrics fm = fontMetrics();
QString hour;
QString suffix = "am";
int timeHeight = fm.ascent();
QFont nFont = font();
p->setFont( font());
if (!KGlobal::locale()->use12Clock()) {
suffix = "00";
} else
if (cell > 11) suffix = "pm";
if ( timeHeight > mCellHeight ) {
timeHeight = mCellHeight-1;
int pointS = nFont.pointSize();
while ( pointS > 4 ) {
nFont.setPointSize( pointS );
fm = QFontMetrics( nFont );
if ( fm.ascent() < mCellHeight )
break;
-- pointS;
}
fm = QFontMetrics( nFont );
timeHeight = fm.ascent();
}
//timeHeight -= (timeHeight/4-2);
QFont sFont = nFont;
sFont.setPointSize( sFont.pointSize()/2 );
QFontMetrics fmS( sFont );
int sHei = fmS.ascent() ;
//sHei -= (sHei/4-2);
int startW = mMiniWidth - frameWidth()-2 ;
int tw2 = fmS.width(suffix);
timeHeight = (timeHeight-1) /2 -1;
//testline
//p->drawLine(0,0,0,contentsHeight());
while (y < cy + ch+mCellHeight) {
p->drawLine(startW-tw2+1 ,y,cw+2,y);
hour.setNum(cell);
// handle 24h and am/pm time formats
if (KGlobal::locale()->use12Clock()) {
if (cell == 12) suffix = "pm";
if (cell == 0) hour.setNum(12);
if (cell > 12) hour.setNum(cell - 12);
}
// center and draw the time label
int timeWidth = fm.width(hour);
int offset = startW - timeWidth - tw2 -1 ;
p->setFont( nFont );
p->drawText( offset, y+ timeHeight, hour);
p->setFont( sFont );
offset = startW - tw2;
p->drawText( offset, y -1, suffix);
// increment indices
y += mCellHeight;
@@ -480,195 +480,218 @@ KOAgendaView::KOAgendaView(Calendar *cal,QWidget *parent,const char *name) :
mAgenda->setPopup( mAllAgendaPopup );
mAllDayAgenda->setPopup( mAllAgendaPopup );
// make connections between dependent widgets
mTimeLabels->setAgenda(mAgenda);
// Update widgets to reflect user preferences
// updateConfig();
// createDayLabels();
// these blank widgets make the All Day Event box line up with the agenda
dummyAllDayRight->setFixedWidth(mAgenda->verticalScrollBar()->width());
dummyAgendaRight->setFixedWidth(mAgenda->verticalScrollBar()->width());
mDummyAllDayLeft->setFixedWidth(mTimeLabels->width());
// Scrolling
connect(mAgenda->verticalScrollBar(),SIGNAL(valueChanged(int)),
mTimeLabels, SLOT(positionChanged()));
connect(mTimeLabels->verticalScrollBar(),SIGNAL(valueChanged(int)),
SLOT(setContentsPos(int)));
connect(mAgenda,SIGNAL(showDateView( int, int)),SLOT(slotShowDateView( int, int )));
connect(mAllDayAgenda,SIGNAL(showDateView( int, int )), SLOT(slotShowDateView( int, int ) ));
// Create/Show/Edit/Delete Event
connect(mAgenda,SIGNAL(newEventSignal(int,int)),
SLOT(newEvent(int,int)));
connect(mAgenda,SIGNAL(newTodoSignal(int,int)),
SLOT(newTodo(int,int)));
connect(mAgenda,SIGNAL(newEventSignal(int,int,int,int)),
SLOT(newEvent(int,int,int,int)));
connect(mAllDayAgenda,SIGNAL(newEventSignal(int,int)),
SLOT(newEventAllDay(int,int)));
connect(mAllDayAgenda,SIGNAL(newTodoSignal(int,int)),
SLOT(newTodoAllDay(int,int)));
connect(mAllDayAgenda,SIGNAL(newEventSignal(int,int,int,int)),
SLOT(newEventAllDay(int,int)));
connect(mAgenda,SIGNAL(newTimeSpanSignal(int,int,int,int)),
SLOT(newTimeSpanSelected(int,int,int,int)));
connect(mAllDayAgenda,SIGNAL(newTimeSpanSignal(int,int,int,int)),
SLOT(newTimeSpanSelectedAllDay(int,int,int,int)));
connect(mAgenda,SIGNAL(newStartSelectSignal()),SLOT(updateView()));
connect(mAllDayAgenda,SIGNAL(newStartSelectSignal()),SLOT(updateView()));
connect(mAgenda,SIGNAL(editIncidenceSignal(Incidence *)),
SIGNAL(editIncidenceSignal(Incidence *)));
connect(mAllDayAgenda,SIGNAL(editIncidenceSignal(Incidence *)),
SIGNAL(editIncidenceSignal(Incidence *)));
connect(mAgenda,SIGNAL(showIncidenceSignal(Incidence *)),
SIGNAL(showIncidenceSignal(Incidence *)));
connect(mAllDayAgenda,SIGNAL(showIncidenceSignal(Incidence *)),
SIGNAL(showIncidenceSignal(Incidence *)));
connect(mAgenda,SIGNAL(deleteIncidenceSignal(Incidence *)),
SIGNAL(deleteIncidenceSignal(Incidence *)));
connect(mAllDayAgenda,SIGNAL(deleteIncidenceSignal(Incidence *)),
SIGNAL(deleteIncidenceSignal(Incidence *)));
connect(mAgenda,SIGNAL(itemModified(KOAgendaItem *, int )),
SLOT(updateEventDates(KOAgendaItem *, int )));
connect(mAllDayAgenda,SIGNAL(itemModified(KOAgendaItem *, int )),
SLOT(updateEventDates(KOAgendaItem *, int)));
// event indicator update
connect(mAgenda,SIGNAL(lowerYChanged(int)),
SLOT(updateEventIndicatorTop(int)));
connect(mAgenda,SIGNAL(upperYChanged(int)),
SLOT(updateEventIndicatorBottom(int)));
// drag signals
/*
connect(mAgenda,SIGNAL(startDragSignal(Event *)),
SLOT(startDrag(Event *)));
connect(mAllDayAgenda,SIGNAL(startDragSignal(Event *)),
SLOT(startDrag(Event *)));
*/
// synchronize selections
connect( mAgenda, SIGNAL( incidenceSelected( Incidence * ) ),
mAllDayAgenda, SLOT( deselectItem() ) );
connect( mAllDayAgenda, SIGNAL( incidenceSelected( Incidence * ) ),
mAgenda, SLOT( deselectItem() ) );
connect( mAgenda, SIGNAL( incidenceSelected( Incidence * ) ),
SIGNAL( incidenceSelected( Incidence * ) ) );
connect( mAllDayAgenda, SIGNAL( incidenceSelected( Incidence * ) ),
SIGNAL( incidenceSelected( Incidence * ) ) );
connect( mAgenda, SIGNAL( resizedSignal() ),
SLOT( updateConfig( ) ) );
connect( mAgenda, SIGNAL( addToCalSignal(Incidence *, Incidence *) ),
SLOT( addToCalSlot(Incidence *, Incidence * ) ) );
connect( mAllDayAgenda, SIGNAL( addToCalSignal(Incidence * ,Incidence *) ),
SLOT( addToCalSlot(Incidence * , Incidence *) ) );
// connect( mAgenda, SIGNAL( cloneIncidenceSignal(Incidence *) ), SIGNAL( cloneIncidenceSignal(Incidence *) ) );
//connect( mAllDayAgenda, SIGNAL( cloneIncidenceSignal(Incidence *) ), SIGNAL( cloneIncidenceSignal(Incidence *) ) );
connect( mAllDayAgenda, SIGNAL( signalClearSelection() ),mAgenda, SLOT( slotClearSelection()) );
connect( mAgenda, SIGNAL( signalClearSelection() ),mAllDayAgenda, SLOT( slotClearSelection()) );
+ connect( mAllDayAgenda, SIGNAL( updateViewSignal() ),this, SLOT( fillAgenda()) );
+ connect( mAgenda, SIGNAL( updateViewSignal() ), this, SLOT( fillAgenda()) );
+ mIdleTimer = new QTimer ( this );;
+ connect(mIdleTimer,SIGNAL(timeout()),SLOT(slotIdleTimeout()));
+}
+void KOAgendaView::slotIdleTimeout()
+{
+ qDebug("SECS TO %d ",mIdleStart.secsTo( QDateTime::currentDateTime() ) );
+ int secsfromstart = mIdleStart.secsTo( QDateTime::currentDateTime() );
+ mIdleTimer->stop();
+ bool isActice = topLevelWidget()->isActiveWindow();
+ qDebug("KO: Active Window %d ", isActice);
+ // we do nothing if we wake up from a suspend
+ if ( secsfromstart > IDLETIMEOUT + 50 && isActice ) {
+ qDebug("KO: Wakeup from suspend ");
+ mIdleTimer->start( IDLETIMEOUT * 1000 );
+ return;
+ }
+ qDebug("KO: Downsizing Pixmaps ");
+ mAgenda->shrinkPixmap();
+ mAllDayAgenda->shrinkPixmap();
+ KOAgendaItem::paintPix()->resize( 20,20);
+ KOAgendaItem::paintPixAllday()->resize( 20,20);
+
}
-
void KOAgendaView::toggleAllDay()
{
if ( mSplitterAgenda->firstHandle() )
mSplitterAgenda->firstHandle()->toggle();
}
void KOAgendaView::addToCalSlot(Incidence * inc, Incidence * incOld )
{
calendar()->addIncidence( inc );
if ( incOld ) {
if ( incOld->typeID() == todoID )
emit todoMoved((Todo*)incOld, KOGlobals::EVENTEDITED );
else
emit incidenceChanged(incOld, KOGlobals::EVENTEDITED);
}
}
void KOAgendaView::categoryChanged(Incidence * inc)
{
mAgenda->categoryChanged( inc );
mAllDayAgenda->categoryChanged( inc );
}
KOAgendaView::~KOAgendaView()
{
delete mAllAgendaPopup;
//delete mAllDayAgendaPopup;
delete KOAgendaItem::paintPix();
delete KOAgendaItem::paintPixAllday();
}
void KOAgendaView::resizeEvent( QResizeEvent* e )
{
//qDebug("KOAgendaView::resizeEvent( QResizeEvent* e ) %d ", e->size().width());
bool uc = false;
int ow = e->oldSize().width();
int oh = e->oldSize().height();
int w = e->size().width();
int h = e->size().height();
if ( (ow > oh && w< h ) || (ow < oh && w > h ) ) {
if ( ! mBlockUpdating && !globalFlagBlockStartup && !globalFlagBlockAgenda )
uc = true;
//qDebug("view changed %d %d %d %d ", ow, oh , w , h);
}
mUpcomingWidth = e->size().width() ;
if ( mBlockUpdating || uc ) {
mBlockUpdating = false;
//mAgenda->setMinimumSize(800 , 600 );
//qDebug("mAgenda->resize+++++++++++++++ ");
updateConfig();
//qDebug("KOAgendaView::Updating now possible ");
} else
createDayLabels();
//qDebug("resizeEvent end ");
}
void KOAgendaView::slotDaylabelClicked( int num )
{
QDate firstDate = mSelectedDates.first();
if ( num == -1 )
emit showDateView( 6, firstDate );
else if (num >= 0 ) {
if ( mSelectedDates.count() == 1)
emit showDateView( 9, firstDate.addDays( num ) );
else
emit showDateView( 3, firstDate.addDays( num ) );
}
else
showDateView( 10, firstDate.addDays(1) );
}
KOAgendaButton* KOAgendaView::getNewDaylabel()
{
KOAgendaButton * dayLabel = new KOAgendaButton(mDayLabels);
connect( dayLabel, SIGNAL( numClicked(int) ), this, SLOT ( slotDaylabelClicked(int) ) );
mDayLabelsList.append( dayLabel );
mLayoutDayLabels->addWidget(dayLabel);
return dayLabel ;
}
void KOAgendaView::createDayLabels()
{
if ( mBlockUpdating || globalFlagBlockLabel == 1) {
// qDebug(" KOAgendaView::createDayLabels() blocked ");
return;
}
int newHight;
if ( !mSelectedDates.count())
return;
// ### Before deleting and recreating we could check if mSelectedDates changed...
// It would remove some flickering and gain speed (since this is called by
// each updateView() call)
@@ -1205,236 +1228,238 @@ void KOAgendaView::fillAgenda()
int secs = event->dtStart().secsTo( event->dtEnd() );
QDateTime nextOcend =nextOcstart.addSecs( secs ); ;
beginX = currentDate.daysTo(nextOcstart.date()) + curCol;
endX = currentDate.daysTo(nextOcend.date()) + curCol;
}
}
int startY = mAgenda->timeToY(event->dtStart().time());
int endY = mAgenda->timeToY(event->dtEnd().time()) - 1;
//qDebug("insert %d %d %d %d %d ",beginX,endX,startY,endY , curCol );
if ((beginX <= 0 && curCol == 0) || beginX == curCol) {
//qDebug("insert!!! ");
mAgenda->insertMultiItem(event,currentDate,beginX,endX,startY,endY);
}
if (beginX == curCol) {
mMaxY[curCol] = mAgenda->timeToY(QTime(23,59));
if (startY < mMinY[curCol]) mMinY[curCol] = startY;
} else if (endX == curCol) {
mMinY[curCol] = mAgenda->timeToY(QTime(0,0));
if (endY > mMaxY[curCol]) mMaxY[curCol] = endY;
} else {
mMinY[curCol] = mAgenda->timeToY(QTime(0,0));
mMaxY[curCol] = mAgenda->timeToY(QTime(23,59));
}
} else {
int startY = mAgenda->timeToY(event->dtStart().time());
int endY = mAgenda->timeToY(event->dtEnd().time()) - 1;
if (endY < startY) endY = startY;
mAgenda->insertItem(event,currentDate,curCol,startY,endY);
if (startY < mMinY[curCol]) mMinY[curCol] = startY;
if (endY > mMaxY[curCol]) mMaxY[curCol] = endY;
}
}
// ---------- [display Todos --------------
unsigned int numTodo;
for (numTodo = 0; numTodo < todos.count(); ++numTodo) {
Todo *todo = todos.at(numTodo);
if ( ! todo->hasDueDate() && !todo->hasCompletedDate()) continue; // todo shall not be displayed if it has no date
if ( todo->hasCompletedDate() && !KOPrefs::instance()->mShowCompletedTodoInAgenda ) continue;
// ToDo items shall be displayed for the day they are due, but only showed today if they are already overdue.
// Already completed items can be displayed on their original due date
//if not KOPrefs::instance()->mShowTodoInAgenda, show overdue in agenda
bool overdue = (!todo->isCompleted()) && (todo->dtDue() < today) && KOPrefs::instance()->mShowTodoInAgenda;
bool fillIn = false;
if ( todo->hasCompletedDate() && todo->completed().date() == currentDate )
fillIn = true;
if ( ! fillIn && !todo->hasCompletedDate() )
fillIn = ((todo->dtDue().date() == currentDate) && !overdue) || ((currentDate == today) && overdue);
if ( fillIn ) {
if ( (todo->doesFloat() || overdue ) && !todo->hasCompletedDate() ) { // Todo has no due-time set or is already overdue
if ( KOPrefs::instance()->mShowTodoInAgenda )
mAllDayAgenda->insertAllDayItem(todo, currentDate, curCol, curCol);
}
else {
QDateTime dt;
if ( todo->hasCompletedDate() )
dt = todo->completed();
else
dt = todo->dtDue();;
int endY = mAgenda->timeToY(dt.time()) - 1;
int hi = (18/KOPrefs::instance()->mHourSize);
//qDebug("hei %d ",KOPrefs::instance()->mHourSize);
int startY = endY -hi;
mAgenda->insertItem(todo,currentDate,curCol,startY,endY);
if (startY < mMinY[curCol]) mMinY[curCol] = startY;
if (endY > mMaxY[curCol]) mMaxY[curCol] = endY;
}
}
}
// ---------- display Todos] --------------
++curCol;
}
mAgenda->hideUnused();
mAllDayAgenda->hideUnused();
mAgenda->checkScrollBoundaries();
deleteSelectedDateTime();
createDayLabels();
emit incidenceSelected( 0 );
if ( globalFlagBlockAgenda == 2 ) {
if ( KOPrefs::instance()->mSetTimeToDayStartAt )
setStartHour( KOPrefs::instance()->mDayBegins );
else if ( KOPrefs::instance()->mCenterOnCurrentTime )
setStartHour( QTime::currentTime ().hour() );
}
qApp->processEvents();
globalFlagBlockAgenda = 0;
mAllDayAgenda->drawContentsToPainter();
mAgenda->drawContentsToPainter();
repaintAgenda();
+ mIdleTimer->start ( IDLETIMEOUT *1000 );
+ mIdleStart = QDateTime::currentDateTime();
onlyOne = false;
}
void KOAgendaView::repaintAgenda()
{
mAgenda->viewport()->repaint( false );
mAllDayAgenda->viewport()->repaint( false );
mAgenda->finishUpdate();
mAllDayAgenda->finishUpdate();
}
void KOAgendaView::clearView()
{
mAllDayAgenda->clear();
mAgenda->clear();
}
void KOAgendaView::clearList()
{
clearView();
mAllDayAgenda->hideUnused();
mAgenda->hideUnused();
}
void KOAgendaView::printPreview(CalPrinter *calPrinter, const QDate &fd,
const QDate &td)
{
#ifndef KORG_NOPRINTER
if (fd == td)
calPrinter->preview(CalPrinter::Day, fd, td);
else
calPrinter->preview(CalPrinter::Week, fd, td);
#endif
}
// void KOAgendaView::updateMovedTodo()
// {
// // updateConfig();
// // emit updateTodoViews();
// }
void KOAgendaView::slotShowDateView( int mode , int d )
{
if ( d >= mSelectedDates.count() ) {
- qDebug("KOAgendaView::slotShowDateView datecounterror %d d ", d, mSelectedDates.count() );
+ qDebug("KOAgendaView::slotShowDateView datecounterror %d %d ", d, mSelectedDates.count() );
} else {
QDate day = mSelectedDates[d];
emit showDateView(mode , day );
}
}
void KOAgendaView::newEvent(int gx, int gy)
{
if (!mSelectedDates.count()) return;
QDate day = mSelectedDates[gx];
QTime time = mAgenda->gyToTime(gy);
QDateTime dt(day,time);
// if ( dt < QDateTime::currentDateTime () )
// dt = QDateTime::currentDateTime ().addSecs( 3600 );
emit newEventSignal(dt);
}
void KOAgendaView::newEvent(int gxStart, int gyStart, int gxEnd, int gyEnd)
{
if (!mSelectedDates.count()) return;
QDate dayStart = mSelectedDates[gxStart];
QDate dayEnd = mSelectedDates[gxEnd];
QTime timeStart = mAgenda->gyToTime(gyStart);
QTime timeEnd = mAgenda->gyToTime( gyEnd + 1 );
QDateTime dtStart(dayStart,timeStart);
QDateTime dtEnd(dayEnd,timeEnd);
emit newEventSignal(dtStart,dtEnd);
}
void KOAgendaView::newEventAllDay(int gx, int )
{
if (!mSelectedDates.count()) return;
QDate day = mSelectedDates[gx];
emit newEventSignal(day);
}
void KOAgendaView::newTodoAllDay(int gx, int )
{
if (!mSelectedDates.count()) return;
QDateTime day (mSelectedDates[gx] );
emit newTodoSignal(day, true);
}
void KOAgendaView::newTodo(int gx, int gy )
{
if (!mSelectedDates.count()) return;
QDate dayStart = mSelectedDates[gx];
QTime timeStart = mAgenda->gyToTime(gy);
QDateTime dt (dayStart,timeStart);
emit newTodoSignal( dt, false );
}
void KOAgendaView::updateEventIndicatorTop(int newY)
{
uint i;
for(i=0;i<mMinY.size();++i) {
if (newY >= mMinY.at(i)) mEventIndicatorTop->enableColumn(i,true);
else mEventIndicatorTop->enableColumn(i,false);
}
mEventIndicatorTop->update();
}
void KOAgendaView::updateEventIndicatorBottom(int newY)
{
uint i;
for(i=0;i<mMaxY.size();++i) {
if (newY <= mMaxY.at(i)) mEventIndicatorBottom->enableColumn(i,true);
else mEventIndicatorBottom->enableColumn(i,false);
}
mEventIndicatorBottom->update();
}
void KOAgendaView::startDrag(Event *event)
{
#ifndef KORG_NODND
DndFactory factory( calendar() );
ICalDrag *vd = factory.createDrag(event,this);
if (vd->drag()) {
kdDebug() << "KOAgendaView::startDrag(): Delete drag source" << endl;
}
#endif
}
void KOAgendaView::readSettings()
{
readSettings(KOGlobals::config());