--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/javaextensions/pim/framework/src.s60/cpimeventmatcher.cpp Tue Apr 27 16:30:29 2010 +0300
@@ -0,0 +1,335 @@
+/*
+* Copyright (c) 2008 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description: An event occurrence matcher.
+ *
+*/
+
+
+// INCLUDE FILES
+#include "cpimeventmatcher.h"
+#include "cpimeventitem.h"
+#include "cpimrepeatrule.h"
+#include "pimpanics.h"
+#include "logger.h"
+
+CPIMEventMatcher::CPIMEventMatcher(const TPIMEventSearchType aSearchType,
+ const TPIMDate& aStartDate, const TPIMDate& aEndDate,
+ TBool aInitialEventOnly) :
+ iSearchType(aSearchType), iStartDate(aStartDate), iEndDate(aEndDate),
+ iInitialEventOnly(aInitialEventOnly)
+{
+ JELOG2(EPim);
+}
+
+CPIMEventMatcher::~CPIMEventMatcher()
+{
+ JELOG2(EPim);
+}
+
+TBool CPIMEventMatcher::SaneOptions()
+{
+ JELOG2(EPim);
+ if (iSearchType != EPIMEventSearchStarting && iSearchType
+ != EPIMEventSearchEnding && iSearchType != EPIMEventSearchOccurring)
+ {
+ return EFalse;
+ }
+
+ if (iStartDate > iEndDate)
+ {
+ return EFalse;
+ }
+
+ return ETrue;
+}
+
+TBool CPIMEventMatcher::MatchL(const CPIMEventItem& aTestedEvent,
+ TPIMDate& aOccurrenceStart) const
+{
+ JELOG2(EPim);
+ TBool eventMatches = EFalse;
+
+ switch (iSearchType)
+ {
+ case EPIMEventSearchStarting:
+ {
+ eventMatches = MatchStartingL(aTestedEvent, aOccurrenceStart);
+ break;
+ }
+ case EPIMEventSearchEnding:
+ {
+ eventMatches = MatchEndingL(aTestedEvent, aOccurrenceStart);
+ break;
+ }
+ case EPIMEventSearchOccurring:
+ {
+ eventMatches = MatchOccurringL(aTestedEvent, aOccurrenceStart);
+ break;
+ }
+ default:
+ {
+ // Error
+ User::Panic(KPIMPanicCategory, EPIMPanicEventItemsSearchType);
+ break;
+ }
+ }
+
+ return eventMatches;
+}
+
+TBool CPIMEventMatcher::MatchStartingL(const CPIMEventItem& aTestedEvent,
+ TPIMDate& aOccurrenceStart) const
+{
+ JELOG2(EPim);
+ // If the Event, regardless of repeating, starts between the given
+ // range (inclusive), it matches. If we didn't get direct match,
+ // we'll check if any of the repeating occurrences of the item
+ // starts between the given range (if repeating occurrences are
+ // taken into account and the Event is repeating).
+
+ TPIMDate eventStart(0); // For matching and occurrence start
+ TPIMDate dummyEnd(0); // Not used
+ TBool match = EFalse;
+
+ if (ExtractStartAndEndDateL(aTestedEvent, eventStart, dummyEnd) == KErrNone)
+ {
+ if (eventStart >= iStartDate && eventStart <= iEndDate)
+ {
+ aOccurrenceStart = eventStart;
+ match = ETrue;
+ }
+ else if (!iInitialEventOnly && aTestedEvent.IsRepeating())
+ {
+ match = MatchStartingRepeatingL(eventStart, aTestedEvent,
+ aOccurrenceStart);
+ }
+ }
+
+ return match;
+}
+
+TBool CPIMEventMatcher::MatchStartingRepeatingL(const TPIMDate& aEventStart,
+ const CPIMEventItem& aTestedEvent, TPIMDate& aOccurrenceStart) const
+{
+ JELOG2(EPim);
+ TBool match = EFalse;
+
+ const CPIMRepeatRule* repeatRule =
+ static_cast<const CPIMRepeatRule*>(aTestedEvent.GetRepeat());
+
+ CArrayFixFlat<TPIMDate>* occurrences = repeatRule->DatesL(aEventStart,
+ iStartDate, iEndDate);
+
+ const TInt numOccs = occurrences->Count();
+ for (TInt occIndex = 0; occIndex < numOccs; occIndex++)
+ {
+ // Occurrence start date
+ TPIMDate occ = occurrences->At(occIndex);
+
+ if ((occ >= iStartDate) && (occ <= iEndDate))
+ {
+ aOccurrenceStart = occ;
+ match = ETrue;
+ break;
+ }
+ }
+
+ delete occurrences;
+ return match;
+}
+
+TBool CPIMEventMatcher::MatchEndingL(const CPIMEventItem& aTestedEvent,
+ TPIMDate& aOccurrenceStart) const
+{
+ JELOG2(EPim);
+ // If the Event, regardless of repeating, ends between the given
+ // range (inclusive), it matches. If we didn't get direct match,
+ // we'll check if any of the repeating occurrences of the item
+ // ends between the given range (if repeating occurrences are
+ // taken into account and the Event is repeating).
+
+ TPIMDate eventStart(0); // For occurrence start
+ TPIMDate eventEnd(0); // For matching
+ TBool match = EFalse;
+
+ if (ExtractStartAndEndDateL(aTestedEvent, eventStart, eventEnd) == KErrNone)
+ {
+ if (eventEnd >= iStartDate && eventEnd <= iEndDate)
+ {
+ aOccurrenceStart = eventStart;
+ match = ETrue;
+ }
+ else if (!iInitialEventOnly && aTestedEvent.IsRepeating())
+ {
+ match = MatchEndingRepeatingL(eventEnd, aTestedEvent,
+ aOccurrenceStart);
+ }
+ }
+
+ return match;
+}
+
+TBool CPIMEventMatcher::MatchEndingRepeatingL(const TPIMDate& aEventEnd,
+ const CPIMEventItem& aTestedEvent, TPIMDate& aOccurrenceStart) const
+{
+ JELOG2(EPim);
+ TBool match = EFalse;
+
+ // We need the start date for getting the repeating
+ // occurrences of the event. Skip if not present.
+ TPIMDate eventStart(0);
+ if (aTestedEvent.CountValuesL(EPIMEventStart) != 0)
+ {
+ // And again we just use the first start value
+ eventStart = aTestedEvent.GetDateL(EPIMEventStart, 0);
+
+ const CPIMRepeatRule* repeatRule =
+ static_cast<const CPIMRepeatRule*>(aTestedEvent.GetRepeat());
+
+ TTimeIntervalMicroSeconds eventLen = aEventEnd.MicroSecondsFrom(
+ eventStart);
+
+ // We expand the subset of retrieved occurrences a bit
+ // from the start so that the first possible end date is
+ // included.
+ CArrayFixFlat<TPIMDate>* occurrences = repeatRule->DatesL(eventStart,
+ iStartDate - eventLen, iEndDate);
+
+ const TInt numOccs = occurrences->Count();
+ for (TInt occIndex = 0; occIndex < numOccs; occIndex++)
+ {
+ // Occurrence start date
+ TPIMDate occ = occurrences->At(occIndex);
+
+ if (((occ + eventLen) >= iStartDate) && ((occ + eventLen)
+ <= iEndDate))
+ {
+ aOccurrenceStart = occ;
+ match = ETrue;
+ break;
+ }
+ }
+
+ delete occurrences;
+ }
+
+ return match;
+}
+
+TBool CPIMEventMatcher::MatchOccurringL(const CPIMEventItem& aTestedEvent,
+ TPIMDate& aOccurrenceStart) const
+{
+ JELOG2(EPim);
+ // If the Event, regardless of repeating, either starts or ends
+ // between the given range (inclusive) or the start date is before
+ // range start and the end date is after range end, it matches.
+ // If we didn't get direct match, we'll check the same for any
+ // possible repeating occurrences of the item.
+
+ TPIMDate eventStart(0); // For matching and occurrence start
+ TPIMDate eventEnd(0); // For matching
+ TBool match = EFalse;
+
+ if (ExtractStartAndEndDateL(aTestedEvent, eventStart, eventEnd) == KErrNone)
+ {
+ if (eventStart <= iEndDate && eventEnd >= iStartDate)
+ {
+ aOccurrenceStart = eventStart;
+ match = ETrue;
+ }
+ else if (!iInitialEventOnly && aTestedEvent.IsRepeating())
+ {
+ match = MatchOccurringRepeatingL(eventStart, eventEnd,
+ aTestedEvent, aOccurrenceStart);
+ }
+ }
+
+ return match;
+}
+
+TBool CPIMEventMatcher::MatchOccurringRepeatingL(const TPIMDate& aEventStart,
+ const TPIMDate& aEventEnd, const CPIMEventItem& aTestedEvent,
+ TPIMDate& aOccurrenceStart) const
+{
+ JELOG2(EPim);
+ TBool match = EFalse;
+
+ const CPIMRepeatRule* repeatRule =
+ static_cast<const CPIMRepeatRule*>(aTestedEvent.GetRepeat());
+
+ TTimeIntervalMicroSeconds eventLen =
+ aEventEnd.MicroSecondsFrom(aEventStart);
+
+ // We expand the subset of retrieved occurrences a bit from the start
+ // so that the first possible end date is included and a matching
+ // event may start before the given range.
+ CArrayFixFlat<TPIMDate>* occurrences = repeatRule->DatesL(aEventStart,
+ iStartDate - eventLen, iEndDate);
+
+ const TInt numOccs = occurrences->Count();
+ for (TInt occIndex = 0; occIndex < numOccs; occIndex++)
+ {
+ // Occurrence start date
+ TPIMDate occ = occurrences->At(occIndex);
+
+ if (occ <= iEndDate && occ + eventLen >= iStartDate)
+ {
+ aOccurrenceStart = occ;
+ match = ETrue;
+ break;
+ }
+ }
+
+ delete occurrences;
+ return match;
+}
+
+TInt CPIMEventMatcher::ExtractStartAndEndDateL(const CPIMEventItem& aEvent,
+ TPIMDate& aEventStart, TPIMDate& aEventEnd) const
+{
+ JELOG2(EPim);
+ TInt retVal = KErrNone;
+
+ if (aEvent.CountValuesL(EPIMEventStart) != 0)
+ {
+ // Start date is present.
+ aEventStart = aEvent.GetDateL(EPIMEventStart, 0);
+ if (aEvent.CountValuesL(EPIMEventEnd) != 0)
+ {
+ // End date is also present.
+ aEventEnd = aEvent.GetDateL(EPIMEventEnd, 0);
+ }
+ else
+ {
+ // End date is not present - use start date also as end date.
+ aEventEnd = aEventStart;
+ }
+ }
+ else if (aEvent.CountValuesL(EPIMEventEnd) != 0)
+ {
+ // Start date is not present, but end date is present.
+ // Use end date also as start date.
+ aEventEnd = aEvent.GetDateL(EPIMEventEnd, 0);
+ aEventStart = aEventEnd;
+ }
+ else
+ {
+ // Neither start or end date is present.
+ retVal = KErrNotFound;
+ }
+
+ return retVal;
+}
+
+// End of File