summaryrefslogtreecommitdiff
path: root/plugins/QuickMessages/src
diff options
context:
space:
mode:
Diffstat (limited to 'plugins/QuickMessages/src')
-rw-r--r--plugins/QuickMessages/src/Utils.cpp609
-rw-r--r--plugins/QuickMessages/src/Utils.h78
-rw-r--r--plugins/QuickMessages/src/main.cpp363
-rw-r--r--plugins/QuickMessages/src/options.cpp1166
-rw-r--r--plugins/QuickMessages/src/quickmessages.h84
-rw-r--r--plugins/QuickMessages/src/resource.h47
6 files changed, 2347 insertions, 0 deletions
diff --git a/plugins/QuickMessages/src/Utils.cpp b/plugins/QuickMessages/src/Utils.cpp
new file mode 100644
index 0000000000..9531268524
--- /dev/null
+++ b/plugins/QuickMessages/src/Utils.cpp
@@ -0,0 +1,609 @@
+/*
+Quick Messages plugin for Miranda IM
+
+Copyright (C) 2008 Danil Mozhar
+
+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 3 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, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "quickmessages.h"
+
+ListData* ButtonsList[100];
+
+SortedList* QuickList=NULL;
+
+
+typedef void (*ItemDestuctor)(void*);
+
+
+int sstSortButtons(const void * vmtbi1, const void * vmtbi2)
+ {
+ ButtonData * mtbi1=(ButtonData *)*((ButtonData ** )vmtbi1);
+ ButtonData * mtbi2=(ButtonData *)*((ButtonData ** )vmtbi2);
+ if (mtbi1==NULL || mtbi2==NULL) return (mtbi1-mtbi2);
+ return mtbi1->dwPos-mtbi2->dwPos;
+ }
+
+int sstQuickSortButtons(const void * vmtbi1, const void * vmtbi2)
+ {
+ QuickData * mtbi1=(QuickData *)*((QuickData ** )vmtbi1);
+ QuickData * mtbi2=(QuickData *)*((QuickData ** )vmtbi2);
+ if (mtbi1==NULL || mtbi2==NULL) return (mtbi1-mtbi2);
+ return mtbi1->dwPos-mtbi2->dwPos;
+ }
+
+
+int sstOpSortButtons(const void * vmtbi1, const void * vmtbi2)
+ {
+ ButtonData * mtbi1=(ButtonData *)*((ButtonData ** )vmtbi1);
+ ButtonData * mtbi2=(ButtonData *)*((ButtonData ** )vmtbi2);
+ if (mtbi1==NULL || mtbi2==NULL) return (mtbi1-mtbi2);
+ return mtbi1->dwOPPos-mtbi2->dwOPPos;
+ }
+
+
+void li_ListDestruct(SortedList *pList, ItemDestuctor pItemDestructor)
+ {
+ int i=0;
+ if (!pList) return;
+ for (i=0; i<pList->realCount; i++) pItemDestructor(pList->items[i]);
+ List_Destroy(pList);
+ mir_free(pList);
+ }
+
+void li_RemoveDestruct(SortedList *pList, int index, ItemDestuctor pItemDestructor)
+ {
+ if (index>=0 && index<pList->realCount)
+ {
+ pItemDestructor(pList->items[index]);
+ List_Remove(pList, index);
+ }
+ }
+
+void li_RemovePtrDestruct(SortedList *pList, void * ptr, ItemDestuctor pItemDestructor)
+ {
+ if (List_RemovePtr(pList, ptr))
+ pItemDestructor(ptr);
+ }
+
+void li_SortList(SortedList *pList, FSortFunc pSortFunct)
+ {
+ FSortFunc pOldSort=pList->sortFunc;
+ int i;
+ if (!pSortFunct) pSortFunct=pOldSort;
+ pList->sortFunc=NULL;
+ for (i=0; i<pList->realCount-1; i++)
+ if (pOldSort(pList->items[i],pList->items[i+1])<0)
+ {
+ void * temp=pList->items[i];
+ pList->items[i]=pList->items[i+1];
+ pList->items[i+1]=temp;
+ i--;
+ if (i>0) i--;
+ }
+ pList->sortFunc=pOldSort;
+ }
+
+void li_ZeroQuickList(SortedList *pList)
+ {
+ int i;
+ for (i=0; i<pList->realCount; i++)
+ {
+ QuickData * qd=(QuickData *)pList->items[i];
+ qd->dwPos=0;
+ qd->bIsService=0;
+ qd->ptszValue=NULL;
+ qd->ptszValueName=NULL;
+ List_Remove(pList, i);
+ i--;
+ }
+ }
+
+static void listdestructor(void * input)
+ {
+ ButtonData * cbdi=(ButtonData *)input;
+
+ if(cbdi->pszName!=cbdi->pszOpName)
+ {
+ if(cbdi->pszOpName)
+ mir_free(cbdi->pszOpName);
+ if(cbdi->pszName)
+ mir_free(cbdi->pszName);
+ }
+ else if(cbdi->pszName)
+ mir_free(cbdi->pszName);
+
+ if(cbdi->pszValue!=cbdi->pszOpValue)
+ {
+ if(cbdi->pszOpValue)
+ mir_free(cbdi->pszOpValue);
+ if(cbdi->pszValue)
+ mir_free(cbdi->pszValue);
+ }
+ else if(cbdi->pszValue)
+ mir_free(cbdi->pszValue);
+
+ mir_free(cbdi);
+ }
+
+void RemoveMenuEntryNode(SortedList *pList, int index)
+ {
+ li_RemoveDestruct(pList,index,listdestructor);
+ }
+
+void DestroyButton(int listnum)
+ {
+ int i=listnum;
+ ListData* ld=ButtonsList[listnum];
+
+ if(ld->ptszButtonName) mir_free(ld->ptszButtonName);
+
+ if(ld->ptszOPQValue!=ld->ptszQValue)
+ if(ld->ptszOPQValue) mir_free(ld->ptszOPQValue);
+
+ if (ld->ptszQValue) mir_free(ld->ptszQValue);
+
+ li_ListDestruct((SortedList*)ld->sl,listdestructor);
+
+
+ mir_free(ld);
+ ButtonsList[i]=NULL;
+ while(ButtonsList[i+1])
+ {
+ ButtonsList[i]=ButtonsList[i+1];
+ ButtonsList[i+1]=NULL;
+ i++;
+ }
+}
+
+
+void SaveModuleSettings(int buttonnum,ButtonData* bd)
+ {
+ char szMEntry[256]={'\0'};
+
+ mir_snprintf(szMEntry,255,"EntryName_%u_%u",buttonnum,bd->dwPos);
+ DBWriteContactSettingTString(NULL, PLGNAME,szMEntry,bd->pszName );
+
+ mir_snprintf(szMEntry,255,"EntryValue_%u_%u",buttonnum,bd->dwPos);
+ if(bd->pszValue)
+ DBWriteContactSettingTString(NULL, PLGNAME,szMEntry,bd->pszValue );
+ else
+ DBDeleteContactSetting(NULL, PLGNAME,szMEntry);
+
+ mir_snprintf(szMEntry,255,"EntryRel_%u_%u",buttonnum,bd->dwPos);
+ DBWriteContactSettingByte(NULL, PLGNAME,szMEntry,bd->fEntryType );
+
+ mir_snprintf(szMEntry,255,"EntryToQMenu_%u_%u",buttonnum,bd->dwPos);
+ DBWriteContactSettingByte(NULL, PLGNAME,szMEntry,bd->bInQMenu);
+
+ mir_snprintf(szMEntry,255,"EntryIsServiceName_%u_%u",buttonnum,bd->dwPos);
+ DBWriteContactSettingByte(NULL, PLGNAME,szMEntry,bd->bIsServName);
+ }
+
+void CleanSettings(int buttonnum,int from)
+ {
+ char szMEntry[256]={'\0'};
+ DBVARIANT dbv = {0};
+ if(from==-1){
+ mir_snprintf(szMEntry,255,"ButtonName_%u",buttonnum);
+ DBDeleteContactSetting(NULL, PLGNAME,szMEntry);
+ mir_snprintf(szMEntry,255,"ButtonValue_%u",buttonnum);
+ DBDeleteContactSetting(NULL, PLGNAME,szMEntry);
+ mir_snprintf(szMEntry,255,"RCEntryIsServiceName_%u",buttonnum);
+ DBDeleteContactSetting(NULL, PLGNAME,szMEntry);
+ }
+
+ mir_snprintf(szMEntry,255,"EntryName_%u_%u",buttonnum,from);
+ while(!DBGetContactSettingTString(NULL, PLGNAME,szMEntry,&dbv)) {
+ DBDeleteContactSetting(NULL, PLGNAME,szMEntry);
+ mir_snprintf(szMEntry,255,"EntryValue_%u_%u",buttonnum,from);
+ DBDeleteContactSetting(NULL, PLGNAME,szMEntry);
+ mir_snprintf(szMEntry,255,"EntryRel_%u_%u",buttonnum,from);
+ DBDeleteContactSetting(NULL, PLGNAME,szMEntry);
+ mir_snprintf(szMEntry,255,"EntryToQMenu_%u_%u",buttonnum,from);
+ DBDeleteContactSetting(NULL, PLGNAME,szMEntry);
+ mir_snprintf(szMEntry,255,"EntryIsServiceName_%u_%u",buttonnum,from);
+ DBDeleteContactSetting(NULL, PLGNAME,szMEntry);
+
+ mir_snprintf(szMEntry,255,"EntryName_%u_%u",buttonnum,++from);
+ }
+ DBFreeVariant(&dbv);
+ }
+
+BYTE getEntryByte(int buttonnum,int entrynum,BOOL mode)
+ {
+ char szMEntry[256]={'\0'};
+ if (mode==0)
+ mir_snprintf(szMEntry,255,"EntryToQMenu_%u_%u",buttonnum,entrynum);
+ else if (mode==1)
+ mir_snprintf(szMEntry,255,"EntryRel_%u_%u",buttonnum,entrynum);
+ else if (mode==2)
+ mir_snprintf(szMEntry,255,"EntryIsServiceName_%u_%u",buttonnum,entrynum);
+ else if (mode==3)
+ mir_snprintf(szMEntry,255,"RCEntryIsServiceName_%u",buttonnum);
+ return DBGetContactSettingByte(NULL, PLGNAME,szMEntry, 0);
+ }
+
+DWORD BalanceButtons(int buttonsWas,int buttonsNow)
+ {
+ if (ServiceExists(MS_BB_ADDBUTTON))
+ {
+ BBButton bb={0};
+ bb.cbSize=sizeof(BBButton);
+ bb.pszModuleName=PLGNAME;
+
+ while(buttonsWas>(buttonsNow))
+ {
+ bb.dwButtonID=--buttonsWas;
+ CallService(MS_BB_REMOVEBUTTON,0,(LPARAM)&bb);
+ }
+ while (buttonsWas<(buttonsNow))
+ {
+ if (ServiceExists(MS_BB_ADDBUTTON))
+ {
+ char iconname[20]={'\0'};
+ mir_snprintf(iconname,SIZEOF(iconname),"QMessagesButton_%u",buttonsWas);
+ bb.bbbFlags=BBBF_ISIMBUTTON|BBBF_ISCHATBUTTON|BBBF_ISLSIDEBUTTON;
+ bb.dwButtonID=buttonsWas++;
+ bb.dwDefPos=300+buttonsWas;
+ bb.hIcon = (HANDLE)AddIcon(hIcon, iconname, iconname);
+ CallService(MS_BB_ADDBUTTON, 0, (LPARAM)&bb);
+ }
+ }
+ }
+ return buttonsNow;
+ }
+
+
+void InitButtonsList()
+ {
+ int i,j,k=0;
+ QuickList=List_Create(0,1);
+ for(i=0;i<g_iButtonsCount;i++)
+ {
+ TCHAR* pszBName=NULL;
+ ListData* ld=NULL;
+ if (!(pszBName=getMenuEntry(i,0,3))) {
+ g_iButtonsCount=i;
+ DBWriteContactSettingByte(NULL, PLGNAME,"ButtonsCount", (BYTE)g_iButtonsCount);
+ break;}
+
+ ld = (ListData *)mir_alloc(sizeof(ListData));
+ ButtonsList[i]=ld;
+ ld->sl=List_Create(0,1);
+ ld->ptszQValue=ld->ptszOPQValue=getMenuEntry(i,0,2);
+ ld->ptszButtonName=pszBName;
+ ld->dwPos=ld->dwOPPos=i;
+ ld->dwOPFlags=0;
+ ld->bIsServName=ld->bIsOpServName=getEntryByte(i,0,3);
+ for(j=0;;j++)
+ {
+ TCHAR* pszEntry=NULL;
+ ButtonData *bd=NULL;
+
+ if (!(pszEntry=getMenuEntry(i,j,0)))
+ break;
+
+ bd = (ButtonData *)mir_alloc(sizeof(ButtonData));
+ memset(bd,0,sizeof(ButtonData));
+
+ bd->dwPos=bd->dwOPPos=j;
+ bd->pszName=bd->pszOpName=pszEntry;
+ bd->pszValue=bd->pszOpValue=getMenuEntry(i,j,1);
+ bd->fEntryType=bd->fEntryOpType=getEntryByte(i,j,1);
+ bd->bInQMenu=bd->bOpInQMenu=getEntryByte(i,j,0);
+ bd->bIsServName=bd->bIsOpServName=getEntryByte(i,j,2);
+ if(bd->bInQMenu){
+ QuickData* qd = (QuickData *)mir_alloc(sizeof(QuickData));
+ qd->dwPos=k++;
+ qd->ptszValue=bd->pszValue;
+ qd->ptszValueName=bd->pszName;
+ List_InsertPtr(QuickList,qd);
+ }
+ List_InsertPtr((SortedList*)ld->sl,bd);
+ }
+ }
+
+ }
+
+void DestructButtonsList()
+{
+ int i=0;
+// for ( i=0; i < g_iButtonsCount; i++ )
+while(ButtonsList[i])
+ {
+ li_ListDestruct(ButtonsList[i]->sl,listdestructor);
+ mir_free(ButtonsList[i]->ptszButtonName);
+ if(ButtonsList[i]->ptszOPQValue!=ButtonsList[i]->ptszQValue)
+ if (ButtonsList[i]->ptszOPQValue) mir_free(ButtonsList[i]->ptszOPQValue);
+ if (ButtonsList[i]->ptszQValue) mir_free(ButtonsList[i]->ptszQValue);
+ i++;
+ }
+if(QuickList)
+ {
+ li_ZeroQuickList(QuickList);
+ List_Destroy(QuickList);
+ }
+}
+
+TCHAR* getMenuEntry(int buttonnum,int entrynum,BYTE mode)
+ {
+ TCHAR* buffer=NULL;
+ char szMEntry[256]={'\0'};
+ DBVARIANT dbv = {0};
+
+ if(mode==0)
+ mir_snprintf(szMEntry,255,"EntryName_%u_%u",buttonnum,entrynum);
+ else if (mode==1)
+ mir_snprintf(szMEntry,255,"EntryValue_%u_%u",buttonnum,entrynum);
+ else if (mode==2)
+ mir_snprintf(szMEntry,255,"ButtonValue_%u",buttonnum);
+ else if (mode==3)
+ mir_snprintf(szMEntry,255,"ButtonName_%u",buttonnum);
+
+
+ DBGetContactSettingTString(NULL, PLGNAME,szMEntry, &dbv);
+
+ if(dbv.ptszVal&&_tcslen(dbv.ptszVal))
+ {
+ buffer=mir_tstrdup(dbv.ptszVal);
+ DBFreeVariant(&dbv);
+ }
+
+ return buffer;
+ }
+
+
+int AddIcon(HICON icon, char *name, char *description)
+{
+ SKINICONDESC sid = {0};
+ sid.cbSize = sizeof(SKINICONDESC);
+ sid.pszSection = "Quick Messages";
+ sid.cx = sid.cy = 16;
+ sid.pszDescription = description;
+ sid.pszName = name;
+ sid.hDefaultIcon = icon;
+
+ return (int)Skin_AddIcon(&sid);
+}
+
+int RegisterCustomButton(WPARAM wParam,LPARAM lParam)
+ {
+ if (ServiceExists(MS_BB_ADDBUTTON))
+ {
+ int i;
+ for(i=0;i<g_iButtonsCount;i++)
+ {
+ BBButton bbd={0};
+ ListData* ld=ButtonsList[i];
+ char iconname[20]={'\0'};
+ mir_snprintf(iconname,SIZEOF(iconname),"QMessagesButton_%u",i);
+
+ bbd.cbSize=sizeof(BBButton);
+ bbd.bbbFlags=BBBF_ISIMBUTTON|BBBF_ISCHATBUTTON|BBBF_ISLSIDEBUTTON;
+ bbd.dwButtonID=i;
+ bbd.dwDefPos=320+i;
+ bbd.hIcon=(HANDLE)AddIcon(hIcon, iconname, iconname);
+ bbd.pszModuleName=PLGNAME;
+ bbd.ptszTooltip=ld->ptszButtonName;
+ CallService(MS_BB_ADDBUTTON, 0, (LPARAM)&bbd);
+ }
+ return 0;
+ }
+ return 1;
+ }
+
+TCHAR* ParseString(HANDLE hContact,TCHAR* ptszQValIn,TCHAR* ptszText,TCHAR* ptszClip,int QVSize,int TextSize ,int ClipSize)
+ {
+ int i=0,iOffset=0,iCount=0;
+ TCHAR* tempPointer=NULL;
+ TCHAR* ptszQValue=_tcsdup(ptszQValIn);
+ TCHAR* tempQValue=ptszQValue;
+ TCHAR varstr=_T('%');
+
+ if(TextSize&&ptszText[TextSize-1]=='\0') TextSize--;
+ if(ClipSize&&ptszClip[ClipSize-1]=='\0') ClipSize--;
+
+ if (!_tcschr(ptszQValue,varstr))
+ return ptszQValue;
+
+ while(ptszQValue[i])
+ {
+ if(ptszQValue[i]=='%') {
+ switch(ptszQValue[i+1])
+ {
+ case 't':{
+ TCHAR* p=NULL;
+ p = (TCHAR *)realloc(tempQValue, (QVSize + TextSize+1)*sizeof(TCHAR));
+ if(p){
+ int test=0;
+ i=iOffset;
+ tempQValue=ptszQValue=p;
+
+ tempPointer = (TCHAR *)memmove(ptszQValue + i + TextSize, ptszQValue + i + 2, (QVSize - i - 1)*sizeof(TCHAR));
+
+ if(TextSize) memcpy(ptszQValue+i, ptszText, TextSize*sizeof(TCHAR));
+
+ QVSize+=(TextSize-2);
+
+ ptszQValue[QVSize]='\0';
+
+ if (!_tcschr(ptszQValue,varstr))
+ return ptszQValue;
+
+ ptszQValue=tempPointer;
+ iOffset+=TextSize-1;
+ i=-1;
+ }
+ }break;
+
+ case 'c':{
+ TCHAR* p=NULL;
+ p = (TCHAR *)realloc(tempQValue, (QVSize + ClipSize + 1)*sizeof(TCHAR));
+ if(p){
+ i=iOffset;
+ tempQValue=ptszQValue=p;
+
+ tempPointer = (TCHAR *)memmove(ptszQValue + i + ClipSize, ptszQValue + i + 2, (QVSize - i - 1)*sizeof(TCHAR));
+ if(ClipSize) memcpy(ptszQValue+i, ptszClip, ClipSize*sizeof(TCHAR));
+ QVSize+=(ClipSize-2);
+
+ ptszQValue[QVSize]='\0';
+
+ if (!_tcschr(ptszQValue,varstr))
+ return ptszQValue;
+
+ ptszQValue=tempPointer;
+ iOffset+=ClipSize-1;
+ i=-1;
+ }
+ }break;
+
+ case 'P':{
+ TCHAR* p=NULL;
+ int NameLenght=0;
+ TCHAR* ptszName=NULL;
+
+ ptszName=mir_a2u((char*)CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)hContact, 0));
+
+ NameLenght=(int)_tcslen(ptszName);
+
+ p = (TCHAR *)realloc(tempQValue, (QVSize + NameLenght + 1)*sizeof(TCHAR));
+ if(p){
+ i=iOffset;
+ tempQValue=ptszQValue=p;
+
+ tempPointer = (TCHAR *)memmove(ptszQValue + i + NameLenght, ptszQValue + i + 2, (QVSize - i - 1)*sizeof(TCHAR));
+ if(NameLenght) memcpy(ptszQValue+i, ptszName, NameLenght*sizeof(TCHAR));
+ QVSize+=(NameLenght-2);
+
+ ptszQValue[QVSize]='\0';
+ if(ptszName) mir_free(ptszName);
+
+ if (!_tcschr(ptszQValue,varstr))
+ return ptszQValue;
+
+ ptszQValue=tempPointer;
+ iOffset+=NameLenght-1;
+ i=-1;
+ }
+ }break;
+
+ case 'n':{
+ TCHAR* p=NULL;
+ int NameLenght=0;
+ TCHAR* ptszName=NULL;
+
+ ptszName=(TCHAR *)CallService(MS_CLIST_GETCONTACTDISPLAYNAME, (WPARAM)hContact, GCDNF_TCHAR);
+ NameLenght=(int)_tcslen(ptszName);
+ p = (TCHAR *)realloc(tempQValue, (QVSize + NameLenght + 1)*sizeof(TCHAR));
+ if(p){
+ i=iOffset;
+ tempQValue=ptszQValue=p;
+
+ tempPointer = (TCHAR *)memmove(ptszQValue + i + NameLenght, ptszQValue + i + 2, (QVSize - i - 1)*sizeof(TCHAR));
+ if(NameLenght)memcpy(ptszQValue+i, ptszName, NameLenght*sizeof(TCHAR));
+ QVSize+=(NameLenght-2);
+
+ //if(ptszName) mir_free(ptszName);
+
+ ptszQValue[QVSize]='\0';
+
+ if (!_tcschr(ptszQValue,varstr))
+ return ptszQValue;
+
+ ptszQValue=tempPointer;
+ iOffset+=NameLenght-1;
+ i=-1;
+ }
+ }break;
+ case 'F':{
+ TCHAR* p=NULL;
+ int NameLenght=0;
+ TCHAR* ptszName=NULL;
+ CONTACTINFO ci;
+ ZeroMemory(&ci,sizeof(CONTACTINFO));
+ ci.cbSize = sizeof(CONTACTINFO);
+ ci.hContact = hContact;
+
+ ci.dwFlag =CNF_FIRSTNAME|CNF_UNICODE;
+
+ ci.szProto=(char*)CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)hContact, 0);
+ if (!CallService(MS_CONTACT_GETCONTACTINFO,(WPARAM)0,(LPARAM)&ci)&&ci.pszVal){
+ NameLenght=(int)_tcslen(ci.pszVal);
+ ptszName=ci.pszVal;
+ }
+ p = (TCHAR *)realloc(tempQValue, (QVSize + NameLenght + 1)*sizeof(TCHAR));
+ if(p){
+ i=iOffset;
+ tempQValue=ptszQValue=p;
+
+ tempPointer = (TCHAR *)memmove(ptszQValue + i + NameLenght, ptszQValue + i + 2, (QVSize - i - 1)*sizeof(TCHAR));
+ if(NameLenght)memcpy(ptszQValue+i, ptszName, NameLenght*sizeof(TCHAR));
+ QVSize+=(NameLenght-2);
+
+ if(ptszName) mir_free(ptszName);
+
+ ptszQValue[QVSize]='\0';
+
+ if (!_tcschr(ptszQValue,varstr))
+ return ptszQValue;
+
+ ptszQValue=tempPointer;
+ iOffset+=NameLenght-1;
+ i=-1;
+ }
+ }break;
+ case 'L':{
+ TCHAR* p=NULL;
+ int NameLenght=0;
+ TCHAR* ptszName=NULL;
+ CONTACTINFO ci;
+ ZeroMemory(&ci,sizeof(CONTACTINFO));
+ ci.cbSize = sizeof(CONTACTINFO);
+ ci.hContact = hContact;
+ ci.szProto=(char*)CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)hContact, 0);
+
+ ci.dwFlag =CNF_LASTNAME|CNF_UNICODE;
+
+ if (!CallService(MS_CONTACT_GETCONTACTINFO,(WPARAM)0,(LPARAM)&ci)&&ci.pszVal){
+ NameLenght=(int)_tcslen(ci.pszVal);
+ ptszName=ci.pszVal;
+ }
+ p = (TCHAR *)realloc(tempQValue, (QVSize + NameLenght + 1)*sizeof(TCHAR));
+ if(p){
+ i=iOffset;
+ tempQValue=ptszQValue=p;
+
+ tempPointer = (TCHAR *)memmove(ptszQValue + i + NameLenght, ptszQValue + i + 2, (QVSize - i - 1)*sizeof(TCHAR));
+ if(NameLenght)memcpy(ptszQValue+i, ptszName, NameLenght*sizeof(TCHAR));
+ QVSize+=(NameLenght-2);
+
+ ptszQValue[QVSize]='\0';
+
+ if (!_tcschr(ptszQValue,varstr))
+ return ptszQValue;
+
+ ptszQValue=tempPointer;
+ iOffset+=NameLenght-1;
+ i=-1;
+ }
+ }break;
+ }
+ }
+ iOffset++;
+ i++;
+ }
+ return ptszQValue;
+ } \ No newline at end of file
diff --git a/plugins/QuickMessages/src/Utils.h b/plugins/QuickMessages/src/Utils.h
new file mode 100644
index 0000000000..c136459239
--- /dev/null
+++ b/plugins/QuickMessages/src/Utils.h
@@ -0,0 +1,78 @@
+/*
+Quick Messages plugin for Miranda IM
+
+Copyright (C) 2008 Danil Mozhar
+
+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 3 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, see <http://www.gnu.org/licenses/>.
+*/
+#define QMF_NEW (1<<0)
+#define QMF_DELETNEEDED (1<<1)
+#define QMF_RENAMED (1<<2)
+
+#define QMF_EX_CHILD (1<<0)
+#define QMF_EX_SEPARATOR (1<<1)
+
+typedef struct _tagButtonData
+ {
+ DWORD dwPos;
+ DWORD dwOPPos;
+ BYTE fEntryType;
+ BYTE fEntryOpType;
+ BYTE bIsServName;
+ BYTE bIsOpServName;
+ BYTE bInQMenu;
+ BYTE bOpInQMenu;
+ DWORD dwOPFlags;
+ TCHAR *pszName;
+ TCHAR *pszValue;
+ TCHAR *pszOpValue;
+ TCHAR *pszOpName;
+ }ButtonData;
+
+typedef struct _tagListData
+ {
+ SortedList* sl;
+ DWORD dwPos;
+ DWORD dwOPPos;
+ TCHAR* ptszQValue;
+ TCHAR* ptszOPQValue;
+ TCHAR* ptszButtonName;
+ BYTE bIsServName;
+ BYTE bIsOpServName;
+ DWORD dwOPFlags;
+ }ListData;
+
+typedef struct _tagQuickData
+ {
+ DWORD dwPos;
+ BOOL bIsService;
+ BYTE fEntryType;
+ TCHAR* ptszValue;
+ TCHAR* ptszValueName;
+ }QuickData;
+
+void InitButtonsList();
+void DestructButtonsList();
+int sstSortButtons(const void * vmtbi1, const void * vmtbi2);
+int sstOpSortButtons(const void * vmtbi1, const void * vmtbi2);
+int sstQuickSortButtons(const void * vmtbi1, const void * vmtbi2);
+void li_ZeroQuickList(SortedList *pList);
+TCHAR* getMenuEntry(int entrynum,int buttonnum,BYTE mode) ;
+int RegisterCustomButton(WPARAM wParam,LPARAM lParam);
+void RemoveMenuEntryNode(SortedList *pList, int index);
+void DestroyButton(int listnum);
+void SaveModuleSettings(int buttonnum,ButtonData* bd);
+void CleanSettings(int buttonnum,int from);
+DWORD BalanceButtons(int buttonsWas,int buttonsNow);
+TCHAR* ParseString(HANDLE hContact,TCHAR* ptszQValueIn,TCHAR* ptszText,TCHAR* ptszClip,int QVSize,int TextSize ,int ClipSize); \ No newline at end of file
diff --git a/plugins/QuickMessages/src/main.cpp b/plugins/QuickMessages/src/main.cpp
new file mode 100644
index 0000000000..3720d84a6a
--- /dev/null
+++ b/plugins/QuickMessages/src/main.cpp
@@ -0,0 +1,363 @@
+/*
+Quick Messages plugin for Miranda IM
+
+Copyright (C) 2008 Danil Mozhar
+
+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 3 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, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "quickmessages.h"
+
+HINSTANCE hinstance;
+
+WNDPROC mainProc;
+
+HANDLE hEventCBButtonPressed, hEventCBInit,hEventInputMenu, hEventDbOptionsInit, hEventDbPluginsLoaded,
+hEventDbPreShutdown;
+HICON hIcon;
+
+int g_iButtonsCount=0;
+int g_bShutDown=0;
+int g_bStartup=0;
+BOOL g_bRClickAuto=0;
+BOOL g_bLClickAuto=0;
+BOOL g_bQuickMenu=0;
+
+
+int hLangpack;
+
+PLUGININFOEX pluginInfo = {
+ sizeof(PLUGININFOEX),
+ MODULENAME,
+ PLUGIN_MAKE_VERSION(0,0,4,2),
+ "Plugin for quick insert pre-defined messages in message input area.",
+ "MaD_CLuSTeR",
+ "daniok@yandex.ru",
+ "© 2008 Danil Mozhar",
+ "http://miranda.radicaled.ru/index.php?plugin=3",
+ UNICODE_AWARE,
+ // {37ED754B-6CF9-40ed-9EB6-0FEF8E822475}
+ { 0x37ed754b, 0x6cf9, 0x40ed, { 0x9e, 0xb6, 0xf, 0xef, 0x8e, 0x82, 0x24, 0x75 } }
+};
+
+int PreShutdown(WPARAM wparam,LPARAM lparam)
+{
+ g_bShutDown=1;
+ DestructButtonsList();
+
+ if(hEventCBButtonPressed) UnhookEvent(hEventCBButtonPressed);
+ if(hEventCBInit) UnhookEvent(hEventCBInit);
+ if(hEventInputMenu) UnhookEvent(hEventInputMenu);
+ UnhookEvent(hEventDbPluginsLoaded);
+ UnhookEvent(hEventDbOptionsInit);
+ UnhookEvent(hEventDbPreShutdown);
+
+ return 0;
+}
+
+static int InputMenuPopup(WPARAM wParam,LPARAM lParam)
+{
+ HMENU hSubMenu=NULL;
+ int i=0;
+ MessageWindowPopupData * mwpd = (MessageWindowPopupData *)lParam;
+ if(mwpd->uFlags==MSG_WINDOWPOPUP_LOG||!g_bQuickMenu||!QuickList->realCount) return 0;
+
+ if(mwpd->uType==MSG_WINDOWPOPUP_SHOWING)
+ {
+ hSubMenu = CreatePopupMenu();
+
+ InsertMenu((HMENU)mwpd->hMenu,6,MF_STRING|MF_POPUP|MF_BYPOSITION,(UINT_PTR)hSubMenu,TranslateT("Quick Messages"));
+ InsertMenu((HMENU)mwpd->hMenu,7,MF_SEPARATOR|MF_BYPOSITION,0,0);
+ qsort(QuickList->items,QuickList->realCount,sizeof(QuickData *),sstQuickSortButtons);
+ for(i=0;i<QuickList->realCount;i++)
+ {
+ QuickData* qd= (QuickData *)QuickList->items[i];
+ if(qd->fEntryType&QMF_EX_SEPARATOR)
+ AppendMenu(hSubMenu,MF_SEPARATOR,0,NULL);
+ else
+ AppendMenu(hSubMenu,MF_STRING,qd->dwPos+254,qd->ptszValueName);
+ }
+ }
+ else if(mwpd->uType==MSG_WINDOWPOPUP_SELECTED&&mwpd->selection>=254)
+ {
+ for(i=0;i<QuickList->realCount;i++)
+ {
+ QuickData* qd= (QuickData *)QuickList->items[i];
+ if ((qd->dwPos+254)==mwpd->selection)
+ {
+ CHARRANGE cr;
+ UINT textlenght=0;
+ TCHAR* pszText=NULL;
+ TCHAR* ptszQValue=NULL;
+ TCHAR* pszCBText=NULL;
+ BOOL bIsService=0;
+
+ if(IsClipboardFormatAvailable(CF_TEXT)) {
+ if (OpenClipboard(mwpd->hwnd)) {
+ HANDLE hData=NULL;
+ TCHAR* chBuffer=NULL;
+ int textLength=0;
+
+ hData= GetClipboardData(CF_UNICODETEXT);
+
+ chBuffer= (TCHAR*)GlobalLock(hData);
+ textLength=(int)_tcslen(chBuffer);
+ pszCBText=mir_tstrdup(chBuffer);
+ GlobalUnlock(hData);
+ CloseClipboard();
+ }
+ }
+
+ SendMessage(mwpd->hwnd, EM_EXGETSEL, 0, (LPARAM)&cr);
+ textlenght=cr.cpMax-cr.cpMin;
+
+ if(textlenght)
+ {
+ pszText = (TCHAR *)mir_alloc((textlenght+10)*sizeof(TCHAR));
+ ZeroMemory(pszText,(textlenght+10)*sizeof(TCHAR));
+ SendMessage(mwpd->hwnd,EM_GETSELTEXT, 0, (LPARAM)pszText);
+ }
+ if(qd->ptszValue){
+ ptszQValue=ParseString(mwpd->hContact,qd->ptszValue,pszText?pszText:_T(""),pszCBText?pszCBText:_T(""),(int)_tcslen(qd->ptszValue),textlenght,pszCBText?(int)_tcslen(pszCBText):0);
+ if ((bIsService=qd->bIsService)&&ptszQValue)
+
+ CallService(mir_u2a(ptszQValue),(WPARAM)mwpd->hContact,0);
+
+ }
+
+ if(ptszQValue)
+ SendMessage(mwpd->hwnd, EM_REPLACESEL, TRUE, (LPARAM)ptszQValue);
+
+ if(pszText) mir_free(pszText);
+ if(ptszQValue) free(ptszQValue);
+ if(pszCBText) mir_free(pszCBText);
+ break;
+ }
+ }
+ return 1;
+ }
+ return 0;
+}
+
+static int CustomButtonPressed(WPARAM wParam,LPARAM lParam)
+{
+ CustomButtonClickData *cbcd=(CustomButtonClickData *)lParam;
+
+ CHARRANGE cr;
+ HWND hEdit=NULL;
+ int i=0;
+ BOOL bCTRL=0;
+ BOOL bIsService=0;
+ TCHAR* pszText=NULL;
+ TCHAR* pszCBText=NULL;
+ TCHAR* pszFormatedText=NULL;
+ TCHAR* ptszQValue=NULL;
+ int cblenght=0,qvlenght=0;
+ int count=0,mode=0;
+ UINT textlenght=0;
+ BBButton bbd={0};
+ SortedList* sl=NULL;
+ int state=0;
+
+ if(strcmp(cbcd->pszModule,PLGNAME)) return 0;
+
+ if (!ButtonsList[cbcd->dwButtonId]) return 1;
+
+ sl=ButtonsList[cbcd->dwButtonId]->sl;
+
+ if (!sl) return 1;
+
+ if(IsClipboardFormatAvailable(CF_TEXT)) {
+ if (OpenClipboard(cbcd->hwndFrom)) {
+ HANDLE hData=NULL;
+ TCHAR* chBuffer=NULL;
+ int textLength=0;
+
+ hData= GetClipboardData(CF_UNICODETEXT);
+
+ chBuffer= (TCHAR*)GlobalLock(hData);
+ textLength=(int)_tcslen(chBuffer);
+ pszCBText=mir_tstrdup(chBuffer);
+ GlobalUnlock(hData);
+ CloseClipboard();
+ }
+ }
+
+
+
+
+ qsort(sl->items,sl->realCount,sizeof(ButtonData *),sstSortButtons);
+
+ hEdit=GetDlgItem(cbcd->hwndFrom,IDC_MESSAGE);
+ if (!hEdit) hEdit=GetDlgItem(cbcd->hwndFrom,IDC_CHATMESSAGE);
+
+ cr.cpMin = cr.cpMax = 0;
+ SendMessage(hEdit, EM_EXGETSEL, 0, (LPARAM)&cr);
+
+ textlenght=cr.cpMax-cr.cpMin;
+ if(textlenght)
+ {
+ pszText = (TCHAR *)mir_alloc((textlenght+10)*sizeof(TCHAR));
+ ZeroMemory(pszText,(textlenght+10)*sizeof(TCHAR));
+ SendMessage(hEdit,EM_GETSELTEXT, 0, (LPARAM)pszText);
+ }
+
+ if(cbcd->flags&BBCF_RIGHTBUTTON)
+ state=1;
+ else if(sl->realCount==1)
+ state=2;
+ else
+ state=3;
+
+
+ switch(state)
+ {
+ case 1:
+ if(ButtonsList[cbcd->dwButtonId]->ptszQValue)
+ ptszQValue=ParseString(cbcd->hContact,ButtonsList[cbcd->dwButtonId]->ptszQValue,pszText?pszText:_T(""),pszCBText?pszCBText:_T(""),(int)_tcslen(ButtonsList[cbcd->dwButtonId]->ptszQValue),textlenght,pszCBText?(int)_tcslen(pszCBText):0);
+ if ((bIsService=ButtonsList[cbcd->dwButtonId]->bIsServName)&&ptszQValue)
+
+ CallService(mir_u2a(ptszQValue),(WPARAM)cbcd->hContact,0);
+
+ break;
+ case 2:
+ {
+ ButtonData * bd=NULL;
+ bd=(ButtonData *)sl->items[0];
+ if(bd&&bd->pszValue){
+ ptszQValue=ParseString(cbcd->hContact,bd->pszValue,pszText?pszText:_T(""),pszCBText?pszCBText:_T(""),(int)_tcslen(bd->pszValue),textlenght,pszCBText?(int)_tcslen(pszCBText):0);
+ if ((bIsService=bd->bIsServName)&&ptszQValue)
+
+ CallService(mir_u2a(ptszQValue),(WPARAM)cbcd->hContact,0);
+
+ }
+ }
+ break;
+ case 3:{
+ int res=0;
+ int menunum;
+ ButtonData * bd=NULL;
+ HMENU hMenu=NULL,hSubMenu=NULL;
+ BOOL bSetPopUpMark=FALSE;
+
+ if(g_iButtonsCount){
+ hMenu = CreatePopupMenu();
+ }
+ else break;
+ for(menunum=0;menunum<sl->realCount;menunum++)
+ {
+ bd=(ButtonData *)sl->items[menunum];
+ if(bd->dwOPFlags&QMF_NEW)
+ continue;
+
+ bSetPopUpMark=FALSE;
+ if(bd->pszValue==0&&bd->fEntryType==0)
+ {
+ hSubMenu = CreatePopupMenu();
+ bSetPopUpMark=TRUE;
+ }
+
+ if(bd->pszValue&&bd->fEntryType==0)
+ hSubMenu=NULL;
+
+ if(bd->fEntryType&QMF_EX_SEPARATOR)
+ AppendMenu((HMENU)((hSubMenu&&!bSetPopUpMark)?hSubMenu:hMenu),MF_SEPARATOR,0,NULL);
+ else
+ AppendMenu((HMENU)((hSubMenu&&!bSetPopUpMark)?hSubMenu:hMenu),
+ MF_STRING|(bSetPopUpMark?MF_POPUP:0),
+ (bSetPopUpMark?(UINT_PTR)hSubMenu:(menunum+1)), bd->pszName);
+ }
+
+ res = TrackPopupMenu(hMenu, TPM_RETURNCMD, cbcd->pt.x, cbcd->pt.y, 0, cbcd->hwndFrom, NULL);
+ if(res==0) break;
+
+ bd= (ButtonData *)sl->items[res-1];
+ bCTRL=(GetKeyState(VK_CONTROL)&0x8000)?1:0;
+ if(bd->pszValue){
+ ptszQValue=ParseString(cbcd->hContact,bd->pszValue,pszText?pszText:_T(""),pszCBText?pszCBText:_T(""),(int)_tcslen(bd->pszValue),textlenght,pszCBText?(int)_tcslen(pszCBText):0);
+ if ((bIsService=bd->bIsServName)&&ptszQValue)
+
+ CallService(mir_u2a(ptszQValue),(WPARAM)cbcd->hContact,0);
+
+ }
+ }break;
+ }
+
+
+ if(ptszQValue){
+ if (!bIsService){
+ SendMessage(hEdit, EM_REPLACESEL, TRUE, (LPARAM)ptszQValue);
+
+ if ((g_bLClickAuto&&state!=1)||(g_bRClickAuto&&state==1)||cbcd->flags&BBCF_CONTROLPRESSED||bCTRL)
+ SendMessage(cbcd->hwndFrom, WM_COMMAND,IDOK,0);
+ }
+ free(ptszQValue);
+ }
+
+
+ if(pszText) mir_free(pszText);
+ if(pszCBText) mir_free(pszCBText);
+ return 1;
+}
+
+
+static int PluginInit(WPARAM wparam,LPARAM lparam)
+{
+ g_bStartup=1;
+ hEventDbOptionsInit=HookEvent(ME_OPT_INITIALISE,OptionsInit);
+ hEventCBButtonPressed=HookEvent(ME_MSG_BUTTONPRESSED,CustomButtonPressed);
+ hEventCBInit=HookEvent(ME_MSG_TOOLBARLOADED,RegisterCustomButton);
+
+ hEventInputMenu=HookEvent(ME_MSG_WINDOWPOPUP,InputMenuPopup);
+
+
+ g_bRClickAuto=DBGetContactSettingByte(NULL,PLGNAME,"RClickAuto",0);
+ g_bLClickAuto=DBGetContactSettingByte(NULL,PLGNAME,"LClickAuto",0);
+ g_iButtonsCount=DBGetContactSettingByte(NULL, PLGNAME,"ButtonsCount", 0);
+ g_bQuickMenu=DBGetContactSettingByte(NULL, PLGNAME,"QuickMenu", 1);
+
+ hIcon = LoadIcon(hinstance, MAKEINTRESOURCE(IDI_QICON));
+
+ InitButtonsList();
+
+ g_bStartup=0;
+ return 0;
+}
+
+extern "C" __declspec(dllexport) PLUGININFOEX* MirandaPluginInfoEx(DWORD mirandaVersion)
+{
+ return &pluginInfo;
+}
+
+extern "C" __declspec(dllexport) int Unload(void)
+{
+ return 0;
+}
+
+BOOL WINAPI DllMain(HINSTANCE hinst, DWORD fdwReason, LPVOID lpvReserved)
+{
+ hinstance=hinst;
+ return 1;
+}
+
+extern "C" __declspec(dllexport) int Load(void)
+{
+
+
+ mir_getLP(&pluginInfo);
+
+ hEventDbPluginsLoaded=HookEvent(ME_SYSTEM_MODULESLOADED,PluginInit);
+ hEventDbPreShutdown=HookEvent(ME_SYSTEM_PRESHUTDOWN,PreShutdown);
+ return 0;
+} \ No newline at end of file
diff --git a/plugins/QuickMessages/src/options.cpp b/plugins/QuickMessages/src/options.cpp
new file mode 100644
index 0000000000..4527e1c858
--- /dev/null
+++ b/plugins/QuickMessages/src/options.cpp
@@ -0,0 +1,1166 @@
+/*
+Quick Messages plugin for Miranda IM
+
+Copyright (C) 2008 Danil Mozhar
+
+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 3 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, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "quickmessages.h"
+
+int g_iOPButtonsCount;
+BOOL bNeedRestart = FALSE;
+BOOL drag = FALSE, bOptionsInit = TRUE;
+HTREEITEM hDragItem = NULL;
+HWND hButtonsList = NULL;
+HWND hMenuTree = NULL;
+HWND hwndEdit = NULL;
+WNDPROC oldEditProc = 0, oldBNameProc = 0, oldMNameProc = 0;
+
+HWND g_opHdlg = NULL, g_varhelpDlg = NULL;
+
+INT_PTR CALLBACK HelpDlgProc(HWND hdlg,UINT msg,WPARAM wparam,LPARAM lparam)
+ {
+ switch(msg){
+ case WM_INITDIALOG:{
+ LOGFONT logFont;
+ HFONT hFont;
+ RECT rc;
+ g_varhelpDlg=hdlg;
+ TranslateDialogDefault(hdlg);
+ hFont = (HFONT)SendMessage(GetDlgItem(hdlg, IDC_STATICTITLE), WM_GETFONT, 0, 0);
+ GetObject(hFont, sizeof logFont, &logFont);
+ logFont.lfWeight = FW_BOLD;
+ hFont = CreateFontIndirect(&logFont);
+ SendMessage(GetDlgItem(hdlg, IDC_STATICTITLE), WM_SETFONT, (WPARAM)hFont, 0);
+ SendMessage(GetDlgItem(hdlg, IDC_STATICTITLE2), WM_SETFONT, (WPARAM)hFont, 0);
+ SendMessage(GetDlgItem(hdlg, IDC_VARTEXT), WM_SETFONT, (WPARAM)hFont, 0);
+ SendMessage(GetDlgItem(hdlg, IDC_VARCLIP), WM_SETFONT, (WPARAM)hFont, 0);
+ SendMessage(GetDlgItem(hdlg, IDC_VARPUNAME), WM_SETFONT, (WPARAM)hFont, 0);
+ SendMessage(GetDlgItem(hdlg, IDC_VARPLNAME), WM_SETFONT, (WPARAM)hFont, 0);
+ SendMessage(GetDlgItem(hdlg, IDC_VARCNAME), WM_SETFONT, (WPARAM)hFont, 0);
+ SendMessage(GetDlgItem(hdlg, IDC_VARCFNAME), WM_SETFONT, (WPARAM)hFont, 0);
+ SendMessage(GetDlgItem(hdlg, IDC_VARCLNAME), WM_SETFONT, (WPARAM)hFont, 0);
+
+ GetWindowRect(g_opHdlg,&rc);
+ SetWindowPos(hdlg,0,rc.left,rc.top,0,0,SWP_SHOWWINDOW|SWP_NOSIZE);
+ }break;
+
+ case WM_LBUTTONDOWN:{
+ PostMessage( hdlg,WM_NCLBUTTONDOWN, HTCAPTION,lparam);
+ }break;
+
+ case WM_CLOSE:
+ case WM_DESTROY:
+ DestroyWindow(g_varhelpDlg);
+ g_varhelpDlg=NULL;
+ break;
+ default:
+ return FALSE;
+ }
+ return TRUE;
+ }
+
+static LRESULT CALLBACK LabelEditSubclassProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+ {
+ switch (msg) {
+ case WM_GETDLGCODE:
+ return DLGC_WANTALLKEYS;
+ }
+ return CallWindowProc(oldEditProc, hwnd, msg, wParam, lParam);
+ }
+
+static LRESULT CALLBACK EditSubclassProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+ {
+ HWND hParent=GetParent(hwnd);
+ switch (msg) {
+ case WM_GETDLGCODE:
+ return DLGC_WANTALLKEYS|DLGC_HASSETSEL;
+ case WM_SETFOCUS:
+ PostMessage(hwnd,EM_SETSEL,0,-1);
+ break;
+ case WM_KEYDOWN:
+ {
+ if(wParam==VK_RETURN)
+ if(hwnd==GetDlgItem(hParent,IDC_BUTTONNAME))
+ SendMessage(hParent,WM_COMMAND,IDC_BLISTADD,0);
+ else
+ SendMessage(hParent,WM_COMMAND,IDC_MTREEADD,0);
+ }break;
+ }
+ if(hwnd==GetDlgItem(hParent,IDC_BUTTONNAME))
+ return CallWindowProc(oldBNameProc, hwnd, msg, wParam, lParam);
+ else
+ return CallWindowProc(oldMNameProc, hwnd, msg, wParam, lParam);
+ }
+
+void SetMenuEntryProperties(HWND hdlg)
+ {
+ TVITEM tvi;
+ HTREEITEM hItem=NULL;
+ ButtonData* bd=NULL;
+ int pos=0;
+
+ if(TreeView_GetCount(hButtonsList)&&(tvi.hItem=TreeView_GetSelection(hButtonsList)))
+ {
+ tvi.mask=TVIF_HANDLE|TVIF_PARAM;
+ TreeView_GetItem(hButtonsList,&tvi);
+
+ if (tvi.lParam)
+ {
+ ListData* ld = ( ListData* )tvi.lParam;
+ TCHAR szValue[256];
+ GetWindowText(GetDlgItem(hdlg,IDC_RCLICKVALUE), szValue, sizeof(szValue));
+ if(_tcslen(szValue))
+ {
+ if(ld->ptszOPQValue&&(ld->ptszOPQValue!=ld->ptszQValue))
+ mir_free(ld->ptszOPQValue);
+ ld->ptszOPQValue=mir_tstrdup(szValue);
+ }
+ ld->bIsOpServName=IsDlgButtonChecked(hdlg,IDC_ISSERVNAME2);
+ }
+ }
+
+ tvi.hItem=NULL;
+ if(TreeView_GetCount(hMenuTree)&&(tvi.hItem=TreeView_GetSelection(hMenuTree)))
+ {
+ tvi.mask=TVIF_HANDLE|TVIF_PARAM;
+ TreeView_GetItem(hMenuTree,&tvi);
+
+ if (tvi.lParam)
+ {
+ ButtonData* bd = ( ButtonData* )tvi.lParam;
+ TCHAR szValue[256];
+ GetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE), szValue, sizeof(szValue));
+ if(_tcslen(szValue))
+ {
+ if(_tcslen(bd->pszOpValue)&&(bd->pszOpValue!=bd->pszValue))
+ mir_free(bd->pszOpValue);
+ bd->pszOpValue=mir_tstrdup(szValue);
+ }
+ bd->bOpInQMenu=IsDlgButtonChecked(hdlg,IDC_INQMENU);
+ bd->bIsOpServName=IsDlgButtonChecked(hdlg,IDC_ISSERVNAME);
+ }
+
+ tvi.mask = TVIF_HANDLE | TVIF_PARAM;
+ tvi.hItem = TreeView_GetRoot(hMenuTree);
+ }
+ while (tvi.hItem) {
+ TreeView_GetItem(hMenuTree, &tvi);
+ bd= (ButtonData*)tvi.lParam;
+
+ bd->dwOPPos=pos++;
+
+ if(hItem=TreeView_GetChild(hMenuTree, tvi.hItem)) {
+
+ bd->fEntryOpType&=~QMF_EX_CHILD;
+
+ if(bd->pszOpValue){
+ mir_free(bd->pszOpValue);
+ bd->pszOpValue=NULL;
+ }
+ tvi.hItem=hItem;
+ continue;
+ }
+ else
+ {
+ if(bd->fEntryOpType&QMF_EX_SEPARATOR){
+ if(bd->pszOpValue){
+ mir_free(bd->pszOpValue);
+ bd->pszOpValue=NULL;
+ }}
+ else
+ {
+ if (!bd->pszOpValue)
+ bd->pszOpValue=mir_tstrdup(_T("Enter Value"));
+ }
+ if(TreeView_GetParent(hMenuTree, tvi.hItem))
+ bd->fEntryOpType|=QMF_EX_CHILD;
+ else bd->fEntryOpType&=~QMF_EX_CHILD;
+
+ if (!(hItem=TreeView_GetNextSibling(hMenuTree, tvi.hItem)))
+ tvi.hItem=TreeView_GetNextSibling(hMenuTree, TreeView_GetParent(hMenuTree,tvi.hItem));
+ else
+ tvi.hItem=hItem;
+
+ }
+ }
+ }
+
+void SaveMenuTree(HWND hdlg)
+ {
+ int iBl=0,i=0,k=0;
+ int iBtd=g_iButtonsCount;
+ BOOL bDeleted=FALSE;
+ char szMEntry[256]={'\0'};
+ TCHAR strbuf[256];
+ HTREEITEM hti=NULL;
+ TVITEM tvi;
+
+ g_iButtonsCount=TreeView_GetCount(hButtonsList);
+
+ tvi.pszText = strbuf;
+ tvi.cchTextMax = 256;
+ tvi.mask=TVIF_HANDLE|TVIF_TEXT ;
+ tvi.hItem=TreeView_GetRoot(hButtonsList);
+
+ TreeView_GetItem(hButtonsList,&tvi);
+
+ li_ZeroQuickList(QuickList);
+
+ BalanceButtons(iBtd,g_iButtonsCount);
+
+ while(ButtonsList[iBl])
+ {
+ SortedList * sl=NULL;
+ ListData* ld=ButtonsList[iBl];
+
+ if (!ld->sl) break;
+
+ sl=ld->sl;
+
+ if(ld->dwOPFlags&QMF_DELETNEEDED)
+ {
+ bDeleted=(ld->dwOPFlags&QMF_NEW)?FALSE:TRUE;
+ if(bDeleted) CleanSettings(ld->dwPos,-1);
+ DestroyButton(iBl);
+ continue;
+ }
+ if(ld->ptszQValue!=ld->ptszOPQValue)
+ {
+ if(ld->ptszQValue)
+ mir_free(ld->ptszQValue);
+
+ ld->ptszQValue=(ld->ptszOPQValue)?ld->ptszOPQValue:NULL;
+ }
+
+ if(ld->ptszButtonName)
+ mir_free(ld->ptszButtonName);
+ if(iBl>0)
+ if(hti=TreeView_GetNextSibling(hButtonsList,hti?hti:tvi.hItem))
+ {
+ tvi.hItem=hti;
+ TreeView_GetItem(hButtonsList,&tvi);
+ }
+
+ ld->ptszButtonName=mir_tstrdup(tvi.pszText);
+
+ if(ld->ptszQValue)
+ {
+ mir_snprintf(szMEntry,255,"ButtonValue_%u",iBl);
+ DBWriteContactSettingTString(NULL, PLGNAME,szMEntry,ld->ptszQValue);
+ }
+
+
+ if (ServiceExists(MS_BB_MODIFYBUTTON)&&((ld->dwOPFlags&QMF_NEW)||(ld->dwOPFlags&QMF_RENAMED)||bDeleted))
+ {
+ BBButton bb={0};
+ bb.cbSize=sizeof(BBButton);
+ bb.pszModuleName=PLGNAME;
+ bb.dwButtonID=iBl;
+ bb.ptszTooltip=ld->ptszButtonName;
+ CallService(MS_BB_MODIFYBUTTON,0,(LPARAM)&bb);
+ }
+
+
+ mir_snprintf(szMEntry,255,"ButtonName_%u",iBl);
+ DBWriteContactSettingTString(NULL, PLGNAME,szMEntry,ld->ptszButtonName);
+
+ ld->dwOPFlags=0;
+ ld->dwPos=iBl;
+ ld->bIsServName=ld->bIsOpServName;
+ mir_snprintf(szMEntry,255,"RCEntryIsServiceName_%u",iBl);
+ DBWriteContactSettingByte(NULL, PLGNAME,szMEntry,ld->bIsServName);
+
+ bDeleted=FALSE;
+
+ qsort(sl->items,sl->realCount,sizeof(ButtonData *),sstSortButtons);
+
+ for ( i=0; i < sl->realCount; i++ ) {
+ ButtonData * bd= (ButtonData *)sl->items[i];
+
+ if(bd->dwOPFlags&QMF_DELETNEEDED){
+ RemoveMenuEntryNode(sl, i--);
+ continue;
+ }
+ bd->bIsServName=bd->bIsOpServName;
+ bd->bInQMenu=bd->bOpInQMenu;
+ bd->dwPos=bd->dwOPPos;
+ bd->fEntryType=bd->fEntryOpType;
+ bd->dwOPFlags=0;
+
+ if(bd->pszName!=bd->pszOpName)
+ {
+ if(bd->pszName)
+ mir_free(bd->pszName);
+ bd->pszName=bd->pszOpName?bd->pszOpName:NULL;
+ }
+
+ if(bd->pszValue!=bd->pszOpValue)
+ {
+ if(bd->pszValue)
+ mir_free(bd->pszValue);
+ bd->pszValue=bd->pszOpValue?bd->pszOpValue:NULL;
+ }
+ if(bd->bInQMenu)
+ {
+ QuickData* qd = (QuickData *)mir_alloc(sizeof(QuickData));
+ qd->dwPos=k++;
+ qd->fEntryType=bd->fEntryType;
+ qd->bIsService=bd->bIsServName;
+ qd->ptszValue=bd->pszValue;
+ qd->ptszValueName=bd->pszName;
+ List_InsertPtr(QuickList,qd);
+ }
+
+ SaveModuleSettings(iBl,bd);
+ }
+ CleanSettings(iBl,sl->realCount);
+
+ iBl++;
+ }
+
+ DBWriteContactSettingByte(NULL, PLGNAME,"ButtonsCount", (BYTE)g_iButtonsCount);
+ }
+
+void RestoreModuleData(HWND hdlg)
+ {
+ int iBl=0,i=0;
+ char szMEntry[256]={'\0'};
+ while(ButtonsList[iBl])
+ {
+ SortedList * sl=NULL;
+ ListData* ld=ButtonsList[iBl];
+
+ if (!(sl=ld->sl)) break;
+
+ if(ld->dwOPFlags&QMF_NEW)
+ {
+ DestroyButton(iBl);
+ continue;
+ }
+
+ if(ld->ptszQValue!=ld->ptszOPQValue)
+ {
+ if(ld->ptszOPQValue)
+ mir_free(ld->ptszOPQValue);
+
+ ld->ptszOPQValue=(ld->ptszQValue)?ld->ptszQValue:NULL;
+ }
+
+ ld->bIsOpServName=ld->bIsServName;
+ ld->dwOPFlags=0;
+
+ qsort(sl->items,sl->realCount,sizeof(ButtonData *),sstSortButtons);
+
+ for ( i=0; i < sl->realCount; i++ ) {
+ ButtonData * bd= (ButtonData *)sl->items[i];
+
+ if(bd->dwOPFlags&QMF_NEW){
+ RemoveMenuEntryNode(sl, i--);
+ continue;
+ }
+ bd->bIsOpServName=bd->bIsServName;
+ bd->bOpInQMenu=bd->bInQMenu;
+ bd->dwOPPos=bd->dwPos;
+ bd->fEntryOpType=bd->fEntryType;
+ bd->dwOPFlags=0;
+
+ if(bd->pszName!=bd->pszOpName)
+ {
+ if(bd->pszOpName)
+ mir_free(bd->pszOpName);
+ bd->pszOpName=bd->pszName?bd->pszName:NULL;
+ }
+
+ if(bd->pszValue!=bd->pszOpValue)
+ {
+ if(bd->pszOpValue)
+ mir_free(bd->pszOpValue);
+ bd->pszOpValue=bd->pszValue?bd->pszValue:NULL;
+ }
+ }
+ iBl++;
+ }
+ }
+
+static int BuildMenuTree(HWND hToolBarTree,SortedList * sl)
+ {
+ TVINSERTSTRUCT tvis;
+ int i;
+ HTREEITEM hParent=NULL;
+ tvis.hParent = NULL;
+ tvis.hInsertAfter = TVI_LAST;
+ tvis.item.mask = TVIF_PARAM | TVIF_TEXT;
+
+ TreeView_DeleteAllItems( hToolBarTree );
+ if (!sl) return 1;
+
+ qsort(sl->items,sl->realCount,sizeof(ButtonData *),sstOpSortButtons);
+
+ for ( i=0; i < sl->realCount; i++ ) {
+ ButtonData * bd= (ButtonData *)sl->items[i];
+
+ if(bd->dwOPFlags&QMF_DELETNEEDED)
+ continue;
+
+ tvis.item.lParam= (LPARAM) bd;
+ tvis.item.pszText= bd->pszOpName;
+
+ if(bd->fEntryOpType==0)
+ tvis.hParent = NULL;
+
+ hParent=TreeView_InsertItem( hToolBarTree, &tvis );
+ if(tvis.hParent) TreeView_Expand( hMenuTree, tvis.hParent, TVE_EXPAND );
+ if (!bd->pszOpValue&&bd->fEntryOpType==0)
+ {
+ tvis.hParent = hParent;
+ }
+// else if (!(bd->fEntryOpType&QMF_EX_CHILD))
+// tvis.hParent = NULL;
+ }
+
+ return 1;
+ }
+
+static int BuildButtonsList(HWND hToolBarTree)
+ {
+ TVINSERTSTRUCT tvis;
+ int i=0;
+ tvis.hParent = NULL;
+ tvis.hInsertAfter = TVI_LAST;
+ tvis.item.mask =TVIF_PARAM | TVIF_TEXT;
+
+ TreeView_DeleteAllItems( hToolBarTree );
+
+ //for(i=0;i<g_iButtonsCount;i++)
+ while(ButtonsList[i])
+ {
+ tvis.item.lParam =(LPARAM) ButtonsList[i];
+ tvis.item.pszText = ButtonsList[i]->ptszButtonName;
+
+ TreeView_InsertItem( hToolBarTree, &tvis );
+ i++;
+ }
+ return 1;
+ }
+///////////////////////////////////
+//From UserInfoEx by DeathAxe
+//
+void MoveItem( HTREEITEM hItem, HTREEITEM hInsertAfter, BOOLEAN bAsChild )
+ {
+ TVINSERTSTRUCT tvis;
+ //TCHAR strbuf[128];
+ HTREEITEM hParent, hChild, hNewItem;
+
+ if ( !hItem || !hInsertAfter )
+ return;
+ if ( hItem == hInsertAfter )
+ return;
+
+ switch( ( ULONG_PTR )hInsertAfter ) {
+ case TVI_ROOT:
+ case TVI_FIRST:
+ case TVI_LAST:
+ hParent = NULL;
+ bAsChild = FALSE;
+ break;
+ default:
+ hParent = TreeView_GetParent( hMenuTree, hInsertAfter );
+ break;
+ }
+ // do not move a parent next to its own children!
+ if ( hItem == hParent )
+ return;
+
+ // prepare the insert structure
+ {
+ TCHAR strbuf[128];
+ tvis.item.mask=TVIF_HANDLE|TVIF_PARAM|TVIF_TEXT;
+
+ tvis.item.pszText=strbuf;
+ tvis.item.cchTextMax=sizeof(strbuf);
+ tvis.item.hItem=hItem;
+ TreeView_GetItem(hMenuTree,&tvis.item);
+ }
+
+ // item should be inserted as the first child of an existing root item
+ if ( bAsChild ) {
+ tvis.hParent = hInsertAfter;
+ tvis.hInsertAfter = ( bAsChild == 2 ) ? TVI_LAST : TVI_FIRST ;
+ }
+ // item should be inserted after an existing item
+ else {
+ tvis.hParent = hParent;
+ tvis.hInsertAfter = hInsertAfter;
+ }
+ // insert the item
+ if ( !( hNewItem = TreeView_InsertItem( hMenuTree, &tvis )) )
+ return;
+
+ // move children
+ hInsertAfter = hNewItem;
+ while( hChild = TreeView_GetChild( hMenuTree, hItem )) {
+ MoveItem( hChild, hInsertAfter, 2 );
+ }
+ // delete old tree
+ TreeView_DeleteItem( hMenuTree, hItem );
+
+ TreeView_SelectItem( hMenuTree, hNewItem );
+ //TreeView_Expand( hMenuTree, hNewItem, TVE_EXPAND );
+ }
+
+
+///////
+INT_PTR CALLBACK OptionsProc(HWND hdlg,UINT msg,WPARAM wparam,LPARAM lparam)
+ {
+ switch(msg){
+ case WM_INITDIALOG:{
+ DWORD style;
+ g_opHdlg=hdlg;
+ bOptionsInit=TRUE;
+ TranslateDialogDefault(hdlg);
+ if(g_iButtonsCount!=DBGetContactSettingByte(NULL, PLGNAME,"ButtonsCount", 0))
+ {
+ LOGFONT logFont;
+ HFONT hFont;
+ bNeedRestart=TRUE;
+ EnableWindow(GetDlgItem(hdlg,IDC_BUTTONSLIST),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_BLISTADD),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_BLISTREMOVE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUTREE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_MTREEADD),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_MTREEREMOVE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUVALUE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_RCLICKVALUE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_BUTTONNAME),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_INQMENU),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUNAME),FALSE);
+ ShowWindow(GetDlgItem(hdlg,IDC_WARNING),SW_SHOW);
+
+ hFont = (HFONT)SendMessage(GetDlgItem(hdlg, IDC_WARNING), WM_GETFONT, 0, 0);
+ GetObject(hFont, sizeof logFont, &logFont);
+ logFont.lfWeight = FW_BOLD;
+ hFont = CreateFontIndirect(&logFont);
+ SendMessage(GetDlgItem(hdlg, IDC_WARNING), WM_SETFONT, (WPARAM)hFont, 0);
+ break;
+ }
+
+ g_iOPButtonsCount=g_iButtonsCount;
+
+ hButtonsList=GetDlgItem(hdlg,IDC_BUTTONSLIST);
+ hMenuTree=GetDlgItem(hdlg,IDC_MENUTREE);
+
+ style = GetWindowLongPtr(hButtonsList,GWL_STYLE);
+ style |=TVS_NOHSCROLL;
+ SetWindowLongPtr(hButtonsList,GWL_STYLE, style);
+
+ style = GetWindowLongPtr(hMenuTree,GWL_STYLE);
+ style |=TVS_NOHSCROLL;
+ SetWindowLongPtr(hMenuTree,GWL_STYLE, style);
+ BuildButtonsList(hButtonsList);
+
+ if (!TreeView_GetCount(hButtonsList)) EnableWindow(GetDlgItem(hdlg,IDC_RCLICKVALUE),FALSE);
+
+ oldBNameProc = (WNDPROC) SetWindowLongPtr(GetDlgItem(hdlg,IDC_BUTTONNAME), GWLP_WNDPROC, (LONG) EditSubclassProc);
+ oldMNameProc = (WNDPROC) SetWindowLongPtr(GetDlgItem(hdlg,IDC_MENUNAME) , GWLP_WNDPROC, (LONG) EditSubclassProc);
+
+
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUVALUE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_INQMENU),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME),FALSE);
+ CheckDlgButton(hdlg,IDC_RAUTOSEND,(g_bRClickAuto=DBGetContactSettingByte(NULL,PLGNAME,"RClickAuto",0)));
+ CheckDlgButton(hdlg,IDC_LAUTOSEND,(g_bLClickAuto=DBGetContactSettingByte(NULL,PLGNAME,"LClickAuto",0)));
+ CheckDlgButton(hdlg,IDC_ENABLEQUICKMENU,(g_bQuickMenu=DBGetContactSettingByte(NULL, PLGNAME,"QuickMenu", 1)));
+
+ bOptionsInit=FALSE;
+ }break;
+
+ case WM_LBUTTONUP:
+ if(drag) {
+ TVHITTESTINFO hti;
+ HTREEITEM htiAfter=NULL;
+ ButtonData* bd=NULL;
+ TVITEM tvi;
+ RECT rc;
+ BYTE height;
+ BOOLEAN bAsChild = FALSE;
+
+ TreeView_SetInsertMark(hMenuTree, NULL, 0 );
+ ReleaseCapture();
+ SetCursor( LoadCursor( NULL, IDC_ARROW ));
+
+ hti.pt.x = ( SHORT )LOWORD( lparam );
+ hti.pt.y = ( SHORT )HIWORD( lparam );
+ ClientToScreen(hdlg,&hti.pt);
+ ScreenToClient(hMenuTree,&hti.pt);
+ TreeView_HitTest( hMenuTree, &hti );
+
+ if(TreeView_GetParent(hMenuTree,hti.hItem)&&TreeView_GetChild(hMenuTree,hDragItem))
+ break;
+
+ if(TreeView_GetChild(hMenuTree,hti.hItem)&&TreeView_GetChild(hMenuTree,hDragItem))
+ break;
+
+
+ if ( hti.flags & TVHT_ABOVE ) {
+ htiAfter = TVI_FIRST;
+ }
+ else
+ if ( hti.flags & ( TVHT_NOWHERE|TVHT_BELOW )) {
+ htiAfter = TVI_LAST;
+ }
+ else
+ if ( hti.flags & ( TVHT_ONITEM|TVHT_ONITEMRIGHT )) {
+ // check where over the item, the pointer is
+ if ( !TreeView_GetItemRect( hMenuTree, hti.hItem, &rc, FALSE )) {
+ drag=0;
+ break;
+ }
+ height = ( BYTE )( rc.bottom - rc.top );
+
+ if ( hti.pt.y - ( height / 3 ) < rc.top ) {
+ HTREEITEM hItem = hti.hItem;
+
+ if ( !( hti.hItem = TreeView_GetPrevSibling( hMenuTree, hItem )) ) {
+ if ( !( hti.hItem = TreeView_GetParent(hMenuTree, hItem )))
+ htiAfter = TVI_FIRST;
+ else
+ bAsChild = TRUE;
+ }
+ }
+ else
+ if ( hti.pt.y + ( height / 3 ) <= rc.bottom ) {
+ bAsChild = TRUE;
+ }
+ }
+
+
+ if(TreeView_GetChild(hMenuTree,hDragItem)&&bAsChild)
+ break;
+
+
+ if(hti.hItem){
+ tvi.hItem=hti.hItem;
+ tvi.mask=TVIF_PARAM |TVIF_HANDLE;
+ TreeView_GetItem(hMenuTree,&tvi);
+ if ((bd=(ButtonData*)tvi.lParam)&&(bd->fEntryOpType&QMF_EX_SEPARATOR))
+ bAsChild = FALSE;
+ }
+
+ if(TreeView_GetParent(hMenuTree,hti.hItem))
+ bAsChild = FALSE;
+
+
+ MoveItem( hDragItem, htiAfter?htiAfter:hti.hItem, bAsChild );
+ SendMessage(GetParent(hdlg),PSM_CHANGED,0,0);
+ drag=0;
+
+ }
+ break;
+
+ ///////////////////////////////////
+ //From UserInfoEx by DeathAxe
+ //
+ case WM_MOUSEMOVE:
+ {
+ if (!drag) break;
+ {
+ TVHITTESTINFO hti;
+
+ hti.pt.x=(short)LOWORD(lparam);
+ hti.pt.y=(short)HIWORD(lparam);
+ ClientToScreen(hdlg,&hti.pt);
+ ScreenToClient(hMenuTree,&hti.pt);
+ TreeView_HitTest(hMenuTree,&hti);
+ if ( hti.flags & ( TVHT_ONITEM|TVHT_ONITEMRIGHT )) {
+ RECT rc;
+ BYTE height;
+
+ if ( TreeView_GetItemRect(hMenuTree, hti.hItem, &rc, FALSE )) {
+ height = ( BYTE )( rc.bottom - rc.top );
+
+ if ( hti.pt.y - ( height / 3 ) < rc.top ) {
+ SetCursor( LoadCursor( NULL, IDC_ARROW ));
+ TreeView_SetInsertMark( hMenuTree, hti.hItem, 0 );
+ }
+ else
+ if ( hti.pt.y + ( height / 3 ) > rc.bottom ) {
+ SetCursor( LoadCursor( NULL, IDC_ARROW ));
+ TreeView_SetInsertMark( hMenuTree, hti.hItem, 1 );
+ }
+ else {
+ TreeView_SetInsertMark( hMenuTree, NULL, 0 );
+ SetCursor( LoadCursor( GetModuleHandle(NULL), MAKEINTRESOURCE( 183 )) );
+ }
+ }
+ }
+ else {
+ if ( hti.flags & TVHT_ABOVE ) SendMessage( hMenuTree, WM_VSCROLL, MAKEWPARAM( SB_LINEUP, 0 ), 0 );
+ if ( hti.flags & TVHT_BELOW ) SendMessage( hMenuTree, WM_VSCROLL, MAKEWPARAM( SB_LINEDOWN, 0 ), 0 );
+ TreeView_SetInsertMark( hMenuTree, NULL, 0 );
+ }
+ }
+ }break;
+ /////////////
+ case WM_DESTROY:
+ if (g_varhelpDlg)
+ DestroyWindow(g_varhelpDlg);
+ g_varhelpDlg=NULL;
+ break;
+
+ case WM_NOTIFY:{
+ switch(((LPNMHDR)lparam)->idFrom) {
+ case 0:{
+ if (((LPNMHDR)lparam)->code == PSN_APPLY ) {
+ if (!bNeedRestart){
+ SetMenuEntryProperties(hdlg);
+ SaveMenuTree(hdlg);
+ }
+ DBWriteContactSettingByte(NULL,PLGNAME,"RClickAuto",(BYTE)(g_bRClickAuto=IsDlgButtonChecked(hdlg,IDC_RAUTOSEND)));
+ DBWriteContactSettingByte(NULL,PLGNAME,"LClickAuto",(BYTE)(g_bLClickAuto=IsDlgButtonChecked(hdlg,IDC_LAUTOSEND)));
+ DBWriteContactSettingByte(NULL,PLGNAME,"QuickMenu",(BYTE)(g_bQuickMenu=IsDlgButtonChecked(hdlg,IDC_ENABLEQUICKMENU)));
+ return 1;
+ }
+ else if (((LPNMHDR)lparam)->code == PSN_RESET ) {
+ if (!bNeedRestart)
+ RestoreModuleData(hdlg);
+ return 1;
+ }
+ }
+ break;
+
+ case IDC_MENUTREE:
+ switch (((LPNMHDR)lparam)->code){
+
+ case TVN_KEYDOWN:{
+ TV_KEYDOWN* pTVKeyDown = (TV_KEYDOWN*) ((LPNMHDR)lparam);
+ if ( pTVKeyDown->wVKey == VK_F2 )
+ TreeView_EditLabel(hMenuTree,TreeView_GetSelection(hMenuTree));
+ else if ( pTVKeyDown->wVKey == VK_DELETE )
+ SendMessage(hdlg,WM_COMMAND,IDC_MTREEREMOVE,0);
+ }break;
+
+ case TVN_BEGINLABELEDITA:
+ case TVN_BEGINLABELEDITW:
+ hwndEdit=TreeView_GetEditControl(hMenuTree);
+ oldEditProc = (WNDPROC) SetWindowLongPtr(hwndEdit, GWLP_WNDPROC, (LONG) LabelEditSubclassProc);
+ break;
+
+ case TVN_ENDLABELEDITA:
+ case TVN_ENDLABELEDITW:
+ {
+ TVITEM tvi;
+ ButtonData* bd=NULL;
+ TCHAR strbuf[256];
+ TCHAR szLabel[256];
+
+ SetWindowLongPtr(hwndEdit, GWLP_WNDPROC, (LONG) oldEditProc);
+
+ tvi.pszText = strbuf;
+ tvi.cchTextMax = sizeof(strbuf);
+ tvi.mask=TVIF_TEXT |TVIF_HANDLE|TVIF_PARAM;
+ tvi.hItem=TreeView_GetSelection(hMenuTree);
+ TreeView_GetItem(hMenuTree,&tvi);
+
+ GetWindowText(hwndEdit, szLabel, sizeof(szLabel));
+ hwndEdit=NULL;
+ if (!_tcslen(szLabel)) break;
+ if (bd = (ButtonData*)tvi.lParam){
+ if (!_tcscmp(szLabel,_T("---"))) {
+ if(TreeView_GetChild(hMenuTree,tvi.hItem))
+ break;
+ else{
+ bd->fEntryOpType=QMF_EX_SEPARATOR;
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUVALUE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME),FALSE);
+ SetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE),_T(""));
+ }
+ }
+ else {
+ bd->fEntryOpType&=~QMF_EX_SEPARATOR;
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUVALUE),TRUE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME),TRUE);
+ SetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE),bd->pszOpValue/*?bd->pszOpValue:bd->pszValue*/);
+ }
+
+ bd->pszOpName=mir_tstrdup(szLabel);
+
+ tvi.pszText=szLabel;
+ TreeView_SetItem(hMenuTree, &tvi);
+ SendMessage(GetParent(hdlg),PSM_CHANGED,0,0);
+ }
+ }break;
+
+ case NM_KILLFOCUS:
+ TreeView_EndEditLabelNow(hButtonsList, 1);
+ break;
+
+ case TVN_BEGINDRAGA:
+ case TVN_BEGINDRAGW:
+ SetCapture(hdlg);
+ drag=1;
+ hDragItem=((LPNMTREEVIEW)lparam)->itemNew.hItem;
+ TreeView_SelectItem(hMenuTree,hDragItem);
+ break;
+
+ case TVN_SELCHANGINGA:
+ case TVN_SELCHANGINGW:
+ {
+ TVITEM tvi;
+ HTREEITEM hti;
+ ButtonData* bd;
+
+ hti=TreeView_GetSelection(hMenuTree);
+
+ if (hti==NULL)
+ break;
+
+ tvi.hItem=hti;
+ tvi.mask=TVIF_HANDLE|TVIF_PARAM;
+ TreeView_GetItem(hMenuTree,&tvi);
+
+ if (tvi.lParam == 0)
+ break;
+
+ bd = ( ButtonData* )tvi.lParam;
+ if (bd) {
+ TCHAR szValue[256];
+ GetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE), szValue, sizeof(szValue));
+ if(_tcslen(szValue))
+ {
+ if(bd->pszOpValue&&(bd->pszOpValue!=bd->pszValue))
+ mir_free(bd->pszOpValue);
+ bd->pszOpValue=mir_tstrdup(szValue);
+ }
+ bd->bOpInQMenu=IsDlgButtonChecked(hdlg,IDC_INQMENU);
+ bd->bIsOpServName=IsDlgButtonChecked(hdlg,IDC_ISSERVNAME);
+ }
+ }break;
+ case TVN_SELCHANGEDA:
+ case TVN_SELCHANGEDW:
+ {
+ TVITEM tvi;
+ HTREEITEM hti;
+ ButtonData* bd=NULL;
+
+ hti=TreeView_GetSelection(hMenuTree);
+
+ if (hti==NULL)
+ break;
+
+ tvi.mask=TVIF_HANDLE|TVIF_PARAM;
+
+ tvi.hItem=hti;
+ TreeView_GetItem(hMenuTree,&tvi);
+
+
+ bd = ( ButtonData* )tvi.lParam;
+ if (bd) {
+ if (!TreeView_GetChild(hMenuTree, tvi.hItem)&&!(bd->fEntryOpType&QMF_EX_SEPARATOR))
+ {
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUVALUE),TRUE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME),TRUE);
+ EnableWindow(GetDlgItem(hdlg,IDC_INQMENU),TRUE);
+ SetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE),bd->pszOpValue/*?bd->pszOpValue:bd->pszValue*/);
+ }
+ else
+ {
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUVALUE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME),FALSE);
+ if (!(bd->fEntryOpType&QMF_EX_SEPARATOR))
+ EnableWindow(GetDlgItem(hdlg,IDC_INQMENU),FALSE);
+ SetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE),_T(""));
+ }
+ CheckDlgButton(hdlg,IDC_INQMENU,bd->bOpInQMenu);
+ CheckDlgButton(hdlg,IDC_ISSERVNAME,bd->bIsOpServName);
+ }
+ }
+ }break;
+
+ case IDC_BUTTONSLIST:
+ switch (((LPNMHDR)lparam)->code) {
+
+ case TVN_KEYDOWN:{
+ TV_KEYDOWN* pTVKeyDown = (TV_KEYDOWN*) ((LPNMHDR)lparam);
+ if ( pTVKeyDown->wVKey == VK_F2 )
+ TreeView_EditLabel(hButtonsList,TreeView_GetSelection(hButtonsList));
+ else if ( pTVKeyDown->wVKey == VK_DELETE )
+ SendMessage(hdlg,WM_COMMAND,IDC_BLISTREMOVE,0);
+ }break;
+
+ case TVN_BEGINLABELEDITA:
+ case TVN_BEGINLABELEDITW:
+ hwndEdit=TreeView_GetEditControl(hButtonsList);
+ oldEditProc = (WNDPROC) SetWindowLongPtr(hwndEdit, GWLP_WNDPROC, (LONG) LabelEditSubclassProc);
+ break;
+
+ case TVN_ENDLABELEDITA:
+ case TVN_ENDLABELEDITW:{
+ TVITEM tvi;
+ TCHAR strbuf[128];
+ TCHAR szLabel[128];
+
+ SetWindowLongPtr(hwndEdit, GWLP_WNDPROC, (LONG) oldEditProc);
+
+ tvi.pszText = strbuf;
+ tvi.cchTextMax = sizeof(strbuf);
+ tvi.mask=TVIF_TEXT |TVIF_HANDLE|TVIF_PARAM;
+ tvi.hItem=TreeView_GetSelection(hButtonsList);
+ TreeView_GetItem(hButtonsList,&tvi);
+
+ GetWindowText(hwndEdit, szLabel, sizeof(szLabel));
+ hwndEdit=NULL;
+ if (!_tcslen(szLabel)) break;
+
+ tvi.pszText=szLabel;
+ ((ListData*)tvi.lParam)->dwOPFlags|=QMF_RENAMED;
+
+ TreeView_SetItem(hButtonsList, &tvi);
+ SendMessage(GetParent(hdlg),PSM_CHANGED,0,0);
+ }break;
+
+ case TVN_SELCHANGINGA:
+ case TVN_SELCHANGINGW:
+ SetMenuEntryProperties(hdlg);
+ break;
+
+ case TVN_SELCHANGEDA:
+ case TVN_SELCHANGEDW:{
+ TVITEM tvi;
+ HTREEITEM hti;
+
+ hti=TreeView_GetSelection(hButtonsList);
+
+ if(hti==NULL||!TreeView_GetCount(hButtonsList)) {
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUVALUE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_INQMENU),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME2),FALSE);
+ SetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE),_T(""));
+ break;
+ }
+
+ tvi.mask=TVIF_HANDLE|TVIF_PARAM;
+ tvi.hItem=hti;
+ TreeView_GetItem(hButtonsList,&tvi);
+
+ if(tvi.lParam==0) break;
+
+ BuildMenuTree(hMenuTree,(SortedList *)((ListData*)tvi.lParam)->sl);
+
+ SetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE),_T(""));
+ EnableWindow(GetDlgItem(hdlg,IDC_RCLICKVALUE),TRUE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME2),TRUE);
+ CheckDlgButton(hdlg,IDC_ISSERVNAME2,((ListData*)tvi.lParam)->bIsOpServName);
+
+ if (((ListData*)tvi.lParam)->ptszOPQValue)
+ SetWindowText(GetDlgItem(hdlg,IDC_RCLICKVALUE),((ListData*)tvi.lParam)->ptszOPQValue);
+ else
+ SetWindowText(GetDlgItem(hdlg,IDC_RCLICKVALUE),_T(""));
+
+ }break;
+ }break;
+ }
+ }break;
+
+ case WM_COMMAND:{
+ switch(LOWORD(wparam)) {
+ case IDC_VARHELP:{
+ if (!g_varhelpDlg)
+ g_varhelpDlg=CreateDialog(hinstance,MAKEINTRESOURCE(IDD_HELPDIALOG), 0, HelpDlgProc);
+ else
+ //ShowWindow(g_varhelpDlg,SW_SHOWDEFAULT);
+ SetWindowPos(g_varhelpDlg,0,0,0,0,0,SWP_SHOWWINDOW|SWP_NOMOVE|SWP_NOSIZE);
+ }break;
+ case IDC_BLISTADD:{
+ TVINSERTSTRUCT tvis;
+ ListData* ld=NULL;
+ TCHAR namebuff[MAX_PATH]={'\0'};
+ int count=TreeView_GetCount(hButtonsList);
+ if (count>10) break;
+ if(g_iOPButtonsCount==99){
+ MessageBox(NULL,_T("Congratulation!\n\
+ You have clicked this button 100 times!\n\
+ There was access violation at this point...\n\
+ And now function for freeing resources must be called...\n\
+ But no! there's only break :D"),_T("You win!"),MB_OK);
+ break;
+ }
+
+ ld = (ListData *)mir_alloc(sizeof(ListData));
+ ButtonsList[g_iOPButtonsCount++]=ld;
+
+ ld->sl=List_Create(0,1);
+ ld->dwOPFlags=QMF_NEW;
+ ld->bIsOpServName=0;
+ ld->ptszButtonName=NULL;
+ ld->ptszOPQValue=NULL;
+ ld->ptszQValue=NULL;
+ tvis.hParent = NULL;
+ tvis.hInsertAfter = TVI_LAST;
+
+ GetWindowText(GetDlgItem(hdlg,IDC_BUTTONNAME),namebuff,MAX_PATH);
+
+ tvis.item.mask=TVIF_PARAM|TVIF_TEXT;
+ tvis.item.pszText=(_tcslen(namebuff))?namebuff:TranslateT("New Button");
+ tvis.item.lParam=(LPARAM)ld;
+ TreeView_SelectItem(hButtonsList,TreeView_InsertItem(hButtonsList,&tvis));
+
+ }break;
+
+ case IDC_BLISTREMOVE:{
+ TVITEM tvi;
+ ListData* ld;
+
+ if (!(tvi.hItem=TreeView_GetSelection(hButtonsList)))
+ break;
+
+ tvi.mask=TVIF_HANDLE|TVIF_PARAM;
+ TreeView_GetItem(hButtonsList,&tvi);
+
+ ld= (ListData*)tvi.lParam;
+
+ ld->dwOPFlags|=QMF_DELETNEEDED;
+
+ TreeView_DeleteItem(hButtonsList,tvi.hItem);
+ if (!TreeView_GetCount(hButtonsList))
+ {
+ TreeView_DeleteAllItems(hMenuTree);
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUVALUE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_RCLICKVALUE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_INQMENU),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME2),FALSE);
+ SetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE),_T(""));
+ SetWindowText(GetDlgItem(hdlg,IDC_RCLICKVALUE),_T(""));
+ }
+ }break;
+
+ case IDC_MTREEADD:{
+ TVINSERTSTRUCT tvis;
+ TVITEM tvi;
+ ButtonData *bd=NULL;
+ SortedList *sl=NULL;
+ TCHAR namebuff[MAX_PATH]={'\0'};
+
+ if (!TreeView_GetCount(hButtonsList)) break;
+ if (!(tvi.hItem=TreeView_GetSelection(hButtonsList))) break;
+
+ bd = (ButtonData *)mir_alloc(sizeof(ButtonData));
+ memset(bd,0,sizeof(ButtonData));
+
+ GetWindowText(GetDlgItem(hdlg,IDC_MENUNAME),namebuff,MAX_PATH);
+
+ bd->dwOPPos=TreeView_GetCount(hMenuTree)-1;
+ bd->pszOpName=_tcslen(namebuff)?mir_tstrdup(namebuff):mir_tstrdup(TranslateT("New Menu Entry"));
+ bd->pszOpValue=mir_tstrdup(bd->pszOpName);
+ bd->fEntryOpType=!_tcscmp(namebuff,_T("---"))?QMF_EX_SEPARATOR:0;
+ bd->dwOPFlags=QMF_NEW;
+ bd->pszName=NULL;
+ bd->pszValue=NULL;
+
+
+ tvi.mask=TVIF_HANDLE|TVIF_PARAM;
+
+ TreeView_GetItem(hButtonsList,&tvi);
+
+ sl=((ListData*)tvi.lParam)->sl;
+
+ List_InsertPtr(sl,bd);
+
+ tvis.hParent = NULL;
+ tvis.hInsertAfter = TVI_LAST;
+ tvis.item.mask=TVIF_PARAM|TVIF_TEXT;
+ tvis.item.pszText=bd->pszOpName;
+ tvis.item.lParam=(LPARAM)bd;
+ TreeView_SelectItem(hMenuTree,TreeView_InsertItem(hMenuTree,&tvis));
+ }break;
+
+ case IDC_MTREEREMOVE:{
+ TVITEM tvi;
+ TVINSERTSTRUCT tvis;
+ HTREEITEM hti=NULL;
+ ButtonData *bd=NULL;
+ tvi.mask=TVIF_HANDLE|TVIF_PARAM;
+ if (!(tvi.hItem=TreeView_GetSelection(hMenuTree)))
+ break;
+ TreeView_GetItem(hMenuTree,&tvi);
+ hti=tvi.hItem;
+
+ bd= (ButtonData*)tvi.lParam;
+ bd->dwOPFlags|=QMF_DELETNEEDED;
+
+ if(tvi.hItem=TreeView_GetChild(hMenuTree,tvi.hItem)) {
+ TCHAR strbuf[128];
+ while(tvi.hItem){
+ tvis.hInsertAfter=hti;
+ tvi.pszText = strbuf;
+ tvi.cchTextMax = sizeof(strbuf);
+ tvi.mask=TVIF_HANDLE|TVIF_PARAM|TVIF_TEXT;
+
+ TreeView_GetItem(hMenuTree,&tvi);
+ tvis.hParent=NULL;
+ tvis.item=tvi;
+ TreeView_InsertItem(hMenuTree,&tvis);
+ tvi.hItem=TreeView_GetNextSibling(hMenuTree,tvi.hItem);
+ }
+ }
+
+ TreeView_DeleteItem(hMenuTree,hti);
+ if (!TreeView_GetCount(hMenuTree)) {
+ EnableWindow(GetDlgItem(hdlg,IDC_MENUVALUE),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_ISSERVNAME),FALSE);
+ EnableWindow(GetDlgItem(hdlg,IDC_INQMENU),FALSE);
+ SetWindowText(GetDlgItem(hdlg,IDC_MENUVALUE),_T(""));
+ }
+
+ }break;
+
+ }
+ }break;
+
+ case WM_NCDESTROY:
+ if(oldBNameProc) SetWindowLongPtr(GetDlgItem(hdlg,IDC_BUTTONNAME), GWLP_WNDPROC, (LONG) oldBNameProc);
+ if(oldMNameProc) SetWindowLongPtr(GetDlgItem(hdlg,IDC_MENUNAME) , GWLP_WNDPROC, (LONG) oldMNameProc);
+ break;
+
+ case WM_CLOSE:
+ EndDialog(hdlg,0);
+ return 0;
+ }
+ if (HIWORD(wparam)==BN_CLICKED && GetFocus()==(HWND)lparam)
+ SendMessage(GetParent(hdlg),PSM_CHANGED,0,0);
+ else if ((HIWORD(wparam) == EN_CHANGE)&&(GetFocus()==(HWND)lparam))
+ if (!bOptionsInit) SendMessage(GetParent(hdlg),PSM_CHANGED,0,0);
+
+ return 0;
+ }
+
+int OptionsInit(WPARAM wparam,LPARAM lparam)
+{
+ OPTIONSDIALOGPAGE odp={0};
+ odp.cbSize = sizeof(odp);
+ odp.position = 940000000;
+ odp.hInstance = hinstance;
+ odp.pszTemplate = MAKEINTRESOURCEA(IDD_OPTIONS);
+ odp.pszTitle = LPGEN("Quick Messages");
+ odp.pfnDlgProc = OptionsProc;
+ odp.pszGroup = LPGEN("Plugins");
+ odp.flags = ODPF_BOLDGROUPS;
+ Options_AddPage(wparam,&odp);
+
+ return 0;
+}
diff --git a/plugins/QuickMessages/src/quickmessages.h b/plugins/QuickMessages/src/quickmessages.h
new file mode 100644
index 0000000000..f236b4175f
--- /dev/null
+++ b/plugins/QuickMessages/src/quickmessages.h
@@ -0,0 +1,84 @@
+/*
+Quick Messages plugin for Miranda IM
+
+Copyright (C) 2008 Danil Mozhar
+
+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 3 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, see <http://www.gnu.org/licenses/>.
+*/
+#define _CRT_SECURE_NO_DEPRECATE
+
+
+#include <tchar.h>
+#include <windows.h>
+#include "resource.h"
+#include <stdio.h>
+#include <commctrl.h>
+#include <Richedit.h>
+
+#define MIRANDA_VER 0x0A00
+#include "newpluginapi.h"
+#include "m_utils.h"
+#include "m_system.h"
+#include "m_clist.h"
+#include "m_options.h"
+#include "m_database.h"
+#include "m_protomod.h"
+#include "m_langpack.h"
+#include "m_icolib.h"
+#include "m_message.h"
+#include "m_contacts.h"
+
+#include "Utils.h"
+#include "m_msg_buttonsbar.h"
+
+#pragma optimize("gsy",on)
+
+#define MODULENAME "Quick Messages"
+#define PLGNAME "QuickMessages"
+
+extern HINSTANCE hinstance;
+extern HICON hIcon;
+extern ListData* ButtonsList[100];
+extern SortedList* QuickList;
+extern BOOL g_bRClickAuto;
+extern BOOL g_bLClickAuto;
+extern BOOL g_bQuickMenu;
+extern int g_iButtonsCount;
+
+//#define MIIM_STRING 0x00000040
+
+
+
+int AddIcon(HICON icon, char *name, char *description);
+int OptionsInit(WPARAM,LPARAM);
+
+
+#define IDC_MESSAGE 1002
+#define IDC_CHATMESSAGE 1009
+
+#define SIZEOF(X)(sizeof(X)/sizeof(X[0]))
+
+
+#define QMESSAGES_NAME "quickmessages"
+
+
+#define QMESSAGES_VERSION_URL "http://miranda.radicaled.ru/public/updater/quickmessages.txt"
+
+#define QMESSAGES_CHAGELOG_URL "http://miranda.radicaled.ru/public/quickmessages/changelog_en.txt"
+
+#define QMESSAGES_UPDATE_URL "http://miranda.radicaled.ru/public/quickmessages/"QMESSAGES_NAME".zip"
+
+#define QMESSAGES_UPDATE_URL "http://miranda.radicaled.ru/public/quickmessages/"QMESSAGES_NAME".zip"
+
+#define QMESSAGES_VERSION_PREFIX "QuickMessages "
diff --git a/plugins/QuickMessages/src/resource.h b/plugins/QuickMessages/src/resource.h
new file mode 100644
index 0000000000..9facd53bf2
--- /dev/null
+++ b/plugins/QuickMessages/src/resource.h
@@ -0,0 +1,47 @@
+//{{NO_DEPENDENCIES}}
+// Microsoft Visual C++ generated include file.
+// Used by quickmessages.rc
+//
+#define IDD_OPTIONS 101
+#define IDI_QICON 102
+#define IDC_BUTTONSLIST 104
+#define IDC_BLISTADD 105
+#define IDC_BLISTREMOVE 106
+#define IDC_MENUTREE 107
+#define IDC_MTREEADD 108
+#define IDC_MTREEREMOVE 109
+#define IDC_MENUVALUE 110
+#define IDC_RCLICKVALUE 111
+#define IDD_HELPDIALOG 112
+#define IDC_BUTTONNAME 1076
+#define IDC_MENUNAME 1077
+#define IDC_LAUTOSEND 1079
+#define IDC_RAUTOSEND 1080
+#define IDC_INQMENU 1081
+#define IDC_RAUTOSEND2 1082
+#define IDC_ENABLEQUICKMENU 1082
+#define IDC_ISSERVNAME 1083
+#define IDC_WARNING 1084
+#define IDC_VARHELP 1085
+#define IDC_VARTEXT 1086
+#define IDC_ISSERVNAME2 1086
+#define IDC_VARCLIP 1087
+#define IDC_VARPUNAME 1088
+#define IDC_VARPLNAME 1089
+#define IDC_VARCNAME 1090
+#define IDC_STATICTITLE 1091
+#define IDC_STATICTITLE2 1092
+#define IDC_VARCFNAME 1093
+#define IDC_VARCLNAME 1094
+#define IDC_STATIC -1
+
+// Next default values for new objects
+//
+#ifdef APSTUDIO_INVOKED
+#ifndef APSTUDIO_READONLY_SYMBOLS
+#define _APS_NEXT_RESOURCE_VALUE 113
+#define _APS_NEXT_COMMAND_VALUE 40015
+#define _APS_NEXT_CONTROL_VALUE 1092
+#define _APS_NEXT_SYMED_VALUE 1125
+#endif
+#endif