-rw-r--r-- | korganizer/koeditorgeneraltodo.cpp | 2 | ||||
-rw-r--r-- | korganizer/koeditorgeneraltodo.h | 1 | ||||
-rw-r--r-- | korganizer/koeditorrecurrence.cpp | 20 | ||||
-rw-r--r-- | korganizer/koeditorrecurrence.h | 4 | ||||
-rw-r--r-- | korganizer/kotodoeditor.cpp | 43 | ||||
-rw-r--r-- | korganizer/kotodoeditor.h | 4 | ||||
-rw-r--r-- | libkcal/icalformatimpl.cpp | 10 | ||||
-rw-r--r-- | libkcal/incidence.cpp | 35 | ||||
-rw-r--r-- | libkcal/incidence.h | 9 | ||||
-rw-r--r-- | microkde/kdialogbase.h | 2 |
10 files changed, 119 insertions, 11 deletions
diff --git a/korganizer/koeditorgeneraltodo.cpp b/korganizer/koeditorgeneraltodo.cpp index 6370b54..a9d1ed3 100644 --- a/korganizer/koeditorgeneraltodo.cpp +++ b/korganizer/koeditorgeneraltodo.cpp @@ -364,16 +364,17 @@ void KOEditorGeneralTodo::enableDueEdit(bool enable) mTimeButton->setChecked(false); } if (enable) { mDueTimeEdit->setEnabled( mTimeButton->isChecked() ); } else { mDueTimeEdit->setEnabled( false ); } + emit datesChecked(); } void KOEditorGeneralTodo::enableStartEdit( bool enable ) { mStartDateEdit->setEnabled( enable ); if(mDueCheck->isChecked() || mStartCheck->isChecked()) { mTimeButton->setEnabled(true); @@ -383,16 +384,17 @@ void KOEditorGeneralTodo::enableStartEdit( bool enable ) mTimeButton->setChecked(false); } if (enable) { mStartTimeEdit->setEnabled( mTimeButton->isChecked() ); } else { mStartTimeEdit->setEnabled( false ); } + emit datesChecked(); } void KOEditorGeneralTodo::enableTimeEdits(bool enable) { if(mStartCheck->isChecked()) { mStartTimeEdit->setEnabled( enable ); } if(mDueCheck->isChecked()) { diff --git a/korganizer/koeditorgeneraltodo.h b/korganizer/koeditorgeneraltodo.h index 98f43dd..b198539 100644 --- a/korganizer/koeditorgeneraltodo.h +++ b/korganizer/koeditorgeneraltodo.h @@ -67,16 +67,17 @@ class KOEditorGeneralTodo : public KOEditorGeneral /** Check if the input is valid. */ bool validateInput(); /** The todo has been modified externally */ void modified (Todo*, int); signals: void openCategoryDialog(); + void datesChecked(); protected slots: void completedChanged(int); void enableDueEdit( bool enable ); void enableStartEdit( bool enable ); void enableTimeEdits( bool enable ); void showAlarm(); diff --git a/korganizer/koeditorrecurrence.cpp b/korganizer/koeditorrecurrence.cpp index 4209e10..bedc75a 100644 --- a/korganizer/koeditorrecurrence.cpp +++ b/korganizer/koeditorrecurrence.cpp @@ -37,16 +37,17 @@ #include <kdialog.h> #include <kglobal.h> #include <klocale.h> #include <kiconloader.h> #include <kdebug.h> #include <knumvalidator.h> #include <libkcal/event.h> +#include <libkcal/todo.h> #include <libkdepim/kdateedit.h> #include "koprefs.h" #include "koeditorrecurrence.h" /////////////////////////// RecurBase /////////////////////////////// @@ -900,40 +901,47 @@ void KOEditorRecurrence::setDefaults( QDateTime from, QDateTime to, bool ) mMonthly->setFrequency( 1 ); mMonthly->setByPos((from.date().day()/7), from.date().dayOfWeek()-1 ); mMonthly->setByDay( from.date().day()-1 ); mYearly->setFrequency( 1 ); mYearly->setByDay( from.date().dayOfYear() ); mYearly->setByMonth( from.date().month(), from.date().day() ); } -void KOEditorRecurrence::readEvent(Event *event) +void KOEditorRecurrence::readEvent(Incidence *event) { - setDefaults( event->dtStart(), event->dtEnd(), true ); + + QDateTime dtEnd; + if ( event->type() == "Event" ) + dtEnd = ((Event*)event)->dtEnd(); + else + dtEnd = ((Todo*)event)->dtDue(); + + setDefaults( event->dtStart(), dtEnd, true ); QBitArray rDays( 7 ); QPtrList<Recurrence::rMonthPos> rmp; QPtrList<int> rmd; int day = 0; int count = 0; int month = 0; - setDateTimes( event->dtStart(), event->dtEnd() ); + setDateTimes( event->dtStart(), dtEnd ); Recurrence *r = event->recurrence(); int f = r->frequency(); int recurs = r->doesRecur(); mEnabledCheck->setChecked( recurs ); setEnabled( recurs ); int recurrenceType = RecurrenceChooser::Weekly; switch ( recurs ) { case Recurrence::rNone: - setDefaults( event->dtStart(), event->dtEnd(), true ); + setDefaults( event->dtStart(), dtEnd, true ); break; case Recurrence::rDaily: recurrenceType = RecurrenceChooser::Daily; mDaily->setFrequency( f ); break; case Recurrence::rWeekly: recurrenceType = RecurrenceChooser::Weekly; mWeekly->setFrequency( f ); @@ -995,17 +1003,17 @@ void KOEditorRecurrence::readEvent(Event *event) break; case Recurrence::rYearlyDay: qDebug("Recurrence::rYearlyDay: "); recurrenceType = RecurrenceChooser::Yearly; mYearly->setByDay( event->dtStart().date().dayOfYear() ); mYearly->setFrequency( f ); break; default: - setDefaults( event->dtStart(), event->dtEnd(), true ); + setDefaults( event->dtStart(), dtEnd, true ); break; } mRecurrenceChooser->setType( recurrenceType ); showCurrentRule( recurrenceType ); mRecurrenceRange->setDateTimes( event->dtStart() ); @@ -1019,17 +1027,17 @@ void KOEditorRecurrence::readEvent(Event *event) mRecurrenceRange->setEndDate( r->endDate() ); } else mRecurrenceRange->setEndDate( event->dtStart().date() ); } mExceptions->setDates( event->exDates() ); } -void KOEditorRecurrence::writeEvent( Event *event ) +void KOEditorRecurrence::writeEvent( Incidence *event ) { Recurrence *r = event->recurrence(); // clear out any old settings; r->unsetRecurs(); if ( mEnabledCheck->isChecked() ) { int duration = mRecurrenceRange->duration(); diff --git a/korganizer/koeditorrecurrence.h b/korganizer/koeditorrecurrence.h index 2b59085..a15afcb 100644 --- a/korganizer/koeditorrecurrence.h +++ b/korganizer/koeditorrecurrence.h @@ -269,19 +269,19 @@ class KOEditorRecurrence : public QWidget KOEditorRecurrence ( QWidget *parent = 0, const char *name = 0 ); virtual ~KOEditorRecurrence(); enum { Daily, Weekly, Monthly, Yearly }; /** Set widgets to default values */ void setDefaults( QDateTime from, QDateTime to, bool allday ); /** Read event object and setup widgets accordingly */ - void readEvent( Event * ); + void readEvent( Incidence * ); /** Write event settings to event object */ - void writeEvent( Event * ); + void writeEvent( Incidence * ); /** Check if the input is valid. */ bool validateInput(); public slots: void setEnabled( bool ); void setDateTimes( QDateTime start, QDateTime end ); void setDateTimeStr( const QString & ); diff --git a/korganizer/kotodoeditor.cpp b/korganizer/kotodoeditor.cpp index 70dfbd1..069dda8 100644 --- a/korganizer/kotodoeditor.cpp +++ b/korganizer/kotodoeditor.cpp @@ -25,29 +25,31 @@ #include <qtooltip.h> #include <qframe.h> #include <qpixmap.h> #include <qlayout.h> #include <qhbox.h> #include <qdir.h> #include <qdatetime.h> #include <qapplication.h> +#include <qtabwidget.h> #include <kiconloader.h> #include <klocale.h> #include <kfiledialog.h> #include <kstandarddirs.h> #include <kmessagebox.h> #include <libkdepim/categoryselectdialog.h> #include <libkcal/calendarlocal.h> #include <libkcal/calendarresources.h> #include <libkcal/resourcecalendar.h> #include <libkcal/icalformat.h> #include <kresources/resourceselectdialog.h> +#include <libkdepim/kdateedit.h> #include "koprefs.h" #include "kolocationbox.h" #include "kotodoeditor.h" extern int globalFlagBlockAgenda; KOTodoEditor::KOTodoEditor( Calendar *calendar, QWidget *parent ) : @@ -63,17 +65,28 @@ KOTodoEditor::~KOTodoEditor() { emit dialogClose( mTodo ); } void KOTodoEditor::init() { setupGeneral(); setupAttendeesTab(); + setupRecurrence(); + connect(mGeneral,SIGNAL(datesChecked()),this ,SLOT(checkRecurrence())); } +void KOTodoEditor::setupRecurrence() +{ + QFrame *topFrame = addPage( i18n("Recurrence") ); + QBoxLayout *topLayout = new QVBoxLayout( topFrame ); + + mRecurrence = new KOEditorRecurrence( topFrame ); + topLayout->addWidget( mRecurrence ); +} + void KOTodoEditor::setCategories( QString s ) { mGeneral->setCategories(s); } void KOTodoEditor::setSecrecy( int sec ) { mGeneral->setSecrecy( sec ); } @@ -189,16 +202,17 @@ void KOTodoEditor::editTodo(Todo *todo, bool editDescription) readTodo(mTodo); if ( editDescription ) { showPage( 1 ); mGeneral->setFocusOn( 1 ); } else { showPage( 0 ); mGeneral->setFocusOn( 2 ); } + checkRecurrence(); } void KOTodoEditor::newTodo(QDateTime due,Todo *relatedTodo,bool allDay) { //init(); mTodo = 0; setDefaults(due,relatedTodo,allDay); @@ -282,18 +296,43 @@ void KOTodoEditor::setDefaults(QDateTime due,Todo *relatedEvent,bool allDay) mGeneral->mSummaryEdit->lineEdit()->setText(mRelatedTodo->summary()+": "); int len = mRelatedTodo->summary().length(); mGeneral->mSummaryEdit->lineEdit()->setFocus(); mGeneral->mSummaryEdit->lineEdit()->setCursorPosition ( len+2 ); mGeneral->mSummaryEdit->lineEdit()->setSelection ( 0, len+2 ); } else mGeneral->setFocusOn( 2 ); + tabWidget()->setTabEnabled ( mRecurrence->parentWidget(), false ); + mRecurrence->setDefaults(QDateTime::currentDateTime(),QDateTime::currentDateTime().addSecs( 3600 ),true); } +void KOTodoEditor::checkRecurrence() +{ + if ( mGeneral->mDueCheck->isChecked() && mGeneral->mStartCheck->isChecked()) { + tabWidget()->setTabEnabled ( mRecurrence->parentWidget(), true ); + if ( mTodo ) + mRecurrence->readEvent( mTodo ); + else { + bool time = mGeneral->mTimeButton->isChecked(); + QDateTime from,to; + if ( time ) { + to = QDateTime( mGeneral->mDueDateEdit->date(), mGeneral->mDueTimeEdit->getTime() ) ; + from = QDateTime( mGeneral->mStartDateEdit->date(),mGeneral->mStartTimeEdit->getTime( )) ; + } else { + to = QDateTime( mGeneral->mDueDateEdit->date(), QTime( 0,0,0) ) ; + from = QDateTime( mGeneral->mStartDateEdit->date(),QTime( 0,0,0) ) ; + } + mRecurrence->setDefaults(from,to,!time); + } + } else { + tabWidget()->setTabEnabled ( mRecurrence->parentWidget(), false ); + mRecurrence->setDefaults(QDateTime::currentDateTime(),QDateTime::currentDateTime().addSecs( 3600 ),true); + } +} void KOTodoEditor::readTodo(Todo *todo) { mGeneral->readTodo(todo); mDetails->readEvent(todo); mRelatedTodo = 0;//todo->relatedTo(); // categories // mCategoryDialog->setSelected(todo->categories()); @@ -304,16 +343,20 @@ void KOTodoEditor::writeTodo(Todo *event) { mGeneral->writeTodo(event); mDetails->writeEvent(event); // set related event, i.e. parent to-do in this case. if (mRelatedTodo) { event->setRelatedTo(mRelatedTodo); } + if ( mGeneral->mDueCheck->isChecked() && mGeneral->mStartCheck->isChecked()) { + mRecurrence->writeEvent(event); + } else + event->recurrence()->unsetRecurs(); } bool KOTodoEditor::validateInput() { if (!mGeneral->validateInput()) return false; if (!mDetails->validateInput()) return false; return true; } diff --git a/korganizer/kotodoeditor.h b/korganizer/kotodoeditor.h index 2657bd8..1b5e3b4 100644 --- a/korganizer/kotodoeditor.h +++ b/korganizer/kotodoeditor.h @@ -24,16 +24,17 @@ #ifndef _KOTODOEDITOR_H #define _KOTODOEDITOR_H #include <libkcal/calendar.h> #include "koeditorgeneraltodo.h" #include "koeditordetails.h" #include "koincidenceeditor.h" +#include "koeditorrecurrence.h" class QDateTime; /** This class provides a dialog for editing a Todo. */ class KOTodoEditor : public KOIncidenceEditor { @@ -77,26 +78,29 @@ class KOTodoEditor : public KOIncidenceEditor void todoChanged(Todo *); void todoAdded(Todo *); void todoToBeDeleted(Todo *); void todoDeleted(); protected slots: void loadDefaults(); void deleteTodo(); + void checkRecurrence(); void slotLoadTemplate(); void slotSaveTemplate(); void saveTemplate( const QString & ); protected: void setupGeneral(); int msgItemDelete(); + void setupRecurrence(); private: Todo *mTodo; Incidence *mRelatedTodo; KOEditorGeneralTodo *mGeneral; + KOEditorRecurrence *mRecurrence; }; #endif diff --git a/libkcal/icalformatimpl.cpp b/libkcal/icalformatimpl.cpp index bd13132..bb9cb29 100644 --- a/libkcal/icalformatimpl.cpp +++ b/libkcal/icalformatimpl.cpp @@ -395,17 +395,20 @@ void ICalFormatImpl::writeIncidence(icalcomponent *parent,Incidence *incidence) QPtrList<Alarm> alarms = incidence->alarms(); Alarm* alarm; for (alarm = alarms.first(); alarm; alarm = alarms.next()) { if (alarm->enabled()) { kdDebug(5800) << "Write alarm for " << incidence->summary() << endl; icalcomponent_add_component(parent,writeAlarm(alarm)); } } - + if( incidence->hasRecurrenceID() ) { + icalcomponent_add_property(parent, + icalproperty_new_recurrenceid( writeICalDateTime( incidence->recurrenceID()))); + } // duration // turned off as it always is set to PTS0 (and must not occur together with DTEND // if (incidence->hasDuration()) { // icaldurationtype duration; // duration = writeICalDuration(incidence->duration()); // icalcomponent_add_property(parent,icalproperty_new_duration(duration)); @@ -1199,16 +1202,21 @@ void ICalFormatImpl::readIncidence(icalcomponent *parent,Incidence *incidence) } break; case ICAL_LOCATION_PROPERTY: // location text = icalproperty_get_location(p); incidence->setLocation(QString::fromUtf8(text)); break; + case ICAL_RECURRENCEID_PROPERTY: + icaltime = icalproperty_get_recurrenceid(p); + incidence->setRecurrenceID( readICalDateTime(icaltime) ); + qDebug(" RecurrenceID %s",incidence->recurrenceID().toString().latin1() ); + break; #if 0 // status if ((vo = isAPropertyOf(vincidence, VCStatusProp)) != 0) { incidence->setStatus(s = fakeCString(vObjectUStringZValue(vo))); deleteStr(s); } else incidence->setStatus("NEEDS ACTION"); diff --git a/libkcal/incidence.cpp b/libkcal/incidence.cpp index f9e1e9e..dbc159c 100644 --- a/libkcal/incidence.cpp +++ b/libkcal/incidence.cpp @@ -34,16 +34,17 @@ Incidence::Incidence() : mRelatedTo(0), mSecrecy(SecrecyPublic), mPriority(3) { mRecurrence = new Recurrence(this); mCancelled = false; recreate(); mHasStartDate = true; mAlarms.setAutoDelete(true); mAttachments.setAutoDelete(true); + mHasRecurrenceID = false; } Incidence::Incidence( const Incidence &i ) : IncidenceBase( i ) { // TODO: reenable attributes currently commented out. mRevision = i.mRevision; mCreated = i.mCreated; mDescription = i.mDescription; @@ -66,32 +67,53 @@ Incidence::Incidence( const Incidence &i ) : IncidenceBase( i ) while( (a = it.current()) ) { Alarm *b = new Alarm( *a ); b->setParent( this ); mAlarms.append( b ); ++it; } mAlarms.setAutoDelete(true); - + mHasRecurrenceID = i.mHasRecurrenceID; + mRecurrenceID = i.mRecurrenceID; mRecurrence = new Recurrence( *(i.mRecurrence), this ); } Incidence::~Incidence() { Incidence *ev; QPtrList<Incidence> Relations = relations(); for (ev=Relations.first();ev;ev=Relations.next()) { if (ev->relatedTo() == this) ev->setRelatedTo(0); } if (relatedTo()) relatedTo()->removeRelation(this); delete mRecurrence; } +bool Incidence::hasRecurrenceID() const +{ + return mHasRecurrenceID; +} + +void Incidence::setHasRecurrenceID( bool b ) +{ + mHasRecurrenceID = b; +} + +void Incidence::setRecurrenceID(QDateTime d) +{ + mRecurrenceID = d; + mHasRecurrenceID = true; + updated(); +} +QDateTime Incidence::recurrenceID () const +{ + return mRecurrenceID; +} bool Incidence::cancelled() const { return mCancelled; } void Incidence::setCancelled( bool b ) { mCancelled = b; @@ -138,16 +160,26 @@ bool KCal::operator==( const Incidence& i1, const Incidence& i2 ) continue; } else { return false; } } #endif + if ( i1.hasRecurrenceID() == i2.hasRecurrenceID() ) { + if ( i1.hasRecurrenceID() ) { + if ( i1.recurrenceID() != i2.recurrenceID() ) + return false; + } + + } else { + return false; + } + if ( ! operator==( (const IncidenceBase&)i1, (const IncidenceBase&)i2 ) ) return false; if ( i1.hasStartDate() == i2.hasStartDate() ) { if ( i1.hasStartDate() ) { if ( i1.dtStart() != i2.dtStart() ) return false; } } else { @@ -165,16 +197,17 @@ bool KCal::operator==( const Incidence& i1, const Incidence& i2 ) // no need to compare mRelatedTo stringCompare( i1.relatedToUid(), i2.relatedToUid() ) && // i1.relations() == i2.relations() && i1.exDates() == i2.exDates() && i1.attachments() == i2.attachments() && i1.resources() == i2.resources() && i1.secrecy() == i2.secrecy() && i1.priority() == i2.priority() && + i1.cancelled() == i2.cancelled() && stringCompare( i1.location(), i2.location() ); } Incidence* Incidence::recreateCloneException( QDate d ) { Incidence* newInc = clone(); newInc->recreate(); if ( doesRecur() ) { diff --git a/libkcal/incidence.h b/libkcal/incidence.h index de2a381..38d2aaa 100644 --- a/libkcal/incidence.h +++ b/libkcal/incidence.h @@ -259,24 +259,33 @@ class Incidence : public IncidenceBase /** returns TRUE or FALSE depending on whether the todo has a start date */ bool hasStartDate() const; /** sets the event's hasStartDate value. */ void setHasStartDate(bool f); QDateTime getNextOccurence( const QDateTime& dt, bool* yes ) const; bool cancelled() const; void setCancelled( bool b ); + bool hasRecurrenceID() const; + void setHasRecurrenceID( bool b ); + + void setRecurrenceID(QDateTime); + QDateTime recurrenceID () const; + + protected: QPtrList<Alarm> mAlarms; QPtrList<Incidence> mRelations; private: int mRevision; bool mCancelled; // base components of jounal, event and todo + QDateTime mRecurrenceID; + bool mHasRecurrenceID; QDateTime mCreated; QString mDescription; QString mSummary; QStringList mCategories; Incidence *mRelatedTo; QString mRelatedToUid; DateList mExDates; QPtrList<Attachment> mAttachments; diff --git a/microkde/kdialogbase.h b/microkde/kdialogbase.h index 7b44bfb..a2fc2dc 100644 --- a/microkde/kdialogbase.h +++ b/microkde/kdialogbase.h @@ -112,19 +112,19 @@ class KDialogBase : public KDialog virtual void slotApply(); virtual void slotCancel(); virtual void slotClose(); virtual void slotUser1(); virtual void slotUser2(); protected: QPushButton *findButton( ButtonCode ); + QTabWidget *tabWidget(); private: - QTabWidget *tabWidget(); void init( const QString &caption, int buttonMask, const QString &user1=QString::null, const QString &user2=QString::null ); void initLayout(); QWidget *mMainWidget; QTabWidget *mTabWidget; QFrame *mPlainPage; QBoxLayout *mTopLayout; |