1 package jp.sourceforge.gokigen.memoma.io;
3 import static jp.sourceforge.gokigen.memoma.Main.APP_NAMESPACE;
6 import java.io.OutputStream;
7 import java.io.OutputStreamWriter;
8 import java.text.SimpleDateFormat;
9 import java.util.Calendar;
10 import java.util.Enumeration;
11 import java.util.Locale;
13 import android.app.ProgressDialog;
14 import android.content.ContentResolver;
15 import android.content.ContentValues;
16 import android.content.Context;
17 import android.graphics.RectF;
18 import android.net.Uri;
19 import android.os.AsyncTask;
20 import android.os.Build;
21 import android.os.Environment;
22 import android.provider.MediaStore;
23 import android.util.Log;
25 import jp.sourceforge.gokigen.memoma.R;
26 import jp.sourceforge.gokigen.memoma.holders.MeMoMaObjectHolder;
27 import jp.sourceforge.gokigen.memoma.holders.PositionObject;
30 * データをファイルに保存するとき用 アクセスラッパ (非同期処理を実行)
32 public class MeMoMaFileExportCsvProcess extends AsyncTask<MeMoMaObjectHolder, Integer, String>
34 private final String TAG = toString();
35 private final Context context;
36 private final IResultReceiver receiver;
37 private String exportedFileName = null;
39 private final ProgressDialog savingDialog;
44 public MeMoMaFileExportCsvProcess(Context context, IResultReceiver resultReceiver)
46 this.context = context;
47 receiver = resultReceiver;
49 // プログレスダイアログ(「保存中...」)を表示する。
50 savingDialog = new ProgressDialog(context);
51 savingDialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);
52 savingDialog.setMessage(context.getString(R.string.dataSaving));
53 savingDialog.setIndeterminate(true);
54 savingDialog.setCancelable(false);
65 protected void onPreExecute()
74 private String exportToCsvFile(String baseName, MeMoMaObjectHolder objectHolder)
76 String resultMessage = "";
79 String outputDir = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS).getPath() + "/" + APP_NAMESPACE + "/";
80 ContentResolver resolver = context.getContentResolver();
83 Calendar calendar = Calendar.getInstance();
84 SimpleDateFormat outFormat = new SimpleDateFormat("yyyyMMdd_HHmmss_", Locale.US);
85 exportedFileName = outFormat.format(calendar.getTime()) + baseName + ".csv";
88 ContentValues values = new ContentValues();
89 values.put(MediaStore.Downloads.TITLE, exportedFileName);
90 values.put(MediaStore.Downloads.DISPLAY_NAME, exportedFileName);
91 values.put(MediaStore.Downloads.MIME_TYPE, "text/csv"); // text/plain or text/csv
92 if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q)
94 values.put(MediaStore.Downloads.RELATIVE_PATH, "Download/" + APP_NAMESPACE);
95 values.put(MediaStore.Downloads.IS_PENDING, true);
96 extStorageUri = MediaStore.Downloads.getContentUri(MediaStore.VOLUME_EXTERNAL_PRIMARY);
100 File path = new File(outputDir);
101 values.put(MediaStore.Downloads.DATA, path.getAbsolutePath() + File.separator + exportedFileName);
102 extStorageUri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
104 Log.v(TAG, "---------- " + exportedFileName + " " + values);
106 Uri documentUri = resolver.insert(extStorageUri, values);
108 if (documentUri == null)
110 resultMessage = "documentUri is NULL.";
111 return (resultMessage);
114 OutputStream outputStream = resolver.openOutputStream(documentUri, "wa");
115 OutputStreamWriter writer = new OutputStreamWriter(outputStream);
118 String str = "; label,detail,userChecked,shape,style,centerX,centerY,width,height,;!<_$ (';!<_$' is a record Separator)\r\n";
121 // オブジェクトの出力 (保持しているものをすべて表示する)
122 Enumeration<Integer> keys = objectHolder.getObjectKeys();
123 while (keys.hasMoreElements())
125 Integer key = keys.nextElement();
126 PositionObject pos = objectHolder.getPosition(key);
127 RectF posRect = pos.getRect();
129 // TODO: 絞り込み条件がある場合には、その条件に従ってしぼり込む必要あり。
132 str = str + "\"" + pos.getLabel() + "\"";
133 str = str + ",\"" + pos.getDetail() + "\"";
134 if (pos.getUserChecked())
140 str = str + ",False";
142 str = str + "," + pos.getDrawStyle(); // オブジェクトの形状
143 str = str + "," + pos.getPaintStyle(); // オブジェクトの塗りつぶし状態
144 str = str + "," + (Math.round(posRect.centerX() * 100.0f) / 100.0f);
145 str = str + "," + (Math.round(posRect.centerY() * 100.0f) / 100.0f);
146 str = str + "," + (Math.round(posRect.width() * 100.0f) / 100.0f);
147 str = str + "," + (Math.round(posRect.height() * 100.0f) / 100.0f);
148 str = str + ",;!<_$\r\n";
154 if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q)
156 values.put(MediaStore.Downloads.IS_PENDING, false);
157 resolver.update(documentUri, values, null, null);
162 resultMessage = " ERR " + e.getMessage();
163 Log.v(TAG, resultMessage);
166 return (resultMessage);
171 * (バックグラウンドで実行する(このメソッドは、UIスレッドと別のところで実行する))
175 protected String doInBackground(MeMoMaObjectHolder... datas)
177 // ファイル名の設定 ... (拡張子なし)
178 String fileName = context.getFilesDir() + "/exported/" + datas[0].getDataTitle();
181 String result = exportToCsvFile(fileName, datas[0]);
193 protected void onProgressUpdate(Integer... values)
203 protected void onPostExecute(String result)
207 if (receiver != null)
209 receiver.onExportedResult(exportedFileName, result);
214 Log.v(TAG, "MeMoMaFileExportCsvProcess::onPostExecute() : " + ex.toString());
217 savingDialog.dismiss();
221 * 結果報告用のインタフェース(積極的に使う予定はないけど...)
226 public interface IResultReceiver
229 void onExportedResult(String exportedFileName, String detail);