Android 打开文件对话框与保存文件对话框
背景
写一个安卓程序的时候需要一个像windows一样封装好的OpenFileDialog,然后网上搜索了一番,结果Android自身没有提供封装好的系统函数,于是想着网上找找,但是别人写的一个是和我的程序风格不搭,第二是也想自己熟悉一下这类的操作。
源代码
openfiledialog.xml
<?xml version="1.0" encoding="utf-8"?> <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="com.fieldsoft.lagrange.OpenFileDialogActivity" > <LinearLayout android:id="@+id/layout_top" android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_alignParentTop="true" > <LinearLayout android:layout_width="wrap_content" android:layout_height="wrap_content" > <Button android:id="@+id/Return" android:layout_width="wrap_content" android:layout_height="wrap_content" android:onClick="Return" android:text="@string/Return" /> </LinearLayout> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="right" > <Button android:id="@+id/Cancel" android:layout_width="wrap_content" android:layout_height="wrap_content" android:onClick="Cancel" android:text="@string/Cancel" /> <Button android:id="@+id/Enter" android:layout_width="wrap_content" android:layout_height="wrap_content" android:onClick="Enter" android:text="@string/Enter" /> </LinearLayout> </LinearLayout> <LinearLayout android:id="@+id/layout_buttom" android:layout_width="fill_parent" android:layout_height="wrap_content" android:orientation="vertical" android:layout_alignParentBottom="true" android:layout_alignParentLeft="true"> <LinearLayout android:layout_width="fill_parent" android:layout_height="wrap_content"> <TextView android:id="@+id/TextFileName" android:layout_width="match_parent" android:layout_height="wrap_content"/> </LinearLayout> </LinearLayout> <ListView android:id="@+id/FileList" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@id/layout_top" android:layout_above="@id/layout_buttom"> </ListView> </RelativeLayout>
savefiledialog.xml<?xml version="1.0" encoding="utf-8"?> <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="com.fieldsoft.lagrange.SaveFileDialogActivity" > <LinearLayout android:id="@+id/layout_top" android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_alignParentTop="true" > <LinearLayout android:layout_width="wrap_content" android:layout_height="wrap_content" > <Button android:id="@+id/Return" android:layout_width="wrap_content" android:layout_height="wrap_content" android:onClick="Return" android:text="@string/Return" /> </LinearLayout> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="right" > <Button android:id="@+id/Cancel" android:layout_width="wrap_content" android:layout_height="wrap_content" android:onClick="Cancel" android:text="@string/Cancel" /> <Button android:id="@+id/Enter" android:layout_width="wrap_content" android:layout_height="wrap_content" android:onClick="Enter" android:text="@string/Enter" /> </LinearLayout> </LinearLayout> <LinearLayout android:id="@+id/layout_buttom" android:layout_width="fill_parent" android:layout_height="wrap_content" android:orientation="vertical" android:layout_alignParentBottom="true" android:layout_alignParentLeft="true"> <LinearLayout android:layout_width="fill_parent" android:layout_height="wrap_content"> <EditText android:id="@+id/editFileName" android:layout_width="match_parent" android:layout_height="wrap_content" /> </LinearLayout> </LinearLayout> <ListView android:id="@+id/FileList" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@id/layout_top" android:layout_above="@id/layout_buttom"> </ListView> </RelativeLayout>
OpenFileDialogActivity.javapackage com.fieldsoft.lagrange; import java.io.File; import java.util.ArrayList; import com.google.gson.Gson; import android.app.*; import android.content.Intent; import android.os.Bundle; import android.view.View; import android.widget.AdapterView; import android.widget.AdapterView.OnItemClickListener; import android.widget.ArrayAdapter; import android.widget.EditText; import android.widget.ListView; import android.widget.TextView; import android.widget.Toast; public class OpenFileDialogActivity extends Activity{ String DefaultFilePath; String DefaultFileName; ArrayList<File> FileList = new ArrayList<File>(); File FileNow; String Ext; public final static int RESULT_CODE = 5; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.openfiledialog); //获取参数 Intent intent = getIntent(); DefaultFilePath = intent.getStringExtra("DefaultFilePath"); DefaultFileName = intent.getStringExtra("DefaultFileName"); this.Ext = intent.getStringExtra("Ext"); //Toast.makeText(this,DefaultFilePath + "," + DefaultFileName, Toast.LENGTH_LONG).show(); //Toast.makeText(this,(new File(DefaultFilePath)).toString(), Toast.LENGTH_LONG).show(); // this.FileNow = new File(DefaultFilePath); this.RefreshFileList(); // TextView EditFileName = (TextView)findViewById(R.id.TextFileName); EditFileName.setText(DefaultFileName); //设置ListView单击事件 ListView mListView = (ListView)findViewById(R.id.FileList); mListView.setOnItemClickListener(new OnItemClickListener(){ @Override public void onItemClick(AdapterView<?> arg0, View arg1, int arg2, long arg3) { if (FileList.get(arg2).isDirectory()){ FileNow = FileList.get(arg2); RefreshFileList(); } else{ TextView EditFileName = (TextView)findViewById(R.id.TextFileName); EditFileName.setText(FileList.get(arg2).getName()); } } }); } protected void RefreshFileList(){ //将这些文件名加入listview this.FileList.clear(); File[] TempFiles = this.FileNow.listFiles(); if (TempFiles != null){ for (int i = 0;i < TempFiles.length;i ++){ if (TempFiles[i].isDirectory()){ this.FileList.add(TempFiles[i]); } else{ if (TempFiles[i].getName().endsWith(this.Ext)){ this.FileList.add(TempFiles[i]); } } } //赋值给listView String[] TempStrArr = new String[this.FileList.size()]; for (int i = 0;i < TempStrArr.length;i ++){ TempStrArr[i] = this.FileList.get(i).isDirectory() ? "[" + this.FileList.get(i).getName() + "]" : this.FileList.get(i).getName(); } ListView mListView = (ListView)findViewById(R.id.FileList); mListView.setAdapter(new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, TempStrArr)); } else{ Toast.makeText(this,"权限不够!", Toast.LENGTH_LONG).show(); if (this.FileNow.getParentFile() != null){ this.FileNow = this.FileNow.getParentFile(); } else{ this.FileNow = new File(DefaultFilePath); } this.RefreshFileList(); } } public void Return (View srcView){ if (this.FileNow.getParentFile() != null){ this.FileNow = this.FileNow.getParentFile(); this.RefreshFileList(); } } public void Cancel(View srcView){ this.finish(); } public void Enter (View srcView){ Intent intent = new Intent(); TextView EditFileName = (TextView)findViewById(R.id.TextFileName); intent.putExtra("FilePathName",this.FileNow.getAbsolutePath() + "/" + EditFileName.getText()); setResult(OpenFileDialogActivity.RESULT_CODE, intent); this.finish(); } }
SaveFileDialogActivity.javapackage com.fieldsoft.lagrange; import java.io.File; import java.util.ArrayList; import com.google.gson.Gson; import android.app.*; import android.content.Intent; import android.os.Bundle; import android.view.View; import android.widget.AdapterView; import android.widget.AdapterView.OnItemClickListener; import android.widget.ArrayAdapter; import android.widget.EditText; import android.widget.ListView; import android.widget.Toast; public class SaveFileDialogActivity extends Activity{ String DefaultFilePath; String DefaultFileName; ArrayList<File> FileList = new ArrayList<File>(); File FileNow; String Ext; public final static int RESULT_CODE = 4; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.savefiledialog); //获取参数 Intent intent = getIntent(); DefaultFilePath = intent.getStringExtra("DefaultFilePath"); DefaultFileName = intent.getStringExtra("DefaultFileName"); this.Ext = intent.getStringExtra("Ext"); //Toast.makeText(this,DefaultFilePath + "," + DefaultFileName, Toast.LENGTH_LONG).show(); //Toast.makeText(this,(new File(DefaultFilePath)).toString(), Toast.LENGTH_LONG).show(); // this.FileNow = new File(DefaultFilePath); this.RefreshFileList(); // EditText EditFileName = (EditText)findViewById(R.id.editFileName); EditFileName.setText(DefaultFileName); //设置ListView单击事件 ListView mListView = (ListView)findViewById(R.id.FileList); mListView.setOnItemClickListener(new OnItemClickListener(){ @Override public void onItemClick(AdapterView<?> arg0, View arg1, int arg2, long arg3) { if (FileList.get(arg2).isDirectory()){ FileNow = FileList.get(arg2); RefreshFileList(); } else{ EditText EditFileName = (EditText)findViewById(R.id.editFileName); EditFileName.setText(FileList.get(arg2).getName()); } } }); } protected void RefreshFileList(){ //将这些文件名加入listview this.FileList.clear(); File[] TempFiles = this.FileNow.listFiles(); if (TempFiles != null){ for (int i = 0;i < TempFiles.length;i ++){ if (TempFiles[i].isDirectory()){ this.FileList.add(TempFiles[i]); } else{ if (TempFiles[i].getName().endsWith(this.Ext)){ this.FileList.add(TempFiles[i]); } } } //赋值给listView String[] TempStrArr = new String[this.FileList.size()]; for (int i = 0;i < TempStrArr.length;i ++){ TempStrArr[i] = this.FileList.get(i).isDirectory() ? "[" + this.FileList.get(i).getName() + "]" : this.FileList.get(i).getName(); } ListView mListView = (ListView)findViewById(R.id.FileList); mListView.setAdapter(new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, TempStrArr)); } else{ Toast.makeText(this,"权限不够!", Toast.LENGTH_LONG).show(); if (this.FileNow.getParentFile() != null){ this.FileNow = this.FileNow.getParentFile(); } else{ this.FileNow = new File(DefaultFilePath); } this.RefreshFileList(); } } public void Return (View srcView){ if (this.FileNow.getParentFile() != null){ this.FileNow = this.FileNow.getParentFile(); this.RefreshFileList(); } } public void Cancel(View srcView){ this.finish(); } public void Enter (View srcView){ Intent intent = new Intent(); EditText EditFileName = (EditText)findViewById(R.id.editFileName); intent.putExtra("FilePathName",this.FileNow.getAbsolutePath() + "/" + EditFileName.getText()); setResult(SaveFileDialogActivity.RESULT_CODE, intent); this.finish(); } }
配置
千万别忘了给程序读写的权限,加在AndroidManifest.xml的application标签前
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"></uses-permission> <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"></uses-permission>
并且把这两个activity加在AndroidManifest.xml的application标签内<activity android:name=".SaveFileDialogActivity" android:label="@string/SaveFile"> <intent-filter> <action android:name="android.intent.action.EDIT" /> <category android:name="android.intent.category.DEFAULT" /> </intent-filter> </activity> <activity android:name=".OpenFileDialogActivity" android:label="@string/OpenFile"> <intent-filter> <action android:name="android.intent.action.EDIT" /> <category android:name="android.intent.category.DEFAULT" /> </intent-filter> </activity>
调用
Intent intent = new Intent(AddDataActivity.this, OpenFileDialogActivity.class); intent.putExtra("DefaultFilePath", Environment.getExternalStorageDirectory().getPath()); intent.putExtra("DefaultFileName", "default.lag"); intent.putExtra("Ext", ".lag"); startActivityForResult(intent, AddDataActivity.REQUEST_CODE);
在这个例子中我是用AddDataActivity这个Activity调用OpenFileDialogActivity。三个参数分别是:
DefaultFilePath:默认文件路径
DefaultFileName:默认文件名
Ext:想显示的文件后缀
调用保存也是同理
Intent intent = new Intent(AddDataActivity.this, SaveFileDialogActivity.class); intent.putExtra("DefaultFilePath", Environment.getExternalStorageDirectory().getPath()); intent.putExtra("DefaultFileName", "default.lag"); intent.putExtra("Ext", ".lag"); startActivityForResult(intent, AddDataActivity.REQUEST_CODE);
接受结果
if (requestCode == AddDataActivity.REQUEST_CODE) { if (resultCode == SaveFileDialogActivity.RESULT_CODE) { //获取文件名 String FilePathName = data.getStringExtra("FilePathName"); //保存 String Write_Str = (new Gson()).toJson(this.mData); try { FileOutputStream fout = new FileOutputStream(FilePathName); byte [] bytes = Write_Str.getBytes(); fout.write(bytes); fout.close(); Toast.makeText(this,"保存到" + FilePathName, Toast.LENGTH_LONG).show(); } catch (IOException e) { Toast.makeText(this,"保存到" + FilePathName +"失败,可能是权限不够!", Toast.LENGTH_LONG).show(); } } else if (resultCode == OpenFileDialogActivity.RESULT_CODE){ //获取文件名 String FilePathName = data.getStringExtra("FilePathName"); //保存 String Read_Str; try { FileInputStream fin = new FileInputStream(FilePathName); int length = fin.available(); byte [] buffer = new byte[length]; fin.read(buffer); Read_Str = EncodingUtils.getString(buffer, "UTF-8"); fin.close(); MyPoint[] Points = (new Gson()).fromJson(Read_Str, MyPoint[].class); ArrayList<MyPoint> TempArr = new ArrayList<MyPoint>(); for (int i = 0;i < Points.length;i ++){ TempArr.add(Points[i]); } this.mData = TempArr; this.ListViewRefresh(); Toast.makeText(this,"读取成功!", Toast.LENGTH_LONG).show(); } catch (IOException e) { Toast.makeText(this,"读取失败,可能是权限不够!", Toast.LENGTH_LONG).show(); } } }
看一下例子应该就能懂,通过返回的resultCode来判断是打开文件还是保存文件然后从返回的data获取FilePathName就可以了。
我这里用Json保存数据。
运行效果
文件夹将用中括号 [ ] 括起来。