Avatar billede djfonzi Nybegynder
06. februar 2011 - 12:24 Der er 24 kommentarer

Læse output fra en exe fil (cmd) til en textbox ?

Hey Eksperter

Jeg sidder og roder med lidt simpel programmering..

Problemstillingen var at jeg havde to programmer der skulle køre.. Et som kørte i full screen og et andet som skulle køre bagved og holde øje med netværkspakker osv..

Mit "program" gør at den starter dette værktøj og tilfører det  det nødvendige input for at være klar og derefter starter det andet program, så man ikke behøver andet end at starte mit program op.. Simpelt!

Dog vil jeg gerne have det lavet sådan, at det program jeg har lavet, viser det bagved liggendes output i en textbox.. Det cmd lignende program der kører bagved kommer nemlig konstant med output, og det er så dette jeg gerne vil have vist i mit vb.net program!

Input er ikke nødvendigt.. Kun outputtet skal jeg have vist i min textbox og det skal helst opdatere med det samme outputtet kommer i det bagved liggende cmd program (eller inden for 3 seks ca)!

Nogen som har nogle idéer ? Er det noget med Pipes ?

NB : Bær lige over med mig for jeg har aldrig programmeret før !
Avatar billede claes57 Ekspert
06. februar 2011 - 12:36 #1
jeg har en gang lavet noget i vb (før .net) med chkdsk - der kunne jeg hente chkdsk data løbende (% færdig), og vise det i mit program.
Chkdsk kørte så i et skjult vindue uden at blive vist på processlinjen - kun mit program var synligt.
Der var så noget med vb ikke blev opdateret (pga .net fremkomst) og sikkerhed i vista/win7 forhindrede den type kald - men .net må da have tilsvarende mulighed.
Jeg har sourcekoden liggende, hvis du kan bruge den til noget.
Avatar billede djfonzi Nybegynder
06. februar 2011 - 12:49 #2
Det kunne da være interresant at kigge på, men fatter bare ikke at skrive koden om :P
Avatar billede nissen2630 Novice
06. februar 2011 - 12:59 #3
Måske dette link kan hjælpe lidt på vej:
http://www.codeguru.com/forum/showthread.php?threadid=460918
Avatar billede nissen2630 Novice
06. februar 2011 - 13:51 #4
Var det ikke en ide at se lidt på denne liste : http://www.eksperten.dk/list/aabnespoergsmaal/djfonzi

Det fremmer tit hastigheden for en løsning på det problem man står med.

Hvis du er i tvivl om hvordan man afslutter sine spørgsmål bør du læse : http://www.eksperten.dk/faq#faq-4-2
Avatar billede djfonzi Nybegynder
06. februar 2011 - 14:15 #5
nissen2630

Så fik jeg lige ryddet lidt op der ! Har faktisk slet ikke tænkt over det med de point .. Men det er ordnet nu :)
Avatar billede arne_v Ekspert
06. februar 2011 - 15:19 #6
Linket i #3 forklarer fint hvordan det skal gøres i .NET.
Avatar billede djfonzi Nybegynder
06. februar 2011 - 23:50 #7
Jeg prøver det lige af her i løbet af imorgen.. :)
Avatar billede djfonzi Nybegynder
07. februar 2011 - 00:02 #8
Har kigget lidt på det nu .. Og kan selvfølgelig ikke få det til at virke .. :P

Ved ikke om jeg har nævnt det, men det er i Visual Basic .NET 2010 Express jeg sidder med..
Avatar billede nissen2630 Novice
07. februar 2011 - 06:49 #9
Hvis du bruger følgende eks. så skulle det virke.

Du skal lave en tekstbox med navn tb og klikke i tb

Public Class Form1

    Private WithEvents tb As New TextBox

    Sub New()
        InitializeComponent()
        Me.Text = "click the textbox"
        Me.Controls.Add(tb)
        tb.Dock = DockStyle.Fill
        tb.ReadOnly = True
        tb.ScrollBars = ScrollBars.Both
        tb.Multiline = True
        Me.Width = 500
    End Sub

    Sub Go()
        Dim p As New Process
        p.StartInfo.FileName = "ping.exe"
        p.StartInfo.Arguments = "www.bbc.co.uk"
        p.StartInfo.UseShellExecute = False
        p.StartInfo.RedirectStandardOutput = True
        AddHandler p.OutputDataReceived, AddressOf HelloMum
        p.Start()
        p.BeginOutputReadLine()
    End Sub

    Sub HelloMum(ByVal sender As Object, ByVal e As DataReceivedEventArgs)
        UpdateTextBox(e.Data)
    End Sub

    Private Delegate Sub UpdateTextBoxDelegate(ByVal Text As String)
    Private Sub UpdateTextBox(ByVal Tex As String)
        If Me.InvokeRequired Then
            Dim del As New UpdateTextBoxDelegate(AddressOf UpdateTextBox)
            Dim args As Object() = {Tex}
            Me.Invoke(del, args)
        Else
            tb.Text &= Tex & Environment.NewLine
        End If
    End Sub

    Private Sub tb_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles tb.Click
        Go()
    End Sub

End Class

Avatar billede nissen2630 Novice
07. februar 2011 - 07:00 #10
Husk lige at sætte en vertikal scroll bar på din textbox.

eksemplet er lavet i VB 2010 express
Avatar billede djfonzi Nybegynder
07. februar 2011 - 12:05 #11
Tak Nissen har fået ovenstående til at fungere faktisk!

Men det vil kræve en smule tilpasning

Ser du, mit kode er lavet således at det starter et program op og sender et tastetryk til programmet (My.Computer.Keyboard.SendKeys("1", True)). Hvis jeg bruger koden vist ovenfor åbner den så bare programmet igen når det kører det kode. Mon man kan lave det sådan at der i det ovenstående kode, et sted i midten bliver sendt taste trykket 1 til programmet ?
Avatar billede djfonzi Nybegynder
07. februar 2011 - 14:31 #12
Jeg ligger lige mit kode ind så du/i kan se det.. Det kan være det er nemmere at se hvad det er jeg vil hvis du/i kan se koden :)

Public Class Main

    Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
        Dim ProcID As Integer
        RichTextBox1.Text = "* - Starter software..."
        Dim p As New Process
        p.StartInfo.FileName = TextBox1.Text 'softwaren der startes er skrevet i denne tekstboks (blabla.exe)
        p.StartInfo.Arguments = ""
        p.StartInfo.UseShellExecute = False
        p.StartInfo.RedirectStandardOutput = True
        p.StartInfo.RedirectStandardInput = True
        p.StartInfo.CreateNoWindow = True
        AddHandler p.OutputDataReceived, AddressOf HelloMum
        p.Start()
        p.BeginOutputReadLine()
        Dim SW As System.IO.StreamWriter = p.StandardInput
        SW.WriteLine("1") 'her sender jeg kommandoen til programmet så det går igang.
        System.Threading.Thread.Sleep(1000)
        RichTextBox1.Text = RichTextBox1.Text & vbCrLf & "* - Starter sekundær software..."
        System.Threading.Thread.Sleep(500)
        ProcID = Shell(TextBox2.Text, AppWinStyle.NormalFocus)
    End Sub

    Sub HelloMum(ByVal sender As Object, ByVal e As DataReceivedEventArgs)
        UpdateTextBox(e.Data)
    End Sub

    Private Delegate Sub UpdateTextBoxDelegate(ByVal Text As String)

    Private Sub UpdateTextBox(ByVal Tex As String)
        If Me.InvokeRequired Then
            Dim del As New UpdateTextBoxDelegate(AddressOf UpdateTextBox)
            Dim args As Object() = {Tex}
            Me.Invoke(del, args)
        Else
            RichTextBox2.Text &= Tex & Environment.NewLine
        End If
    End Sub
Avatar billede djfonzi Nybegynder
07. februar 2011 - 20:45 #13
Efter at have fiflet meget frem og tilbage med det her, fandt jeg ud af, at den exe fil jeg skal sende kommandoer til ikke understøtter det igennem det her, men kun igennem sendkeys.. Så går jeg ikke ud fra at det kan lade sig gøre :(
Avatar billede nissen2630 Novice
07. februar 2011 - 23:55 #14
Alle programmer der har output til console kan fanges på den beskrevne måde
Avatar billede djfonzi Nybegynder
08. februar 2011 - 08:06 #15
Hmm..

Gad vide hvorfor det så ikke virker.. Nissen, kan du se ud fra det kode jeg har lagt op ovenfor hvad der kan være galt ?
Avatar billede nissen2630 Novice
08. februar 2011 - 08:24 #16
Hvis du tager eksemplet fra #9 og indsætter dit program så skulle det gerne virke. Kan ikke se hvorfor du har omskrevet koden så meget.Det giver ingen mening for mig
Avatar billede djfonzi Nybegynder
08. februar 2011 - 08:47 #17
Jeg kan lige forsøge mig med at skrive mit program ind i det kode i 9# istedet for ping.exe..

Grunden til at jeg har skrevet det om er fordi at jeg faktisk alligevel skal have sendt input til programmet.. Dog drejer det sig bare om ét enkelt tastetryk.
Avatar billede djfonzi Nybegynder
08. februar 2011 - 08:47 #18
Ups skulle ikke være et svar selvf.
Avatar billede djfonzi Nybegynder
08. februar 2011 - 11:46 #19
Har nu forsøgt mig med koden som vist i #9 og det virkede, hvilket også var forventet.. Det kode jeg har lagt op i 12# virker som sådan også.

Men med udgangspunkt i post #9 hvordan får jeg så gjort så jeg kan sede et enkelt tastetryk til programmet ?

Det er jo nok ved hjælp af

p.StartInfo.RedirectStandardInput = True

på en måde, ved bare ikke lige hvordan
Avatar billede nissen2630 Novice
08. februar 2011 - 12:06 #20
Disse bruges til at sende til en app.
SendKeys.Send()
Sendkeys.SendWait()
Avatar billede djfonzi Nybegynder
08. februar 2011 - 12:26 #21
SendKeys er nok nærmere til hvis du åbner en applikation som kører ved siden af.. Så kan du sende tastetryk til applikationen, men i det kode der er skrevet i #9 så åbner applikationen jo inde i ens VB app og derfor skal man på en måde have omdirigeret input til programmet gennem ens app.
Avatar billede nissen2630 Novice
08. februar 2011 - 15:29 #22
p.StartInfo.RedirectStandardInput = True

p.StandardInput.WriteLine()
eller
p.StandardInput.Write
Avatar billede djfonzi Nybegynder
08. februar 2011 - 15:43 #23
Har lige forsøgt med det du skrev Nissen.. Og det virker desværre ikke. Det ser ikke ud som om den modtager det input jeg sender.

Her er lige et uddrag af min kode:
    Sub Go()
        Dim p As New Process
        p.StartInfo.FileName = "test.exe"
        p.StartInfo.Arguments = ""
        p.StartInfo.WindowStyle = ProcessWindowStyle.Hidden
        p.StartInfo.UseShellExecute = False
        p.StartInfo.RedirectStandardOutput = True
        p.StartInfo.RedirectStandardInput = True
        AddHandler p.OutputDataReceived, AddressOf HelloMum
        p.Start()
        p.BeginOutputReadLine()
        System.Threading.Thread.Sleep(1000) 'lige til at give exe filen 1 sekund at starte op i.
        p.StandardInput.Write("1")
    End Sub

Resten af koden er fuldstændigt den samme som den i #9.. Som du kan se bruger jeg System.Threading.Thread.Sleep til at give det program der skal sendes kommando til, 1 sekund til at starte op i.

En anden ting der undrer mig er at p.StartInfo.WindowStyle = ProcessWindowStyle.Hidden ikke ser ud til at virke.. vinduet kommer stadig frem, men dette er dog ligegyldigt, ville bare lige nævne det.
Avatar billede djfonzi Nybegynder
08. februar 2011 - 15:46 #24
Jeg har også prøvet med StandardInputWriteLine, men med samme resultat
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Kurser inden for grundlæggende programmering

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester