コマンドラインlsコマンドのAndroidファイルブラウズコントロールを使用して、root過のデバイスに適しており、システムファイルを読み取ることができます


package talent.fm;

import java.io.File;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

import android.content.Context;
import android.content.res.TypedArray;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.AttributeSet;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.TextView;

public class FileView extends ListView{
	private FileAdapter browser;
	
	public interface OnPathChanged{
		abstract boolean onChanged(String old,String path);
	}
	public void SetOnPathChangedListener(OnPathChanged listener){
		if(browser==null) return;
		browser.onChanged = listener;
	}
	public FileView(Context context, AttributeSet attrs, int defStyle) {
		super(context, attrs, defStyle);
		init();
	}
	public FileView(Context context, AttributeSet attrs) {
		super(context, attrs);
		init();
        TypedArray a = context.obtainStyledAttributes(attrs,R.styleable.FileView);             
        String path = a.getString(R.styleable.FileView_path);  
        a.recycle();
        if(path!=null)
        	browser.SetPath(path);
    }
	public FileView(Context context) {
		super(context);
		init();
	}
	private void init(){
		browser = new FileAdapter();
		setAdapter(browser);
        setOnItemClickListener(onItemClick);
	}
    private OnItemClickListener onItemClick = new OnItemClickListener(){
		@Override
		public void onItemClick(AdapterView<?> arg0, View arg1, int arg2,long arg3) {
			//com.Logi("item:"+arg2);
			if(!browser.OpenChild(arg2)){
				com.Toast(arg1.getContext(),"folder is empty or can't open");
				return;
			}
		}
    };
    /**goto parent folder,return false if no parent folder.*/
    public boolean Up(){
    	return browser.Up();
    }
    public void SetPath(String path){
    	browser.SetPath(path);
    }
    public String GetPath(){
    	return browser.GetPath();
    }
}
class FileAdapter extends BaseAdapter{
	private String path = "/";
	private List<FileInfo> contents = new ArrayList<FileInfo>();
	protected	FileView.OnPathChanged onChanged;
    Console cs = new Console();
    private final static int BROWS_MODE_SU = 1,
    		BROWS_MODE_APK = 2;
    private int mode = BROWS_MODE_SU;
    private class FileInfo{
    	String	Name;
    	int		IconId;
    	FileInfo(String name,int id){
    		Name = name;
    		IconId = id;
    	}
    	boolean IsFolder(){
    		return R.drawable.icon_folder==IconId;
    	}
    }
    public boolean SetSUMode(){
    	mode = BROWS_MODE_SU;
    	return true;
    }
    public void SetAPKMode(){
    	mode = BROWS_MODE_APK;
    	SetPath(path);
    }
	public FileAdapter(){
		cs.SetOnOutput(onConsoleOutput);
		if(!cs.Create())
			SetAPKMode();
	}
	@Override
	public int getCount() {
		return contents.size();
	}
	/**return a File Object*/
	@Override
	public Object getItem(int position) {
		if(position>=contents.size()) return null;
		return contents.get(position);
	}
	@Override
	public long getItemId(int position) {
		return 0;
	}
	@Override
	public View getView(int position, View convertView, ViewGroup parent) {
		if (convertView == null) {
	        LayoutInflater inflater = LayoutInflater.from(parent.getContext());
	        convertView = inflater.inflate(R.layout.item_explorer,null);
		} 
        
		FileInfo fi = contents.get(position);
		
		ImageView iv = (ImageView)convertView.findViewById(R.id.explorer_iv_image);
		iv.setImageResource(fi.IconId);
		
		TextView tv = (TextView)convertView.findViewById(R.id.explorer_iv_text);
		tv.setText(fi.Name);

		return convertView;
	}
	public void SetPath(String path){
		com.Logi(path);
		if(path==null||path.length()==0)
			path = "/";
		contents.clear();
		notifyDataSetChanged();
		if(onChanged!=null) onChanged.onChanged(this.path,path);
		this.path = path;
		if(this.mode==BROWS_MODE_APK){
			File file = new File(path);
			String[] fnl = file.list();
			com.Logw("fnl:"+fnl);
			File[] fl = file.listFiles();
			if(fl==null){
				com.Loge("init path:"+path);
				return;
			}
			Arrays.sort(fl);
			folderInsertPos = 0;
			for(int i=0;i<fl.length;i++){
				insertByFile(fl[i]);
			}
			notifyDataSetChanged();
		}else if(mode==BROWS_MODE_SU){
			String cmd = "ls " + path;
			if(!cs.Exec(cmd))
				SetAPKMode();
		}
	}
	public String GetPath(){
		return path;
	}
	public boolean OpenChild(int index){
		if(index<0||index>=contents.size()) return false;
		FileInfo fi = contents.get(index);
		if(!fi.IsFolder()) return false;
		if(path.equals("/")) path = "";
		SetPath(path+"/"+fi.Name);
		return true;
	}
	public boolean Up(){
		File file = new File(path);
		File root = file.getParentFile();
		if(root==null) return false;
		SetPath(root.getPath());
		return true;
	}
	private Console.OnOutput onConsoleOutput = new Console.OnOutput(){
		@Override
		public void onOutput(String str) {
			Message msg = new Message();
			msg.what = MSG_NOTIFY_STR;
			Bundle bundle = new Bundle();
			bundle.putString("output_str",str);
			msg.setData(bundle);
			notifyHandler.sendMessage(msg);
		}
	};
	private int folderInsertPos = 0;
	/**insert FileInfo object in contents set,and position by name*/
	private void insertByName(String str){
        String fp = path + "/" + str;
        File file = new File(fp);
        insertByFile(file);
        
	}
	private void insertByFile(File file){
		int icon;
		if(file.isDirectory()){
			icon = R.drawable.icon_folder;
			contents.add(folderInsertPos,new FileInfo(file.getName(),icon));
			folderInsertPos++;
		}
		else{
	        if(file.isFile()){
	        	icon = R.drawable.icon_file;
	        }
	        else{
	        	icon = R.drawable.icon_script;
	        }
			contents.add(new FileInfo(file.getName(),icon));
		}
	}
	private final static int MSG_NOTIFY_DATA = 1,
			MSG_NOTIFY_STR = 2;
	private Handler notifyHandler = new Handler(){
		@Override
		public void handleMessage(Message msg){
			if(msg.what==MSG_NOTIFY_STR){
				String str = msg.getData().getString("output_str");
				if(str.length()==0) return;
				String[] fns = str.split("\\|");
				Arrays.sort(fns);
				folderInsertPos = 0;
				for(int i=0;i<fns.length;i++){
					insertByName(fns[i]);
				}
				notifyDataSetChanged();
			}else if(msg.what==MSG_NOTIFY_DATA){
			}
		}
	};
}
package talent.fm;

import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;

public class Console{
	private boolean notExit = true;
	private ReadThread readTh = new ReadThread();
	private DataInputStream input;
	private DataOutputStream output;
	private OnOutput onOutput;
	
	public interface OnOutput{
		void onOutput(String str);
	}
	/**must call this function or thread will not terminate*/
	public void Close(){
		notExit = false;
		if(input!=null){
			try {
				input.close();
			} catch (IOException e) {
				com.Loge("Console.Close input:"+e.getMessage());
			}
		}
	}
	public boolean Create(){
		//   Root   android    su  
		Process process;
		try {
			process = Runtime.getRuntime().exec("su ");
		} catch (IOException e) {
			com.Loge("Console.Create:"+e.getMessage());
			return false;
		} catch (SecurityException e){
			com.Loge("Console.Create:"+e.getMessage());
			return false;
		}
		output = new DataOutputStream(process.getOutputStream());
		input = new DataInputStream(process.getInputStream());
		readTh.start();
		return true;
	}
	public boolean Exec(String cmd){
		try {
			output.writeBytes(cmd+"
"); output.flush(); return true; } catch (IOException e) { com.Loge("Console.Exec:"+e.getMessage()); } return false; } class ReadThread extends Thread{ @Override public void run() { String outstr = ""; while(notExit){ try { int len = input.available(); if(0==len){ if(onOutput!=null) onOutput.onOutput(outstr); outstr = ""; } String str = input.readLine(); if(str==null) break; outstr += str + "|"; } catch (IOException e) { com.Loge("Console.Thread.run:"+e.getMessage()); break; } } } } public void SetOnOutput(OnOutput opt) { onOutput = opt; } }