📄 mouse.c
字号:
/*
* ReactOS
* Copyright (C) 2004 ReactOS Team
*
* 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., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* $Id: mouse.c 24031 2006-09-10 16:32:37Z fireball $
*
* PROJECT: ReactOS Main Control Panel
* FILE: lib/cpl/main/mouse.c
* PURPOSE: Mouse Control Panel
* PROGRAMMER: Eric Kohl
* Johannes Anderwald
*/
//TODO:
//detect slider changes - for apply stuff
//implement Double-Click Speed measuring
// cursor icon shows - may need overriden items
// implement Pointer-APPLY
// implement Pointer-Browser
// add missing icons
// Options- pointer precision
#define WINVER 0x0501
#include <windows.h>
#include <winuser.h>
#include <devguid.h>
#include <commctrl.h>
#include <cpl.h>
#include <tchar.h>
#include <math.h>
#include <limits.h>
#include "main.h"
#include "resource.h"
#define DEFAULT_DOUBLE_CLICK_SPEED 500
#define DEFAULT_CLICK_LOCK_TIME 2200
#define DEFAULT_MOUSE_SENSITIVITY 16
#define DEFAULT_MOUSE_THRESHOLD1 6
#define DEFAULT_MOUSE_THRESHOLD2 10
#define MIN_DOUBLE_CLICK_SPEED 200
#define MAX_DOUBLE_CLICK_SPEED 900
#define DEFAULT_WHEEL_SCROLL_LINES 3
ULONG g_Initialized = 0;
UINT g_WheelScrollLines = 5;
ULONG g_SwapMouseButtons = 0;
ULONG g_DoubleClickSpeed = DEFAULT_DOUBLE_CLICK_SPEED;
BOOL g_ClickLockEnabled = 0;
BOOL g_DropShadow = 0;
DWORD g_ClickLockTime = DEFAULT_CLICK_LOCK_TIME;
ULONG g_MouseSensitivity = DEFAULT_MOUSE_SENSITIVITY;
ULONG g_MouseSpeed = 1;
ULONG g_MouseThreshold1 = DEFAULT_MOUSE_THRESHOLD1;
ULONG g_MouseThreshold2 = DEFAULT_MOUSE_THRESHOLD2;
ULONG g_SnapToDefaultButton = 0;
ULONG g_MouseTrails = 0;
ULONG g_ShowPointer = 0;
ULONG g_HidePointer = 0;
ULONG g_ApplyCount = 0;
TCHAR g_CurrentScheme[MAX_PATH];
TCHAR g_szArrow[MAX_PATH];
TCHAR g_szHelp[MAX_PATH];
TCHAR g_szAppStarting[MAX_PATH];
TCHAR g_szWait[MAX_PATH];
TCHAR g_szCrosshair[MAX_PATH];
TCHAR g_szIBeam[MAX_PATH];
TCHAR g_szNWPen[MAX_PATH];
TCHAR g_szNo[MAX_PATH];
TCHAR g_szSizeNS[MAX_PATH];
TCHAR g_szSizeWE[MAX_PATH];
TCHAR g_szSizeNWSE[MAX_PATH];
TCHAR g_szSizeNESW[MAX_PATH];
TCHAR g_szSizeAll[MAX_PATH];
TCHAR g_szUpArrow[MAX_PATH];
TCHAR g_szHand[MAX_PATH];
TCHAR g_szNewScheme[MAX_PATH];
/* Property page dialog callback */
static INT_PTR CALLBACK
MouseHardwareProc(IN HWND hwndDlg,
IN UINT uMsg,
IN WPARAM wParam,
IN LPARAM lParam)
{
GUID Guids[1];
Guids[0] = GUID_DEVCLASS_MOUSE;
UNREFERENCED_PARAMETER(lParam);
UNREFERENCED_PARAMETER(wParam);
switch(uMsg)
{
case WM_INITDIALOG:
{
/* create the hardware page */
DeviceCreateHardwarePageEx(hwndDlg,
Guids,
sizeof(Guids) / sizeof(Guids[0]),
HWPD_STANDARDLIST);
break;
}
}
return FALSE;
}
BOOL InitializeMouse()
{
/* mouse trails */
SystemParametersInfo(SPI_GETMOUSETRAILS, 0, &g_MouseTrails, 0);
/* snap to default button */
SystemParametersInfo(SPI_GETSNAPTODEFBUTTON, 0, &g_SnapToDefaultButton, 0);
/* wheel scroll lines */
SystemParametersInfo(SPI_GETWHEELSCROLLLINES, 0, &g_WheelScrollLines, 0);
//FIXME
//pointer precision
// SPI_GETMOUSE?
/* mouse sensitivity */
SystemParametersInfo(SPI_GETMOUSESPEED, 0, &g_MouseSensitivity, 0);
/* hide pointer while typing */
SystemParametersInfo(SPI_GETMOUSEVANISH, 0, &g_HidePointer, 0);
/* click lock time */
SystemParametersInfo(SPI_GETMOUSECLICKLOCK, 0, &g_ClickLockEnabled, 0);
SystemParametersInfo(SPI_GETMOUSECLICKLOCKTIME, 0, &g_ClickLockTime, 0);
g_DoubleClickSpeed = GetDoubleClickTime();
g_SwapMouseButtons = GetSystemMetrics(SM_SWAPBUTTON);
/* show pointer with Ctrl-Key */
SystemParametersInfo(SPI_GETMOUSESONAR, 0, &g_ShowPointer, 0);
return TRUE;
}
static INT_PTR CALLBACK
ClickLockProc(IN HWND hwndDlg,
IN UINT uMsg,
IN WPARAM wParam,
IN LPARAM lParam)
{
HWND hDlgCtrl;
int pos;
UNREFERENCED_PARAMETER(lParam);
switch(uMsg)
{
case WM_INITDIALOG:
{
hDlgCtrl = GetDlgItem(hwndDlg, IDC_SLIDER_CLICK_LOCK);
SendMessage(hDlgCtrl, TBM_SETRANGE, (WPARAM)TRUE, (LPARAM)MAKELONG(0, 10));
pos = (g_ClickLockTime-200) / 200;
SendMessage(hDlgCtrl, TBM_SETPOS, (WPARAM)TRUE, (LPARAM)pos);
return TRUE;
}
case WM_COMMAND:
{
if (LOWORD(wParam) == IDOK)
{
hDlgCtrl = GetDlgItem(hwndDlg, IDC_SLIDER_CLICK_LOCK);
g_ClickLockTime = (DWORD) (SendMessage(hDlgCtrl, TBM_GETPOS, 0, 0) * 200) + 200;
EndDialog(hwndDlg, TRUE);
}
else if (LOWORD(wParam) == IDCANCEL)
{
EndDialog(hwndDlg, FALSE);
}
}
}
return FALSE;
}
static INT_PTR CALLBACK
ButtonProc(IN HWND hwndDlg,
IN UINT uMsg,
IN WPARAM wParam,
IN LPARAM lParam)
{
HWND hDlgCtrl;
LRESULT lResult;
float pos;
LPPSHNOTIFY lppsn;
switch(uMsg)
{
case WM_INITDIALOG:
{
if (InitializeMouse())
{
if (g_SwapMouseButtons)
{
hDlgCtrl = GetDlgItem(hwndDlg, IDC_SWAP_MOUSE_BUTTONS);
SendMessage(hDlgCtrl, BM_SETCHECK, (WPARAM)BST_CHECKED, (LPARAM)0);
}
if (g_ClickLockEnabled)
{
hDlgCtrl = GetDlgItem(hwndDlg, IDC_CHECK_CLICK_LOCK);
SendMessage(hDlgCtrl, BM_SETCHECK, (WPARAM)BST_CHECKED, (LPARAM)0);
}
else
{
hDlgCtrl = GetDlgItem(hwndDlg, IDC_BUTTON_CLICK_LOCK);
EnableWindow(hDlgCtrl, FALSE);
}
hDlgCtrl = GetDlgItem(hwndDlg, IDC_SLIDER_DOUBLE_CLICK_SPEED);
SendMessage(hDlgCtrl, TBM_SETRANGE, (WPARAM)TRUE, (LPARAM)MAKELONG(0, 14));
pos = ((float)g_DoubleClickSpeed / MAX_DOUBLE_CLICK_SPEED);
pos /= (1.0f/11.0f);
SendMessage(hDlgCtrl, TBM_SETPOS, (WPARAM)TRUE, (LPARAM)(INT)ceil(pos));
}
return TRUE;
}
case WM_COMMAND:
{
switch(LOWORD(wParam))
{
case IDC_SWAP_MOUSE_BUTTONS:
{
lResult = SendMessage((HWND)lParam, BM_GETCHECK, (WPARAM)0, (LPARAM)0);
if (lResult == BST_CHECKED)
{
g_SwapMouseButtons = FALSE;
SendMessage((HWND)lParam, BM_SETCHECK, (WPARAM)BST_UNCHECKED, (LPARAM)0);
}
else if (lResult == BST_UNCHECKED)
{
g_SwapMouseButtons = TRUE;
SendMessage((HWND)lParam, BM_SETCHECK, (WPARAM)BST_CHECKED, (LPARAM)0);
}
break;
}
case IDC_CHECK_CLICK_LOCK:
{
lResult = SendMessage((HWND)lParam, BM_GETCHECK, (WPARAM)0, (LPARAM)0);
hDlgCtrl = GetDlgItem(hwndDlg, IDC_BUTTON_CLICK_LOCK);
if (lResult == BST_CHECKED)
{
SendMessage((HWND)lParam, BM_SETCHECK, (WPARAM)BST_UNCHECKED, (LPARAM)0);
g_ClickLockEnabled = FALSE;
EnableWindow(hDlgCtrl, FALSE);
}
else if (lResult == BST_UNCHECKED)
{
SendMessage((HWND)lParam, BM_SETCHECK, (WPARAM)BST_CHECKED, (LPARAM)0);
EnableWindow(hDlgCtrl, TRUE);
g_ClickLockEnabled = TRUE;
}
break;
}
case IDC_BUTTON_CLICK_LOCK:
{
lResult = DialogBox(hApplet, MAKEINTRESOURCE(IDD_CLICK_LOCK), hwndDlg, ClickLockProc);
if ((INT)lResult == FALSE)
return FALSE; // no need to enable apply button
break;
}
}
PropSheet_Changed(GetParent(hwndDlg), hwndDlg);
break;
}
case WM_NOTIFY:
{
lppsn = (LPPSHNOTIFY) lParam;
if (lppsn->hdr.code == PSN_APPLY)
{
/* apply swap mouse button */
SystemParametersInfo(SPI_SETMOUSEBUTTONSWAP, g_SwapMouseButtons, NULL, SPIF_SENDCHANGE);
/* apply double click speed */
hDlgCtrl = GetDlgItem(hwndDlg, IDC_SLIDER_DOUBLE_CLICK_SPEED);
lResult = SendMessage(hDlgCtrl, TBM_GETPOS, 0, 0);
g_DoubleClickSpeed = (INT)lResult * 50 + 200;
SystemParametersInfo(SPI_SETDOUBLECLICKTIME, g_DoubleClickSpeed, NULL, SPIF_SENDCHANGE);
#if (WINVER >= 0x0500)
SystemParametersInfo(SPI_SETMOUSECLICKLOCK, g_ClickLockEnabled, NULL, SPIF_SENDCHANGE);
if (g_ClickLockEnabled)
SystemParametersInfo(SPI_SETMOUSECLICKLOCKTIME, g_ClickLockTime, NULL, SPIF_SENDCHANGE);
#endif
SetWindowLong(hwndDlg, DWL_MSGRESULT, PSNRET_NOERROR);
return TRUE;
}
}
case WM_DRAWITEM:
{
LPDRAWITEMSTRUCT drawItem;
drawItem = (LPDRAWITEMSTRUCT)lParam;
if(drawItem->CtlID == IDC_IMAGE_SWAP_MOUSE)
{
//FIXME
//show mouse with left/right button highlighted
// depending on val g_SwapMouseButtons
return TRUE;
}
else if (drawItem->CtlID == IDC_IMAGE_DOUBLE_CLICK_SPEED)
{
//FIXME
//measure click speed && draw item
}
break;
}
case WM_HSCROLL:
{
PropSheet_Changed(GetParent(hwndDlg), hwndDlg);
break;
}
}
return FALSE;
}
BOOL ReadActiveCursorScheme()
{
HKEY hCuKey;
HKEY hCuCursorKey;
DWORD dwIndex;
TCHAR szValueName[MAX_PATH];
DWORD dwValueName;
TCHAR szValueData[2000];
DWORD dwValueData;
LONG dwResult;
if (RegOpenCurrentUser(KEY_READ, &hCuKey) != ERROR_SUCCESS)
return FALSE;
if (RegOpenKeyEx(hCuKey, _T("Control Panel\\Cursors"), 0, KEY_READ, &hCuCursorKey) != ERROR_SUCCESS)
{
RegCloseKey(hCuKey);
return FALSE;
}
memset(g_szArrow, 0x0, sizeof(g_szArrow));
memset(g_szHelp, 0x0, sizeof(g_szHelp));
memset(g_szAppStarting, 0x0, sizeof(g_szAppStarting));
memset(g_szWait, 0x0, sizeof(g_szWait));
memset(g_szCrosshair, 0x0, sizeof(g_szCrosshair));
memset(g_szIBeam, 0x0, sizeof(g_szIBeam));
memset(g_szNWPen, 0x0, sizeof(g_szNWPen));
memset(g_szNo, 0x0, sizeof(g_szNo));
memset(g_szSizeNS, 0x0, sizeof(g_szSizeNS));
memset(g_szSizeWE, 0x0, sizeof(g_szSizeWE));
memset(g_szSizeNWSE, 0x0, sizeof(g_szSizeNWSE));
memset(g_szSizeNESW, 0x0, sizeof(g_szSizeNESW));
memset(g_szSizeAll, 0x0, sizeof(g_szSizeAll));
memset(g_szUpArrow, 0x0, sizeof(g_szUpArrow));
memset(g_szHand, 0x0, sizeof(g_szHand));
dwIndex = 0;
do
{
dwValueName = sizeof(szValueName) / sizeof(TCHAR);
dwValueData = sizeof(szValueData) / sizeof(TCHAR);
dwResult = RegEnumValue(hCuCursorKey, dwIndex, szValueName, &dwValueName, NULL, NULL, (LPBYTE)szValueData, &dwValueData);
if (dwResult == ERROR_NO_MORE_ITEMS)
break;
if (_tcsicmp(_T("Arrow"), szValueName))
_tcsncpy(g_szArrow, szValueData, MAX_PATH);
else if (_tcsicmp(_T("Help"), szValueName))
_tcsncpy(g_szHelp, szValueData, MAX_PATH);
else if (_tcsicmp(_T("AppStarting"), szValueName))
_tcsncpy(g_szAppStarting, szValueData, MAX_PATH);
else if (_tcsicmp(_T("Wait"), szValueName))
_tcsncpy(g_szWait, szValueData, MAX_PATH);
else if (_tcsicmp(_T("Crosshair"), szValueName))
_tcsncpy(g_szCrosshair, szValueData, MAX_PATH);
else if (_tcsicmp(_T("IBeam"), szValueName))
_tcsncpy(g_szIBeam, szValueData, MAX_PATH);
else if (_tcsicmp(_T("NWPen"), szValueName))
_tcsncpy(g_szNWPen, szValueData, MAX_PATH);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -