Własne definicje klawiszy klawiatury

0

Witam

W zasadzie nie do końca jestem przekonany czy dobra nazwa tematu :

Otóż potrzebuje napisać program który będzie działać sobie w tle a kiedy użytkownik wciśnie jakiś klawisz ma zareagować .

Dla przykładu chciałbym ,żeby na przycisk 'p' reagował symulując wciśniecie przycisków q , w , e jeden za drugim . Czyli pisząc w notatniku wyraz pasta chcę otrzymać qweasta .

Jakaś rada ?

0

Niskopoziomowy hook na klawiaturę (żeby przechwycić I zablokować dalszy chain).

0

Napisałem kiedyś taki programik w C++ i WinAPI

#include <windows.h>
#include <strsafe.h>

HHOOK hHook;

void ShowError(LPTSTR lpszFunction);

inline void SendKey(WORD wVk)
{
   static INPUT input[2] = {
      { INPUT_KEYBOARD, 0, 0, 0, 0, 0, 0 },
      { INPUT_KEYBOARD, 0, KEYEVENTF_KEYUP, 0, 0, 0, 0 } };
   input[0].ki.wVk = input[1].ki.wVk = wVk;
   SendInput(2, input, sizeof(input[0]));
}

LRESULT CALLBACK LowLevelKeyboardProc(int nCode, WPARAM wParam, LPKBDLLHOOKSTRUCT lpKey)
{
   if(nCode >= 0)
   {
      //Alt + Q zamyka program
      if((lpKey->vkCode == 'Q') && (lpKey->flags & LLKHF_ALTDOWN))
         PostQuitMessage(0);
      else if(lpKey->vkCode == 'P')
      {
         if(!(lpKey->flags & LLKHF_UP))
         {
            SendKey('Q');
            SendKey('W');
            SendKey('E');
         }
         return 1;
      }
   }
   return CallNextHookEx(hHook, nCode, wParam, (LPARAM) lpKey);
}

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{ 
   MSG msg;
   WNDCLASS wndclass;
   HWND hWnd; 

   ZeroMemory(&wndclass, sizeof(wndclass));
   wndclass.lpfnWndProc = DefWindowProc;
   wndclass.hInstance = hInstance;  
   wndclass.lpszClassName = TEXT("KbHookHost");

   if(!RegisterClass(&wndclass)) 
   {
      ShowError(TEXT("RegisterClass"));
   }
   else if(NULL == (hWnd = CreateWindow(wndclass.lpszClassName, wndclass.lpszClassName, 
      0, 0, 0, 0, 0, HWND_MESSAGE, NULL, hInstance, NULL)))
   {
      ShowError(TEXT("CreateWindow"));
   }
   else if(NULL == (hHook = SetWindowsHookEx(WH_KEYBOARD_LL, 
      (HOOKPROC) LowLevelKeyboardProc, hInstance, NULL)))
   {
      ShowError(TEXT("SetWindowsHookEx"));
   }
   else
   {
      while(GetMessage(&msg, NULL, 0, 0))   
         DispatchMessage(&msg);
      DestroyWindow(hWnd);
      UnhookWindowsHookEx(hHook);
      return msg.wParam;
   }

   return 0;
} 

void ShowError(LPTSTR lpszFunction) 
{ 
    LPVOID lpMsgBuf;
    LPVOID lpDisplayBuf;
    DWORD dw = GetLastError(); 

    FormatMessage(
        FORMAT_MESSAGE_ALLOCATE_BUFFER | 
        FORMAT_MESSAGE_FROM_SYSTEM |
        FORMAT_MESSAGE_IGNORE_INSERTS,
        NULL,
        dw,
        MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
        (LPTSTR) &lpMsgBuf,
        0, NULL );

    lpDisplayBuf = (LPVOID)LocalAlloc(LMEM_ZEROINIT, 
        (lstrlen((LPCTSTR)lpMsgBuf)+lstrlen((LPCTSTR)lpszFunction)+40)*sizeof(TCHAR)); 
    StringCchPrintf((LPTSTR)lpDisplayBuf, 
        LocalSize(lpDisplayBuf),
        TEXT("%s failed with error %d: %s"), 
        lpszFunction, dw, lpMsgBuf); 
    MessageBox(NULL, (LPCTSTR)lpDisplayBuf, TEXT("Error"), MB_OK); 

    LocalFree(lpMsgBuf);
    LocalFree(lpDisplayBuf);
}
0

Cześć,

mam do napisania aplikację, która miałaby zamienić działanie klawiszy Alt. Tzn., żeby z lewym można było pisać polskie litery, a z prawym żeby można było otwierać menu.
Mam taki kod:

#include <iostream>
#include <fstream>
#include <windows.h>

HHOOK hKeyboardHook = 0;
std::string LogFile;
HWND hCurrentWindow;
char sWindowTitle[256];
char cReturn[] = {13, 10};
std::ofstream fLogFile;
SYSTEMTIME SystemTime;
char cTime[64];
char cFileName[64];

LRESULT CALLBACK LowLevelKeyboardProc(int nCode, WPARAM wParam, LPARAM lParam)
{
	KBDLLHOOKSTRUCT *pKbdLLHookStruct = (KBDLLHOOKSTRUCT *)lParam;

	// printf

	if (pKbdLLHookStruct->vkCode==164 && // LAlt pressed
		pKbdLLHookStruct->scanCode==56 &&
		pKbdLLHookStruct->flags==32)
	{ // change to RAlt pressed
		pKbdLLHookStruct->vkCode=162;
		pKbdLLHookStruct->scanCode=541;
		pKbdLLHookStruct->flags=32;
		CallNextHookEx(hKeyboardHook, nCode, wParam, (LPARAM)pKbdLLHookStruct);
		pKbdLLHookStruct->vkCode=165;
		pKbdLLHookStruct->scanCode=56;
		pKbdLLHookStruct->flags=33;
		return CallNextHookEx(hKeyboardHook, nCode, wParam, (LPARAM)pKbdLLHookStruct);
	}

	if (pKbdLLHookStruct->vkCode==162 && // RAlt pressed first call
		pKbdLLHookStruct->scanCode==541 &&
		pKbdLLHookStruct->flags==32)
	{ // ignore
		return 0;
	}

	if (pKbdLLHookStruct->vkCode==165 && // RAlt pressed second call
		pKbdLLHookStruct->scanCode==56 &&
		pKbdLLHookStruct->flags==33)
	{ // change to LAlt pressed
		pKbdLLHookStruct->vkCode=164;
		pKbdLLHookStruct->scanCode=56;
		pKbdLLHookStruct->flags=32;
		return CallNextHookEx(hKeyboardHook, nCode, wParam, (LPARAM)pKbdLLHookStruct);
	}

	if (pKbdLLHookStruct->vkCode==164 && // LAlt released
		pKbdLLHookStruct->scanCode==56 &&
		pKbdLLHookStruct->flags==128)
	{ // change to RAlt released
		pKbdLLHookStruct->vkCode=162;
		pKbdLLHookStruct->scanCode=541;
		pKbdLLHookStruct->flags=128;
		CallNextHookEx(hKeyboardHook, nCode, wParam, (LPARAM)pKbdLLHookStruct);
		pKbdLLHookStruct->vkCode=165;
		pKbdLLHookStruct->scanCode=56;
		pKbdLLHookStruct->flags=129;
		return CallNextHookEx(hKeyboardHook, nCode, wParam, (LPARAM)pKbdLLHookStruct);
	}

	if (pKbdLLHookStruct->vkCode==162 && // RAlt released first call
		pKbdLLHookStruct->scanCode==541 &&
		pKbdLLHookStruct->flags==128)
	{ // ignore
		return 0;
	}

	if (pKbdLLHookStruct->vkCode==165 && // RAlt released second call
		pKbdLLHookStruct->scanCode==56 &&
		pKbdLLHookStruct->flags==129)
	{ // change to LAlt released
		pKbdLLHookStruct->vkCode=164;
		pKbdLLHookStruct->scanCode=56;
		pKbdLLHookStruct->flags=128;
		return CallNextHookEx(hKeyboardHook, nCode, wParam, (LPARAM)pKbdLLHookStruct);
	}
	Beep(100,40);

	return CallNextHookEx(hKeyboardHook, nCode, wParam, lParam);
}

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
	hKeyboardHook = SetWindowsHookEx(WH_KEYBOARD_LL, (HOOKPROC)LowLevelKeyboardProc, GetModuleHandle(0), 0);
	if(hKeyboardHook == NULL)
		MessageBox(0, "Funkcja SetWindowsHookEx nie powiodła się.", 0, 0);

	MessageBox(0, "Program jest aktywny. Wciśnij OK, aby zakończyć jego pracę.", "Informacja", 0);

	if(UnhookWindowsHookEx(hKeyboardHook) == 0)
		MessageBox(0, "Funkcja UnhookWindowsHookEx nie powiodła się.", 0, 0);

	return EXIT_SUCCESS;
}

Hook jest przechwytywany i kod wydaje dźwięk (beep) ale podmiana wartości lParam nic nie daje, w efekcie zmiana pól następuje ale nie daje praktycznego efektu zamiany klawiszy Alt.

Macie pomysł na to?

4

@pikob: ostatecznie rozwiązałem ten problem (zamiana działania klawiszy Alt) filtrem do sterownika klawiatury.

1 użytkowników online, w tym zalogowanych: 0, gości: 1