Echange de données entre processus

Partagez votre expérience de PureBasic avec les autres utilisateurs.
nico
Messages : 3702
Inscription : ven. 13/févr./2004 0:57

Echange de données entre processus

Message par nico »

Code : Tout sélectionner

;C'est une simple démonstration d'échange de données entre processus
;je recommande de compiler le code pour l'essayer
;ensuite, il faut exécuter deux fois l'exécutable
;la structure info peut prendre plusieurs variables mais pas de chaine
;pour l'exemple, ne pas toucher à la structure info

Structure info
  a.l
EndStructure
 
Procedure MaProcedureCallback(WindowID, Message, wParam, lParam) 
  Resultat = #PB_ProcessPureBasicEvents
  Select Message 
    Case #WM_COPYDATA
      *copie.COPYDATASTRUCT=lParam
        Select *copie\dwData
          Case 12
            *donnee.info=*copie\lpData
            SetGadgetText(1, Str(*donnee\a))
            ProcedureReturn 0
      EndSelect
  EndSelect
  ProcedureReturn Resultat 
EndProcedure 

If FindWindow_( 0, "Fenêtre 1" )
  test.l=1
EndIf 

If OpenWindow(0, 600, 200, 200, 200, #PB_Window_SystemMenu | #PB_Window_MinimizeGadget | #PB_Window_MaximizeGadget, "Fenêtre 1")
  If test=1
    SetWindowTitle(0, "Fenêtre 2")
  EndIf
  
  CreateGadgetList(WindowID(0))
  TextGadget(0, 20, 10,160,20,"Donnée numériques reçues")
  StringGadget(1,20, 30,160,20,"")
  TextGadget(2, 20, 70,160,20,"Donnée numériques à envoyer")
  StringGadget(3,20, 90,160,20,"")
  ButtonGadget(4, 20, 120, 160, 20, "Envoyer donnée") 
  
  SetWindowCallback(@MaProcedureCallback())   
  Repeat
    EventID.l = WaitWindowEvent()
    Select EventID
      Case #PB_EventGadget
        Select EventGadgetID()      
          Case 4
            donnee.info 
            donnee\a=Val(GetGadgetText(3)) 
            
            envoie.COPYDATASTRUCT   
            envoie\dwData=12
            envoie\cbData=SizeOf(donnee)
            envoie\lpData=@donnee
            
            Resultat$ = GetWindowTitle(0) 
            If Resultat$="Fenêtre 1"
              cible.l = FindWindow_( 0, "Fenêtre 2" )
            Else
              cible.l = FindWindow_( 0, "Fenêtre 1" )
            EndIf
            
            If cible
              SendMessage_(cible, #WM_COPYDATA, WindowID(0), envoie)
            Else 
              MessageRequester("Info","Cible non trouvée")
            EndIf 
        EndSelect
         
      Case #PB_Event_CloseWindow  
           Quit = 1
    EndSelect
  Until Quit = 1 
EndIf
End  
:)
Avatar de l’utilisateur
Kwai chang caine
Messages : 6989
Inscription : sam. 23/sept./2006 18:32
Localisation : Isere

Message par Kwai chang caine »

Bonjour Nico

J'ai essayé ton joli code, mais chez moi, il ne me remonte que zero dans le champ du haut.

J'ai compilé, puis démarré 2 fois, et rien touché, ou ai-je merdé ???

Merci et bonne soiree
ImageLe bonheur est une route...
Pas une destination

PureBasic Forum Officiel - Site PureBasic
nico
Messages : 3702
Inscription : ven. 13/févr./2004 0:57

Message par nico »

Je pense que tu n'as pas lu l'entête du code!

Le code ne sert pas à envoyer du texte mais une valeur numérique.
Avatar de l’utilisateur
Kwai chang caine
Messages : 6989
Inscription : sam. 23/sept./2006 18:32
Localisation : Isere

Message par Kwai chang caine »

Bonjour NICO

Tu as entierement raison.
Et pourtant j'avais bien lu les instructions.(Sisi je te jure) :(
Et en plus c'est encore marqué sur le masque de l'application. :oops:

Cela paraissait tellement evident que l'on puisse envoyer du texte.

En tout cas, il est genial ce code meme qu'avec des chiffres.

Encore merci de ta patience.
Excelente journée
ImageLe bonheur est une route...
Pas une destination

PureBasic Forum Officiel - Site PureBasic
nico
Messages : 3702
Inscription : ven. 13/févr./2004 0:57

Message par nico »

Ben en fait, on peut aussi envoyer du texte mais c'est plus contraignant, il faut dans la structure mettre un tableau et copier la chaine dans ce tableau, je ferais un exmple ce soir!
Backup
Messages : 14526
Inscription : lun. 26/avr./2004 0:40

Message par Backup »

crois tu que ces fonctions Api puisse permettre de recuperer
l'adresse de debut et de fin d'un process en Memoire

genre tu lance Notepad , y a t'il moyen a l'aide de ces commande Api de recuperer l'emplacement du DEbut et de Fin de Ce Notepad ??

a quoi pensai-je la ?

ben imagine que tu surveille le segment memoire (entre debut et Fin) d'un Jeu en memoire , il serai peut etre facile de se pacher un nombre de vie infini
ou bien se rajouter de l'argent en "live"

il suffirai d'indiquer la valeur que l'on surveille dans le segment memoire
et proceder par elimination , a chaque changement de la valeur dans le jeu on regarde dans la Ram , et on note l'adresse qui contient la valeur changé
apres plusieurs essai on serai sur que l'adresse contiens bien la valeur qui correspond au niveau de vie !!

bref faire comme le logiciel RAM Cheat
http://www.winhex.com/ramcheat-f.html


***************************************
:D :D
nico
Messages : 3702
Inscription : ven. 13/févr./2004 0:57

Message par nico »

@Dobro, ça doit être possible avec WriteProcessMemory mais je n'en sais pas plus!

@Kwai chang caine,

Code : Tout sélectionner

Structure info 
  a.b[25]  ; la chaine sera limité à (25-1)= 24 caractères
           ; le dernier octet sera toujours à zero
EndStructure 
  
Procedure MaProcedureCallback(WindowID, Message, wParam, lParam) 
  Resultat = #PB_ProcessPureBasicEvents 
  Select Message 
    Case #WM_COPYDATA 
      *copie.COPYDATASTRUCT=lParam 
        Select *copie\dwData 
          Case 12 
            *donnee.info=*copie\lpData 
            SetGadgetText(1, PeekS(@*donnee\a[0])) 
            ProcedureReturn 0 
      EndSelect 
  EndSelect 
  ProcedureReturn Resultat 
EndProcedure 

If FindWindow_( 0, "Fenêtre 1" ) 
  test.l=1 
EndIf 

If OpenWindow(0, 600, 200, 200, 200, "Fenêtre 1", #PB_Window_SystemMenu | #PB_Window_MinimizeGadget | #PB_Window_MaximizeGadget) 
  If test=1 
    SetWindowTitle(0, "Fenêtre 2") 
  EndIf 
  
  CreateGadgetList(WindowID(0)) 
  TextGadget(0, 20, 10,160,20,"Chaine de caractère reçue") 
  StringGadget(1,20, 30,160,20,"") 
  TextGadget(2, 20, 60,160,40,"Chaine de caractère à envoyer (longueur < à 255)") 
  StringGadget(3,20, 90,160,20,"") 
  ButtonGadget(4, 20, 120, 160, 20, "Envoyer la chaine") 
  
  SetWindowCallback(@MaProcedureCallback())    
  Repeat 
    EventID.l = WaitWindowEvent() 
    Select EventID 
      Case #PB_Event_Gadget 
        Select EventGadget()      
          Case 4 
            donnee.info 
            ; Initialise le tableau avec des zéros avnt chaque envoie
            ZeroMemory_(@donnee\a[0],25)
            ;--------------------------------------------------------
            chaine.s=GetGadgetText(3)
            If Len(chaine)<25  ; Important la chaine doit être inférieur d'1 octet au tableau
                                ; pour que la chaine se termine par un zero
                CopyMemory(@chaine,@donnee\a[0],Len(chaine))
            EndIf 
            
            envoie.COPYDATASTRUCT    
            envoie\dwData=12 
            envoie\cbData=SizeOf(info) 
            envoie\lpData=@donnee
            
            Resultat$ = GetWindowTitle(0) 
            If Resultat$="Fenêtre 1" 
              cible.l = FindWindow_( 0, "Fenêtre 2" ) 
            Else 
              cible.l = FindWindow_( 0, "Fenêtre 1" ) 
            EndIf 
            
            If cible 
              SendMessage_(cible, #WM_COPYDATA, WindowID(0), envoie) 
            Else 
              MessageRequester("Info","Cible non trouvée") 
            EndIf 
        EndSelect 
          
      Case #PB_Event_CloseWindow  
           Quit = 1 
    EndSelect 
  Until Quit = 1 
EndIf 
End  
Dr. Dri
Messages : 2527
Inscription : ven. 23/janv./2004 18:10

Message par Dr. Dri »

@nico
t'as essayé .s{taille} dans ta structure ? c'est peut etre plus simple à gérer

Dri
nico
Messages : 3702
Inscription : ven. 13/févr./2004 0:57

Message par nico »

J'ai pas essayé car c'est interdit , on est obligé de passer par un tableau mais finalement on y arrive très bien.
Dr. Dri
Messages : 2527
Inscription : ven. 23/janv./2004 18:10

Message par Dr. Dri »

bah pour moi ca fonctionne ca:

Code : Tout sélectionner

Structure info
  a.s{25}
EndStructure

t.info

t\a = Space(50)
Debug Len(t\a)
[edit]
carrément plus simple à gérer

Dri
gnozal
Messages : 832
Inscription : mar. 07/déc./2004 17:35
Localisation : France
Contact :

Message par gnozal »

Jetez un coup d'oeil au code source de jaPBe.
Le message #wm_copydata est utilisé pour envoyer / recevoir du texte lors de la communication avec les plugins.
KarLKoX
Messages : 1191
Inscription : jeu. 26/févr./2004 15:36
Localisation : France
Contact :

Message par KarLKoX »

C'est un peu ce qu'utilise nico :roll:
"Qui baise trop bouffe un poil." P. Desproges
Dr. Dri
Messages : 2527
Inscription : ven. 23/janv./2004 18:10

Message par Dr. Dri »

Voila un exemple avec une chaine de taille fixe

Code : Tout sélectionner

Structure info  ;MODIF ICI
  a.s{24}  ; la chaine sera limité à 24 caractères
           ; le dernier octet sera toujours à zero
EndStructure
 
Procedure MaProcedureCallback(WindowID, Message, wParam, lParam)
  Resultat = #PB_ProcessPureBasicEvents
  Select Message
    Case #WM_COPYDATA
      *copie.COPYDATASTRUCT=lParam
        Select *copie\dwData
          Case 12
            *donnee.info=*copie\lpData
            SetGadgetText(1, *donnee\a) ;MODIF ICI
            ProcedureReturn 0
      EndSelect
  EndSelect
  ProcedureReturn Resultat
EndProcedure

If FindWindow_( 0, "Fenêtre 1" )
  test.l=1
EndIf

If OpenWindow(0, 600, 200, 200, 200, "Fenêtre 1", #PB_Window_SystemMenu | #PB_Window_MinimizeGadget | #PB_Window_MaximizeGadget)
  If test=1
    SetWindowTitle(0, "Fenêtre 2")
  EndIf
 
  CreateGadgetList(WindowID(0))
  TextGadget(0, 20, 10,160,20,"Chaine de caractère reçue")
  StringGadget(1,20, 30,160,20,"")
  TextGadget(2, 20, 60,160,40,"Chaine de caractère à envoyer (longueur < à 255)")
  StringGadget(3,20, 90,160,20,"")
  ButtonGadget(4, 20, 120, 160, 20, "Envoyer la chaine")
 
  SetWindowCallback(@MaProcedureCallback())   
  Repeat
    EventID.l = WaitWindowEvent()
    Select EventID
      Case #PB_Event_Gadget
        Select EventGadget()     
          Case 4
            donnee.info\a = GetGadgetText(3) ;MODIF ICI
           
            envoie.COPYDATASTRUCT   
            envoie\dwData=12
            envoie\cbData=SizeOf(info)
            envoie\lpData=@donnee
           
            Resultat$ = GetWindowTitle(0)
            If Resultat$="Fenêtre 1"
              cible.l = FindWindow_( 0, "Fenêtre 2" )
            Else
              cible.l = FindWindow_( 0, "Fenêtre 1" )
            EndIf
           
            If cible
              SendMessage_(cible, #WM_COPYDATA, WindowID(0), envoie)
            Else
              MessageRequester("Info","Cible non trouvée")
            EndIf
        EndSelect
         
      Case #PB_Event_CloseWindow 
           Quit = 1
    EndSelect
  Until Quit = 1
EndIf
End 
Dri ;)
Avatar de l’utilisateur
Kwai chang caine
Messages : 6989
Inscription : sam. 23/sept./2006 18:32
Localisation : Isere

Message par Kwai chang caine »

Merci Nico.

Cela va m'etre drolement utile pour passer des données entre un exe sortant appelant un autre exe pour prendre sa suite. :10:

Passe une bonne journée.
ImageLe bonheur est une route...
Pas une destination

PureBasic Forum Officiel - Site PureBasic
erix14
Messages : 480
Inscription : sam. 27/mars/2004 16:44
Contact :

Message par erix14 »

Je pense que le plus simple c'est de récupérer directement le contenu du gadget, comme cela il n'y a aucune limite de taille.

Code : Tout sélectionner

Structure info
    hString.l
EndStructure
 
Procedure MaProcedureCallback(WindowID, message, wParam, lParam)
    Resultat = #PB_ProcessPureBasicEvents
    Select message
        Case #WM_COPYDATA
            *copie.COPYDATASTRUCT=lParam
            Select *copie\dwData
                Case 12
                    *donnee.info=*copie\lpData
                    LongueurTexte = SendMessage_(*donnee\hString, #WM_GETTEXTLENGTH, 0, 0)+1
                    Texte.s = Space(LongueurTexte)
                    SendMessage_(*donnee\hString, #WM_GETTEXT, LongueurTexte, @Texte)
                    SetGadgetText(1, Texte)
                    ProcedureReturn 0
            EndSelect
    EndSelect
    ProcedureReturn Resultat
EndProcedure

If FindWindow_( 0, "Fenêtre 1" )
    test.l=1
EndIf

If OpenWindow(0, 600, 200, 200, 200, "Fenêtre 1", #PB_Window_SystemMenu | #PB_Window_MinimizeGadget | #PB_Window_MaximizeGadget)
    If test=1
        SetWindowTitle(0, "Fenêtre 2")
    EndIf
    
    CreateGadgetList(WindowID(0))
    TextGadget(0, 20, 10,160,20,"Chaine de caractère reçue")
    StringGadget(1,20, 30,160,20,"")
    TextGadget(2, 20, 60,160,40,"Chaine de caractère à envoyer (longueur < à 255)")
    donnee.info\hString = StringGadget(3,20, 90,160,20,"")
    ButtonGadget(4, 20, 120, 160, 20, "Envoyer la chaine")
    
    SetWindowCallback(@MaProcedureCallback())   
    Repeat
        EventID.l = WaitWindowEvent()
        Select EventID
            Case #PB_Event_Gadget
                Select EventGadget()     
                    Case 4
                        envoie.COPYDATASTRUCT   
                        envoie\dwData=12
                        envoie\cbData=SizeOf(info)
                        envoie\lpData=@donnee
                        
                        Resultat$ = GetWindowTitle(0)
                        If Resultat$="Fenêtre 1"
                            cible.l = FindWindow_( 0, "Fenêtre 2" )
                        Else
                            cible.l = FindWindow_( 0, "Fenêtre 1" )
                        EndIf
                        
                        If cible
                            SendMessage_(cible, #WM_COPYDATA, WindowID(0), envoie)
                        Else
                            MessageRequester("Info","Cible non trouvée")
                        EndIf
                EndSelect
                
            Case #PB_Event_CloseWindow
                Quit = 1
        EndSelect
    Until Quit = 1
EndIf
End
Répondre