IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C++Builder Discussion :

[HOOK] Problème(s) pour réaliser le tutoriel sur les HOOKS


Sujet :

C++Builder

  1. #1
    Membre habitué Avatar de Rodrigue
    Inscrit en
    Août 2002
    Messages
    487
    Détails du profil
    Informations forums :
    Inscription : Août 2002
    Messages : 487
    Points : 157
    Points
    157
    Par défaut [HOOK] Problème(s) pour réaliser le tutoriel sur les HOOKS
    Bonjour,

    Voilà j'ai quelques problèmes pour réaliser le tutoriel de gRRosminet sur les HOOKS. Celui-ci est disponible à l'adresse suivante : http://tcharles.developpez.com/simul/#hooks.

    J'arrive bien à créer la DLL hooksClSo.dll (8,50 Ko (8*704 octets)) ainsi que l'exécutable. Au début j'avais pensé créer une fiche dans la DLL même (je l'ai déclarée C++ + multithreaded mais pas VCL car cela me faisait une erreur de link!!!) mais ça ne créait aucun exécutable d'où j'ai crée une application externe qui appelle la DLL. Je pense ne pas m'être trompé en faisant de la sorte ...

    Alors lorsque j'exécute mon application. Je vois bien que la DLL est chargée (j'affiche un messagebox dans une fonction test!) ... mais lorsque je clique avec ma souris ou que j'appuie sur la touche ENTER rien ne se passe : aucun son, ni incrémentation de mon compteur.

    Je peux à la limite envoyer mes sources pour essayer de régler mon problème!!!

    Merci d'avance.
    Rodrigue

  2. #2
    Membre confirmé

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2002
    Messages
    137
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Ain (Rhône Alpes)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2002
    Messages : 137
    Points : 621
    Points
    621
    Par défaut
    Est-ce que par le plus grand des hasards, ton projet DLL ne serait pas un projet C++ à la place d'un projet C ?
    Dans ce cas hyperbrobable, il serait judicieux de placer tout le code de mon exemple dans un bloc
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    extern "C" { ... }
    (je ne garantie pas que ce soit exactement la bonne syntaxe, mais je sais qu'il y a un truc dans le genre => cf l'aide)

    Et pensez que ce n'est pas la peine de faire un projet C++ si vous n'utilisez que du code C, surtout pour les DLL !

  3. #3
    Membre habitué Avatar de Rodrigue
    Inscrit en
    Août 2002
    Messages
    487
    Détails du profil
    Informations forums :
    Inscription : Août 2002
    Messages : 487
    Points : 157
    Points
    157
    Par défaut
    Oui en effet j'avais crée un DLL Wizard en C++ + multithreaded ...

    Bon alors j'ai essayé avec un DLL Wizard en C + multithreaded :
    j'ai collé dans la DLL le bout de code de ton tutoriel :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
     
    #include <windows.h>
    // Définition de la structure de la zone mémoire partagée
    typedef struct _TDonnees
    &#123;
         HHOOK MouseHookHandle; // Handle du hook de la souris 
         HHOOK KeybdHookHandle; // Handle du hook du clavier
         HWND hDestWindow; // Handle de la fenêtre à laquelle le hook du clavier doit les données
         // Mettez ici toutes les données que vous voulez partager
    &#125; TDonnees;
     
    // Déclaration des variables globales de la DLL
    HANDLE MemPartagee; // Handle de la zone de mémoire partagée
    TDonnees * VueDonnees; // Pointeur vers la zone de mémoire
    HINSTANCE HInst; // Handle d'intance de la DLL
     
    // Déclaration des fonctions de la DLL
    void _export InitHook&#40;HWND hDest&#41;;
    void _export EndHook&#40;&#41;;
    LRESULT CALLBACK MouseProc&#40;int nCode,WPARAM wParam,LPARAM lParam&#41;;
    LRESULT CALLBACK KeybdProc&#40;int nCode,WPARAM wParam,LPARAM lParam&#41;;
     
    // fonction d'initialisation de la DLL
    int WINAPI DllEntryPoint&#40;HINSTANCE hinst, unsigned long reason, void* lpReserved&#41;
    &#123;
         HInst = hinst;
         switch &#40;reason&#41;
         &#123;
              case DLL_PROCESS_ATTACH &#58; // à la création de l'instance de la DLL
                   // Attachement d'une zone de mémoire partagée &#40;notez le cast&#41;
                   MemPartagee = CreateFileMapping&#40;&#40;HANDLE&#41;0xFFFFFFFF, // On map un espace mémoire
                                            NULL, // Pas d'informations de sécurité
                                            PAGE_READWRITE, // Partage en lecture/écriture
                                            0, // Taille de la zone réservée sur 64 bits &#40;32 bits de poid fort&#41;
                                            sizeof&#40;TDonnees&#41;, // 32 bits de poids faible
                                            "Tutoriel Hooks par gRRosminet"&#41;; // Nom de la zone réservée
     
                   // Création d'une vue pour pouvoir accéder à la zone de mémoire partagée &#40;notez le cast&#41;
                   VueDonnees = &#40;TDonnees *&#41;&#40;MapViewOfFile&#40;&#40;HANDLE&#41;MemPartagee, // Zone sur laquelle créer la vue
                                            FILE_MAP_WRITE, // Mode d'accès en lecture/écriture
                                            0, 0, // Offset de début de la vue sur 64 bits
                                            0&#41;&#41;; // Taille de la vue &#40;0 = tout&#41;
                                            break;
     
              case DLL_PROCESS_DETACH &#58; // au détachement de la DLL
                   // Destruction de la vue sur la zone de mémoire partagée
                   UnmapViewOfFile&#40;&#40;LPVOID&#41;VueDonnees&#41;;
                   // Détachement de la zone de mémoire partagée
                   CloseHandle&#40;MemPartagee&#41;;
                   break;
     
              default &#58;
                   // DLL_THREAD_ATTACH, DLL_THREAD_DETACH
                   break;
         &#125;
         return 1;
    &#125;
     
    void _export InitHook&#40;HWND hDest&#41; // _export est spécifique à BCB 
    &#123;
         // Installation du hook sur la souris
         VueDonnees->MouseHookHandle = SetWindowsHookEx&#40;WH_MOUSE, // Créer un hook sur la souris
                                                 &#40;HOOKPROC&#41;MouseProc, // Utiliser la fonction MouseProc
                                                 HInst, // Dans la DLL d'instance HInst
                                                 0&#41;; // Pour tous les threads
     
         // Installation du hook pour le clavier
         VueDonnees->KeybdHookHandle = SetWindowsHookEx&#40;WH_KEYBOARD, // Créer un hook sur le clavier
                                                 &#40;HOOKPROC&#41;KeybdProc, // Utiliser la fonction KeybdProc
                                                 HInst, // Dans la DLL d'instance HInst
                                                 0&#41;; // Pour tous les threads
     
         // Partage de la fenêtre destinatrice des données du clavier
         VueDonnees->hDestWindow = hDest;
    &#125;
     
    void _export EndHook&#40;&#41;
    &#123;
         // Supression des hooks
         UnhookWindowsHookEx&#40;VueDonnees->MouseHookHandle&#41;;
         UnhookWindowsHookEx&#40;VueDonnees->KeybdHookHandle&#41;;
    &#125;
     
    LRESULT CALLBACK _export MouseProc&#40;int nCode,WPARAM wParam,LPARAM lParam&#41;
    &#123;
         // On joue un son à chaque fois que l'utilisateur enfonce le bouton gauche
         if &#40;wParam == WM_LBUTTONDOWN&#41;
    	      MessageBeep&#40;MB_OK&#41;;
    	 return CallNextHookEx&#40;VueDonnees->MouseHookHandle,nCode,wParam,lParam&#41;;
    &#125;
     
    #define WMAP_KEYBDHOOKMSG WM_APP + 1
     
    LRESULT CALLBACK _export KeybdProc&#40;int nCode,WPARAM wParam,LPARAM lParam&#41;
    &#123;
         // On envoie un message WMAP_KEYBDHOOKMSG à chaque fois que
    	 // l'utilisateur presse la touche ENTREE
         if &#40;wParam == VK_RETURN&#41;
              PostMessage&#40;VueDonnees->hDestWindow, WMAP_KEYBDHOOKMSG, 0, 0&#41;;
     
         return CallNextHookEx&#40;VueDonnees->KeybdHookHandle,nCode,wParam,lParam&#41;;
    &#125;
    Après j'ai fait un CLOSE ALL et j'ai crée une nouvelle APPLICATION :

    j'y ai collé les bouts de code suivants :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    #ifndef appliH
    #define appliH
     
    #include <Classes.hpp>
    #include <Controls.hpp>
    #include <StdCtrls.hpp>
     
    typedef void &#40;*TInitFunc&#41;&#40;HWND&#41;;
    typedef void &#40;*TEndFunc&#41;&#40;&#41;;
     
    #define WMAP_KEYBDHOOKMSG WM_APP + 1
     
    class TForm1 &#58; public TForm
    &#123;
         __published&#58; // Composants gérés par l'EDI
              TCheckBox *CheckBox1;
              TLabel *Label1;
              void          __fastcall CheckBox1Click&#40;TObject *Sender&#41;;
              void          __fastcall FormClose&#40;TObject *Sender, TCloseAction &Action&#41;;
         private&#58; // Déclarations utilisateur
              TInitFunc InitHooks; // fonction d'initialisation des hooks
              TEndFunc EndHooks; // fonction de suppression des hooks
              HINSTANCE hinstDLL; // instance de la DLL
              bool bHook; // Les hooks ont-ils été initialisés ?
              int nbEntree; // compteur de pressions pour le gestionnaire de messages
              public&#58; // Déclarations utilisateur
              void __fastcall PressionEntree&#40;TWMNoParams &p&#41;;
              __fastcall TForm1&#40;TComponent* Owner&#41;;
         protected&#58; // déclaration du gestionaire de messages
              BEGIN_MESSAGE_MAP
                   VCL_MESSAGE_HANDLER&#40;WMAP_KEYBDHOOKMSG, TWMNoParams, PressionEntree&#41;
              END_MESSAGE_MAP&#40;TForm&#41;
    &#125;;
     
    extern PACKAGE TForm1 *Form1;
     
    #endif
    et pour le code

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
     
    #include <vcl.h>
    #include "appli.h"
     
    #pragma package&#40;smart_init&#41;
    #pragma resource "*.dfm"
     
    TForm1 *Form1;
     
    __fastcall TForm1&#58;&#58;TForm1&#40;TComponent* Owner&#41;
              &#58; TForm&#40;Owner&#41;
    &#123;
         bHook = false; // Les hooks ne sont pas initialisés
         hinstDLL = LoadLibrary&#40;"hooksClSo.dll"&#41;; // Chargement de la librairie
         if &#40;!hinstDLL&#41; // Erreur lors du chargement de la librairie ?
              Application->MessageBox&#40;"Impossible de charger la librairie.","gloups",MB_OK&#41;;
         else
    	 &#123;
              // On récupère les adresses des fonctions
              InitHooks = &#40;TInitFunc&#41;GetProcAddress&#40;hinstDLL, "_InitHook"&#41;;
              EndHooks = &#40;TEndFunc&#41;GetProcAddress&#40;hinstDLL, "_EndHook"&#41;;
         &#125;
    &#125;
     
    void __fastcall TForm1&#58;&#58;CheckBox1Click&#40;TObject *Sender&#41;
    &#123;
         if &#40;!hinstDLL&#41; // La librairie n'est pas chargée, inutile de continuer
              Close&#40;&#41;;
         else if &#40;CheckBox1->Checked&#41; // Activer les hooks
         &#123;
              nbEntree = 0; // On réinitialise le compteur
              InitHooks&#40;Form1->Handle&#41;; // On initialise les hooks
         &#125;
         else // Désactiver les hooks
              EndHooks&#40;&#41;; // On supprime les hooks
         &#125;
     
     void __fastcall TForm1&#58;&#58;FormClose&#40;TObject *Sender, TCloseAction &Action&#41;
    &#123;
         if &#40;bHook&#41; // Si les hooks sont actifs, on les supprime avant de quitter
              EndHooks&#40;&#41;;
     
         Action = caFree;
    &#125;
     
    void __fastcall TForm1&#58;&#58;PressionEntree&#40;TWMNoParams &p&#41;
    &#123;
         nbEntree++; // On a reçu un message du hook &#58; on incrémente et on affiche le compteur
         Label1->Caption = AnsiString&#40;"Pressions de ENTREE &#58; "&#41; + nbEntree;
    &#125;
    et ça ne fonctionne pas!!! Est-ce que tu vois où j'ai fais une faute ???

    Merci d'avance!
    Rodrigue

  4. #4
    Membre confirmé

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2002
    Messages
    137
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Ain (Rhône Alpes)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2002
    Messages : 137
    Points : 621
    Points
    621
    Par défaut
    t'as essayé sans le multithreaded ?
    A noter : tu est en v6 et moi en V5, je crois que y'avait déjà eu un pb du genre. Essaye tjs avec extern "C"

  5. #5
    Membre habitué Avatar de Rodrigue
    Inscrit en
    Août 2002
    Messages
    487
    Détails du profil
    Informations forums :
    Inscription : Août 2002
    Messages : 487
    Points : 157
    Points
    157
    Par défaut
    J'ai essayé sans le multithread et ça ne change pas ... est-ce que l'application et la DLL sont bel et bien deux projets complètement disjoint ???
    Si oui, ne faut-il pas dans l'application ajouté au projet le .lib de la DLL ?

    Je n'ai pas essayé le extern C ... est-ce que je dois tout simplement encadré tout le code de la DLL (même #include <windows.h>) avec ... ?

    Tu n'aurais pas une source qui fonctionne ?

    Merci,
    Rodrigue

  6. #6
    Membre chevronné
    Avatar de DjmSoftware
    Homme Profil pro
    Responsable de compte
    Inscrit en
    Mars 2002
    Messages
    1 044
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Suisse

    Informations professionnelles :
    Activité : Responsable de compte
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Mars 2002
    Messages : 1 044
    Points : 2 187
    Points
    2 187
    Billets dans le blog
    1
    Par défaut
    Salut,
    qu'est ce qui ne fonctionne pas
    le Hook Clavier ,le HOOK Souris
    pour ma part j'ai creé la DLL en C++ mode Visual sans la VCL,sans le Multithread, sans la gestion des exceptions
    les fonctions exportées sont nommées comme suit
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    extern "C" __stdcall void _export InitHook&#40;HWND hDest&#41;;
    extern "C" __stdcall void _export EndHook&#40;&#41;;
    j'ai modifié la procédure MouseProc de la manière suivante
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    MessageBeep&#40;MB_ICONEXCLAMATION&#41;;
    attention les fonctions CallBAck ne doive pas être exportée comme tu l'a fait
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    LRESULT CALLBACK _export MouseProc&#40;int nCode,WPARAM wParam,LPARAM lParam&#41;
    LRESULT CALLBACK _export KeybdProc&#40;int nCode,WPARAM wParam,LPARAM lParam&#41;
    le .h de ton application test est modifié comme suit
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    typedef void &#40;__stdcall *TInitFunc&#41;&#40;HWND&#41;;
    typedef void &#40;__stdcall *TEndFunc&#41;&#40;&#41;;
    l'appel de la dll est modifié comme suit dans le constructeur de ton application

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
     
     bHook = false; // Les hooks ne sont pas initialisés
         hinstDLL = LoadLibrary&#40;"hook.dll"&#41;; // Chargement de la librairie
         if &#40;!hinstDLL&#41; // Erreur lors du chargement de la librairie ?
           &#123;
              Application->MessageBox&#40;"Impossible de charger la librairie.","gloups",MB_OK&#41;;
              Application->Terminate&#40;&#41;;
           &#125;
         else
        &#123;
              // On récupère les adresses des fonctions
              InitHooks = &#40;TInitFunc&#41;GetProcAddress&#40;hinstDLL, "InitHook"&#41;;
              EndHooks = &#40;TEndFunc&#41;GetProcAddress&#40;hinstDLL, "EndHook"&#41;;
         &#125;
    et voila cela fonctionne
    Cordialement
    vous trouverez mes tutoriels à l'adresse suivante: http://djmsoftware.developpez.com/
    je vous en souhaite une excellente lecture ...

    A lire : Les règles du forum

  7. #7
    Membre à l'essai
    Inscrit en
    Août 2002
    Messages
    19
    Détails du profil
    Informations forums :
    Inscription : Août 2002
    Messages : 19
    Points : 21
    Points
    21
    Par défaut
    Djm si tu fais deux clics droits sur le bureau à la suite , le hook te détecte bien SEULEMENT 2 clics droits ou pas ?

    car chez moi , avec le tuto de grosminet , il me détecte 3 clics...

  8. #8
    Membre habitué Avatar de Rodrigue
    Inscrit en
    Août 2002
    Messages
    487
    Détails du profil
    Informations forums :
    Inscription : Août 2002
    Messages : 487
    Points : 157
    Points
    157
    Par défaut
    Merci beaucoup! J'ai réussi à le faire fonctionner mais par une autre méthode ... mais ça ne fait rien ça me donne plusieurs façons de le faire!!! Ca m'a permis d'apprendre les DLL...

    Merci à tous!
    Rodrigue

  9. #9
    Membre confirmé

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2002
    Messages
    137
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Ain (Rhône Alpes)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2002
    Messages : 137
    Points : 621
    Points
    621
    Par défaut
    Ca serai bien que vous mettiez tous vos façons de faire, parceque ce que j'ai fait l'a été avec C++ Builder 5 Entse mais déjà la il y avait des possibilités pour que ca ne marche pas.

    Certes, il est vrai que je ne vai pas chercher à trouver LA solution universelle, d'autant plus que j'ai abandonné le monde microsoft (au boulot ca me suffit), mais cela me permettrait d'ajouter VOS solutions personnelles à mon tuto pour que tout le monde puisse trouver plus facilement une solution qui lui conviens.

    Voilà, merci pour vos solution et pour l'intérêt que vous portez a mes tutos !

    une question : pourquoi c'est le tuto que j'ai fais avec le moins de conviction qui déconne et qui vous intéresse le plus ?

  10. #10
    Membre à l'essai
    Inscrit en
    Août 2002
    Messages
    19
    Détails du profil
    Informations forums :
    Inscription : Août 2002
    Messages : 19
    Points : 21
    Points
    21
    Par défaut
    bonne idée grot minet , ca serait bien que tous le monde mettent sa méthode pour réaliser les hooks !

    Car avec la méthode du tuto , j'ai trouvé quelques petits bugs hé hé

    Sinon il est vrai que beaucoup de monde est intéressé par ce tuto , on l'aime on y peut rien , c plus fort que nous

  11. #11
    Membre à l'essai
    Profil pro
    Inscrit en
    Février 2003
    Messages
    17
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2003
    Messages : 17
    Points : 20
    Points
    20
    Par défaut
    Bonjour,

    je viens de récupérer le tuto de grosminet, effectivement je rencontre quelques soucis, je n'ai pas encore approfondi la question mais je vous tiendrai au courant de mes recherches.
    @+

  12. #12
    Membre du Club

    Inscrit en
    Août 2002
    Messages
    24
    Détails du profil
    Informations forums :
    Inscription : Août 2002
    Messages : 24
    Points : 52
    Points
    52
    Par défaut
    Bonjours les developpez,

    Je tenais répondre à ce post, vu que j'ai pas mal lutté pour faire fonctionner ce tutorial

    J'ai fait le teste du tutorial sur un Builder v6 sans succès. Lorsque je cliquais sur le checkbox j'obtenais une erreur du type "Violation d'accès à l'adresse ..."

    Mais gràce aux modifications apportées par DjmSoftware cela marche nikel chrome

    merci à gRRosminet pour ce fabuleux tutorial et à DjmSoftware pour les modif

  13. #13
    Nouveau Candidat au Club
    Profil pro
    Inscrit en
    Mars 2004
    Messages
    1
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2004
    Messages : 1
    Points : 1
    Points
    1
    Par défaut
    Bonsoir à tous,
    J'ai moi aussi pas mal galèré pour faire tourner ce tutorial sur les hooks en Builder V6, mais grâce aux modif de DjmSoftware, ça marche nickel!

    Y a peut être "plus qu'à" mettre à jour le tutorial à jour pour éviter que d'autres galèrent (quoique c'est formateur )
    En tout cas, merci à tous, et encore bravo gRRosminet pour ce tutorial !

  14. #14
    Futur Membre du Club
    Inscrit en
    Avril 2011
    Messages
    8
    Détails du profil
    Informations forums :
    Inscription : Avril 2011
    Messages : 8
    Points : 5
    Points
    5
    Par défaut Hook avec Code::blocks
    Bonjour,

    Ne souhaitant pas payer une licence pour un outil qui semble compliqué, j'utilise CodeBlocks (free) pour mes développements.

    Malheureusement, je rencontre un soucis majeur pour ce tutoriel : au moment d'utiliser la fonction "GetProcAddress", l'adresse retournée reste à 0. Du coup, à l'appel de "InitHooks(fenetrePrincipale);", un "segmentation fault" a tout stoppé.
    Je devine donc que la fonction n'a pas réussi à trouver l'adresse de la procédure.

    Voici le code de la DLL Hook :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    #include <windows.h>
     
    #define DLL_EXPORT __declspec(dllexport)
     
    // Définition de la structure de la zone mémoire partagée
    typedef struct _TDonnees {
         HHOOK MouseHookHandle; // Handle du hook de la souris
         HHOOK KeybdHookHandle; // Handle du hook du clavier
         HWND hDestWindow; // Handle de la fenêtre à laquelle le hook du clavier doit les données
         // Mettez ici toutes les données que vous voulez partager
    } TDonnees;
     
    // Déclaration des variables globales de la DLL
    HANDLE MemPartagee; // Handle de la zone de mémoire partagée
    TDonnees * VueDonnees; // Pointeur vers la zone de mémoire
    HINSTANCE HInst; // Handle d'intance de la DLL
     
    // Déclaration des fonctions de la DLL
    EXTERN_C CALLBACK void DLL_EXPORT InitHook(HWND hDest);
    EXTERN_C CALLBACK void DLL_EXPORT EndHook();
    LRESULT CALLBACK DLL_EXPORT MouseProc(int nCode,WPARAM wParam,LPARAM lParam);
    LRESULT CALLBACK DLL_EXPORT KeybdProc(int nCode,WPARAM wParam,LPARAM lParam);
     
    // fonction d'initialisation de la DLL
    int WINAPI DllEntryPoint(HINSTANCE hinst, unsigned long reason, void* lpReserved) {
        HInst = hinst;
        switch (reason) {
            case DLL_PROCESS_ATTACH : // à la création de l'instance de la DLL
                // Attachement d'une zone de mémoire partagée (notez le cast)
                MemPartagee = CreateFileMapping((HANDLE)0xFFFFFFFF, // On map un espace mémoire
                                NULL, // Pas d'informations de sécurité
                                PAGE_READWRITE, // Partage en lecture/écriture
                                0, // Taille de la zone réservée sur 64 bits (32 bits de poid fort)
                                sizeof(TDonnees), // 32 bits de poids faible
                                "Tutoriel Hooks par gRRosminet"); // Nom de la zone réservée
     
                // Création d'une vue pour pouvoir accéder à la zone de mémoire partagée (notez le cast)
                VueDonnees = (TDonnees *)(MapViewOfFile((HANDLE)MemPartagee, // Zone sur laquelle créer la vue
                                FILE_MAP_WRITE, // Mode d'accès en lecture/écriture
                                0, 0, // Offset de début de la vue sur 64 bits
                                0)); // Taille de la vue (0 = tout)
                break;
     
            case DLL_PROCESS_DETACH : // au détachement de la DLL
                // Destruction de la vue sur la zone de mémoire partagée
                UnmapViewOfFile((LPVOID)VueDonnees);
                // Détachement de la zone de mémoire partagée
                CloseHandle(MemPartagee);
                break;
     
            default :
                // DLL_THREAD_ATTACH, DLL_THREAD_DETACH
                break;
        }
        return 1;
    }
     
    void DLL_EXPORT InitHook(HWND hDest) {// _export est spécifique à BCB
        // Installation du hook sur la souris
        VueDonnees->MouseHookHandle = SetWindowsHookEx(WH_MOUSE, // Créer un hook sur la souris
                                        (HOOKPROC)MouseProc, // Utiliser la fonction MouseProc
                                        HInst, // Dans la DLL d'instance HInst
                                        0); // Pour tous les threads
     
        // Installation du hook pour le clavier
        VueDonnees->KeybdHookHandle = SetWindowsHookEx(WH_KEYBOARD, // Créer un hook sur le clavier
                                        (HOOKPROC)KeybdProc, // Utiliser la fonction KeybdProc
                                        HInst, // Dans la DLL d'instance HInst
                                        0); // Pour tous les threads
     
     
        // Partage de la fenêtre destinatrice des données du clavier
        VueDonnees->hDestWindow = hDest;
    }
     
    void DLL_EXPORT EndHook() {
        // Supression des hooks
        UnhookWindowsHookEx(VueDonnees->MouseHookHandle);
        UnhookWindowsHookEx(VueDonnees->KeybdHookHandle);
    }
     
    LRESULT CALLBACK DLL_EXPORT MouseProc(int nCode,WPARAM wParam,LPARAM lParam) {
        // On joue un son à chaque fois que l'utilisateur enfonce le bouton gauche
        if (wParam == WM_LBUTTONDOWN)
            MessageBeep(MB_ICONEXCLAMATION);
     
        return CallNextHookEx(VueDonnees->MouseHookHandle,nCode,wParam,lParam);
    }
     
    #define WMAP_KEYBDHOOKMSG WM_APP + 1
     
    LRESULT CALLBACK DLL_EXPORT KeybdProc(int nCode,WPARAM wParam,LPARAM lParam) {
        // On envoie un message WMAP_KEYBDHOOKMSG à chaque fois que
        // l'utilisateur presse la touche ENTREE
        if (wParam == VK_RETURN)
            PostMessage(VueDonnees->hDestWindow, WMAP_KEYBDHOOKMSG, 0, 0);
     
        return CallNextHookEx(VueDonnees->KeybdHookHandle,nCode,wParam,lParam);
    }
    où EXTERN_C = extern "C"
    et CALLBACK = __stdcall

    Et pour la WINAPI, voici le code (je n'ai pas fait de header) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
    152
    153
    154
    155
    156
    157
    158
    159
    160
    161
    162
    163
    164
    165
    166
    167
    168
    169
    170
    171
    172
    173
    174
    175
    176
    177
    178
    179
    180
    181
    182
    183
    184
    185
    186
    187
    188
    189
    190
    191
    192
    193
    194
    195
    196
    197
    198
    199
    200
    201
    202
     
    #include <windows.h>
    #include <stdio.h>
     
    #define ID_CHECKBOX_1       113
    #define WMAP_KEYBDHOOKMSG WM_APP + 1
     
    HINSTANCE instance;
    typedef void (*TInitFunc) (HWND);
    typedef void (*TEndFunc) ();
     
    bool bHook;
    int nbEntree;
     
    TInitFunc InitHooks; // fonction d'initialisation des hooks
    TEndFunc EndHooks; // fonction de suppression des hooks
    HINSTANCE hinstDLL; // instance de la DLL
     
    /*  Declare Windows procedure  */
    LRESULT CALLBACK procedureFenetrePrincipale (HWND, UINT, WPARAM, LPARAM);
    VOID RemplieFenetrePrincipale(HWND fenetrePrincipale);
    VOID NotificationControle(HWND fenetrePrincipale,UINT message, WPARAM wParam, LPARAM lParam);
    VOID ActionCheckBox(int index,HWND hCtl,HWND fenetrePrincipale);
    void dessineTexte (HWND fenetreCiblee, char *chaine, int left, int top);
     
    int WINAPI WinMain (HINSTANCE cetteInstance, HINSTANCE precedenteInstance, LPSTR lignesDeCommande, int modeDAffichage) {
     
        HWND fenetrePrincipale;     /* This is the handle for our window */
        MSG messages;               /* Here messages to the application are saved */
        WNDCLASS classeFenetre;    /* Data structure for the windowclass */
     
        /* The Window structure */
        classeFenetre.style = 0;                             /* None */
        classeFenetre.lpfnWndProc = procedureFenetrePrincipale;     /* This function is called by windows */
        classeFenetre.cbClsExtra = 0;                      /* No extra bytes after the window class */
        classeFenetre.cbWndExtra = 0;                      /* No extra bytes after the window class */
        classeFenetre.hInstance = NULL;
        classeFenetre.hIcon = LoadIcon (NULL, IDI_APPLICATION);
        classeFenetre.hCursor = LoadCursor (NULL, IDC_ARROW);
        classeFenetre.hbrBackground = (HBRUSH)(1 + COLOR_BTNFACE);
        classeFenetre.lpszMenuName = NULL;                 /* No menu */
        classeFenetre.lpszClassName = "classeF";
     
        /* Register the window class, and if it fails quit the program */
        if (!RegisterClass(&classeFenetre)) return FALSE;
     
        /* The class is registered, let's create the program*/
        fenetrePrincipale = CreateWindow(
            "classeF",
            "Première fenêtre en winAPI !",
            WS_OVERLAPPEDWINDOW, /*Style qui permet d'avoir une fenêtre tout ce qu'il y a de plus normale : barre de titre, menu système (réduire, maximiser, fermer), bordure etc...*/
            CW_USEDEFAULT, // Permet à l'OS de déterminer dynamiquement la position de la fenêtre
            CW_USEDEFAULT, //Idem
            450,
            320,
            NULL, // Pas de fenêtre parent, puisque c'est la principale
            NULL, //Aucun menu ne lui est associé
            cetteInstance,
            NULL); // Aucun paramètre à lui envoyer en plus
     
        if (!fenetrePrincipale) return FALSE;
     
        /* Make the window visible on the screen */
        ShowWindow(fenetrePrincipale, modeDAffichage);
        UpdateWindow(fenetrePrincipale);
     
        /* Run the message loop. It will run until GetMessage() returns 0 */
        while (GetMessage(&messages, NULL, 0, 0)) {
            /* Translate virtual-key messages into character messages */
            TranslateMessage(&messages);
            /* Send message to WindowProcedure */
            DispatchMessage(&messages);
        }
     
        /* The program return-value is 0 - The value that PostQuitMessage() gave */
        return messages.wParam;
    }
     
     
    /*  This function is called by the Windows function DispatchMessage()  */
    LRESULT CALLBACK procedureFenetrePrincipale(HWND fenetrePrincipale, UINT message, WPARAM wParam, LPARAM lParam) {
     
        char texte[] = "Pressions de ENTREE : 0";
     
        switch (message) {
            case WM_CREATE:
                RemplieFenetrePrincipale(fenetrePrincipale);
                return 0;
            case WM_PAINT:
                sprintf(texte, "Pressions de ENTREE : %d",nbEntree);
                dessineTexte(fenetrePrincipale, texte, 20, 80);
                return 0;
     
            case WM_COMMAND:
                NotificationControle(fenetrePrincipale,message,wParam,lParam);
                return 0;
     
            case WM_DESTROY:
                if (bHook) EndHooks();
                PostQuitMessage(0);
                return 0;
     
            default:
                return DefWindowProc(fenetrePrincipale, message, wParam, lParam);
        }
    }
     
    VOID RemplieFenetrePrincipale(HWND fenetrePrincipale) {
     
        HWND hGroup = CreateWindow(
            "BUTTON",
            "La check box",
            WS_CHILD|WS_VISIBLE|BS_GROUPBOX,
            10,10,
            200,50,
            fenetrePrincipale,
            NULL,
            instance,
            NULL);
        {
            HWND hControle;
            // une check box automatique deux états
            hControle=CreateWindow(
                "BUTTON",
                "Hook (ON/OFF)",
                WS_CHILD|WS_VISIBLE|BS_AUTOCHECKBOX,
                10+10,10+20,
                180,20,
                fenetrePrincipale,
                (HMENU)ID_CHECKBOX_1,
                instance,
                NULL);
        }
     
        bHook = false;
        hinstDLL = LoadLibrary("hook.dll");
        if (!hinstDLL) // Erreur lors du chargement de la librairie ?
            MessageBox(fenetrePrincipale,"Impossible de charger la librairie.","gloups",MB_OK);
        else {
            // On récupère les adresses des fonctions
            InitHooks = (TInitFunc)GetProcAddress(hinstDLL, "InitHook");
            EndHooks = (TEndFunc)GetProcAddress(hinstDLL, "EndHook");
        }
     
    }
     
    VOID NotificationControle(HWND fenetrePrincipale,UINT message, WPARAM wParam, LPARAM lParam) {
        UINT iId=LOWORD(wParam);
        HWND hCtl=(HWND)lParam;
     
        switch(iId) {
            case ID_CHECKBOX_1:
                ActionCheckBox(iId-ID_CHECKBOX_1,hCtl,fenetrePrincipale);
                break;
        }
    }
     
    VOID ActionCheckBox(int index,HWND hCtl,HWND fenetrePrincipale) {
        // test si la check box est cochée, non cochée ou inderterminée.
        LRESULT lRes=SendMessage(hCtl,BM_GETCHECK,0,0);
        CHAR lpMessage[128];
     
        sprintf(lpMessage,"La check box n°%d est maintenant %s",index,
            (lRes==BST_CHECKED)?"cochée":
            (lRes==BST_UNCHECKED)?"décochée":"inderterminée");
     
        MessageBox(fenetrePrincipale,lpMessage,"Vous avez modifié une check box",
            MB_ICONINFORMATION|MB_OK);
     
        if (hinstDLL) { // Vérifie que la librairie est chargée, sinon, inutile de continuer
            if (lRes==BST_CHECKED) { // Activer les hooks
                nbEntree = 0; // On réinitialise le compteur
                InitHooks(fenetrePrincipale); // On initialise les hooks
            } else { // Désactiver les hooks
                EndHooks(); // On supprime les hooks
            }
        }
     
    }
     
    void dessineTexte(HWND fenetreCiblee, char *chaine, int left, int top) {
        //Déclarations préalables
        PAINTSTRUCT ps;
        HDC dc;
     
        //Récupération de la surface de dessin dans dc
        dc = BeginPaint(fenetreCiblee, &ps);
     
        //Permet au texte d'avoir un fond transparent
        SetBkMode(dc, TRANSPARENT);
        //Applique la couleur de texte au dc
        SetTextColor(dc, 0x00000000);
     
        //Affichage du texte
        TextOut(dc, left, top, chaine, strlen(chaine));
        //TextOut(dc, 40, 50, "Toto", 4);
     
        //Libération de la surface et du dc
        EndPaint(fenetreCiblee, &ps);
     
        return;
    }
    Merci d'avance pour votre aide

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 2
    Dernier message: 12/05/2009, 18h32
  2. Problème de traduction du tutoriel sur les VBO
    Par Lung dans le forum OpenGL
    Réponses: 18
    Dernier message: 19/01/2009, 17h00
  3. Comment proceder pour publier un tutoriel sur developpez ?
    Par KING_OF_GRACELAND dans le forum Mode d'emploi & aide aux nouveaux
    Réponses: 9
    Dernier message: 04/05/2008, 18h22
  4. Réponses: 2
    Dernier message: 30/01/2008, 11h35

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo