qtmobility/plugins/contacts/symbian/src/filtering/cntsymbianfilterdbms.cpp
changeset 4 90517678cc4f
parent 1 2b40d63a9c3d
child 8 71781823f776
--- a/qtmobility/plugins/contacts/symbian/src/filtering/cntsymbianfilterdbms.cpp	Fri Apr 16 15:51:22 2010 +0300
+++ b/qtmobility/plugins/contacts/symbian/src/filtering/cntsymbianfilterdbms.cpp	Mon May 03 13:18:40 2010 +0300
@@ -90,6 +90,13 @@
  * are sorted only if the sort order is supported by contacts database. See
  * CntSymbianSorterDbms::filterSupportLevel for the list of supported sort
  * orders.
+ * 
+ * Using detail filter with match flag MatchPhoneNumber is implemented by the
+ * contact model "phone number match" that filters by comparing the search
+ * string characters (digits) starting from the rightmost digit. The detail
+ * filter value must be at least 7 digits, otherwise an error code
+ * NotSupportedError is given. The actual digit count that is used is 7 to 15
+ * digits, depending on the configuration of the device.
  *
  * \a filter The QContactFilter to be used.
  * \a sortOrders The sort orders to be used. If the sort orders are not
@@ -101,7 +108,7 @@
     const QContactFilter &filter,
     const QList<QContactSortOrder> &sortOrders,
     bool &filterSupportedFlag,
-    QContactManager::Error &error)
+    QContactManager::Error* error)
 {
     QList<QContactLocalId> result;
 
@@ -134,7 +141,7 @@
             && (static_cast<const QContactDetailFilter &>(filter)).value().type() == QVariant::StringList) {
         QStringList values = (static_cast<const QContactDetailFilter &>(filter)).value().toStringList();
         QContactIntersectionFilter intersectionFilter;
-        foreach(QString value, values) {
+        foreach(const QString& value, values) {
             QContactDetailFilter detailFilter = filter;
             detailFilter.setValue(value);
             intersectionFilter.append(detailFilter);
@@ -142,15 +149,20 @@
         // The resulting filter is handled with a recursive function call
         result = contacts(intersectionFilter, sortOrders, filterSupportedFlag, error);
     } else {
-        if (filterSupportLevel(filter) == Supported) {
+        FilterSupport filterSupport = filterSupportLevel(filter);
+        if (filterSupport == Supported) {
             filterSupportedFlag = true;
             // Filter supported, use as the result directly
             result = filterContacts(filter, error);
-        } else if (filterSupportLevel(filter) == SupportedPreFilterOnly) {
+        } else if (filterSupport == SupportedPreFilterOnly) {
             // Filter only does pre-filtering, the caller is responsible of
             // removing possible false positives after filtering
             filterSupportedFlag = false;
             result = filterContacts(filter, error);
+        } else if (filterSupport == IllegalFilter) {
+            // Don't do filtering; fail with an error
+            filterSupportedFlag = false;
+            *error = QContactManager::NotSupportedError;
         } else {
             // Don't do filtering here, return all contact ids and tell the
             // caller to do slow filtering
@@ -225,13 +237,29 @@
         if (defName == QContactPhoneNumber::DefinitionName) {
             
             if (matchFlags == QContactFilter::MatchPhoneNumber) {
-                return Supported;
-            }
-            
-            if (matchFlags == QContactFilter::MatchExactly ||
-                matchFlags == QContactFilter::MatchEndsWith ||
-                matchFlags == QContactFilter::MatchFixedString) {
-                return SupportedPreFilterOnly;
+                if (detailFilter.value().canConvert(QVariant::String)) {
+                    if (detailFilter.value().toString().length() >= 7) {
+                        return Supported;
+                    } else {
+                        // It is a feature of Symbian contact model that phone
+                        // number match requires at least 7 digits. In case of
+                        // phone number match it is best to give an error as a
+                        // result because the phone number match logic would
+                        // not be much of use with less than 7 digit matching.
+                        // It would give false positives too often.
+                        return IllegalFilter;
+                    }
+                }
+            } else if (matchFlags == QContactFilter::MatchExactly
+                || matchFlags == QContactFilter::MatchEndsWith
+                || matchFlags == QContactFilter::MatchFixedString) {
+                if (detailFilter.value().canConvert(QVariant::String)) {
+                    // It is a feature of Symbian contact model that phone
+                    // number match requires at least 7 digits
+                    if (detailFilter.value().toString().length() >= 7) {
+                        return SupportedPreFilterOnly;
+                    }
+                }
             }
         // Names
         } else if (defName == QContactName::DefinitionName
@@ -276,16 +304,16 @@
 
 QList<QContactLocalId> CntSymbianFilter::filterContacts(
     const QContactFilter& filter,
-    QContactManager::Error& error)
+    QContactManager::Error* error)
 {
     QList<QContactLocalId> matches;
     CContactIdArray* idArray(0);
 
-    if (filter.type() == QContactFilter::InvalidFilter ){
+    if (filter.type() == QContactFilter::InvalidFilter) {
         TTime epoch(0);
         idArray = m_contactDatabase.ContactsChangedSinceL(epoch); // return all contacts
     } else if(filterSupportLevel(filter) == NotSupported) {
-        error = QContactManager::NotSupportedError;
+        *error = QContactManager::NotSupportedError;
     } else if (filter.type() == QContactFilter::ContactDetailFilter) {
         const QContactDetailFilter &detailFilter = static_cast<const QContactDetailFilter &>(filter);
 
@@ -327,7 +355,7 @@
                     && detailFilter.matchFlags() == QContactFilter::MatchStartsWith) {
 
                     // Remove false positives
-                    for(TInt i(0); i < idArray->Count(); i++) {
+                    for(TInt i(0); i < idArray->Count(); ++i) {
                         CContactItem* contactItem = m_contactDatabase.ReadContactLC((*idArray)[i]);
                         const CContactItemFieldSet& fieldSet(contactItem->CardFields());
                         if(isFalsePositive(fieldSet, KUidContactFieldGivenName, namePtr)
@@ -345,7 +373,7 @@
         }
     }
 
-    if(idArray && (error == QContactManager::NoError)) {
+    if(idArray && (*error == QContactManager::NoError)) {
         // copy the matching contact ids
         for(int i(0); i < idArray->Count(); i++) {
             matches.append(QContactLocalId((*idArray)[i]));
@@ -377,7 +405,7 @@
         // Check if this is the first word beginning with search string
         if(index == 0)
             value = false;
-        // Check if this is in the beginning of a word (the preceeding
+        // Check if this is in the beginning of a word (the preceding
         // character is a space)
         else if(index > 0 && TChar(text[index-1]) == TChar(0x20))
             value = false;
@@ -405,11 +433,11 @@
     if(detailFilter.detailDefinitionName() == QContactName::DefinitionName) {
         if(detailFilter.detailFieldName() == QContactName::FieldPrefix) {
             tempFieldDef->AppendL(KUidContactFieldPrefixName);
-        } else if(detailFilter.detailFieldName() == QContactName::FieldFirst) {
+        } else if(detailFilter.detailFieldName() == QContactName::FieldFirstName) {
             tempFieldDef->AppendL(KUidContactFieldGivenName);
-        } else if(detailFilter.detailFieldName() == QContactName::FieldMiddle) {
+        } else if(detailFilter.detailFieldName() == QContactName::FieldMiddleName) {
             tempFieldDef->AppendL(KUidContactFieldAdditionalName);
-        } else if(detailFilter.detailFieldName() == QContactName::FieldLast) {
+        } else if(detailFilter.detailFieldName() == QContactName::FieldLastName) {
             tempFieldDef->AppendL(KUidContactFieldFamilyName);
         } else if(detailFilter.detailFieldName() == QContactName::FieldSuffix) {
             tempFieldDef->AppendL(KUidContactFieldSuffixName);