From a70382b0e8bed265a1d314d9f6aae8f2dd48d20b Mon Sep 17 00:00:00 2001 From: George Hazan Date: Wed, 28 Nov 2012 18:45:54 +0000 Subject: ex-protos moved to the Plugins folder git-svn-id: http://svn.miranda-ng.org/main/trunk@2545 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- plugins/Weather/src/weather_mwin.cpp | 420 +++++++++++++++++++++++++++++++++++ 1 file changed, 420 insertions(+) create mode 100644 plugins/Weather/src/weather_mwin.cpp (limited to 'plugins/Weather/src/weather_mwin.cpp') diff --git a/plugins/Weather/src/weather_mwin.cpp b/plugins/Weather/src/weather_mwin.cpp new file mode 100644 index 0000000000..8a7798b3b1 --- /dev/null +++ b/plugins/Weather/src/weather_mwin.cpp @@ -0,0 +1,420 @@ +/* +Weather Protocol plugin for Miranda IM +Copyright (c) 2012 Miranda NG Team +Copyright (c) 2006-2009 Boris Krasnovskiy All Rights Reserved +Copyright (c) 2002-2006 Calvin Che + +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 "weather.h" +#include "m_acc.h" + +#define MS_TOOLTIP_SHOWTIP "mToolTip/ShowTip" +#define MS_TOOLTIP_HIDETIP "mToolTip/HideTip" + +typedef BOOL (WINAPI *ft_TrackMouseEvent) (LPTRACKMOUSEEVENT lpEventTrack); + +static ft_TrackMouseEvent f_TrackMouseEvent = NULL; +static HANDLE hMwinWindowList; +static HANDLE hFontHook; + +HANDLE hMwinMenu; + +typedef struct +{ + HANDLE hContact; + HWND hAvt; + BOOL haveAvatar; +} MWinDataType; + +#define WM_REDRAWWIN (WM_USER + 17369) + +static LRESULT CALLBACK wndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) +{ + MWinDataType *data = (MWinDataType*)GetWindowLongPtr(hwnd, GWLP_USERDATA); + + switch(msg) + { + case WM_CREATE: + data = (MWinDataType*)mir_calloc(sizeof(MWinDataType)); + SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR)data); + + data->hContact = (HANDLE)((LPCREATESTRUCT)lParam)->lpCreateParams; + data->hAvt = CreateWindow(AVATAR_CONTROL_CLASS, TEXT(""), WS_CHILD, + 0, 0, opt.AvatarSize, opt.AvatarSize, hwnd, NULL, hInst, 0); + if (data->hAvt) SendMessage(data->hAvt, AVATAR_SETCONTACT, 0, (LPARAM)data->hContact); + break; + + case WM_DESTROY: + mir_free(data); + break; + + case WM_CONTEXTMENU: + { + POINT pt; + + HMENU hMenu = (HMENU)CallService(MS_CLIST_MENUBUILDCONTACT, (WPARAM)data->hContact, 0); + GetCursorPos(&pt); + TrackPopupMenu(hMenu, TPM_LEFTALIGN, pt.x, pt.y, 0, hwnd, NULL); + DestroyMenu(hMenu); + } + break; + + case WM_MOUSEMOVE: + if (f_TrackMouseEvent) + { + TRACKMOUSEEVENT tme = {0}; + tme.cbSize = sizeof(TRACKMOUSEEVENT); + tme.hwndTrack = hwnd; + tme.dwFlags = TME_QUERY; + f_TrackMouseEvent(&tme); + + if (tme.dwFlags == 0) + { + tme.dwFlags = TME_HOVER | TME_LEAVE; + tme.hwndTrack = hwnd; + tme.dwHoverTime = CallService(MS_CLC_GETINFOTIPHOVERTIME, 0, 0); + f_TrackMouseEvent(&tme); + } + } + break; + + case WM_MOUSEHOVER: + { + POINT pt; + CLCINFOTIP ti = {0}; + + GetCursorPos(&pt); + GetWindowRect(hwnd, &ti.rcItem); + + ti.cbSize = sizeof(ti); + ti.hItem = data->hContact; + ti.ptCursor = pt; + ti.isTreeFocused = 1; + CallService(MS_TOOLTIP_SHOWTIP, 0, (LPARAM)&ti); + } + break; + + case WM_LBUTTONDBLCLK: + BriefInfo((WPARAM)data->hContact, 0); + break; + + case WM_COMMAND: //Needed by the contact's context menu + if ( CallService(MS_CLIST_MENUPROCESSCOMMAND, MAKEWPARAM(LOWORD(wParam),MPCF_CONTACTMENU), (LPARAM)data->hContact)) + break; + return FALSE; + + case WM_MEASUREITEM: //Needed by the contact's context menu + return CallService(MS_CLIST_MENUMEASUREITEM, wParam, lParam); + + case WM_DRAWITEM: //Needed by the contact's context menu + return CallService(MS_CLIST_MENUDRAWITEM, wParam, lParam); + + case WM_NOTIFY: + if (((LPNMHDR)lParam)->code == NM_AVATAR_CHANGED) + { + BOOL newava = CallService(MS_AV_GETAVATARBITMAP, (WPARAM)data->hContact, 0) != 0; + if (newava != data->haveAvatar) + { + LONG_PTR style = GetWindowLongPtr(data->hAvt, GWL_STYLE); + data->haveAvatar = newava; + SetWindowLongPtr(data->hAvt, GWL_STYLE, newava ? (style | WS_VISIBLE) : (style & ~WS_VISIBLE)); + RedrawWindow(hwnd, NULL, NULL, RDW_INVALIDATE); + } + } + break; + + case WM_REDRAWWIN: + if (data->hAvt != NULL) MoveWindow(data->hAvt, 0, 0, opt.AvatarSize, opt.AvatarSize, TRUE); + RedrawWindow(hwnd, NULL, NULL, RDW_INVALIDATE | RDW_UPDATENOW); + break; + + case WM_PAINT: + { + RECT r, rc; + + if (GetUpdateRect(hwnd, &r, FALSE)) + { + DBVARIANT dbv = {0}; + PAINTSTRUCT ps; + LOGFONT lfnt, lfnt1; + COLORREF fntc, fntc1; + COLORREF clr; + int picSize = opt.AvatarSize; + HICON hIcon = NULL; + + if ( !data->haveAvatar) + { + int statusIcon = db_get_w(data->hContact, WEATHERPROTONAME, "Status", 0); + + picSize = GetSystemMetrics(SM_CXICON); + hIcon = LoadSkinnedProtoIconBig(WEATHERPROTONAME, statusIcon); + if ((INT_PTR)hIcon == CALLSERVICE_NOTFOUND) + { + picSize = GetSystemMetrics(SM_CXSMICON); + hIcon = LoadSkinnedProtoIcon(WEATHERPROTONAME, statusIcon); + } + } + + clr = db_get_dw(NULL, WEATHERPROTONAME, "ColorMwinFrame", GetSysColor(COLOR_3DFACE)); + + { + FontIDT fntid = {0}; + _tcscpy(fntid.group, _T(WEATHERPROTONAME)); + _tcscpy(fntid.name, LPGENT("Frame Font")); + fntc = CallService(MS_FONT_GETT, (WPARAM)&fntid, (LPARAM)&lfnt); + + _tcscpy(fntid.name, LPGENT("Frame Title Font")); + fntc1 = CallService(MS_FONT_GETT, (WPARAM)&fntid, (LPARAM)&lfnt1); + } + + DBGetContactSettingTString(data->hContact, WEATHERCONDITION, "WeatherInfo", &dbv); + + GetClientRect(hwnd, &rc); + + HDC hdc = BeginPaint(hwnd, &ps); + + if ( ServiceExists(MS_SKIN_DRAWGLYPH)) { + SKINDRAWREQUEST rq; + memset(&rq, 0, sizeof(rq)); + rq.hDC = hdc; + rq.rcDestRect = rc; + rq.rcClipRect = rc; + + strcpy(rq.szObjectID, "Main,ID=WeatherFrame"); + CallService(MS_SKIN_DRAWGLYPH, (WPARAM)&rq, 0); + } + + if (clr != 0xFFFFFFFF) { + HBRUSH hBkgBrush = CreateSolidBrush(clr); + FillRect(hdc, &rc, hBkgBrush); + DeleteObject(hBkgBrush); + } + + if ( !data->haveAvatar) + DrawIconEx(hdc, 1, 1, hIcon, 0, 0, 0, NULL, DI_NORMAL); + + SetBkMode(hdc, TRANSPARENT); + + HFONT hfnt = CreateFontIndirect(&lfnt1); + HFONT hfntold = ( HFONT )SelectObject(hdc, hfnt); + SIZE fontSize; + + TCHAR *nick = ( TCHAR* )CallService(MS_CLIST_GETCONTACTDISPLAYNAME, (WPARAM)data->hContact, GCDNF_TCHAR); + + GetTextExtentPoint32(hdc, _T("|"), 1, &fontSize); + + rc.top += 1; + rc.left += picSize + fontSize.cx; + + SetTextColor(hdc, fntc1); + DrawText(hdc, nick, -1, &rc, DT_LEFT | DT_EXPANDTABS); + + rc.top += fontSize.cy; + + SelectObject(hdc, hfntold); + DeleteObject(hfnt); + + if (dbv.pszVal) + { + HFONT hfnt = CreateFontIndirect(&lfnt); + HFONT hfntold = ( HFONT )SelectObject(hdc, hfnt); + + SetTextColor(hdc, fntc); + DrawText(hdc, dbv.ptszVal, -1, &rc, DT_LEFT | DT_EXPANDTABS); + + SelectObject(hdc, hfntold); + DeleteObject(hfnt); + } + EndPaint(hwnd, &ps); + Skin_ReleaseIcon(hIcon); + db_free(&dbv); + } + break; + } + + default: + return DefWindowProc(hwnd, msg, wParam, lParam); + } + return(TRUE); +} + +static void addWindow(HANDLE hContact) +{ + DBVARIANT dbv; + DBGetContactSettingTString(hContact, WEATHERPROTONAME, "Nick", &dbv); + + TCHAR winname[512]; + mir_sntprintf(winname, SIZEOF(winname), _T("Weather: %s"), dbv.ptszVal); + db_free(&dbv); + + HWND hWnd = CreateWindow( _T("WeatherFrame"), _T(""), WS_CHILD | WS_VISIBLE, + 0, 0, 10, 10, (HWND)CallService(MS_CLUI_GETHWND, 0, 0), NULL, hInst, hContact); + WindowList_Add(hMwinWindowList, hWnd, hContact); + + CLISTFrame Frame = {0}; + Frame.tname = winname; + Frame.hIcon = LoadIconEx("main",FALSE); + Frame.cbSize = sizeof(Frame); + Frame.hWnd = hWnd; + Frame.align = alBottom; + Frame.Flags = F_VISIBLE|F_NOBORDER|F_TCHAR; + Frame.height = 32; + DWORD frameID = CallService(MS_CLIST_FRAMES_ADDFRAME, (WPARAM)&Frame, 0); + + db_set_dw(hContact, WEATHERPROTONAME, "mwin", frameID); + db_set_b(hContact, "CList", "Hidden", TRUE); +} + +void removeWindow(HANDLE hContact) +{ + DWORD frameId = db_get_dw(hContact, WEATHERPROTONAME, "mwin", 0); + + WindowList_Remove(hMwinWindowList, WindowList_Find(hMwinWindowList, hContact)); + CallService(MS_CLIST_FRAMES_REMOVEFRAME, frameId, 0); + + db_set_dw(hContact, WEATHERPROTONAME, "mwin", 0); + db_unset(hContact, "CList", "Hidden"); +} + +void UpdateMwinData(HANDLE hContact) +{ + HWND hwnd = WindowList_Find(hMwinWindowList, hContact); + if (hwnd != NULL) + RedrawWindow(hwnd, NULL, NULL, RDW_INVALIDATE | RDW_UPDATENOW); +} + + +INT_PTR Mwin_MenuClicked(WPARAM wParam,LPARAM lParam) +{ + BOOL addwnd = WindowList_Find(hMwinWindowList, (HANDLE)wParam) == NULL; + if (addwnd) + addWindow((HANDLE)wParam); + else + removeWindow((HANDLE)wParam); + return 0; +} + + +int BuildContactMenu(WPARAM wparam,LPARAM lparam) +{ + CLISTMENUITEM mi = {0}; + + mi.cbSize = sizeof(mi); + mi.flags = CMIM_FLAGS | + (db_get_dw((HANDLE)wparam, WEATHERPROTONAME, "mwin", 0) ? CMIF_CHECKED : 0); + CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMwinMenu, (LPARAM)&mi); + return 0; +} + + +int RedrawFrame(WPARAM wParam, LPARAM lParam) +{ + WindowList_Broadcast(hMwinWindowList, WM_REDRAWWIN, 0, 0); + return 0; +} + + +void InitMwin(void) +{ + HMODULE hUser = GetModuleHandle(_T("user32.dll")); + + if ( !ServiceExists(MS_CLIST_FRAMES_ADDFRAME)) return; + + f_TrackMouseEvent = (ft_TrackMouseEvent)GetProcAddress(hUser, "TrackMouseEvent"); + + + hMwinWindowList = (HANDLE)CallService(MS_UTILS_ALLOCWINDOWLIST,0,0); + + { + WNDCLASS wndclass; + wndclass.style = CS_DBLCLKS | CS_HREDRAW | CS_VREDRAW; + wndclass.lpfnWndProc = wndProc; + wndclass.cbClsExtra = 0; + wndclass.cbWndExtra = 0; + wndclass.hInstance = hInst; + wndclass.hIcon = NULL; + wndclass.hCursor = LoadCursor (NULL, IDC_ARROW); + wndclass.hbrBackground = 0; //(HBRUSH)(COLOR_3DFACE+1); + wndclass.lpszMenuName = NULL; + wndclass.lpszClassName = _T("WeatherFrame"); + RegisterClass(&wndclass); + } + + { + ColourIDT colourid = {0}; + colourid.cbSize = sizeof(ColourIDT); + strcpy(colourid.dbSettingsGroup, WEATHERPROTONAME); + strcpy(colourid.setting, "ColorMwinFrame"); + _tcscpy(colourid.name, LPGENT("Frame Background")); + _tcscpy(colourid.group, _T(WEATHERPROTONAME)); + colourid.defcolour = GetSysColor(COLOR_3DFACE); + ColourRegisterT(&colourid); + + FontIDT fontid = {0}; + fontid.cbSize = sizeof(FontIDT); + fontid.flags = FIDF_ALLOWREREGISTER | FIDF_DEFAULTVALID; + strcpy(fontid.dbSettingsGroup, WEATHERPROTONAME); + _tcscpy(fontid.group, _T(WEATHERPROTONAME)); + _tcscpy(fontid.name, LPGENT("Frame Font")); + strcpy(fontid.prefix, "fnt0"); + + HDC hdc = GetDC(NULL); + fontid.deffontsettings.size = -13; + ReleaseDC(0, hdc); + + fontid.deffontsettings.charset = DEFAULT_CHARSET; + _tcscpy(fontid.deffontsettings.szFace, _T("Verdana")); + _tcscpy(fontid.backgroundGroup, _T(WEATHERPROTONAME)); + _tcscpy(fontid.backgroundName, LPGENT("Frame Background")); + FontRegisterT(&fontid); + + fontid.deffontsettings.style = DBFONTF_BOLD; + _tcscpy(fontid.name, LPGENT("Frame Title Font")); + strcpy(fontid.prefix, "fnt1"); + FontRegisterT(&fontid); + } + + HANDLE hContact = db_find_first(); + while(hContact) + { + // see if the contact is a weather contact + if (IsMyContact(hContact)) + { + if (db_get_dw(hContact, WEATHERPROTONAME, "mwin", 0)) + addWindow(hContact); + } + hContact = db_find_next(hContact); + } + hFontHook = HookEvent(ME_FONT_RELOAD, RedrawFrame); +} + +void DestroyMwin(void) +{ + HANDLE hContact = db_find_first(); + while(hContact) + { + // see if the contact is a weather contact + if (IsMyContact(hContact)) + { + DWORD frameId = db_get_dw(hContact, WEATHERPROTONAME, "mwin", 0); + if (frameId) + CallService(MS_CLIST_FRAMES_REMOVEFRAME, frameId, 0); + } + hContact = db_find_next(hContact); + } + UnregisterClass( _T("WeatherFrame"), hInst); + UnhookEvent(hFontHook); +} -- cgit v1.2.3