From 9242a80a84fa5c96dbadec9594177875aeeec1ac Mon Sep 17 00:00:00 2001 From: Kirill Volinsky Date: Tue, 10 Jul 2012 18:37:21 +0000 Subject: only added MyDetails and Skins. not adopted yet git-svn-id: http://svn.miranda-ng.org/main/trunk@892 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- plugins/Skins/options.cpp | 487 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 487 insertions(+) create mode 100644 plugins/Skins/options.cpp (limited to 'plugins/Skins/options.cpp') diff --git a/plugins/Skins/options.cpp b/plugins/Skins/options.cpp new file mode 100644 index 0000000000..086b7cb9eb --- /dev/null +++ b/plugins/Skins/options.cpp @@ -0,0 +1,487 @@ +/* +Copyright (C) 2008 Ricardo Pescuma Domenecci + +This is free software; you can redistribute it and/or +modify it under the terms of the GNU Library General Public +License as published by the Free Software Foundation; either +version 2 of the License, or (at your option) any later version. + +This 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 +Library General Public License for more details. + +You should have received a copy of the GNU Library General Public +License along with this file; see the file license.txt. If +not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. +*/ + + +#include "commons.h" + +#include "options.h" + + + +// Prototypes ///////////////////////////////////////////////////////////////////////////////////// + +HANDLE hOptHook = NULL; + +Options opts; + + +static BOOL CALLBACK SkinOptDlgProc(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam); + + +// Functions ////////////////////////////////////////////////////////////////////////////////////// + + +int InitOptionsCallback(WPARAM wParam,LPARAM lParam) +{ + OPTIONSDIALOGPAGE odp; + ZeroMemory(&odp, sizeof(odp)); + odp.cbSize = sizeof(odp); + odp.position = 0; + odp.hInstance = hInst; + odp.pszGroup = "Skins"; + odp.pszTab = "Skin"; + odp.pfnDlgProc = SkinOptDlgProc; + odp.pszTemplate = MAKEINTRESOURCEA(IDD_SKIN_OPT); + odp.flags = ODPF_BOLDGROUPS; + + for(unsigned int i = 0; i < dlgs.size(); i++) + { + MirandaSkinnedDialog * dlg = dlgs[i]; + odp.pszTitle = (char *) dlg->getDescription(); // Yeah, yeah, I know... + odp.dwInitParam = (LPARAM) dlg; + CallService(MS_OPT_ADDPAGE, wParam, (LPARAM)&odp); + } + + return 0; +} + + +void InitOptions() +{ + LoadOptions(); + + hOptHook = HookEvent(ME_OPT_INITIALISE, InitOptionsCallback); +} + + +void DeInitOptions() +{ + UnhookEvent(hOptHook); +} + + +void LoadOptions() +{ +} + +static void GetTextMetric(HFONT hFont, TEXTMETRIC *tm) +{ + HDC hdc = GetDC(NULL); + HFONT hOldFont = (HFONT) SelectObject(hdc, hFont); + GetTextMetrics(hdc, tm); + SelectObject(hdc, hOldFont); + ReleaseDC(NULL, hdc); +} + + +static BOOL ScreenToClient(HWND hWnd, LPRECT lpRect) +{ + BOOL ret; + + POINT pt; + + pt.x = lpRect->left; + pt.y = lpRect->top; + + ret = ScreenToClient(hWnd, &pt); + + if (!ret) return ret; + + lpRect->left = pt.x; + lpRect->top = pt.y; + + + pt.x = lpRect->right; + pt.y = lpRect->bottom; + + ret = ScreenToClient(hWnd, &pt); + + lpRect->right = pt.x; + lpRect->bottom = pt.y; + + return ret; +} + + +#define V_SPACE 5 +#define H_INITIAL_SPACE 10 +#define MAX_TEXT_SIZE 128 + +static BOOL CALLBACK SkinOptDlgProc(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam) +{ + switch (msg) + { + case WM_INITDIALOG: + { + MirandaSkinnedDialog * dlg = (MirandaSkinnedDialog *) lParam; + _ASSERT(dlg != NULL); + SetWindowLong(hwndDlg, GWL_USERDATA, (LONG) NULL); + + std::vector skins; + getAvaiableSkins(skins, dlg); + for(unsigned int i = 0; i < skins.size(); i++) + { + std::tstring &sk = skins[i]; + SendDlgItemMessage(hwndDlg, IDC_SKIN, CB_ADDSTRING, 0, (LONG) skins[i].c_str()); + } + SendDlgItemMessage(hwndDlg, IDC_SKIN, CB_SELECTSTRING, (WPARAM)-1, (LPARAM)dlg->getSkinName()); + + HWND skinOptsLabel = GetDlgItem(hwndDlg, IDC_SKIN_OPTS_L); + + SkinOptions *opts = dlg->getOpts(); + if (opts == NULL) + { + ShowWindow(skinOptsLabel, SW_HIDE); + ShowScrollBar(hwndDlg, SB_VERT, FALSE); + } + else + { + HWND skinLabel = GetDlgItem(hwndDlg, IDC_SKIN_L); + HWND skinCombo = GetDlgItem(hwndDlg, IDC_SKIN); + + RECT labelRc = {0}; + GetWindowRect(skinLabel, &labelRc); + ScreenToClient(hwndDlg, &labelRc); + labelRc.left += H_INITIAL_SPACE; + + RECT valueRc = {0}; + GetWindowRect(skinCombo, &valueRc); + ScreenToClient(hwndDlg, &valueRc); + + RECT lineRc = {0}; + GetWindowRect(skinOptsLabel, &lineRc); + ScreenToClient(hwndDlg, &lineRc); + + HFONT hFont = (HFONT) SendMessage(hwndDlg, WM_GETFONT, 0, 0); + TEXTMETRIC font; + GetTextMetric(hFont, &font); + + int lineHeight = max(font.tmHeight, 16) + 4; + int y = lineRc.bottom + V_SPACE; + int id = IDC_SKIN_OPTS_L + 1; + + for (unsigned int i = 0; i < opts->getNumOptions(); i++) + { + SkinOption *opt = opts->getOption(i); + + switch(opt->getType()) + { + case CHECKBOX: + { + HWND chk = CreateWindow(_T("BUTTON"), opt->getDescription(), + WS_CHILD | WS_VISIBLE | WS_TABSTOP | BS_CHECKBOX | BS_AUTOCHECKBOX, + labelRc.left, y, + lineRc.right - labelRc.left, + lineHeight, hwndDlg, (HMENU) id, hInst, NULL); + SendMessage(chk, BM_SETCHECK, opt->getValueCheckbox() ? BST_CHECKED : BST_UNCHECKED, 0); + SendMessage(chk, WM_SETFONT, (WPARAM) hFont, FALSE); + + break; + } + case NUMBER: + { + std::tstring tmp = opt->getDescription(); + tmp += _T(":"); + HWND lbl = CreateWindow(_T("STATIC"), tmp.c_str(), + WS_CHILD | WS_VISIBLE, + labelRc.left, y + (lineHeight - font.tmHeight) / 2, + labelRc.right - labelRc.left, font.tmHeight, + hwndDlg, (HMENU) id + 2, hInst, NULL); + SendMessage(lbl, WM_SETFONT, (WPARAM) hFont, FALSE); + + HWND edit = CreateWindowEx(WS_EX_CLIENTEDGE, _T("EDIT"), _T(""), + WS_CHILD | WS_VISIBLE | WS_TABSTOP | ES_LEFT | ES_AUTOHSCROLL | ES_NUMBER, + valueRc.left, y, + (valueRc.right - valueRc.left) / 2, lineHeight, + hwndDlg, (HMENU) id, hInst, NULL); + SendMessage(edit, WM_SETFONT, (WPARAM) hFont, FALSE); + SendMessage(edit, EM_LIMITTEXT, 10, 0); + + HWND spin = CreateWindow(UPDOWN_CLASS, NULL, + WS_CHILD | WS_VISIBLE | UDS_SETBUDDYINT | UDS_ALIGNRIGHT | UDS_ARROWKEYS | UDS_NOTHOUSANDS | UDS_HOTTRACK, + valueRc.left, y, + 1, 1, + hwndDlg, (HMENU) (id + 1), hInst, NULL); + SendMessage(spin, WM_SETFONT, (WPARAM) hFont, FALSE); + SendMessage(spin, UDM_SETBUDDY, (WPARAM) edit, 0); + SendMessage(spin, UDM_SETRANGE, 0, MAKELONG(min(0x7fff, opt->getMax()), max(-0x7fff, min(0x7fff, opt->getMin())))); + SendMessage(spin, UDM_SETPOS, 0, MAKELONG(opt->getValueNumber(), 0)); + + break; + } + case TEXT: + { + std::tstring tmp = opt->getDescription(); + tmp += _T(":"); + HWND lbl = CreateWindow(_T("STATIC"), tmp.c_str(), + WS_CHILD | WS_VISIBLE, + labelRc.left, y + (lineHeight - font.tmHeight) / 2, + labelRc.right - labelRc.left, font.tmHeight, + hwndDlg, (HMENU) id + 1, hInst, NULL); + SendMessage(lbl, WM_SETFONT, (WPARAM) hFont, FALSE); + + HWND edit = CreateWindowEx(WS_EX_CLIENTEDGE, _T("EDIT"), _T(""), + WS_CHILD | WS_VISIBLE | WS_TABSTOP | ES_LEFT | ES_AUTOHSCROLL, + valueRc.left, y, + lineRc.right - valueRc.left, lineHeight, + hwndDlg, (HMENU) id, hInst, NULL); + SendMessage(edit, WM_SETFONT, (WPARAM) hFont, FALSE); + SendMessage(edit, EM_LIMITTEXT, MAX_TEXT_SIZE, 0); + + SetWindowText(edit, opt->getValueText()); + + break; + } + } + + id += 3; + y += lineHeight + V_SPACE; + } + + RECT rc = {0}; + GetClientRect(hwndDlg, &rc); + int avaiable = rc.bottom - rc.top; + int total = y - V_SPACE; + int current = 0; + + SCROLLINFO si; + si.cbSize = sizeof(si); + si.fMask = SIF_RANGE | SIF_PAGE | SIF_POS; + si.nMin = 0; + si.nMax = total; + si.nPage = avaiable; + si.nPos = current; + SetScrollInfo(hwndDlg, SB_VERT, &si, TRUE); + } + + TranslateDialogDefault(hwndDlg); + + SetWindowLong(hwndDlg, GWL_USERDATA, (LONG) dlg); + + break; + } + + case WM_VSCROLL: + { + if (lParam != 0) + break; + + SCROLLINFO si = {0}; + si.cbSize = sizeof(si); + si.fMask = SIF_RANGE | SIF_PAGE | SIF_POS; + GetScrollInfo(hwndDlg, SB_VERT, &si); + + int total = si.nMax; + int avaiable = si.nPage; + int current = si.nPos; + + HFONT hFont = (HFONT) SendMessage(hwndDlg, WM_GETFONT, 0, 0); + TEXTMETRIC font; + GetTextMetric(hFont, &font); + int lineHeight = max(font.tmHeight, 16) + 4; + + int yDelta; // yDelta = new_pos - current_pos + int yNewPos; // new position + + switch (LOWORD(wParam)) + { + case SB_PAGEUP: + yNewPos = current - avaiable / 2; + break; + case SB_PAGEDOWN: + yNewPos = current + avaiable / 2; + break; + case SB_LINEUP: + yNewPos = current - lineHeight; + break; + case SB_LINEDOWN: + yNewPos = current + lineHeight; + break; + case SB_THUMBPOSITION: + yNewPos = HIWORD(wParam); + break; + case SB_THUMBTRACK: + yNewPos = HIWORD(wParam); + break; + default: + yNewPos = current; + } + + yNewPos = min(total - avaiable, max(0, yNewPos)); + + if (yNewPos == current) + break; + + yDelta = yNewPos - current; + current = yNewPos; + + // Scroll the window. (The system repaints most of the + // client area when ScrollWindowEx is called; however, it is + // necessary to call UpdateWindow in order to repaint the + // rectangle of pixels that were invalidated.) + + ScrollWindowEx(hwndDlg, 0, -yDelta, (CONST RECT *) NULL, + (CONST RECT *) NULL, (HRGN) NULL, (LPRECT) NULL, + /* SW_ERASE | SW_INVALIDATE | */ SW_SCROLLCHILDREN); + UpdateWindow(hwndDlg); + InvalidateRect(hwndDlg, NULL, TRUE); + + // Reset the scroll bar. + + si.fMask = SIF_POS; + si.nPos = current; + SetScrollInfo(hwndDlg, SB_VERT, &si, TRUE); + + break; + } + + case WM_COMMAND: + { + MirandaSkinnedDialog * dlg = (MirandaSkinnedDialog *) GetWindowLong(hwndDlg, GWL_USERDATA); + if (dlg == NULL) + break; + + SkinOptions *opts = dlg->getOpts(); + + if (LOWORD(wParam) == IDC_SKIN) + { + if (HIWORD(wParam) == CBN_SELCHANGE && (HWND)lParam == GetFocus()) + { + SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0); + + // Disable all options + if (opts != NULL) + { + int id = IDC_SKIN_OPTS_L + 1; + for (unsigned int i = 0; i < opts->getNumOptions(); i++) + { + EnableWindow(GetDlgItem(hwndDlg, id), FALSE); + EnableWindow(GetDlgItem(hwndDlg, id+1), FALSE); + EnableWindow(GetDlgItem(hwndDlg, id+2), FALSE); + id += 3; + } + } + } + break; + } + + if (opts == NULL) + break; + + bool changed = false; + int id = IDC_SKIN_OPTS_L + 1; + for (unsigned int i = 0; i < opts->getNumOptions() && !changed; i++) + { + SkinOption *opt = opts->getOption(i); + + if (LOWORD(wParam) == id) + { + switch(opt->getType()) + { + case CHECKBOX: + { + changed = true; + break; + } + case NUMBER: + case TEXT: + { + // Don't make apply enabled during buddy set + if (HIWORD(wParam) == EN_CHANGE && (HWND)lParam == GetFocus()) + changed = true; + break; + } + } + } + + id += 3; + } + + if (changed) + SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0); + + break; + } + case WM_NOTIFY: + { + LPNMHDR lpnmhdr = (LPNMHDR) lParam; + + if (lpnmhdr->idFrom == 0 && lpnmhdr->code == PSN_APPLY) + { + MirandaSkinnedDialog * dlg = (MirandaSkinnedDialog *) GetWindowLong(hwndDlg, GWL_USERDATA); + if (dlg == NULL) + break; + + bool changedSkin = false; + + // TODO Correctly handle changing skins + int pos = SendDlgItemMessage(hwndDlg, IDC_SKIN, CB_GETCURSEL, 0, 0); + if (pos != CB_ERR) + { + TCHAR tmp[1024]; + GetWindowText(GetDlgItem(hwndDlg, IDC_SKIN), tmp, MAX_REGS(tmp)); + + changedSkin = (lstrcmp(dlg->getSkinName(), tmp) != 0); + + dlg->setSkinName(tmp); + } + + SkinOptions *opts = dlg->getOpts(); + if (opts != NULL && !changedSkin) + { + int id = IDC_SKIN_OPTS_L + 1; + for (unsigned int i = 0; i < opts->getNumOptions(); i++) + { + SkinOption *opt = opts->getOption(i); + + switch(opt->getType()) + { + case CHECKBOX: + { + opt->setValueCheckbox(IsDlgButtonChecked(hwndDlg, id) != 0); + break; + } + case NUMBER: + { + opt->setValueNumber(SendDlgItemMessage(hwndDlg, id + 1, UDM_GETPOS, 0, 0)); + break; + } + case TEXT: + { + TCHAR tmp[MAX_TEXT_SIZE]; + GetDlgItemText(hwndDlg, id, tmp, MAX_TEXT_SIZE); + opt->setValueText(tmp); + break; + } + } + + id += 3; + } + + dlg->storeToDB(opts); + } + + return TRUE; + } + break; + } + } + + return 0; +} -- cgit v1.2.3