使用RootTools实现对Android系统文件的读写

 作者:          蒋东国
 时间:     2016年11月2日 星期三
 应用来源:     hqt APP(测试机型:华为荣耀4X、三星 Note4/S5)
 博客地址:     http://blog.csdn.net/andrexpert/article/details/53082397 

  

  情景再现:“前几天客户说,他们部署的一款手机在录制视频的时候不能屏蔽提示音,希望能够解决这个问题。好吧,由于Google禁止开发人员关闭相机使用提示音,除了部分厂商对Android系统进行了重新定制允许用户屏蔽相机提示音,通常情况,只要调用Google官方API都无法屏蔽相机提示音。也就是说,如果我们希望自己的应用能够在使用相机时静音,就必须地绕过官方API,从Framework层去重新实现。由于时间紧迫,就找了些第三方多媒体项目,比如vitamio、ffpeg、美拍SDK等,但这些项目要么就是太大了,要么就是需要授权,而为了这么几部手机感觉有点发不来。突然想到自己以前在帮别人刷机的时候,也老是去操作这些音频文件,因此我就想如果我将与相机相关的系统音频文件删掉会不会就达到我的要求了呢?”

RootTools是一个辅助开发者开发Root应用的开源项目,可用于判断Android终端是否具有Root权限和执行shell命令。RootTools对相关的Root操作进行了深度封装,且对开发者提供了一个jar包(目前最新版:RootTools-4.2.jar),开发人员可以非常轻松的开发出拥有Root操作权限的应用。比如:

(1)通过RootTools的isRootAvailable()来判断终端是否具有Root权限,代码如下:

public static boolean isDeviceRooted(){if(RootTools.isRootAvailable()){return true;}return false;
}

(2) 通过RootTools的remount方法修改文件(如”/system”)的挂载方式,其中mountType的值可为”RO”为只读方式或”RW”为读写方式,代码如下:

public static boolean changeMountType(String filePath,String mountType){if(RootTools.remount(filePath, mountType)){return true;}return false;
}

(3)通过RootTools的restartAndroid方法重启Android系统,但不是重启整个Android设备。因为该方法主要是通过杀死名zygote线程(即init线程)。当zygote线程被杀死后,会自动重启,从而实现系统重启。

public static void restartDevice(){try{RootTools.restartAndroid();}catch(java.util.concurrent.TimeoutException e){e.printTrace();}
}

(4)RootTools最方便之处就是深度封装了对各种文件(系统/SD卡)的大部分操作,开发者几乎只需一行代码就可以达到对系统文件的操作,比如:

复制文件:copyFile(String src,String des,booleanremountAsRw,boolean fileAttr);

删除文件:deleteFileOrDirectory(String targetFile,booleanremountAsRw);

判断文件是否存在:boolean exist(String file);

当然,如果你热衷于使用Shell命令,来实现对系统(或SD卡存储)的文件进行相关的操作。RootTools自然也提供了相关的接口和工具类。我们可以通过RootTools的getShell方法获得一个Shell对象,然后通过Shell对象的add(Command cmd)方法执行指定的shell命令。为了方便使用,我将相关方法进行了封装,代码如下:

/***@dscrible 系统文件操作工具类** Created by jiangdongguo on 2016-11-2 上午10:48:55*/
public classSysFileHandleUtils {private static final String cmdMountRo = "mount -oremount ro";private static final String cmdMountRw = "mount -oremount rw";private static final int CMD_ID_FIRST = 1;private static boolean isDeviceRooted(){if(RootTools.isRootAvailable()){return true;}return false;}public static void mountFileRo(String filePath){runShellCmd(cmdMountRo+” ”+filePath, true);}public static void mountFileRw(String filePath){runShellCmd(cmdMountRw+” ”+filePath, true);}public static ArrayList<String> runShellCmd(StringcmdStr,final boolean openShellOrNot){     final ArrayList<String> output = newArrayList<String>();try {      //封装要执行的shell命令,处理最后的结果Command command = newCommand(CMD_ID_FIRST,cmdStr) {         @Overridepublic void commandTerminated(int arg0,String msg) {Log.d("Debug", "执行结果,错误:"+openShellOrNot+"-->"+msg);}                  @Overridepublic void commandOutput(int arg0,String msg) {output.add(msg);Log.d("Debug", "执行结果,成功:"+openShellOrNot+"-->"+msg);}                  @Overridepublic void commandCompleted(int arg0,int arg1) {}};//获得shell对象,添加shell命令Shell rootShell =RootTools.getShell(openShellOrNot);rootShell.add(command);//检测是否命令执行完成//否则休眠2s等待直到执行完才能执行下一个命令if(!waitForCommand(command)){return null;}} catch (IOException e) {e.printStackTrace();return null;} catch (TimeoutException e) {e.printStackTrace();return null;} catch (RootDeniedException e) {e.printStackTrace();return null;}return output;}private static boolean waitForCommand(Command cmd) {while (!cmd.isFinished()) {synchronized (cmd) {try {if (!cmd.isFinished()) {cmd.wait(2000);}} catch (InterruptedException e) {e.printStackTrace();}}if (!cmd.isExecuting() &&!cmd.isFinished()) {Log.d("Debug", "错误:命令执行失败");return false;}}Log.d("Debug", "命令执行成功");return true;}
}

接下来,就是如何使用这个工具类。由于我希望能够让相机静音,就打算将以Cam、Video为前缀的所有音频文件移动到上一级目录。在移动之前需要给相关目录,如/system,授予可读写权限,否则会出现” Read-only file system”异常,当然为了系统文件安全,在移动命令执行完后再将/system目录置于只读权限。相关代码如下:

/*** @dscrible 通过RootTools操作移动系统音频文件* *  Created by jiangdongguo on 2016-11-2 上午10:32:33*/
public class SysHandleActivity extends Activity {private static final String cmdMoveFiles = "mv /system/media/audio/ui/Cam* /system/media/audio/ui/Video* system/media/audio/";@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);  if(!SysFileHandleUtils.isDeviceRooted()){Toast.makeText(SysHandleActivity.this, "无root", Toast.LENGTH_SHORT).show();return;}Button handleBtn = (Button)findViewById(R.id.handle_btn);handleBtn.setOnClickListener(new OnClickListener() {        @Overridepublic void onClick(View v) {//移动多媒体文件            moveMediaFiles();}});       }private  void moveMediaFiles() {new Thread(new Runnable() {                @Overridepublic void run() {SysFileHandleUtils.mountFileRw("/system");SysFileHandleUtils.runShellCmd(cmdMoveFiles, true);SysFileHandleUtils.mountFileRo("/system");}}).start();}
}

最后,还需要在AndroidMainfest.xml中添加超级用户权限:

<uses-permissionandroid:name="android.permission.ACCESS_SUPERUSER"/>

最后的话:“说句实话,通过删除系统音频文件的方法,来解决相机提示音的问题也是最笨的方法。虽然方便、快捷,但是这需要部署终端必须先”越狱”,且RootTools无法Root Android终端。RootTools确实是一个非常不错第三方包,使用该项目我们可以很轻松的开发具有Root操作权限的应用,类似于Re文件管理器。”

关于资料与Demo:

RootTools项目:https://github.com/Stericson/RootTools/releases

RootTools文档:https://github.com/Stericson/RootTools/wiki

http://blog.csdn.net/itas109/article/details/19682009

使用RootTools实现对Android系统文件的读写相关推荐

  1. AndroidStudio_android中实现对properties文件的读写操作_不把properties文件放在assets文件夹中_支持读写---Android原生开发工作笔记238

    这个东西还挺麻烦,因为是android中,我们一般把文件放到assets文件夹中去,但是实际上,这个raw文件夹和assets文件夹 是只读的,对,就是只读的只能读取,不能写入,所以一定要把文件写入到 ...

  2. 6行代码实现对TF卡的读写功能

    文章目录 前言 一.实现功能 二.材料清单 三.完整代码 四.代码运行结果 前言 shineblink core 开发板(简称Core)的库函数支持TF卡读写功能,所以只需要调用两三个API,即可实现 ...

  3. Codesys用ST语言实现对CSV文件的读写操作的代码案例

    一.开发环境说明 编程软件: Codesys V3.5 SP17 运行设备:PC电脑 编程语言: ST 二.配置操作 1.新建Codesys工程,依次点击[文件]-[新建工程]-[标准工程]- 输入名 ...

  4. uni-app调用Native.jsAPI实现对Android原生日历的增删查操作

    文章目录 前言 一.引入插件(uni-app插件市场) 二.使用步骤 1.手机系统日历操作需要添加权限才能操作 2.在对应的页面中进行使用 总结 前言 最近的uni-app项目中有一个直播日历的功能, ...

  5. 用JAVA Excel API 实现对Excel表格的读写更新 (转)

    package myexceltest; import jxl.*; import java.io.*; import jxl.write.*; /**  * <p>java读取Excel ...

  6. EasyExcel实现对excel文件读写

    EasyExcel实现对excel文件读写 1.EasyExcel介绍 2.EasyExcel特点: 3.EasyExcel写操作 3.1 pom中引入xml相关依赖 3.2 创建实体类 3.3 实现 ...

  7. java实现对properties类型文件的读写

    在java项目中,我们通常会有一些配置属性的数据,采用properties文件对数据进行管理是很有必要的,尤其是在属性值改变和项目环境发生变化时,所以特地总结一下对properties文件的最常见的操 ...

  8. python实现对doc、txt、xls等文档的读写操作

    目录 1.python实现对doc文档的读取 2.python实现对txt文档的读取 3.python实现对xls表格的读取 1.python实现对doc文档的读取 #读取docx中的文本代码示例 i ...

  9. 51单片机实现对24C02进行页写、顺序读取并显示验证

    源:51单片机实现对24C02进行页写.顺序读取并显示验证 //******************************************************************** ...

最新文章

  1. CVPR禁令出台:审稿期间禁止主动在社交媒体宣传论文!LeCun:阻碍科学交流,简直疯了...
  2. BZOJ3566 SHOI2014概率充电器(动态规划+概率期望)
  3. Leetcode114二叉树转链表-树中修改
  4. qt5 linux 窗口不能置顶_Qt 5.15 LTS发布,Qt 6要来了
  5. 基础知识—循环语句-for
  6. Java学习笔记之---集合
  7. USACO / Mother's Milk (DFS)
  8. acl自然语言处理_ACL 2020中自然语言处理中的知识图
  9. android模拟器检测常用方法,Android模拟器检测方案优化
  10. Android控件组合应用四
  11. python转二进制_python转二进制
  12. 统计红楼梦出场次数最多的十个人物
  13. 服务器每天自动变密码,Windows自动修改系统密码分享
  14. 大数据在 IoT 的应用
  15. Domain name server 域名服务
  16. 研究生带28岁腼腆导师一起相亲,被女生围追堵截要微信!
  17. 高数第六章 定积分的应用
  18. Babylon.js 深入 - 第 1 章 - 动画(1)
  19. ubuntu镜像快速下载
  20. android badge xml文件,ToolBar MenuItem 实现 Badge 数字提醒

热门文章

  1. 才智杂志社才智杂志才智编辑部2022年第36期目录
  2. HUAWEI nova 2评测:青春风无敌,拍照能力强大
  3. 亚马逊影响者红人,用关联视频给卖家带来哪些好处?
  4. python客户端软件开发_妙小程python客户端
  5. php同步登录,使用ucenter实现多站点同步登录的讲解
  6. 反查bash历史记录--用Enki学Linux系列(16)
  7. 启用Win11原生支持的DoH(DNS over HTTPS)和配置自定义的DoH服务
  8. 二阶边值问题的数值解matlab,二阶线性微分方程边值问题的MATLAB求解
  9. AVB之镜像的签名及验证签名详解
  10. 【小白学Java】D19》》》Collection集合