phonebookui/pbkcommonui/src/cntcollectionlistmodel.cpp
changeset 71 7cc7d74059f9
parent 65 ae724a111993
equal deleted inserted replaced
65:ae724a111993 71:7cc7d74059f9
    31 
    31 
    32 #include <qtcontacts.h>
    32 #include <qtcontacts.h>
    33 #include <hbglobal.h>
    33 #include <hbglobal.h>
    34 #include <hbicon.h>
    34 #include <hbicon.h>
    35 
    35 
       
    36 #include <QtAlgorithms>
       
    37 
       
    38 namespace
       
    39 {
       
    40     bool caseInsensitiveLessThan(const QContact &c1, const QContact &c2)
       
    41     {
       
    42         return c1.displayLabel().toLower() < c2.displayLabel().toLower();
       
    43     }
       
    44 }
       
    45 
    36 /*!
    46 /*!
    37     Constructor
    47     Constructor
    38 */
    48 */
    39 CntCollectionListModel::CntCollectionListModel(CntAbstractEngine* aEngine, QObject *parent)
    49 CntCollectionListModel::CntCollectionListModel(CntAbstractEngine* aEngine, QObject *parent)
    40     : QAbstractListModel(parent)
    50     : QAbstractListModel(parent)
    52     QString unnamed = hbTrId("txt_phob_dblist_unnamed");
    62     QString unnamed = hbTrId("txt_phob_dblist_unnamed");
    53     QString noFavs = hbTrId("txt_phob_dblist_favorites_val_no_favorites_selecte");
    63     QString noFavs = hbTrId("txt_phob_dblist_favorites_val_no_favorites_selecte");
    54     QString noMembers = hbTrId("txt_phob_dblist_val_no_members_selected");
    64     QString noMembers = hbTrId("txt_phob_dblist_val_no_members_selected");
    55     mThread = new CntCollectionListModelWorker(unnamed, noFavs, noMembers, order);
    65     mThread = new CntCollectionListModelWorker(unnamed, noFavs, noMembers, order);
    56     
    66     
    57     connect(mThread, SIGNAL(fetchDone(int, const QString&, int)), this, SLOT(informationUpdated(int, const QString&, int)));
    67     connect(mThread, SIGNAL(fetchDone(int, const QString&, const QList<int>&)), this, 
       
    68             SLOT(informationUpdated(int, const QString&, const QList<int>&)));
    58     connect(d->mThumbnailManager, SIGNAL(thumbnailReady(QPixmap, void *, int, int)),
    69     connect(d->mThumbnailManager, SIGNAL(thumbnailReady(QPixmap, void *, int, int)),
    59              this, SLOT(onIconReady(QPixmap, void *, int, int)));
    70              this, SLOT(onIconReady(QPixmap, void *, int, int)));
    60     
    71     
    61     doConstruct();
    72     doConstruct();
    62     
    73     
    92     \param role the requested role
   103     \param role the requested role
    93     \return QVariant with requested data
   104     \return QVariant with requested data
    94 */
   105 */
    95 QVariant CntCollectionListModel::data(const QModelIndex& index, int role) const
   106 QVariant CntCollectionListModel::data(const QModelIndex& index, int role) const
    96 {
   107 {
       
   108     CNT_ENTRY_ARGS(index << role)
       
   109     
    97     int row = index.row();
   110     int row = index.row();
    98     
   111     
    99     if ( !validateRowIndex(row) )
   112     if ( !validateRowIndex(row) )
   100         return QVariant();
   113         return QVariant();
   101     
   114     
   188 /*!
   201 /*!
   189     Remove given group from the model. Ignore plugin groups.
   202     Remove given group from the model. Ignore plugin groups.
   190 
   203 
   191     \param localId QContactLocalId of the group that should be removed
   204     \param localId QContactLocalId of the group that should be removed
   192 */
   205 */
   193 void CntCollectionListModel::removeGroup(int localId)
   206 bool CntCollectionListModel::removeGroup(int localId)
   194 {
   207 {
   195     CNT_ENTRY
   208     CNT_ENTRY_ARGS(localId)
       
   209     
       
   210     bool groupRemoved = false;
   196     
   211     
   197     for (int i = 0;i < rowCount();i++)
   212     for (int i = 0;i < rowCount();i++)
   198     {
   213     {
   199         if (!d->mList.at(i)->isPlugin && d->mList.at(i)->id == localId)
   214         if (!d->mList.at(i)->isPlugin && d->mList.at(i)->id == localId)
   200         {
   215         {
   201             removeRow(i);
   216             removeRow(i);
       
   217             groupRemoved = true;
   202             break;
   218             break;
   203         }
   219         }
   204     }
   220     }
   205     
   221     
   206     CNT_EXIT
   222     CNT_EXIT_ARGS(groupRemoved)
       
   223     
       
   224     return groupRemoved;
   207 }
   225 }
   208 
   226 
   209 /*!
   227 /*!
   210     Add a new group to the model. This also takes care of putting it in the
   228     Add a new group to the model. This also takes care of putting it in the
   211     correct row.
   229     correct row.
   212 
   230 
   213     \param localId QContactLocalId of the group that should be added
   231     \param localId QContactLocalId of the group that should be added
   214 */
   232 */
   215 void CntCollectionListModel::addGroup(int localId)
   233 void CntCollectionListModel::addGroup(int localId)
   216 {
   234 {
   217     CNT_ENTRY
   235     CNT_ENTRY_ARGS(localId)
   218     
   236     
   219     QContactDetailFilter groupFilter;
   237     QContactDetailFilter groupFilter;
   220     groupFilter.setDetailDefinitionName(QContactType::DefinitionName, QContactType::FieldType);
   238     groupFilter.setDetailDefinitionName(QContactType::DefinitionName, QContactType::FieldType);
   221     groupFilter.setValue(QString(QLatin1String(QContactType::TypeGroup)));
   239     groupFilter.setValue(QString(QLatin1String(QContactType::TypeGroup)));
   222 
   240 
   310     \param row the row of the activated plugin item
   328     \param row the row of the activated plugin item
   311     \return view parameters used for view switching
   329     \return view parameters used for view switching
   312 */
   330 */
   313 CntViewParameters CntCollectionListModel::extensionGroupActivated(int row)
   331 CntViewParameters CntCollectionListModel::extensionGroupActivated(int row)
   314 {
   332 {
       
   333     CNT_ENTRY_ARGS(row)
       
   334 
   315     CntViewParameters params;
   335     CntViewParameters params;
   316     for(int i = 0;i < d->mExtensions.value(row)->groupCount();i++)
   336     for(int i = 0;i < d->mExtensions.value(row)->groupCount();i++)
   317     {
   337     {
   318         CntUiExtensionGroup& group = d->mExtensions.value(row)->groupAt(i);
   338         CntUiExtensionGroup& group = d->mExtensions.value(row)->groupAt(i);
   319         if (group.serviceId() == d->mList.at(row)->id)
   339         if (group.serviceId() == d->mList.at(row)->id)
   320         {
   340         {
   321             group.activated(params);
   341             group.activated(params);
   322             break;
   342             break;
   323         }
   343         }
   324     }
   344     }
       
   345     
       
   346     CNT_EXIT_ARGS(params)
       
   347     
   325     return params;
   348     return params;
   326 }
   349 }
   327 
   350 
   328 /*!
   351 /*!
   329     Called when a list item from a plugin is long pressed. Callback is done asynch, as HbMenu usage
   352     Called when a list item from a plugin is long pressed. Callback is done asynch, as HbMenu usage
   333     \param coords the coordinates of the long tap gesture
   356     \param coords the coordinates of the long tap gesture
   334     \param interface callback interface for asynch handling
   357     \param interface callback interface for asynch handling
   335 */
   358 */
   336 void CntCollectionListModel::extensionGroupLongPressed(int row, const QPointF& coords, CntExtensionGroupCallback* interface)
   359 void CntCollectionListModel::extensionGroupLongPressed(int row, const QPointF& coords, CntExtensionGroupCallback* interface)
   337 {
   360 {
   338     CNT_ENTRY
   361     CNT_ENTRY_ARGS(row << coords << interface)
   339     
   362     
   340     for(int i = 0;i < d->mExtensions.value(row)->groupCount();i++)
   363     for(int i = 0;i < d->mExtensions.value(row)->groupCount();i++)
   341     {
   364     {
   342         CntUiExtensionGroup& group = d->mExtensions.value(row)->groupAt(i);
   365         CntUiExtensionGroup& group = d->mExtensions.value(row)->groupAt(i);
   343         if (group.serviceId() == d->mList.at(row)->id)
   366         if (group.serviceId() == d->mList.at(row)->id)
   356     \param localId the id of the group
   379     \param localId the id of the group
   357     \return QModelIndex of the group
   380     \return QModelIndex of the group
   358 */
   381 */
   359 QModelIndex CntCollectionListModel::indexOfGroup(int localId)
   382 QModelIndex CntCollectionListModel::indexOfGroup(int localId)
   360 {
   383 {
       
   384     CNT_ENTRY_ARGS(localId)
       
   385             
       
   386     QModelIndex groupIndex;
       
   387 
   361     for (int i = 0;i < d->mList.count();i++)
   388     for (int i = 0;i < d->mList.count();i++)
   362     {
   389     {
   363         if (d->mList.at(i)->id == localId && !d->mList.at(i)->isPlugin)
   390         if (d->mList.at(i)->id == localId && !d->mList.at(i)->isPlugin)
   364         {
   391         {
   365             return index(i);
   392             groupIndex = index(i);
   366         }
   393             break;
   367     }
   394         }
   368     
   395     }
   369     return QModelIndex();
   396     
       
   397     CNT_EXIT_ARGS(groupIndex)
       
   398     
       
   399     return groupIndex;
   370 }
   400 }
   371 
   401 
   372 /*!
   402 /*!
   373     Initialize different groups.
   403     Initialize different groups.
   374 */
   404 */
   377     CNT_ENTRY
   407     CNT_ENTRY
   378     
   408     
   379     initializeStaticGroups();
   409     initializeStaticGroups();
   380     initializeExtensions();
   410     initializeExtensions();
   381     initializeUserGroups();
   411     initializeUserGroups();
       
   412     
       
   413     connect(d->mContactManager, SIGNAL(contactsAdded(const QList<QContactLocalId>&)), this, SLOT(handleAdded(const QList<QContactLocalId>&)));
       
   414     connect(d->mContactManager, SIGNAL(contactsChanged(const QList<QContactLocalId>&)), this, SLOT(handleChanged(const QList<QContactLocalId>&)));
       
   415     connect(d->mContactManager, SIGNAL(contactsRemoved(const QList<QContactLocalId>&)), this, SLOT(handleRemoved(const QList<QContactLocalId>&)));
       
   416     connect(d->mContactManager, SIGNAL(relationshipsAdded(const QList<QContactLocalId>&)), this, SLOT(handleAddedRelationship(const QList<QContactLocalId>&)));
       
   417     connect(d->mContactManager, SIGNAL(relationshipsRemoved(const QList<QContactLocalId>&)), this, SLOT(handleRemovedRelationship(const QList<QContactLocalId>&)));
       
   418 
   382     
   419     
   383     CNT_EXIT
   420     CNT_EXIT
   384 }
   421 }
   385 
   422 
   386 /*!
   423 /*!
   524     \param item the collection item from where data is read
   561     \param item the collection item from where data is read
   525     \return QVariant containing the requested data
   562     \return QVariant containing the requested data
   526 */
   563 */
   527 QVariant CntCollectionListModel::displayRoleData(const CntCollectionItem& item) const
   564 QVariant CntCollectionListModel::displayRoleData(const CntCollectionItem& item) const
   528 {
   565 {
       
   566     CNT_ENTRY
       
   567     
   529     QStringList list;
   568     QStringList list;
   530 
   569 
   531     list << item.groupName << item.secondLineText;
   570     list << item.groupName << item.secondLineText;
   532     
   571     
   533     if (item.memberCount > 0)
   572     if (item.memberCount > 0)
   536     }
   575     }
   537     else if (item.memberCount < 0)
   576     else if (item.memberCount < 0)
   538     {
   577     {
   539         list << " ";
   578         list << " ";
   540     }
   579     }
       
   580     
       
   581     CNT_EXIT
   541     
   582     
   542     return QVariant(list);
   583     return QVariant(list);
   543 }
   584 }
   544 
   585 
   545 /*!
   586 /*!
   548     \param item the collection item from where data is read
   589     \param item the collection item from where data is read
   549     \return QVariant containing the requested data
   590     \return QVariant containing the requested data
   550 */
   591 */
   551 QVariant CntCollectionListModel::decorationRoleData(const CntCollectionItem& item) const
   592 QVariant CntCollectionListModel::decorationRoleData(const CntCollectionItem& item) const
   552 {
   593 {
       
   594     CNT_ENTRY
       
   595     
   553     QList<QVariant> icons;
   596     QList<QVariant> icons;
   554     icons << item.icon;
   597     icons << item.icon;
   555     
   598     
   556     if (!item.secondaryIcon.isNull())
   599     if (!item.secondaryIcon.isNull())
   557     {
   600     {
   558         icons << item.secondaryIcon;
   601         icons << item.secondaryIcon;
   559     }
   602     }
       
   603     
       
   604     CNT_EXIT
   560     
   605     
   561     return QVariant(icons);
   606     return QVariant(icons);
   562 }
   607 }
   563 
   608 
   564 /*!
   609 /*!
   578 
   623 
   579     \param row the row receiving the updated information
   624     \param row the row receiving the updated information
   580     \param secondRowText text to be shown in the second row
   625     \param secondRowText text to be shown in the second row
   581     \param memberCount the amount of members the group has (shown in text-3 in HbListViewItem)
   626     \param memberCount the amount of members the group has (shown in text-3 in HbListViewItem)
   582 */
   627 */
   583 void CntCollectionListModel::informationUpdated(int id, const QString& secondRowText, int memberCount)
   628 void CntCollectionListModel::informationUpdated(int id, const QString& secondRowText, const QList<int>& members)
   584 {
   629 {
   585     CNT_ENTRY
   630     CNT_ENTRY_ARGS(id << secondRowText << members)
   586     
   631     
   587     for (int i = 0;i < d->mList.count();i++)
   632     for (int i = 0;i < d->mList.count();i++)
   588     {
   633     {
   589         if (d->mList.at(i)->id == id && !d->mList.at(i)->isPlugin)
   634         if (d->mList.at(i)->id == id && !d->mList.at(i)->isPlugin)
   590         {
   635         {
   591             CollectionItemPointer item = d->mList.at(i);
   636             CollectionItemPointer item = d->mList.at(i);
   592             
   637             
   593             item->secondLineText = secondRowText;
   638             item->secondLineText = secondRowText;
   594             item->memberCount = memberCount;
   639             item->memberCount = members.count();
       
   640             item->members = members;
   595             
   641             
   596             int idx = d->mList.indexOf(item);
   642             int idx = d->mList.indexOf(item);
   597             emit dataChanged(index(idx, 0), index(idx, 0));
   643             emit dataChanged(index(idx, 0), index(idx, 0));
   598             
   644             
   599             break;
   645             break;
   612     \param id the id of the request
   658     \param id the id of the request
   613     \param error 0 if no error happened
   659     \param error 0 if no error happened
   614 */
   660 */
   615 void CntCollectionListModel::onIconReady(const QPixmap& pixmap, void *data, int id, int error)
   661 void CntCollectionListModel::onIconReady(const QPixmap& pixmap, void *data, int id, int error)
   616 {
   662 {
   617     CNT_ENTRY
   663     CNT_ENTRY_ARGS(pixmap << data << id << error)
   618     
   664     
   619     Q_UNUSED(data);
   665     Q_UNUSED(data);
   620     
   666     
   621     if (error == 0)
   667     if (error == 0)
   622     {
   668     {
   647     also care of updating the mapping between row and CntUiGroupSuppliers
   693     also care of updating the mapping between row and CntUiGroupSuppliers
   648     in case there was already some synchronously loaded extension groups.
   694     in case there was already some synchronously loaded extension groups.
   649 */
   695 */
   650 void CntCollectionListModel::extensionGroupsReady()
   696 void CntCollectionListModel::extensionGroupsReady()
   651 {
   697 {
       
   698     CNT_ENTRY
       
   699     
   652     CntUiGroupSupplier* groupSupplier = static_cast<CntUiGroupSupplier*>(sender());
   700     CntUiGroupSupplier* groupSupplier = static_cast<CntUiGroupSupplier*>(sender());
   653     
   701     
   654     int addedCount = groupSupplier->groupCount();
   702     int addedCount = groupSupplier->groupCount();
   655     
   703     
   656     if (addedCount > 0)
   704     if (addedCount > 0)
   691             d->mList.insert(1 + j, item);
   739             d->mList.insert(1 + j, item);
   692         }
   740         }
   693         
   741         
   694         endInsertRows();
   742         endInsertRows();
   695     }
   743     }
   696 }
   744     
       
   745     CNT_EXIT
       
   746 }
       
   747 
       
   748 void CntCollectionListModel::handleAdded(const QList<QContactLocalId>& contactIds)
       
   749 {
       
   750     CNT_ENTRY_ARGS(contactIds)
       
   751             
       
   752     if (contactIds.count() == 1)
       
   753     {
       
   754         QContactFetchHint noRelationshipsFetchHint;
       
   755         noRelationshipsFetchHint.setOptimizationHints(QContactFetchHint::NoRelationships);
       
   756         
       
   757         QContact contact = d->mContactManager->contact(contactIds.first(), noRelationshipsFetchHint);
       
   758         
       
   759         if (contact.type() == QContactType::TypeGroup)
       
   760         {
       
   761             addGroup(contactIds.first());
       
   762             emit groupCountChanged();
       
   763         }
       
   764     }
       
   765     else
       
   766     {
       
   767         QList<QContact> addedGroups;
       
   768         
       
   769         foreach (QContactLocalId id, contactIds)
       
   770         {
       
   771             QContactFetchHint noRelationshipsFetchHint;
       
   772             noRelationshipsFetchHint.setOptimizationHints(QContactFetchHint::NoRelationships);
       
   773             
       
   774             QContact contact = d->mContactManager->contact(id, noRelationshipsFetchHint);
       
   775             
       
   776             if (contact.type() == QContactType::TypeGroup)
       
   777             {
       
   778                 addedGroups << contact;
       
   779             }
       
   780         }
       
   781         
       
   782         if (addedGroups.count() == 1)
       
   783         {
       
   784             addGroup(addedGroups.first().localId());
       
   785             emit groupCountChanged();
       
   786         }
       
   787         else if (addedGroups.count() > 1)
       
   788         {
       
   789             qSort(addedGroups.begin(), addedGroups.end(), caseInsensitiveLessThan);
       
   790             
       
   791             foreach (QContact c, addedGroups)
       
   792             {
       
   793                 addGroup(c.localId());
       
   794             }
       
   795             emit groupCountChanged();
       
   796         }
       
   797     }
       
   798 
       
   799     CNT_EXIT
       
   800 }
       
   801 
       
   802 void CntCollectionListModel::handleRemoved(const QList<QContactLocalId>& contactIds)
       
   803 {
       
   804     CNT_ENTRY_ARGS(contactIds)
       
   805             
       
   806     foreach (QContactLocalId id, contactIds)
       
   807     {
       
   808         if (removeGroup(id))
       
   809         {
       
   810             emit groupCountChanged();
       
   811         }
       
   812         else
       
   813         {
       
   814             for (int i = 0;i < d->mList.count();i++)
       
   815             {
       
   816                 if (d->mList.at(i)->members.contains(id))
       
   817                 {
       
   818                     CollectionItemPointer item = d->mList.at(i);
       
   819 
       
   820                     item->fetched = false;
       
   821 
       
   822                     int idx = d->mList.indexOf(item);
       
   823                     emit dataChanged(index(idx, 0), index(idx, 0));
       
   824                 }
       
   825             }
       
   826         }
       
   827     }
       
   828             
       
   829     CNT_EXIT
       
   830 }
       
   831 
       
   832 void CntCollectionListModel::handleChanged(const QList<QContactLocalId>& contactIds)
       
   833 {
       
   834     CNT_ENTRY_ARGS(contactIds)
       
   835 
       
   836     foreach (QContactLocalId id, contactIds)
       
   837     {
       
   838         QContact contact = d->mContactManager->contact(id);
       
   839 
       
   840         if (contact.type() == QContactType::TypeGroup)
       
   841         {
       
   842             for (int i = 0;i < d->mList.count();i++)
       
   843             {
       
   844                 if (d->mList.at(i)->id == id && !d->mList.at(i)->isPlugin)
       
   845                 {
       
   846                     CollectionItemPointer item = d->mList.at(i);
       
   847 
       
   848                     QContactName contactName = contact.detail<QContactName>();
       
   849                     QString groupName = contactName.customLabel();
       
   850 
       
   851                     if (groupName != item->groupName)
       
   852                     {
       
   853                         if (groupName.isNull())
       
   854                         {
       
   855                             item->groupName = hbTrId("txt_phob_dblist_unnamed");
       
   856                         }
       
   857                         else
       
   858                         {
       
   859                             item->groupName = groupName;
       
   860                         }
       
   861 
       
   862                         int idx = d->mList.indexOf(item);
       
   863                         emit dataChanged(index(idx, 0), index(idx, 0));
       
   864                     }
       
   865 
       
   866                     break;
       
   867                 }
       
   868             }
       
   869         }
       
   870         else if (contact.type() == QContactType::TypeContact)
       
   871         {
       
   872             for (int i = 0;i < d->mList.count();i++)
       
   873             {
       
   874                 if (d->mList.at(i)->members.contains(id))
       
   875                 {
       
   876                     CollectionItemPointer item = d->mList.at(i);
       
   877 
       
   878                     item->fetched = false;
       
   879 
       
   880                     int idx = d->mList.indexOf(item);
       
   881                     emit dataChanged(index(idx, 0), index(idx, 0));
       
   882                 }
       
   883             }
       
   884         }
       
   885     }
       
   886     
       
   887     CNT_EXIT
       
   888 }
       
   889 
       
   890 void CntCollectionListModel::handleAddedRelationship(const QList<QContactLocalId>& contactIds)
       
   891 {
       
   892     CNT_ENTRY_ARGS(contactIds)
       
   893             
       
   894     foreach (QContactLocalId id, contactIds)
       
   895     {      
       
   896         for (int i = 0;i < d->mList.count();i++)
       
   897         {
       
   898             if (d->mList.at(i)->id == id && !d->mList.at(i)->isPlugin)
       
   899             {
       
   900                 CollectionItemPointer item = d->mList.at(i);
       
   901 
       
   902                 item->fetched = false;
       
   903 
       
   904                 int idx = d->mList.indexOf(item);
       
   905                 emit dataChanged(index(idx, 0), index(idx, 0));
       
   906 
       
   907                 break;
       
   908             }
       
   909         }
       
   910     }
       
   911             
       
   912     CNT_EXIT
       
   913 }
       
   914 
       
   915 void CntCollectionListModel::handleRemovedRelationship(const QList<QContactLocalId>& contactIds)
       
   916 {
       
   917     CNT_ENTRY_ARGS(contactIds)
       
   918     
       
   919     foreach (QContactLocalId id, contactIds)
       
   920     {      
       
   921         for (int i = 0;i < d->mList.count();i++)
       
   922         {
       
   923             if (d->mList.at(i)->id == id && !d->mList.at(i)->isPlugin)
       
   924             {
       
   925                 CollectionItemPointer item = d->mList.at(i);
       
   926 
       
   927                 item->fetched = false;
       
   928 
       
   929                 int idx = d->mList.indexOf(item);
       
   930                 emit dataChanged(index(idx, 0), index(idx, 0));
       
   931 
       
   932                 break;
       
   933             }
       
   934         }
       
   935     }
       
   936             
       
   937     CNT_EXIT
       
   938 }