summaryrefslogtreecommitdiff
path: root/protocols
diff options
context:
space:
mode:
authorGeorge Hazan <george.hazan@gmail.com>2024-09-22 18:51:04 +0300
committerGeorge Hazan <george.hazan@gmail.com>2024-09-22 18:51:04 +0300
commitea62db13f9ea4b3b8bd3238de83f18ddd2af0be2 (patch)
tree4cd309f8205b06d3eb856193452d47d254c584e5 /protocols
parentf7ec875eee3960f5883448d536b10c2830f15057 (diff)
fixes #4689 (SkypeWeb: кривое форматирование текста)
Diffstat (limited to 'protocols')
-rw-r--r--protocols/SkypeWeb/src/requests/messages.h37
-rw-r--r--protocols/SkypeWeb/src/skype_chatrooms.cpp5
-rw-r--r--protocols/SkypeWeb/src/skype_files.cpp10
-rw-r--r--protocols/SkypeWeb/src/skype_messages.cpp87
-rw-r--r--protocols/SkypeWeb/src/skype_utils.cpp66
-rw-r--r--protocols/SkypeWeb/src/skype_utils.h2
6 files changed, 135 insertions, 72 deletions
diff --git a/protocols/SkypeWeb/src/requests/messages.h b/protocols/SkypeWeb/src/requests/messages.h
index 378c8d8549..345ce2e662 100644
--- a/protocols/SkypeWeb/src/requests/messages.h
+++ b/protocols/SkypeWeb/src/requests/messages.h
@@ -18,43 +18,6 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
#ifndef _SKYPE_REQUEST_MESSAGES_H_
#define _SKYPE_REQUEST_MESSAGES_H_
-struct SendMessageParam
-{
- MCONTACT hContact;
- uint32_t hMessage;
-};
-
-struct SendMessageRequest : public AsyncHttpRequest
-{
- SendMessageRequest(const char *username, time_t timestamp, const char *message, const char *MessageType = nullptr) :
- AsyncHttpRequest(REQUEST_POST, HOST_DEFAULT, 0, &CSkypeProto::OnMessageSent)
- {
- m_szUrl.AppendFormat("/users/ME/conversations/%s/messages", mir_urlEncode(username).c_str());
-
- JSONNode node;
- node << INT64_PARAM("clientmessageid", timestamp) << CHAR_PARAM("messagetype", MessageType ? MessageType : "Text")
- << CHAR_PARAM("contenttype", "text") << CHAR_PARAM("content", message);
- m_szParam = node.write().c_str();
- }
-};
-
-struct SendActionRequest : public AsyncHttpRequest
-{
- SendActionRequest(const char *username, time_t timestamp, const char *message, CSkypeProto *ppro) :
- AsyncHttpRequest(REQUEST_POST, HOST_DEFAULT, 0, &CSkypeProto::OnMessageSent)
- {
- m_szUrl.AppendFormat("/users/ME/conversations/%s/messages", mir_urlEncode(username).c_str());
-
- CMStringA content;
- content.AppendFormat("%s %s", ppro->m_szSkypename.c_str(), message);
-
- JSONNode node;
- node << INT64_PARAM("clientmessageid", timestamp) << CHAR_PARAM("messagetype", "RichText") << CHAR_PARAM("contenttype", "text")
- << CHAR_PARAM("content", content) << INT_PARAM("skypeemoteoffset", ppro->m_szSkypename.GetLength() + 1);
- m_szParam = node.write().c_str();
- }
-};
-
struct SendTypingRequest : public AsyncHttpRequest
{
SendTypingRequest(const char *username, int iState) :
diff --git a/protocols/SkypeWeb/src/skype_chatrooms.cpp b/protocols/SkypeWeb/src/skype_chatrooms.cpp
index e5b75a7131..de34a66fa8 100644
--- a/protocols/SkypeWeb/src/skype_chatrooms.cpp
+++ b/protocols/SkypeWeb/src/skype_chatrooms.cpp
@@ -331,8 +331,9 @@ void CSkypeProto::SendChatMessage(SESSION_INFO *si, const wchar_t *tszMessage)
return;
T2Utf chat_id(si->ptszID);
- ptrA szMessage(mir_utf8encodeW(tszMessage));
- rtrim(szMessage);
+ CMStringA szMessage(ptrA(mir_utf8encodeW(tszMessage)));
+ szMessage.TrimRight();
+ AddBbcodes(szMessage);
if (strncmp(szMessage, "/me ", 4) == 0)
PushRequest(new SendChatActionRequest(chat_id, time(0), szMessage));
diff --git a/protocols/SkypeWeb/src/skype_files.cpp b/protocols/SkypeWeb/src/skype_files.cpp
index 721186434a..24f279a600 100644
--- a/protocols/SkypeWeb/src/skype_files.cpp
+++ b/protocols/SkypeWeb/src/skype_files.cpp
@@ -232,13 +232,13 @@ void CSkypeProto::OnASMObjectUploaded(MHttpResponse *response, AsyncHttpRequest
tinyxml2::XMLPrinter printer(0, true);
doc.Print(&printer);
- SendMessageParam *param = new SendMessageParam();
- param->hContact = fup->hContact;
- Utils_GetRandom(&param->hMessage, sizeof(param->hMessage));
- param->hMessage &= ~0x80000000;
+ uint32_t hMessage;
+ Utils_GetRandom(&hMessage, sizeof(hMessage));
+ hMessage &= ~0x80000000;
auto *pReq = new SendFileRequest(fup, getId(fup->hContact), printer.CStr());
- pReq->pUserInfo = param;
+ pReq->hContact = fup->hContact;
+ pReq->pUserInfo = (HANDLE)hMessage;
PushRequest(pReq);
ProtoBroadcastAck(fup->hContact, ACKTYPE_FILE, ACKRESULT_SUCCESS, (HANDLE)fup);
diff --git a/protocols/SkypeWeb/src/skype_messages.cpp b/protocols/SkypeWeb/src/skype_messages.cpp
index e99d5fcdb1..6ec31d0df5 100644
--- a/protocols/SkypeWeb/src/skype_messages.cpp
+++ b/protocols/SkypeWeb/src/skype_messages.cpp
@@ -17,40 +17,44 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
#include "stdafx.h"
-/* MESSAGE SENDING */
+/////////////////////////////////////////////////////////////////////////////////////////
+// MESSAGE SENDING
-// outcoming message flow
-int CSkypeProto::SendMsg(MCONTACT hContact, MEVENT, const char *szMessage)
+struct SendMessageRequest : public AsyncHttpRequest
{
- if (!IsOnline())
- return -1;
-
- SendMessageParam *param = new SendMessageParam();
- param->hContact = hContact;
- Utils_GetRandom(&param->hMessage, sizeof(param->hMessage));
- param->hMessage &= ~0x80000000;
-
- CMStringA id(getId(hContact));
-
- AsyncHttpRequest *pReq;
- if (strncmp(szMessage, "/me ", 4) == 0)
- pReq = new SendActionRequest(id, param->hMessage, &szMessage[4], this);
- else
- pReq = new SendMessageRequest(id, param->hMessage, szMessage);
- pReq->pUserInfo = param;
- PushRequest(pReq);
+ SendMessageRequest(const char *username, time_t timestamp, const char *message, const char *MessageType = nullptr) :
+ AsyncHttpRequest(REQUEST_POST, HOST_DEFAULT, 0, &CSkypeProto::OnMessageSent)
+ {
+ m_szUrl.AppendFormat("/users/ME/conversations/%s/messages", mir_urlEncode(username).c_str());
+
+ JSONNode node;
+ node << INT64_PARAM("clientmessageid", timestamp) << CHAR_PARAM("messagetype", MessageType ? MessageType : "Text")
+ << CHAR_PARAM("contenttype", "text") << CHAR_PARAM("content", message);
+ m_szParam = node.write().c_str();
+ }
+};
- mir_cslock lck(m_lckOutMessagesList);
- m_OutMessages.insert((void*)param->hMessage);
- return param->hMessage;
-}
+struct SendActionRequest : public AsyncHttpRequest
+{
+ SendActionRequest(const char *username, time_t timestamp, const char *message, CSkypeProto *ppro) :
+ AsyncHttpRequest(REQUEST_POST, HOST_DEFAULT, 0, &CSkypeProto::OnMessageSent)
+ {
+ m_szUrl.AppendFormat("/users/ME/conversations/%s/messages", mir_urlEncode(username).c_str());
+
+ CMStringA content;
+ content.AppendFormat("%s %s", ppro->m_szSkypename.c_str(), message);
+
+ JSONNode node;
+ node << INT64_PARAM("clientmessageid", timestamp) << CHAR_PARAM("messagetype", "RichText") << CHAR_PARAM("contenttype", "text")
+ << CHAR_PARAM("content", content) << INT_PARAM("skypeemoteoffset", ppro->m_szSkypename.GetLength() + 1);
+ m_szParam = node.write().c_str();
+ }
+};
void CSkypeProto::OnMessageSent(MHttpResponse *response, AsyncHttpRequest *pRequest)
{
- auto *param = (SendMessageParam*)pRequest->pUserInfo;
- MCONTACT hContact = param->hContact;
- HANDLE hMessage = (HANDLE)param->hMessage;
- delete param;
+ MCONTACT hContact = pRequest->hContact;
+ HANDLE hMessage = (HANDLE)pRequest->pUserInfo;
if (response != nullptr) {
if (response->resultCode != 201) {
@@ -69,6 +73,33 @@ void CSkypeProto::OnMessageSent(MHttpResponse *response, AsyncHttpRequest *pRequ
else ProtoBroadcastAck(hContact, ACKTYPE_MESSAGE, ACKRESULT_FAILED, hMessage, (LPARAM)TranslateT("Network error!"));
}
+// outcoming message flow
+int CSkypeProto::SendMsg(MCONTACT hContact, MEVENT, const char *szMessage)
+{
+ if (!IsOnline())
+ return -1;
+
+ uint32_t hMessage;
+ Utils_GetRandom(&hMessage, sizeof(hMessage));
+ hMessage &= ~0x80000000;
+
+ CMStringA str(szMessage);
+ AddBbcodes(str);
+
+ AsyncHttpRequest *pReq;
+ if (strncmp(str, "/me ", 4) == 0)
+ pReq = new SendActionRequest(getId(hContact), hMessage, str.c_str() + 4, this);
+ else
+ pReq = new SendMessageRequest(getId(hContact), hMessage, str);
+ pReq->hContact = hContact;
+ pReq->pUserInfo = (HANDLE)hMessage;
+ PushRequest(pReq);
+
+ mir_cslock lck(m_lckOutMessagesList);
+ m_OutMessages.insert((void*)hMessage);
+ return hMessage;
+}
+
// preparing message/action to be written into db
int CSkypeProto::OnPreCreateMessage(WPARAM, LPARAM lParam)
{
diff --git a/protocols/SkypeWeb/src/skype_utils.cpp b/protocols/SkypeWeb/src/skype_utils.cpp
index 9d37275a69..0866a2cc75 100644
--- a/protocols/SkypeWeb/src/skype_utils.cpp
+++ b/protocols/SkypeWeb/src/skype_utils.cpp
@@ -360,6 +360,26 @@ CMStringW CSkypeProto::RemoveHtml(const CMStringW &data, bool bCheckSS)
m_wstrMoodMessage = wszStatusMsg;
inSS = false;
}
+ else if (m_bUseBBCodes) {
+ bool bEnable = true;
+ if (data[i + 1] == '/') {
+ i++;
+ bEnable = false;
+ }
+
+ switch (data[i + 1]) {
+ case 'b': new_string.Append(bEnable ? L"[b]" : L"[/b]"); break;
+ case 'i': new_string.Append(bEnable ? L"[i]" : L"[/i]"); break;
+ case 'u': new_string.Append(bEnable ? L"[u]" : L"[/u]"); break;
+ case 's': new_string.Append(bEnable ? L"[s]" : L"[/s]"); break;
+ default:
+ if (!wcsncmp(data.c_str() + i + 1, L"pre ", 4))
+ new_string.Append(L"[code]");
+ else if (!wcsncmp(data.c_str() + i + 1, L"pre>", 4))
+ new_string.Append(L"[/code]");
+ break;
+ }
+ }
i = data.Find('>', i);
if (i == -1)
@@ -456,6 +476,52 @@ CMStringW CSkypeProto::RemoveHtml(const CMStringW &data, bool bCheckSS)
return new_string;
}
+void AddBbcodes(CMStringA &str)
+{
+ CMStringA ret;
+
+ for (const char *p = str; *p; p++) {
+ if (*p == '[') {
+ p++;
+ if (!strncmp(p, "b]", 2)) {
+ p++;
+ ret.Append("<b _pre=\"*\" _post=\"*\">");
+ }
+ else if (!strncmp(p, "/b]", 3)) {
+ p += 2;
+ ret.Append("</b>");
+ }
+ else if (!strncmp(p, "i]", 2)) {
+ p++;
+ ret.Append("<i _pre=\"_\" _post=\"_\">");
+ }
+ else if (!strncmp(p, "/i]", 3)) {
+ p += 2;
+ ret.Append("</i>");
+ }
+ else if (!strncmp(p, "s]", 2)) {
+ p++;
+ ret.Append("<s _pre=\"~\" _post=\"~\">");
+ }
+ else if (!strncmp(p, "/s]", 3)) {
+ p += 2;
+ ret.Append("</s>");
+ }
+ else if (!strncmp(p, "code]", 5)) {
+ p += 4;
+ ret.Append("<pre _pre=\"```\" _post=\"```\">");
+ }
+ else if (!strncmp(p, "/code]", 6)) {
+ p += 5;
+ ret.Append("</pre>");
+ }
+ }
+ else ret.AppendChar(*p);
+ }
+
+ str = ret;
+}
+
//////////////////////////////////////////////////////////////////////////////////////////
void Utf32toUtf16(uint32_t c, CMStringW &dest)
diff --git a/protocols/SkypeWeb/src/skype_utils.h b/protocols/SkypeWeb/src/skype_utils.h
index 4a7f28e4c4..718cbc68d4 100644
--- a/protocols/SkypeWeb/src/skype_utils.h
+++ b/protocols/SkypeWeb/src/skype_utils.h
@@ -26,6 +26,8 @@ const wchar_t* GetSkypeNick(const wchar_t *szSkypeId);
CMStringA ParseUrl(const char *url, const char *token);
+void AddBbcodes(CMStringA &str);
+
bool IsPossibleUserType(const char *pszUserId);
CMStringA UrlToSkypeId(const char *url, int *pUserType = nullptr);