PC SOFT

FORUMS PROFESSIONNELS
WINDEVWEBDEV et WINDEV Mobile

Accueil → WINDEV (précédentes versions) → [WD14] Touches Enfoncées
[WD14] Touches Enfoncées
Débuté par Marie Anthony, 01 sep. 2010 19:00 - 9 réponses
Posté le 01 septembre 2010 - 19:00
Bonjour à tous,

J'ai parcouru le forum et je n'ai pas trouvé de réponse alors je vais vous poser mon problème en espérant trouver une aide précieuse.

J'ai besoin d'enregistrer les touches du claviers qui sont enfoncées, mais cela hors de mon application. Le plus simplement possible.

En espérant avoir des réponses pouvant m'aider. Je reste à votre disposition si vous voulez d'avantage de détails.

Merci
Posté le 02 septembre 2010 - 08:51
bonjour,

heu ce n'est pas si simple pour récupérer les touches enfoncées dans d'autres applications. Il faut utiliser ce qu'on appelle un hook clavier et pour cela utiliser des API windows. Voici un petit exemple que j'ai bricolé (vite fait sur le gaz) qui est loin d'être parfait. En effet la procédure hookeuse ne distingue pas les minuscules des majuscules (shift) et doit avoir bien d'autres défauts :-(

1 - il faut déclarer quelques constantes et structure dans le code du projet (initialisation du projet :

CONSTANTE
HC_ACTION=0//0
WH_JOURNALRECORD = 0
WH_JOURNALPLAYBACK = 1
WH_KEYBOARD = 2
WH_GETMESSAGE = 3
WH_CALLWNDPROC = 4
WH_CBT = 5
WH_SYSMSGFILTER = 6
WH_MOUSE = 7
WH_HARDWARE = 8
WH_DEBUG = 9
WH_SHELL = 10
WH_FOREGROUNDIDLE = 11
WH_CALLWNDPROCRET = 12
WH_KEYBOARD_LL = 13
WH_MOUSE_LL = 14
WM_KEYDOWN=256//0x0100

FIN
KBDLLHOOKSTRUCT est une structure
vkCode est un entier
scanCode est un entier
flags est un entier
time est un entier
dwExtraInfo est un entier
FIN
gnHandleHook est un entier // handle du hook


ensuite pour mettre en oeuvre le hook il faut un code du genre :
// Procédure_Hookeuse est la procédure appelée à chaque hook clavier
gnHandleHook = API("User32", "SetWindowsHookExA", WH_KEYBOARD_LL, &Procédure_Hookeuse, Instance(), 0)


pour terminer de hooker le clavier un code du type:
SI PAS API("user32","UnhookWindowsHookEx",gnHandleHook) ALORS
Erreur("erreur de désinstallation du hook ")
FIN


et voici un exemple de procédure de hook qu'il faudra déclarer comme procédure globale
Procedure Procédure_Hookeuse(ncode,wparam,lparam)
clavier est un KBDLLHOOKSTRUCT
KeyState est un tableau fixe de 256 entiers sans signe sur 1 octet
RetourFonction est un entier
MonChar est un caractère

SI ncode = HC_ACTION ALORS
// Sur touche enfoncée uniquement
SI wparam <> WM_KEYDOWN ALORS
RENVOYER API("user32","CallNextHookEx",gnHandleHook, ncode, wparam, lparam)
FIN
Transfert(&clavier,lparam,20) // transfert de la structure ( méthode peu recommandable avez-vous mieux ? cast?)
RetourFonction=API("USER32","GetKeyboardState",&KeyState)
RetourFonction=API("USER32","ToAscii",clavier:vkCode,clavier:scanCode,&KeyState,&MonChar,0)

Fenêtre1.Memo += MonChar // Memo est un champ de saisie qui affiche les caractères tapés

FIN

// Renvoie la suite du hook afin de permettre le traitement de l'appui par la fenetre d'origine
RENVOYER API("user32","CallNextHookEx",gnHandleHook, ncode, wparam, lparam)


si quelqu'un peut améliorer ce code qu'il en fasse profiter tout le monde :-)


Ami calmant, J.P ;-)
Posté le 02 septembre 2010 - 12:49
Merci beaucoup pour cette réponse.
En effet ça n'a pas l'air simple du tout.

Petites questions :


// Procédure_Hookeuse est la procédure appelée à chaque hook clavier
gnHandleHook = API("User32", "SetWindowsHookExA", WH_KEYBOARD_LL, &Procédure_Hookeuse, Instance(), 0)

SI PAS API("user32","UnhookWindowsHookEx",gnHandleHook) ALORS
Erreur("erreur de désinstallation du hook ")
FIN

Où mettre ces lignes de codes ? Dans l'initialisation du projet ?

Merci ;)
Posté le 02 septembre 2010 - 14:01
bonjour,

ce code :
gnHandleHook = API("User32", "SetWindowsHookExA", WH_KEYBOARD_LL, &Procédure_Hookeuse, Instance(), 0)

tu le mets à l'initialisation si tu veux "hooker" dès le lancement de ton programme

et celui là :
SI PAS API("user32","UnhookWindowsHookEx",gnHandleHook) ALORS
Erreur("erreur de désinstallation du hook ")
FIN

à la fermeture de ton application ou par un bouton pour arrêter le hook.

Ami calmant, J.P ;-)
Posté le 03 septembre 2010 - 12:41
Merci pour ces explications et de ta réactivité ;)

Je vais essayer avec ça et je te tiens au courant.

Merci
Posté le 15 septembre 2010 - 13:53
Ca marche très bien.

Un grand merci pour ton aide et ta rapidité. Ca m'a bien dépanné.

Encore Merci
Posté le 16 septembre 2010 - 18:55
Bonjour,
C'est encore moi, j'ai quelques question car je ne maitrise pas du tout l'utilisation des touches clavier et j'aimerai savoir comment maitrisé les caractères envoyés par le clavier.
Par exemple quand j'appuie sur la touche d'effacement cela n'efface pas.

Et si un caractère n'apparait pas comme je veux, comment faire ?


Merci
Posté le 19 septembre 2010 - 23:50
Bonjour,

Pas de réponses ce coup çi :(
J'ai quelques soucis concernant certaines touches.
Quand je sors de ma fenetre de projet la touche shift n'est plus reconnue (avec tout les soucis que cela peux poser au niveau des caractères).

Est ce que quelqu'un à une solution à proposer ?

Merci par avance
Posté le 20 septembre 2010 - 17:59
Je n'arrive pas à trouver, si quelqu'un peut m'aider ...

Merci
Posté le 23 septembre 2010 - 09:02
bonjour,
j'ai trouvé une solution pour le shift :

dans les constantes il faut rajouter :
VK_SHIFT=16


et la procédure hookeuse devient :
Procedure Procédure_Hookeuse(ncode,wparam,lparam)
clavier est un KBDLLHOOKSTRUCT
KeyState est un tableau fixe de 256 entiers sans signe sur 1 octet
MonCharEx est un tableau fixe de 2 caractères
RetourFonction est un entier
vk est un entier sans signe
//MonChar est un caractère
keylayout est un entier
tailleChar est un entier
x est un entier

SI ncode = HC_ACTION ALORS
// Sur touche enfoncé uniquement
SI wparam <> WM_KEYDOWN ALORS
RENVOYER API("user32","CallNextHookEx",gnHandleHook, ncode, wparam, lparam)
FIN
Transfert(&clavier,lparam,Dimension(clavier)) // transfert de la structure ( méthode peu recommandable avez-vous mieux ? cast?)
keylayout=API("USER32","GetKeyboardLayout",0)
RetourFonction=API("USER32","GetKeyboardState",&KeyState)
vk = API("USER32","MapVirtualKeyExA",clavier:scanCode,1,keylayout)
// on place l'état de la touche Shift dans le tableau des états des touches
KeyState[VK_SHIFT +1]= ETBinaire((API("USER32","GetAsyncKeyState",VK_SHIFT)/256),255)
//RetourFonction=API("USER32","ToAscii",clavier:vkCode,clavier:scanCode,&KeyState,&MonChar,0)
// on appelle ToAsciiEx plus balaise que ToAscii
tailleChar =API("USER32","ToAsciiEx",vk, clavier:scanCode,&KeyState,&MonCharEx, 0, keylayout)

POUR x = 1 A tailleChar
Fenêtre1.Memo += MonCharEx[x] // Memo est un champ de saisie qui affiche les caractères tapés
FIN

FIN

// Renvoie la suite du hook afin de permettre le traitement de l'appui par la fenetre d'origine
RENVOYER API("user32","CallNextHookEx",gnHandleHook, ncode, wparam, lparam)


Je ne sais pas si il y a plus simple, mais cela semble marcher sur mon PC. Toute contribution sera la bienvenue !

Ami calmant, J.P ;-)