/* Miranda SmileyAdd Plugin Copyright (C) 2005 - 2012 Boris Krasnovskiy All Rights Reserved Copyright (C) 2003 - 2004 Rein-Peter de Boer This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation version 2 of the License. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "stdafx.h" static mir_cs csWndList; // type definitions struct MsgWndData : public MZeroedObject { CSrmmBaseDialog *pDlg; char *szProto; MsgWndData(CSrmmBaseDialog *p) : pDlg(p) { szProto = Proto_GetBaseAccountName(DecodeMetaContact(pDlg->m_hContact)); } void CreateSmileyButton(void) { SmileyPackType *SmileyPack = FindSmileyPack(szProto, pDlg->m_hContact); bool doSmileyButton = SmileyPack && SmileyPack->VisibleSmileyCount() != 0; if (szProto) { INT_PTR cap = CallProtoService(szProto, PS_GETCAPS, PFLAGNUM_1, 0); doSmileyButton &= ((cap & (PF1_IMSEND | PF1_CHAT)) != 0); } BBButton bbd = {}; bbd.pszModuleName = MODULENAME; if (!doSmileyButton) bbd.bbbFlags = BBBF_DISABLED; Srmm_SetButtonState(pDlg->m_hContact, &bbd); } }; static OBJLIST g_MsgWndList(10, HandleKeySortT); // find the dialog info in the stored list static MsgWndData* IsMsgWnd(HWND hwnd) { mir_cslock lck(csWndList); for (auto &it : g_MsgWndList) if (it->pDlg->GetHwnd() == hwnd) return it; return nullptr; } ///////////////////////////////////////////////////////////////////////////////////////// // toolbar button processing int SmileyButtonCreate(WPARAM, LPARAM) { // create a hotkey for the button first HOTKEYDESC desc = {}; desc.pszName = "srmm_smileyadd"; desc.szSection.a = BB_HK_SECTION; desc.szDescription.a = LPGEN("Smiley selector"); desc.DefHotKey = HOTKEYCODE(HOTKEYF_ALT, 'E'); desc.lParam = LPARAM(g_plugin.getInst()); g_plugin.addHotkey(&desc); BBButton bbd = {}; bbd.pszModuleName = MODULENAME; bbd.pwszTooltip = LPGENW("Show smiley selection window"); bbd.dwDefPos = 31; bbd.hIcon = IcoLib_GetIconHandle("SmileyAdd_ButtonSmiley"); bbd.bbbFlags = BBBF_ISIMBUTTON | BBBF_ISCHATBUTTON | BBBF_NOREADONLY; bbd.pszHotkey = desc.pszName; g_plugin.addButton(&bbd); return 0; } int SmileyButtonPressed(WPARAM, LPARAM lParam) { CustomButtonClickData *pcbc = (CustomButtonClickData*)lParam; if (mir_strcmp(pcbc->pszModule, MODULENAME)) return 0; MsgWndData *dat = IsMsgWnd(pcbc->hwndFrom); if (dat == nullptr) return 0; SmileyToolWindowParam *stwp = new SmileyToolWindowParam; stwp->pSmileyPack = FindSmileyPack(dat->szProto, dat->pDlg->m_hContact); stwp->hWndParent = pcbc->hwndFrom; stwp->hWndTarget = dat->pDlg->GetInput(); stwp->targetMessage = EM_REPLACESEL; stwp->targetWParam = TRUE; stwp->direction = 0; stwp->xPosition = pcbc->pt.x; stwp->yPosition = pcbc->pt.y; mir_forkThread(SmileyToolThread, stwp); return 0; } ///////////////////////////////////////////////////////////////////////////////////////// // window hook static HWND checkRichEdit(HWND hwnd) { wchar_t wszClass[200]; if (GetClassNameW(hwnd, wszClass, _countof(wszClass))) if (!wcsicmp(wszClass, L"RICHEDIT50W")) return hwnd; return nullptr; } static int MsgDlgHook(WPARAM uType, LPARAM lParam) { auto *pDlg = (CSrmmBaseDialog *)lParam; auto hwndLog = checkRichEdit(pDlg->log()->GetHwnd()); auto hwndInput = checkRichEdit(pDlg->GetInput()); switch (uType) { case MSG_WINDOW_EVT_OPENING: { MsgWndData *msgwnd = new MsgWndData(pDlg); msgwnd->CreateSmileyButton(); mir_cslock lck(csWndList); g_MsgWndList.insert(msgwnd); } SetRichOwnerCallback(pDlg->GetHwnd(), hwndInput, hwndLog); if (hwndLog) SetRichCallback(hwndLog, pDlg->m_hContact, false, false); if (hwndInput) SetRichCallback(hwndInput, pDlg->m_hContact, false, false); break; case MSG_WINDOW_EVT_OPEN: SetRichOwnerCallback(pDlg->GetHwnd(), hwndInput, hwndLog); if (hwndLog) SetRichCallback(hwndLog, pDlg->m_hContact, true, true); if (hwndInput) { SetRichCallback(hwndInput, pDlg->m_hContact, true, true); SendMessage(hwndInput, WM_REMAKERICH, 0, 0); } break; case MSG_WINDOW_EVT_CLOSE: CloseRichOwnerCallback(pDlg->GetHwnd()); mir_cslock lck(csWndList); g_MsgWndList.remove((MsgWndData *)&pDlg); } return 0; } void InstallDialogBoxHook(void) { HookEvent(ME_MSG_WINDOWEVENT, MsgDlgHook); } void RemoveDialogBoxHook(void) { g_MsgWndList.destroy(); }