Commit 30d82bdf authored by Alan McNatty's avatar Alan McNatty
Browse files

Next round of changes to get the camera working, and sync save posts upload working.

Time to move onto the journal posts and UI ..

Much refactoring/clean-up required once everthing calms down .. just pushing in functionality at the moment.
parent f58a9c63
......@@ -46,13 +46,6 @@
</intent-filter>
</activity>
<activity android:name=".ui.TransferProgress" android:label="@string/transferprogress">
<intent-filter>
<action android:name="nz.net.catalyst.MaharaDroid.TRANSFERPROGRESS" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
<activity android:name=".upload.ArtifactSenderActivity"
android:label="@string/app_name"
android:enabled="true" android:exported="true">
......@@ -76,8 +69,9 @@
<activity android:name=".authenticator.AuthenticatorActivity"
android:theme="@android:style/Theme.Dialog"
android:excludeFromRecents="true" />
<service android:name=".upload.TransferService" android:label="@string/filetransfers"/>
<service android:name=".authenticator.AccountAuthenticatorService"
android:exported="true">
<intent-filter>
......@@ -104,11 +98,12 @@
android:syncable="true"
android:enabled="true">
</provider>
</application>
<!-- API Level 4 aka 1.6 required for multi-send support -->
<!-- API Level 5 aka 2.0 required for Account & Sync support -->
<uses-sdk android:minSdkVersion="5" />
<uses-permission android:name="android.permission.INTERNET"/>
</application>
<!-- API Level 4 aka 1.6 required for multi-send support -->
<!-- API Level 5 aka 2.0 required for Account & Sync support -->
<!-- API Level 7 aka 2.2 required for (filtered) Account & Sync Intent support -->
<uses-sdk android:minSdkVersion="7" />
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.GET_ACCOUNTS" />
<uses-permission android:name="android.permission.USE_CREDENTIALS" />
......
......@@ -8,4 +8,4 @@
# project structure.
# Project target.
target=android-5
target=android-8
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
<item android:id="@+id/option_camera"
android:icon= "@android:drawable/ic_menu_camera"
android:title="@string/options_menu_camera" />
<item android:id="@+id/option_account"
android:icon="@drawable/ic_menu_login"
android:title="@string/options_menu_account" />
<item android:id="@+id/about"
android:icon="@android:drawable/ic_menu_info_details"
android:title="@string/pref_menu_about" />
......
......@@ -7,6 +7,8 @@
<string name="artefacts_no_saved_artefacts">Nothing saved.</string>
<string name="options_menu_prefs">Preferences</string>
<string name="options_menu_account">Account &amp; Sync</string>
<string name="options_menu_camera">Camera</string>
<string name="options_menu_deleteall">Delete All</string>
<string name="options_menu_uploadall">Upload All</string>
<string name="options_menu_viewsaved">Saved</string>
......@@ -33,20 +35,6 @@
<string name="pref_auth_token_title">Token</string>
<string name="pref_auth_token_summary">Enter your Mahara mobile token</string>
<string name="prefcat_advanced">Advanced</string>
<string name="pref_upload_journal_key">upload.journal</string>
<string name="pref_upload_journal_title">Journal</string>
<string name="pref_upload_journal_summary">Select the default journal to post to</string>
<string name="pref_upload_folder_key">upload.folder</string>
<string name="pref_upload_folder_title">Upload Folder</string>
<string name="pref_upload_folder_summary">Select the default folder to upload your files into</string>
<string name="pref_upload_tags_key">upload.tags</string>
<string name="pref_upload_tags_title">Tags</string>
<string name="pref_upload_tags_summary">Select the default tag to add to all uploaded files/journals</string>
<string name="pref_upload_connection_key">upload.connection</string>
<string name="pref_upload_connection_title">Connection Type</string>
<string name="pref_upload_connection_summary">Restrict upload to the following connection types (default is fall back to handset settings):</string>
......@@ -60,7 +48,25 @@
<item>wifi</item>
<item>mobile</item>
</string-array>
<string name="prefcat_advanced">Advanced</string>
<string name="pref_upload_journal_key">upload.journal</string>
<string name="pref_upload_journal_title">Journal</string>
<string name="pref_upload_journal_summary">Select the default journal to post to</string>
<string name="pref_upload_folder_key">upload.folder</string>
<string name="pref_upload_folder_title">Upload Folder</string>
<string name="pref_upload_folder_summary">Select the default folder to upload your files into</string>
<string name="pref_upload_tags_key">upload.tags</string>
<string name="pref_upload_tags_title">Tags</string>
<string name="pref_upload_tags_summary">Select the default tag to add to all uploaded files/journals</string>
<string name="pref_sync_periodic_key">sync.periodic</string>
<string name="pref_sync_periodic_title">Periodic Sync</string>
<string name="pref_sync_periodic_summary">Enter the time in minutes to force a perioidc sync (leave blank for none)</string>
<string name="pref_menu_reset">Reset</string>
<string name="pref_menu_about">About</string>
<string name="pref_menu_scan">Scan</string>
......
......@@ -13,7 +13,7 @@
android:title="@string/pref_sync_url_title"
android:summary="@string/pref_sync_url_summary"
android:defaultValue="@string/pref_sync_url_default" />
<EditTextPreference
<EditTextPreference
android:key="@string/pref_auth_username_key"
android:title="@string/pref_auth_username_title"
android:summary="@string/pref_auth_username_summary" />
......@@ -21,6 +21,16 @@
android:key="@string/pref_auth_token_key"
android:title="@string/pref_auth_token_title"
android:summary="@string/pref_auth_token_summary" />
<ListPreference
android:key="@string/pref_upload_connection_key"
android:title="@string/pref_upload_connection_title"
android:summary="@string/pref_upload_connection_summary"
android:defaultValue=""
android:entries="@array/pref_upload_connection_entry"
android:entryValues="@array/pref_upload_connection_entryValues"
android:dialogTitle="@string/pref_upload_connection_title" />
<PreferenceCategory
android:title="@string/prefcat_advanced">
......@@ -42,14 +52,11 @@
android:summary="@string/pref_upload_tags_summary"
android:dialogTitle="@string/pref_upload_tags_title" />
<ListPreference
android:key="@string/pref_upload_connection_key"
android:title="@string/pref_upload_connection_title"
android:summary="@string/pref_upload_connection_summary"
android:defaultValue=""
android:entries="@array/pref_upload_connection_entry"
android:entryValues="@array/pref_upload_connection_entryValues"
android:dialogTitle="@string/pref_upload_connection_title" />
<EditTextPreference
android:key="@string/pref_sync_periodic_key"
android:title="@string/pref_sync_periodic_title"
android:summary="@string/pref_sync_periodic_summary"
android:defaultValue="" />
</PreferenceCategory>
......
......@@ -50,8 +50,13 @@ public class GlobalResources {
public static final String ACCOUNT_TYPE = "nz.net.catalyst.MaharaDroid.account";
public static final String AUTHTOKEN_TYPE = "nz.net.catalyst.MaharaDroid.account";
public static final String CONTENT_URL = "nz.net.catalyst.MaharaDroid";
public static final String[] CONTENT_TABLES = new String[] { "tag", "blog", "folder" };
public static final String[] CONTENT_FIELDS = new String[] { "ID", "VALUE" };
public static final String SYNC_AUTHORITY = "nz.net.catalyst.MaharaDroid";
public static final int REGISTRATION_TIMEOUT = 30 * 1000; // ms
}
\ No newline at end of file
......@@ -27,6 +27,7 @@ import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import nz.net.catalyst.MaharaDroid.R;
import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
......@@ -56,6 +57,12 @@ public class Utils {
SharedPreferences mPrefs = PreferenceManager.getDefaultSharedPreferences(mContext);
boolean allowWiFi = false, allowMobile = false;
// Haven't confirmed upload conditions.
// TODO validate it's OK to have this here.
if ( ! mPrefs.getBoolean("Upload Conditions Confirmed", false) ) {
return false;
}
String mSetting = mPrefs.getString(mContext.getResources().getString(R.string.pref_upload_connection_key), "");
......@@ -95,7 +102,7 @@ public class Utils {
if ( DEBUG ) Log.d(TAG, "URI = '" + uri.toString() + "', scheme = '" + uri.getScheme() + "'");
if ( uri.getScheme().equals("content") ) {
if ( uri.getScheme() != null && uri.getScheme().equals("content") ) {
// Get the filename of the media file and use that as the default title.
ContentResolver cr = context.getContentResolver();
Cursor cursor = cr.query(uri, new String[]{android.provider.MediaStore.MediaColumns.DATA}, null, null, null);
......@@ -121,6 +128,15 @@ public class Utils {
if ( ! t.exists() )
return null;
}
if ( DEBUG ) Log.d(TAG, "file path = '" + file_path + "'");
// Online image not in gallery
// TODO check http://jimmi1977.blogspot.co.nz/2012/01/android-api-quirks-getting-image-from.html
// for workaround
if ( file_path == "null" ){
return null;
}
return file_path;
}
......@@ -274,11 +290,6 @@ public class Utils {
return mPrefs.getString(mContext.getResources().getString(R.string.pref_upload_url_key), "");
}
public static Boolean getUploadCreateViewPref(Context mContext) {
SharedPreferences mPrefs = PreferenceManager.getDefaultSharedPreferences(mContext);
return mPrefs.getBoolean(mContext.getResources().getString(R.string.pref_upload_view_key), false);
}
public static String getUploadFolderPref(Context mContext) {
SharedPreferences mPrefs = PreferenceManager.getDefaultSharedPreferences(mContext);
......
......@@ -17,7 +17,7 @@
package nz.net.catalyst.MaharaDroid.authenticator;
import nz.net.catalyst.MaharaDroid.authenticator.AuthenticatorActivity;
import nz.net.catalyst.MaharaDroid.provider.MaharaProvider;
import nz.net.catalyst.MaharaDroid.syncadapter.ThreadedSyncAdapter;
import nz.net.catalyst.MaharaDroid.GlobalResources;
import nz.net.catalyst.MaharaDroid.LogConfig;
import android.accounts.Account;
......@@ -89,9 +89,13 @@ public class AuthenticatorActivity extends AccountAuthenticatorActivity {
final Account account = new Account(username, GlobalResources.ACCOUNT_TYPE);
if (mRequestNewAccount) {
Bundle bundle = new Bundle();
bundle.putBoolean(ThreadedSyncAdapter.EXTRAS_SYNC_IS_PERIODIC, true);
mAccountManager.addAccountExplicitly(account, null, null);
// Set contacts sync for this account.
ContentResolver.setSyncAutomatically(account, GlobalResources.SYNC_AUTHORITY, true);
ContentResolver.addPeriodicSync(account, GlobalResources.SYNC_AUTHORITY, bundle, ThreadedSyncAdapter.DEFAULT_SYNC_FREQUENCY);
ContentResolver.setIsSyncable(account, GlobalResources.SYNC_AUTHORITY, 1);
}
......
......@@ -22,6 +22,7 @@
package nz.net.catalyst.MaharaDroid.data;
import nz.net.catalyst.MaharaDroid.ui.ArtifactSettingsActivity;
import nz.net.catalyst.MaharaDroid.upload.TransferService;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
......@@ -132,11 +133,16 @@ public class Artefact extends Object implements Parcelable {
}
public void upload(Boolean auto, Context mContext) {
Intent i = new Intent(mContext, ArtifactSettingsActivity.class);
Intent i = new Intent(mContext, TransferService.class);
i.putExtra("artefact", (Parcelable) this);
if ( auto )
i.putExtra("auto", "yes please");
mContext.startActivity(i);
mContext.startService(i);
}
public void delete(Context mContext) {
ArtefactDataSQLHelper artefactData = new ArtefactDataSQLHelper(mContext);
artefactData.deleteSavedArtefact(id);
artefactData.close();
}
public void view(Context mContext) {
Intent i = new Intent(Intent.ACTION_VIEW).setData(Uri.parse(this.getFilename()));
......
......@@ -21,6 +21,7 @@
package nz.net.catalyst.MaharaDroid.data;
import nz.net.catalyst.MaharaDroid.Utils;
import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
......@@ -79,10 +80,16 @@ public class ArtefactDataSQLHelper extends SQLiteOpenHelper {
db.execSQL(sql);
}
public void uploadAllSavedArtefacts() {
public void uploadAllSavedArtefacts(Boolean uploaded) {
SQLiteDatabase db = this.getReadableDatabase();
if ( uploaded == null ) {
uploaded = false;
}
Cursor cursor = db.query(ArtefactDataSQLHelper.TABLE, null, null, null, null,
null, null);
null, null);
// Cursor cursor = db.query(ArtefactDataSQLHelper.TABLE, null, " UPLOADED = ? ", new String[] { uploaded.toString() }, null,
// null, null);
//startManagingCursor(cursor);
......@@ -93,8 +100,17 @@ public class ArtefactDataSQLHelper extends SQLiteOpenHelper {
String title = cursor.getString(3);
String description = cursor.getString(4);
String tags = cursor.getString(5);
Artefact a = new Artefact(id, time, filename, title, description, tags);
a.upload(true, mContext);
if ( filename == null ) {
continue;
}
String file_path = Utils.getFilePath(mContext, filename);
if ( file_path != null ) {
Artefact a = new Artefact(id, time, file_path, title, description, tags);
// TODO - if success, delete them?
a.upload(true, mContext);
}
}
}
//---deletes a particular item---
......
package nz.net.catalyst.MaharaDroid.provider;
import nz.net.catalyst.MaharaDroid.GlobalResources;
import android.content.ContentProvider;
import android.content.ContentValues;
import android.content.Context;
......@@ -17,7 +18,6 @@ public class MaharaProvider extends ContentProvider {
private static final String DATABASE_NAME = "maharadroid_sync.db";
private static final int DATABASE_VERSION = 1;
private static final String[] TABLES = new String[] { "tag", "blog", "folder" };
private static final String TAG = "MyContentProvider";
private static class DatabaseHelper extends SQLiteOpenHelper {
......@@ -29,17 +29,17 @@ public class MaharaProvider extends ContentProvider {
@Override
public void onCreate(SQLiteDatabase db) {
// create table to store user names
for ( int i = 0; i < TABLES.length; i++ ) {
for ( int i = 0; i < GlobalResources.CONTENT_TABLES.length; i++ ) {
db.execSQL("Create table "
+ TABLES[i]
+ GlobalResources.CONTENT_TABLES[i]
+ "( _id INTEGER PRIMARY KEY AUTOINCREMENT, ID TEXT, VALUE TEXT);");
}
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
for ( int i = 0; i < TABLES.length; i++ ) {
db.execSQL("DROP TABLE IF EXISTS " + TABLES[i]);
for ( int i = 0; i < GlobalResources.CONTENT_TABLES.length; i++ ) {
db.execSQL("DROP TABLE IF EXISTS " + GlobalResources.CONTENT_TABLES[i]);
}
onCreate(db);
}
......
package nz.net.catalyst.MaharaDroid.syncadapter;
import java.util.Date;
import org.json.JSONObject;
import nz.net.catalyst.MaharaDroid.R;
import nz.net.catalyst.MaharaDroid.Utils;
import nz.net.catalyst.MaharaDroid.data.ArtefactDataSQLHelper;
import nz.net.catalyst.MaharaDroid.upload.http.RestClient;
import android.accounts.Account;
import android.content.AbstractThreadedSyncAdapter;
import android.content.ContentProviderClient;
import android.content.ContentResolver;
import android.content.Context;
import android.content.SharedPreferences;
import android.content.SyncResult;
......@@ -28,6 +32,15 @@ public class ThreadedSyncAdapter extends AbstractThreadedSyncAdapter{
private Context mContext;
private static final String TAG = "ThreadedSyncAdapter";
public static final String EXTRAS_SYNC_IS_PERIODIC = "MaharaDroid.periodic";
static final String SYNC_AUTOMATICALLY_PREF = "sync_automatically";
static final String SYNC_FREQUENCY_PREF = "sync_frequency";
public static final boolean DEFAULT_SYNC_AUTOMATICALLY = false;
public static final long DEFAULT_SYNC_FREQUENCY = 900; // 15 minutes for testing
private static long sLastCompletedSync = 0;
public ThreadedSyncAdapter(Context context) {
super(context, true);
mContext = context;
......@@ -36,7 +49,36 @@ public class ThreadedSyncAdapter extends AbstractThreadedSyncAdapter{
@Override
public void onPerformSync(Account account, Bundle extras, String authority,
ContentProviderClient myProvider, SyncResult syncResult) {
Log.e(TAG, "Sync request issued");
// One way or another, delay follow-up syncs for another 10 minutes.
syncResult.delayUntil = 600;
boolean manual = extras.getBoolean(ContentResolver.SYNC_EXTRAS_MANUAL, false);
boolean ignoreSettings = extras.getBoolean(ContentResolver.SYNC_EXTRAS_IGNORE_SETTINGS, false);
boolean isPeriodic = extras.getBoolean(EXTRAS_SYNC_IS_PERIODIC, false);
if (manual || ignoreSettings) {
Log.i(TAG, "Starting a MANUAL sync");
manual = true;
} else if (isPeriodic) {
Log.i(TAG, "Starting a scheduled PERIODIC sync");
} else {
Log.i(TAG, "Starting an AUTOMATIC sync from a network tickle");
}
Date now = new Date();
if (sLastCompletedSync > 0 && now.getTime() - sLastCompletedSync < 5000) {
// If the last sync completed 10 seconds ago, ignore this request anyway.
Log.e(TAG, "Sync was CANCELLED because a sync completed within the past 5 seconds.");
return;
}
// Check if we have appropriate data access
if ( ! Utils.canUpload(mContext) ) {
Log.e(TAG, "Sync was CANCELLED because user does not wish to use this connection type.");
return;
}
//sync
// application preferences
SharedPreferences mPrefs = PreferenceManager.getDefaultSharedPreferences(mContext);
......@@ -52,6 +94,7 @@ public class ThreadedSyncAdapter extends AbstractThreadedSyncAdapter{
Log.v(TAG, "Synchronizing Mahara account '" + username + "', " + "'" + token + "' and lastsync '" + lastsync + "'");
// Get latest details from sync
JSONObject result = RestClient.AuthSync(authSyncURI, token, username, lastsync, mContext);
if ( Utils.updateTokenFromResult(result, mContext) == null ) {
......@@ -61,6 +104,10 @@ public class ThreadedSyncAdapter extends AbstractThreadedSyncAdapter{
} else {
syncResult.stats.numParseExceptions++;
}
// Now push any saved posts as 2nd part of sync
ArtefactDataSQLHelper artefactData = new ArtefactDataSQLHelper(mContext);
artefactData.uploadAllSavedArtefacts(false);
artefactData.close();
}
}
......@@ -21,17 +21,24 @@
package nz.net.catalyst.MaharaDroid.ui;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.Date;
import nz.net.catalyst.MaharaDroid.GlobalResources;
import nz.net.catalyst.MaharaDroid.LogConfig;
import nz.net.catalyst.MaharaDroid.R;
import nz.net.catalyst.MaharaDroid.Utils;
import nz.net.catalyst.MaharaDroid.data.Artefact;
import nz.net.catalyst.MaharaDroid.data.ArtefactDataSQLHelper;
import nz.net.catalyst.MaharaDroid.ui.EditPreferences.ConfigXMLHandler;
import nz.net.catalyst.MaharaDroid.ui.about.AboutActivity;
import android.app.Activity;
import android.app.ExpandableListActivity;
import android.content.ContentValues;
import android.content.Context;
import android.content.Intent;
import android.content.res.Configuration;
......@@ -41,6 +48,8 @@ import android.net.Uri;
import android.os.Bundle;
import android.os.Parcelable;
import android.provider.BaseColumns;
import android.provider.MediaStore;
import android.provider.Settings;
import android.util.Log;
import android.view.ContextMenu;
import android.view.LayoutInflater;
......@@ -77,6 +86,8 @@ public class ArtefactExpandableListAdapterActivity extends Activity implements O
private ExpandableListAdapter adapter;
private ExpandableListView listview;
private Uri imageUri = null;
@Override
public void onCreate(Bundle savedInstanceState) {
......@@ -136,7 +147,10 @@ public class ArtefactExpandableListAdapterActivity extends Activity implements O
String description = cursor.getString(4);
String tags = cursor.getString(5);
// TODO: check if file exists
// TODO: check if file exists
if ( filename == null ) {
artefactData.deleteSavedArtefact(id);
}
if ( Utils.getFilePath(this, filename) != null ) {
Artefact a = new Artefact(id, time, filename, title, description, tags);
......@@ -167,45 +181,6 @@ public class ArtefactExpandableListAdapterActivity extends Activity implements O
return items;
}
// public void uploadAllSavedArtefacts() {
// if ( artefactData == null )
// artefactData = new ArtefactDataSQLHelper(this);
//
// SQLiteDatabase db = artefactData.getReadableDatabase();
// Cursor cursor = db.query(ArtefactDataSQLHelper.TABLE, null, null, null, null,
// null, null);
//
// //startManagingCursor(cursor);
//
// while (cursor.moveToNext()) {
// Long id = cursor.getLong(0);
// Long time = cursor.getLong(1);
// String filename = cursor.getString(2);
// String title = cursor.getString(3);
// String description = cursor.getString(4);
// String tags = cursor.getString(5);
// Artefact a = new Artefact(id, time, filename, title, description, tags);
// a.upload(true, this);
// }
// artefactData.close();
// }
// //---deletes a particular item---
// public boolean deleteSavedArtefact(long id) {
// if ( artefactData == null )
// artefactData = new ArtefactDataSQLHelper(this);
//
// SQLiteDatabase db = artefactData.getWritableDatabase();
// return db.delete(ArtefactDataSQLHelper.TABLE, BaseColumns._ID + "=" + id, null) > 0;
// }
// //---deletes all items---
// private boolean deleteAllSavedArtefacts() {
// if ( artefactData == null )
// artefactData = new ArtefactDataSQLHelper(this);
//
// SQLiteDatabase db = artefactData.getWritableDatabase();
// return db.delete(ArtefactDataSQLHelper.TABLE, null, null) > 0;
//
// }
public boolean onCreateOptionsMenu(Menu menu) {
boolean result = super.onCreateOptionsMenu(menu);
......@@ -222,7 +197,7 @@ public class ArtefactExpandableListAdapterActivity extends Activity implements O
loadSavedArtefacts();
break;
case R.id.option_upload:
artefactData.uploadAllSavedArtefacts();
artefactData.uploadAllSavedArtefacts(true);
loadSavedArtefacts();
break;
case R.id.about:
......@@ -233,9 +208,38 @@ public class ArtefactExpandableListAdapterActivity extends Activity implements O
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
break;
case R.id.option_account:
//i.putExtra(Settings.EXTRA_AUTHORITIES, new String[] {GlobalResources.ACCOUNT_TYPE});
startActivity(new Intent(Settings.ACTION_SYNC_SETTINGS).putExtra(Settings.EXTRA_AUTHORITIES, new String[] {GlobalResources.SYNC_AUTHORITY}));
break;
case R.id.option_camera:
//define the file-name to save photo taken by Camera activity
String fileName = "maharadroid-tmp.jpg";
//create parameters for Intent with filename
ContentValues values = new ContentValues();
values.put(MediaStore.Images.Media.TITLE, fileName);
values.put(MediaStore.Images.Media.DESCRIPTION,"Image capture by camera for MaharaDroid");
//imageUri is the current activity attribute, define and save it for later usage (also in onSaveInstanceState)
imageUri = getContentResolver().insert(
MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values);
//create new Intent
Intent i = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
i.putExtra(MediaStore.EXTRA_OUTPUT, imageUri);
i.putExtra(MediaStore.EXTRA_VIDEO_QUALITY, 1);
startActivityForResult(i, 0);
break;
}
return true;
}
public void onActivityResult(int requestCode, int resultCode, Intent intent) {