#include "common.h" #include "popups.h" bool bPopupsEnabled = false; HWND hwndPop = 0; HANDLE hEventPop; bool pop_cancelled; typedef struct { unsigned flags; HICON hIcon; } PopupDataType; LRESULT CALLBACK NullWindowProc( HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam ) { switch( message ) { case UM_INITPOPUP: { PopupDataType* popup = (PopupDataType*)CallService(MS_POPUP_GETPLUGINDATA, (WPARAM)hWnd,0); if(popup->flags & POPFLAG_SAVEHWND) hwndPop = hWnd; } return 0; case WMU_CLOSEPOP: SetEvent(hEventPop); PUDeletePopUp( hWnd ); return TRUE; case WM_COMMAND: { PopupDataType* popup = (PopupDataType*)CallService(MS_POPUP_GETPLUGINDATA, (WPARAM)hWnd,0); if(popup->flags & POPFLAG_SAVEHWND) pop_cancelled = false; } SetEvent(hEventPop); PUDeletePopUp( hWnd ); return TRUE; case WM_CONTEXTMENU: { PopupDataType* popup = (PopupDataType*)CallService(MS_POPUP_GETPLUGINDATA, (WPARAM)hWnd,0); if(popup->flags & POPFLAG_SAVEHWND) pop_cancelled = true; } SetEvent(hEventPop); PUDeletePopUp( hWnd ); return TRUE; case UM_FREEPLUGINDATA: { PopupDataType* popup = (PopupDataType*)CallService(MS_POPUP_GETPLUGINDATA, (WPARAM)hWnd, 0); if ((unsigned)popup != CALLSERVICE_NOTFOUND) { if (popup->flags & POPFLAG_SAVEHWND) hwndPop = 0; if(popup->hIcon) ReleaseIconEx(popup->hIcon); free(popup); } return TRUE; } } return DefWindowProc(hWnd, message, wParam, lParam); } void __stdcall sttPopupProcA( ULONG dwParam ) { POPUPDATAEX* ppd = ( POPUPDATAEX* )dwParam; if ( ServiceExists(MS_POPUP_ADDPOPUPEX) ) CallService( MS_POPUP_ADDPOPUPEX, ( WPARAM )ppd, 0 ); else if ( ServiceExists(MS_POPUP_ADDPOPUP) ) CallService( MS_POPUP_ADDPOPUP, ( WPARAM )ppd, 0 ); free( ppd ); } void __stdcall sttPopupProcW( ULONG dwParam ) { POPUPDATAW* ppd = ( POPUPDATAW* )dwParam; if ( ServiceExists(MS_POPUP_ADDPOPUPW) ) CallService( MS_POPUP_ADDPOPUPW, ( WPARAM )ppd, 0 ); free( ppd ); } void ShowPopupA( HANDLE hContact, const char* line1, const char* line2, int flags, int timeout ) { if(CallService(MS_SYSTEM_TERMINATED, 0, 0)) return; if ( !ServiceExists( MS_POPUP_ADDPOPUP )) { char title[256]; sprintf(title, "%s Message", MODULE); if(line1 && line2) { char *message = new char[strlen(line1) + strlen(line2) + 2]; // newline and null terminator sprintf(message, "%s\n%s", line1, line2); MessageBoxA( NULL, message, title, MB_OK | MB_ICONINFORMATION ); delete message; } else if(line1) { MessageBoxA( NULL, line1, title, MB_OK | MB_ICONINFORMATION ); } else if(line2) { MessageBoxA( NULL, line2, title, MB_OK | MB_ICONINFORMATION ); } return; } SetEvent(hEventPop); ResetEvent(hEventPop); if(ServiceExists(MS_POPUP_ADDPOPUPCLASS)) { POPUPDATACLASS d = {sizeof(d), "updaterpopups"}; d.pszTitle = (char *)line1; d.pszText = (char *)line2; d.PluginData = malloc(sizeof(PopupDataType)); ((PopupDataType*)d.PluginData)->flags = flags; ((PopupDataType*)d.PluginData)->hIcon = 0; CallService(MS_POPUP_ADDPOPUPCLASS, 0, (LPARAM)&d); } else { POPUPDATAEX* ppd = ( POPUPDATAEX* )malloc( sizeof( POPUPDATAEX )); memset((void *)ppd, 0, sizeof(POPUPDATAEX)); ppd->lchContact = hContact; ppd->lchIcon = LoadIconEx(I_CHKUPD); if(line1 && line2) { strcpy( ppd->lpzContactName, line1 ); strcpy( ppd->lpzText, line2 ); } else { if(line1) { strcpy( ppd->lpzText, line1 ); } else { if(line2) strcpy( ppd->lpzText, line2 ); } } if(options.set_colours) { ppd->colorBack = options.bkCol; ppd->colorText = options.textCol; } else { //ppd->colorText = 0x00FFFFFF; // otherwise old popups are black on black ppd->colorText = 0; //ppd->colorBack = POPUP_USE_SKINNED_BG; ppd->colorBack = 0; } ppd->iSeconds = timeout; ppd->PluginWindowProc = ( WNDPROC )NullWindowProc; ppd->PluginData = malloc(sizeof(PopupDataType)); ((PopupDataType*)ppd->PluginData)->flags = flags; ((PopupDataType*)ppd->PluginData)->hIcon = ppd->lchIcon; QueueUserAPC( sttPopupProcA , mainThread, ( ULONG )ppd ); } } void ShowPopupW( HANDLE hContact, const wchar_t* line1, const wchar_t* line2, int flags, int timeout ) { if(CallService(MS_SYSTEM_TERMINATED, 0, 0)) return; if ( !ServiceExists( MS_POPUP_ADDPOPUPW )) { wchar_t title[256]; swprintf(title, L"%s Message", _T(MODULE)); if(line1 && line2) { wchar_t *message = new wchar_t[wcslen(line1) + wcslen(line2) + 2]; // newline and null terminator swprintf(message, L"%s\n%s", line1, line2); MessageBoxW( NULL, message, title, MB_OK | MB_ICONINFORMATION ); delete message; } else if(line1) { MessageBoxW( NULL, line1, title, MB_OK | MB_ICONINFORMATION ); } else if(line2) { MessageBoxW( NULL, line2, title, MB_OK | MB_ICONINFORMATION ); } return; } SetEvent(hEventPop); ResetEvent(hEventPop); if(ServiceExists(MS_POPUP_ADDPOPUPCLASS)) { POPUPDATACLASS d = {sizeof(d), "updaterpopups"}; d.pwszTitle = (wchar_t *)line1; d.pwszText = (wchar_t *)line2; d.PluginData = malloc(sizeof(PopupDataType)); ((PopupDataType*)d.PluginData)->flags = flags; ((PopupDataType*)d.PluginData)->hIcon = 0; CallService(MS_POPUP_ADDPOPUPCLASS, 0, (LPARAM)&d); } else { POPUPDATAW* ppd = ( POPUPDATAW* )malloc( sizeof( POPUPDATAW )); memset((void *)ppd, 0, sizeof(POPUPDATAW)); ppd->lchContact = hContact; ppd->lchIcon = LoadIconEx(I_CHKUPD); if(line1 && line2) { wcscpy( ppd->lpwzContactName, line1 ); wcscpy( ppd->lpwzText, line2 ); } else { if(line1) { wcscpy( ppd->lpwzText, line1 ); } else { if(line2) wcscpy( ppd->lpwzText, line2 ); } } if(options.set_colours) { ppd->colorBack = options.bkCol; ppd->colorText = options.textCol; } else { //ppd->colorText = 0x00FFFFFF; ppd->colorText = 0; //ppd->colorBack = POPUP_USE_SKINNED_BG; ppd->colorBack = 0; } ppd->iSeconds = timeout; ppd->PluginWindowProc = ( WNDPROC )NullWindowProc; ppd->PluginData = malloc(sizeof(PopupDataType)); ((PopupDataType*)ppd->PluginData)->flags = flags; ((PopupDataType*)ppd->PluginData)->hIcon = ppd->lchIcon; QueueUserAPC( sttPopupProcW , mainThread, ( ULONG )ppd ); } } void ShowWarning(TCHAR *msg) { if(ServiceExists(MS_POPUP_SHOWMESSAGE)) { TCHAR title[512]; _stprintf(title, _T("%s Warning"), _T(MODULE)); TCHAR message[1024]; _stprintf(message, _T("%s: %s"), _T(MODULE), msg); ShowPopup(0, title, message, 0, 10); //PUShowMessage(message, SM_WARNING); } else { TCHAR title[512]; _stprintf(title, _T("%s Warning"), MODULE); MessageBox(0, msg, title, MB_OK | MB_ICONWARNING); } } void ShowPopup(HANDLE hContact, const TCHAR *line1, const TCHAR *line2, int flags, int timeout) { #ifdef _UNICODE if(ServiceExists(MS_POPUP_ADDPOPUPW)) ShowPopupW(hContact, line1, line2, flags, timeout); else { char *al1 = w2a(line1), *al2 = w2a(line2); ShowPopupA(hContact, al1, al2, flags, timeout); free(al1); free(al2); } #else if(ServiceExists(MS_POPUP_ADDPOPUP)) ShowPopupA(hContact, line1, line2, flags, timeout); else { wchar_t *wl1 = a2w(line1), *wl2 = a2w(line2); ShowPopupW(hContact, wl1, wl2, flags, timeout); free(wl1); free(wl2); } #endif } void ShowError(TCHAR *msg) { if(ServiceExists(MS_POPUP_SHOWMESSAGE)) { TCHAR title[512]; _stprintf(title, _T("%s Error"), _T(MODULE)); TCHAR message[1024]; _stprintf(message, _T("%s: %s"), _T(MODULE), msg); //PUShowMessage(message, SM_WARNING); ShowPopup(0, title, message, 0, 10); } else { TCHAR title[512]; _stprintf(title, _T("%s Error"), _T(MODULE)); MessageBox(0, msg, title, MB_OK | MB_ICONERROR); } } void ChangePopupText(HWND hwnd, TCHAR *text) { #ifdef _UNICODE if(ServiceExists(MS_POPUP_CHANGETEXTW)) CallService(MS_POPUP_CHANGETEXTW, (WPARAM)hwnd, (LPARAM)text); else { char *atext = w2a(text); CallService(MS_POPUP_CHANGETEXT, (WPARAM)hwnd, (LPARAM)atext); free(atext); } #else if(ServiceExists(MS_POPUP_CHANGETEXT)) CallService(MS_POPUP_CHANGETEXT, (WPARAM)hwnd, (LPARAM)text); else { wchar_t *wtext = a2w(text); CallService(MS_POPUP_CHANGETEXTW, (WPARAM)hwnd, (LPARAM)wtext); free(wtext); } #endif } bool ArePopupsEnabled() { return bPopupsEnabled; } HICON hPopupIcon; void InitPopups() { bPopupsEnabled = (ServiceExists(MS_POPUP_ADDPOPUP) == 0 && ServiceExists(MS_POPUP_ADDPOPUPW) == 0 ? false : true); hEventPop = CreateEvent( NULL, TRUE, FALSE, NULL ); if(ServiceExists(MS_POPUP_ADDPOPUPCLASS)) { hPopupIcon = LoadIconEx(I_CHKUPD); POPUPCLASS test = {0}; test.cbSize = sizeof(test); test.flags = PCF_TCHAR; test.hIcon = hPopupIcon; test.iSeconds = -1; test.ptszDescription = TranslateT("Updater"); test.pszName = "updaterpopups"; test.PluginWindowProc = NullWindowProc; CallService(MS_POPUP_REGISTERCLASS, 0, (WPARAM)&test); } } void DeinitPopups() { CloseHandle(hEventPop); ReleaseIconEx(hPopupIcon); }