From 4adc7e198f49bbd5b39141f13322b653402c8a79 Mon Sep 17 00:00:00 2001 From: Alexander Lantsev Date: Mon, 10 Jun 2013 19:42:11 +0000 Subject: Skype: - fixed chat role updating - fixed chat commands git-svn-id: http://svn.miranda-ng.org/main/trunk@4911 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- protocols/Skype/src/resource.h | 6 +- protocols/Skype/src/skype_account.cpp | 4 +- protocols/Skype/src/skype_chat.cpp | 298 +++++++++++++++++--------- protocols/Skype/src/skype_chat.h | 19 +- protocols/Skype/src/skype_contacts.cpp | 4 + protocols/Skype/src/skype_dialogs.cpp | 3 +- protocols/Skype/src/skype_events.cpp | 42 ++++ protocols/Skype/src/skype_proto.h | 7 +- protocols/Skype/src/skype_utils.cpp | 3 + protocols/Skype/src/skypekit/account.cpp | 15 +- protocols/Skype/src/skypekit/account.h | 6 +- protocols/Skype/src/skypekit/conversation.cpp | 12 +- protocols/Skype/src/skypekit/conversation.h | 9 + protocols/Skype/src/skypekit/participant.cpp | 14 +- protocols/Skype/src/skypekit/participant.h | 9 + 15 files changed, 322 insertions(+), 129 deletions(-) (limited to 'protocols/Skype/src') diff --git a/protocols/Skype/src/resource.h b/protocols/Skype/src/resource.h index 71d16a52b9..c0b6b8b23c 100644 --- a/protocols/Skype/src/resource.h +++ b/protocols/Skype/src/resource.h @@ -1,6 +1,6 @@ //{{NO_DEPENDENCIES}} // Microsoft Visual C++ generated include file. -// Used by e:\Projects\C++\MirandaNG\protocols\Skype\res\Resource.rc +// Used by E:\Projects\C++\MirandaNG\protocols\Skype\res\Resource.rc // #define IDD_ACCMGR 9 #define IDD_OPT_MAIN 10 @@ -69,13 +69,15 @@ #define IDC_CHAT_GUIDLINE 1045 #define IDC_CHAT_JOINING 1046 #define IDC_COMBO1 1047 +#define IDC_ROLES 1047 #define IDC_CHAT_JOINING2 1048 +#define IDC_CHAT_SECURED 1048 #define IDC_EDIT1 1049 #define IDC_EDIT2 1050 #define IDC_EDIT3 1051 // Next default values for new objects -// +// #ifdef APSTUDIO_INVOKED #ifndef APSTUDIO_READONLY_SYMBOLS #define _APS_NEXT_RESOURCE_VALUE 111 diff --git a/protocols/Skype/src/skype_account.cpp b/protocols/Skype/src/skype_account.cpp index c60941ee9d..ff44128bd2 100644 --- a/protocols/Skype/src/skype_account.cpp +++ b/protocols/Skype/src/skype_account.cpp @@ -110,9 +110,7 @@ bool CSkypeProto::LogIn() return false; this->account.fetch(); - this->account->SetOnAccountChangedCallback( - (CAccount::OnAccountChanged)&CSkypeProto::OnAccountChanged, - this); + this->account->SetOnAccountChangedCallback(&CSkypeProto::OnAccountChanged, this); this->InitProxy(); diff --git a/protocols/Skype/src/skype_chat.cpp b/protocols/Skype/src/skype_chat.cpp index 50786daea9..c167168241 100644 --- a/protocols/Skype/src/skype_chat.cpp +++ b/protocols/Skype/src/skype_chat.cpp @@ -11,7 +11,7 @@ enum CHAT_LIST_MENU ICM_AUTH_REQUEST, ICM_CONF_INVITE, ICM_ROLE, ICM_ROLE_ADMIN, ICM_ROLE_SPEAKER, ICM_ROLE_WRITER, ICM_ROLE_SPECTATOR, - ICM_KICK, ICM_BAN, + ICM_ADD, ICM_KICK, ICM_BAN, ICM_COPY_SID, ICM_COPY_URI }; @@ -23,11 +23,12 @@ static struct gc_item crListItems[] = { LPGENT("Invite to conferance"), ICM_CONF_INVITE, MENU_ITEM }, { NULL, 0, MENU_SEPARATOR }, { LPGENT("Set &role"), ICM_ROLE, MENU_NEWPOPUP }, - { LPGENT("&Administrator"), ICM_ROLE_ADMIN, MENU_POPUPITEM }, - { LPGENT("&Speaker"), ICM_ROLE_SPEAKER, MENU_POPUPITEM }, - { LPGENT("&Writer"), ICM_ROLE_WRITER, MENU_POPUPITEM }, + { LPGENT("&Master"), ICM_ROLE_ADMIN, MENU_POPUPITEM }, + { LPGENT("&Helper"), ICM_ROLE_SPEAKER, MENU_POPUPITEM }, + { LPGENT("&User"), ICM_ROLE_WRITER, MENU_POPUPITEM }, { LPGENT("&Listener"), ICM_ROLE_SPECTATOR, MENU_POPUPITEM }, { NULL, 0, MENU_SEPARATOR }, + { LPGENT("&Add"), ICM_ADD, MENU_ITEM }, { LPGENT("&Kick"), ICM_KICK, MENU_ITEM }, { LPGENT("Outlaw (&ban)"), ICM_BAN, MENU_ITEM }, { NULL, 0, MENU_SEPARATOR }, @@ -56,16 +57,12 @@ static void ResetChatMenuItem() crListItems[i].bDisabled = FALSE; } -static const COLORREF crCols[16] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15}; - void CSkypeProto::InitChat() { GCREGISTER gcr = {0}; gcr.cbSize = sizeof(gcr); - gcr.dwFlags = GC_TCHAR | GC_TYPNOTIF | GC_CHANMGR; + gcr.dwFlags = GC_TCHAR; gcr.iMaxText = 0; - gcr.nColors = 16; - gcr.pColors = (COLORREF*)crCols; gcr.ptszModuleDispName = this->m_tszUserName; gcr.pszModule = this->m_szModuleName; ::CallServiceSync(MS_GC_REGISTER, 0, (LPARAM)&gcr); @@ -81,9 +78,9 @@ wchar_t *ChatRoom::Roles[] = L"", // --- L"Creator", // CREATOR = 1 L"Master", // ADMIN = 2 - L"Speaker", // SPEAKER = 3 - L"Writer", // WRITER = 4 - L"Spectator", // SPECTATOR= 5 + L"Helper", // SPEAKER = 3 + L"User", // WRITER = 4 + L"Listener", // SPECTATOR= 5 L"Applicant", // APPLICANT= 6 L"Retried", // RETIRED = 7 L"Outlaw", // OUTLAW = 8 @@ -106,6 +103,11 @@ ChatRoom::ChatRoom(const wchar_t *cid, const wchar_t *name, CSkypeProto *ppro) : this->me->SetNick(::TranslateT("me")); this->me->SetRank(0); this->me->SetStatus(ID_STATUS_OFFLINE); + // + this->sys = new ChatMember(L"sys"); + this->sys->SetNick(L"System"); + this->sys->SetRank(0); + this->sys->SetStatus(ID_STATUS_OFFLINE); } ChatRoom::~ChatRoom() @@ -144,14 +146,19 @@ void ChatRoom::Start(bool showWindow) gce.cbSize = sizeof(GCEVENT); gce.dwFlags = GC_TCHAR; gce.pDest = &gcd; - for (int i = 1; i < SIZEOF(ChatRoom::Roles); i++) + + for (int i = 1; i < SIZEOF(ChatRoom::Roles) - 2; i++) { gce.ptszStatus = ::TranslateW(ChatRoom::Roles[i]); - ::CallServiceSync(MS_GC_EVENT, NULL, (LPARAM)&gce); + ::CallServiceSync(MS_GC_EVENT, 0, (LPARAM)&gce); } + + /*gce.ptszStatus = ::TranslateT("Other"); + ::CallServiceSync(MS_GC_EVENT, 0, (LPARAM)&gce);*/ // init [and show window] gcd.iType = GC_EVENT_CONTROL; + gce.ptszStatus = NULL; ::CallServiceSync(MS_GC_EVENT, showWindow ? SESSION_INITDONE : WINDOW_HIDDEN, (LPARAM)&gce); ::CallServiceSync(MS_GC_EVENT, SESSION_ONLINE, (LPARAM)&gce); } @@ -187,7 +194,8 @@ void ChatRoom::Start(const ParticipantRefs &participants, bool showWindow) } member.SetPaticipant(participant); - member.participant.fetch(); + /*member.participant.fetch(); + member.participant->SetOnChangedCallback(&ChatRoom::OnParticipantChanged, this);*/ this->AddMember(member, NULL, NULL); } @@ -224,20 +232,23 @@ void ChatRoom::SendEvent(const ChatMember &item, int eventType, DWORD timestamp, gce.ptszStatus = status; gce.ptszText = message; gce.time = timestamp; + ::CallServiceSync(MS_GC_EVENT, 0, (LPARAM)&gce); } void ChatRoom::SendEvent(const wchar_t *sid, int eventType, DWORD timestamp, DWORD flags, DWORD itemData, const wchar_t *status, const wchar_t *message) { - if ( !this->IsMe(sid)) + if (this->IsMe(sid)) + this->SendEvent(*this->me, eventType, timestamp, flags, itemData, status, message); + else if (this->IsSys(sid)) + this->SendEvent(*this->sys, eventType, timestamp, flags, itemData, status, message); + else { ChatMember search(sid); ChatMember *member = this->members.find(&search); if (member != NULL) this->SendEvent(*member, eventType, timestamp, flags, itemData, status, message); } - else - this->SendEvent(*this->me, eventType, timestamp, flags, itemData, status, message); } bool ChatRoom::IsMe(const wchar_t *sid) const @@ -250,6 +261,16 @@ bool ChatRoom::IsMe(const ChatMember &item) const return ::lstrcmpi(this->ppro->login, item.GetSid()) == 0; } +bool ChatRoom::IsSys(const wchar_t *sid) const +{ + return ::lstrcmpi(L"sys", sid) == 0; +} + +bool ChatRoom::IsSys(const ChatMember &item) const +{ + return ::lstrcmpi(L"sys", item.GetSid()) == 0; +} + ChatMember *ChatRoom::FindChatMember(const wchar_t *sid) { if ( !IsMe(sid)) @@ -261,7 +282,7 @@ ChatMember *ChatRoom::FindChatMember(const wchar_t *sid) return this->me; } -void ChatRoom::AddMember(const ChatMember &item, const ChatMember *author, DWORD timestamp) +void ChatRoom::AddMember(const ChatMember &item, const ChatMember &author, DWORD timestamp) { if ( !this->IsMe(item)) { @@ -272,7 +293,10 @@ void ChatRoom::AddMember(const ChatMember &item, const ChatMember *author, DWORD } else { - this->members.insert(new ChatMember(item)); + ChatMember *newMember = new ChatMember(item); + newMember->participant.fetch(); + newMember->participant->SetOnChangedCallback(&ChatRoom::OnParticipantChanged, this); + this->members.insert(newMember); this->SendEvent(item, GC_EVENT_JOIN, timestamp, GCEF_ADDTOLOG, 0, ::TranslateW(ChatRoom::Roles[item.GetRank()])); this->SendEvent(item, GC_EVENT_SETCONTACTSTATUS, timestamp, 0, item.GetStatus()); @@ -280,37 +304,58 @@ void ChatRoom::AddMember(const ChatMember &item, const ChatMember *author, DWORD } else { + if (!this->me->participant) + { + this->me->participant = item.participant; + this->me->participant.fetch(); + this->me->participant->SetOnChangedCallback(&ChatRoom::OnParticipantChanged, this); + } if (this->me->GetRank() != item.GetRank()) { this->SendEvent(*this->me, GC_EVENT_REMOVESTATUS, timestamp, 0, 0, ::TranslateW(ChatRoom::Roles[this->me->GetRank()])); - this->SendEvent(*this->me, GC_EVENT_ADDSTATUS, timestamp, !this->me->GetRank() ? 0 : GCEF_ADDTOLOG, 0, ::TranslateW(ChatRoom::Roles[item.GetRank()]), author == NULL ? NULL : author->GetNick()); + this->SendEvent(*this->me, GC_EVENT_ADDSTATUS, timestamp, !this->me->GetRank() ? 0 : GCEF_ADDTOLOG, 0, ::TranslateW(ChatRoom::Roles[item.GetRank()]), author == NULL ? this->sys->GetNick() : author.GetNick()); this->me->SetRank(item.GetRank()); } } } -void ChatRoom::UpdateMember(const wchar_t *sid, const wchar_t *nick, int rank, int status, DWORD timestamp) +void ChatRoom::UpdateMemberNick(ChatMember *member, const wchar_t *nick, DWORD timestamp) +{ + if (::lstrcmp(member->GetNick(), nick) != 0) + { + this->SendEvent(*member, GC_EVENT_NICK, timestamp, GCEF_ADDTOLOG, 0, nick); + member->SetNick(nick); + } +} + +void ChatRoom::UpdateMemberRole(ChatMember *member, int role, const ChatMember &author, DWORD timestamp) +{ + if (member->GetRank() != role) + { + this->SendEvent(*member, GC_EVENT_REMOVESTATUS, timestamp, 0, 0, ::TranslateW(ChatRoom::Roles[member->GetRank()])); + this->SendEvent(*member, GC_EVENT_ADDSTATUS, timestamp, GCEF_ADDTOLOG, 0, ::TranslateW(ChatRoom::Roles[role]), author == NULL ? this->sys->GetNick() : author.GetNick()); + member->SetRank(role); + } +} + +void ChatRoom::UpdateMemberStatus(ChatMember *member, int status, DWORD timestamp) +{ + if (member->GetStatus() != status) + { + this->SendEvent(*member, GC_EVENT_SETCONTACTSTATUS, timestamp, 0, status); + member->SetStatus(status); + } +} + +void ChatRoom::UpdateMember(const wchar_t *sid, const wchar_t *nick, int role, int status, DWORD timestamp) { ChatMember search(sid); ChatMember *member = this->members.find(&search); if (member != NULL) { - if (::lstrcmp(member->GetNick(), nick) != 0) - { - this->SendEvent(*member, GC_EVENT_NICK, timestamp, GCEF_ADDTOLOG, 0, nick); - member->SetNick(nick); - } - if (member->GetRank() != rank) - { - this->SendEvent(*member, GC_EVENT_REMOVESTATUS, timestamp, 0, 0, ::TranslateW(ChatRoom::Roles[member->GetRank()])); - this->SendEvent(*member, GC_EVENT_ADDSTATUS, timestamp, GCEF_ADDTOLOG, 0, ::TranslateW(ChatRoom::Roles[rank])); - member->SetRank(rank); - } - if (member->GetStatus() != status) - { - this->SendEvent(*member, GC_EVENT_SETCONTACTSTATUS, timestamp, 0, status); - member->SetStatus(status); - } + this->UpdateMemberNick(member, nick, timestamp); + this->UpdateMemberRole(member, role, NULL, timestamp); + this->UpdateMemberStatus(member, status, timestamp); } } @@ -354,7 +399,7 @@ void ChatRoom::KickMember(const ChatMember &item, const ChatMember *author, DWOR else { this->SendEvent(*this->me, GC_EVENT_KICK, timestamp, GCEF_ADDTOLOG, 0, author->GetNick()); - this->me->SetRank(/*APPLICANT= */6); + this->me->SetRank(/*RETIRED= */7); } } @@ -460,9 +505,10 @@ void ChatRoom::OnEvent(const ConversationRef &conversation, const MessageRef &me } member.participant = participants[i]; - member.participant.fetch(); + /*member.participant.fetch(); + member.participant->SetOnChangedCallback(&ChatRoom::OnParticipantChanged, this);*/ - this->AddMember(member, author, timestamp); + this->AddMember(member, *author, timestamp); } } @@ -566,35 +612,35 @@ void ChatRoom::OnEvent(const ConversationRef &conversation, const MessageRef &me } break; - case Message::SET_RANK: - { - SEString data; - message->GetPropBodyXml(data); - ptrA text = ::mir_strdup(data); - int i = 0; - - /*Message::CONSUMPTION_STATUS status; - message->GetPropConsumptionStatus(status); - if (status == Message::UNCONSUMED_NORMAL)*/ - { - message->GetPropAuthor(data); - ptrW sid = ::mir_utf8decodeW(data); - - ChatMember search(sid); - ChatMember *member = this->FindChatMember(sid); - if (member != NULL) - { - uint timestamp; - message->GetPropTimestamp(timestamp); - - message->GetPropBodyXml(data); - ptrW rank = ::mir_utf8decodeW(data); - - member->SetRank(0); - } - } - } - break; + //case Message::SET_RANK: + // { + // SEString data; + // message->GetPropBodyXml(data); + // ptrA text = ::mir_strdup(data); + // int i = 0; + + // /*Message::CONSUMPTION_STATUS status; + // message->GetPropConsumptionStatus(status); + // if (status == Message::UNCONSUMED_NORMAL)*/ + // { + // message->GetPropAuthor(data); + // ptrW sid = ::mir_utf8decodeW(data); + + // ChatMember search(sid); + // ChatMember *member = this->FindChatMember(sid); + // if (member != NULL) + // { + // uint timestamp; + // message->GetPropTimestamp(timestamp); + + // message->GetPropBodyXml(data); + // ptrW rank = ::mir_utf8decodeW(data); + + // member->SetRank(0); + // } + // } + // } + // break; case CMessage::STARTED_LIVESESSION: { @@ -650,6 +696,23 @@ void ChatRoom::OnEvent(const ConversationRef &conversation, const MessageRef &me } } +void ChatRoom::OnParticipantChanged(const ParticipantRef &participant, int prop) +{ + if (prop == Participant::P_RANK) + { + Participant::RANK rank; + participant->GetPropRank(rank); + + SEString identity; + participant->GetPropIdentity(identity); + + ptrW sid(::mir_utf8decodeW(identity)); + ChatMember *member = this->FindChatMember(sid); + if (member != NULL) + this->UpdateMemberRole(member, rank); + } +} + /// void CSkypeProto::ChatValidateContact(HANDLE hItem, HWND hwndList, const StringList &contacts) @@ -949,18 +1012,6 @@ int __cdecl CSkypeProto::OnGCEventHook(WPARAM, LPARAM lParam) switch (gch->pDest->iType) { - /*case GC_SESSION_TERMINATE: - { - ptrA cid = ::mir_utf8encodeW(gch->pDest->ptszID); - if (this->GetConversationByIdentity((char *)cid, conversation, false)) - { - Participant::Refs participants; - conversation->GetParticipants(participants, CConversation::MYSELF); - participants[0]->Retire(); - } - } - break;*/ - case GC_USER_MESSAGE: if (gch->ptszText && gch->ptszText[0]) { @@ -1017,13 +1068,25 @@ int __cdecl CSkypeProto::OnGCEventHook(WPARAM, LPARAM lParam) } if (member->participant && member->participant->SetRankTo(rank)) { - member->SetRank(rank); - room->UpdateMember(member->GetSid(), member->GetNick(), rank, member->GetStatus()); + //member->SetRank(rank); + room->UpdateMemberRole(member, rank, *room->me); } } } break; + case CHAT_LIST_MENU::ICM_ADD: + { + ChatMember *member = room->FindChatMember(gch->ptszUID); + if (member != NULL) + { + SEStringList consumers; + consumers.append((char *)ptrA(::mir_utf8encodeW(gch->ptszUID))); + room->conversation->AddConsumers(consumers); + } + } + break; + case CHAT_LIST_MENU::ICM_KICK: { ChatMember *member = room->FindChatMember(gch->ptszUID); @@ -1137,16 +1200,23 @@ int __cdecl CSkypeProto::OnGCMenuHook(WPARAM, LPARAM lParam) DisableChatMenuItem(ICM_COPY_SID); } - if (room->me->GetRank() > Participant::ADMIN && room->me->GetRank() == 0) + if (room->me->GetRank() > Participant::ADMIN || room->me->GetRank() == 0) { //CHAT_LIST_MENU adminItems[] = { ICM_ROLE, ICM_ROLE_ADMIN, ICM_ROLE_SPEAKER, ICM_ROLE_WRITER, ICM_ROLE_SPECTATOR }; //DisableChatMenuItems(adminItems); DisableChatMenuItem(ICM_ROLE); + DisableChatMenuItem(ICM_ADD); DisableChatMenuItem(ICM_KICK); DisableChatMenuItem(ICM_BAN); } + ChatMember *member = room->FindChatMember(gcmi->pszUID); + if (member != NULL && member->GetRank() > Participant::SPECTATOR) + { + DisableChatMenuItem(ICM_ROLE); + } + gcmi->nItems = SIZEOF(crListItems); gcmi->Item = crListItems; @@ -1189,12 +1259,39 @@ void CSkypeProto::UpdateChatUserStatus(CContact::Ref contact) ChatRoom *room = (ChatRoom *)gci.dwItemData; if (room != NULL) { - room->SendEvent( - sid, - GC_EVENT_SETCONTACTSTATUS, - 0, - 0, - CSkypeProto::SkypeToMirandaStatus(availability)); + ChatMember *member = room->FindChatMember(sid); + if (member != NULL) + room->UpdateMemberStatus(member, CSkypeProto::SkypeToMirandaStatus(availability)); + } + } +} + +void CSkypeProto:: UpdateChatUserNick(CContact::Ref contact) +{ + SEString data; + + contact->GetIdentity(data); + ptrW sid(::mir_utf8decodeW(data)); + + contact->GetPropFullname(data); + ptrW nick(::mir_utf8decodeW(data)); + + GC_INFO gci = {0}; + gci.Flags = BYINDEX | DATA; + gci.pszModule = this->m_szModuleName; + + int count = ::CallServiceSync(MS_GC_GETSESSIONCOUNT, 0, (LPARAM)this->m_szModuleName); + for (int i = 0; i < count ; i++) + { + gci.iItem = i; + ::CallServiceSync(MS_GC_GETINFO, 0, (LPARAM)&gci); + + ChatRoom *room = (ChatRoom *)gci.dwItemData; + if (room != NULL) + { + ChatMember *member = room->FindChatMember(sid); + if (member != NULL) + room->UpdateMemberNick(member, nick); } } } @@ -1224,10 +1321,11 @@ INT_PTR __cdecl CSkypeProto::OnJoinChat(WPARAM wParam, LPARAM) ChatRoom *room = new ChatRoom(cid, name, this); room->conversation = conversation; - //room->conversation.fetch(); + room->conversation.fetch(); + //room->conversation->SetOnConvoChangedCallback(this->OnConversationChanged); Participant::Refs participants; - conversation->GetParticipants(participants, Conversation::ALL); + conversation->GetParticipants(participants, Conversation::CONSUMERS_AND_APPLICANTS); room->Start(participants, true); } @@ -1290,11 +1388,13 @@ void __cdecl CSkypeProto::LoadChatList(void*) ChatRoom *room = new ChatRoom(cid, name, this); room->conversation = conversation; - //room->conversation.fetch(); + room->conversation.fetch(); + //room->conversation->SetOnConvoChangedCallback(&CSkypeProto::OnConversationChanged); + this->AddChatRoom(conversation); Participant::Refs participants; - conversation->GetParticipants(participants, Conversation::ALL); + conversation->GetParticipants(participants, Conversation::CONSUMERS_AND_APPLICANTS); room->Start(participants); } @@ -1335,11 +1435,11 @@ void CSkypeProto::OnChatEvent(const ConversationRef &conversation, const Message ChatRoom *room = new ChatRoom(cid, name, this); room->conversation = conversation; - //room->conversation.fetch(); + room->conversation.fetch(); this->AddChatRoom(conversation); Participant::Refs participants; - conversation->GetParticipants(participants, Conversation::ALL); + conversation->GetParticipants(participants, Conversation::CONSUMERS_AND_APPLICANTS); room->Start(participants, true); } @@ -1368,11 +1468,11 @@ void CSkypeProto::OnConversationListChange( ChatRoom *room = new ChatRoom(cid, name, this); room->conversation = conversation; - //room->conversation.fetch(); + room->conversation.fetch(); this->AddChatRoom(conversation); Participant::Refs participants; - conversation->GetParticipants(participants, Conversation::ALL); + conversation->GetParticipants(participants, Conversation::CONSUMERS_AND_APPLICANTS); room->Start(participants, true); } diff --git a/protocols/Skype/src/skype_chat.h b/protocols/Skype/src/skype_chat.h index d070cb0b44..c2d0fa80b9 100644 --- a/protocols/Skype/src/skype_chat.h +++ b/protocols/Skype/src/skype_chat.h @@ -84,7 +84,6 @@ public: void SetPaticipant(const ParticipantRef &participant) { this->participant = participant; - //this->participant.fetch(); } static int Compare(const ChatMember *p1, const ChatMember *p2) @@ -128,9 +127,7 @@ private: wchar_t *cid; wchar_t *name; - HANDLE hContact; - - + HANDLE hContact; LIST members; @@ -145,6 +142,7 @@ private: inline static int CompareMembers(const ChatMember *p1, const ChatMember *p2) { return ChatMember::Compare(p1, p2); } bool IsMe(const ChatMember &item) const; + bool IsSys(const ChatMember &item) const; void SendEvent(const ChatMember &item, int eventType, DWORD timestamp = time(NULL), DWORD flags = GCEF_ADDTOLOG, DWORD itemData = 0, const wchar_t *status = NULL, const wchar_t *message = NULL); void UpdateMember(const ChatMember &item, DWORD timestamp = time(NULL)); @@ -153,6 +151,7 @@ private: public: ChatMember *me; + ChatMember *sys; CConversation::Ref conversation; ChatRoom(const wchar_t *cid, const wchar_t *name, CSkypeProto *ppro); @@ -166,18 +165,26 @@ public: void SendEvent(const wchar_t *sid, int eventType, DWORD timestamp = time(NULL), DWORD flags = GCEF_ADDTOLOG, DWORD itemData = 0, const wchar_t *status = NULL, const wchar_t *message = NULL); bool IsMe(const wchar_t *sid) const; + bool IsSys(const wchar_t *sid) const; // ChatMember *FindChatMember(const wchar_t *sid); - void AddMember(const ChatMember &item, const ChatMember *author, DWORD timestamp = time(NULL)); + void AddMember(const ChatMember &item, const ChatMember &author, DWORD timestamp = time(NULL)); + + void UpdateMemberNick(ChatMember *member, const wchar_t *nick, DWORD timestamp = time(NULL)); + void UpdateMemberRole(ChatMember *member, int role, const ChatMember &author = NULL, DWORD timestamp = time(NULL)); + void UpdateMemberStatus(ChatMember *member, int status, DWORD timestamp = time(NULL)); + + void UpdateMember(const wchar_t *sid, const wchar_t *nick, int role, int status, DWORD timestamp = time(NULL)); - void UpdateMember(const wchar_t *sid, const wchar_t *nick, int rank, int status, DWORD timestamp = time(NULL)); void KickMember(const wchar_t *sid, const wchar_t *author, DWORD timestamp = time(NULL)); void RemoveMember(const wchar_t *sid, DWORD timestamp = time(NULL)); void OnEvent(const ConversationRef &conversation, const MessageRef &message); + void OnParticipantChanged(const ParticipantRef &participant, int prop); + static int __cdecl OnGCEventHook(WPARAM, LPARAM lParam); static int __cdecl OnGCMenuHook(WPARAM, LPARAM lParam); }; \ No newline at end of file diff --git a/protocols/Skype/src/skype_contacts.cpp b/protocols/Skype/src/skype_contacts.cpp index 35c61d6357..6b60eae031 100644 --- a/protocols/Skype/src/skype_contacts.cpp +++ b/protocols/Skype/src/skype_contacts.cpp @@ -123,6 +123,10 @@ void CSkypeProto::OnContactChanged(CContact::Ref contact, int prop) this->UpdateProfileStatusMessage(contactObj, hContact); break; + case CContact::P_FULLNAME: + this->UpdateChatUserNick(contact); + break; + case CContact::P_PROFILE_TIMESTAMP: this->UpdateProfile(contactObj, hContact); break; diff --git a/protocols/Skype/src/skype_dialogs.cpp b/protocols/Skype/src/skype_dialogs.cpp index 41817a0c18..250e18a530 100644 --- a/protocols/Skype/src/skype_dialogs.cpp +++ b/protocols/Skype/src/skype_dialogs.cpp @@ -117,8 +117,7 @@ INT_PTR CALLBACK CSkypeProto::SkypeMainOptionsProc(HWND hwnd, UINT message, WPAR CAccount::Ref account; proto->GetAccount(sid, proto->account); proto->account->SetStrProperty(CAccount::P_FULLNAME, sid); - proto->account->SetOnAccountChangedCallback( - (CAccount::OnAccountChanged)&CSkypeProto::OnAccountChanged, proto); + proto->account->SetOnAccountChangedCallback(&CSkypeProto::OnAccountChanged, proto); proto->account->Register(pwd, false, false); } else diff --git a/protocols/Skype/src/skype_events.cpp b/protocols/Skype/src/skype_events.cpp index e889326d8d..8d48c579c7 100644 --- a/protocols/Skype/src/skype_events.cpp +++ b/protocols/Skype/src/skype_events.cpp @@ -250,4 +250,46 @@ void CSkypeProto::OnMessage ( //case CMessage::BLOCKED: // break; } +} + +void CSkypeProto::OnConversationChanged(const ConversationRef &conversation, int prop) +{ + if (prop == Conversation::P_LOCAL_LIVESTATUS) + { + Conversation::LOCAL_LIVESTATUS liveStatus; + conversation->GetPropLocalLivestatus(liveStatus); + if (liveStatus == Conversation::RINGING_FOR_ME) + { + SEString data; + + CConversation::TYPE type; + conversation->GetPropType(type); + if (type == 0 || type == CConversation::DIALOG) + { + ParticipantRefs participants; + conversation->GetParticipants(participants, Conversation::OTHER_CONSUMERS); + + participants[0]->GetPropIdentity(data); + + ContactRef author; + this->GetContact(data, author); + + HANDLE hContact = this->AddContact(author); + + char *message = ::mir_utf8encode(::Translate("Incoming call received")); + + this->AddDBEvent( + hContact, + SKYPE_DB_EVENT_TYPE_CALL, + time(NULL), + DBEF_UTF, + (DWORD)::strlen(message) + 1, + (PBYTE)message); + } + //temp popup + TCHAR popuptext[MAX_PATH]; + mir_sntprintf(popuptext, SIZEOF(popuptext), TranslateT("Incoming call from %s. Use offical skype for calling."), ptrW(::mir_utf8decodeW(data))); + this->ShowNotification(popuptext); + } + } } \ No newline at end of file diff --git a/protocols/Skype/src/skype_proto.h b/protocols/Skype/src/skype_proto.h index 07dccd1d3f..38f68e9557 100644 --- a/protocols/Skype/src/skype_proto.h +++ b/protocols/Skype/src/skype_proto.h @@ -270,8 +270,9 @@ protected: HANDLE GetChatRoomByCid(const wchar_t *cid); HANDLE AddChatRoom(CConversation::Ref conversation); - wchar_t *CSkypeProto::GetChatUsers(const wchar_t *cid); - void CSkypeProto::UpdateChatUserStatus(CContact::Ref contact); + wchar_t *GetChatUsers(const wchar_t *cid); + void UpdateChatUserStatus(CContact::Ref contact); + void UpdateChatUserNick(CContact::Ref contact); void ChatValidateContact(HANDLE hItem, HWND hwndList, const StringList &contacts); void ChatPrepare(HANDLE hItem, HWND hwndList, const StringList &contacts); @@ -477,4 +478,6 @@ protected: int __cdecl OnMessagePreCreate(WPARAM, LPARAM); int __cdecl OnTabSRMMButtonPressed(WPARAM, LPARAM); + + void OnConversationChanged(const ConversationRef &conversation, int prop); }; diff --git a/protocols/Skype/src/skype_utils.cpp b/protocols/Skype/src/skype_utils.cpp index 4c908788d6..10203a3577 100644 --- a/protocols/Skype/src/skype_utils.cpp +++ b/protocols/Skype/src/skype_utils.cpp @@ -414,6 +414,9 @@ char *CSkypeProto::RemoveHtml(const char *text) std::string new_string = ""; std::string data = text; + if (data.find("\x1b\xe3\xac\x8d\x1d") != -1) + data = "CONVERSATION MEMBERS:" + data.substr(5, data.length() - 5); + for (std::string::size_type i = 0; i < data.length(); i++) { if (data.at(i) == '<' && data.at(i+1) != ' ') diff --git a/protocols/Skype/src/skypekit/account.cpp b/protocols/Skype/src/skypekit/account.cpp index 08c37d67e2..088d747a77 100644 --- a/protocols/Skype/src/skypekit/account.cpp +++ b/protocols/Skype/src/skypekit/account.cpp @@ -2,15 +2,12 @@ CAccount::CAccount(unsigned int oid, SERootObject* root) : Account(oid, root) { - this->proto = NULL; - this->callback == NULL; + this->ppro = NULL; } -void CAccount::SetOnAccountChangedCallback(OnAccountChanged callback, CSkypeProto* proto) +void CAccount::SetOnAccountChangedCallback(OnAccountChanged callback, CSkypeProto *ppro) { - this->skype = (Skype *)root; - - this->proto = proto; + this->ppro = ppro; this->callback = callback; } @@ -24,7 +21,7 @@ bool CAccount::IsOnline() bool CAccount::SetAvatar(SEBinary avatar, Skype::VALIDATERESULT &result) { int fbl; - if (!this->skype->ValidateAvatar(avatar, result, fbl) || result != Skype::VALIDATED_OK) + if (!((Skype*)this->root)->ValidateAvatar(avatar, result, fbl) || result != Skype::VALIDATED_OK) return false; if (!this->SetBinProperty(Account::P_AVATAR_IMAGE, avatar)) @@ -35,6 +32,6 @@ bool CAccount::SetAvatar(SEBinary avatar, Skype::VALIDATERESULT &result) void CAccount::OnChange(int prop) { - if (this->proto) - (proto->*callback)(prop); + if (this->ppro != NULL) + (ppro->*callback)(prop); } \ No newline at end of file diff --git a/protocols/Skype/src/skypekit/account.h b/protocols/Skype/src/skypekit/account.h index 36a78e745b..ce6151da63 100644 --- a/protocols/Skype/src/skypekit/account.h +++ b/protocols/Skype/src/skypekit/account.h @@ -15,11 +15,11 @@ public: bool IsOnline(); bool SetAvatar(SEBinary avatar, Skype::VALIDATERESULT &result); - void SetOnAccountChangedCallback(OnAccountChanged callback, CSkypeProto* proto); + void SetOnAccountChangedCallback(OnAccountChanged callback, CSkypeProto *ppro); private: - Skype *skype; - CSkypeProto* proto; + CSkypeProto* ppro; OnAccountChanged callback; + void OnChange(int prop); }; \ No newline at end of file diff --git a/protocols/Skype/src/skypekit/conversation.cpp b/protocols/Skype/src/skypekit/conversation.cpp index 3c56e57559..25ffbffbfe 100644 --- a/protocols/Skype/src/skypekit/conversation.cpp +++ b/protocols/Skype/src/skypekit/conversation.cpp @@ -1,3 +1,13 @@ #include "conversation.h" -CConversation::CConversation(unsigned int oid, SERootObject* root) : Conversation(oid, root) { } \ No newline at end of file +CConversation::CConversation(unsigned int oid, SERootObject* root) : Conversation(oid, root) { } + +void CConversation::SetOnConvoChangedCallback(OnConvoChanged callback) +{ + this->callback = callback; +} + +void CConversation::OnChange(int prop) +{ + //(((CSkypeProto*)this->root)->*callback)(this->ref(), prop); +} \ No newline at end of file diff --git a/protocols/Skype/src/skypekit/conversation.h b/protocols/Skype/src/skypekit/conversation.h index 2527ced564..b9b1a51da1 100644 --- a/protocols/Skype/src/skypekit/conversation.h +++ b/protocols/Skype/src/skypekit/conversation.h @@ -5,8 +5,17 @@ class CConversation : public Conversation { public: + typedef void (CSkypeProto::* OnConvoChanged)(const ConversationRef &conversation, int); + typedef DRef Ref; typedef DRefs Refs; CConversation(unsigned int oid, SERootObject* root); + + void SetOnConvoChangedCallback(OnConvoChanged callback); + +private: + OnConvoChanged callback; + + void OnChange(int prop); }; \ No newline at end of file diff --git a/protocols/Skype/src/skypekit/participant.cpp b/protocols/Skype/src/skypekit/participant.cpp index 035003d1c9..9b35cfabb2 100644 --- a/protocols/Skype/src/skypekit/participant.cpp +++ b/protocols/Skype/src/skypekit/participant.cpp @@ -1,8 +1,18 @@ #include "participant.h" -CParticipant::CParticipant(unsigned int oid, SERootObject* root) : Participant(oid, root) { } +CParticipant::CParticipant(unsigned int oid, SERootObject* root) : Participant(oid, root) +{ + this->room = NULL; +} + +void CParticipant::SetOnChangedCallback(OnChanged callback, ChatRoom *room) +{ + this->room = room; + this->callback = callback; +} void CParticipant::OnChange(int prop) { - int i = 0; + if (this->room != NULL) + (room->*callback)(this->ref(), prop); } \ No newline at end of file diff --git a/protocols/Skype/src/skypekit/participant.h b/protocols/Skype/src/skypekit/participant.h index 3d6e38b445..e6db40ca1f 100644 --- a/protocols/Skype/src/skypekit/participant.h +++ b/protocols/Skype/src/skypekit/participant.h @@ -2,14 +2,23 @@ #include "common.h" +class ChatRoom; + class CParticipant : public Participant { public: + typedef void (ChatRoom::* OnChanged)(const ParticipantRef &participant, int); + typedef DRef Ref; typedef DRefs Refs; CParticipant(unsigned int oid, SERootObject* root); + void SetOnChangedCallback(OnChanged callback, ChatRoom *room); + private: + ChatRoom *room; + OnChanged callback; + void OnChange(int prop); }; \ No newline at end of file -- cgit v1.2.3