Page 1 sur 4

[R] Récupérer le contenu de cmd.exe Sous MMB + Codes Source

Posté : lun. 17 janv. 2011 17:12
par Anthony
Problème résolu, le code source est disponible ici:
http://autoitscript.fr/forum/viewtopic. ... 744#p44744


Bonjour,

Etant newbies avec AutoIt je cherche depuis quelques jours la fonction qui me permettrai de récupérer
le contenu de cmd.exe et de l'injecter dans mon application sous forme de variable.
L'envoi est possible et sans problèmes grâce à ce code:
► Afficher le texte
Je sais que c'est possible car la solution est dans ces 2 codes
MMBLib.au3
► Afficher le texte


MPlayerController.au3
► Afficher le texte
Le but étant de récupérer ces 3 informations en 3 variables (Title$,Batch$,LastLine$)
La variable $ est inversé dans:
AutoIt => $Title
MMB => Title$
1° le nom de la fenêtre (Title$ dans MMB) => C:\Windows\system32\cmd.exe
2° le contenu (Batch$ dans MMB)
► Afficher le texte
3° La dernière ligne (LastLine$ dans MMB) => [0.1%] 160/123122 frames, 17.78 fps, 1962.91 kb/s, eta 1:55:16

Je met à disposition le programme de test
how get.rar
how get.rar
(508.27 Kio) Téléchargé 308 fois
Je mettrai le Fichier code source MMB quand tout sera OK, la richesse ne vaut que si elle est partagé

Re: [..] Récupérer le contenu de cmd.exe

Posté : lun. 17 janv. 2011 18:19
par Tlem
Regardez dans la documentation en tapant StdoutRead dans la recherche. L'exemple qui y est joint, est plus que parlant ... ;)

Re: [..] Récupérer le contenu de cmd.exe

Posté : lun. 17 janv. 2011 19:12
par Anthony
J'ai trouvé çà mais je ne vois pas comment ce scripte fonctionne...
► Afficher le texte
► Afficher le texte

Re: [..] Récupérer le contenu de cmd.exe

Posté : lun. 17 janv. 2011 22:44
par Tlem
Voici le script d'exemple vu sous un autre angle :

Code : Tout sélectionner

#include <Constants.au3>

; Exemple de l'utilisation d'un DIR sur le dossier Windows.
Local $Stream = Run(@ComSpec & " /c dir C:\windows", @SystemDir, @SW_HIDE, $STDERR_CHILD + $STDOUT_CHILD)
Local $line
While 1
    $line = StdoutRead($Stream)
    If @error Then ExitLoop
    FileWrite("Test.txt", $line)
Wend
ShellExecute("Test.txt")
:mrgreen:

Re: [..] Récupérer le contenu de cmd.exe

Posté : mar. 18 janv. 2011 14:44
par Anthony
Erreur -1 j'ai passé la nuit dessus :shock:
Je cherche juste à récupérer le contenu en variable ou alors je suis neuneu.
Au moins dans: MsgBox(0, "Path de $handle", "$handle")

Code : Tout sélectionner

#include <Constants.au3>
; Change into the WinTitleMatchMode that supports classnames and handles
AutoItSetOption("WinTitleMatchMode", 4)
AutoItSetOption("WinSearchChildren", 1)
; Get the handle of a cmd.exe window (from its classname)
$handle = WinGetHandle("classname=ConsoleWindowClass", "")

Local $Stream = Run(@ComSpec & " /c " $handle, @SW_HIDE, $STDERR_CHILD + $STDOUT_CHILD)
Local $line
While 1
    $line = StdoutRead($Stream)
    If @error Then ExitLoop
    #FileWrite("Test.txt", $line)
    MsgBox(0, "", "$line")
Wend
ShellExecute("Test.txt")

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : mar. 18 janv. 2011 15:36
par TommyDDR
Hum, regardez plus attentivement l'aide du Run()

en réalité, @Comspec contient le chemin de votre executable cmd.exe (en général : C:\Windows\System32\cmd.exe)

Et un Run() sert à executer un fichier.

Or vous écrivez :

Code : Tout sélectionner

$handle = WinGetHandle("classname=ConsoleWindowClass", "")

Local $Stream = Run(@ComSpec & " /c " $handle, @SW_HIDE, $STDERR_CHILD + $STDOUT_CHILD)
Traduction :
- Run : Execute
- @ComSpec : cmd.exe
- /c : Interprete la commande (Commande DOS à entrer ensuite)
- $handle : 0x14A8E8 (j'invente la)

Cependant ... 0x14A8E8 n'est pas une commande DOS.

Ce qu'il vous faudrai c'est rediriger les sorties standard ($STDERR_CHILD + $STDOUT_CHILD) d'un process déjà existant vers votre process.
Mais Run sert à créer le dit process.

En esperant que quelqu'un pourra vous aider.

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : mar. 18 janv. 2011 16:18
par Anthony
Merci d'éclaircir le sujet TommyDDR :wink:

En fait j'ai trouvé pourquoi çà ne marche pas, je m'éxplique.
L'aide que je demandais est de récupérer le contenu du cmd.exe qui est inclu dans mon programme demo.
Sous MMB cette fonction est (Binder) qui lance la commande (cmd.exe /K).
Il ne s'agit pas de lancer une ligne de commande et de récupérer le contenu mais de récupérer le contenu de la fenêtre déjà existante par le ($handle) de mon application.
Sans télécharger mon application de démo vous ne verez pas trop de quoi je parle.
Il suffit de taper (dir *.* /s/p) sur la ligne de commande qui se trouve juste devant (SEND).
L'application de test est en pièce jointe dans le premier message.

Cordialement.

Image
Image

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : mar. 18 janv. 2011 17:11
par Anthony
J'ai réussi à récupérer ces infos:
► Afficher le texte
Quelle serai la fonction pour récupérer le batch complet avec la progression ?

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : mar. 18 janv. 2011 22:18
par TommyDDR
Hum, à voir votre impression écran, je dirai que le cmd.exe est bel et bien un 2nd processus dont on lui a dit "Je suis ta fenêtre parent)

Surement un :

Code : Tout sélectionner

_WinAPI_SetParent($HandleCmd, $HandleGui)
Désolé de ne pas vous aider plus que ça.
Vérifiez si vous avez bien un 2nd process nommé cmd.exe dans votre gestionnaire (Ctrl+Shift+Echap / onglet processus)

Si oui : Il faudra surement essayer de redirigé les sorties de celui ci vers votre programme.

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : mer. 19 janv. 2011 00:00
par Anthony
C'est exactement çà cmd.exe est chargé dans un second processus, mais la ligne de commande cmd.exe n'est pas modifiable une fois le programme compilé c'est pour cette raison que je me suis tourné vers AutoIt.
Je vais tester ton bout de code......
En tout cas encore merci de te pencher sur le sujet et à Tlem ;-)
J'encourage les autres car çà à l'air plus compliqué que prévu :roll:

Pour vérifier il faut le fichier joint, pas de panique pas de virus :!:

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : mer. 19 janv. 2011 00:20
par Tlem
Récupérer ces infos via l'interface ne me semble pas viable.
Vous allez devoir récupérer le stream de cette fenêtre DOS que visiblement vous ne pouvez contrôler.
Je ne suis pas certains que cela soit possible avec AutoIt, mais essayez de faire une recherche sur le forum, pour voir si ce sujet n'aurait pas déjà été abordé, ou alors posez clairement votre question sur le forum Anglais. ;)

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : mer. 19 janv. 2011 01:31
par Anthony
J'ai trouvé comment renvoyer une valeur AutoIt dans MMB grace à cette fonction :D

Code : Tout sélectionner

#$Param = "Title$='Yes çà marche'" & @LF & 'Message("Ce code est envoyé par AutoIt","Title$")'
SendScriptMMB("MMBTitle", $Param)
Par contre j'ai du mal avec l'ajout de variable (2° ligne) je ne voit pas ce qui n'est pas bon ici:

Code : Tout sélectionner

$text = WinGetText("MMBTitle", "")
$Param = "Title$='" & $text & "'"
SendScriptMMB("MMBTitle", $Param)
Devrait donner dans MMB:

Code : Tout sélectionner

Title$='C:\Windows\system32\cmd.exe'
mais donne:

Code : Tout sélectionner

Title$='C:\Windows\system32\cmd.exe
Car il manque à la fin de la variable: Résultat:
Image

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : mer. 19 janv. 2011 12:31
par Anthony
En fait ce qui est envoyé en variable est:

Code : Tout sélectionner

Title$='C:\Windows\system32\cmd.exe
'
Il y à un retour à la ligne qui s'est ajouté à la fin de la variable et comment la supprimer ?
J'ai vérifié avec cette commande:

Code : Tout sélectionner

$text = WinGetText("MMBTitle", "")
$Param = "Title$='" & $text & "'"
MsgBox(0, "Full title read was:", $Param)
Ce qui donne:
Image

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : mer. 19 janv. 2011 23:45
par Anthony
La variable éronnée n'est pas récupérable s'il y à un retour à la ligne.
Comment puis-je supprimer ce saut de ligne ? Aux dieux tous puissants :roll:

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : jeu. 20 janv. 2011 00:01
par Tlem
Avec StringReplace par exemple. :roll:

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : jeu. 20 janv. 2011 23:32
par Anthony
Génial çà commence à me plaire tout çà :D

Y à t'il une fonction pour accélérer ce script ?

Code : Tout sélectionner

$Param=$CmdLine[1]
For $i = 1 to $Param_Len 
  $CharSend=StringMid($Param,$i,1)
  Send($CharSend)
Next
Du genre:

Code : Tout sélectionner

Send($CmdLine[1])

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : ven. 21 janv. 2011 00:40
par Tlem
Que contient $CmdLine[1] ?
D’où sort $Param_Len ?
Si je comprend votre code, celui-ci doit envoyer à la fenêtre active le contenu de $Param, caractère par caractère.
Donc Send($Param) est sensé envoyer la totalité des caractères à la fenêtre active. Par contre attention au retour chariot et retour de ligne (@CR et @LF ou @CRLF). :roll:
Si Send ne convient pas, essayez ControlSend.

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : ven. 21 janv. 2011 10:08
par Anthony
Encore merci d'être là :wink:
Avec ControlSend c'est pas plus rapide ou j'ai fait une érreur:

Code : Tout sélectionner

ControlSend("", "", $handle,$Param)
çà fait la même chose que:

Code : Tout sélectionner

For $i = 1 to $Param_Len 
  $CharSend=StringMid($Param,$i,1)
  Send($CharSend)
Next
Voici mon code actuellement:
► Afficher le texte

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : ven. 21 janv. 2011 21:43
par Tlem
Voici ce qui est écrit dans la documentation de la commande ControlSend :

Code : Tout sélectionner

ControlSend ( "title", "text", controlID, "string" [, flag] )

[b]Parameters[/b]
title           The title of the window to access. 
text            The text of the window to access. 
controlID       The control to interact with. See Controls. 
string          String of characters to send to the control. 
flag [optional]     Changes how "keys" is processed:
                     flag = 0 (default), Text contains special characters like + to indicate SHIFT and {LEFT} to indicate left arrow.
                     flag = 1, keys are sent raw.
Comme vous pouvez le relire, le troisième paramètre et un ControlID et non un handle !
Or un ControlID n'est unique que dans une seul interface, c'est à dire que si vous avez plusieurs fenêtres ouvertes, alors vous avez inexorablement plusieurs ControlID identiques.
Vous devez donc préciser le titre de la fenêtre ou alors (là vous pouvez le faire) utiliser le handle de la fenêtre.

Re: [..] Récupérer le contenu de cmd.exe (pour newbies)

Posté : dim. 23 janv. 2011 12:14
par Anthony
Donc si je peu le faire j'ai aucun risque de voir mes commandes AutoIt partir dans une autre fenêtre ?
N'y à t'il pas la possibilité de faire comme un copier coller qui serai instantané, en évitant le presse papier ?