android/NDK开发assets资源中文名打包问题

项目是C开发的能在android跑了,最近想把项目打包上传googleplay碰到一个问题资源图片没办法打包,原先我的图片资源都是直接拷贝到SDcard一个文件夹下的,C代码层直接访问SDcard的资源图片就OK了 ,安装过程好麻烦图片资源要手动拷贝到sdcard上。
这问题纠结了好久 
本想把资源放到res目录下的,但是资源有图片 ini配置档之类的文件C代码层访问这个目录也是问题。
放到这个assets文件呢? 测试过这个目录不支持中文名字,由于项目的资源都是中文命名的,改成英文工作量大也影响其他人的修改。
后来发现把资源压缩成zip能放到assets目录下,太高兴了问题能解决了。
解决方案:
把资源打包成zip 放入assets目录下,当程序启动的时候把zip解压到sdcard目录下,这样C层代码能直接访问sdcard下的资源包了。


解压的代码:
Test.java: //判断资源是否需要安装,需要跳转到安装页面


public class Test extends Activity {
    super.onCreate(savedInstanceState);
        JmpPage();


}
private void JmpPage(){
        String path = android.os.Environment.getExternalStorageDirectory() + "/Test";
        String ZipPath = android.os.Environment.getExternalStorageDirectory() + "/Test.zip";
        
         long length = 28;//Test 文件大小 设置比原文件夹小
       //判断是否有SDcard
        if(android.os.Environment.getExternalStorageState().equals(android.os.Environment.MEDIA_MOUNTED)){
       	File file = new File(path);
       	long FileSize = 0;
       	
       	if(file.exists())
       	{
       	  FileSize = GetFileSize(new File(path))/(1024*1024); //获取SDcard剩余容量
       	  Log.v("Test","FileSize:"+FileSize);
       	}
       	
       	file = new File(ZipPath);//删除zip
       	if(file.exists()){
       		file.delete();
       	}
       	if(FileSize < length){//如果资源包小于37M数据包不完整
       		if(GetAvailableSdcard() > (length+4))//sdcard内存需要大于39M才可以安装资源
       		{
       		  Intent intent = new Intent(Test.this, InstallActivity.class); //跳转到解压页面
                  intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); 
                  startActivity(intent);
       		}
       		else
       		{
       			Toast.makeText(Test.this, "sdcard容量满了,请删除一些!", 1).show();
       		}
       	}
       	Log.v("Test","FileSize > length");
       }
       else{
       	
       	Toast.makeText(Test.this, "未找到sdcard无法安装程序!", 1).show();
       }
	} 
	
	private long GetAvailableSdcard()
	{
		android.os.Environment.getExternalStorageDirectory();
		StatFs statFs = new StatFs(android.os.Environment.getExternalStorageDirectory().toString());


       // 获取block的SIZE
       long BlockSize = statFs.getBlockSize();
       // 可使用的Block的数量
       long AvailaBlock = statFs.getAvailableBlocks();
       long AvailableSize = AvailaBlock * BlockSize;
       return AvailableSize;
	}
	
	//获取文件夹大小
	private long GetFileSize(File file){
		long result = 0;
		
		 File[] filelist=file.listFiles();
		 for(int i = 0; i < filelist.length; i++) {
		        
		        if(filelist[i].isDirectory()) {
		            result += GetFileSize(filelist[i]);
		        } else {
		            result += filelist[i].length();
		        }
		    }
		    return result;
	}
InstallActivity.java //解压zip
package com.Test;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;




import com.Test.R;




import android.app.Activity;
import android.content.res.AssetManager;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.widget.ProgressBar;
import android.widget.TextView;
import android.widget.Toast;




public class InstallActivity extends Activity {
 
	    final private int ZipFileMax = 29965053;//文件夹大小
	    private int UnZipSize;
	    private ProgressBar progressbar;
	    private TextView    showtext;
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		// TODO Auto-generated method stub
		super.onCreate(savedInstanceState);
		setContentView(R.layout.install);
		progressbar = (ProgressBar)findViewById(R.id.progressBar1);
        showtext    = (TextView)findViewById(R.id.textView1);
        
        
        
        final String ZipFileName = android.os.Environment.getExternalStorageDirectory() + "/Test.zip";  
        final String UnZipLocation = android.os.Environment.getExternalStorageDirectory() + "/"; 
       
        
        new Thread(){
            public void run(){
            
              CopyAssets();
             
              
              Log.e("Test",ZipFileName);
              Decompression dec = new Decompression(ZipFileName, UnZipLocation);  
              dec.UnZip(); 
              File file = new File(ZipFileName);//zipFilename
              
              if(file.exists()){
            	  file.delete();
              }
              UpdateProgress(2);
              try {
				sleep(2000);
			   finish();
			} catch (InterruptedException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
             




        	}
        }.start();
	}




	private Handler handler = new Handler(){
		  @Override
		  public void handleMessage(Message msg){
			  if(!Thread.currentThread().isInterrupted()){
				  switch(msg.what){
				  
				  case 0:
					  progressbar.setMax(ZipFileMax);
					  break;
				  case 1:
					  progressbar.setProgress(UnZipSize);
					 // int n = (UnZipSize*100)/ZipFileMax;
					  //Log.v("Test","百分比:"+n+"%");
					  //showtext.setText(n);
					  break;
				  case 2:
					  //Toast.makeText(GetNumberActivity.this, "安装完毕", 1).show();
					  showtext.setText("安装完毕,请重新启动程序进入!");
					  break;
				  case 3:
					  showtext.setText("配置系统中。。。");
				  case -1:
					  //String error = msg.getData().getString("error");
			          // Toast.makeText(InstallActivity.this, error, 1).show();
					  break;
				  }
			  }
		  super.handleMessage(msg);
		  }
		};
		private void UpdateProgress(int type)
		{
		    Message msg = new Message();
		    msg.what = type;
		    handler.sendMessage(msg);
		}
		public String getSDPath(){ 
			File sdDir = null; 
			boolean sdCardExist = android.os.Environment.getExternalStorageState().equals(android.os.Environment.MEDIA_MOUNTED); //判断sd卡是否存在 
			if (sdCardExist) 
			{ 
			  sdDir =android.os.Environment.getExternalStorageDirectory();//获取跟目录 
			} 
			return sdDir.toString(); 
		}




		public class Decompression {  
			  private String ZipFile;  
			  private String Location;  
			 
			  public Decompression(String zipFile, String location) {  
			    ZipFile = zipFile;  
			    Location = location;  
			 
			    _dirChecker("");  
			  }  
			 
			  public void UnZip() {  
			    try  {  
			      BufferedInputStream fin = new BufferedInputStream(new FileInputStream(ZipFile));  
			      ZipInputStream zin = new ZipInputStream(fin);  
			      ZipEntry ze = null;
			      byte[] buf = new byte[1024];
			      int n= 0;
			      int len = 0;
			      
			     // ZipFileMax = 52272746;//zin.available();
			      Log.v("Test","ZipFileMax:"+ZipFileMax);
			      UpdateProgress(0);
			      
			      while ((ze = zin.getNextEntry()) != null) {  
			       // Log.v("Test", "pacth:" + ze.getName());  
			       // Log.v("Test","Len:"+ze.getSize());
			       // Log.v("Test","Time:"+ze.getTime());
			 
			        if(ze.isDirectory()) {  
			          _dirChecker(ze.getName());  
			        } else {  
			        BufferedOutputStream fout = new BufferedOutputStream(new FileOutputStream(Location + ze.getName()));  
			      
			        
			       while((n = zin.read(buf,0,1024))> 0)
			        	 {
			        	   
			        	   fout.write(buf,0,n);
			        	   UnZipSize += n;
			        	   UpdateProgress(1);
			        	 }
			 
			          zin.closeEntry();  
			          fout.close();  
			        }  
			        
			      }  
			     
			      zin.close();  
			    } catch(Exception e) {  
			      Log.e("Test", "unzip", e);  
			    }  
			 
			  }  
			 
			  private void _dirChecker(String dir) {  
			  File f = new File(Location + dir);  
			 
			    if(!f.isDirectory()) {  
			      f.mkdirs();  
			    }  
			  }  
	   } 
		
		
		private void CopyAssets() { 
		    AssetManager assetManager = getAssets(); 
		    String[] files = null; 
		    try { 
		        files = assetManager.list(""); 
		    } catch (IOException e) { 
		        Log.e("Test", e.getMessage()); 
		    } 
		    UpdateProgress(3);
		    for(String filename : files) { 
		        InputStream in = null; 
		        OutputStream out = null; 
		        try { 
		          in = assetManager.open(filename); 
		          out = new FileOutputStream(android.os.Environment.getExternalStorageDirectory()+"/" + filename); 
		          CopyFile(in, out); 
		          in.close(); 
		          in = null; 
		          out.flush(); 
		          out.close(); 
		          out = null; 
		        } catch(Exception e) { 
		            Log.e("Test", e.getMessage()); 
		        }        
		    } 
		} 
		private void CopyFile(InputStream in, OutputStream out) throws IOException { 
		    byte[] buf = new byte[1024]; 
		    int n; 
		    
		    BufferedInputStream fin = new BufferedInputStream(in);
		    BufferedOutputStream fout = new BufferedOutputStream(out);
		    while((n = fin.read(buf)) != -1){ 
		      fout.write(buf, 0, n); 
		    } 
		} 
}


AndroidManifest.xml


      
    
    
    
    
    
    
    
     
    
         
                          
            
                
                
            
        
         
        
    
 




这有个很严重问题apk会很大,而且apk卸载了sdcard中的文件不会自动删除希望各位同仁提供方法。
上面代码有部分参考其他人的,本人一直玩C刚学java不久,相信也有人遇到同样的问题拿出来分享一下,如果有更好的方法希望可以交流交流。







你可能感兴趣的:(android,android,string,file,null,exception,byte)