//************************************************************************ // changes the groups membercount //************************************************************************ void CContactList::ChangeGroupObjectCounters(tstring strGroup,int iMembers,int iOnline,int iEvents) { CContactListGroup* pGroup = GetGroupObjectByPath(strGroup); if(!pGroup) return; pGroup->iMembers += iMembers; pGroup->iOnline += iOnline; pGroup->iEvents += iEvents; tstring strParse = pGroup->strPath; tstring::size_type pos; while((pos = strParse.rfind('\\')) != tstring::npos ) { strParse = strParse.substr(0,pos); pGroup = GetGroupObjectByPath(strParse); if(!pGroup) break; pGroup->iMembers += iMembers; pGroup->iOnline += iOnline; pGroup->iEvents += iEvents; } }
//************************************************************************ // deletes a group object by string //************************************************************************ void CContactList::DeleteGroupObjectByPath(tstring strPath) { ASSERT(!strPath.empty()); CContactListGroup *pParentGroup = NULL; vector<CContactListGroup*>::iterator iter = m_Groups.begin(); for(iter = m_Groups.begin();iter != m_Groups.end();iter++) { if((*iter)->strPath == strPath) { CContactListGroup *pGroup = *iter; m_Groups.erase(iter); if(pGroup->pContactListEntry) { DeleteEntry(pGroup->pContactListEntry); } delete pGroup; tstring strParse = strPath; tstring::size_type pos = strParse.rfind('\\'); if(pos != tstring::npos ) { strParse = strParse.substr(0,pos); pParentGroup = GetGroupObjectByPath(strParse); pParentGroup->iGroups--; if(pParentGroup->iMembers <= 0 && pParentGroup->iGroups <= 0) DeleteGroupObjectByPath(strParse); } return; } } }
//************************************************************************ // Adds a group //************************************************************************ CListContainer<CContactListEntry*,CContactListGroup*> *CContactList::AddGroupByString(tstring strGroup) { tstring strParse = strGroup; tstring strPath = _T(""); CListContainer<CContactListEntry*,CContactListGroup*> *pGroup = (CListContainer<CContactListEntry*,CContactListGroup*>*)this; CListContainer<CContactListEntry*,CContactListGroup*> *pGroup2 = NULL; tstring::size_type pos; while((pos = strParse.find('\\')) != tstring::npos ) { strGroup = strParse.substr(0,pos); strParse = strParse.substr(pos+1); strPath += strGroup; if(pGroup2 = FindGroupInGroup(strGroup,pGroup)) pGroup = pGroup2; else { CContactListGroup *pGroupObject = GetGroupObjectByPath(strPath); if(!pGroupObject) pGroupObject = CreateGroupObjectByPath(strPath); pGroup2 = pGroup->InsertGroup(pGroup->begin(),pGroupObject); pGroup->sort(CContactList::CompareEntries); pGroup = pGroup2; } ASSERT(pGroup != NULL); strPath += _T("\\"); } strPath += strParse; if(pGroup2 = FindGroupInGroup(strParse,pGroup)) return pGroup2; else { CContactListGroup *pGroupObject = GetGroupObjectByPath(strPath); if(!pGroupObject) pGroupObject = CreateGroupObjectByPath(strPath); pGroup2 = pGroup->InsertGroup(pGroup->begin(),pGroupObject); pGroup->sort(CContactList::CompareEntries); return pGroup2; } }
//************************************************************************ // called when a contact has been added //************************************************************************ void CContactList::OnContactAdded(MCONTACT hContact) { // Update the list AddContact(hContact); // increase the membercount of the new group, and check if it needs to be created tstring strGroup = GetContactGroupPath(hContact); if(!strGroup.empty()) { CContactListGroup *pGroup = GetGroupObjectByPath(strGroup); if(!pGroup) pGroup = CreateGroupObjectByPath(strGroup); if(!db_mc_isSub(hContact)) ChangeGroupObjectCounters(strGroup,1); } }
//************************************************************************ // initializes the group objects //************************************************************************ void CContactList::InitializeGroupObjects() { UninitializeGroupObjects(); int res = 0; CContactListGroup *pGroup = NULL; HANDLE hContact = db_find_first(); HANDLE hMetaContact = NULL; char *szProto = NULL; while(hContact != NULL) { tstring strGroup = GetContactGroupPath(hContact); szProto = (char*)CallService(MS_PROTO_GETCONTACTBASEPROTO,(UINT)hContact,0); if(szProto && db_get_b(NULL,"MetaContacts","Enabled",1) && !stricmp(szProto,"MetaContacts")) { tstring strName = CAppletManager::GetContactDisplayname(hContact); tstring strPath = _T(""); if(CConfig::GetBoolSetting(CLIST_USEGROUPS)) strPath += strGroup; strPath += (strPath.empty()?_T(""):_T("\\")) + strName; pGroup = CreateGroupObjectByPath(strPath); pGroup->hMetaContact = hContact; if(!strGroup.empty()) ChangeGroupObjectCounters(strGroup,1); } // If the contact has no group, continue else if(!strGroup.empty() && CConfig::GetBoolSetting(CLIST_USEGROUPS)) { pGroup = GetGroupObjectByPath(strGroup); // create the group if(!pGroup) pGroup = CreateGroupObjectByPath(strGroup); // update it's counters if(!CAppletManager::IsSubContact(hContact)) ChangeGroupObjectCounters(strGroup,1); } hContact = db_find_next(hContact); } }
//************************************************************************ // initializes the group objects //************************************************************************ void CContactList::InitializeGroupObjects() { UninitializeGroupObjects(); int res = 0; CContactListGroup *pGroup = NULL; HANDLE hMetaContact = NULL; char *szProto = NULL; for(MCONTACT hContact = db_find_first();hContact != NULL;hContact = db_find_next(hContact)) { tstring strGroup = GetContactGroupPath(hContact); szProto = GetContactProto(hContact); if(szProto && db_get_b(NULL,META_PROTO,"Enabled",1) && !mir_strcmpi(szProto,META_PROTO)) { tstring strName = CAppletManager::GetContactDisplayname(hContact); tstring strPath = _T(""); if(CConfig::GetBoolSetting(CLIST_USEGROUPS)) strPath += strGroup; strPath += (strPath.empty()?_T(""):_T("\\")) + strName; pGroup = CreateGroupObjectByPath(strPath); pGroup->hMetaContact = hContact; if(!strGroup.empty()) ChangeGroupObjectCounters(strGroup,1); } // If the contact has no group, continue else if(!strGroup.empty() && CConfig::GetBoolSetting(CLIST_USEGROUPS)) { pGroup = GetGroupObjectByPath(strGroup); // create the group if(!pGroup) pGroup = CreateGroupObjectByPath(strGroup); // update it's counters if(!db_mc_isSub(hContact)) ChangeGroupObjectCounters(strGroup,1); } } }
//************************************************************************ // called when a contact has been deleted //************************************************************************ void CContactList::OnContactDeleted(MCONTACT hContact) { // Update the list RemoveContact(hContact); // Decrease the membercount of the old group, and check if it needs to be deleted int res = 0; tstring strGroup = GetContactGroupPath(hContact); if(!strGroup.empty()) { CContactListGroup *pGroup = GetGroupObjectByPath(strGroup); if(!db_mc_isSub(hContact)) ChangeGroupObjectCounters(strGroup,-1); if(pGroup->iMembers <= 0) DeleteGroupObjectByPath(pGroup->strPath); } }
//************************************************************************ // creates a group object by string //************************************************************************ CContactListGroup *CContactList::CreateGroupObjectByPath(tstring strPath) { ASSERT(!strPath.empty()); CContactListGroup *pNewGroup = new CContactListGroup(); CContactListGroup *pParentGroup = NULL; tstring strParsePath = _T(""); tstring strName = strPath; tstring::size_type pos; while((pos = strName.find('\\')) != tstring::npos ) { strParsePath += strName.substr(0,pos); strName = strName.substr(pos+1); pParentGroup = GetGroupObjectByPath(strParsePath); if(!pParentGroup) pParentGroup = CreateGroupObjectByPath(strParsePath); strParsePath += _T("\\"); } if(pParentGroup) pParentGroup->iGroups++; pNewGroup->strName = strName; pNewGroup->strPath = strPath; pNewGroup->iMembers = 0; pNewGroup->iOnline = 0; pNewGroup->iGroups = 0; pNewGroup->iEvents = 0; pNewGroup->hMetaContact = NULL; pNewGroup->pContactListEntry = NULL; m_Groups.push_back(pNewGroup); return pNewGroup; }
//************************************************************************ // called when a contacts group has changed //************************************************************************ void CContactList::OnContactGroupChanged(MCONTACT hContact,tstring strGroup) { bool bMetaContact = false; strGroup = GetContactGroupPath(hContact); // Decrease the membercount of the old group CListEntry<CContactListEntry *,CContactListGroup*> *pContactEntry = FindContact(hContact); CContactListGroup *pOldGroup = NULL; // If the contactentry was not found, try adding the contact (metacontacts fix) if(!pContactEntry) { return; } if(pContactEntry->GetType() == CONTAINER) bMetaContact = true; CListContainer<CContactListEntry*,CContactListGroup*>* pContainer = ((CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry->GetParent()); // Update the contacts group if it has one if(pContainer->GetType() != ROOT) { pOldGroup = pContainer->GetGroupData(); if(!db_mc_isSub(hContact)) ChangeGroupObjectCounters(pOldGroup->strPath,-1); } // increase the membercount of the new group, and check if it needs to be created if(!strGroup.empty()) { CContactListGroup *pGroup = GetGroupObjectByPath(strGroup); if(!pGroup) pGroup = CreateGroupObjectByPath(strGroup); if(!db_mc_isSub(hContact)) ChangeGroupObjectCounters(strGroup,1); } // move subcontacts if(pContactEntry->GetType() == CONTAINER) { CListContainer<CContactListEntry*,CContactListGroup*> *pGroup = (CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry; CListContainer<CContactListEntry*,CContactListGroup*>::iterator iter = pGroup->begin(); while(!pGroup->empty()) { iter = pGroup->begin(); if((*iter)->GetType() == ITEM) OnContactGroupChanged(GetContactData(*iter)->hHandle,_T("")); Sleep(1); } } // update the list RemoveContact(hContact); AddContact(hContact); if(bMetaContact) { tstring strName = CAppletManager::GetContactDisplayname(hContact); tstring strPath = _T(""); if(pOldGroup) strPath += pOldGroup->strPath; strPath += (strPath.empty()?_T(""):_T("\\")) + strName; DeleteGroupObjectByPath(strPath); } // check if the old group ( if it exists ) needs to be deleted if(pOldGroup && !pOldGroup->hMetaContact && pOldGroup->iMembers <= 0 && pOldGroup->iGroups <= 0) DeleteGroupObjectByPath(pOldGroup->strPath); }