summaryrefslogtreecommitdiff
path: root/plugins/RecentContacts/src
diff options
context:
space:
mode:
authorVadim Dashevskiy <watcherhd@gmail.com>2012-07-23 13:03:18 +0000
committerVadim Dashevskiy <watcherhd@gmail.com>2012-07-23 13:03:18 +0000
commit60338d55bb73d0c45b6e092703c4bb88a3c49755 (patch)
tree30305d6576617177f237046d95474173ba6ab194 /plugins/RecentContacts/src
parent201ace762530e0bec270301fd23f039af3872875 (diff)
Rate, RecentContacts, Scriver: changed folder structure
git-svn-id: http://svn.miranda-ng.org/main/trunk@1121 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c
Diffstat (limited to 'plugins/RecentContacts/src')
-rw-r--r--plugins/RecentContacts/src/RecentContacts.cpp634
-rw-r--r--plugins/RecentContacts/src/RecentContacts.h92
-rw-r--r--plugins/RecentContacts/src/options.cpp73
-rw-r--r--plugins/RecentContacts/src/resource.h25
4 files changed, 824 insertions, 0 deletions
diff --git a/plugins/RecentContacts/src/RecentContacts.cpp b/plugins/RecentContacts/src/RecentContacts.cpp
new file mode 100644
index 0000000000..fcc3dda6ac
--- /dev/null
+++ b/plugins/RecentContacts/src/RecentContacts.cpp
@@ -0,0 +1,634 @@
+
+#include "RecentContacts.h"
+
+extern int onOptInitialise(WPARAM wParam, LPARAM lParam);
+
+using namespace std;
+static const basic_string <char>::size_type npos = -1;
+
+char *szProto;
+HINSTANCE hInst = NULL;
+int hLangpack = 0;
+
+
+HANDLE hTopToolbarButtonShowList;
+HANDLE hMsgWndEvent;
+HANDLE hWindowList;
+HANDLE hMenuItemRemove;
+HANDLE hIcon;
+
+const INT_PTR boo = 0;
+LIST<void> ServiceList(10,boo), HookList(10,boo);
+
+BOOL IsMessageAPI = FALSE;
+
+LastUCOptions LastUCOpt = {0};
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
+{
+ hInst = hinstDLL;
+ return TRUE;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+PLUGININFOEX pluginInfo =
+{
+ sizeof(PLUGININFOEX),
+ "Recent Contacts",
+ PLUGIN_MAKE_VERSION(0,0,2,0),
+ "Adds a menu item in main menu, which open the window with list of last used contacts names,"
+ " sorted in order from most recent to least.",
+ "ValeraVi, Kildor",
+ "kostia@ngs.ru",
+ "© 2005 ValeraVi, © 2009 Kildor",
+ "http://kildor.miranda.im",
+ UNICODE_AWARE, //doesn't replace anything built-in
+ { 0x0e5f3b9d, 0xebcd, 0x44d7, {0x93, 0x74, 0xd8, 0xe5, 0xd8, 0x8d, 0xf4, 0xe3}}
+ /* 0e5f3b9d-ebcd-44d7-9374-d8e5d88df4e3 */
+};
+
+extern "C" __declspec(dllexport) PLUGININFOEX* MirandaPluginInfoEx(DWORD mirandaVersion)
+{
+ return &pluginInfo;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+extern "C" __declspec(dllexport) const MUUID MirandaInterfaces[] = {MIID_RECENTCONTACTS, MIID_LAST};
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+void LoadDBSettings()
+{
+ ZeroMemory(&LastUCOpt, sizeof(LastUCOpt));
+ LastUCOpt.MaxShownContacts = (INT)DBGetContactSettingByte( NULL, dbLastUC_ModuleName, dbLastUC_MaxShownContacts, 0 );
+ LastUCOpt.HideOffline = DBGetContactSettingByte( NULL, dbLastUC_ModuleName, dbLastUC_HideOfflineContacts, 0 );
+
+ DBVARIANT dbv;
+ dbv.type = DBVT_ASCIIZ;
+ dbv.pszVal = NULL;
+ if ( db_get(NULL, dbLastUC_ModuleName, dbLastUC_DateTimeFormat, &dbv) == 0 && dbv.pszVal[0]!=0 ) {
+ LastUCOpt.DateTimeFormat = dbv.pszVal;
+ DBFreeVariant(&dbv);
+ }
+ else LastUCOpt.DateTimeFormat = "(%Y-%m-%d %H:%M) ";
+}
+
+void ShowListMainDlgProc_AdjustListPos(HWND hDlg, LASTUC_DLG_DATA *DlgDat)
+{
+ HWND hList = GetDlgItem(hDlg, IDC_CONTACTS_LIST);
+ if (hList == NULL)
+ return;
+
+ RECT rc;
+ SIZE cur;
+ GetWindowRect(hDlg, &rc);
+ cur.cx = rc.right - rc.left;
+ cur.cy = rc.bottom - rc.top;
+ rc.left = DlgDat->ListUCRect.left;
+ rc.top = DlgDat->ListUCRect.top;
+ rc.right = DlgDat->ListUCRect.right + cur.cx - DlgDat->WindowMinSize.cx;
+ rc.bottom = DlgDat->ListUCRect.bottom + cur.cy - DlgDat->WindowMinSize.cy;
+ MoveWindow(hList, rc.left, rc.top, rc.right - rc.left, rc.bottom - rc.top, TRUE);
+
+ LVCOLUMN lvc = { 0 };
+ lvc.mask = LVCF_WIDTH;
+ lvc.cx = rc.right - rc.left - GetSystemMetrics(SM_CYHSCROLL) - 4;
+ if (lvc.cx < 10)
+ lvc.cx = 10;
+ ListView_SetColumn(hList, 0, &lvc);
+}
+
+BOOL ShowListMainDlgProc_OpenContact(HWND hList, int item)
+{
+ if (item != -1) {
+ LVITEM lvi;
+ ZeroMemory(&lvi, sizeof(lvi));
+ lvi.mask = LVIF_PARAM;
+ lvi.lParam = NULL;
+ lvi.iItem = item;
+ lvi.iSubItem = 0;
+ ListView_GetItem(hList, &lvi);
+ if (lvi.lParam != NULL) {
+ CallService(MS_CLIST_CONTACTDOUBLECLICKED, (WPARAM)lvi.lParam, NULL);
+ return TRUE;
+ }
+ }
+ return FALSE;
+}
+
+BOOL ShowListMainDlgProc_OpenContactMenu(HWND hDlg, HWND hList, int item, LASTUC_DLG_DATA *DlgDat)
+{
+ if (item != -1) {
+ LVITEM lvi;
+ ZeroMemory(&lvi, sizeof(lvi));
+ lvi.mask = LVIF_PARAM;
+ lvi.lParam = NULL;
+ lvi.iItem = item;
+ lvi.iSubItem = 0;
+ ListView_GetItem(hList, &lvi);
+ if (lvi.lParam != NULL) {
+ HMENU hCMenu = (HMENU)CallService(MS_CLIST_MENUBUILDCONTACT, (WPARAM)lvi.lParam, NULL);
+ if (hCMenu != NULL) {
+ POINT p;
+ GetCursorPos(&p);
+ DlgDat->hContact = (HANDLE) lvi.lParam;
+ BOOL ret = TrackPopupMenu(hCMenu, 0, p.x, p.y, 0, hDlg, NULL);
+ DestroyMenu(hCMenu);
+ if (ret)
+ return TRUE;
+ DlgDat->hContact = NULL;
+ }
+ }
+ }
+ return FALSE;
+}
+
+void wSetData(char **Data, const char *Value)
+{
+ if (Value[0] != 0) {
+ char *newData = (char*)mir_alloc(strlen(Value)+3);
+ strcpy(newData, Value);
+ *Data = newData;
+ }
+ else *Data = "";
+}
+
+void wfree(char **Data)
+{
+ if (*Data && strlen(*Data) > 0) mir_free(*Data);
+ *Data = NULL;
+}
+
+HWND hwndContactTree = NULL;
+
+INT_PTR CALLBACK ShowListMainDlgProc(HWND hDlg, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ LASTUC_DLG_DATA *DlgDat;
+
+ DlgDat = (LASTUC_DLG_DATA *)GetWindowLongPtr(hDlg, GWLP_USERDATA);
+ HWND hList = GetDlgItem(hDlg, IDC_CONTACTS_LIST);
+ if (hList == NULL)
+ return FALSE;
+
+ switch( msg ) {
+ case WM_INITDIALOG:
+ TranslateDialogDefault(hDlg);
+ {
+ DlgDat = new LASTUC_DLG_DATA;
+ ZeroMemory(DlgDat, sizeof(LASTUC_DLG_DATA));
+ DlgDat->Contacts = (cmultimap*)lParam;
+
+ RECT rc;
+ GetWindowRect(hDlg, &rc);
+ DlgDat->WindowMinSize.cx = rc.right - rc.left;
+ DlgDat->WindowMinSize.cy = rc.bottom - rc.top;
+ GetWindowRect(hList, &DlgDat->ListUCRect);
+
+ POINT p;
+ p.x = DlgDat->ListUCRect.left;
+ p.y = DlgDat->ListUCRect.top;
+ ScreenToClient(hDlg, &p);
+ DlgDat->ListUCRect.left = p.x;
+ DlgDat->ListUCRect.top = p.y;
+ p.x = DlgDat->ListUCRect.right;
+ p.y = DlgDat->ListUCRect.bottom;
+ ScreenToClient(hDlg, &p);
+ DlgDat->ListUCRect.right = p.x;
+ DlgDat->ListUCRect.bottom = p.y;
+ SetWindowLongPtr(hDlg, GWLP_USERDATA, (LONG)DlgDat);
+
+ //set listview styles
+ ListView_SetExtendedListViewStyleEx(hList,
+ LVS_EX_FULLROWSELECT | LVS_EX_GRIDLINES | LVS_EX_LABELTIP
+ | LVS_EX_ONECLICKACTIVATE | LVS_EX_UNDERLINEHOT, -1);
+
+ // add header columns to listview
+ LVCOLUMN lvc;
+ ZeroMemory(&lvc, sizeof(lvc));
+ lvc.mask = LVCF_FMT | LVCF_SUBITEM | LVCF_TEXT | LVCF_WIDTH;
+ lvc.fmt = LVCFMT_LEFT;
+ lvc.iSubItem = 0;
+ lvc.pszText = TranslateT("Contact");
+ lvc.cx = 10;
+ ListView_InsertColumn(hList, 0, &lvc);
+
+ // add conacts to listview
+ HIMAGELIST hImgList = (HIMAGELIST)CallService(MS_CLIST_GETICONSIMAGELIST, 0, 0);
+ if (hImgList != NULL)
+ ListView_SetImageList(hList, hImgList, LVSIL_SMALL);
+
+ LVITEM lvi = { 0 };
+ lvi.mask = LVIF_TEXT | LVIF_PARAM | LVIF_IMAGE;
+
+ int i=0;
+ cmultimap::iterator curContact;
+ std::tstring str;
+ char strtim[256 + 16];
+
+ string strtimformat;
+ DBVARIANT dbv;
+ dbv.type = DBVT_ASCIIZ;
+ dbv.pszVal = NULL;
+ if (db_get(NULL, dbLastUC_ModuleName, dbLastUC_DateTimeFormat, &dbv) == 0) {
+ strtimformat = dbv.pszVal;
+ DBFreeVariant(&dbv);
+ }
+ else strtimformat = dbLastUC_DateTimeFormatDefault;
+
+ for(curContact = DlgDat->Contacts->begin(); curContact != DlgDat->Contacts->end(); curContact++) {
+ if (curContact->second != NULL && db_byte_get(curContact->second, dbLastUC_ModuleName, dbLastUC_IgnoreContact, 0) == 0 ) {
+ TCHAR *cname = ( TCHAR* )CallService(MS_CLIST_GETCONTACTDISPLAYNAME, (WPARAM)curContact->second, GCDNF_TCHAR);
+ if ( cname == NULL )
+ continue;
+
+ if (LastUCOpt.HideOffline == 1) {
+ szProto = (char*)CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)curContact->second, 0);
+ if (szProto != NULL && DBGetContactSettingWord((HANDLE)curContact->second, szProto, "Status", ID_STATUS_OFFLINE) == ID_STATUS_OFFLINE)
+ continue;
+ }
+
+ lvi.iItem = i;
+ lvi.iSubItem = 0;
+ lvi.lParam = (LPARAM)curContact->second;
+
+ strftime(strtim, 256, strtimformat.c_str(), _localtime64(&curContact->first));
+ strtim[255] = 0;
+ str = _A2T(strtim);
+ str += cname;
+ lvi.pszText = (LPTSTR)str.c_str();
+ lvi.iImage = CallService(MS_CLIST_GETCONTACTICON, (WPARAM)curContact->second, 0);
+ ListView_InsertItem(hList, &lvi);
+ i++;
+
+ }
+ if (LastUCOpt.MaxShownContacts > 0 && i >= LastUCOpt.MaxShownContacts)
+ break;
+ }
+
+ SAVEWINDOWPOS pos;
+ pos.hContact = NULL;
+ pos.hwnd = hDlg;
+ pos.szModule = dbLastUC_ModuleName;
+ pos.szNamePrefix = dbLastUC_WindowPosPrefix;
+ CallService(MS_UTILS_RESTOREWINDOWPOSITION, 0, (LPARAM)(SAVEWINDOWPOS*)&pos);
+ SendMessage(hDlg, WM_SIZE, 0, 0);
+ WindowList_Add(hWindowList, hDlg, NULL);
+ return TRUE;
+ }
+
+ case WM_ACTIVATE:
+ if (LOWORD(wParam) == WA_INACTIVE)
+ SendMessage(hDlg, WM_CLOSE, 0, 0);
+ break;
+
+ case WM_NOTIFY:
+ {
+ LPNMHDR lpNmhdr;
+ lpNmhdr = (LPNMHDR)lParam;
+ if (lpNmhdr->hwndFrom == hList) {
+ if (lpNmhdr->code == NM_CLICK || lpNmhdr->code == NM_RCLICK) {
+ RECT r;
+ POINT p;
+ GetCursorPos(&p);
+ GetWindowRect(hList, &r);
+ if (PtInRect(&r, p)) {
+ LVHITTESTINFO lvh;
+ ZeroMemory(&lvh, sizeof(lvh));
+ lvh.pt = p;
+ ScreenToClient(hList, &lvh.pt);
+ ListView_HitTest(hList, &lvh);
+ if ((lvh.flags & (LVHT_ONITEMICON | LVHT_ONITEMLABEL | LVHT_ONITEMSTATEICON)) && lvh.iItem != -1) {
+ if (lpNmhdr->code == NM_CLICK) {
+ if (ShowListMainDlgProc_OpenContact(hList, lvh.iItem))
+ SendMessage(hDlg, WM_CLOSE, 0, 0);
+ }
+ else ShowListMainDlgProc_OpenContactMenu(hDlg, hList, lvh.iItem, DlgDat);
+ }
+ }
+ }
+ else if (lpNmhdr->code == NM_RETURN) {
+ if (ShowListMainDlgProc_OpenContact(hList, ListView_GetNextItem(hList, -1, LVIS_SELECTED)))
+ SendMessage(hDlg, WM_CLOSE, 0, 0);
+ }
+ }
+ break;
+ }
+
+ case WM_MEASUREITEM:
+ return CallService(MS_CLIST_MENUMEASUREITEM, wParam, lParam);
+
+ case WM_DRAWITEM:
+ return CallService(MS_CLIST_MENUDRAWITEM, wParam, lParam);
+
+ case WM_COMMAND:
+ if (CallService(MS_CLIST_MENUPROCESSCOMMAND, MAKEWPARAM(LOWORD(wParam), MPCF_CONTACTMENU), (LPARAM)DlgDat->hContact))
+ break;
+
+ switch(wParam) {
+ case IDOK:
+ ShowListMainDlgProc_OpenContact(hList, ListView_GetNextItem(hList, -1, LVIS_SELECTED));
+ case IDCANCEL:
+ SendMessage(hDlg, WM_CLOSE, 0, 0);
+ break;
+ }
+ break;
+
+ case WM_GETMINMAXINFO:
+ {
+ MINMAXINFO *mmi = (MINMAXINFO *) lParam;
+ mmi->ptMinTrackSize.x = 100;
+ mmi->ptMinTrackSize.y = 150;
+ return 0;
+ }
+
+ case WM_SIZE:
+ ShowListMainDlgProc_AdjustListPos(hDlg, DlgDat);
+ break;
+
+ case WM_CLOSE:
+ DestroyWindow(hDlg);
+ break;
+
+ case WM_DESTROY:
+ {
+ // Save current window position.
+ SAVEWINDOWPOS pos;
+ pos.hContact = NULL;
+ pos.hwnd = hDlg;
+ pos.szModule = dbLastUC_ModuleName;
+ pos.szNamePrefix = dbLastUC_WindowPosPrefix;
+ CallService(MS_UTILS_SAVEWINDOWPOSITION, 0, (LPARAM)(SAVEWINDOWPOS*)&pos);
+ delete DlgDat->Contacts;
+ delete DlgDat;
+ // Remove entry from Window list
+ WindowList_Remove(hWindowList, hDlg);
+ break;
+ }
+ }
+ return FALSE;
+}
+
+INT_PTR OnMenuCommandShowList(WPARAM wParam, LPARAM lParam)
+{
+ cmultimap *contacts = new cmultimap;
+
+ __time64_t curTime;
+ //DWORD t;
+ DBEVENTINFO dbe;
+ ZeroMemory(&dbe, sizeof(dbe));
+ dbe.cbSize = sizeof(dbe);
+ BYTE buf[1];
+ dbe.pBlob = buf;
+ HANDLE curEvent;
+ HANDLE curContact = (HANDLE)CallService(MS_DB_CONTACT_FINDFIRST, 0, 0);
+ for (; curContact != NULL; curContact = (HANDLE)CallService(MS_DB_CONTACT_FINDNEXT, (WPARAM)curContact, 0))
+ {
+// if (IsMessageAPI)
+ {
+ curTime = ((__time64_t)db_dword_get(curContact, dbLastUC_ModuleName, dbLastUC_LastUsedTimeLo, -1)) |
+ (((__time64_t)db_dword_get(curContact, dbLastUC_ModuleName, dbLastUC_LastUsedTimeHi, -1)) << 32);
+ //use TabSRMM last used time. ! NOT used, because bug: TabSRMM reset last used time to time when miranda started at miranda start!
+ //t = ((DWORD)db_dword_get(curContact, "Tab_SRMsg", "isRecent", -1));
+ //if (t != -1)
+ //{
+ // if (curTime == -1 || (__time64_t)t > curTime)
+ // curTime = (__time64_t)t;
+ //}
+ }
+// else
+ {
+ curEvent = (HANDLE)CallService(MS_DB_EVENT_FINDLAST, (WPARAM)curContact, 0);
+ if (curEvent != NULL)
+ {
+ for ( ; curEvent != NULL; curEvent = (HANDLE)CallService(MS_DB_EVENT_FINDPREV, (WPARAM)curEvent, 0))
+ {
+ dbe.cbBlob = 1;
+ if (CallService(MS_DB_EVENT_GET, (WPARAM)curEvent, (LPARAM)&dbe) != 0)
+ {
+ curEvent = NULL;
+ break;
+ }
+ if ((dbe.flags & (DBEF_READ | DBEF_SENT)) && dbe.eventType < 2000)
+ break;
+ }
+ if (curEvent != NULL)
+ if (curTime == -1 || (__time64_t)dbe.timestamp > curTime)
+ curTime = (__time64_t)dbe.timestamp;
+ }
+ }
+ if (curTime != -1)
+ contacts->insert(cpair(curTime, curContact));
+ }
+
+ HWND hWndMain;
+ if ((hWndMain = CreateDialogParam(hInst, MAKEINTRESOURCE(IDD_LASTUC_DIALOG), NULL, ShowListMainDlgProc, (LPARAM)contacts)) == NULL)
+ return -1;
+
+ ShowWindow(hWndMain, SW_SHOW);
+
+ if (hTopToolbarButtonShowList != NULL)
+ CallService(MS_TTB_SETBUTTONSTATE, (WPARAM)hTopToolbarButtonShowList, TTBST_RELEASED);
+ return 0;
+}
+
+static int OnContactSettingChanged( WPARAM wParam, LPARAM lParam )
+{
+ HANDLE hContact = ( HANDLE )wParam;
+ DBCONTACTWRITESETTING* pdbcws = ( DBCONTACTWRITESETTING* )lParam;
+
+ if ( hContact == NULL )
+ if ( !stricmp( pdbcws->szModule, dbLastUC_ModuleName))
+ LoadDBSettings();
+
+ return 0;
+}
+
+int Create_TopToolbarShowList(WPARAM wParam, LPARAM lParam)
+{
+ TTBButton ttbb = {0};
+ ttbb.cbSize = sizeof(ttbb);
+ ttbb.hIconHandleUp = hIcon;
+ ttbb.pszService = msLastUC_ShowList;
+ ttbb.dwFlags = TTBBF_VISIBLE | TTBBF_SHOWTOOLTIP;
+ ttbb.name = ttbb.pszTooltipUp = LPGEN(msLastUC_ShowListName);
+ hTopToolbarButtonShowList = TopToolbar_AddButton(&ttbb);
+ return 0;
+}
+
+int Create_MenuitemShowList(void)
+{
+ CLISTMENUITEM mi = { 0 };
+ mi.cbSize = sizeof(mi);
+ mi.hIcon = ( HICON )CallService( MS_SKIN2_GETICON, 0, ( LPARAM )"recent_main" );
+ mi.pszName = msLastUC_ShowListName;
+ mi.pszService = msLastUC_ShowList;
+ Menu_AddMainMenuItem(&mi);
+
+ ZeroMemory( &mi, sizeof( mi ));
+ mi.cbSize = sizeof( mi );
+ mi.position = 0xFFFFF;
+ mi.hIcon = ( HICON )CallService( MS_SKIN2_GETICON, 0, ( LPARAM )"recent_main" );
+ mi.ptszName = _T("Toggle Ignore");
+ mi.pszService = V_RECENTCONTACTS_TOGGLE_IGNORE;
+ hMenuItemRemove = Menu_AddContactMenuItem(&mi);
+ return 0;
+}
+
+BOOL SaveLastUsedTimeStamp(HANDLE hContact)
+{
+ __time64_t ct = _time64(NULL);
+ db_dword_set(hContact, dbLastUC_ModuleName, dbLastUC_LastUsedTimeLo, (DWORD)ct);
+ db_dword_set(hContact, dbLastUC_ModuleName, dbLastUC_LastUsedTimeHi, (DWORD)(ct >> 32));
+ return TRUE;
+}
+
+int OnMsgEvent(WPARAM wParam, LPARAM lParam)
+{
+ MessageWindowEventData *ed = (MessageWindowEventData *)lParam;
+ if (ed->hContact == NULL)
+ return 0;
+
+ if (ed->uType == MSG_WINDOW_EVT_OPEN)
+ SaveLastUsedTimeStamp(ed->hContact);
+ else if (ed->uType == MSG_WINDOW_EVT_CUSTOM) {
+ struct TABSRMM_SessionInfo *si = (struct TABSRMM_SessionInfo*) ed->local;
+ if (si != NULL)
+ if (si->evtCode == tabMSG_WINDOW_EVT_CUSTOM_BEFORESEND)
+ SaveLastUsedTimeStamp(ed->hContact);
+ }
+ return 0;
+}
+
+static void iconsInit(void)
+{
+ TCHAR szFile[MAX_PATH];
+ GetModuleFileName(hInst, szFile, SIZEOF(szFile));
+
+ SKINICONDESC sid = {0};
+ sid.cbSize = sizeof(sid);
+ sid.flags = SIDF_PATH_UNICODE;
+ sid.pszSection = Translate(msLastUC_ShowListName);
+ sid.ptszDefaultFile = szFile;
+
+ sid.pszDescription = LPGEN("Main icon");
+ sid.pszName = "recent_main";
+ sid.iDefaultIndex = -IDI_SHOWRECENT;
+ hIcon = Skin_AddIcon(&sid);
+}
+
+static int OnPrebuildContactMenu (WPARAM wParam, LPARAM lParam)
+{
+ CLISTMENUITEM clmi = { 0 };
+ clmi.cbSize = sizeof( clmi );
+ clmi.flags = CMIM_NAME | CMIF_TCHAR;
+
+ if ( DBGetContactSettingByte((HANDLE)wParam, dbLastUC_ModuleName, dbLastUC_IgnoreContact, 0) == 0)
+ clmi.ptszName = TranslateT("Ignore Contact");
+ else
+ clmi.ptszName = TranslateT("Show Contact");
+
+ CallService( MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuItemRemove, (LPARAM)&clmi );
+ return 0;
+}
+
+int OnModulesLoaded(WPARAM wParam, LPARAM lParam)
+{
+ iconsInit();
+ Create_MenuitemShowList();
+ IsMessageAPI = (CallService(MS_MSG_GETWINDOWAPI, 0, 0) != CALLSERVICE_NOTFOUND);
+ //maxShownContacts = ;
+ LoadDBSettings();
+
+ /*
+ if (ServiceExists(MS_FONT_REGISTERT)) {
+ FontIDT fid={0};
+
+ fid.cbSize=sizeof(fid);
+ fid.group = _T("Console");
+ fid.name,TranslateT = "Text";
+ fid.dbSettingsGroup = "Console";
+ fid.prefix = "ConsoleFont";
+
+ fid.backgroundGroup = _T("Console");
+ fid.backgroundName = _T("Background");
+
+ fid.flags = FIDF_DEFAULTVALID;
+
+ fid.deffontsettings.charset = DEFAULT_CHARSET;
+ fid.deffontsettings.colour = RGB(0, 0, 0);
+ fid.deffontsettings.size = 10;
+ fid.deffontsettings.style = 0;
+ _tcsncpy(fid.deffontsettings.szFace, _T("Tahoma"), LF_FACESIZE);
+
+ CallService(MS_FONT_REGISTERT,(WPARAM)&fid,0);
+
+ hHooks[i++] = HookEvent(ME_FONT_RELOAD,OnFontChange);
+ }
+ */
+
+ // hotkeys
+ HOTKEYDESC hk = {0};
+ hk.cbSize = sizeof(hk);
+ hk.pszName = msLastUC_ShowList;
+ hk.pszDescription = LPGEN("Show Recent Contacts");
+ hk.pszSection = "Contacts";
+ hk.pszService = msLastUC_ShowList;
+ hk.DefHotKey = MAKEWORD('R', HOTKEYF_CONTROL | HOTKEYF_SHIFT);
+ Hotkey_Register(&hk);
+
+ return 0;
+}
+
+INT_PTR ToggleIgnore (WPARAM wParam, LPARAM lParam)
+{
+ if (wParam != NULL) {
+ HANDLE hContact = ( HANDLE )wParam;
+ int state = DBGetContactSettingByte(hContact, dbLastUC_ModuleName, dbLastUC_IgnoreContact, 0) == 0 ? 1 : 0 ;
+ DBWriteContactSettingByte(hContact, dbLastUC_ModuleName, dbLastUC_IgnoreContact, state);
+ return state;
+ }
+
+ return -1;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+extern "C" __declspec(dllexport) int Load(void)
+{
+
+ mir_getLP( &pluginInfo );
+
+ CoInitialize(NULL);
+ hWindowList = (HANDLE)CallService(MS_UTILS_ALLOCWINDOWLIST, 0, 0);
+
+ ServiceList.insert( CreateServiceFunction(msLastUC_ShowList, OnMenuCommandShowList));
+ ServiceList.insert( CreateServiceFunction(V_RECENTCONTACTS_TOGGLE_IGNORE, ToggleIgnore));
+
+ HookList.insert( HookEvent(ME_SYSTEM_MODULESLOADED, OnModulesLoaded));
+ HookList.insert( HookEvent(ME_CLIST_PREBUILDCONTACTMENU, OnPrebuildContactMenu ));
+ HookList.insert( HookEvent(ME_TTB_MODULELOADED, Create_TopToolbarShowList));
+ HookList.insert( HookEvent(ME_MSG_WINDOWEVENT, OnMsgEvent));
+ HookList.insert( HookEvent(ME_DB_CONTACT_SETTINGCHANGED, OnContactSettingChanged ));
+ HookList.insert( HookEvent(ME_OPT_INITIALISE, onOptInitialise));
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+extern "C" __declspec(dllexport) int Unload(void)
+{
+ int i;
+
+ for (i=0; i < ServiceList.getCount(); ++i)
+ DestroyServiceFunction( ServiceList[i] );
+
+ for (i=0; i < HookList.getCount(); ++i)
+ UnhookEvent( HookList[i] );
+
+ CoUninitialize();
+ return 0;
+}
diff --git a/plugins/RecentContacts/src/RecentContacts.h b/plugins/RecentContacts/src/RecentContacts.h
new file mode 100644
index 0000000000..6b5731fa7d
--- /dev/null
+++ b/plugins/RecentContacts/src/RecentContacts.h
@@ -0,0 +1,92 @@
+
+#pragma once
+
+#define _CRT_SECURE_NO_WARNINGS
+#define _CRT_NONSTDC_NO_DEPRECATE
+#define MIRANDA_VER 0x0A00
+
+#include <windows.h>
+#include <commctrl.h>
+#include <string>
+#include <map>
+#include "resource.h"
+#include <time.h>
+
+#include <newpluginapi.h>
+#include <m_clist.h>
+#include <m_contacts.h>
+#include <m_langpack.h>
+#include <m_database.h>
+#include <m_system.h>
+#include <m_system_cpp.h>
+#include <m_message.h>
+#include <m_utils.h>
+#include <m_icolib.h>
+#include <m_hotkeys.h>
+#include <m_protosvc.h>
+#include <m_options.h>
+#include <win2k.h>
+
+#include <m_toptoolbar.h>
+
+/* dc90285a-9985-4b7a-baad-e70ae1dfc1d9 */
+#define MIID_RECENTCONTACTS { 0xdc90285a, 0x9985, 0x4b7a, {0xba, 0xad, 0xe7, 0x0a, 0xe1, 0xdf, 0xc1, 0xd9}}
+
+#define V_RECENTCONTACTS_TOGGLE_IGNORE "RecentContacts/ToggleIgnore"
+
+using namespace std;
+
+void wSetData(char **Data, const char *Value);
+void wfree(char **Data);
+
+static char msLastUC_ShowListName[] = "Recent Contacts";
+
+static char dbLastUC_ModuleName[] = "RecentContacts";
+static char dbLastUC_LastUsedTimeLo[] = "LastUsedTimeLo";
+static char dbLastUC_LastUsedTimeHi[] = "LastUsedTimeHi";
+static char dbLastUC_WindowPosPrefix[] = "Window";
+static char dbLastUC_DateTimeFormat[] = "DateTimeFormat";
+static char dbLastUC_DateTimeFormatDefault[] = "(%Y-%m-%d %H:%M) ";
+static char dbLastUC_MaxShownContacts[] = "MaxShownContacts";
+static char dbLastUC_IgnoreContact[] = "Ignore";
+static char dbLastUC_HideOfflineContacts[] = "HideOfflineContacts";
+
+static char msLastUC_ShowList[] = "RecentContacts/ShowList";
+static char msLastUC_IgnoreOff[] = "RecentContacts/SetIgnoreOff";
+static char msLastUC_IgnoreOn[] = "RecentContacts/SetIgnoreOn";
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+typedef struct _LastUCOptions
+{
+ int MaxShownContacts;
+ int HideOffline;
+ string DateTimeFormat;
+}
+ LastUCOptions;
+
+extern LastUCOptions LastUCOpt;
+//#include "m_tabsrmm.h"
+// custom tabSRMM events
+#define tabMSG_WINDOW_EVT_CUSTOM_BEFORESEND 1
+struct TABSRMM_SessionInfo {
+ unsigned int cbSize;
+ unsigned int evtCode;
+ HWND hwnd; // handle of the message dialog (tab)
+ HWND hwndContainer; // handle of the parent container
+ HWND hwndInput; // handle of the input area (rich edit)
+ /*struct MessageWindowData*/ void *dat; // the session info
+ /*struct ContainerWindowData*/ void *pContainer;
+};
+
+
+typedef std::multimap <__time64_t, HANDLE, std::greater<__time64_t> > cmultimap;
+typedef std::pair <__time64_t, HANDLE> cpair;
+
+typedef struct LASTUC_DLG_DATA
+{
+ cmultimap *Contacts;
+ SIZE WindowMinSize;
+ RECT ListUCRect;
+ HANDLE hContact;
+} LASTUC_DLG_DATA; \ No newline at end of file
diff --git a/plugins/RecentContacts/src/options.cpp b/plugins/RecentContacts/src/options.cpp
new file mode 100644
index 0000000000..d8f09adb9b
--- /dev/null
+++ b/plugins/RecentContacts/src/options.cpp
@@ -0,0 +1,73 @@
+#include "RecentContacts.h"
+#include "resource.h"
+
+extern HINSTANCE hInst;
+void LoadDBSettings();
+
+INT_PTR CALLBACK DlgProcOptions(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ char str[32];
+
+ switch (msg) {
+ case WM_INITDIALOG:
+ TranslateDialogDefault(hwndDlg);
+ CheckDlgButton(hwndDlg, IDC_HIDEOFFLINE, (LastUCOpt.HideOffline ? BST_CHECKED : BST_UNCHECKED));
+
+ mir_snprintf(str, SIZEOF(str), "%d", LastUCOpt.MaxShownContacts);
+ SetDlgItemTextA(hwndDlg, IDC_SHOWNCONTACTS, str);
+
+ mir_snprintf(str, SIZEOF(str), "%s", LastUCOpt.DateTimeFormat.c_str());
+ SetDlgItemTextA(hwndDlg, IDC_DATETIME, str);
+
+ SetWindowLongPtr(hwndDlg,GWLP_USERDATA,lParam);
+ return TRUE;
+
+ case WM_COMMAND:
+ switch(HIWORD(wParam)) {
+ case EN_CHANGE:
+ case BN_CLICKED:
+ case CBN_EDITCHANGE:
+ case CBN_SELCHANGE:
+ SendMessage(GetParent(hwndDlg),PSM_CHANGED,0,0);
+ }
+ break;
+
+ case WM_NOTIFY:
+ {
+ LPNMHDR phdr = (LPNMHDR)(lParam);
+ if (phdr->idFrom == 0 && phdr->code == PSN_APPLY) {
+ BOOL bSuccess = FALSE;
+
+ LastUCOpt.HideOffline = (BOOL)IsDlgButtonChecked(hwndDlg, IDC_HIDEOFFLINE);
+ DBWriteContactSettingByte(NULL, dbLastUC_ModuleName, dbLastUC_HideOfflineContacts, (BYTE)LastUCOpt.HideOffline);
+
+ GetDlgItemTextA(hwndDlg, IDC_SHOWNCONTACTS, str, SIZEOF(str));
+ LastUCOpt.MaxShownContacts= atoi(str);
+ DBWriteContactSettingByte(0,dbLastUC_ModuleName, dbLastUC_MaxShownContacts, LastUCOpt.MaxShownContacts);
+
+ GetDlgItemTextA(hwndDlg, IDC_DATETIME, str, SIZEOF(str));
+ DBWriteContactSettingString(0,dbLastUC_ModuleName, dbLastUC_DateTimeFormat, str );
+
+ LoadDBSettings();
+ return TRUE;
+ }
+ break;
+ }
+ }
+ return FALSE;
+}
+
+int onOptInitialise(WPARAM wParam, LPARAM lParam)
+{
+ OPTIONSDIALOGPAGE odp = { 0 };
+ odp.cbSize = sizeof(odp);
+ odp.hInstance = hInst;
+ odp.pszGroup = LPGEN("Contact List");
+ odp.pszTemplate = MAKEINTRESOURCEA(IDD_LASTUC_OPT);
+ odp.pszTitle = msLastUC_ShowListName;
+ odp.pfnDlgProc = DlgProcOptions;
+ odp.flags = ODPF_BOLDGROUPS;
+ Options_AddPage(wParam, &odp);
+
+ return 0;
+}
diff --git a/plugins/RecentContacts/src/resource.h b/plugins/RecentContacts/src/resource.h
new file mode 100644
index 0000000000..59e47a934a
--- /dev/null
+++ b/plugins/RecentContacts/src/resource.h
@@ -0,0 +1,25 @@
+//{{NO_DEPENDENCIES}}
+// Microsoft Visual C++ generated include file.
+// Used by resource.rc
+//
+#define IDD_LASTUC_OPT 9
+#define IDI_FOLDER 101
+#define IDI_CMD_BROWSE 102
+#define IDI_SHOWRECENT 103
+#define IDD_LASTUC_DIALOG 105
+#define IDC_LIST1 1000
+#define IDC_CONTACTS_LIST 1000
+#define IDC_SHOWNCONTACTS 1002
+#define IDC_HIDEOFFLINE 1004
+#define IDC_DATETIME 1005
+
+// Next default values for new objects
+//
+#ifdef APSTUDIO_INVOKED
+#ifndef APSTUDIO_READONLY_SYMBOLS
+#define _APS_NEXT_RESOURCE_VALUE 106
+#define _APS_NEXT_COMMAND_VALUE 40001
+#define _APS_NEXT_CONTROL_VALUE 1006
+#define _APS_NEXT_SYMED_VALUE 101
+#endif
+#endif