;Display Control plugin for Miranda. Turns on the screen if in power saving mode, when a message arives ;Copyright © 2006-2007 A. Chilaru ; ;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; either version 2 ;of the License, or (at your option) any later version. ; ;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, write to the Free Software ;Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. .386 .model flat,stdcall option casemap:none include \masm32\include\windows.inc include \masm32\include\kernel32.inc include \masm32\include\user32.inc include \masm32\include\comctl32.inc include \masm32\include\gdi32.inc include ..\inc\IcoLib.inc include ..\inc\m_clist.inc include ..\inc\m_clc.inc include ..\inc\m_database.inc include ..\inc\m_langpack.inc include ..\inc\m_options.inc include ..\inc\m_protocols.inc include ..\inc\m_protosvc.inc include ..\inc\m_updater.inc include ..\inc\newpluginapi.inc include ..\inc\statusmodes.inc includelib \masm32\lib\kernel32.lib includelib \masm32\lib\user32.lib includelib \masm32\lib\comctl32.lib includelib \masm32\lib\gdi32.lib ;function definitions for debuggers ;hook functions are C-style functions. The rest are stdcall OptInit proto C wParam:DWORD, lParam:DWORD Message proto C wParam:DWORD, lParam:DWORD MdLoaded proto C wParam:DWORD, lParam:DWORD IcoLibEv proto C wParam:DWORD, lParam: DWORD CallService proto lpServiceName:DWORD, wParam:DWORD, lParam:DWORD ServiceExists proto lpServiceName:DWORD HookEvent proto lpHookName:DWORD, lpFunction:DWORD UnhookEvent proto HookHandle:DWORD Translate proto lpStr:DWORD Error proto lpStr:DWORD IgnoreCheck proto pStri:DWORD ResetListOptions proto hCList:DWORD SetAllContactIcons proto hCList:DWORD SetListGroupIcons proto hCList:DWORD, hFirstItem:DWORD, hParentItem:DWORD, groupChildCount:DWORD SetAllChildIcons proto hCList:DWORD, hFirstItem:DWORD, iColumn:DWORD, iImage:DWORD MetaConClick proto hContact:DWORD, iCount:DWORD, iValue: DWORD MetaSubClick proto hContact:DWORD DLGHDR struct ;Structure to hold info about tabs hDlg dd ? hTab dd ? hDisplay dd ? rcDisplay RECT <> hTab1 dd ? hTab2 dd ? DLGHDR ends ;Macro to create lParam DWORD from two WORDs (low WORDs used if DWORD given) MAKELPARAM macro lowWord, highWord push ebx mov ebx, lowWord mov eax, highWord shl eax, 16 mov ax, bx pop ebx ENDM .const ;option controls IDC_ENABLED equ 40071 ;Plugin enables checkbox ID IDC_PROTO equ 40081 ;Protocol listbox ID IDC_STARTTIME equ 40088 ;time selector IDC_ENDTIME equ 40089 ;time selector IDC_SHOWHIDDEN equ 50071 ;Show hidden contacts IDC_CLIST equ 3000 ;CList component IDI_PC equ 101 ;PC icon ;const from miranda resource file (small dot in CListControl) IDI_SMALLDOT equ 211 ;const from skin header SKINICON_EVENT_MESSAGE equ 100 WM_IMGLIST equ WM_USER+273 .data hInstance dd 0 ;Plugin hWnd hApp dd 0 ;Miranda .exe hWnd hDlgWnd dd 0 ;Option dialog hWnd hIcoLibEv dd 0 ;IcoLib dialog hWnd hIml dd 0 ;Image list hItemAll dd 0 ;CListControl "Group" ** All contacts **" hItemUnk dd 0 ;CListControl "Group" ** Unknown contacts **" ddRetAddr dd 0 ;Miranda proto ret. address ddRetStack dd 0 ;Miranda proto EBP backup hMsgHook dd 0 ;Message hook hWnd hOptHook dd 0 ;Options hook hWnd hMdLHook dd 0 ;Modules loaded hook ddVar1 dd 0 ddVar2 dd 0 ;Just three DWORD variables ;) ddVar3 dd 0 ddInt dd 0 ddFlags dd 0 ;Various flags. Descriptions (starting from the lower bit) ;Reserved ;OptEditing2 On while options are loaded from the DB ;OptEditing2 On while options are loaded from the DB ;noUniConvert Don't convert to Unicode while translating sPluginInfo PLUGININFO <0> ;plugin info structure sPluginLink PLUGINLINK <> ;miranda procedure adresses structure sOptionsPage OPTIONSDIALOGPAGE <0> ;options struct sDBVariant DBVARIANT <> ;DB write/get variable struct sDBGetSetting DBCONTACTGETSETTING <> ;DB get struct sDBWriteSetting DBCONTACTWRITESETTING <>;DB write struct sDBEventInfo DBEVENTINFO <> ;Event ifnfo struct sUpdate UPDATE <0> ;Updater struct sTCITEM TCITEM <0> ;struct for tabbing sDlgHdr DLGHDR <0> ;struct for tabbing sSystemTime SYSTEMTIME <> ;datetime struct sLngPackDialog LANGPACKTRANSLATEDIALOG <> ;langpack dialog struct sClcInfoItem CLCINFOITEM <> ;contact list child item info sSkinIconDesc SKINICONDESC <> ;IcoLib struct ;plugin details szShortName db "Display Control",0 szShortNamev db "Display Control " IFDEF _UNICODE szPlVer db "(Unicode)",0 ELSE szPlVer db "(ANSI)",0 ENDIF ddVersion dd 0001011Eh szDescription db "The plugin turns your monitor power on as soon as a message arrives.",10,13,"Uses triggers, such as time, protocol, message type, status and individual contact, as rules.",0 szAuthor db "A. Chilaru",0 szAthorEmail db "flexlabs@gmail.com",0 szCopyright db "© 2007 A. Chilaru (FlexLabs Inc.)",0 szHomepage db "http://dev.mirandaim.ru/dspcontrol",0 ;additional details for updater IFDEF _UNICODE szURL db "http://addons.miranda-im.org/details.php?action=viewfile&id=3232",0 szURLKey db "Display Control (Unicode) ",0 ddURLKeyLen dd 37h szDnURL db "http://addons.miranda-im.org/feed.php?dlfile=3232",0 ELSE szURL db "http://addons.miranda-im.org/details.php?action=viewfile&id=3261",0 szURLKey db "Display Control (ANSI) ",0 ddURLKeyLen dd 34h szDnURL db "http://addons.miranda-im.org/feed.php?dlfile=3261",0 ENDIF szBetaURL db "http://svn.mirandaim.ru/mainrepo/dspcontrol/trunk/BETA",0 szBetaURLKey db "DspControl_v.",0 ddBetaURLKeyLen dd 0Dh IFDEF _UNICODE szBetaDnURL db "http://svn.mirandaim.ru/mainrepo/dspcontrol/trunk/bin/Unicode/DspControl.dll",0 ELSE szBetaDnURL db "http://svn.mirandaim.ru/mainrepo/dspcontrol/trunk/bin/ANSI/DspControl.dll",0 ENDIF szVersion db "0.1.1.30",0 ddVersionLen dd 08h ddBeta dd 0 ;If plugin is beta - 1. Else - 0 szBetaChangelogURL db "http://svn.mirandaim.ru/mainrepo/dspcontrol/trunk/CHANGELOG.txt",0 ;miranda functions MS_DB_CONTACT_GETSETTING db "DB/Contact/GetSetting",0 MS_DB_CONTACT_WRITESETTING db "DB/Contact/WriteSetting",0 MS_DB_CONTACT_FINDFIRST db "DB/Contact/FindFirst",0 MS_DB_CONTACT_FINDNEXT db "DB/Contact/FindNext",0 MS_DB_EVENT_GET db "DB/Event/Get",0 MS_DB_EVENT_GETBLOBSIZE db "DB/Event/GetBlobSize",0 MS_DB_EVENT_GETCONTACT db "DB/Event/GetContact",0 MS_PROTO_GETCONTACTBASEPROTO db "Proto/GetContactBaseProto",0 MS_CLIST_ADDMAINMENUITEM db "CList/AddMainMenuItem",0 MS_CLIST_GETSTATUSMODE db "CList/GetStatusMode",0 MS_OPT_ADDPAGE db "Opt/AddPage",0 MS_PROTO_ENUMPROTOCOLS db "Proto/EnumProtocols",0 MS_MC_GETMETACONTACT db "MetaContacts/GetMeta",0 MS_MC_GETSUBCONTACT db "MetaContacts/GetSubContact",0 ME_SYSTEM_MODULESLOADED db "Miranda/System/ModulesLoaded",0 MS_SKIN_LOADICON db "Skin/Icons/Load",0 MS_SKIN2_ADDICON db "Skin2/Icons/AddIcon",0 MS_SKIN2_GETICON db "Skin2/Icons/GetIcon",0 MS_UPDATE_REGISTER db "Update/Register",0 MS_LANGPACK_TRANSLATESTRING db "LangPack/TranslateString",0 MS_LANGPACK_TRANSLATEDIALOG db "LangPack/TranslateDialog",0 PS_GETCAPS db "/GetCaps",0 ;Takes form of "PROTO/GetCaps",0 (GetCapabilities of a PROTO) ;miranda events ME_DB_EVENT_ADDED db "DB/Event/Added",0 ME_OPT_INITIALISE db "Opt/Initialise",0 ME_SKIN2_ICONSCHANGED db "Skin2/IconsChanged",0 ;options szOptGroup db "Events",0 szOptGroupW db "Unicod",0 szOptTitle db "Display Control",0 szOptTitleW db "UnicodeUnicodeU",0 szOModule db "DspControl",0 szOFlags db "Flags",0 szOTime db "Time",0 szOEnabled db "Enabled",0 szONotOnList db "NotOnList",0 szOCList db "CList",0 szOShowHidden db "ShowHidden",0 szOMetaContacts db "MetaContacts",0 szOMetaCount db "NumContacts",0 szOMetaLink db "MetaLink",0 ;tab captions szTab1 db "Triggers",0 szTab1W db "UnicodeU",0 szTab2 db "Contacts",0 szTab2W db "UnicodeU",0 ;IcoLib szIlDesc db "Enabled",0 szIlName db "dspc_screen",0 ;other strings szDtFormat db "HH':'mm",0 szError db "Default error message",0 szAllContacts db "** All contacts **",0 szAllContactsW db "UnicodeUnicodeUnic",0 szUnkContacts db "** Unknown contacts **",0 szUnkContactsW db "UnicodeUnicodeUnicodeU",0 ;option control info IDC_ETYPE_MESSAGE dd 40082 IDC_ETYPE_MESSAGE_V dd EVENTTYPE_MESSAGE IDC_ETYPE_URL dd 40083 IDC_ETYPE_URL_V dd EVENTTYPE_URL IDC_ETYPE_CONTACTS dd 40084 IDC_ETYPE_CONTACTS_V dd EVENTTYPE_CONTACTS IDC_ETYPE_ADDED dd 40085 IDC_ETYPE_ADDED_V dd EVENTTYPE_ADDED IDC_ETYPE_AUTHREQUEST dd 40086 IDC_ETYPE_AUTHREQUEST_V dd EVENTTYPE_AUTHREQUEST IDC_ETYPE_FILE dd 40087 IDC_ETYPE_FILE_V dd EVENTTYPE_FILE .data? ;option control hWnd's HC_CLIST dd ? HC_ENABLED dd ? HC_STATUS_ONLINE dd ? HC_STATUS_AWAY dd ? HC_STATUS_DND dd ? HC_STATUS_NA dd ? HC_STATUS_OCCUPIED dd ? HC_STATUS_FREECHAT dd ? HC_STATUS_INVISIBLE dd ? HC_STATUS_ONTHEPHONE dd ? HC_STATUS_OUTTOLUNCH dd ? HC_PROTO dd ? HC_ETYPE_MESSAGE dd ? HC_ETYPE_URL dd ? HC_ETYPE_CONTACTS dd ? HC_ETYPE_ADDED dd ? HC_ETYPE_AUTHREQUEST dd ? HC_ETYPE_FILE dd ? HC_STARTTIME dd ? HC_ENDTIME dd ? HC_SHOWHIDDEN dd ? ;empty string space szGeneral db 256 DUP(?) .code DllMain proc hInst:HINSTANCE, reason:DWORD, reserved1:DWORD push hInst pop hInstance ;save hWnd of the library invoke GetModuleHandle, NULL mov hApp, eax ;save hWnd of Miranda mov sPluginInfo.cbSize, sizeof PLUGININFO ;set the library's info mov sPluginInfo.shortName, offset szShortNamev push ddVersion pop sPluginInfo.version mov sPluginInfo.description, offset szDescription mov sPluginInfo.author, offset szAuthor mov sPluginInfo.authorEmail, offset szAthorEmail mov sPluginInfo.copyright, offset szCopyright mov sPluginInfo.homepage, offset szHomepage mov eax, TRUE ret DllMain Endp MirandaPluginInfo proc mov eax, offset sPluginInfo ;return plugin info struct ret MirandaPluginInfo Endp ;internal miranda functions. Not necessary, but allow viewing them in the debugger CallService proc lpServiceName:DWORD, wParam:DWORD, lParam:DWORD pop ddRetStack pop ddRetAddr call sPluginLink.lpCallService push ddRetAddr push ddRetStack ret CallService endp ServiceExists proc lpServiceName:DWORD pop ddRetStack pop ddRetAddr call sPluginLink.lpServiceExists push ddRetAddr push ddRetStack ret ServiceExists endp HookEvent proc lpHookName:DWORD, lpFunction:DWORD pop ddRetStack pop ddRetAddr call sPluginLink.lpHookEvent push ddRetAddr push ddRetStack ret HookEvent endp UnhookEvent proc HookHandle:DWORD pop ddRetStack pop ddRetAddr call sPluginLink.lpUnhookEvent push ddRetAddr push ddRetStack ret UnhookEvent endp ;call to Miranda translate module Translate proc lpString:DWORD LOCAL ddLng:DWORD mov eax, ddFlags and eax, 8 .IF eax==0 IFDEF _UNICODE mov ddLng, LANG_UNICODE ELSE mov ddLng, 0 ENDIF .ELSE and ddFlags, -9 mov ddLng, 0 .ENDIF invoke CallService, offset MS_LANGPACK_TRANSLATESTRING, ddLng, lpString ;translate the string ret Translate endp ;Just an info func. Shows a message or Default error if NULL Error proc lpString:DWORD .IF lpString==0 mov lpString, offset szError .ENDIF invoke MessageBox, NULL, lpString, addr szShortName, MB_OK ret Error endp ;ignores protocols that can't receive messages... IgnoreCheck proc pStri:DWORD invoke lstrcpy, offset szGeneral, pStri invoke lstrcat, offset szGeneral, offset PS_GETCAPS invoke CallService, offset szGeneral, PFLAGNUM_1, 0 and eax, PF1_IMRECV .IF eax!=0 mov eax, 1 .ENDIF ret IgnoreCheck endp Load proc link:DWORD invoke RtlMoveMemory, addr sPluginLink, link, sizeof PLUGINLINK ;get miranda proc struct IFDEF _UNICODE invoke lstrcpy, offset szGeneral, offset szOptGroup invoke MultiByteToWideChar, CP_ACP, MB_PRECOMPOSED, offset szGeneral, -1, offset szOptGroup, 7 invoke lstrcpy, offset szGeneral, offset szOptTitle invoke MultiByteToWideChar, CP_ACP, MB_PRECOMPOSED, offset szGeneral, -1, offset szOptTitle, 16 invoke lstrcpy, offset szGeneral, offset szTab1 invoke MultiByteToWideChar, CP_ACP, MB_PRECOMPOSED, offset szGeneral, -1, offset szTab1, 9 invoke lstrcpy, offset szGeneral, offset szTab2 invoke MultiByteToWideChar, CP_ACP, MB_PRECOMPOSED, offset szGeneral, -1, offset szTab2, 9 invoke lstrcpy, offset szGeneral, offset szAllContacts invoke MultiByteToWideChar, CP_ACP, MB_PRECOMPOSED, offset szGeneral, -1, offset szAllContacts, 19 invoke lstrcpy, offset szGeneral, offset szUnkContacts invoke MultiByteToWideChar, CP_ACP, MB_PRECOMPOSED, offset szGeneral, -1, offset szUnkContacts, 23 ENDIF mov sSystemTime.wYear, 1870 mov sSystemTime.wMonth, 1 mov sSystemTime.wDay, 1 mov sOptionsPage.cbSize, sizeof OPTIONSDIALOGPAGE ;set the option dialog's properties invoke Translate, offset szOptTitle IFDEF _UNICODE mov sOptionsPage.flags, ODPF_UNICODE ENDIF mov sOptionsPage.pszTitle, eax mov sOptionsPage.pfnDlgProc, offset TabOptions mov sOptionsPage.pszTemplate, 100 push hInstance pop sOptionsPage.hInstance push offset szOptGroup pop sOptionsPage.pszGroup invoke HookEvent, offset ME_DB_EVENT_ADDED, offset Message ;set the message hook mov hMsgHook, eax ;save hook hWnd invoke HookEvent, offset ME_OPT_INITIALISE, offset OptInit ;set the options hook mov hOptHook, eax ;save hook hWnd invoke HookEvent, offset ME_SYSTEM_MODULESLOADED, offset MdLoaded ;set the ModulesLoaded hook mov hMdLHook, eax ;save hook hWnd xor eax, eax ret Load Endp IcoLibEv proc C wParam:DWORD, lParam: DWORD invoke SendMessage, hDlgWnd, WM_IMGLIST, 0, 0 xor eax, eax ret IcoLibEv endp ;############################## ; Runs when all modules are loaded ;############################## MdLoaded proc C wParam:DWORD, lParam:DWORD invoke UnhookEvent, hMdLHook ;unhook invoke ServiceExists, offset MS_UPDATE_REGISTER .IF eax!=0 mov sUpdate.cbSize, sizeof UPDATE ;initialize updater struct mov sUpdate.szComponentName, offset szShortNamev .IF ddBeta==0 mov sUpdate.szVersionURL, offset szURL ;check if is Beta .ENDIF mov sUpdate.pbVersionPrefix, offset szURLKey push ddURLKeyLen pop sUpdate.cpbVersionPrefix mov sUpdate.szUpdateURL, offset szDnURL mov sUpdate.szBetaVersionURL, offset szBetaURL mov sUpdate.pbBetaVersionPrefix, offset szBetaURLKey push ddBetaURLKeyLen pop sUpdate.cpbBetaVersionPrefix mov sUpdate.szBetaUpdateURL, offset szBetaDnURL mov sUpdate.pbVersion, offset szVersion push ddVersionLen pop sUpdate.cpbVersion mov sUpdate.szBetaChangelogURL, offset szBetaChangelogURL invoke CallService, offset MS_UPDATE_REGISTER, 0, offset sUpdate ;register updater service .ENDIF ;registering icon in IcoLib invoke ServiceExists, offset MS_SKIN2_ADDICON .IF eax!=0 invoke GetModuleFileNameA, hInstance, offset szGeneral, 255 mov sSkinIconDesc.cbSize, sizeof SKINICONDESC mov sSkinIconDesc.pszSection, offset szShortName or ddFlags, 8 invoke Translate, offset szIlDesc mov sSkinIconDesc.pszDescription, eax mov sSkinIconDesc.pszName, offset szIlName mov sSkinIconDesc.pszDefaultFile, offset szGeneral mov sSkinIconDesc.iDefaultIndex, -IDI_PC invoke CallService, offset MS_SKIN2_ADDICON, 0, offset sSkinIconDesc invoke HookEvent, offset ME_SKIN2_ICONSCHANGED, offset IcoLibEv ;set the IconChanged hook mov hIcoLibEv, eax ;save hook hWnd .ENDIF xor eax, eax ret MdLoaded endp ;set CListControl style defaults ResetListOptions proc hCList:DWORD LOCAL Col, i:DWORD invoke SendMessage, hCList, CLM_SETBKBITMAP, 0, 0 invoke GetSysColor, COLOR_WINDOW mov Col, eax invoke SendMessage, hCList, CLM_SETBKCOLOR, Col, 0 invoke SendMessage, hCList, CLM_SETGREYOUTFLAGS, 0, 0 invoke SendMessage, hCList, CLM_SETLEFTMARGIN, 2, 0 invoke SendMessage, hCList, CLM_SETINDENT, 10, 0 invoke GetSysColor, COLOR_WINDOWTEXT mov Col, eax mov i, FONTID_MAX .WHILE i!=0 invoke SendMessage, hCList, CLM_SETTEXTCOLOR, i, Col dec i .ENDW mov sDBGetSetting.szModule, offset szOModule ;load the flags mov sDBGetSetting.szSetting, offset szOShowHidden mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_DWORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting .IF eax==0 .IF sDBVariant.VAR2!=0 invoke GetWindowLong, hCList, GWL_STYLE or eax, CLS_SHOWHIDDEN invoke SetWindowLong, hCList, GWL_STYLE, eax .ENDIF .ENDIF xor eax, eax ret ResetListOptions endp ;load per contact trigger settings from DB SetAllContactIcons proc hCList:DWORD LOCAL hContact, hItem, szProto, flags, flag:DWORD invoke CallService, offset MS_DB_CONTACT_FINDFIRST, 0, 0 mov hContact, eax invoke SendMessage, hCList, WM_TIMER, 14, 0 ;Note: Hack. Wait for the CList To be ready. Thanks to FYR .WHILE hContact!=0 invoke SendMessage, hCList, CLM_FINDCONTACT, hContact, 0 mov hItem, eax .IF eax!=0 invoke CallService, offset MS_PROTO_GETCONTACTBASEPROTO, hContact, 0 ;get PROTO for each contact mov szProto, eax .IF eax==0 mov flag, 1 mov flags, 1 .ELSE invoke IgnoreCheck, szProto ;Check PROTO Capabilities mov flags, eax mov sDBGetSetting.szModule, offset szOModule ;load settings mov sDBGetSetting.szSetting, offset szOEnabled mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_WORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, hContact, offset sDBGetSetting .IF eax==0 push sDBVariant.VAR2 pop flag .ELSE mov flag, 1 .ENDIF .ENDIF .IF flags!=0 ;finally set the necesarry image xor eax, eax ;Use (MAKELPARAM "column", "image") instead of just 0 invoke SendMessage, hCList, CLM_GETEXTRAIMAGE, hItem, eax .IF eax==0FFh .IF flag!=0 mov flag, 1 .ENDIF MAKELPARAM 0, flag invoke SendMessage, hCList, CLM_SETEXTRAIMAGE, hItem, eax .ENDIF .ENDIF .ENDIF invoke CallService, offset MS_DB_CONTACT_FINDNEXT, hContact, 0 mov hContact, eax .ENDW ret SetAllContactIcons endp ;Set group icons according to the contacts inside SetListGroupIcons proc hCList:DWORD, hFirstItem:DWORD, hParentItem:DWORD, groupChildCount:DWORD LOCAL typeOfFirst, iconOn, childCount, iImage, hItem, hChildItem:DWORD mov iconOn, 1 ;assume all are enabled mov childCount, 0 invoke SendMessage, hCList, CLM_GETITEMTYPE,hFirstItem, 0 mov typeOfFirst, eax ;check groups .IF typeOfFirst==CLCIT_GROUP push hFirstItem pop hItem .ELSE invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTGROUP, hFirstItem mov hItem, eax .ENDIF .WHILE hItem!=NULL invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_CHILD, hItem mov hChildItem, eax .IF eax!=0 invoke SetListGroupIcons, hCList, hChildItem, hItem, addr childCount .ENDIF .IF iconOn!=0 invoke SendMessage, hCList, CLM_GETEXTRAIMAGE, hItem, 0 .IF eax==0 mov iconOn, 0 .ENDIF .ENDIF invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTGROUP, hItem mov hItem, eax .ENDW ;check contacts .IF typeOfFirst==CLCIT_CONTACT push hFirstItem pop hItem .ELSE invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTCONTACT, hFirstItem mov hItem, eax .ENDIF .WHILE hItem!=0 invoke SendMessage, hCList, CLM_GETEXTRAIMAGE, hItem, 0 .IF iconOn!=0 .IF eax==0 mov iconOn, 0 .ENDIF .ENDIF .IF eax!=0FFh inc childCount .ENDIF invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTCONTACT, hItem mov hItem, eax .ENDW ;set group icons .IF childCount==0 mov eax, 0FFh .ELSEIF iconOn==0 mov eax, 0 .ELSE mov eax, 1 .ENDIF MAKELPARAM 0, eax invoke SendMessage, hCList, CLM_SETEXTRAIMAGE, hParentItem, eax .IF groupChildCount!=0 mov eax, [groupChildCount] add eax, childCount mov [groupChildCount], eax .ENDIF ret SetListGroupIcons endp ;set group child icons SetAllChildIcons proc hCList:DWORD, hFirstItem:DWORD, iColumn:DWORD, iImage:DWORD LOCAL typeOfFirst, iOldIcon, hItem, hChildItem:DWORD invoke SendMessage, hCList, CLM_GETITEMTYPE, hFirstItem, 0 mov typeOfFirst, eax ;set icons for groups .IF typeOfFirst==CLCIT_GROUP push hFirstItem pop hItem .ELSE invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTGROUP, hFirstItem mov hItem, eax .ENDIF .WHILE hItem!=0 invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_CHILD, hItem mov hChildItem, eax .IF hChildItem!=0 invoke SetAllChildIcons, hCList, hChildItem, iColumn, iImage .ENDIF invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTGROUP, hItem mov hItem, eax .ENDW ;set icons for contacts .IF typeOfFirst==CLCIT_CONTACT push hFirstItem pop hItem .ELSE invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTCONTACT, hFirstItem mov hItem, eax .ENDIF .WHILE hItem!=0 invoke SendMessage, hCList, CLM_GETEXTRAIMAGE, hItem, iColumn mov iOldIcon, eax .IF iOldIcon!=0FFh mov eax, iImage .IF iOldIcon!=eax MAKELPARAM iColumn, iImage invoke SendMessage, hCList, CLM_SETEXTRAIMAGE, hItem, eax mov sDBGetSetting.szModule, offset szOMetaContacts ;load settings mov sDBGetSetting.szSetting, offset szOMetaCount mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_WORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, hItem, offset sDBGetSetting .IF eax==0 invoke MetaConClick, hItem, sDBVariant.VAR2, iImage .ENDIF .ENDIF .ENDIF invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTCONTACT, hItem mov hItem, eax .ENDW ret SetAllChildIcons endp ;set icons to contacts Not on list SetUnkChildIcons proc hCList:DWORD, hFirstItem:DWORD, iColumn:DWORD, iImage:DWORD LOCAL typeOfFirst, iOldIcon, hItem, hChildItem:DWORD invoke SendMessage, hCList, CLM_GETITEMTYPE, hFirstItem, 0 mov typeOfFirst, eax ;set icons for groups .IF typeOfFirst==CLCIT_GROUP push hFirstItem pop hItem .ELSE invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTGROUP, hFirstItem mov hItem, eax .ENDIF .WHILE hItem!=0 invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_CHILD, hItem mov hChildItem, eax .IF hChildItem!=0 invoke SetUnkChildIcons, hCList, hChildItem, iColumn, iImage .ENDIF invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTGROUP, hItem mov hItem, eax .ENDW ;set icons for contacts .IF typeOfFirst==CLCIT_CONTACT push hFirstItem pop hItem .ELSE invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTCONTACT, hFirstItem mov hItem, eax .ENDIF .WHILE hItem!=0 invoke SendMessage, hCList, CLM_GETEXTRAIMAGE, hItem, iColumn mov iOldIcon, eax .IF iOldIcon!=0FFh mov eax, iImage .IF iOldIcon!=eax mov sDBGetSetting.szModule, offset szOCList mov sDBGetSetting.szSetting, offset szONotOnList mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_BYTE invoke CallService, offset MS_DB_CONTACT_GETSETTING, hItem, offset sDBGetSetting .IF eax==0 lea esi, sDBVariant.VAR2 mov al, [esi] .IF al!=0 MAKELPARAM iColumn, iImage invoke SendMessage, hCList, CLM_SETEXTRAIMAGE, hItem, eax .ENDIF .ENDIF .ENDIF .ENDIF invoke SendMessage, hCList, CLM_GETNEXTITEM, CLGN_NEXTCONTACT, hItem mov hItem, eax .ENDW ret SetUnkChildIcons endp MetaConClick proc hContact:DWORD, iCount:DWORD, iValue: DWORD dec iCount .WHILE iCount!=-1 invoke CallService, offset MS_MC_GETSUBCONTACT, hContact, iCount .IF eax!=0 mov ebx, eax MAKELPARAM 0, 0 invoke SendDlgItemMessage, hDlgWnd, IDC_CLIST, CLM_GETEXTRAIMAGE, ebx, eax .IF eax!= 0FFh MAKELPARAM 0, iValue invoke SendDlgItemMessage, hDlgWnd, IDC_CLIST, CLM_SETEXTRAIMAGE, ebx, eax .ENDIF .ENDIF dec iCount .ENDW ret MetaConClick endp MetaSubClick proc hContact:DWORD LOCAL iVal, iCounter:DWORD invoke CallService, offset MS_MC_GETMETACONTACT, hContact, 0 .IF eax!=0 mov hContact, eax mov sDBGetSetting.szModule, offset szOMetaContacts ;load settings mov sDBGetSetting.szSetting, offset szOMetaCount mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_WORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, hContact, offset sDBGetSetting .IF eax==0 push sDBVariant.VAR2 pop iCounter dec iCounter mov iVal, 1 .WHILE iCounter!=-1 invoke CallService, offset MS_MC_GETSUBCONTACT, hContact, iCounter .IF eax!=0 mov ebx, eax MAKELPARAM 0, 0 invoke SendDlgItemMessage, hDlgWnd, IDC_CLIST, CLM_GETEXTRAIMAGE, ebx, eax .IF eax==0 mov iVal, 0 .ENDIF .ENDIF dec iCounter .ENDW .ENDIF .ENDIF MAKELPARAM 0, iVal invoke SendDlgItemMessage, hDlgWnd, IDC_CLIST, CLM_SETEXTRAIMAGE, hContact, eax ret MetaSubClick endp ;############################## ; Options hook proc ;############################## OptInit proc C wParam:DWORD, lParam:DWORD mov eax, wParam ;init the options dialog invoke CallService, addr MS_OPT_ADDPAGE, eax, addr sOptionsPage xor eax, eax ret OptInit Endp ;############################## ; Message hook proc ;############################## Message proc C wParam:DWORD, lParam:DWORD LOCAL hContact:DWORD push lParam ;save hDBEvent pop ddVar1 invoke CallService, offset MS_DB_EVENT_GETCONTACT, ddVar1, 0 mov hContact, eax mov sDBGetSetting.szModule, offset szOModule ;load the flags mov sDBGetSetting.szSetting, offset szOEnabled mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_DWORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, hContact, offset sDBGetSetting .IF eax==0 .IF sDBVariant.VAR2==0 ret .ENDIF .ENDIF mov sDBGetSetting.szModule, offset szOCList mov sDBGetSetting.szSetting, offset szONotOnList mov sDBVariant.VAR1, DBVT_BYTE invoke CallService, offset MS_DB_CONTACT_GETSETTING, hContact, offset sDBGetSetting .IF eax==0 push esi lea esi, sDBVariant.VAR2 mov al, [esi] pop esi .IF al!=0 mov sDBGetSetting.szModule, offset szOModule mov sDBVariant.VAR1, DBVT_DWORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting .IF eax==0 .IF sDBVariant.VAR2==0 ret .ENDIF .ENDIF .ENDIF .ENDIF mov sDBGetSetting.szModule, offset szOModule mov sDBGetSetting.szSetting, offset szOFlags mov sDBVariant.VAR1, DBVT_DWORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting push sDBVariant.VAR2 ;backup the value pop ddVar3 push ddVar3 pop ddVar2 and sDBVariant.VAR2, 1 ;select a flag .IF eax==0 .IF sDBVariant.VAR2==0 ret .ENDIF .ENDIF invoke CallService, offset MS_CLIST_GETSTATUSMODE, 0, 0 .IF eax!=0 ;on error, status=offline sub eax, IDC_ENABLED .ENDIF push esi mov esi, 1 .WHILE eax!=0 ;generate flag from status shl esi, 1 dec eax .ENDW and ddVar3, esi ;check status filter pop esi .IF ddVar3==0 xor eax, eax ret .ENDIF mov sDBEventInfo.cbSize, sizeof DBEVENTINFO ;load message info and protocol mov sDBEventInfo.cbBlob, 150 mov sDBEventInfo.pBlob, offset szGeneral invoke CallService, offset MS_DB_EVENT_GET, ddVar1, offset sDBEventInfo mov sDBGetSetting.szModule, offset szOModule ;load protocol settings push sDBEventInfo.szModule pop sDBGetSetting.szSetting mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_DWORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting .IF eax==0 .IF sDBVariant.VAR2==0 ret .ENDIF .ENDIF mov eax, sDBEventInfo.eventType ;check for message type push esi push edi mov edi, offset IDC_ETYPE_MESSAGE_V mov esi, 800h .WHILE esi!=20000h && eax!=[edi] ;list message types add edi, 08h shl esi, 1 .ENDW and esi, 1FFFFh and esi, ddVar2 mov ddVar3, esi pop edi pop esi .IF ddVar3==0 ret .ENDIF push ecx ;check time trigger push ebx invoke GetSystemTime, addr sSystemTime ;local time xor eax, eax mov ax, sSystemTime.wHour shl eax, 16 mov ax, sSystemTime.wMinute shl ax, 8 shr eax, 8 mov ddVar2, eax mov sDBGetSetting.szSetting, offset szOTime ;load DB settings invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting .IF eax==0 mov eax, sDBVariant.VAR2 xor ebx, ebx ;check time mov bx, ax shr eax, 16 mov ecx, ddVar2 mov ddVar3, 0 .IF eaxebx .IF ecx>=eax mov ddVar3, 1 .ELSEIF ebx>=ecx mov ddVar3, 1 .ENDIF .ELSE mov ddVar3, 1 .ENDIF .ENDIF pop ebx pop ecx .IF ddVar3 invoke SendMessage, HWND_BROADCAST, WM_SYSCOMMAND, SC_MONITORPOWER, -1 ;turn monitor on .ENDIF xor eax, eax ret Message Endp ;############################## ; First tab event proc ;############################## Options1 proc, dhWnd:DWORD, uMsg:DWORD, wParam:DWORD, lParam:DWORD .IF uMsg==WM_INITDIALOG ;if user opens options invoke SetWindowPos, dhWnd, HWND_TOP, sDlgHdr.rcDisplay.left, sDlgHdr.rcDisplay.top, 0, 0, SWP_NOSIZE .IF ddInt==0 or ddFlags, 2 push esi push edi mov edi, offset HC_ENABLED ;get control hWnd's from ID's mov esi, IDC_ENABLED .WHILE esi<=IDC_ENDTIME invoke GetDlgItem, dhWnd, esi mov [edi], eax inc esi add edi,4 .ENDW pop edi pop esi mov ddInt, 1 invoke SendMessage, HC_STARTTIME, DTM_SETFORMAT, 0, addr szDtFormat ;datetime pickers format invoke SendMessage, HC_ENDTIME, DTM_SETFORMAT, 0, addr szDtFormat mov sDBGetSetting.szModule, offset szOModule ;load time triggers mov sDBGetSetting.szSetting, offset szOTime mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_DWORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting mov eax, sDBVariant.VAR2 ;get start and end time push ax and ax, 00FFh mov sSystemTime.wMinute, ax pop ax shr ax, 8 mov sSystemTime.wHour, ax push eax invoke SendMessage, HC_ENDTIME, DTM_SETSYSTEMTIME, GDT_VALID, addr sSystemTime pop eax shr eax, 16 push ax and ax, 00FFh mov sSystemTime.wMinute, ax pop ax shr ax, 8 mov sSystemTime.wHour, ax invoke SendMessage, HC_STARTTIME, DTM_SETSYSTEMTIME, GDT_VALID, addr sSystemTime mov sDBGetSetting.szModule, offset szOModule mov sDBGetSetting.szSetting, offset szOFlags ;load flags mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_DWORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting push edi push ebx mov edi, offset HC_ENABLED ;disable controls if plugin disabled push sDBVariant.VAR2 pop sDBVariant.VAR3 mov ebx, 01h .WHILE edi<=offset HC_ETYPE_FILE and sDBVariant.VAR2, ebx .IF eax!=0 || (eax==0 && sDBVariant.VAR2 !=0) push eax Invoke SendMessage, [edi], BM_SETCHECK, BST_CHECKED, 0 pop eax .ENDIF shl ebx, 1 push sDBVariant.VAR3 pop sDBVariant.VAR2 add edi, 04h .ENDW pop ebx pop edi invoke CallService, offset MS_PROTO_ENUMPROTOCOLS, offset ddVar1, offset ddVar2 ;get protocol list push esi ;then load them into list box push edi push ebx mov esi, ddVar1 mov edi, esi dec edi shl edi, 2 add edi, ddVar2 mov sDBGetSetting.szModule, offset szOModule ;and also check if it's enabled mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_DWORD .WHILE esi!=0 mov ebx, [edi] invoke IgnoreCheck, [ebx+04h] ;check for ignore list .IF eax!=0 mov eax, [ebx+08h] .IF eax==03E8h ;check if it really is a protocol push [ebx+04h] pop sDBGetSetting.szSetting invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting .IF eax!=0 mov sDBVariant.VAR2, 01h .ENDIF invoke SendMessage, HC_PROTO, LB_INSERTSTRING, 0, [ebx+04h] ;add it to the list invoke SendMessage, HC_PROTO, LB_SETSEL, sDBVariant.VAR2, 0 .ENDIF .ENDIF sub edi, 04h dec esi .ENDW pop ebx pop edi pop esi or ddFlags, 6 invoke PostMessage, dhWnd, WM_COMMAND, IDC_ENABLED, dhWnd .ENDIF .ELSEIF uMsg==WM_COMMAND ;if sth. happened in the dialog mov eax, wParam .IF lParam!=0 .IF ax==IDC_ENABLED push edi ;enable/disable the controls on the dialog push esi invoke IsDlgButtonChecked, dhWnd, IDC_ENABLED mov esi, eax mov edi, offset HC_STATUS_ONLINE .WHILE edi<=offset HC_ENDTIME invoke EnableWindow, [edi], esi add edi, 04h .ENDW pop esi pop edi .ENDIF .ENDIF mov eax, ddFlags and eax, 6 .IF eax==0 invoke GetParent, dhWnd invoke GetParent, eax push eax invoke SendMessage, eax, PSM_CHANGED, 0, 0 ;enable the Apply button pop eax invoke GetParent, eax invoke SendMessage, eax, PSM_CHANGED, 0, 0 ;enable the Apply button .ELSEIF ddFlags==6 and ddFlags, -7 .ENDIF .ELSEIF uMsg==WM_NOTIFY .IF wParam==IDC_STARTTIME || wParam==IDC_ENDTIME ;if a message from time controls mov edi, lParam assume edi:ptr NMHDR .IF [edi].code==DTN_DATETIMECHANGE invoke GetParent, dhWnd invoke GetParent, eax push eax invoke SendMessage, eax, PSM_CHANGED, 0, 0 ;enable the Apply button pop eax invoke GetParent, eax invoke SendMessage, eax, PSM_CHANGED, 0, 0 ;enable the Apply button .ENDIF assume edi:nothing .ENDIF mov eax, lParam ;check if apply or OK pressed .IF eax==0 xor eax, eax ret .ENDIF mov eax, [eax+8] add eax, 201 .IF eax==0 push esi mov esi, offset HC_ETYPE_FILE ;start saving all the settings xor ebx, ebx .WHILE esi>=offset HC_ENABLED shl ebx, 1 ;shift ebx, to make room for next invoke SendMessage, [esi], BM_GETCHECK, 0, 0 ;get state of buttons, 1=checked, 0=unchecked .IF eax==BST_CHECKED xor eax, eax inc eax .ELSE xor eax, eax .ENDIF or ebx, eax ;add it to ebx sub esi, 4 .ENDW mov sDBWriteSetting.szModule, offset szOModule ;save them mov sDBWriteSetting.szSetting, offset szOFlags mov sDBWriteSetting.VAR1, DBVT_DWORD mov sDBWriteSetting.VAR2, ebx invoke CallService, offset MS_DB_CONTACT_WRITESETTING, 0, offset sDBWriteSetting invoke SendMessage, HC_STARTTIME, DTM_GETSYSTEMTIME, 0, addr sSystemTime ;get start time mov ax, sSystemTime.wHour shl eax, 16 mov ax, sSystemTime.wMinute shl ax, 8 shl eax, 8 push eax invoke SendMessage, HC_ENDTIME, DTM_GETSYSTEMTIME, 0, addr sSystemTime ;get end time pop eax mov bx, sSystemTime.wHour shl ebx, 16 mov bx, sSystemTime.wMinute shl bx, 8 shr ebx, 8 mov ax, bx mov sDBWriteSetting.szSetting, offset szOTime ;save time options in DB mov sDBWriteSetting.VAR2, eax invoke CallService, offset MS_DB_CONTACT_WRITESETTING, 0, offset sDBWriteSetting invoke CallService, offset MS_PROTO_ENUMPROTOCOLS, offset ddVar1, offset ddVar2 ;get protocol list push esi ;then load them into list box push edi push ebx mov esi, ddVar1 mov edi, ddVar2 mov ddVar3, 0 mov sDBWriteSetting.szModule, offset szOModule ;and also check if it's enabled mov sDBWriteSetting.VAR1, DBVT_DWORD .WHILE esi!=0 mov ebx, [edi] invoke IgnoreCheck, [ebx+04h] ;check for ignore list .IF eax!=0 mov eax, [ebx+08h] .IF eax==03E8h ;check if it really is a protocol invoke SendMessage, HC_PROTO, LB_GETSEL, ddVar3, 0 mov sDBWriteSetting.VAR2, eax push [ebx+04h] pop sDBWriteSetting.szSetting invoke CallService, offset MS_DB_CONTACT_WRITESETTING, 0, offset sDBWriteSetting inc ddVar3 .ENDIF .ENDIF add edi, 04h dec esi .ENDW pop ebx pop edi pop esi .ENDIF .ENDIF xor eax,eax ret Options1 endp ;############################## ; Second tab event proc ;############################## Options2 proc, dhWnd:DWORD, uMsg:DWORD, wParam:DWORD, lParam:DWORD LOCAL hContact, hItem, hitFlags, iImage, itemType, i:DWORD push dhWnd pop hDlgWnd .IF uMsg==WM_INITDIALOG invoke SetWindowPos, dhWnd, HWND_TOP, sDlgHdr.rcDisplay.left, sDlgHdr.rcDisplay.top, 0, 0, SWP_NOSIZE invoke GetDlgItem, dhWnd, IDC_SHOWHIDDEN mov HC_SHOWHIDDEN, eax mov sDBGetSetting.szModule, offset szOModule ;load the flags mov sDBGetSetting.szSetting, offset szOShowHidden mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_DWORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting .IF eax==0 .IF sDBVariant.VAR2!=0 Invoke SendMessage, HC_SHOWHIDDEN, BM_SETCHECK, BST_CHECKED, 0 .ENDIF .ENDIF invoke SendMessage, dhWnd, WM_IMGLIST, wParam, lParam invoke GetDlgItem, dhWnd, IDC_CLIST mov HC_CLIST, eax invoke ResetListOptions, HC_CLIST invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_SETEXTRACOLUMNS, 1, 0 ;set no of icon columns mov sClcInfoItem.cbSize, sizeof CLCINFOITEM ;add additional items mov sClcInfoItem.flags, CLCIIF_GROUPFONT invoke Translate, offset szAllContacts ;** All contacts ** mov sClcInfoItem.pszText, eax invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_ADDINFOITEM, 0, addr sClcInfoItem mov hItemAll, eax invoke Translate, offset szUnkContacts ;** Unknown contacts ** mov sClcInfoItem.pszText, eax invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_ADDINFOITEM, 0, addr sClcInfoItem mov hItemUnk, eax invoke SetAllContactIcons, HC_CLIST ;Init control values invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETNEXTITEM, CLGN_ROOT, 0 invoke SetListGroupIcons, HC_CLIST, eax, hItemAll, NULL mov sDBGetSetting.szModule, offset szOModule ;load the flags mov sDBGetSetting.szSetting, offset szONotOnList mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_DWORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, 0, offset sDBGetSetting .IF eax==0 .IF sDBVariant.VAR2!=0 mov eax, 1 .ENDIF .ELSE mov eax, 1 .ENDIF push eax invoke SetUnkChildIcons, HC_CLIST, hItemUnk, 0, eax pop eax MAKELPARAM 0, eax invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_SETEXTRAIMAGE, hItemUnk, eax .ELSEIF uMsg==WM_IMGLIST invoke GetVersion ;check win version .IF al==5 .IF ah!=0 mov eax, ILC_COLOR32 or ILC_MASK .ELSEIF mov eax, ILC_COLOR16 or ILC_MASK .ENDIF .ENDIF invoke ImageList_Create, 16, 16, eax, 3, 3 ;create image list mov hIml, eax invoke LoadIcon, hApp, IDI_SMALLDOT ;add icon push eax invoke ImageList_AddIcon, hIml, eax pop eax invoke DeleteObject, eax invoke CallService, offset MS_SKIN2_GETICON, 0, offset szIlName invoke ImageList_AddIcon, hIml, eax invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_SETEXTRAIMAGELIST, 0, hIml ;link image list to CList .ELSEIF uMsg==WM_SETFOCUS invoke SetFocus, HC_CLIST .ELSEIF uMsg==WM_COMMAND mov eax, wParam .IF lParam!=0 .IF ax==IDC_SHOWHIDDEN mov sDBWriteSetting.szModule, offset szOModule mov sDBWriteSetting.szSetting, offset szOShowHidden mov sDBWriteSetting.VAR1, DBVT_DWORD invoke SendMessage, HC_SHOWHIDDEN, BM_GETCHECK, 0, 0 .IF eax==BST_CHECKED mov sDBWriteSetting.VAR2, 1 invoke GetWindowLong, HC_CLIST, GWL_STYLE or eax, CLS_SHOWHIDDEN .ELSE mov sDBWriteSetting.VAR2, 0 invoke GetWindowLong, HC_CLIST, GWL_STYLE mov ebx, -CLS_SHOWHIDDEN dec ebx and eax, ebx .ENDIF invoke SetWindowLong, HC_CLIST, GWL_STYLE, eax invoke CallService, offset MS_DB_CONTACT_WRITESETTING, 0, offset sDBWriteSetting invoke SendMessage, HC_CLIST, CLM_SETUSEGROUPS, 1, 0 invoke SetAllContactIcons, HC_CLIST invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETNEXTITEM, CLGN_ROOT, 0 invoke SetListGroupIcons, HC_CLIST, eax, hItemAll, NULL .ENDIF .ENDIF .ELSEIF uMsg==WM_NOTIFY ;if sth changes mov edi, lParam assume edi:ptr NMHDR .IF [edi].idFrom==IDC_CLIST .IF [edi].code==CLN_NEWCONTACT invoke SetAllContactIcons, HC_CLIST invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETNEXTITEM, CLGN_ROOT, 0 invoke SetListGroupIcons, HC_CLIST, eax, hItemAll, NULL .ELSEIF [edi].code==CLN_LISTREBUILT invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETNEXTITEM, CLGN_ROOT, 0 invoke SetListGroupIcons, HC_CLIST, eax, hItemAll, NULL .ELSEIF [edi].code==CLN_CONTACTMOVED invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETNEXTITEM, CLGN_ROOT, 0 invoke SetListGroupIcons, HC_CLIST, eax, hItemAll, NULL .ELSEIF [edi].code==CLN_OPTIONSCHANGED invoke ResetListOptions, HC_CLIST .ELSEIF [edi].code==NM_CLICK ;Click on the CList assume edi:ptr NMCLISTCONTROL .IF [edi].iColumn!=-1 MAKELPARAM [edi].pt.x, [edi].pt.y invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_HITTEST, addr hitFlags, eax mov hItem, eax .IF hItem!=0 and hitFlags, CLCHT_ONITEMEXTRA ;if click on icon, then analyze and edit .IF hitFlags!=0 invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETEXTRAIMAGE, hItem, [edi].iColumn .IF eax==0 mov iImage, 1 .ELSE mov iImage, 0 .ENDIF MAKELPARAM [edi].iColumn, 0 invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETEXTRAIMAGE, hItem, eax .IF eax!= 0FFh MAKELPARAM [edi].iColumn, iImage invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_SETEXTRAIMAGE, hItem, eax invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETITEMTYPE, hItem, 0 mov itemType, eax .IF itemType==CLCIT_CONTACT ;if click on contact MAKELPARAM [edi].iColumn, iImage invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_SETEXTRAIMAGE, hItem, eax mov sDBGetSetting.szModule, offset szOMetaContacts ;load settings mov sDBGetSetting.szSetting, offset szOMetaCount mov sDBGetSetting.pValue, offset sDBVariant mov sDBVariant.VAR1, DBVT_WORD invoke CallService, offset MS_DB_CONTACT_GETSETTING, hItem, offset sDBGetSetting .IF eax==0 ;is MetaContact invoke MetaConClick, hItem, sDBVariant.VAR2, iImage .ELSE mov sDBGetSetting.szSetting, offset szOMetaLink invoke CallService, offset MS_DB_CONTACT_GETSETTING, hItem, offset sDBGetSetting .IF eax==0 ;is subcontact invoke MetaSubClick, hItem .ENDIF .ENDIF .ENDIF .IF itemType==CLCIT_INFO ;if click on extra item mov eax, hItem .IF eax==hItemAll invoke SetAllChildIcons, HC_CLIST, hItem, [edi].iColumn, iImage .ELSEIF eax==hItemUnk invoke SetUnkChildIcons, HC_CLIST, hItem, [edi].iColumn, iImage .ENDIF .ENDIF .IF itemType==CLCIT_GROUP ;if click on group invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETNEXTITEM, CLGN_CHILD, hItem mov hItem, eax .IF hItem!=0 invoke SetAllChildIcons, HC_CLIST, hItem, [edi].iColumn, iImage .ENDIF .ENDIF invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETNEXTITEM, CLGN_ROOT, 0 invoke SetListGroupIcons, HC_CLIST, eax, hItemAll, NULL invoke GetParent, dhWnd invoke GetParent, eax push eax invoke SendMessage, eax, PSM_CHANGED, 0, 0 ;enable the Apply button pop eax invoke GetParent, eax invoke SendMessage, eax, PSM_CHANGED, 0, 0 ;enable the Apply button .ENDIF .ENDIF .ENDIF .ENDIF assume edi:ptr NMHDR .ENDIF .ELSEIF [edi].idFrom==0 .IF [edi].code==PSN_APPLY ;if OK/Apply pressed. Save options invoke CallService, addr MS_DB_CONTACT_FINDFIRST, 0, 0 mov hContact, eax .WHILE hContact!=0 invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_FINDCONTACT, hContact, 0 mov hItem, eax .IF eax!=0 xor eax, eax ;Use (MAKELPARAM "column", "image") instead of just 0 invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETEXTRAIMAGE, hItem, eax mov sDBWriteSetting.szModule, offset szOModule mov sDBWriteSetting.szSetting, offset szOEnabled mov sDBWriteSetting.VAR1, DBVT_DWORD mov sDBWriteSetting.VAR2, eax invoke CallService, offset MS_DB_CONTACT_WRITESETTING, hContact, offset sDBWriteSetting .ENDIF invoke CallService, addr MS_DB_CONTACT_FINDNEXT, hContact, 0 mov hContact, eax .ENDW invoke SendDlgItemMessage, dhWnd, IDC_CLIST, CLM_GETEXTRAIMAGE, hItemUnk, 0 mov sDBWriteSetting.szModule, offset szOModule mov sDBWriteSetting.szSetting, offset szONotOnList mov sDBWriteSetting.VAR1, DBVT_DWORD mov sDBWriteSetting.VAR2, eax invoke CallService, offset MS_DB_CONTACT_WRITESETTING, 0, offset sDBWriteSetting .ENDIF .ENDIF assume edi:nothing .ELSEIF uMsg==WM_DESTROY invoke ImageList_Destroy, hIml ;Free used resources .ENDIF xor eax, eax ret Options2 endp TabOptions proc, dhWnd:DWORD, uMsg:DWORD, wParam:DWORD, lParam:DWORD push dhWnd pop sDlgHdr.hDlg .IF uMsg==WM_INITDIALOG ;if user opens options mov ddInt, 0 invoke InitCommonControls invoke GetDlgItem, dhWnd, 1000 ;get hWnd of tabs control mov sDlgHdr.hTab, eax mov edi, offset sTCITEM ;insert tabs mov eax, TCIF_TEXT mov [edi], eax invoke Translate, offset szTab1 ;translate Tab name IFDEF _UNICODE mov sTCITEM.pszText, eax invoke SendMessage, sDlgHdr.hTab, TCM_INSERTITEMW, 0, addr sTCITEM ELSE mov sTCITEM.pszText, eax invoke SendMessage, sDlgHdr.hTab, TCM_INSERTITEMA, 0, addr sTCITEM ENDIF mov sDlgHdr.hDisplay, NULL invoke SetRectEmpty, addr sDlgHdr.rcDisplay invoke SendMessage, sDlgHdr.hTab, TCM_ADJUSTRECT, FALSE, addr sDlgHdr.rcDisplay invoke FindResource, hInstance, 101, RT_DIALOG ;load first tab in memory invoke LoadResource, hInstance, eax invoke LockResource, eax invoke CreateDialogIndirectParam, hInstance, eax, sDlgHdr.hTab, Options1, NULL mov sDlgHdr.hTab1, eax mov sDlgHdr.hDisplay, eax invoke Translate, offset szTab2 ;translate Tab name IFDEF _UNICODE mov sTCITEM.pszText, eax invoke SendMessage, sDlgHdr.hTab, TCM_INSERTITEMW, 1, addr sTCITEM ELSE mov sTCITEM.pszText, eax invoke SendMessage, sDlgHdr.hTab, TCM_INSERTITEMA, 1, addr sTCITEM ENDIF invoke FindResource, hInstance, 102, RT_DIALOG ;load second tab in memory invoke LoadResource, hInstance, eax invoke LockResource, eax invoke CreateDialogIndirectParam, hInstance, eax, sDlgHdr.hTab, Options2, NULL mov sDlgHdr.hTab2, eax invoke ShowWindow, sDlgHdr.hTab2, SW_HIDE mov sLngPackDialog.cbSize, sizeof LANGPACKTRANSLATEDIALOG mov sLngPackDialog.flags, 0 push dhWnd pop sLngPackDialog.hwndDlg mov sLngPackDialog.ignoreControls, 0 invoke CallService, offset MS_LANGPACK_TRANSLATEDIALOG, LPTDF_NOTITLE, offset sLngPackDialog ;translate dialogs .ELSEIF uMsg==WM_NOTIFY .IF wParam==1000 ;if message from tab control mov edi, lParam assume edi:ptr NMHDR .IF [edi].code==TCN_SELCHANGE ;if tab changed .IF sDlgHdr.hDisplay!=0 invoke ShowWindow, sDlgHdr.hDisplay, SW_HIDE ;hide old tab .ENDIF invoke SendMessage, sDlgHdr.hTab, TCM_GETCURSEL, 0, 0 ;get current tab and show it .IF eax==0 mov eax, sDlgHdr.hTab1 .ELSEIF eax==1 mov eax, sDlgHdr.hTab2 .ELSE invoke Error, 0 .ENDIF mov sDlgHdr.hDisplay, eax invoke ShowWindow, sDlgHdr.hDisplay, SW_SHOW .ENDIF assume edi:nothing .ELSEIF invoke SendMessage, sDlgHdr.hTab1, WM_NOTIFY, wParam, lParam invoke SendMessage, sDlgHdr.hTab2, WM_NOTIFY, wParam, lParam .ENDIF .ENDIF xor eax, eax ret TabOptions endp Unload proc invoke UnhookEvent, hMsgHook ;unhook events and exit invoke UnhookEvent, hOptHook invoke UnhookEvent, hIcoLibEv xor eax, eax ret Unload Endp End DllMain