diff options
Diffstat (limited to 'plugins/TopToolBar/src')
-rw-r--r-- | plugins/TopToolBar/src/BkgrCfg.h | 18 | ||||
-rw-r--r-- | plugins/TopToolBar/src/InternalButtons.cpp | 121 | ||||
-rw-r--r-- | plugins/TopToolBar/src/common.h | 157 | ||||
-rw-r--r-- | plugins/TopToolBar/src/main.cpp | 51 | ||||
-rw-r--r-- | plugins/TopToolBar/src/resource.h | 66 | ||||
-rw-r--r-- | plugins/TopToolBar/src/toolbar.cpp | 707 | ||||
-rw-r--r-- | plugins/TopToolBar/src/toolbarwnd.cpp | 330 | ||||
-rw-r--r-- | plugins/TopToolBar/src/topbutton.cpp | 178 | ||||
-rw-r--r-- | plugins/TopToolBar/src/ttbopt.cpp | 559 | ||||
-rw-r--r-- | plugins/TopToolBar/src/version.h | 46 |
10 files changed, 2233 insertions, 0 deletions
diff --git a/plugins/TopToolBar/src/BkgrCfg.h b/plugins/TopToolBar/src/BkgrCfg.h new file mode 100644 index 0000000000..4533267fcb --- /dev/null +++ b/plugins/TopToolBar/src/BkgrCfg.h @@ -0,0 +1,18 @@ +//
+// Register of plugin's user
+//
+// wParam = (WPARAM)szSetting - string that describes a user
+// format: Category/ModuleName,
+// eg: "Contact list background/CLUI",
+// "Status bar background/StatusBar"
+// lParam = (LPARAM)dwFlags
+//
+#define MS_BACKGROUNDCONFIG_REGISTER "BkgrCfg/Register"
+
+//
+// Notification about changed background
+// wParam = ModuleName
+// lParam = 0
+#define ME_BACKGROUNDCONFIG_CHANGED "BkgrCfg/Changed"
+
+#define CLBF_TILEVTOROWHEIGHT 0x0100
diff --git a/plugins/TopToolBar/src/InternalButtons.cpp b/plugins/TopToolBar/src/InternalButtons.cpp new file mode 100644 index 0000000000..7fcdc1cef8 --- /dev/null +++ b/plugins/TopToolBar/src/InternalButtons.cpp @@ -0,0 +1,121 @@ +
+#include "common.h"
+
+#define TTBI_GROUPSHOWHIDE "TTBInternal/GroupShowHide"
+#define TTBI_SOUNDSONOFF "TTBInternal/SoundsOnOFF"
+#define TTBI_MAINMENUBUTT "TTBInternal/MainMenuBUTT"
+
+extern HINSTANCE hInst;
+
+static HWND hwndContactTree;
+
+struct
+{
+ char *name, *pszService;
+ int iconidUp, iconidDn;
+ char *tooltipUp, *tooltipDn;
+ HANDLE hButton;
+}
+static stdButtons[] =
+{
+ { "Show only Online Users", MS_CLIST_SETHIDEOFFLINE, IDI_SHOWONLINEUP, IDI_SHOWONLINEDN, "Hide Offline Users", "Show All Users" },
+ { "Groups On/Off", TTBI_GROUPSHOWHIDE, IDI_GROUPSUP, IDI_GROUPSDN, "Hide Groups", "Show Groups" },
+ { "Sounds Enable/Disable", TTBI_SOUNDSONOFF, IDI_SOUNDUP, IDI_SOUNDDN, "Disable Sounds", "Enable Sounds" },
+
+ { "Show Options Page", "Options/OptionsCommand", IDI_OPTIONSUP, 0, "Show Options" },
+ { "Minimize Button", MS_CLIST_SHOWHIDE, IDI_MINIMIZEUP, 0, NULL },
+ { "Find/Add Contacts", MS_FINDADD_FINDADD, IDI_FINDADDUP, 0, NULL },
+ { "Show Main Menu", TTBI_MAINMENUBUTT, IDI_MIRANDAUP, 0, "Show Main Menu" }
+};
+
+///////////////////////////////////////////////////////////////////////////////
+
+int OnSettingChanging(WPARAM wParam, LPARAM lParam)
+{
+ DBCONTACTWRITESETTING *dbcws = (DBCONTACTWRITESETTING *)lParam;
+ if (wParam != 0 || dbcws == NULL)
+ return 0;
+
+ if ( !strcmp(dbcws->szModule, "CList")) {
+ if ( !strcmp(dbcws->szSetting, "HideOffline"))
+ CallService(MS_TTB_SETBUTTONSTATE, (WPARAM)stdButtons[0].hButton, (dbcws->value.bVal) ? TTBST_PUSHED : TTBST_RELEASED);
+
+ else if (!strcmp(dbcws->szSetting, "UseGroups"))
+ CallService(MS_TTB_SETBUTTONSTATE, (WPARAM)stdButtons[1].hButton, (dbcws->value.bVal) ? TTBST_PUSHED : TTBST_RELEASED);
+ }
+
+ else if (!strcmp(dbcws->szModule, "Skin")) {
+ if (!strcmp(dbcws->szSetting, "UseSound"))
+ CallService(MS_TTB_SETBUTTONSTATE, (WPARAM)stdButtons[2].hButton, (dbcws->value.bVal) ? TTBST_RELEASED : TTBST_PUSHED);
+ }
+
+ return 0;
+}
+
+INT_PTR TTBInternalMainMenuButt(WPARAM wParam, LPARAM lParam)
+{
+ HMENU hMenu = (HMENU)CallService(MS_CLIST_MENUGETMAIN, 0, 0);
+
+ POINT pt;
+ GetCursorPos(&pt);
+ TrackPopupMenu(hMenu, TPM_TOPALIGN|TPM_LEFTALIGN|TPM_RIGHTBUTTON, pt.x, pt.y, 0, (HWND)CallService(MS_CLUI_GETHWND, 0, 0), NULL);
+ return 0;
+}
+
+INT_PTR TTBInternalGroupShowHide(WPARAM wParam, LPARAM lParam)
+{
+ int newVal = !(GetWindowLongPtr(hwndContactTree, GWL_STYLE)&CLS_USEGROUPS);
+ db_set_b(NULL, "CList", "UseGroups", (BYTE)newVal);
+ SendMessage(hwndContactTree, CLM_SETUSEGROUPS, newVal, 0);
+ return 0;
+}
+
+INT_PTR TTBInternalSoundsOnOff(WPARAM wParam, LPARAM lParam)
+{
+ int newVal = !(db_get_b(NULL, "Skin", "UseSound", 1));
+ db_set_b(NULL, "Skin", "UseSound", (BYTE)newVal);
+ return 0;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+
+int InitInternalButtons(WPARAM, LPARAM)
+{
+ hwndContactTree = (HWND)CallService(MS_CLUI_GETHWNDTREE, 0, 0);
+
+ CreateServiceFunction(TTBI_GROUPSHOWHIDE, TTBInternalGroupShowHide);
+ CreateServiceFunction(TTBI_SOUNDSONOFF, TTBInternalSoundsOnOff);
+ CreateServiceFunction(TTBI_MAINMENUBUTT, TTBInternalMainMenuButt);
+
+ TTBButton ttb = { 0 };
+ ttb.cbSize = sizeof(ttb);
+
+ for (int i=0; i < SIZEOF(stdButtons); i++) {
+ ttb.name = stdButtons[i].name;
+ ttb.pszService = stdButtons[i].pszService;
+ ttb.dwFlags = TTBBF_VISIBLE | TTBBF_INTERNAL;
+ if ((ttb.pszTooltipDn = stdButtons[i].tooltipDn) != NULL)
+ ttb.dwFlags |= TTBBF_SHOWTOOLTIP;
+ ttb.pszTooltipUp = stdButtons[i].tooltipUp;
+ ttb.hIconUp = (HICON)LoadImage(hInst, MAKEINTRESOURCE(stdButtons[i].iconidUp), IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR);
+ if (stdButtons[i].iconidDn) {
+ ttb.dwFlags |= TTBBF_ASPUSHBUTTON;
+ ttb.hIconDn = (HICON)LoadImage(hInst, MAKEINTRESOURCE(stdButtons[i].iconidDn), IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR);
+ }
+ else ttb.hIconDn = NULL;
+
+ stdButtons[i].hButton = (HANDLE)TTBAddButton((WPARAM)&ttb, 0);
+ }
+
+ CallService(MS_TTB_SETBUTTONSTATE, (WPARAM)stdButtons[0].hButton,
+ db_get_b(NULL, "CList", "HideOffline", 0) ? TTBST_PUSHED : TTBST_RELEASED);
+
+ CallService(MS_TTB_SETBUTTONSTATE, (WPARAM)stdButtons[1].hButton,
+ db_get_b(NULL, "CList", "UseGroups", 1) ? TTBST_PUSHED : TTBST_RELEASED);
+
+ CallService(MS_TTB_SETBUTTONSTATE, (WPARAM)stdButtons[2].hButton,
+ db_get_b(NULL, "Skin", "UseSound", 1) ? TTBST_RELEASED : TTBST_PUSHED);
+
+ HookEvent(ME_DB_CONTACT_SETTINGCHANGED, OnSettingChanging);
+ return 0;
+}
diff --git a/plugins/TopToolBar/src/common.h b/plugins/TopToolBar/src/common.h new file mode 100644 index 0000000000..0840111f2f --- /dev/null +++ b/plugins/TopToolBar/src/common.h @@ -0,0 +1,157 @@ +#ifndef TTB_COMMON_H
+#define TTB_COMMON_H
+
+
+#define _CRT_SECURE_NO_WARNINGS
+
+#include <windows.h>
+#include <commctrl.h>
+#include <time.h>
+#include <stddef.h>
+#include <process.h>
+#include <math.h>
+#include <vsstyle.h>
+
+#include "win2k.h"
+#include "newpluginapi.h"
+#include "m_system.h"
+#include "m_system_cpp.h"
+#include "m_database.h"
+#include "m_clist.h"
+#include "m_skin.h"
+#include "m_utils.h"
+#include "m_cluiframes.h"
+#include "m_clui.h"
+#include "m_clc.h"
+#include "m_findadd.h"
+#include "m_langpack.h"
+#include "m_options.h"
+#include "resource.h"
+#include "m_protocols.h"
+#include "m_protosvc.h"
+#include "m_toptoolbar.h"
+#include "m_button.h"
+#include "m_icolib.h"
+#include "BkgrCfg.h"
+
+#define TTB_BUTTON_CLASS _T("TopToolbarButtonClass")
+
+#define TTB_REPOSBUTTONS (WM_USER+10)
+#define TTB_UPDATEFRAMEVISIBILITY (WM_USER+11)
+
+#define TTBDEFAULT_BKBMPUSE CLB_STRETCH
+#define TTBDEFAULT_BKCOLOUR GetSysColor(COLOR_3DFACE)
+#define TTBDEFAULT_USEBITMAP 0
+#define TTBDEFAULT_SELBKCOLOUR GetSysColor(COLOR_HIGHLIGHT)
+
+#define TTBBF_INTERNAL 0x1000000
+#define TTBBF_OPTIONAL 0x2000000
+
+///////////////////////////////////////////////////////////////////////////////
+// TopButtonInt class
+
+struct TopButtonInt : public MZeroedObject
+{
+ ~TopButtonInt();
+
+ DWORD CheckFlags(DWORD Flags);
+ void CreateWnd(void);
+ void LoadSettings(void);
+ void SaveSettings(int *SepCnt, int *LaunchCnt);
+ void SetBitmap(void);
+
+ __inline bool isSep() const
+ { return (dwFlags & TTBBF_ISSEPARATOR) != 0;
+ }
+
+ __inline bool isVisible() const
+ { return (dwFlags & TTBBF_VISIBLE) != 0;
+ }
+
+ HWND hwnd;
+ int id;
+ BOOL bPushed;
+ int dwFlags;
+ int x, y, arrangedpos;
+ HICON hIconUp, hIconDn;
+ HANDLE hIconHandleUp, hIconHandleDn;
+
+ char *pszService;
+ TCHAR *ptszProgram;
+ char *pszName;
+ TCHAR *ptszTooltip;
+
+ LPARAM lParamUp;
+ WPARAM wParamUp;
+ LPARAM lParamDown;
+ WPARAM wParamDown;
+
+ int hLangpack;
+ TCHAR *ptszTooltipUp, *ptszTooltipDn;
+};
+
+///////////////////////////////////////////////////////////////////////////////
+
+int TTBOptInit(WPARAM wParam, LPARAM lParam);
+//append string
+char __inline *AS(char *str, const char *setting, char *addstr);
+
+TopButtonInt* CreateButton(TTBButton* but);
+
+int LoadBackgroundOptions();
+
+int ArrangeButtons();
+
+#define DEFBUTTWIDTH 20
+#define DEFBUTTHEIGHT 20
+#define DEFBUTTGAP 1
+
+#define SEPWIDTH 3
+
+extern TTBCtrl* g_ctrl;
+
+extern LIST<TopButtonInt> Buttons;
+extern HINSTANCE hInst;
+extern HBITMAP hBmpBackground, hBmpSeparator;
+extern CRITICAL_SECTION csButtonsHook;
+extern pfnCustomProc g_CustomProc;
+extern LPARAM g_CustomProcParam;
+extern HANDLE hTTBModuleLoaded, hTTBInitButtons;
+
+void AddToOptions(TopButtonInt* b);
+void RemoveFromOptions(int id);
+
+//append string
+char *AS(char *str, const char *setting, char *addstr)
+{
+ if (str != NULL) {
+ strcpy(str, setting);
+ strcat(str, addstr);
+ }
+ return str;
+}
+
+#define TTB_LAUNCHSERVICE "TTB/LaunchService"
+
+TopButtonInt* idtopos(int id, int* pPos=NULL);
+
+INT_PTR TTBAddButton(WPARAM, LPARAM);
+INT_PTR TTBRemoveButton(WPARAM, LPARAM);
+
+int InitInternalButtons(WPARAM, LPARAM);
+
+int LoadToolbarModule( void );
+int UnloadToolbarModule( void );
+
+void SetAllBitmaps( void );
+int SaveAllLButs( void );
+int SaveAllButtonsOptions( void );
+
+void InsertSeparator( int i );
+void DeleteSeparator(int i);
+void DeleteLBut(int i);
+void InsertLBut(int i);
+
+int OnModulesLoad(WPARAM, LPARAM);
+
+#endif
\ No newline at end of file diff --git a/plugins/TopToolBar/src/main.cpp b/plugins/TopToolBar/src/main.cpp new file mode 100644 index 0000000000..601de36408 --- /dev/null +++ b/plugins/TopToolBar/src/main.cpp @@ -0,0 +1,51 @@ +
+#include "common.h"
+#include "version.h"
+
+HINSTANCE hInst;
+int hLangpack;
+
+PLUGININFOEX pluginInfo =
+{
+ sizeof(PLUGININFOEX),
+ __PLUGIN_NAME,
+ PLUGIN_MAKE_VERSION(__MAJOR_VERSION, __MINOR_VERSION, __RELEASE_NUM, __BUILD_NUM),
+ __PLUGIN_DESC,
+ __PLUGIN_AUTHOR,
+ __PLUGIN_EMAIL,
+ __PLUGIN_RIGHTS,
+ __PLUGIN_AUTHORWEB,
+ UNICODE_AWARE,
+ {0xf593c752, 0x51d8, 0x4d46, {0xba, 0x27, 0x37, 0x57, 0x79, 0x53, 0xf5, 0x5c}}
+};
+
+extern "C" __declspec(dllexport) PLUGININFOEX* MirandaPluginInfoEx(DWORD mirandaVersion)
+{
+ return &pluginInfo;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+extern "C" int __declspec(dllexport) Load(void)
+{
+ mir_getLP(&pluginInfo);
+
+ LoadToolbarModule();
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+extern "C" int __declspec(dllexport) Unload(void)
+{
+ UnloadToolbarModule();
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
+{
+ hInst = hinstDLL;
+ return TRUE;
+}
diff --git a/plugins/TopToolBar/src/resource.h b/plugins/TopToolBar/src/resource.h new file mode 100644 index 0000000000..498762de51 --- /dev/null +++ b/plugins/TopToolBar/src/resource.h @@ -0,0 +1,66 @@ +//{{NO_DEPENDENCIES}}
+// Microsoft Visual C++ generated include file.
+// Used by main.rc
+//
+#define IDB_SEP 118
+#define IDI_SHOWONLINEUP 125
+#define IDI_SHOWONLINEDN 126
+#define IDI_GROUPSUP 127
+#define IDI_GROUPSDN 128
+#define IDI_SOUNDDN 129
+#define IDI_SOUNDUP 130
+#define IDI_OPTIONSUP 131
+#define IDI_MINIMIZEUP 133
+#define IDI_FINDADDUP 135
+#define IDI_MIRANDAUP 137
+#define IDI_RUN 140
+#define IDD_OPT_TTBBKG 230
+#define IDD_OPT_INTERNALORDER 262
+#define IDD_OPT_BUTORDER 262
+#define IDD_FRAMEPLUG2 265
+#define IDC_BUTTON1 1002
+#define IDC_ADDSEP 1003
+#define IDC_REMOVEBUTTON 1004
+#define IDC_ADDLBUTTON 1005
+#define IDC_DELLBUTTON 1006
+#define IDC_ENAME 1007
+#define IDC_LBUTTONNAME 1008
+#define IDC_EPATH 1009
+#define IDC_AUTOSIZE 1010
+#define IDC_LBUTTONPATH 1011
+#define IDC_LBUTTONSET 1012
+#define IDC_BUTTHEIGHT 1015
+#define IDC_EDIT2 1016
+#define IDC_BUTTWIDTH 1016
+#define IDC_BUTTGAP 1017
+#define IDC_USEFLAT 1018
+#define IDC_AUTORESIZE 1019
+#define IDC_SINGLELINE 1020
+#define IDC_SPIN_HEIGHT 1024
+#define IDC_SPIN_WIDTH 1025
+#define IDC_SPIN_GAP 1026
+#define IDC_BROWSE 1184
+#define IDC_BKGCOLOUR 1269
+#define IDC_FILENAME 1271
+#define IDC_SCROLL 1277
+#define IDC_PROPORTIONAL 1278
+#define IDC_SELCOLOUR 1281
+#define IDC_STRETCHH 1298
+#define IDC_STRETCHV 1299
+#define IDC_TILEH 1300
+#define IDC_TILEV 1301
+#define IDC_BITMAP 1363
+#define IDC_P2ONLINEBUTT 1562
+#define IDC_P2GROUPBUTT 1564
+#define IDC_BUTTONORDERTREE 1591
+
+// Next default values for new objects
+//
+#ifdef APSTUDIO_INVOKED
+#ifndef APSTUDIO_READONLY_SYMBOLS
+#define _APS_NEXT_RESOURCE_VALUE 139
+#define _APS_NEXT_COMMAND_VALUE 40001
+#define _APS_NEXT_CONTROL_VALUE 1025
+#define _APS_NEXT_SYMED_VALUE 101
+#endif
+#endif
diff --git a/plugins/TopToolBar/src/toolbar.cpp b/plugins/TopToolBar/src/toolbar.cpp new file mode 100644 index 0000000000..156b83dbb7 --- /dev/null +++ b/plugins/TopToolBar/src/toolbar.cpp @@ -0,0 +1,707 @@ +
+#include "common.h"
+
+#define OLD_TBBUTTON_SIZE (offsetof(TTBButton, pszTooltipUp))
+
+pfnCustomProc g_CustomProc = NULL;
+LPARAM g_CustomProcParam = 0;
+TTBCtrl *g_ctrl = NULL;
+
+INT_PTR OnEventFire(WPARAM wParam, LPARAM lParam);
+
+HWND hwndContactList = 0;
+
+int nextButtonId = 200;
+
+HANDLE hTTBModuleLoaded, hTTBInitButtons;
+static WNDPROC buttonWndProc;
+
+CRITICAL_SECTION csButtonsHook;
+
+int sortfunc(const TopButtonInt* a, const TopButtonInt* b)
+{
+ return a->arrangedpos - b->arrangedpos;
+}
+
+LIST<TopButtonInt> Buttons(8, sortfunc);
+
+TopButtonInt* idtopos(int id, int* pPos)
+{
+ for ( int i = 0; i < Buttons.getCount(); i++)
+ if (Buttons[i]->id == id) {
+ if (pPos) *pPos = i;
+ return Buttons[i];
+ }
+
+ if (pPos) *pPos = -1;
+ return NULL;
+}
+
+//----- Service buttons -----
+void InsertSBut(int i)
+{
+ TTBButton ttb = { 0 };
+ ttb.cbSize = sizeof(ttb);
+ ttb.hIconDn = (HICON)LoadImage(hInst, MAKEINTRESOURCE(IDI_RUN), IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR);
+ ttb.hIconUp = (HICON)LoadImage(hInst, MAKEINTRESOURCE(IDI_RUN), IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR);
+ ttb.dwFlags = TTBBF_VISIBLE | TTBBF_ISSBUTTON | TTBBF_INTERNAL;
+ ttb.wParamDown = i;
+ TTBAddButton(( WPARAM )&ttb, 0);
+}
+
+void LoadAllSButs()
+{
+ //must be locked
+ int cnt = db_get_b(0, TTB_OPTDIR, "ServiceCnt", 0);
+ if (cnt > 0) {
+ for (int i = 1; i<=cnt; i++)
+ InsertSBut(i);
+ }
+}
+
+//----- Launch buttons -----
+INT_PTR LaunchService(WPARAM wParam, LPARAM lParam)
+{
+ PROCESS_INFORMATION pi;
+ STARTUPINFO si = {0};
+ si.cb = sizeof(si);
+
+ if ( CreateProcess(NULL, Buttons[lParam]->ptszProgram, NULL, NULL, FALSE, 0, NULL, NULL, &si, &pi)) {
+ CloseHandle(pi.hProcess);
+ CloseHandle(pi.hThread);
+ }
+
+ return 0;
+}
+
+void InsertLBut(int i)
+{
+ TTBButton ttb = { 0 };
+ ttb.cbSize = sizeof(ttb);
+ ttb.hIconDn = (HICON)LoadImage(hInst, MAKEINTRESOURCE(IDI_RUN), IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR);
+ ttb.dwFlags = TTBBF_VISIBLE | TTBBF_ISLBUTTON | TTBBF_INTERNAL;
+ ttb.name = LPGEN("Default");
+ ttb.program = _T("Execute Path");
+ ttb.wParamDown = i;
+ TTBAddButton(( WPARAM )&ttb, 0);
+}
+
+void LoadAllLButs()
+{
+ //must be locked
+ int cnt = db_get_b(0, TTB_OPTDIR, "LaunchCnt", 0);
+ for (int i = 0; i < cnt; i++)
+ InsertLBut(i);
+}
+
+//----- Separators -----
+
+void InsertSeparator(int i)
+{
+ TTBButton ttb = { 0 };
+ ttb.cbSize = sizeof(ttb);
+ ttb.dwFlags = TTBBF_VISIBLE | TTBBF_ISSEPARATOR | TTBBF_INTERNAL;
+ ttb.wParamDown = i;
+ TTBAddButton((WPARAM)&ttb, 0);
+}
+
+void LoadAllSeparators()
+{
+ //must be locked
+ int cnt = db_get_b(0, TTB_OPTDIR, "SepCnt", 0);
+ for (int i = 0; i < cnt; i++)
+ InsertSeparator(i);
+}
+
+int SaveAllButtonsOptions()
+{
+ int SeparatorCnt = 0;
+ int LaunchCnt = 0;
+ {
+ mir_cslock lck(csButtonsHook);
+ for (int i = 0; i < Buttons.getCount(); i++)
+ Buttons[i]->SaveSettings(&SeparatorCnt, &LaunchCnt);
+ }
+ db_set_b(0, TTB_OPTDIR, "SepCnt", SeparatorCnt);
+ db_set_b(0, TTB_OPTDIR, "LaunchCnt", LaunchCnt);
+ return 0;
+}
+
+static bool nameexists(const char *name)
+{
+ if (name == NULL)
+ return false;
+
+ for (int i = 0; i < Buttons.getCount(); i++)
+ if ( !lstrcmpA(Buttons[i]->pszName, name))
+ return true;
+
+ return false;
+}
+
+static void Icon2button(TTBButton* but, HANDLE& hIcoLib, HICON& hIcon, bool bIsUp)
+{
+ HANDLE hSrc = bIsUp ? but->hIconHandleUp : but->hIconHandleDn;
+ if (hSrc == NULL) {
+ hIcoLib = NULL, hIcon = NULL;
+ return;
+ }
+
+ hIcoLib = (HANDLE)CallService(MS_SKIN2_ISMANAGEDICON, WPARAM(hSrc), 0);
+ if (!hIcoLib) {
+ char buf[256];
+ mir_snprintf(buf, SIZEOF(buf), "toptoolbar_%s%s", but->name, (bIsUp) ? (but->hIconDn ? "%s_up" : "%s") : "%s_dn");
+ SKINICONDESC sid = {0};
+ sid.cbSize = sizeof(sid);
+ sid.pszSection = "Toolbar";
+ sid.pszName = buf;
+ sid.pszDefaultFile = NULL;
+ sid.pszDescription = but->name;
+ sid.hDefaultIcon = (bIsUp) ? but->hIconUp : but->hIconDn;
+ hIcoLib = Skin_AddIcon(&sid);
+ }
+
+ hIcon = Skin_GetIconByHandle(hIcoLib);
+}
+
+TopButtonInt* CreateButton(TTBButton* but)
+{
+ TopButtonInt* b = new TopButtonInt;
+ b->id = nextButtonId++;
+
+ b->dwFlags = but->dwFlags;
+
+ b->wParamUp = but->wParamUp;
+ b->lParamUp = but->lParamUp;
+ b->wParamDown = but->wParamDown;
+ b->lParamDown = but->lParamDown;
+
+ if ( !(b->dwFlags & TTBBF_ISSEPARATOR)) {
+ b->bPushed = (but->dwFlags & TTBBF_PUSHED) ? TRUE : FALSE;
+
+ if (but->dwFlags & TTBBF_ISLBUTTON) {
+ b->ptszProgram = mir_tstrdup(but->program);
+ b->pszService = mir_strdup(TTB_LAUNCHSERVICE);
+ }
+ else {
+ b->ptszProgram = NULL;
+ b->pszService = mir_strdup(but->pszService);
+ }
+
+ b->pszName = mir_strdup(but->name);
+
+ Icon2button(but, b->hIconHandleUp, b->hIconUp, true);
+ Icon2button(but, b->hIconHandleDn, b->hIconDn, false);
+
+ if (but->cbSize > OLD_TBBUTTON_SIZE) {
+ b->ptszTooltipUp = mir_a2t(but->pszTooltipUp);
+ b->ptszTooltipDn = mir_a2t(but->pszTooltipDn);
+ }
+ }
+ return b;
+}
+
+int ArrangeButtons()
+{
+ mir_cslock lck(csButtonsHook);
+
+ RECT rcClient;
+ GetClientRect(g_ctrl->hWnd, &rcClient);
+ int nBarSize = rcClient.right - rcClient.left;
+ if (nBarSize == 0)
+ return 0;
+
+ int nLineCount = 0;
+ int i, ypos = 1, xpos = g_ctrl->nButtonSpace, nextX = 0, y = 0;
+ int newheight = g_ctrl->nButtonHeight+1, nButtonCount=0;
+
+ for (i=0; i < Buttons.getCount(); i++)
+ if (Buttons[i]->hwnd)
+ nButtonCount++;
+
+ if (nButtonCount == 0)
+ return 0;
+
+ HDWP hdwp = BeginDeferWindowPos(nButtonCount);
+
+ bool bWasButttonBefore;
+ int nUsedWidth, iFirstButtonId = 0, iLastButtonId = 0;
+
+ do
+ {
+ nLineCount++;
+ bWasButttonBefore = false;
+ nUsedWidth = 0;
+
+ for (i=iFirstButtonId; i < Buttons.getCount(); i++) {
+ TopButtonInt *b = Buttons[i];
+ if (b->hwnd == NULL)
+ continue;
+
+ int width = 0;
+ if ( b->isVisible())
+ width = (b->isSep()) ? SEPWIDTH+2 : g_ctrl->nButtonWidth + ((bWasButttonBefore) ? g_ctrl->nButtonSpace : 0);
+ if (nUsedWidth + width > nBarSize)
+ break;
+
+ nUsedWidth += width;
+ iLastButtonId = i+1;
+ bWasButttonBefore = !b->isSep();
+ }
+
+ int nFreeSpace = nBarSize - nUsedWidth;
+
+ for (i=iFirstButtonId; i < iLastButtonId; i++) {
+ TopButtonInt *b = Buttons[i];
+ if (b->hwnd == NULL)
+ continue;
+
+ bool bOldVisible = IsWindowVisible(b->hwnd) != 0;
+ if (bOldVisible != b->isVisible())
+ g_ctrl->bOrderChanged = TRUE;
+
+ if ( b->isVisible()) {
+ hdwp = DeferWindowPos(hdwp, b->hwnd, NULL, nextX, y, 0, 0, SWP_NOSIZE | SWP_NOZORDER | SWP_SHOWWINDOW);
+ if ( b->isSep())
+ nextX += SEPWIDTH+2;
+ else
+ nextX += g_ctrl->nButtonWidth + g_ctrl->nButtonSpace;
+ }
+ else hdwp = DeferWindowPos(hdwp, Buttons[i]->hwnd, NULL, nextX, y, 0, 0, SWP_NOSIZE | SWP_NOZORDER | SWP_HIDEWINDOW);
+ }
+
+ if (iFirstButtonId == iLastButtonId)
+ break;
+
+ iFirstButtonId = iLastButtonId;
+ y += g_ctrl->nButtonHeight + g_ctrl->nButtonSpace;
+ nextX = 0;
+ if (g_ctrl->bSingleLine)
+ break;
+ }
+ while (iFirstButtonId < Buttons.getCount() && y >= 0 && (g_ctrl->bAutoSize || (y + g_ctrl->nButtonHeight <= rcClient.bottom - rcClient.top)));
+
+ if (hdwp)
+ EndDeferWindowPos(hdwp);
+
+ return (g_ctrl->nButtonHeight + g_ctrl->nButtonSpace)*nLineCount - g_ctrl->nButtonSpace;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+// Toolbar services
+
+// wparam = (TTBButton*)lpTTBButton
+// lparam = hLangpack
+INT_PTR TTBAddButton(WPARAM wParam, LPARAM lParam)
+{
+ if (wParam == 0)
+ return -1;
+
+ TTBButton *but = (TTBButton*)wParam;
+ if (but->cbSize != sizeof(TTBButton) && but->cbSize != OLD_TBBUTTON_SIZE)
+ return -1;
+
+ if ( !(but->dwFlags && TTBBF_ISLBUTTON) && nameexists(but->name))
+ return -1;
+
+ TopButtonInt* b = CreateButton(but);
+ b->hLangpack = (int)lParam;
+ b->LoadSettings();
+ b->CreateWnd();
+ if (b->hwnd == NULL) {
+ delete b;
+ return -1;
+ }
+ {
+ mir_cslock lck(csButtonsHook);
+ Buttons.insert(b);
+ }
+
+ g_ctrl->bOrderChanged = TRUE;
+ ArrangeButtons();
+ AddToOptions(b);
+ return b->id;
+}
+
+// wparam = (HANDLE)hTTButton
+// lparam = 0
+INT_PTR TTBRemoveButton(WPARAM wParam, LPARAM lParam)
+{
+ mir_cslock lck(csButtonsHook);
+
+ int idx;
+ TopButtonInt* b = idtopos(wParam, &idx);
+ if (b == NULL)
+ return -1;
+
+ RemoveFromOptions(b->id);
+
+ Buttons.remove(idx);
+ delete b;
+
+ g_ctrl->bOrderChanged = TRUE;
+ ArrangeButtons();
+ return 0;
+}
+
+// wparam = hTTBButton
+// lparam = state
+INT_PTR TTBSetState(WPARAM wParam, LPARAM lParam)
+{
+ mir_cslock lck(csButtonsHook);
+
+ TopButtonInt* b = idtopos(wParam);
+ if (b == NULL)
+ return -1;
+
+ b->bPushed = (lParam & TTBST_PUSHED)?TRUE:FALSE;
+ b->bPushed = (lParam & TTBST_RELEASED)?FALSE:TRUE;
+ b->SetBitmap();
+ return 0;
+}
+
+// wparam = hTTBButton
+// lparam = 0
+//return = state
+INT_PTR TTBGetState(WPARAM wParam, LPARAM lParam)
+{
+ mir_cslock lck(csButtonsHook);
+ TopButtonInt* b = idtopos(wParam);
+ if (b == NULL)
+ return -1;
+
+ int retval = (b->bPushed == TRUE) ? TTBST_PUSHED : TTBST_RELEASED;
+ return retval;
+}
+
+INT_PTR TTBGetOptions(WPARAM wParam, LPARAM lParam)
+{
+ INT_PTR retval;
+
+ mir_cslock lck(csButtonsHook);
+ TopButtonInt* b = idtopos(wParam);
+ if (b == NULL)
+ return -1;
+
+ switch(LOWORD(wParam)) {
+ case TTBO_FLAGS:
+ retval = b->dwFlags & (~TTBBF_PUSHED);
+ if (b->bPushed)
+ retval |= TTBBF_PUSHED;
+ break;
+
+ case TTBO_TIPNAME:
+ retval = (INT_PTR)b->ptszTooltip;
+ break;
+
+ case TTBO_ALLDATA:
+ if (lParam) {
+ lpTTBButton lpTTB = (lpTTBButton)lParam;
+ if (lpTTB->cbSize != sizeof(TTBButton))
+ break;
+
+ lpTTB->dwFlags = b->dwFlags & (~TTBBF_PUSHED);
+ if (b->bPushed)
+ lpTTB->dwFlags |= TTBBF_PUSHED;
+
+ lpTTB->hIconDn = b->hIconDn;
+ lpTTB->hIconUp = b->hIconUp;
+
+ lpTTB->lParamUp = b->lParamUp;
+ lpTTB->wParamUp = b->wParamUp;
+ lpTTB->lParamDown = b->lParamDown;
+ lpTTB->wParamDown = b->wParamDown;
+
+ if (b->dwFlags & TTBBF_ISLBUTTON)
+ replaceStrT(lpTTB->program, b->ptszProgram);
+ else
+ replaceStr(lpTTB->pszService, b->pszService);
+
+ retval = ( INT_PTR )lpTTB;
+ }
+ break;
+
+ default:
+ retval = -1;
+ break;
+ }
+
+ return retval;
+}
+
+INT_PTR TTBSetOptions(WPARAM wParam, LPARAM lParam)
+{
+ int retval;
+
+ mir_cslock lck(csButtonsHook);
+ TopButtonInt* b = idtopos(HIWORD(wParam));
+ if (b == NULL)
+ return -1;
+
+ switch(LOWORD(wParam)) {
+ case TTBO_FLAGS:
+ if (b->dwFlags == lParam)
+ break;
+
+ retval = b->CheckFlags(lParam);
+
+ if (retval & TTBBF_PUSHED)
+ b->SetBitmap();
+ if (retval & TTBBF_VISIBLE) {
+ ArrangeButtons();
+ b->SaveSettings(0,0);
+ }
+
+ retval = 1;
+ break;
+
+ case TTBO_TIPNAME:
+ if (lParam == 0)
+ break;
+
+ replaceStrT(b->ptszTooltip, TranslateTS( _A2T((LPCSTR)lParam)));
+ SendMessage(b->hwnd,BUTTONADDTOOLTIP,(WPARAM)b->ptszTooltip,BATF_UNICODE);
+ retval = 1;
+ break;
+
+ case TTBO_ALLDATA:
+ if (lParam) {
+ lpTTBButton lpTTB = (lpTTBButton)lParam;
+ if (lpTTB->cbSize != sizeof(TTBButton))
+ break;
+
+ retval = b->CheckFlags(lpTTB->dwFlags);
+
+ int changed = 0;
+ if (b->hIconUp != lpTTB->hIconUp) {
+ b->hIconUp = lpTTB->hIconUp;
+ changed = 1;
+ }
+ if (b->hIconDn != lpTTB->hIconDn) {
+ b->hIconDn = lpTTB->hIconDn;
+ changed = 1;
+ }
+ if (changed)
+ b->SetBitmap();
+
+ if (retval & TTBBF_VISIBLE) {
+ ArrangeButtons();
+ b->SaveSettings(0,0);
+ }
+
+ if (b->dwFlags & TTBBF_ISLBUTTON)
+ replaceStrT(b->ptszProgram, lpTTB->program);
+ else
+ replaceStr(b->pszService, lpTTB->pszService);
+
+ b->lParamUp = lpTTB->lParamUp;
+ b->wParamUp = lpTTB->wParamUp;
+ b->lParamDown = lpTTB->lParamDown;
+ b->wParamDown = lpTTB->wParamDown;
+
+ retval = 1;
+ }
+ break;
+
+ default:
+ retval = -1;
+ break;
+ }
+
+ return retval;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+// Reload all icons from their icolib handles
+
+int OnIconChange(WPARAM wParam, LPARAM lParam)
+{
+ mir_cslock lck(csButtonsHook);
+ for (int i = 0; i < Buttons.getCount(); i++) {
+ TopButtonInt* b = Buttons[i];
+ if ( !b->hIconHandleUp && !b->hIconHandleDn)
+ continue;
+
+ if (b->hIconHandleUp) {
+ Skin_ReleaseIcon(b->hIconUp);
+ b->hIconUp = Skin_GetIconByHandle(b->hIconHandleUp);
+ }
+ if (b->hIconHandleDn) {
+ Skin_ReleaseIcon(b->hIconDn);
+ b->hIconDn = Skin_GetIconByHandle(b->hIconHandleDn);
+ }
+ DestroyWindow(b->hwnd);
+ b->CreateWnd();
+ }
+
+ if (g_ctrl->hWnd) {
+ g_ctrl->bOrderChanged = true;
+ PostMessage(g_ctrl->hWnd, TTB_UPDATEFRAMEVISIBILITY, TRUE, 0);
+ }
+
+ return 0;
+}
+
+static int OnBGChange(WPARAM wParam, LPARAM lParam)
+{
+ LoadBackgroundOptions();
+ return 0;
+}
+
+static INT_PTR TTBSetCustomProc(WPARAM wParam, LPARAM lParam)
+{
+ g_CustomProc = (pfnCustomProc)wParam;
+ g_CustomProcParam = lParam;
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+// Adds buttons of plugins being loaded. lParam = HINSTANCE
+
+int OnPluginLoad(WPARAM wParam, LPARAM lParam)
+{
+ CallPluginEventHook((HINSTANCE)lParam, hTTBModuleLoaded, 0, 0);
+ if (g_ctrl->hWnd && g_ctrl->bOrderChanged)
+ PostMessage(g_ctrl->hWnd, TTB_UPDATEFRAMEVISIBILITY, TRUE, 0);
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+// Removes buttons of plugins being unloaded. lParam = HINSTANCE
+
+int OnPluginUnload(WPARAM wParam, LPARAM lParam)
+{
+ int hLangpack = CallService(MS_LANGPACK_LOOKUPHANDLE, 0, lParam);
+ if (hLangpack) {
+ bool bNeedUpdate = false;
+ mir_cslock lck(csButtonsHook);
+
+ for (int i=Buttons.getCount()-1; i >= 0; i--)
+ if (Buttons[i]->hLangpack == hLangpack) {
+ TTBRemoveButton(Buttons[i]->id, 0);
+ bNeedUpdate = true;
+ }
+
+ if (bNeedUpdate) {
+ ArrangeButtons();
+ if (g_ctrl->hWnd)
+ PostMessage(g_ctrl->hWnd, TTB_UPDATEFRAMEVISIBILITY, TRUE, 0);
+ }
+ }
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+int OnModulesLoad(WPARAM wParam, LPARAM lParam)
+{
+ LoadAllSeparators();
+ LoadAllLButs();
+
+ ArrangeButtons();
+
+ HANDLE hEvent = CreateEvent(NULL, TRUE, TRUE, NULL);//anonymous event
+ if (hEvent != 0)
+ CallService(MS_SYSTEM_WAITONHANDLE, (WPARAM)hEvent, (LPARAM)"TTB_ONSTARTUPFIRE");
+
+ if ( HookEvent(ME_BACKGROUNDCONFIG_CHANGED, OnBGChange)) {
+ char buf[256];
+ sprintf(buf, "TopToolBar Background/%s", TTB_OPTDIR);
+ CallService(MS_BACKGROUNDCONFIG_REGISTER, (WPARAM)buf, 0);
+ }
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+static LRESULT CALLBACK TTBButtonWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ LRESULT lResult = buttonWndProc(hwnd, msg, wParam, lParam);
+
+ if (msg == WM_NCCREATE) {
+ TopButtonInt* p = (TopButtonInt*)((CREATESTRUCT*)lParam)->lpCreateParams;
+ if (g_CustomProc)
+ g_CustomProc((HANDLE)p->id, hwnd, g_CustomProcParam);
+ }
+
+ return lResult;
+}
+
+int LoadToolbarModule()
+{
+ if ( !ServiceExists(MS_CLIST_FRAMES_ADDFRAME)) {
+ if ( !db_get_b(NULL, TTB_OPTDIR, "WarningDone", 0))
+ MessageBox(0, TranslateT("Frames Services not found - plugin disabled.You need MultiWindow plugin."), _T("TopToolBar"), 0);
+ db_set_b(NULL, TTB_OPTDIR, "WarningDone", 1);
+ return 1;
+ }
+
+ g_ctrl = (TTBCtrl*)mir_calloc( sizeof(TTBCtrl));
+ g_ctrl->nButtonHeight = db_get_dw(0, TTB_OPTDIR, "BUTTHEIGHT", DEFBUTTHEIGHT);
+ g_ctrl->nButtonWidth = db_get_dw(0, TTB_OPTDIR, "BUTTWIDTH", DEFBUTTWIDTH);
+ g_ctrl->nButtonSpace = db_get_dw(0, TTB_OPTDIR, "BUTTGAP", DEFBUTTGAP);
+ g_ctrl->nLastHeight = db_get_dw(0, TTB_OPTDIR, "LastHeight", DEFBUTTHEIGHT);
+
+ g_ctrl->bFlatButtons = db_get_b(0, TTB_OPTDIR, "UseFlatButton", true);
+ g_ctrl->bSingleLine = db_get_b(0, TTB_OPTDIR, "SingleLine", false);
+ g_ctrl->bAutoSize = db_get_b(0, TTB_OPTDIR, "AutoSize", true);
+
+ db_unset(NULL, TTB_OPTDIR, "WarningDone");
+
+ InitializeCriticalSection(&csButtonsHook);
+ hBmpSeparator = LoadBitmap(hInst, MAKEINTRESOURCE(IDB_SEP));
+
+ HookEvent(ME_SYSTEM_MODULELOAD, OnPluginLoad);
+ HookEvent(ME_SYSTEM_MODULEUNLOAD, OnPluginUnload);
+ HookEvent(ME_SYSTEM_MODULESLOADED, OnModulesLoad);
+ HookEvent(ME_SKIN2_ICONSCHANGED, OnIconChange);
+ HookEvent(ME_OPT_INITIALISE, TTBOptInit);
+
+ hTTBModuleLoaded = CreateHookableEvent(ME_TTB_MODULELOADED);
+ hTTBInitButtons = CreateHookableEvent(ME_TTB_INITBUTTONS);
+ SetHookDefaultForHookableEvent(hTTBInitButtons, InitInternalButtons);
+
+ CreateServiceFunction("TopToolBar/AddButton", TTBAddButton);
+ CreateServiceFunction(MS_TTB_REMOVEBUTTON, TTBRemoveButton);
+
+ CreateServiceFunction(MS_TTB_SETBUTTONSTATE, TTBSetState);
+ CreateServiceFunction(MS_TTB_GETBUTTONSTATE, TTBGetState);
+
+ CreateServiceFunction(MS_TTB_GETBUTTONOPTIONS, TTBGetOptions);
+ CreateServiceFunction(MS_TTB_SETBUTTONOPTIONS, TTBSetOptions);
+
+ CreateServiceFunction(TTB_LAUNCHSERVICE, LaunchService);
+
+ CreateServiceFunction("TopToolBar/SetCustomProc", TTBSetCustomProc);
+ CreateServiceFunction("TTB_ONSTARTUPFIRE", OnEventFire);
+
+ buttonWndProc = (WNDPROC)CallService("Button/GetWindowProc",0,0);
+ WNDCLASSEX wc = {0};
+ wc.cbSize = sizeof(wc);
+ wc.lpszClassName = TTB_BUTTON_CLASS;
+ wc.lpfnWndProc = TTBButtonWndProc;
+ wc.hCursor = LoadCursor(NULL, IDC_ARROW);
+ wc.cbWndExtra = sizeof(void*);
+ wc.hbrBackground = 0;
+ wc.style = CS_GLOBALCLASS;
+ RegisterClassEx(&wc);
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+int UnloadToolbarModule()
+{
+ DestroyHookableEvent(hTTBModuleLoaded);
+ DestroyHookableEvent(hTTBInitButtons);
+
+ DeleteObject(hBmpSeparator);
+ DeleteCriticalSection(&csButtonsHook);
+
+ for (int i=0; i < Buttons.getCount(); i++)
+ delete Buttons[i];
+ Buttons.destroy();
+
+ mir_free(g_ctrl);
+ return 0;
+}
diff --git a/plugins/TopToolBar/src/toolbarwnd.cpp b/plugins/TopToolBar/src/toolbarwnd.cpp new file mode 100644 index 0000000000..e3f19f693b --- /dev/null +++ b/plugins/TopToolBar/src/toolbarwnd.cpp @@ -0,0 +1,330 @@ +
+#include "common.h"
+
+COLORREF bkColour;
+HBITMAP hBmpBackground, hBmpSeparator;
+int backgroundBmpUse;
+
+static TCHAR pluginname[] = _T("TopToolBar");
+
+/////////////////////////////////////////////////////////////////////////////////////////
+// Toolbar window procedure
+
+static void PaintToolbar(HWND hwnd)
+{
+ InvalidateRect(hwnd, 0, FALSE);
+
+ PAINTSTRUCT paintst;
+ HDC hdc = BeginPaint(hwnd, &paintst);
+ RECT *rcPaint = &paintst.rcPaint;
+
+ RECT clRect;
+ GetClientRect(hwnd, &clRect);
+ if (rcPaint == NULL) rcPaint = &clRect;
+
+ int yScroll = 0;
+ int y = -yScroll;
+
+ HDC hdcMem = CreateCompatibleDC(hdc);
+ HBITMAP hBmpOsb = CreateBitmap(clRect.right, clRect.bottom, 1, GetDeviceCaps(hdc, BITSPIXEL), NULL);
+ HBITMAP hOldBmp = (HBITMAP)SelectObject(hdcMem, hBmpOsb);
+ SetBkMode(hdcMem, TRANSPARENT);
+
+ HBRUSH hBrush = CreateSolidBrush(bkColour);
+ HBRUSH hoBrush = (HBRUSH)SelectObject(hdcMem, hBrush);
+ FillRect(hdcMem, rcPaint, hBrush);
+ SelectObject(hdcMem, hoBrush);
+ DeleteObject(hBrush);
+ if (hBmpBackground) {
+ BITMAP bmp;
+ GetObject(hBmpBackground, sizeof(bmp), &bmp);
+
+ HDC hdcBmp = CreateCompatibleDC(hdcMem);
+ SelectObject(hdcBmp, hBmpBackground);
+ int y = backgroundBmpUse & CLBF_SCROLL ? -yScroll : 0;
+ int maxx = backgroundBmpUse & CLBF_TILEH ? clRect.right : 1;
+ int maxy = backgroundBmpUse & CLBF_TILEV ? maxy = rcPaint->bottom : y+1;
+
+ int destw, desth;
+ switch(backgroundBmpUse & CLBM_TYPE) {
+ case CLB_STRETCH:
+ if (backgroundBmpUse&CLBF_PROPORTIONAL) {
+ if (clRect.right * bmp.bmHeight < clRect.bottom * bmp.bmWidth) {
+ desth = clRect.bottom;
+ destw = desth * bmp.bmWidth/bmp.bmHeight;
+ }
+ else {
+ destw = clRect.right;
+ desth = destw * bmp.bmHeight/bmp.bmWidth;
+ }
+ }
+ else {
+ destw = clRect.right;
+ desth = clRect.bottom;
+ }
+ break;
+ case CLB_STRETCHH:
+ if (backgroundBmpUse & CLBF_PROPORTIONAL) {
+ destw = clRect.right;
+ desth = destw * bmp.bmHeight/bmp.bmWidth;
+ if (backgroundBmpUse & CLBF_TILEVTOROWHEIGHT)
+ desth = g_ctrl->nButtonHeight+2;
+ }
+ else {
+ destw = clRect.right;
+ desth = bmp.bmHeight;
+ }
+ break;
+ case CLB_STRETCHV:
+ if (backgroundBmpUse & CLBF_PROPORTIONAL) {
+ desth = clRect.bottom;
+ destw = desth*bmp.bmWidth/bmp.bmHeight;
+ }
+ else {
+ destw = bmp.bmWidth;
+ desth = clRect.bottom;
+ }
+ break;
+ default: //clb_topleft
+ destw = bmp.bmWidth;
+ desth = bmp.bmHeight;
+ if (backgroundBmpUse & CLBF_TILEVTOROWHEIGHT)
+ desth = g_ctrl->nButtonHeight+2;
+ break;
+ }
+
+ for (; y < maxy; y += desth) {
+ if (y < rcPaint->top - desth)
+ continue;
+
+ for (int x = 0; x < maxx; x += destw)
+ StretchBlt(hdcMem, x, y, destw, desth, hdcBmp, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY);
+ }
+ DeleteDC(hdcBmp);
+ }
+ BitBlt(hdc, rcPaint->left, rcPaint->top, rcPaint->right-rcPaint->left, rcPaint->bottom-rcPaint->top, hdcMem, rcPaint->left, rcPaint->top, SRCCOPY);
+ SelectObject(hdcMem, hOldBmp);
+ DeleteDC(hdcMem);
+ DeleteObject(hBmpOsb);
+
+ paintst.fErase = FALSE;
+ EndPaint(hwnd, &paintst);
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+LRESULT CALLBACK TopToolBarProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ static bool supressRepos = false;
+
+ if (g_ctrl->fnWindowProc != NULL)
+ if ( g_ctrl->fnWindowProc(hwnd, msg, wParam, lParam))
+ return g_ctrl->lResult;
+
+ switch(msg) {
+ case WM_CREATE:
+ g_ctrl->hWnd = hwnd;
+ PostMessage(hwnd, TTB_UPDATEFRAMEVISIBILITY, 1, 0);
+ return FALSE;
+
+ case WM_MOVE:
+ return 0;
+
+ case WM_WINDOWPOSCHANGING:
+ case WM_SIZE:
+ if (g_ctrl->nLastHeight != HIWORD(lParam)) {
+ db_set_dw(0, TTB_OPTDIR, "LastHeight", g_ctrl->nLastHeight = HIWORD(lParam));
+ ArrangeButtons();
+ }
+ if (supressRepos) {
+ supressRepos = false;
+ break;
+ }
+ // fall through
+
+ case TTB_REPOSBUTTONS:
+ if (g_ctrl->hWnd == hwnd) {
+ int iHeight = ArrangeButtons();
+ if ( g_ctrl->bAutoSize) {
+ RECT rcClient;
+ GetClientRect(g_ctrl->hWnd, &rcClient);
+ if (rcClient.bottom - rcClient.top != iHeight && iHeight) {
+ supressRepos = true;
+ PostMessage(hwnd, TTB_UPDATEFRAMEVISIBILITY, -1, 0);
+ }
+ }
+ return 0;
+ }
+ break;
+
+ case WM_NCPAINT:
+ case WM_PAINT:
+ PaintToolbar(hwnd);
+ return 0;
+
+ case WM_LBUTTONDOWN:
+ if (db_get_b(NULL, "CLUI", "ClientAreaDrag", 0)) {
+ POINT pt;
+ GetCursorPos(&pt);
+ return SendMessage(GetParent(hwnd), WM_SYSCOMMAND, SC_MOVE|HTCAPTION, MAKELPARAM(pt.x, pt.y));
+ }
+ return 0;
+
+ case WM_COMMAND:
+ switch (HIWORD(wParam)) {
+ case BN_CLICKED:
+ case BN_DOUBLECLICKED:
+ {
+ int id = GetWindowLongPtr((HWND)lParam, GWLP_USERDATA);
+ if (id != 0) {
+ mir_cslock lck(csButtonsHook);
+ TopButtonInt* b = idtopos(id);
+ if (b == NULL || b->isSep())
+ return 0;
+
+ if (b->dwFlags & TTBBF_ASPUSHBUTTON)
+ b->bPushed = !b->bPushed;
+
+ if (b->bPushed) { //Dn -> Up
+ if (!(b->dwFlags & TTBBF_ISLBUTTON)) // must be always true
+ if (b->pszService != NULL)
+ CallService(b->pszService, b->wParamUp, b->lParamUp);
+ }
+ else { //Up -> Dn
+ if (b->pszService != NULL)
+ CallService(b->pszService, b->wParamDown, b->lParamDown);
+ }
+
+ b->SetBitmap();
+ }
+ }
+ break;
+ }
+ break;
+
+ case TTB_UPDATEFRAMEVISIBILITY:
+ {
+ BOOL vis=(BOOL)wParam;
+ BOOL curvis = IsWindowVisible(hwnd);
+ bool bResize = false;
+ int Height = ArrangeButtons();
+
+ if (g_ctrl->bAutoSize) {
+ INT_PTR frameopt = CallService(MS_CLIST_FRAMES_GETFRAMEOPTIONS, MAKEWPARAM(FO_HEIGHT, g_ctrl->hFrame), 0);
+ if (Height != frameopt) {
+ CallService(MS_CLIST_FRAMES_SETFRAMEOPTIONS, MAKEWPARAM(FO_HEIGHT, g_ctrl->hFrame), Height);
+ bResize = TRUE;
+ }
+ }
+
+ if (g_ctrl->bOrderChanged)
+ bResize = TRUE, g_ctrl->bOrderChanged = FALSE;
+
+ if ((curvis != vis || bResize) && vis != -1) {
+ INT_PTR frameopt = CallService(MS_CLIST_FRAMES_GETFRAMEOPTIONS, MAKEWPARAM(FO_FLAGS, g_ctrl->hFrame), 0);
+ frameopt &= ~F_VISIBLE;
+ frameopt |= vis ? F_VISIBLE : 0;
+ CallService(MS_CLIST_FRAMES_SETFRAMEOPTIONS, MAKEWPARAM(FO_FLAGS, g_ctrl->hFrame), frameopt);
+ }
+ }
+ break;
+
+ case TTB_SETCUSTOM:
+ {
+ TTBCtrlCustomize *pCustom = (TTBCtrlCustomize*)lParam;
+ if (pCustom == NULL || g_ctrl->fnWindowProc)
+ break;
+
+ g_ctrl = (TTBCtrl*)mir_realloc(g_ctrl, pCustom->cbLen);
+ if (pCustom->cbLen > sizeof(TTBCtrl))
+ memset(g_ctrl+1, 0, pCustom->cbLen - sizeof(TTBCtrl));
+
+ g_ctrl->fnWindowProc = pCustom->fnWindowProc;
+ SetWindowLongPtr(hwnd, 0, (LONG_PTR)g_ctrl);
+ }
+ break;
+
+ default:
+ return DefWindowProc(hwnd, msg, wParam, lParam);
+ }
+ return(TRUE);
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+INT_PTR OnEventFire(WPARAM wParam, LPARAM lParam)
+{
+ CallService(MS_SYSTEM_REMOVEWAIT, wParam, 0);
+ CloseHandle((HANDLE)wParam);
+
+ HWND parent = (HWND)CallService(MS_CLUI_GETHWND, 0, 0);
+ if (parent == NULL) // no clist, no buttons
+ return -1;
+
+ WNDCLASS wndclass = { 0 };
+ wndclass.lpfnWndProc = TopToolBarProc;
+ wndclass.cbWndExtra = sizeof(void*);
+ wndclass.hInstance = hInst;
+ wndclass.hCursor = LoadCursor(NULL, IDC_ARROW);
+ wndclass.hbrBackground = (HBRUSH)(COLOR_BTNFACE+1);
+ wndclass.lpszClassName = pluginname;
+ RegisterClass(&wndclass);
+
+ g_ctrl->pButtonList = (SortedList*)&Buttons;
+ g_ctrl->hWnd = CreateWindow(pluginname, _T("Toolbar"),
+ WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,
+ 0, 0, 0, g_ctrl->nLastHeight, parent, NULL, hInst, NULL);
+ SetWindowLongPtr(g_ctrl->hWnd, 0, (LPARAM)g_ctrl);
+
+ LoadBackgroundOptions();
+
+ // if we're working in skinned clist, receive the standard buttons & customizations
+ if (g_CustomProc && g_ctrl->hWnd)
+ g_CustomProc(TTB_WINDOW_HANDLE, g_ctrl->hWnd, g_CustomProcParam);
+
+ // if there's no customized frames, create our own
+ if (g_ctrl->hFrame == NULL) {
+ CLISTFrame Frame = { 0 };
+ Frame.cbSize = sizeof(Frame);
+ Frame.tname = _T("Toolbar");
+ Frame.hWnd = g_ctrl->hWnd;
+ Frame.align = alTop;
+ Frame.Flags = F_VISIBLE | F_NOBORDER | F_LOCKED | F_TCHAR;
+ Frame.height = g_ctrl->nLastHeight;
+ g_ctrl->hFrame = (HANDLE)CallService(MS_CLIST_FRAMES_ADDFRAME, (WPARAM)&Frame, 0);
+ }
+
+ // receive all buttons
+ NotifyEventHooks(hTTBInitButtons, 0, 0);
+ NotifyEventHooks(hTTBModuleLoaded, 0, 0);
+
+ return 0;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+int LoadBackgroundOptions()
+{
+ //load options
+ bkColour = DBGetContactSettingDword(NULL, TTB_OPTDIR, "BkColour", TTBDEFAULT_BKCOLOUR);
+ if (hBmpBackground) {
+ DeleteObject(hBmpBackground);
+ hBmpBackground = NULL;
+ }
+
+ if (db_get_b(NULL, TTB_OPTDIR, "UseBitmap", TTBDEFAULT_USEBITMAP)) {
+ DBVARIANT dbv;
+ if (!DBGetContactSetting(NULL, TTB_OPTDIR, "BkBitmap", &dbv)) {
+ hBmpBackground = (HBITMAP)CallService(MS_UTILS_LOADBITMAP, 0, (LPARAM)dbv.pszVal);
+ DBFreeVariant(&dbv);
+ }
+ }
+ backgroundBmpUse = DBGetContactSettingWord(NULL, TTB_OPTDIR, "BkBmpUse", TTBDEFAULT_BKBMPUSE);
+
+ RECT rc;
+ GetClientRect(g_ctrl->hWnd, &rc);
+ InvalidateRect(g_ctrl->hWnd, &rc, TRUE);
+ UpdateWindow(g_ctrl->hWnd);
+
+ return 0;
+}
diff --git a/plugins/TopToolBar/src/topbutton.cpp b/plugins/TopToolBar/src/topbutton.cpp new file mode 100644 index 0000000000..8e2f8a1cfd --- /dev/null +++ b/plugins/TopToolBar/src/topbutton.cpp @@ -0,0 +1,178 @@ +
+#include "common.h"
+
+#define BitChanged(c) (dwFlags ^ Flags) & c
+
+static int maxid = 10000;
+
+TopButtonInt::~TopButtonInt()
+{
+ if (hwnd)
+ DestroyWindow(hwnd);
+
+ if (dwFlags & TTBBF_ISLBUTTON) {
+ mir_free(ptszProgram);
+ }
+ else if (pszService != NULL)
+ mir_free(pszService);
+
+ mir_free(pszName);
+ mir_free(ptszTooltip);
+ mir_free(ptszTooltipDn);
+ mir_free(ptszTooltipUp);
+}
+
+DWORD TopButtonInt::CheckFlags(DWORD Flags)
+{
+ int res = 0;
+ if ( BitChanged(TTBBF_DISABLED)) {
+ dwFlags ^= TTBBF_DISABLED;
+ EnableWindow(hwnd,(dwFlags & TTBBF_DISABLED)?FALSE:TRUE);
+ }
+ if ( BitChanged(TTBBF_ASPUSHBUTTON)) {
+ dwFlags ^= TTBBF_ASPUSHBUTTON;
+ SendMessage(hwnd, BUTTONSETASPUSHBTN, (dwFlags & TTBBF_ASPUSHBUTTON)?1:0, 0);
+ }
+ if ( BitChanged(TTBBF_SHOWTOOLTIP)) {
+ dwFlags ^= TTBBF_SHOWTOOLTIP;
+ SendMessage(hwnd,BUTTONADDTOOLTIP,
+ (WPARAM)((dwFlags & TTBBF_SHOWTOOLTIP) ? ptszTooltip : _T("")), BATF_TCHAR);
+ }
+ // next settings changing visual side, requires additional actions
+ if ( BitChanged(TTBBF_VISIBLE)) {
+ dwFlags ^= TTBBF_VISIBLE;
+ res |= TTBBF_VISIBLE;
+ }
+ if ( BitChanged(TTBBF_PUSHED)) {
+ dwFlags ^= TTBBF_PUSHED;
+ res |= TTBBF_PUSHED;
+ bPushed = (dwFlags & TTBBF_PUSHED) ? TRUE : FALSE;
+ }
+ return res;
+}
+
+void TopButtonInt::CreateWnd()
+{
+ if ( !(dwFlags & TTBBF_ISSEPARATOR)) {
+ hwnd = CreateWindow(TTB_BUTTON_CLASS, _T(""), BS_PUSHBUTTON|WS_CHILD|WS_TABSTOP|SS_NOTIFY, 0, 0, g_ctrl->nButtonWidth, g_ctrl->nButtonHeight, g_ctrl->hWnd, NULL, hInst, this);
+
+ if (dwFlags & TTBBF_ASPUSHBUTTON)
+ SendMessage(hwnd, BUTTONSETASPUSHBTN, 1, 0);
+
+ if (db_get_b(0, TTB_OPTDIR, "UseFlatButton", 1))
+ SendMessage(hwnd, BUTTONSETASFLATBTN, TRUE, 0);
+
+ EnableWindow(hwnd,(dwFlags & TTBBF_DISABLED)?FALSE:TRUE);
+ }
+ // maybe SEPWIDTH, not g_ctrl->nButtonWidth?
+ else
+ hwnd = CreateWindow( _T("STATIC"), _T(""), WS_CHILD|SS_NOTIFY, 0, 0, g_ctrl->nButtonWidth, g_ctrl->nButtonHeight, g_ctrl->hWnd, NULL, hInst, 0);
+
+ SetWindowLongPtr(hwnd, GWLP_USERDATA, id);
+ SetBitmap();
+}
+
+void TopButtonInt::LoadSettings()
+{
+ char buf[255];
+
+ BYTE oldv = isVisible();
+ dwFlags = dwFlags & (~TTBBF_VISIBLE);
+
+ if (dwFlags & TTBBF_ISSEPARATOR) {
+ char buf1[10];
+ _itoa(wParamDown, buf1, 10);
+ char buf2[20];
+ AS(buf2, "Sep", buf1);
+
+ arrangedpos = db_get_b(0, TTB_OPTDIR, AS(buf, buf2, "_Position"), Buttons.getCount());
+ if ( db_get_b(0, TTB_OPTDIR, AS(buf, buf2, "_Visible"), oldv) > 0 )
+ dwFlags |= TTBBF_VISIBLE;
+ }
+ else if ((dwFlags & TTBBF_ISLBUTTON ) && (dwFlags & TTBBF_INTERNAL)) {
+ char buf1[10];
+ _itoa(wParamDown, buf1, 10);
+ char buf2[20];
+ AS(buf2, "Launch", buf1);
+
+ mir_free(pszName);
+ pszName = DBGetString(0, TTB_OPTDIR, AS(buf, buf2, "_name"));
+
+ mir_free(ptszProgram);
+ ptszProgram = DBGetStringT(0, TTB_OPTDIR, AS(buf, buf2, "_lpath"));
+
+ arrangedpos = db_get_b(0, TTB_OPTDIR, AS(buf, buf2, "_Position"), Buttons.getCount());
+ if ( db_get_b(0, TTB_OPTDIR, AS(buf, buf2, "_Visible"), oldv) > 0 )
+ dwFlags |= TTBBF_VISIBLE;
+ }
+ else {
+ arrangedpos = db_get_b(0, TTB_OPTDIR, AS(buf, pszName, "_Position"), Buttons.getCount());
+ if ( db_get_b(0, TTB_OPTDIR, AS(buf, pszName, "_Visible"), oldv) > 0 )
+ dwFlags |= TTBBF_VISIBLE;
+ }
+
+ if (Buttons.getIndex(this) != -1)
+ arrangedpos = maxid++;
+}
+
+void TopButtonInt::SaveSettings(int *SepCnt, int *LaunchCnt)
+{
+ char buf[255];
+
+ if (SepCnt && (dwFlags & TTBBF_ISSEPARATOR) && (dwFlags & TTBBF_INTERNAL)) {
+ char buf1[10];
+ _itoa(SepCnt[0]++, buf1, 10);
+ char buf2[20];
+ AS(buf2, "Sep", buf1);
+
+ db_set_b(0, TTB_OPTDIR, AS(buf, buf2, "_Position"), arrangedpos);
+ db_set_b(0, TTB_OPTDIR, AS(buf, buf2, "_Visible"), isVisible());
+ }
+ else if (LaunchCnt && (dwFlags & TTBBF_ISLBUTTON ) && (dwFlags & TTBBF_INTERNAL)) {
+ char buf1[10];
+ _itoa(LaunchCnt[0]++, buf1, 10);
+ char buf2[20];
+ AS(buf2, "Launch", buf1);
+
+ DBWriteContactSettingString(0, TTB_OPTDIR, AS(buf, buf2, "_name"), pszName);
+ DBWriteContactSettingTString(0, TTB_OPTDIR, AS(buf, buf2, "_lpath"), ptszProgram);
+ db_set_b(0, TTB_OPTDIR, AS(buf, buf2, "_Position"), arrangedpos);
+ db_set_b(0, TTB_OPTDIR, AS(buf, buf2, "_Visible"), isVisible());
+ }
+ else {
+ db_set_b(0, TTB_OPTDIR, AS(buf, pszName, "_Position"), arrangedpos);
+ db_set_b(0, TTB_OPTDIR, AS(buf, pszName, "_Visible"), isVisible());
+ }
+}
+
+void TopButtonInt::SetBitmap()
+{
+ int curstyle = GetWindowLongPtr(hwnd, GWL_STYLE);
+ curstyle &= (~SS_BITMAP);
+ curstyle &= (~SS_ICON);
+
+ if (dwFlags & TTBBF_ISSEPARATOR) {
+ SetWindowLongPtr(hwnd, GWL_STYLE, curstyle | SS_BITMAP);
+ SendMessage(hwnd, STM_SETIMAGE, IMAGE_BITMAP, (LPARAM)hBmpSeparator);
+ SendMessage(hwnd, BM_SETIMAGE, IMAGE_BITMAP, (LPARAM)hBmpSeparator);
+ }
+ else {
+ if (GetWindowLongPtr(hwnd, GWL_STYLE) & SS_ICON)
+ SetWindowLongPtr(hwnd, GWL_STYLE, curstyle | SS_ICON);
+
+ TCHAR* pTooltip;
+ if (bPushed) {
+ SendMessage(hwnd, BM_SETIMAGE, IMAGE_ICON, (LPARAM)((hIconDn) ? hIconDn : hIconUp));
+ SendMessage(hwnd, BM_SETCHECK, BST_CHECKED, 0);
+
+ pTooltip = (ptszTooltipDn) ? ptszTooltipDn : ptszTooltipUp;
+ }
+ else {
+ SendMessage(hwnd, BM_SETIMAGE, IMAGE_ICON, (LPARAM)hIconUp);
+ SendMessage(hwnd, BM_SETCHECK, BST_UNCHECKED, 0);
+ pTooltip = ptszTooltipUp;
+ }
+ if (pTooltip)
+ SendMessage(hwnd, BUTTONADDTOOLTIP, (WPARAM)TranslateTH(hLangpack, pTooltip), BATF_TCHAR);
+ }
+}
diff --git a/plugins/TopToolBar/src/ttbopt.cpp b/plugins/TopToolBar/src/ttbopt.cpp new file mode 100644 index 0000000000..db7d78dcb5 --- /dev/null +++ b/plugins/TopToolBar/src/ttbopt.cpp @@ -0,0 +1,559 @@ +#include "common.h"
+
+static HWND OptionshWnd;
+
+struct OrderData
+{
+ int dragging;
+ HTREEITEM hDragItem;
+ HIMAGELIST himlButtonIcons;
+};
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+static HTREEITEM AddLine(HWND hTree,TopButtonInt *b, HTREEITEM hItem, HIMAGELIST il)
+{
+ TVINSERTSTRUCT tvis = { 0 };
+ tvis.hInsertAfter = hItem;
+ tvis.item.mask = TVIF_PARAM | TVIF_TEXT | TVIF_STATE | TVIF_IMAGE | TVIF_SELECTEDIMAGE;
+
+ int index;
+ TCHAR* tmp;
+
+ if (b->dwFlags & TTBBF_ISSEPARATOR) {
+ tvis.item.pszText = _T("------------------");
+ index = -1;
+ }
+ else {
+ if (b->hIconHandleUp) {
+ HICON hIcon = Skin_GetIconByHandle(b->hIconHandleUp);
+ index = ImageList_AddIcon(il, hIcon);
+ Skin_ReleaseIcon(hIcon);
+ }
+ else index = ImageList_AddIcon(il, b->hIconUp);
+
+ tmp = mir_a2t( b->pszName );
+ tvis.item.pszText = TranslateTS(tmp);
+ }
+ tvis.item.iImage = tvis.item.iSelectedImage = index;
+
+ tvis.item.lParam = (LPARAM)b;
+ HTREEITEM hti = TreeView_InsertItem(hTree, &tvis);
+
+ if (!(b->dwFlags & TTBBF_ISSEPARATOR))
+ mir_free(tmp);
+
+ TreeView_SetCheckState(hTree, hti, b->isVisible());
+ return hti;
+}
+
+static int BuildTree(HWND hwndDlg)
+{
+ HWND hTree = GetDlgItem(hwndDlg, IDC_BUTTONORDERTREE);
+ OrderData *dat = (OrderData*)GetWindowLongPtr(hTree, GWLP_USERDATA);
+
+ dat->himlButtonIcons = ImageList_Create(GetSystemMetrics(SM_CXSMICON), GetSystemMetrics(SM_CYSMICON), ILC_COLOR32 | ILC_MASK, 2, 2);
+ TreeView_SetImageList(hTree, dat->himlButtonIcons, TVSIL_NORMAL);
+ SetWindowLongPtr(hTree, GWL_STYLE, GetWindowLongPtr(hTree,GWL_STYLE)|TVS_NOHSCROLL);
+ TreeView_DeleteAllItems(hTree);
+
+ if (Buttons.getCount() == 0)
+ return FALSE;
+
+ for (int i = 0; i < Buttons.getCount(); i++)
+ AddLine(hTree, Buttons[i], TVI_LAST, dat->himlButtonIcons);
+ return TRUE;
+}
+
+static void SaveTree(HWND hwndDlg)
+{
+ HWND hTree = GetDlgItem(hwndDlg, IDC_BUTTONORDERTREE);
+
+ TVITEM tvi = { 0 };
+ tvi.hItem = TreeView_GetRoot(hTree);
+ tvi.stateMask = TVIS_STATEIMAGEMASK;
+ tvi.mask = TVIF_PARAM | TVIF_HANDLE | TVIF_STATE;
+
+ LIST<TopButtonInt> tmpList(8);
+
+ while(tvi.hItem != NULL) {
+ TreeView_GetItem(hTree, &tvi);
+
+ TopButtonInt* btn = (TopButtonInt*)tvi.lParam;
+ Buttons.remove(btn);
+
+ if (TreeView_GetCheckState(hTree,tvi.hItem))
+ btn->dwFlags |= TTBBF_VISIBLE;
+ else
+ btn->dwFlags &= ~TTBBF_VISIBLE;
+ btn->dwFlags &= ~TTBBF_OPTIONAL;
+ btn->arrangedpos = tmpList.getCount();
+
+ tmpList.insert(btn);
+ tvi.hItem = TreeView_GetNextSibling(hTree, tvi.hItem);
+ }
+ {
+ mir_cslock lck(csButtonsHook);
+ for (int i=0; i < Buttons.getCount(); i++)
+ delete Buttons[i];
+
+ Buttons = tmpList;
+ tmpList.destroy();
+ }
+ SaveAllButtonsOptions();
+}
+
+void CancelProcess(HWND hwndDlg)
+{
+ HWND hTree = GetDlgItem(hwndDlg, IDC_BUTTONORDERTREE);
+
+ TVITEM tvi = { 0 };
+ tvi.hItem = TreeView_GetRoot(hTree);
+
+ while(tvi.hItem != NULL) {
+ tvi.stateMask = TVIS_STATEIMAGEMASK;
+ tvi.mask = TVIF_PARAM | TVIF_HANDLE | TVIF_STATE;
+ TreeView_GetItem(hTree, &tvi);
+
+ TopButtonInt* btn = (TopButtonInt*)tvi.lParam;
+
+ if (btn ->dwFlags & TTBBF_OPTIONAL)
+ delete btn;
+
+ tvi.hItem = TreeView_GetNextSibling(hTree, tvi.hItem);
+ }
+}
+
+static void RecreateWindows()
+{
+ {
+ mir_cslock lck(csButtonsHook);
+ for (int i = 0; i < Buttons.getCount(); i++) {
+ TopButtonInt *b = Buttons[i];
+ if (b->hwnd) {
+ DestroyWindow(b->hwnd);
+ b->CreateWnd();
+ }
+ }
+ }
+
+ if (g_ctrl->hWnd)
+ PostMessage(g_ctrl->hWnd, TTB_UPDATEFRAMEVISIBILITY, TRUE, 0);
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+// external functions
+
+void AddToOptions(TopButtonInt* b)
+{
+ if (OptionshWnd) {
+ HWND hTree = GetDlgItem(OptionshWnd, IDC_BUTTONORDERTREE);
+ OrderData *dat = (OrderData*)GetWindowLongPtr(hTree, GWLP_USERDATA);
+ AddLine(hTree, b, TVI_LAST, dat->himlButtonIcons);
+ }
+}
+
+void RemoveFromOptions(int id)
+{
+ if (OptionshWnd) {
+ HWND hTree = GetDlgItem(OptionshWnd, IDC_BUTTONORDERTREE);
+ TVITEM tvi = { 0 };
+ tvi.hItem = TreeView_GetRoot(hTree);
+ tvi.mask = TVIF_PARAM | TVIF_HANDLE;
+
+ TopButtonInt* btn;
+ while(tvi.hItem != NULL) {
+ TreeView_GetItem(hTree, &tvi);
+ btn = (TopButtonInt*)tvi.lParam;
+ if (btn->id == id) {
+ // delete if was changed
+ if (btn->dwFlags & TTBBF_OPTIONAL)
+ delete btn;
+ TreeView_DeleteItem(hTree,tvi.hItem);
+ break;
+ }
+
+ tvi.hItem = TreeView_GetNextSibling(hTree, tvi.hItem);
+ }
+ }
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+// Options window: main
+
+static INT_PTR CALLBACK ButOrderOpts(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ HWND hTree = GetDlgItem(hwndDlg, IDC_BUTTONORDERTREE);
+ OrderData *dat = (OrderData*)GetWindowLongPtr(hTree, GWLP_USERDATA);
+
+ switch (msg) {
+ case WM_INITDIALOG:
+ TranslateDialogDefault(hwndDlg);
+ dat = (OrderData*)malloc( sizeof(OrderData));
+ SetWindowLongPtr(hTree, GWLP_USERDATA, (LONG)dat);
+ dat->dragging = 0;
+
+ SetWindowLongPtr(hTree, GWL_STYLE, GetWindowLongPtr(hTree, GWL_STYLE)|TVS_NOHSCROLL);
+
+ SetDlgItemInt(hwndDlg, IDC_BUTTHEIGHT, g_ctrl->nButtonHeight, FALSE);
+ SendDlgItemMessage(hwndDlg, IDC_SPIN_HEIGHT, UDM_SETRANGE, 0, MAKELONG(50,10));
+ SendDlgItemMessage(hwndDlg, IDC_SPIN_HEIGHT, UDM_SETPOS, 0, MAKELONG(g_ctrl->nButtonHeight,0));
+
+ SetDlgItemInt(hwndDlg, IDC_BUTTWIDTH, g_ctrl->nButtonWidth, FALSE);
+ SendDlgItemMessage(hwndDlg, IDC_SPIN_WIDTH, UDM_SETRANGE, 0, MAKELONG(50,10));
+ SendDlgItemMessage(hwndDlg, IDC_SPIN_WIDTH, UDM_SETPOS, 0, MAKELONG(g_ctrl->nButtonWidth,0));
+
+ SetDlgItemInt(hwndDlg, IDC_BUTTGAP, g_ctrl->nButtonSpace, FALSE);
+ SendDlgItemMessage(hwndDlg, IDC_SPIN_GAP, UDM_SETRANGE, 0, MAKELONG(20,0));
+ SendDlgItemMessage(hwndDlg, IDC_SPIN_GAP, UDM_SETPOS, 0, MAKELONG(g_ctrl->nButtonSpace,0));
+
+ CheckDlgButton(hwndDlg, IDC_USEFLAT, g_ctrl->bFlatButtons);
+ CheckDlgButton(hwndDlg, IDC_AUTORESIZE, g_ctrl->bAutoSize);
+ CheckDlgButton(hwndDlg, IDC_SINGLELINE, g_ctrl->bSingleLine);
+
+ BuildTree(hwndDlg);
+ EnableWindow(GetDlgItem(hwndDlg, IDC_ENAME), FALSE);
+ EnableWindow(GetDlgItem(hwndDlg, IDC_EPATH), FALSE);
+ EnableWindow(GetDlgItem(hwndDlg, IDC_DELLBUTTON), FALSE);
+
+ OptionshWnd = hwndDlg;
+ return TRUE;
+
+ case WM_COMMAND:
+ if (HIWORD(wParam) == EN_CHANGE && OptionshWnd) {
+ switch(LOWORD(wParam)) {
+ case IDC_ENAME: case IDC_EPATH:
+ break;
+ default:
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+ }
+ break;
+ }
+
+ if ((HIWORD(wParam) == BN_CLICKED || HIWORD(wParam) == BN_DBLCLK)) {
+ int ctrlid = LOWORD(wParam);
+
+ //----- Launch buttons -----
+
+ if (ctrlid == IDC_BROWSE) {
+ TCHAR str[MAX_PATH];
+ OPENFILENAME ofn = {0};
+
+ GetDlgItemText(hwndDlg, IDC_EPATH, str, sizeof(str));
+ ofn.lStructSize = OPENFILENAME_SIZE_VERSION_400;
+ ofn.hwndOwner = hwndDlg;
+ ofn.hInstance = NULL;
+ ofn.lpstrFilter = NULL;
+ ofn.lpstrFile = str;
+ ofn.Flags = OFN_FILEMUSTEXIST | OFN_PATHMUSTEXIST | OFN_EXPLORER;
+ ofn.nMaxFile = sizeof(str);
+ ofn.nMaxFileTitle = MAX_PATH;
+ ofn.lpstrDefExt = _T("exe");
+ if (!GetOpenFileName(&ofn))
+ break;
+
+ SetDlgItemText(hwndDlg, IDC_EPATH, str);
+
+ break;
+ }
+
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+
+ if (ctrlid == IDC_LBUTTONSET) {
+ TVITEM tvi ={0};
+ tvi.hItem = TreeView_GetSelection(hTree);
+ if (tvi.hItem == NULL)
+ break;
+
+ tvi.mask = TVIF_PARAM;
+ TreeView_GetItem(hTree, &tvi);
+
+ TopButtonInt* btn = (TopButtonInt*)tvi.lParam;
+ TCHAR buf [256];
+ // probably, condition not needs
+ if (btn->dwFlags & TTBBF_ISLBUTTON) {
+ if (!(btn->dwFlags & TTBBF_OPTIONAL)) {
+ // create button
+ TTBButton ttb = { 0 };
+ ttb.cbSize = sizeof(ttb);
+ ttb.hIconDn = (HICON)LoadImage(hInst, MAKEINTRESOURCE(IDI_RUN), IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR);
+ ttb.dwFlags = TTBBF_VISIBLE | TTBBF_ISLBUTTON | TTBBF_INTERNAL | TTBBF_OPTIONAL;
+ ttb.name = NULL;
+ ttb.program = NULL;
+ int id = btn->id;
+ btn = CreateButton(&ttb);
+ btn->id = id;
+
+ tvi.lParam = (LPARAM)btn;
+ TreeView_SetItem(hTree, &tvi);
+ }
+
+ GetDlgItemText(hwndDlg, IDC_ENAME, buf, 255);
+ replaceStr(btn->pszName, _T2A(buf));
+
+ tvi.mask = TVIF_TEXT;
+ tvi.pszText = buf;
+ TreeView_SetItem(hTree, &tvi);
+
+ GetDlgItemText(hwndDlg, IDC_EPATH, buf, 255);
+ replaceStrT(btn->ptszProgram, buf);
+ }
+ break;
+ }
+
+ if (ctrlid == IDC_ADDLBUTTON) {
+ // create button
+ TTBButton ttb = { 0 };
+ ttb.cbSize = sizeof(ttb);
+ ttb.hIconDn = (HICON)LoadImage(hInst, MAKEINTRESOURCE(IDI_RUN), IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR);
+ ttb.dwFlags = TTBBF_VISIBLE | TTBBF_ISLBUTTON | TTBBF_INTERNAL | TTBBF_OPTIONAL;
+ ttb.name = LPGEN("Default");
+ ttb.program = _T("Execute Path");
+ TopButtonInt* b = CreateButton(&ttb);
+
+ // get selection for insert
+ TVITEM tvi = {0};
+ tvi.hItem = TreeView_GetSelection(hTree);
+
+ // insert item
+ AddLine(hTree, b, tvi.hItem, dat->himlButtonIcons);
+
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+ break;
+ }
+
+ //----- Separators -----
+
+ if (ctrlid == IDC_ADDSEP) {
+ // create button
+ TTBButton ttb = { 0 };
+ ttb.cbSize = sizeof(ttb);
+ ttb.dwFlags = TTBBF_VISIBLE | TTBBF_ISSEPARATOR | TTBBF_INTERNAL | TTBBF_OPTIONAL;
+ TopButtonInt* b = CreateButton(&ttb);
+
+ // get selection for insert
+ TVITEM tvi = {0};
+ tvi.hItem = TreeView_GetSelection(hTree);
+
+ // insert item
+ AddLine(hTree, b, tvi.hItem, dat->himlButtonIcons);
+
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+ break;
+ }
+
+ if (ctrlid == IDC_REMOVEBUTTON) {
+ TVITEM tvi = {0};
+ tvi.hItem = TreeView_GetSelection(hTree);
+ if (tvi.hItem == NULL)
+ break;
+
+ tvi.mask = TVIF_PARAM;
+ TreeView_GetItem(hTree, &tvi);
+
+ TopButtonInt* btn = (TopButtonInt*)tvi.lParam;
+ // if button enabled for separator and launch only, no need condition
+ // except possible service button introducing
+ if (btn->dwFlags & (TTBBF_ISSEPARATOR | TTBBF_ISLBUTTON)) {
+ // delete if was added in options
+ if (btn->dwFlags & TTBBF_OPTIONAL)
+ delete btn;
+
+ TreeView_DeleteItem(hTree,tvi.hItem);
+
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+ }
+ break;
+ }
+ }
+ break;
+
+ case WM_NOTIFY:
+ switch(((LPNMHDR)lParam)->idFrom) {
+ case 0:
+ switch (((LPNMHDR)lParam)->code) {
+ case PSN_APPLY:
+ g_ctrl->nButtonHeight = GetDlgItemInt(hwndDlg, IDC_BUTTHEIGHT, NULL, FALSE);
+ g_ctrl->nButtonWidth = GetDlgItemInt(hwndDlg, IDC_BUTTWIDTH, NULL, FALSE);
+ g_ctrl->nButtonSpace = GetDlgItemInt(hwndDlg, IDC_BUTTGAP, NULL, FALSE);
+
+ g_ctrl->bFlatButtons = (BYTE)IsDlgButtonChecked(hwndDlg, IDC_USEFLAT);
+ g_ctrl->bAutoSize = (BYTE)IsDlgButtonChecked(hwndDlg, IDC_AUTORESIZE);
+ g_ctrl->bSingleLine = (BYTE)IsDlgButtonChecked(hwndDlg, IDC_SINGLELINE);
+
+ db_set_dw(0, TTB_OPTDIR, "BUTTHEIGHT", g_ctrl->nButtonHeight);
+ db_set_dw(0, TTB_OPTDIR, "BUTTWIDTH", g_ctrl->nButtonWidth);
+ db_set_dw(0, TTB_OPTDIR, "BUTTGAP", g_ctrl->nButtonSpace);
+
+ db_set_b(0, TTB_OPTDIR, "UseFlatButton", g_ctrl->bFlatButtons);
+ db_set_b(0, TTB_OPTDIR, "SingleLine", g_ctrl->bSingleLine);
+ db_set_b(0, TTB_OPTDIR, "AutoSize", g_ctrl->bAutoSize);
+
+ SaveTree(hwndDlg);
+ RecreateWindows();
+ ArrangeButtons();
+ }
+ break;
+
+ case IDC_BUTTONORDERTREE:
+ switch (((LPNMHDR)lParam)->code) {
+ case TVN_BEGINDRAGA:
+ case TVN_BEGINDRAGW:
+ SetCapture(hwndDlg);
+ dat->dragging = 1;
+ dat->hDragItem = ((LPNMTREEVIEW)lParam)->itemNew.hItem;
+ TreeView_SelectItem(hTree, dat->hDragItem);
+ break;
+
+ case NM_CLICK:
+ {
+ TVHITTESTINFO hti;
+ hti.pt.x = (short)LOWORD(GetMessagePos());
+ hti.pt.y = (short)HIWORD(GetMessagePos());
+ ScreenToClient(((LPNMHDR)lParam)->hwndFrom, &hti.pt);
+ if (TreeView_HitTest(((LPNMHDR)lParam)->hwndFrom, &hti))
+ if (hti.flags & TVHT_ONITEMSTATEICON) {
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+ TreeView_SelectItem(hTree, hti.hItem);
+ }
+ }
+ break;
+
+ case TVN_SELCHANGEDA:
+ case TVN_SELCHANGEDW:
+ {
+ HTREEITEM hti = TreeView_GetSelection(hTree);
+ if (hti == NULL)
+ break;
+
+ TopButtonInt *btn = (TopButtonInt*)((LPNMTREEVIEW)lParam)->itemNew.lParam;
+
+ mir_cslock lck(csButtonsHook);
+
+ if (btn->dwFlags & TTBBF_ISLBUTTON) {
+ bool enable = (btn->dwFlags & TTBBF_INTERNAL) !=0;
+ EnableWindow(GetDlgItem(hwndDlg, IDC_ENAME), enable);
+ EnableWindow(GetDlgItem(hwndDlg, IDC_EPATH), enable);
+ EnableWindow(GetDlgItem(hwndDlg, IDC_REMOVEBUTTON), enable);
+ EnableWindow(GetDlgItem(hwndDlg, IDC_LBUTTONSET), enable);
+ if (btn->pszName != NULL)
+ SetDlgItemTextA(hwndDlg, IDC_ENAME, btn->pszName);
+ else
+ SetDlgItemTextA(hwndDlg, IDC_ENAME, "");
+
+ if (btn->ptszProgram != NULL)
+ SetDlgItemText(hwndDlg, IDC_EPATH, btn->ptszProgram);
+ else
+ SetDlgItemTextA(hwndDlg, IDC_EPATH, "");
+ }
+ else {
+ EnableWindow(GetDlgItem(hwndDlg,IDC_REMOVEBUTTON),
+ (btn->dwFlags & TTBBF_ISSEPARATOR)?TRUE:FALSE);
+
+ EnableWindow(GetDlgItem(hwndDlg, IDC_ENAME), FALSE);
+ EnableWindow(GetDlgItem(hwndDlg, IDC_EPATH), FALSE);
+ EnableWindow(GetDlgItem(hwndDlg, IDC_LBUTTONSET), FALSE);
+ SetDlgItemTextA(hwndDlg, IDC_ENAME, "");
+ SetDlgItemTextA(hwndDlg, IDC_EPATH, "");
+ }
+ }
+ }
+ break;
+ }
+ break;
+
+ case WM_MOUSEMOVE:
+ if (dat->dragging) {
+ TVHITTESTINFO hti;
+ hti.pt.x = (short)LOWORD(lParam);
+ hti.pt.y = (short)HIWORD(lParam);
+ ClientToScreen(hwndDlg, &hti.pt);
+ ScreenToClient(hTree, &hti.pt);
+ TreeView_HitTest(hTree, &hti);
+ if (hti.flags & (TVHT_ONITEM | TVHT_ONITEMRIGHT)) {
+ HTREEITEM it=hti.hItem;
+ hti.pt.y -= TreeView_GetItemHeight(hTree)/2;
+ TreeView_HitTest(hTree, &hti);
+ if (!(hti.flags&TVHT_ABOVE))
+ TreeView_SetInsertMark(hTree,hti.hItem,1);
+ else
+ TreeView_SetInsertMark(hTree,it,0);
+ }
+ else {
+ if (hti.flags & TVHT_ABOVE) SendMessage(hTree, WM_VSCROLL, MAKEWPARAM(SB_LINEUP, 0), 0);
+ if (hti.flags & TVHT_BELOW) SendMessage(hTree, WM_VSCROLL, MAKEWPARAM(SB_LINEDOWN, 0), 0);
+ TreeView_SetInsertMark(hTree, NULL, 0);
+ }
+ }
+ break;
+
+ case WM_LBUTTONUP:
+ if (dat->dragging) {
+ TreeView_SetInsertMark(hTree, NULL, 0);
+ dat->dragging = 0;
+ ReleaseCapture();
+
+ TVHITTESTINFO hti;
+ hti.pt.x = (short)LOWORD(lParam);
+ hti.pt.y = (short)HIWORD(lParam);
+ ClientToScreen(hwndDlg, &hti.pt);
+ ScreenToClient(hTree, &hti.pt);
+ hti.pt.y -= TreeView_GetItemHeight(hTree)/2;
+ TreeView_HitTest(hTree, &hti);
+ if (dat->hDragItem == hti.hItem)
+ break;
+ if (hti.flags&TVHT_ABOVE)
+ hti.hItem=TVI_FIRST;
+
+ TVITEM tvi;
+ tvi.mask = TVIF_HANDLE|TVIF_PARAM;
+ tvi.hItem = (HTREEITEM) dat->hDragItem;
+ TreeView_GetItem(hTree, &tvi);
+ if ( (hti.flags & (TVHT_ONITEM | TVHT_ONITEMRIGHT)) || (hti.hItem==TVI_FIRST)) {
+ TVINSERTSTRUCT tvis;
+ TCHAR name[128];
+ tvis.item.mask = TVIF_HANDLE | TVIF_PARAM | TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_STATE;
+ tvis.item.stateMask = 0xFFFFFFFF;
+ tvis.item.pszText = name;
+ tvis.item.cchTextMax = SIZEOF(name);
+ tvis.item.hItem = dat->hDragItem;
+ TreeView_GetItem(hTree, &tvis.item);
+
+ TreeView_DeleteItem(hTree, dat->hDragItem);
+ tvis.hParent = NULL;
+ tvis.hInsertAfter = hti.hItem;
+ TreeView_SelectItem(hTree, TreeView_InsertItem(hTree, &tvis));
+
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+ }
+ }
+ break;
+
+ case WM_DESTROY:
+ if (dat) {
+ ImageList_Destroy(dat->himlButtonIcons);
+ free(dat);
+ }
+ OptionshWnd = NULL;
+ break;
+ }
+ return FALSE;
+}
+
+/////////////////////////////////////////////////////////////////////////////////////////
+
+int TTBOptInit(WPARAM wParam, LPARAM lParam)
+{
+ OPTIONSDIALOGPAGE odp = { 0 };
+ odp.cbSize = sizeof(odp);
+ odp.hInstance = hInst;
+ odp.pszGroup = LPGEN("Contact List");
+
+ odp.position = -1000000000;
+ odp.pszTemplate = MAKEINTRESOURCEA(IDD_OPT_BUTORDER);
+ odp.pszTitle = LPGEN("Toolbar");
+ odp.pfnDlgProc = ButOrderOpts;
+ odp.flags = ODPF_BOLDGROUPS | ODPF_EXPERTONLY;
+ Options_AddPage(wParam, &odp);
+ return 0;
+}
diff --git a/plugins/TopToolBar/src/version.h b/plugins/TopToolBar/src/version.h new file mode 100644 index 0000000000..9a489eebee --- /dev/null +++ b/plugins/TopToolBar/src/version.h @@ -0,0 +1,46 @@ +/*
+
+Miranda IM: the free IM client for Microsoft* Windows*
+
+Copyright 2000-2008 Miranda ICQ/IM project,
+all portions of this codebase are copyrighted to the people
+listed in contributors.txt.
+
+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.
+*/
+
+#define __MAJOR_VERSION 0
+#define __MINOR_VERSION 8
+#define __RELEASE_NUM 0
+#define __BUILD_NUM 1
+
+// other stuff for Version resource
+#define __STRINGIFY_IMPL(x) #x
+#define __STRINGIFY(x) __STRINGIFY_IMPL(x)
+
+#define __FILEVERSION_STRING __MAJOR_VERSION,__MINOR_VERSION,__RELEASE_NUM,__BUILD_NUM
+#define __FILEVERSION_STRING_DOTS __MAJOR_VERSION.__MINOR_VERSION.__RELEASE_NUM.__BUILD_NUM
+#define __VERSION_STRING __STRINGIFY(__FILEVERSION_STRING_DOTS)
+
+#define __PLUGIN_DESC "ToptoolBar adds buttons in top frame for fast access."
+#define __PLUGIN_LONGDESC __PLUGIN_DESC
+#define __PLUGIN_AUTHOR "Bethoven"
+#define __PLUGIN_AUTHORWEB "http://nightly.miranda.im/"
+#define __PLUGIN_EMAIL "Bethoven@mailgate.ru"
+#define __PLUGIN_RIGHTS "© 2003-2008 Bethoven"
+#define __PLUGIN_FILE "TopToolbar.dll"
+#define __PLUGIN_SHORTNAME "TopToolBar"
+
+#define __PLUGIN_NAME __PLUGIN_SHORTNAME
|