From a7e15910e804e742777b7bb54c83c15a22f342fc Mon Sep 17 00:00:00 2001 From: Alexander Lantsev Date: Thu, 10 Apr 2014 08:03:40 +0000 Subject: Steam: - own profile updating - avatar support git-svn-id: http://svn.miranda-ng.org/main/trunk@8911 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- protocols/Steam/Steam_10.vcxproj | 2 + protocols/Steam/Steam_10.vcxproj.filters | 6 ++ protocols/Steam/src/Steam/authorization.h | 2 +- protocols/Steam/src/Steam/avatar.h | 53 ++++++++++++ protocols/Steam/src/Steam/friend.h | 2 +- protocols/Steam/src/Steam/friend_list.h | 2 +- protocols/Steam/src/Steam/login.h | 4 +- protocols/Steam/src/Steam/message.h | 6 +- protocols/Steam/src/Steam/poll.h | 2 +- protocols/Steam/src/Steam/rsa_key.h | 8 +- protocols/Steam/src/Steam/search.h | 2 +- protocols/Steam/src/Steam/steam.h | 1 + protocols/Steam/src/common.h | 4 +- protocols/Steam/src/http_request.h | 9 +- protocols/Steam/src/steam.h | 31 ------- protocols/Steam/src/steam_account.cpp | 38 +------- protocols/Steam/src/steam_avatars.cpp | 102 ++++++++++++++++++++++ protocols/Steam/src/steam_contacts.cpp | 139 ++++++++++++++++++++++++------ protocols/Steam/src/steam_proto.cpp | 8 ++ protocols/Steam/src/steam_proto.h | 10 +++ protocols/Steam/src/steam_thread.cpp | 23 ++--- 21 files changed, 327 insertions(+), 127 deletions(-) create mode 100644 protocols/Steam/src/Steam/avatar.h delete mode 100644 protocols/Steam/src/steam.h create mode 100644 protocols/Steam/src/steam_avatars.cpp (limited to 'protocols/Steam') diff --git a/protocols/Steam/Steam_10.vcxproj b/protocols/Steam/Steam_10.vcxproj index 4f313ffaab..5cd612d9c6 100644 --- a/protocols/Steam/Steam_10.vcxproj +++ b/protocols/Steam/Steam_10.vcxproj @@ -191,6 +191,7 @@ + @@ -205,6 +206,7 @@ + diff --git a/protocols/Steam/Steam_10.vcxproj.filters b/protocols/Steam/Steam_10.vcxproj.filters index 4303fa4594..dc1879a5fa 100644 --- a/protocols/Steam/Steam_10.vcxproj.filters +++ b/protocols/Steam/Steam_10.vcxproj.filters @@ -48,6 +48,9 @@ Source Files + + Source Files + @@ -92,6 +95,9 @@ Header Files\Steam + + Header Files\Steam + diff --git a/protocols/Steam/src/Steam/authorization.h b/protocols/Steam/src/Steam/authorization.h index 27921e2aa1..51643d4dc8 100644 --- a/protocols/Steam/src/Steam/authorization.h +++ b/protocols/Steam/src/Steam/authorization.h @@ -77,7 +77,7 @@ namespace SteamWebApi ptrA(mir_urlEncode(authResult->captcha_text.c_str())), timestamp); - HttpRequest request(hConnection, REQUEST_POST, STEAM_COM_URL "/mobilelogin/dologin"); + SecureHttpRequest request(hConnection, REQUEST_POST, STEAM_COM_URL "/mobilelogin/dologin"); request.AddHeader("Content-Type", "application/x-www-form-urlencoded"); request.SetData(data, strlen(data)); diff --git a/protocols/Steam/src/Steam/avatar.h b/protocols/Steam/src/Steam/avatar.h new file mode 100644 index 0000000000..3fbccaca99 --- /dev/null +++ b/protocols/Steam/src/Steam/avatar.h @@ -0,0 +1,53 @@ +#ifndef _STEAM_AVATAR_H_ +#define _STEAM_AVATAR_H_ + +namespace SteamWebApi +{ + class AvatarApi : public BaseApi + { + public: + + class Avatar : public Result + { + friend AvatarApi; + + private: + size_t size; + BYTE *data; + + public: + Avatar() : size(0), data(NULL) { } + ~Avatar() + { + if (data != NULL) + mir_free(data); + } + + size_t GetDataSize() const { return size; } + const BYTE * GetData() const { return data; } + }; + + static void GetAvatar(HANDLE hConnection, const char *avatarUrl, Avatar *avatar) + { + avatar->success = false; + + HttpRequest request(hConnection, REQUEST_GET, avatarUrl); + + mir_ptr response(request.Send()); + if (!response) + return; + + if ((avatar->status = (HTTP_STATUS)response->resultCode) != HTTP_STATUS_OK) + return; + + avatar->size = response->dataLength; + avatar->data = (BYTE*)mir_alloc(avatar->size); + memcpy(avatar->data, response->pData, avatar->size); + + avatar->success = true; + } + }; +} + + +#endif //_STEAM_AVATAR_H_ \ No newline at end of file diff --git a/protocols/Steam/src/Steam/friend.h b/protocols/Steam/src/Steam/friend.h index 23ce23d319..4f95db4cce 100644 --- a/protocols/Steam/src/Steam/friend.h +++ b/protocols/Steam/src/Steam/friend.h @@ -52,7 +52,7 @@ namespace SteamWebApi { summaries->success = false; - HttpRequest request(hConnection, REQUEST_GET, STEAM_API_URL "/ISteamUserOAuth/GetUserSummaries/v0001"); + SecureHttpRequest request(hConnection, REQUEST_GET, STEAM_API_URL "/ISteamUserOAuth/GetUserSummaries/v0001"); request.AddParameter("access_token", token); request.AddParameter("steamids", steamIds); diff --git a/protocols/Steam/src/Steam/friend_list.h b/protocols/Steam/src/Steam/friend_list.h index c5c529a0b9..02faee7ef1 100644 --- a/protocols/Steam/src/Steam/friend_list.h +++ b/protocols/Steam/src/Steam/friend_list.h @@ -22,7 +22,7 @@ namespace SteamWebApi { friendList->success = false; - HttpRequest request(hConnection, REQUEST_GET, STEAM_API_URL "/ISteamUserOAuth/GetFriendList/v0001"); + SecureHttpRequest request(hConnection, REQUEST_GET, STEAM_API_URL "/ISteamUserOAuth/GetFriendList/v0001"); request.AddParameter("access_token", token); request.AddParameter("steamid", steamId); diff --git a/protocols/Steam/src/Steam/login.h b/protocols/Steam/src/Steam/login.h index e4d748313a..16e5708327 100644 --- a/protocols/Steam/src/Steam/login.h +++ b/protocols/Steam/src/Steam/login.h @@ -29,7 +29,7 @@ namespace SteamWebApi char data[128]; mir_snprintf(data, SIZEOF(data), "access_token=%s", token); - HttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Logon/v0001"); + SecureHttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Logon/v0001"); request.AddHeader("Content-Type", "application/x-www-form-urlencoded"); request.SetData(data, strlen(data)); @@ -65,7 +65,7 @@ namespace SteamWebApi data.AppendFormat("access_token=%s", token); data.AppendFormat("&umqid=%s", sessionId); - HttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Logoff/v0001"); + SecureHttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Logoff/v0001"); request.AddHeader("Content-Type", "application/x-www-form-urlencoded"); request.SetData(data.GetBuffer(), data.GetLength()); diff --git a/protocols/Steam/src/Steam/message.h b/protocols/Steam/src/Steam/message.h index bc3bd8243b..389f50b13e 100644 --- a/protocols/Steam/src/Steam/message.h +++ b/protocols/Steam/src/Steam/message.h @@ -30,7 +30,7 @@ namespace SteamWebApi sessionId, state); - HttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Message/v0001"); + SecureHttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Message/v0001"); request.AddHeader("Content-Type", "application/x-www-form-urlencoded"); request.SetData(data, strlen(data)); @@ -56,7 +56,7 @@ namespace SteamWebApi steamId, ptrA(mir_urlEncode(text))); - HttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Message/v0001"); + SecureHttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Message/v0001"); request.AddHeader("Content-Type", "application/x-www-form-urlencoded"); request.SetData(data, strlen(data)); @@ -92,7 +92,7 @@ namespace SteamWebApi sessionId, steamId); - HttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Message/v0001"); + SecureHttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Message/v0001"); request.AddHeader("Content-Type", "application/x-www-form-urlencoded"); request.SetData(data, strlen(data)); diff --git a/protocols/Steam/src/Steam/poll.h b/protocols/Steam/src/Steam/poll.h index c94551e3e9..6225b5027f 100644 --- a/protocols/Steam/src/Steam/poll.h +++ b/protocols/Steam/src/Steam/poll.h @@ -86,7 +86,7 @@ namespace SteamWebApi char data[512]; mir_snprintf(data, SIZEOF(data), "access_token=%s&umqid=%s&message=%u", token, sessionId, messageId); - HttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Poll/v0001"); + SecureHttpRequest request(hConnection, REQUEST_POST, STEAM_API_URL "/ISteamWebUserPresenceOAuth/Poll/v0001"); request.AddHeader("Content-Type", "application/x-www-form-urlencoded"); request.SetData(data, strlen(data)); request.SetTimeout(90000); // may need to encrease timeout diff --git a/protocols/Steam/src/Steam/rsa_key.h b/protocols/Steam/src/Steam/rsa_key.h index 60efe6ee47..0c56cc26e9 100644 --- a/protocols/Steam/src/Steam/rsa_key.h +++ b/protocols/Steam/src/Steam/rsa_key.h @@ -1,5 +1,5 @@ -#ifndef _STEAM_CRYPTO_H_ -#define _STEAM_CRYPTO_H_ +#ifndef _STEAM_RSA_KEY_H_ +#define _STEAM_RSA_KEY_H_ namespace SteamWebApi { @@ -28,7 +28,7 @@ namespace SteamWebApi ptrA base64Username(mir_urlEncode(ptrA(mir_utf8encodeW(username)))); - HttpRequest request(hConnection, REQUEST_GET, STEAM_COM_URL "/mobilelogin/getrsakey"); + SecureHttpRequest request(hConnection, REQUEST_GET, STEAM_COM_URL "/mobilelogin/getrsakey"); request.AddParameter("username", (char*)base64Username); mir_ptr response(request.Send()); @@ -59,4 +59,4 @@ namespace SteamWebApi } -#endif //_STEAM_CRYPTO_H_ \ No newline at end of file +#endif //_STEAM_RSA_KEY_H_ \ No newline at end of file diff --git a/protocols/Steam/src/Steam/search.h b/protocols/Steam/src/Steam/search.h index dc6f6c0487..1f7f5fc020 100644 --- a/protocols/Steam/src/Steam/search.h +++ b/protocols/Steam/src/Steam/search.h @@ -41,7 +41,7 @@ namespace SteamWebApi // todo: may need to load all results // 15 first at now - HttpRequest request(hConnection, REQUEST_GET, STEAM_API_URL "/ISteamUserOAuth/Search/v0001"); + SecureHttpRequest request(hConnection, REQUEST_GET, STEAM_API_URL "/ISteamUserOAuth/Search/v0001"); request.AddParameter("access_token", token); request.AddParameter("keywords", ptrA(mir_urlEncode(text))); request.AddParameter("offset=0&count=15&targets=users&fields=all"); diff --git a/protocols/Steam/src/Steam/steam.h b/protocols/Steam/src/Steam/steam.h index 8ff9a645d2..603fc877fa 100644 --- a/protocols/Steam/src/Steam/steam.h +++ b/protocols/Steam/src/Steam/steam.h @@ -37,5 +37,6 @@ namespace SteamWebApi #include "Steam\poll.h" #include "Steam\message.h" #include "Steam\search.h" +#include "Steam\avatar.h" #endif //_STEAM_H_ \ No newline at end of file diff --git a/protocols/Steam/src/common.h b/protocols/Steam/src/common.h index 7c0a9a9abe..436d48239d 100644 --- a/protocols/Steam/src/common.h +++ b/protocols/Steam/src/common.h @@ -11,7 +11,7 @@ #include #include #include -//#include +#include #include #include #include @@ -25,8 +25,6 @@ #include #include -//#include - #include "resource.h" #include "version.h" diff --git a/protocols/Steam/src/http_request.h b/protocols/Steam/src/http_request.h index 9425e8223c..8ba2ebffa1 100644 --- a/protocols/Steam/src/http_request.h +++ b/protocols/Steam/src/http_request.h @@ -29,7 +29,7 @@ public: dataLength = 0; headersCount = 0; szResultDescr = NULL; - flags = NLHRF_HTTP11 | NLHRF_SSL; + flags = NLHRF_HTTP11; requestType = request; m_hNetlibUser = hNetlibUser; @@ -136,4 +136,11 @@ public: HttpPostRequest(HANDLE hNetlibUser, LPCSTR url) : HttpRequest(hNetlibUser, REQUEST_POST, url) { } };*/ +class SecureHttpRequest : public HttpRequest +{ +public: + SecureHttpRequest(HANDLE hNetlibUser, int request, LPCSTR url) + : HttpRequest(hNetlibUser, request, url) { flags = NLHRF_HTTP11 | NLHRF_SSL; } +}; + #endif //_HTTP_REQUEST_H_ \ No newline at end of file diff --git a/protocols/Steam/src/steam.h b/protocols/Steam/src/steam.h deleted file mode 100644 index f95e7f9e4e..0000000000 --- a/protocols/Steam/src/steam.h +++ /dev/null @@ -1,31 +0,0 @@ -#ifndef _STEAM_H_ -#define _STEAM_H_ - -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "resource.h" -#include "version.h" - -#define MODULE "Steam" - -class CSteamProto; -extern HINSTANCE g_hInstance; - -#include "steam_proto.h" - -#endif //_STEAM_H_ \ No newline at end of file diff --git a/protocols/Steam/src/steam_account.cpp b/protocols/Steam/src/steam_account.cpp index 4dd80088a4..f7d86e7c68 100644 --- a/protocols/Steam/src/steam_account.cpp +++ b/protocols/Steam/src/steam_account.cpp @@ -150,7 +150,7 @@ void CSteamProto::LogInThread(void* param) if (loginResult.GetStatus() == HTTP_STATUS_UNAUTHORIZED) { delSetting("TokenSecret"); - delSetting("Cookie"); + //delSetting("Cookie"); } // set status to offline @@ -166,40 +166,8 @@ void CSteamProto::LogInThread(void* param) m_iStatus = m_iDesiredStatus; ProtoBroadcastAck(NULL, ACKTYPE_STATUS, ACKRESULT_SUCCESS, (HANDLE)ID_STATUS_CONNECTING, m_iDesiredStatus); - // get contact list - SteamWebApi::FriendListApi::FriendList friendList; - SteamWebApi::FriendListApi::Load(m_hNetlibUser, token, loginResult.GetSteamId(), &friendList); - - if (friendList.IsSuccess()) - { - CMStringA newContacts; - for (int i = 0; i < friendList.GetItemCount(); i++) - { - const char * steamId = friendList.GetAt(i); - if (!FindContact(steamId)) - { - if (newContacts.IsEmpty()) - newContacts.Append(steamId); - else - newContacts.AppendFormat(",%s", steamId); - } - } - - if (!newContacts.IsEmpty()) - { - SteamWebApi::FriendApi::Summaries summaries; - SteamWebApi::FriendApi::LoadSummaries(m_hNetlibUser, token, newContacts, &summaries); - - if (summaries.IsSuccess()) - { - for (int i = 0; i < summaries.GetItemCount(); i++) - { - const SteamWebApi::FriendApi::Summary *summary = summaries.GetAt(i); - AddContact(summary); - } - } - } - } + // load contact list + LoadContactList(); // start pooling thread if (m_hPollingThread == NULL && !m_bTerminated) diff --git a/protocols/Steam/src/steam_avatars.cpp b/protocols/Steam/src/steam_avatars.cpp new file mode 100644 index 0000000000..b009e1c32d --- /dev/null +++ b/protocols/Steam/src/steam_avatars.cpp @@ -0,0 +1,102 @@ +#include "common.h" + +wchar_t * CSteamProto::GetAvatarFilePath(MCONTACT hContact) +{ + TCHAR path[MAX_PATH]; + mir_sntprintf(path, SIZEOF(path), _T("%s\\%S"), VARST(_T("%miranda_avatarcache%")), m_szModuleName); + + DWORD dwAttributes = GetFileAttributes(path); + if (dwAttributes == 0xffffffff || (dwAttributes & FILE_ATTRIBUTE_DIRECTORY) == 0) + CallService(MS_UTILS_CREATEDIRTREET, 0, (LPARAM)path); + + ptrW steamId(db_get_wsa(hContact, m_szModuleName, "SteamID")); + if (hContact != NULL) + mir_sntprintf(path, MAX_PATH, _T("%s\\%s.jpg"), path, steamId); + else if (steamId != NULL) + mir_sntprintf(path, MAX_PATH, _T("%s\\%s avatar.jpg"), path, steamId); + else + return NULL; + + return mir_wstrdup(path); +} + +INT_PTR CSteamProto::GetAvatarInfo(WPARAM, LPARAM lParam) +{ + PROTO_AVATAR_INFORMATIONW *pai = (PROTO_AVATAR_INFORMATIONW *)lParam; + + if (ptrA(getStringA(pai->hContact, "AvatarUrl"))) + return GAIR_NOAVATAR; + + ptrA steamId(getStringA(pai->hContact, "SteamID")); + if (steamId) + { + ptrW path(GetAvatarFilePath(pai->hContact)); + if (path && !_waccess(path, 0)) + { + wcsncpy(pai->filename, path, SIZEOF(pai->filename)); + pai->format = PA_FORMAT_JPEG; + return GAIR_SUCCESS; + } + } + + return GAIR_NOAVATAR; +} + +INT_PTR CSteamProto::GetAvatarCaps(WPARAM wParam, LPARAM lParam) +{ + switch (wParam) + { + case AF_MAXSIZE: + { + POINT *size = (POINT*)lParam; + if (size) + { + size->x = 184; + size->y = 184; + } + } + break; + + case AF_PROPORTION: + return PIP_SQUARE; + + case AF_FORMATSUPPORTED: + return lParam == PA_FORMAT_JPEG; + + case AF_ENABLED: + return 1; + + /*case AF_DONTNEEDDELAYS: + return 1;*/ + + /*case AF_MAXFILESIZE: + // server accepts images of 32000 bytees, not bigger + return 32000;*/ + + /*case AF_DELAYAFTERFAIL: + // do not request avatar again if server gave an error + return 1;// * 60 * 60 * 1000; // one hour*/ + + /*case AF_FETCHIFPROTONOTVISIBLE: + case AF_FETCHIFCONTACTOFFLINE: + // avatars can be fetched all the time (server only operation) + return 1;*/ + } + + return 0; +} + +INT_PTR CSteamProto::GetMyAvatar(WPARAM wParam, LPARAM lParam) +{ + if (!wParam) + return -2; + + ptrW path(GetAvatarFilePath(NULL)); + if (path && !_waccess(path, 0)) + { + wcsncpy((wchar_t *)wParam, path, (int)lParam); + return 0; + } + + return -1; +} \ No newline at end of file diff --git a/protocols/Steam/src/steam_contacts.cpp b/protocols/Steam/src/steam_contacts.cpp index 3aba838dfc..8433425b33 100644 --- a/protocols/Steam/src/steam_contacts.cpp +++ b/protocols/Steam/src/steam_contacts.cpp @@ -18,30 +18,90 @@ void CSteamProto::SetAllContactsStatus(WORD status) } } +MCONTACT CSteamProto::FindContact(const char *steamId) +{ + MCONTACT hContact = NULL; + + EnterCriticalSection(&this->contact_search_lock); + + for (hContact = db_find_first(this->m_szModuleName); hContact; hContact = db_find_next(hContact, this->m_szModuleName)) + { + ptrA cSteamId(db_get_sa(hContact, this->m_szModuleName, "SteamID")); + if (!lstrcmpA(cSteamId, steamId)) + break; + } + + LeaveCriticalSection(&this->contact_search_lock); + + return hContact; +} + void CSteamProto::UpdateContact(MCONTACT hContact, const SteamWebApi::FriendApi::Summary *contact) { + // only if contact is in contact list if (hContact && !FindContact(contact->GetSteamId())) return; // set common data setWString(hContact, "Nick", contact->GetNickname()); - setWord(hContact, "Status", SteamToMirandaStatus(contact->GetState())); setString(hContact, "Homepage", contact->GetHomepage()); - setDword(hContact, "LastEventDateTS", contact->GetLastEvent()); + // only for contacts + if (hContact) + { + setWord(hContact, "Status", SteamToMirandaStatus(contact->GetState())); + setDword(hContact, "LastEventDateTS", contact->GetLastEvent()); + } // set name ptrW realname(mir_wstrdup(contact->GetRealname())); const wchar_t *p = wcschr(realname, ' '); if (p == NULL) + { setWString(hContact, "FirstName", realname); + delSetting(hContact, "LastName"); + } else { int length = p - (wchar_t*)realname; realname[length] = '\0'; - setWString(hContact, "LastName", realname); + setWString(hContact, "FirstName", realname); setWString(hContact, "LastName", p + 1); } + // avatar + ptrA oldAvatar(getStringA("AvatarUrl")); + if (lstrcmpiA(oldAvatar, contact->GetAvatarUrl())) + { + // todo: need to place in thread + SteamWebApi::AvatarApi::Avatar avatar; + SteamWebApi::AvatarApi::GetAvatar(m_hNetlibUser, contact->GetAvatarUrl(), &avatar); + + if (avatar.IsSuccess() && avatar.GetDataSize() > 0) + { + ptrW avatarPath(GetAvatarFilePath(hContact)); + FILE *fp = _wfopen(avatarPath, L"wb"); + if (fp) + { + fwrite(avatar.GetData(), sizeof(char), avatar.GetDataSize(), fp); + fclose(fp); + + if (hContact) + { + PROTO_AVATAR_INFORMATIONW pai = { sizeof(pai) }; + pai.format = PA_FORMAT_JPEG; + pai.hContact = hContact; + wcscpy(pai.filename, avatarPath); + + ProtoBroadcastAck(hContact, ACKTYPE_AVATAR, ACKRESULT_SUCCESS, (HANDLE)&pai, 0); + } + else + CallService(MS_AV_SETMYAVATART, (WPARAM)m_szModuleName, (LPARAM)avatarPath); + } + + setString("AvatarUrl", contact->GetAvatarUrl()); + } + } + // set country const char *isoCode = contact->GetCountryCode(); if (!lstrlenA(isoCode)) @@ -66,36 +126,23 @@ void CSteamProto::UpdateContactsThread(void *arg) if (!summarues.IsSuccess()) return; - for (int i = 0; i < summarues.GetItemCount(); i++) + for (size_t i = 0; i < summarues.GetItemCount(); i++) { const SteamWebApi::FriendApi::Summary *contact = summarues.GetAt(i); - MCONTACT hContact = this->FindContact(contact->GetSteamId()); - if (!hContact) + if (IsMe(contact->GetSteamId())) + UpdateContact(NULL, contact); + else { - UpdateContact(hContact, contact); + MCONTACT hContact = this->FindContact(contact->GetSteamId()); + if (!hContact) + { + UpdateContact(hContact, contact); + } } } } -MCONTACT CSteamProto::FindContact(const char *steamId) -{ - MCONTACT hContact = NULL; - - EnterCriticalSection(&this->contact_search_lock); - - for (hContact = db_find_first(this->m_szModuleName); hContact; hContact = db_find_next(hContact, this->m_szModuleName)) - { - ptrA cSteamId(db_get_sa(hContact, this->m_szModuleName, "SteamID")); - if (!lstrcmpA(cSteamId, steamId)) - break; - } - - LeaveCriticalSection(&this->contact_search_lock); - - return hContact; -} - MCONTACT CSteamProto::AddContact(const SteamWebApi::FriendApi::Summary *contact) { MCONTACT hContact = this->FindContact(contact->GetSteamId()); @@ -122,6 +169,46 @@ MCONTACT CSteamProto::AddContact(const SteamWebApi::FriendApi::Summary *contact) return hContact; } +void CSteamProto::LoadContactList() +{ + ptrA token(getStringA("TokenSecret")); + ptrA steamId(getStringA("SteamID")); + + SteamWebApi::FriendListApi::FriendList friendList; + SteamWebApi::FriendListApi::Load(m_hNetlibUser, token, steamId, &friendList); + + if (friendList.IsSuccess()) + { + CMStringA newContacts; + for (size_t i = 0; i < friendList.GetItemCount(); i++) + { + const char * steamId = friendList.GetAt(i); + if (!FindContact(steamId)) + { + if (newContacts.IsEmpty()) + newContacts.Append(steamId); + else + newContacts.AppendFormat(",%s", steamId); + } + } + + if (!newContacts.IsEmpty()) + { + SteamWebApi::FriendApi::Summaries summaries; + SteamWebApi::FriendApi::LoadSummaries(m_hNetlibUser, token, newContacts, &summaries); + + if (summaries.IsSuccess()) + { + for (size_t i = 0; i < summaries.GetItemCount(); i++) + { + const SteamWebApi::FriendApi::Summary *summary = summaries.GetAt(i); + AddContact(summary); + } + } + } + } +} + void CSteamProto::SearchByIdThread(void* arg) { ptrW steamIdW((wchar_t*)arg); @@ -204,7 +291,7 @@ void CSteamProto::SearchByNameThread(void* arg) return; } - for (int i = 0; i < summarues.GetItemCount(); i++) + for (size_t i = 0; i < summarues.GetItemCount(); i++) { const SteamWebApi::FriendApi::Summary *contact = summarues.GetAt(i); diff --git a/protocols/Steam/src/steam_proto.cpp b/protocols/Steam/src/steam_proto.cpp index 1a7f7f2b7b..94e592e2fb 100644 --- a/protocols/Steam/src/steam_proto.cpp +++ b/protocols/Steam/src/steam_proto.cpp @@ -29,6 +29,12 @@ CSteamProto::CSteamProto(const char* protoName, const TCHAR* userName) : Skin_AddIcon(&sid); SetAllContactsStatus(ID_STATUS_OFFLINE); + + // Avatar API + this->CreateProtoService(PS_GETAVATARINFOT, &CSteamProto::GetAvatarInfo); + this->CreateProtoService(PS_GETAVATARCAPS, &CSteamProto::GetAvatarCaps); + this->CreateProtoService(PS_GETMYAVATART, &CSteamProto::GetMyAvatar); + //this->CreateProtoService(PS_SETMYAVATART, &CSteamProto::SetMyAvatar); } CSteamProto::~CSteamProto() @@ -98,6 +104,8 @@ DWORD_PTR __cdecl CSteamProto:: GetCaps(int type, MCONTACT hContact) return PF1_IM | PF1_BASICSEARCH | PF1_SEARCHBYNAME; case PFLAGNUM_2: return PF2_ONLINE; + case PFLAGNUM_4: + return PF4_AVATARS; case PFLAG_UNIQUEIDTEXT: return (DWORD_PTR)Translate("SteamID"); case PFLAG_UNIQUEIDSETTING: diff --git a/protocols/Steam/src/steam_proto.h b/protocols/Steam/src/steam_proto.h index 1e2bcdd6a6..beef8660fa 100644 --- a/protocols/Steam/src/steam_proto.h +++ b/protocols/Steam/src/steam_proto.h @@ -120,6 +120,8 @@ protected: MCONTACT FindContact(const char *steamId); MCONTACT AddContact(const SteamWebApi::FriendApi::Summary *contact); + + void LoadContactList(); void __cdecl SearchByIdThread(void*); void __cdecl SearchByNameThread(void*); @@ -128,6 +130,14 @@ protected: void __cdecl SendMessageThread(void*); void __cdecl SendTypingThread(void*); + // avatars + wchar_t * GetAvatarFilePath(MCONTACT hContact); + + INT_PTR __cdecl GetAvatarInfo(WPARAM, LPARAM); + INT_PTR __cdecl GetAvatarCaps(WPARAM, LPARAM); + INT_PTR __cdecl GetMyAvatar(WPARAM, LPARAM); + INT_PTR __cdecl SetMyAvatar(WPARAM, LPARAM); + //events int OnModulesLoaded(WPARAM, LPARAM); int OnPreShutdown(WPARAM, LPARAM); diff --git a/protocols/Steam/src/steam_thread.cpp b/protocols/Steam/src/steam_thread.cpp index a4adad5ba8..75c60577fd 100644 --- a/protocols/Steam/src/steam_thread.cpp +++ b/protocols/Steam/src/steam_thread.cpp @@ -8,7 +8,7 @@ void CSteamProto::PollStatus(const char *token, const char *sessionId, UINT32 me return; CMStringA updatedIds; - for (int i = 0; i < pollResult->GetItemCount(); i++) + for (size_t i = 0; i < pollResult->GetItemCount(); i++) { const SteamWebApi::PollApi::PoolItem *item = pollResult->GetAt(i); switch (item->GetType()) @@ -66,30 +66,19 @@ void CSteamProto::PollStatus(const char *token, const char *sessionId, UINT32 me const wchar_t *nickname = state->GetNickname(); if (IsMe(steamId)) - { - const wchar_t *oldNickname = getWStringA("Nick"); - if (lstrcmp(oldNickname, nickname) && lstrlen(nickname)) - setWString("Nick", nickname); - SetStatus(status); - } else { MCONTACT hContact = FindContact(steamId); if (hContact) - { - const wchar_t *oldNickname = getWStringA(hContact, "Nick"); - if (lstrcmp(oldNickname, nickname) && lstrlen(nickname)) - setWString(hContact, "Nick", nickname); - SetContactStatus(hContact, status); - } - if (updatedIds.IsEmpty()) - updatedIds.Append(steamId); - else - updatedIds.AppendFormat(",%s", steamId); } + + if (updatedIds.IsEmpty()) + updatedIds.Append(steamId); + else + updatedIds.AppendFormat(",%s", steamId); } break; } -- cgit v1.2.3