Vous ne trouvez pas de réponse à votre problème ? Alors posez la question dans le forum. Souvenez-vous qu'il n'y a jamais de question bête, mais rester dans l'ignorance parce que l'on n'ose pas poser une question, ça c'est une erreur !

SENDKEYSEX => SIMULER UNE TOUCHE DANS UNE FENETRE PRÉCISE


Information sur la source

Catégorie :API Classé sous : sendkeys, autre, fenetre, hwnd, application Niveau : Débutant Date de création : 27/03/2007 Date de mise à jour : 14/05/2009 12:50:59 Vu / téléchargé: 9 485 / 1 221

Note :
9,14 / 10 - par 7 personnes
9,14 / 10

  • 1

  • 2

  • 3

  • 4

  • 5

  • 6

  • 7

  • 8

  • 9

  • 10

Commentaire sur cette source (25)
Ajouter un commentaire et/ou une note


Description

SendKeys, keybd_event & co c'est bien joli, seul souci majeur, on ne peut pas spécifier de fenêtre cible.
C'est donc un moyen particulièrement dangereux pour piloter précisément quoi que ce soit.

je crée souvent des applications de pilotage pour le boulot, j'ai donc décidé de me pencher sur le probleme...
 

Source

  • Public Sub SendString(ByVal vhTargetWnd As Long, ByRef vsInput As String)
  • Dim i As Long
  • Dim nRc As Integer
  • For i = 1 To Len(vsInput)
  • nRc = VkKeyScan(AscW(Mid$(vsInput, i, 1)))
  • If nRc <> -1 Then
  • SendKeysEx vhTargetWnd, nRc And &HFF&, nRc \ &H100&
  • End If
  • Next i
  • End Sub
  • Public Sub SendKeysEx(ByVal vhTargetWnd As Long, ByVal veKey As VBRUN.KeyCodeConstants, Optional ByVal veShift As VBRUN.ShiftConstants, Optional ByVal vbExtendedKey As Boolean = False)
  • Dim xbMemBuffer(255) As Byte
  • Dim xbNewBuffer(255) As Byte
  • Dim nKeyParam As Long
  • Dim nTargetThreadID As Long
  • '# Si la cible est valide...
  • If IsWindow(vhTargetWnd) Then
  • nTargetThreadID = GetWindowThreadProcessId(vhTargetWnd, ByVal 0&)
  • AttachThreadInput GetCurrentThreadId, nTargetThreadID, 1&
  • nKeyParam = MapVirtualKey(veKey, 0) * &H10000
  • If vbExtendedKey Then
  • nKeyParam = nKeyParam Or &H1000000 '# bit 24
  • End If
  • '# On mémorise l'etat du clavier
  • GetKeyboardState xbMemBuffer(0)
  • If (veShift And vbShiftMask) <> 0 Then
  • xbNewBuffer(vbKeyShift) = &H80
  • End If
  • If (veShift And vbCtrlMask) <> 0 Then
  • xbNewBuffer(vbKeyControl) = &H80
  • End If
  • '# On place notre image du clavier en mémoire
  • SetKeyboardState xbNewBuffer(0)
  • '# On prévient la cible que le clavier a été manipulé
  • PostMessage vhTargetWnd, WM_KEYDOWN, veKey, nKeyParam
  • PostMessage vhTargetWnd, WM_KEYUP, veKey, nKeyParam Or &HC0000000
  • '# On 'force' la cible a prendre en compte les changements effectués
  • Sleep 1
  • '# Il ne nous reste plus alors qu'a restaurer l'image du clavier.
  • SetKeyboardState xbMemBuffer(0)
  • AttachThreadInput GetCurrentThreadId, nTargetThreadID, 0&
  • End If
  • End Sub
Public Sub SendString(ByVal vhTargetWnd As Long, ByRef vsInput As String)
Dim i As Long
Dim nRc As Integer
    For i = 1 To Len(vsInput)
        nRc = VkKeyScan(AscW(Mid$(vsInput, i, 1)))
        If nRc <> -1 Then
            SendKeysEx vhTargetWnd, nRc And &HFF&, nRc \ &H100&
        End If
    Next i
End Sub

Public Sub SendKeysEx(ByVal vhTargetWnd As Long, ByVal veKey As VBRUN.KeyCodeConstants, Optional ByVal veShift As VBRUN.ShiftConstants, Optional ByVal vbExtendedKey As Boolean = False)
Dim xbMemBuffer(255) As Byte
Dim xbNewBuffer(255) As Byte
Dim nKeyParam As Long
Dim nTargetThreadID As Long
    '# Si la cible est valide...
    If IsWindow(vhTargetWnd) Then
        nTargetThreadID = GetWindowThreadProcessId(vhTargetWnd, ByVal 0&)
        AttachThreadInput GetCurrentThreadId, nTargetThreadID, 1&
        
        nKeyParam = MapVirtualKey(veKey, 0) * &H10000
        If vbExtendedKey Then
            nKeyParam = nKeyParam Or &H1000000 '# bit 24
        End If
    
        '# On mémorise l'etat du clavier
        GetKeyboardState xbMemBuffer(0)
        
        If (veShift And vbShiftMask) <> 0 Then
            xbNewBuffer(vbKeyShift) = &H80
        End If
        If (veShift And vbCtrlMask) <> 0 Then
            xbNewBuffer(vbKeyControl) = &H80
        End If
        
        '# On place notre image du clavier en mémoire
        SetKeyboardState xbNewBuffer(0)
            
        '# On prévient la cible que le clavier a été manipulé
        PostMessage vhTargetWnd, WM_KEYDOWN, veKey, nKeyParam
        PostMessage vhTargetWnd, WM_KEYUP, veKey, nKeyParam Or &HC0000000
        
        '# On 'force' la cible a prendre en compte les changements effectués
        Sleep 1
                
        '# Il ne nous reste plus alors qu'a restaurer l'image du clavier.
        SetKeyboardState xbMemBuffer(0)
        AttachThreadInput GetCurrentThreadId, nTargetThreadID, 0&
    End If
End Sub

Fichier Zip

Pour les "Membres Club", vous pouvez télécharger directement un fichier contenu dans le zip sans télécharger le zip en entier !

Télécharger le zip

Historique

28 mars 2007 00:06:16 :
SendMessage en lieu et place de PostMessage (afin de s'assurer que l'action a bien été traitée par la cible quand l'image du clavier est restaurée)
28 mars 2007 01:26:42 :
retour à PostMessage (j'aurais du tester, j'aurais du tester...)
28 mars 2007 01:40:51 :
Ajout d'une Form de démonstration
28 mars 2007 10:45:28 :
Ajout de la gestion des touches Shift, Control et des touches étendues (cf doc sur WM_KEYDOWN)
14 mai 2009 12:48:47 :
Ajout de la procédure SendString, qui permet de simuler la pression des touches nécessaires pour saisir une phrase donnée en parametre.
14 mai 2009 12:50:59 :
Changement de la description

Commentaires et avis

signaler à un administrateur
Commentaire de Renfield le 27/03/2007 18:08:18 administrateur CS

keybd_event (ou SendInput)est pas mal également,
mais dans le cas présent, je simule une pression de touche sur une appli en fond, afin de lui dire "je suis là"...

donc je ne peux pas faire de SetFocus(après un AttachThreadInput) etc, sinon ca ait apparaitre la fenetre cible au dessus de ma fenetre courante, ca clignotte... pas top, quoi ^^

signaler à un administrateur
Commentaire de hvb le 27/03/2007 23:39:42

excellent! comme le nom de la source

signaler à un administrateur
Commentaire de Renfield le 28/03/2007 10:47:32 administrateur CS

je viens d'ajouter le parametre veShift , afin de pouvoir simuler des raccourcis clavier, comme Ctrl+S (dans l'exemple du zip)

signaler à un administrateur
Commentaire de VBGenesis le 28/03/2007 12:53:54

Je n'ai pas encore regardé la source (désolé) mais tu peux aller voire cette source de ym_trainz si tu veux :
http://www.vbfrance.com/code.aspx?ID=39754
Ca gère le sendkeys en fonction de la fenêtre active (récupération du titre de la fenêtre). Je crois que c'est comparable a ta propre source.

A+

signaler à un administrateur
Commentaire de Renfield le 28/03/2007 14:34:38 administrateur CS

pas tout a fait pareil, en fait...

source très interessante...
ym_trainz surveille le clavier. si une sequence particuière de touches est detectée, il simule n pressions de touches au clavier, pour automatiser certaines choses.

ici, je simule la pression de touches a destination d'appli (de fenetres) n'ayant pas forcément le focus.

signaler à un administrateur
Commentaire de Uvatha le 17/05/2007 20:05:55

J'aurais une petite question...

J'ai essayé ta source Renfield et elle fonctionne très bien... seulement, je voulais simuler des touches dans un jeu et pour une raison inconnue, ça ne fonctionne pas, ça ne passe même pas le

     If IsWindow(vhTargetWnd) Then

Je ne connais pas trop bien l'API IsWindow mais je suppose que ça ne fonctionne tout simplement pas pour un jeu.

Si quelqu'un a une solution à ce problème, merci de bien vouloir m'en faire part.

9/10 pour la source, très claire et assez bien commentée.

signaler à un administrateur
Commentaire de Renfield le 19/05/2007 19:08:48 administrateur CS

tout dépend du jeu, et de la technologie qu'il utilise...

fort a parier qu'il s'agit de DirectInput, qui traite directement avec le matériel, sans demander quoi que ce soit à Windows....

signaler à un administrateur
Commentaire de ciberrique le 13/06/2007 20:08:15

Le code fonctionne apparement, mais quand je veux utiliser la combinaison control  +  Z  sous adobe photoshop alors la le resultat est considerer par adobe que comme un Z sans le Control.

Puis aussi comment faire la combinaison Control + Alt + Z ou Control + Shift + Z   qui sont très important sous photoshop.

signaler à un administrateur
Commentaire de Renfield le 14/06/2007 04:41:56 administrateur CS

Le Alt, je ne sais pas, comme ça, faut que je testes

Ctrl + Shift + Z... je dirai :
SendKeysEx xxx, vbKeyZ, vbShiftMask Or vbCtrlMask

je regarderai ca de plus pres

ceci dit, il y a BEAUCOUP plus simple pour faire ce que tu cherches a faire...
lances Spy++ et Photoshop

espionne ta fenetre

cliques dans ton menu.

et recherches  dans SPY++ le message WM_COMMAND correspondant.
lParam et wParam te renverront les précieux parametres qu'il te suffira de retransmettre via un SendMessage pour faire executer ta commande. Tu sera independant des raccourcis clavier, etc... et en plus, ce sera plus rapide ^^

pas clair ?

pas de soucis, redemande moi.... je reexpliquerai ^^

signaler à un administrateur
Commentaire de ciberrique le 14/06/2007 10:25:20

Merci, je connaissais pas !!!
Je vais plancher la dessus.

signaler à un administrateur
Commentaire de Chatbour le 07/09/2007 02:52:44

Bonne source :)

j'ai une question : comment faire l'inverse, c'est à dire contrôler par exemple un TextBox depuis Notepad (j'ai une bonne imagination ;) )..

signaler à un administrateur
Commentaire de phixfoxphixfox le 25/10/2007 14:35:11

Merci bcp pour ce code !!

mais je dois me faire des noeud au cerveau en se moment car je n'arrive pas a faire ce que je veux
donc sendkeysex(handle,codetouche,....) te permet d'envoyer un caractere dans une appli externe
c'est genial
mais d'apres ce que je comprends ce caractere est codé donc 49 permet d'envoyer un "1" etc
j'aimerai pouvoir envoyer une chaine de caractere de ce type directement
"12*45={entrée}Merci{ctrl}A{ctrl}C"
par une fonction du genre :
sendstringex(handle,"12*45={entrée}Merci{ctrl}A{ctrl}C" )
pourrai tu m'aider , car je boucle lamentablement sur ce pb

Merci par avance

signaler à un administrateur
Commentaire de pulpul74 le 03/12/2007 10:05:48 7/10

Source très sympa, très utile, par contre je trouve domage que certaines combinaisons de touches ne marchent pas forcement, comme par exemple un ctrl-C et ctrl-V.Mais bon déja ca peut etre pas mal dans certaines situation, merci!

signaler à un administrateur
Commentaire de Renfield le 03/12/2007 12:27:40 administrateur CS

Ctrl+C/V ?

SendMessage WM_COPY et WM_PASTE ne convient pas ?

signaler à un administrateur
Commentaire de pochagnole le 20/12/2007 09:04:34

Bonjour tout le monde !

Moi j'ai un gros problème, je n'arrive pas à faire fonctionner cette source sous access 2000.

Il me renvoie une erreur à cette ligne : "Public Sub SendKeysEx(ByVal vhTargetWnd As Long, ByVal veKey As VBRUN.KeyCodeConstants, Optional ByVal veShift As VBRUN.ShiftConstants, Optional ByVal vbExtendedKey As Boolean = False)"

Apparemment, il ne connaît pas VBRUN. Il me dit "Type défini par l'utilisateur non défini".
Dans les références, je n'ai pas "visual basic runtime objects and procedures". Est-ce que le problème peut venir de là. Si oui, comment faire pour avoir cette référence : quand je veux ajouter vb6fr.dll, j'ai une erreur... Déjà que j'ai dû rajouter VB6.OLB car je ne l'avais pas sur mon PC (pourtant j'ai installé les runtime vb6).

Aidez-moi, please !

MERCI !!!

signaler à un administrateur
Commentaire de Chatbour le 20/12/2007 10:43:48

Salut,

Ce code n'est pas du VBA : il ne fonctionne pas sous la suite Office, mais sur VB6..

signaler à un administrateur
Commentaire de pochagnole le 20/12/2007 11:50:49

Ok. Mince alors. N'y a-t-il pas moyen de l'adapter en vba ?

Désolé, je n'y connais pas grand chose, je débute (à noter que j'ai essayé le même code sous VB express 2005 et que j'avais les mêmes problèmes...).

signaler à un administrateur
Commentaire de ciberrique le 20/12/2007 12:12:38

Comme Chatbour l'a dis, c'est que sous vb6, pas de vbexpress ou autre.

signaler à un administrateur
Commentaire de Chatbour le 20/12/2007 12:18:55

VB.NET (VB 2005) est un autre langage très différent..

tu veux convertir ce code en VBA : il vaut mieux poser la question sur le forum et mettre le lien vers la source..

Bonne chance :)

signaler à un administrateur
Commentaire de pochagnole le 20/12/2007 14:28:24

Merci beaucoup pour ces info. Je n'avais pas compris la différence entre VB.NET, VB6 et VBA.

Je vais m'en remettre au forum !

signaler à un administrateur
Commentaire de Titant le 21/07/2008 01:56:51

Salut,

Moi j'ai juste une petite question.
Comment on peu faire pour envoyer le textbox directement.
cad pas lettre par lettre mais un mot directement ?

Merci

signaler à un administrateur
Commentaire de boudas le 08/10/2008 17:46:15

bonjour,

une petite question, comment peut-on savoir que le logiciel a bien recu la touche ?
car pour l'instant, on en a aucune assurance (dans le bloc note, il ne prend pas forcément en compte la touche "maj") (je l'utilise pour écrire des lettres en majuscules par exemple.)

d'avance merci

signaler à un administrateur
Commentaire de Renfield le 23/12/2008 09:29:34 administrateur CS

On modifie l'etat du clavier.
en placant un DoEvents (ou ici, un Sleep 1) on redonne rapidement la main au systeme.
Ce dernier va regarder la fenêtre qui détiens le focus du clavier, et l'avertir des modifications du clavier.

pour l'avertir, elle passe par la voie standard: elle lui transmets des messages qui seront stockés dans une file d'attente.

Ces messages seront ensuite traités par la cible, selon sa disponibilité, bien sur, mais dans l'ordre de la file. Pas de perte de touche, donc.

signaler à un administrateur
Commentaire de GrandByblos le 09/03/2009 14:27:47

Bonjour.

Je me permets deux petites questions :

- Comment intégrer cette procédure à un projet VB.NET 2008 ?
En effet, il ne comprend pas le VBRUN.KeyCodeConstants (et je sèche un peu, j'avoue ^_^).

- En fait, j'essaye d'envoyer des codes touches à une application tierce, dont je ne peux modifier le source.
A l'heure actuelle, j'arrive à lui envoyer des touches en lui donnant le focus (par OpenIcon et SetForegroundWindow) puis en lui envoyant les touches via SendWait.
C'est fonctionnel, sauf dans le cas où la session utilisateur est verrouillée (mon appli devant se lancer le soir, vers 23h, et devant être déployée, je n'ai pas la maitrise de l'état de la session) ; en effet, dans le cas d'une session verrouillée, je ne peux plus donner le focus (forcément me direz-vous) et donc ça ne fonctionne plus ...

Avec cette procédure, me sera-t-il possible d'envoyer des touches (F1, etc.) à une application qui n'est pas au 1er plan ?

Merci d'avance pour vos réponses !

Cordialement

signaler à un administrateur
Commentaire de Renfield le 10/03/2009 07:34:37 administrateur CS

utilises System.Windows.Forms.Keys

Ajouter un commentaire

Discussions en rapport avec ce code source dans le forum

Récupérer le N° (hwnd) d'une application [ par luxpo ] Comment faire pour récipérer le N° hwnd d'une fenêtre ?Merci SendKeys vers une fenetre [ par milobac ] Il y a un moyen d'envoyer un SendKeys directemnt vers une fenetre Windows qui n'est pas activée?Ex: On surfe avec Internet Explorer et pendant ce temp recup des infos d'1 fenetre d'une autre application [ par FREDDY ] Bonjour, J'essaye deseperement de recuperer sous visual basic 6 des informations qui défilent dans une fenetre d'un logiciel qui tourne sous window Ouvrir une autre application dans une fenetre vb !! [ par mattheus ] Hello !!Je souhaiterais ouvrir une autre application *.exe dans une form .Je sais comment l'ouvrir avec la commande SHELLmais je sais pas l'integrer d Déplacement d'une application [ par Zeroc00l ] Salut tout le monde merci de lire mon probleme Comment puis je faire pour que grace a MON application, je fasse bouger la fenetre d'une AUTRE applicat hWnd As Long pour .Net [ par dragon ] comment je fait pour avoir le Haddle d'une application que j'ai démarrer par Dim test As New Pass(Me)soft = New Access.Application???au pire, une autr ControlBox [ par Charlie ] Allo... j'ai une fenetre avec le petit X dans le coin supérieur droite de la fenetre (controlbox). J'aimerais que lorsqu'on clique sur le X, pouvoir i shell et sendkeys sont méchants avec moi [ par lutinpitchoune ] Mon problème est simple à la base : Je veux piloter depuis mon application excel, un programme qui tourne dansune session dos sous windows. En fait je extract icon grace au HWND d'un fenetre [ par MarbleMad ] salut,je cherche le moyen de recuperer l'icon 16x16 des applis en cours d'utilisation grace au HWND de la fenetre (appli dans la barre de tache).si q appliquer Sendkeys sur une autre fenetre [ par David75000 ] J'ai essayé :AppActivate titre_actif, TrueSendKeys "{ENTER}", TrueMais cela ne marche pasHistorique:Nous developpons une application dans le domaine d


Nos sponsors

Sondage...

CalendriCode

Juillet 2009
LMMJVSD
  12345
6789101112
13141516171819
20212223242526
2728293031  

Consulter la suite du CalendriCode

Téléchargements

Logiciels à télécharger sur le même thème :

Comparez les prix Nouvelle version

Photothèque Nouveau !



Développement réalisé par Nicolas SOREL (Nix) avec l'aide de : Cyril DURAND et Emmanuel (EBArtSoft), Merci à Vincent pour ses précieux conseils
CodeS-SourceS.com© Toute reproduction même partielle est interdite sauf accord écrit du Webmaster
CodeS-SourceS.com© est une marque déposée tous droits réservés
Temps d'éxécution de la page : 0,125 sec

Google Coop CodeS-SourceS Google Coop CodeS-SourceS


Certaines images présentes sur le site (notament certains avatars) sont issues des collections IconShock, donc si vous souhaitez utiliser ces icons vous devez les acheter, ne les copiez pas et ne utilisez pas dans vos sites et applications sans les avoir commandé.