执行shell命令,并在一个TextView获取输出 [英] Execute shell commands and get output in a TextView

查看:190
本文介绍了执行shell命令,并在一个TextView获取输出的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想执行 shell命令并获得在输出的TextView 。该命令可能有像ping或的logcat 连续输出。此外,的TextView 应自动将命令输出实时添加滚动。
为了做到这一点,我已经做到了这一点:

 包com.example.rootapp;进口java.io.DataOutputStream中;
进口的java.io.InputStream;进口android.app.Activity;
进口android.os.Bundle;
进口android.text.method.ScrollingMovementMethod;
进口android.widget.TextView;公共类MainActivity延伸活动{
    TextView的电视;    @覆盖
    保护无效的onCreate(捆绑savedInstanceState){
        super.onCreate(savedInstanceState);
        的setContentView(R.layout.activity_main);
        的String [] = cmdArray {的logcat -b广播};
        尝试{
            runAsRoot(cmdArray);
        }赶上(例外五){
            // TODO自动生成catch块
            e.printStackTrace();
        }
    }    公共无效runAsRoot(字符串[] CMDS)抛出异常{
        电视=(的TextView)findViewById(R.id.cmdOp);
        tv.setMovementMethod(新ScrollingMovementMethod());
        进程p =调用Runtime.getRuntime()EXEC(苏);
        DataOutputStream类OS =新的DataOutputStream类(p.getOutputStream());
        InputStream为= p.getInputStream();
        对于(字符串tmpCmd:CMDS){
            os.writeBytes(tmpCmd +\\ n);
            INT readed = 0;
            字节[] = BUFF新的字节[4096];
            布尔cmdRequiresAnOutput =真;
            如果(cmdRequiresAnOutput){
                而(is.available()&下; = 0){
                    尝试{了Thread.sleep(5000); }赶上(例外前){}
                }                而(is.available()大于0){
                    readed = is.​​read(BUFF);
                    如果(readed< = 0)打破;
                    字符串SEG =新的String(BUFF,0,readed);
                    tv.append(SEG);
                }
            }
        }
    }
}

这工作得很好,但它并没有持续更新 TextView的。正如你所看到的,我执行用root用户,不断生成的输出无线电logcat的(在终端模拟器和亚行的shell已经选中)。但在我的情况下,输出不是连续增加。它几100行之后停止。
这是我的布局:

 <的RelativeLayout的xmlns:机器人=htt​​p://schemas.android.com/apk/res/android
    的xmlns:工具=htt​​p://schemas.android.com/tool​​s
    机器人:layout_width =match_parent
    机器人:layout_height =match_parent
    机器人:paddingBottom会=@扪/ activity_vertical_margin
    机器人:paddingLeft =@扪/ activity_horizo​​ntal_margin
    机器人:paddingRight =@扪/ activity_horizo​​ntal_margin
    机器人:paddingTop =@扪/ activity_vertical_margin
    工具:上下文=MainActivity。>    <滚动型
    机器人:layout_width =match_parent
    机器人:layout_height =match_parent>    <的TextView
        机器人:ID =@ + ID / cmdOp
        机器人:layout_width =WRAP_CONTENT
        机器人:layout_height =WRAP_CONTENT
        机器人:重力=底
        机器人:文字=@字符串/参考hello world/>
< /滚动型>< / RelativeLayout的>

输出应保持滚动的TextView。至少这是我所期望的......任何办法解决这个吗?


解决方案

  //尝试这种方式,希望这将帮助你...注:苏命令仅在装置扎根否则给你的异常运行。公共类MainActivity延伸活动{    TextView的电视;    @覆盖
    保护无效的onCreate(捆绑savedInstanceState){
        super.onCreate(savedInstanceState);
        的setContentView(R.layout.activity_main);
        电视=(的TextView)findViewById(R.id.cmdOp);
        tv.setText(输出:+\\ n+ runAsRoot());
    }    公共字符串runAsRoot(){        尝试{
            //执行命令。
            工艺过程=调用Runtime.getRuntime()EXEC(ls -l命令);
            //读取标准输出。
            //注意:您可以使用写命令的标准输入
            // process.getOutputStream()。
            读者的BufferedReader =新的BufferedReader(
                    新的InputStreamReader(process.getInputStream()));
            INT读;
            的char []缓冲区=新的char [4096];
            StringBuffer的输出=新的StringBuffer();
            而((读取= reader.read(缓冲液))大于0){
                output.append(缓冲,0,读);
            }
            reader.close();            //等待命令完成。
            process.waitFor();            返回output.toString();
        }赶上(IOException异常五){
            抛出新的RuntimeException(E);
        }赶上(InterruptedException的E){
            抛出新的RuntimeException(E);
        }
    }
}

I want to execute some shell commands and get the output in a TextView. The command may have a continuous output like ping or logcat. Also, the TextView should scroll automatically as the command output is added in real-time. In order to do so, I have done this:

package com.example.rootapp;

import java.io.DataOutputStream;
import java.io.InputStream;

import android.app.Activity;
import android.os.Bundle;
import android.text.method.ScrollingMovementMethod;
import android.widget.TextView;

public class MainActivity extends Activity {
    TextView tv;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        String[] cmdArray={"logcat -b radio"};
        try {
            runAsRoot(cmdArray);
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

    public void runAsRoot(String[] cmds) throws Exception {
        tv=(TextView)findViewById(R.id.cmdOp);
        tv.setMovementMethod(new ScrollingMovementMethod());
        Process p = Runtime.getRuntime().exec("su");
        DataOutputStream os = new DataOutputStream(p.getOutputStream());
        InputStream is = p.getInputStream();
        for (String tmpCmd : cmds) {
            os.writeBytes(tmpCmd+"\n");
            int readed = 0;
            byte[] buff = new byte[4096];
            boolean cmdRequiresAnOutput = true;
            if (cmdRequiresAnOutput) {
                while( is.available() <= 0) {
                    try { Thread.sleep(5000); } catch(Exception ex) {}
                }

                while( is.available() > 0) {
                    readed = is.read(buff);
                    if ( readed <= 0 ) break;
                    String seg = new String(buff,0,readed);   
                    tv.append(seg);
                }
            }
        }        
    }
}

This works fine, but it does not update the TextView continuously. As you can see, I'm executing radio logcat as root user, the output is generated continuously (already checked in terminal emulator and adb shell). But in my case, the output is not added continuously. It stops after a few 100 lines. Here is my layout:

    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:paddingBottom="@dimen/activity_vertical_margin"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    tools:context=".MainActivity" >

    <ScrollView
    android:layout_width="match_parent"
    android:layout_height="match_parent" >

    <TextView
        android:id="@+id/cmdOp"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:gravity="bottom"
        android:text="@string/hello_world" />
</ScrollView>

</RelativeLayout>

The output should keep scrolling the TextView. At least this is what I expect...... Any workaround for this please?

解决方案

// try this way,hope this will help you...

Note : "su" command is only run if your device rooted otherwise is gave you exception.

public class MainActivity extends Activity {

    TextView tv;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        tv=(TextView)findViewById(R.id.cmdOp);
        tv.setText("Output :"+"\n"+runAsRoot());
    }

    public String runAsRoot() {

        try {
            // Executes the command.
            Process process = Runtime.getRuntime().exec("ls -l");
            // Reads stdout.
            // NOTE: You can write to stdin of the command using
            //       process.getOutputStream().
            BufferedReader reader = new BufferedReader(
                    new InputStreamReader(process.getInputStream()));
            int read;
            char[] buffer = new char[4096];
            StringBuffer output = new StringBuffer();
            while ((read = reader.read(buffer)) > 0) {
                output.append(buffer, 0, read);
            }
            reader.close();

            // Waits for the command to finish.
            process.waitFor();

            return output.toString();
        } catch (IOException e) {
            throw new RuntimeException(e);
        } catch (InterruptedException e) {
            throw new RuntimeException(e);
        }
    }
}

这篇关于执行shell命令,并在一个TextView获取输出的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆