package com.distantfuture.videos.activities;
import android.annotation.TargetApi;
import android.app.Activity;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;
import android.os.ParcelFileDescriptor;
import android.view.Window;
import com.distantfuture.videos.R;
import com.distantfuture.videos.misc.BusEvents;
import com.distantfuture.videos.misc.DUtils;
import com.distantfuture.videos.misc.JSONHelper;
import com.distantfuture.videos.misc.Utils;
import org.json.JSONObject;
import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.util.Map;
import de.greenrobot.event.EventBus;
@TargetApi(Build.VERSION_CODES.KITKAT)
public class StorageAccessActivity extends Activity {
private static final int REQUEST_SAVE_FILE = 1;
private static final int REQUEST_LOAD_FILE = 2;
private static final String LOAD_FLAG = "load_flag";
public static void save(final Activity activity, final Uri uri, final String text, final String type) {
Intent intent = saveIntent(activity, uri, text, type);
if (intent != null)
activity.startActivityForResult(intent, 233, null);
}
public static void load(final Activity activity, final String type) {
Intent intent = loadIntent(activity, type);
if (intent != null)
activity.startActivityForResult(intent, 233, null);
}
private static Intent saveIntent(final Context context, final Uri uri, final String text, final String type) {
Intent intent = null;
if (Utils.isKitKatOrNewer()) {
intent = new Intent()
.addFlags(Intent.FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET)
.setType(type)
.setComponent(new ComponentName(context, StorageAccessActivity.class));
if (uri != null) {
intent.putExtra(Intent.EXTRA_STREAM, uri)
.putExtra(Intent.EXTRA_SUBJECT, uri.getLastPathSegment());
} else if (text != null)
intent.putExtra(Intent.EXTRA_TEXT, text);
intent.putExtra(LOAD_FLAG, false);
}
return intent;
}
private static Intent loadIntent(final Context context, final String type) {
Intent intent = null;
if (Utils.isKitKatOrNewer()) {
intent = new Intent()
.addFlags(Intent.FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET)
.setType(type)
.setComponent(new ComponentName(context, StorageAccessActivity.class));
intent.putExtra(LOAD_FLAG, true);
}
return intent;
}
private static void copyStream(final InputStream inStream, final OutputStream outStream)
throws IOException {
// in case Android includes Apache commons IO in the future, this function should be replaced by IOUtils.copy
final int bufferSize = 4096;
final byte[] buffer = new byte[bufferSize];
int len = 0;
try {
while ((len = inStream.read(buffer)) != -1) {
outStream.write(buffer, 0, len);
}
} catch (Throwable t) {
DUtils.log("exception: " + t.toString());
}
}
@Override
protected void onActivityResult(final int requestCode, final int resultCode, final Intent data) {
switch (requestCode) {
case REQUEST_SAVE_FILE:
if (resultCode != Activity.RESULT_OK || data == null) {
finish();
return;
}
runSaveThread(data.getData());
break;
case REQUEST_LOAD_FILE:
if (resultCode != Activity.RESULT_OK || data == null) {
finish();
return;
}
runLoadThread(data.getData());
break;
default:
super.onActivityResult(requestCode, resultCode, data);
}
}
@Override
protected void onCreate(final Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);
setProgressBarIndeterminate(true);
setProgressBarIndeterminateVisibility(true);
setContentView(R.layout.dialog_progressbar);
final Intent intent = getIntent();
if (intent.hasExtra(LOAD_FLAG)) {
boolean load = intent.getBooleanExtra(LOAD_FLAG, false);
final Intent request;
if (load) {
request = new Intent(Intent.ACTION_OPEN_DOCUMENT)
.setType(intent.getType())
.addCategory(Intent.CATEGORY_OPENABLE);
startActivityForResult(request, REQUEST_LOAD_FILE);
} else {
if (!(intent.hasExtra(Intent.EXTRA_STREAM) || intent.hasExtra(Intent.EXTRA_TEXT))) {
setResult(RESULT_CANCELED);
finish();
return;
}
String filename = intent.getStringExtra(Intent.EXTRA_SUBJECT);
if (intent.hasExtra(Intent.EXTRA_STREAM)) {
final Uri src = intent.getParcelableExtra(Intent.EXTRA_STREAM);
if (src.getLastPathSegment() != null)
filename = src.getLastPathSegment();
}
request = new Intent(Intent.ACTION_CREATE_DOCUMENT)
.setType(intent.getType())
.addCategory(Intent.CATEGORY_OPENABLE)
.putExtra(Intent.EXTRA_TITLE, filename);
startActivityForResult(request, REQUEST_SAVE_FILE);
}
}
}
private void runSaveThread(final Uri destinationUri) {
new Thread() {
@Override
public void run() {
final Intent intent = getIntent();
if (destinationUri == null) {
finish();
return;
}
try {
final ParcelFileDescriptor fdOut = getContentResolver().openFileDescriptor(destinationUri, "w");
final FileOutputStream os = new FileOutputStream(fdOut.getFileDescriptor());
if (intent.hasExtra(Intent.EXTRA_STREAM)) {
final Uri src = intent.getParcelableExtra(Intent.EXTRA_STREAM);
final ParcelFileDescriptor fdIn = getContentResolver().openFileDescriptor(src, "r");
final FileInputStream is = new FileInputStream(fdIn.getFileDescriptor());
copyStream(is, os);
is.close();
fdIn.close();
} else if (intent.hasExtra(Intent.EXTRA_TEXT)) {
os.write(intent.getStringExtra(Intent.EXTRA_TEXT).getBytes());
}
os.close();
fdOut.close();
Utils.toast(StorageAccessActivity.this, "Export successful");
} catch (final IOException e) {
DUtils.log("Could not save file!" + e.toString());
}
finish();
}
}.start();
}
private void runLoadThread(final Uri sourceUri) {
new Thread() {
@Override
public void run() {
final Intent intent = getIntent();
if (sourceUri == null) {
finish();
return;
}
try {
final ParcelFileDescriptor fdIn = getContentResolver().openFileDescriptor(sourceUri, "r");
final FileInputStream in = new FileInputStream(fdIn.getFileDescriptor());
BufferedReader streamReader = new BufferedReader(new InputStreamReader(in, "UTF-8"));
StringBuilder responseStrBuilder = new StringBuilder();
String inputStr;
while ((inputStr = streamReader.readLine()) != null)
responseStrBuilder.append(inputStr);
JSONObject jsonObj = null;
try {
jsonObj = new JSONObject(responseStrBuilder.toString());
Map result = JSONHelper.toMap(jsonObj);
EventBus.getDefault().post(new BusEvents.JSONImportEvent(result));
} catch (Throwable t) {
DUtils.log("exception " + t.toString());
}
in.close();
fdIn.close();
} catch (final IOException e) {
DUtils.log("Could not save file!" + e.toString());
}
finish();
}
}.start();
}
}