From 48540940b6c28bb4378abfeb500ec45a625b37b6 Mon Sep 17 00:00:00 2001 From: Vadim Dashevskiy Date: Tue, 15 May 2012 10:38:20 +0000 Subject: initial commit git-svn-id: http://svn.miranda-ng.org/main/trunk@2 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- protocols/IcqOscarJ/changeinfo/editstring.cpp | 374 ++++++++++++++++++++++++++ 1 file changed, 374 insertions(+) create mode 100644 protocols/IcqOscarJ/changeinfo/editstring.cpp (limited to 'protocols/IcqOscarJ/changeinfo/editstring.cpp') diff --git a/protocols/IcqOscarJ/changeinfo/editstring.cpp b/protocols/IcqOscarJ/changeinfo/editstring.cpp new file mode 100644 index 0000000000..1a4d7138c6 --- /dev/null +++ b/protocols/IcqOscarJ/changeinfo/editstring.cpp @@ -0,0 +1,374 @@ +// ---------------------------------------------------------------------------80 +// ICQ plugin for Miranda Instant Messenger +// ________________________________________ +// +// Copyright © 2001-2004 Richard Hughes, Martin Öberg +// Copyright © 2004-2009 Joe Kucera, Bio +// +// 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +// +// ----------------------------------------------------------------------------- +// +// File name : $URL: http://miranda.googlecode.com/svn/trunk/miranda/protocols/IcqOscarJ/changeinfo/editstring.cpp $ +// Revision : $Revision: 11081 $ +// Last change on : $Date: 2009-12-22 00:10:01 +0200 (Ð’Ñ‚, 22 дек 2009) $ +// Last change by : $Author: jokusoftware $ +// +// DESCRIPTION: +// +// ChangeInfo Plugin stuff +// +// ----------------------------------------------------------------------------- + +#include "icqoscar.h" + + +static ChangeInfoData *dataStringEdit = NULL; +static WNDPROC OldStringEditProc, OldExpandButtonProc; +static HWND hwndEdit = NULL, hwndExpandButton = NULL, hwndUpDown = NULL; + +static const char escapes[]={'a','\a', +'b','\b', +'e',27, +'f','\f', +'r','\r', +'t','\t', +'v','\v', +'\\','\\'}; + +static void EscapesToMultiline(WCHAR *str,PDWORD selStart,PDWORD selEnd) +{ //converts "\\n" and "\\t" to "\r\n" and "\t" because a multi-line edit box can show them properly + DWORD i; + + for(i=0; *str; str++, i++) + { + if (*str != '\\') continue; + if (str[1] == 'n') + { + *str++ = '\r'; + i++; + *str = '\n'; + } + else if (str[1] == 't') + { + *str = '\t'; + memmove(str+1, str+2, sizeof(WCHAR)*(strlennull(str)-1)); + + if (*selStart>i) --*selStart; + if (*selEnd>i) --*selEnd; + } + } +} + + + +static void EscapesToBinary(char *str) +{ + for(;*str;str++) + { + if(*str!='\\') continue; + if(str[1]=='n') {*str++='\r'; *str='\n'; continue;} + if(str[1]=='0') + { + char *codeend; + *str=(char)strtol(str+1,&codeend,8); + if(*str==0) {*str='\\'; continue;} + memmove(str+1,codeend,strlennull(codeend)+1); + continue; + } + for(int i=0;i=' ') + { + *pout++=*str; + continue; + } + if(str[0]=='\r' && str[1]=='\n') + { + *pout++='\\'; + *pout++='n'; + str++; + continue; + } + if(extra<3) + { + extra+=8; len+=8; + pout=out=(char*)SAFE_REALLOC(out,len); + } + *pout++='\\'; + for(i = 0; i < SIZEOF(escapes); i += 2) + if(*str==escapes[i+1]) + { + *pout++=escapes[i]; + extra--; + break; + } + if(i < SIZEOF(escapes)) continue; + *pout++='0'; extra--; + if(*str>=8) + { + *pout++=(*str>>3)+'0'; + extra--; + } + *pout++=(*str&7)+'0'; extra--; + } + *pout='\0'; + return out; +} + + + +static LRESULT CALLBACK StringEditSubclassProc(HWND hwnd,UINT msg,WPARAM wParam,LPARAM lParam) +{ + switch(msg) + { + case WM_KEYDOWN: + if (wParam==VK_ESCAPE) + { + if (dataStringEdit) + dataStringEdit->EndStringEdit(0); + return 0; + } + if (wParam==VK_RETURN) + { + if (GetWindowLong(hwnd, GWL_STYLE) & ES_MULTILINE && !(GetKeyState(VK_CONTROL) & 0x8000)) break; + if (dataStringEdit) + dataStringEdit->EndStringEdit(1); + return 0; + } + break; + + case WM_GETDLGCODE: + return DLGC_WANTALLKEYS|CallWindowProc(OldStringEditProc, hwnd, msg, wParam, lParam); + + case WM_KILLFOCUS: + if ((HWND)wParam == hwndExpandButton) break; + if (dataStringEdit) + dataStringEdit->EndStringEdit(1); + return 0; + } + return CallWindowProc(OldStringEditProc, hwnd, msg, wParam, lParam); +} + + + +static LRESULT CALLBACK ExpandButtonSubclassProc(HWND hwnd,UINT msg,WPARAM wParam,LPARAM lParam) +{ + switch(msg) + { + case WM_LBUTTONUP: + if(GetCapture()==hwnd) + { + //do expand + RECT rcStart,rcEnd; + DWORD selStart,selEnd; + WCHAR *text; + BOOL animEnabled=TRUE; + + GetWindowRect(hwndEdit,&rcStart); + InflateRect(&rcStart,2,2); + + text = GetWindowTextUcs(hwndEdit); + SendMessage(hwndEdit,EM_GETSEL,(WPARAM)&selStart,(LPARAM)&selEnd); + DestroyWindow(hwndEdit); + EscapesToMultiline(text,&selStart,&selEnd); + hwndEdit=CreateWindowExA(WS_EX_TOOLWINDOW,"EDIT","",WS_POPUP|WS_BORDER|WS_VISIBLE|ES_WANTRETURN|ES_AUTOVSCROLL|WS_VSCROLL|ES_MULTILINE,rcStart.left,rcStart.top,rcStart.right-rcStart.left,rcStart.bottom-rcStart.top,NULL,NULL,hInst,NULL); + SetWindowTextUcs(hwndEdit, text); + OldStringEditProc=(WNDPROC)SetWindowLongPtr(hwndEdit,GWLP_WNDPROC,(LONG_PTR)StringEditSubclassProc); + SendMessage(hwndEdit,WM_SETFONT,(WPARAM)dataStringEdit->hListFont,0); + SendMessage(hwndEdit,EM_SETSEL,selStart,selEnd); + SetFocus(hwndEdit); + + rcEnd.left=rcStart.left; rcEnd.top=rcStart.top; + rcEnd.right=rcEnd.left+350; + rcEnd.bottom=rcEnd.top+150; + if (LOBYTE(LOWORD(GetVersion()))>4 || HIBYTE(LOWORD(GetVersion()))>0) + SystemParametersInfo(SPI_GETCOMBOBOXANIMATION,0,&animEnabled,FALSE); + if(animEnabled) + { + DWORD startTime,timeNow; + startTime=GetTickCount(); + for(;;) + { + UpdateWindow(hwndEdit); + timeNow=GetTickCount(); + if(timeNow>startTime+200) break; + SetWindowPos(hwndEdit,0,rcEnd.left,rcEnd.top,(rcEnd.right-rcStart.right)*(timeNow-startTime)/200+rcStart.right-rcEnd.left,(rcEnd.bottom-rcStart.bottom)*(timeNow-startTime)/200+rcStart.bottom-rcEnd.top,SWP_NOZORDER); + } + } + SetWindowPos(hwndEdit,0,rcEnd.left,rcEnd.top,rcEnd.right-rcEnd.left,rcEnd.bottom-rcEnd.top,SWP_NOZORDER); + + DestroyWindow(hwnd); + hwndExpandButton=NULL; + + SAFE_FREE((void**)&text); + } + break; + } + return CallWindowProc(OldExpandButtonProc,hwnd,msg,wParam,lParam); +} + + +void ChangeInfoData::BeginStringEdit(int iItem, RECT *rc, int i, WORD wVKey) +{ + char *szValue; + char str[80]; + int alloced=0; + + EndStringEdit(0); + InflateRect(rc,-2,-2); + rc->left-=2; + if (setting[i].displayType & LIF_PASSWORD && !settingData[i].changed) + szValue = " "; + else if ((setting[i].displayType & LIM_TYPE) == LI_NUMBER) + { + szValue = str; + null_snprintf(str, sizeof(str), "%d", settingData[i].value ); + } + else if (settingData[i].value) + { + szValue = BinaryToEscapes((char*)settingData[i].value); + alloced = 1; + } + else szValue = ""; + + iEditItem = iItem; + + if ((setting[i].displayType & LIM_TYPE)==LI_LONGSTRING) + { + rc->right-=rc->bottom-rc->top; + hwndExpandButton=CreateWindowA("BUTTON","",WS_VISIBLE|WS_CHILD|BS_PUSHBUTTON|BS_ICON,rc->right,rc->top,rc->bottom-rc->top,rc->bottom-rc->top,hwndList,NULL,hInst,NULL); + SendMessage(hwndExpandButton,BM_SETIMAGE,IMAGE_ICON,(LPARAM)LoadImage(hInst,MAKEINTRESOURCE(IDI_EXPANDSTRINGEDIT),IMAGE_ICON,0,0,LR_SHARED)); + OldExpandButtonProc=(WNDPROC)SetWindowLongPtr(hwndExpandButton,GWLP_WNDPROC,(LONG_PTR)ExpandButtonSubclassProc); + } + + dataStringEdit = this; + hwndEdit = CreateWindow(_T("EDIT"),_T(""),WS_VISIBLE|WS_CHILD|ES_AUTOHSCROLL|((setting[i].displayType&LIM_TYPE)==LI_NUMBER?ES_NUMBER:0)|(setting[i].displayType&LIF_PASSWORD?ES_PASSWORD:0),rc->left,rc->top,rc->right-rc->left,rc->bottom-rc->top,hwndList,NULL,hInst,NULL); + SetWindowTextUtf(hwndEdit, szValue); + if (alloced) SAFE_FREE(&szValue); + OldStringEditProc=(WNDPROC)SetWindowLongPtr(hwndEdit,GWLP_WNDPROC,(LONG_PTR)StringEditSubclassProc); + SendMessage(hwndEdit,WM_SETFONT,(WPARAM)hListFont,0); + if ((setting[i].displayType & LIM_TYPE) == LI_NUMBER) + { + int *range= (int*)setting[i].pList; + RECT rcUpDown; + hwndUpDown=CreateWindow(UPDOWN_CLASS,_T(""),WS_VISIBLE|WS_CHILD|UDS_AUTOBUDDY|UDS_ALIGNRIGHT|UDS_HOTTRACK|UDS_NOTHOUSANDS|UDS_SETBUDDYINT,0,0,0,0,hwndList,NULL,hInst,NULL); + SendMessage(hwndUpDown, UDM_SETRANGE32, range[0], range[1]); + SendMessage(hwndUpDown, UDM_SETPOS32, 0, settingData[i].value); + if(!(setting[i].displayType & LIF_ZEROISVALID) && settingData[i].value==0) + SetWindowTextA(hwndEdit, ""); + GetClientRect(hwndUpDown, &rcUpDown); + rc->right -= rcUpDown.right; + SetWindowPos(hwndEdit,0,0,0,rc->right-rc->left,rc->bottom-rc->top,SWP_NOZORDER|SWP_NOMOVE); + } + SendMessage(hwndEdit,EM_SETSEL,0,(LPARAM)-1); + SetFocus(hwndEdit); + PostMessage(hwndEdit,WM_KEYDOWN,wVKey,0); +} + + +void ChangeInfoData::EndStringEdit(int save) +{ + if (hwndEdit == NULL || iEditItem == -1 || this != dataStringEdit) return; + if (save) + { + char *text = (char*)SAFE_MALLOC(GetWindowTextLength(hwndEdit)+1); + + GetWindowTextA(hwndEdit,(char*)text,GetWindowTextLength(hwndEdit)+1); + EscapesToBinary(text); + if((setting[iEditItem].displayType&LIM_TYPE)==LI_NUMBER) + { + LPARAM newValue; + int *range=(int*)setting[iEditItem].pList; + newValue = atoi(text); + if (newValue) + { + if (newValuerange[1]) newValue=range[1]; + } + settingData[iEditItem].changed = settingData[iEditItem].value != newValue; + settingData[iEditItem].value = newValue; + SAFE_FREE(&text); + } + else + { + if (!(setting[iEditItem].displayType & LIF_PASSWORD)) + { + SAFE_FREE(&text); + text = GetWindowTextUtf(hwndEdit); + EscapesToBinary(text); + } + if ((setting[iEditItem].displayType & LIF_PASSWORD && strcmpnull(text," ")) || + (!(setting[iEditItem].displayType & LIF_PASSWORD) && strcmpnull(text, (char*)settingData[iEditItem].value) && (strlennull(text) + strlennull((char*)settingData[iEditItem].value)))) + { + SAFE_FREE((void**)&settingData[iEditItem].value); + if (strlennull(text)) + settingData[iEditItem].value = (LPARAM)text; + else + { + settingData[iEditItem].value = 0; + SAFE_FREE(&text); + } + settingData[iEditItem].changed = 1; + } + } + if (settingData[iEditItem].changed) + { + TCHAR tbuf[MAX_PATH]; + + GetWindowText(hwndEdit, tbuf, SIZEOF(tbuf)); + ListView_SetItemText(hwndList, iEditItem, 1, tbuf); + + EnableDlgItem(hwndDlg, IDC_SAVE, TRUE); + } + } + ListView_RedrawItems(hwndList, iEditItem, iEditItem); + iEditItem = -1; + dataStringEdit = NULL; + DestroyWindow(hwndEdit); + hwndEdit = NULL; + if (hwndExpandButton) DestroyWindow(hwndExpandButton); + hwndExpandButton = NULL; + if (hwndUpDown) DestroyWindow(hwndUpDown); + hwndUpDown = NULL; +} + + + +int IsStringEditWindow(HWND hwnd) +{ + if (hwnd == hwndEdit) return 1; + if (hwnd == hwndExpandButton) return 1; + if (hwnd == hwndUpDown) return 1; + return 0; +} -- cgit v1.2.3