Android开发者有些文件比如音频,视频,.html,.mp3等等这些文件不希望编译器编译而保持原始原貌打包进apk文件(这在游戏开发中很常见和普遍,如游戏用到的游戏音乐、图等资源),那么可以使用Android在res目录下的res/raw和assets来保存。res/raw和assets目录下的文件将不被Android编译成二进制,Android将这些文件资源保持原状原封不动的打包进最终编译发布时候的apk文件。
res/raw和res/assets和既有相同点也有不同点。
(1)res/raw目录下的文件将被Android映射成R.id.xxx资源,访问该raw目录下的文件资源,可以通过R.id.filename获得映射,进而文件操作。但res/assets则不是这样,res/assets目录下的文件不会进行R.id. filename这样的映射,res/assets目录下的文件存放和访问模型与Java文件系统的读写模型类似。
(2)assets目录下的文件结构可以出现层级和树形结构;而res/raw则不能分层级。换句话说,可以在assets建立多层级、树形的文件目录结构,而res/raw下的文件资源必须平铺放在res/raw目录下。
(3)文件大小方面。在res/raw目录下的单个文件大小可以大到若干MB的尺寸,但res/assets文件目录下的单个文件大小尺寸尽量控制在MB量级以下,否则可能要出问题。
(4)res/assets目录下的文件资源访问一般是这样(如附录文章1所示):
AssetManager am=getAssets();
InputStream is=am.open("filename");
即通过AssetManager访问res/assets目录下资源。
res/raw目录下的文件资源访问一般是这样:
InputStream is =getResources().openRawResource(R.id.filename);
res/raw目录下的文件资源也可以通过这样先获得URI定位:
Uri uri= Uri.parse("android.resource://"+getPackageName()+"/"+ R.raw.filename);
1 package com.lixu.rawduxie; 2 3 import java.io.BufferedInputStream; 4 5 import java.io.ByteArrayOutputStream; 6 import java.io.IOException; 7 import java.io.InputStream; 8 import android.app.Activity; 9 import android.os.Bundle; 10 import android.widget.Toast; 11 12 public class MainActivity extends Activity { 13 14 @Override 15 protected void onCreate(Bundle savedInstanceState) { 16 super.onCreate(savedInstanceState); 17 setContentView(R.layout.activity_main); 18 19 readraw(); 20 } 21 22 private void readraw() { 23 // 从raw文件读取文件的字节流 24 InputStream is = getResources().openRawResource(R.raw.lixutxt); 25 26 try { 27 byte[] buffer = readByteFromInputstream(is); 28 String s = new String(buffer, 0, buffer.length, "UTF-8"); 29 Toast.makeText(getApplicationContext(), s, 0).show(); 30 31 } catch (IOException e) { 32 e.printStackTrace(); 33 } 34 35 } 36 37 private byte[] readByteFromInputstream(InputStream is) throws IOException { 38 39 BufferedInputStream bis = new BufferedInputStream(is); 40 41 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 42 43 int BYTE_SIZE = 2 * 1024; 44 //创建字节数组作为缓存 45 byte[] b = new byte[BYTE_SIZE]; 46 47 int c; 48 //c = bis.read(b)将字节流读出后放入字节数组b中,baos.write(b, 0, c);读取多少就写入多少 49 while ((c = bis.read(b)) != -1) { 50 baos.write(b, 0, c); 51 baos.flush(); 52 } 53 //将字节数组流转换成字节数组 54 byte[] date = baos.toByteArray(); 55 56 is.close(); 57 baos.close(); 58 59 return date; 60 61 } 62 63 }