X-Git-Url: http://git.linex4red.de/pub/Android/ownCloud.git/blobdiff_plain/c7dc13598737ff21a5d358f5fa4d1f38e2d70fb9..9aab2d26da38f26e7ff03a0b5db3bd01b51bce05:/src/com/owncloud/android/ui/activity/FileDisplayActivity.java diff --git a/src/com/owncloud/android/ui/activity/FileDisplayActivity.java b/src/com/owncloud/android/ui/activity/FileDisplayActivity.java index 1adbb1b0..9b204f36 100644 --- a/src/com/owncloud/android/ui/activity/FileDisplayActivity.java +++ b/src/com/owncloud/android/ui/activity/FileDisplayActivity.java @@ -21,18 +21,19 @@ package com.owncloud.android.ui.activity; import java.io.File; import android.accounts.Account; -import android.accounts.AccountManager; import android.app.AlertDialog; import android.app.ProgressDialog; import android.app.AlertDialog.Builder; import android.app.Dialog; import android.content.BroadcastReceiver; +import android.content.ComponentName; import android.content.ContentResolver; import android.content.Context; import android.content.DialogInterface; import android.content.DialogInterface.OnClickListener; import android.content.Intent; import android.content.IntentFilter; +import android.content.ServiceConnection; import android.content.SharedPreferences; import android.content.pm.PackageInfo; import android.content.pm.PackageManager.NameNotFoundException; @@ -40,8 +41,8 @@ import android.content.res.Resources.NotFoundException; import android.database.Cursor; import android.net.Uri; import android.os.Bundle; -import android.os.Environment; import android.os.Handler; +import android.os.IBinder; import android.preference.PreferenceManager; import android.provider.MediaStore; import android.support.v4.app.FragmentTransaction; @@ -65,13 +66,16 @@ import com.owncloud.android.authenticator.AccountAuthenticator; import com.owncloud.android.datamodel.DataStorageManager; import com.owncloud.android.datamodel.FileDataStorageManager; import com.owncloud.android.datamodel.OCFile; -import com.owncloud.android.db.ProviderMeta.ProviderTableMeta; -import com.owncloud.android.files.OwnCloudFileObserver; import com.owncloud.android.files.services.FileDownloader; +import com.owncloud.android.files.services.FileDownloader.FileDownloaderBinder; import com.owncloud.android.files.services.FileObserverService; import com.owncloud.android.files.services.FileUploader; +import com.owncloud.android.files.services.FileUploader.FileUploaderBinder; import com.owncloud.android.network.OwnCloudClientUtils; +import com.owncloud.android.operations.RemoteOperationResult; import com.owncloud.android.syncadapter.FileSyncService; +import com.owncloud.android.ui.dialog.SslValidatorDialog; +import com.owncloud.android.ui.dialog.SslValidatorDialog.OnSslValidatorListener; import com.owncloud.android.ui.fragment.FileDetailFragment; import com.owncloud.android.ui.fragment.OCFileListFragment; @@ -86,15 +90,20 @@ import eu.alefzero.webdav.WebdavClient; */ public class FileDisplayActivity extends SherlockFragmentActivity implements - OCFileListFragment.ContainerActivity, FileDetailFragment.ContainerActivity, OnNavigationListener { + OCFileListFragment.ContainerActivity, FileDetailFragment.ContainerActivity, OnNavigationListener, OnSslValidatorListener { private ArrayAdapter mDirectories; - private OCFile mCurrentDir; + private OCFile mCurrentDir = null; + private OCFile mCurrentFile = null; private DataStorageManager mStorageManager; private SyncBroadcastReceiver mSyncBroadcastReceiver; private UploadFinishReceiver mUploadFinishReceiver; private DownloadFinishReceiver mDownloadFinishReceiver; + private FileDownloaderBinder mDownloaderBinder = null; + private FileUploaderBinder mUploaderBinder = null; + private ServiceConnection mDownloadConnection = null, mUploadConnection = null; + private RemoteOperationResult mLastSslUntrustedServerResult = null; private OCFileListFragment mFileList; @@ -105,6 +114,9 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements private static final int DIALOG_ABOUT_APP = 2; public static final int DIALOG_SHORT_WAIT = 3; private static final int DIALOG_CHOOSE_UPLOAD_SOURCE = 4; + private static final int DIALOG_SSL_VALIDATOR = 5; + private static final int DIALOG_CERT_NOT_SAVED = 6; + private static final int ACTION_SELECT_CONTENT_FROM_APPS = 1; private static final int ACTION_SELECT_MULTIPLE_FILES = 2; @@ -116,8 +128,15 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements Log.d(getClass().toString(), "onCreate() start"); super.onCreate(savedInstanceState); - /// saved instance state: keep this always before initDataFromCurrentAccount() + /// Load of parameters from received intent + mCurrentDir = getIntent().getParcelableExtra(FileDetailFragment.EXTRA_FILE); // no check necessary, mCurrenDir == null if the parameter is not in the intent + Account account = getIntent().getParcelableExtra(FileDetailFragment.EXTRA_ACCOUNT); + if (account != null) + AccountUtils.setCurrentOwnCloudAccount(this, account.name); + + /// Load of saved instance state: keep this always before initDataFromCurrentAccount() if(savedInstanceState != null) { + // TODO - test if savedInstanceState should take precedence over file in the intent ALWAYS (now), NEVER, or SOME TIMES mCurrentDir = savedInstanceState.getParcelable(FileDetailFragment.EXTRA_FILE); } @@ -128,9 +147,14 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements } else { /// at least an account is available - initDataFromCurrentAccount(); + initDataFromCurrentAccount(); // it checks mCurrentDir and mCurrentFile with the current account } + + mUploadConnection = new ListServiceConnection(); + mDownloadConnection = new ListServiceConnection(); + bindService(new Intent(this, FileUploader.class), mUploadConnection, Context.BIND_AUTO_CREATE); + bindService(new Intent(this, FileDownloader.class), mDownloadConnection, Context.BIND_AUTO_CREATE); // PIN CODE request ; best location is to decide, let's try this first if (getIntent().getAction() != null && getIntent().getAction().equals(Intent.ACTION_MAIN) && savedInstanceState == null) { @@ -138,10 +162,10 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements } // file observer - /*Intent observer_intent = new Intent(this, FileObserverService.class); + Intent observer_intent = new Intent(this, FileObserverService.class); observer_intent.putExtra(FileObserverService.KEY_FILE_CMD, FileObserverService.CMD_INIT_OBSERVED_LIST); startService(observer_intent); - */ + /// USER INTERFACE requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS); @@ -159,10 +183,8 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements setContentView(R.layout.files); mFileList = (OCFileListFragment) getSupportFragmentManager().findFragmentById(R.id.fileList); mDualPane = (findViewById(R.id.file_details_container) != null); - if (mDualPane && getSupportFragmentManager().findFragmentByTag(FileDetailFragment.FTAG) == null) { - FragmentTransaction transaction = getSupportFragmentManager().beginTransaction(); - transaction.replace(R.id.file_details_container, new FileDetailFragment(null, null)); // empty FileDetailFragment - transaction.commit(); + if (mDualPane) { + initFileDetailsInDualPane(); } // Action bar setup @@ -173,11 +195,11 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_LIST); actionBar.setListNavigationCallbacks(mDirectories, this); setSupportProgressBarIndeterminateVisibility(false); // always AFTER setContentView(...) ; to workaround bug in its implementation - + Log.d(getClass().toString(), "onCreate() end"); } - + /** * Launches the account creation activity. To use when no ownCloud account is available */ @@ -197,20 +219,53 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements AccountUtils.getCurrentOwnCloudAccount(this), getContentResolver()); - /// State recovery - CURRENT DIRECTORY ; priority: 1/ getIntent(), 2/ savedInstanceState (in onCreate()), 3/ root dir - if(getIntent().hasExtra(FileDetailFragment.EXTRA_FILE)) { - mCurrentDir = (OCFile) getIntent().getParcelableExtra(FileDetailFragment.EXTRA_FILE); - if(mCurrentDir != null && !mCurrentDir.isDirectory()){ - mCurrentDir = mStorageManager.getFileById(mCurrentDir.getParentId()); - } - // clear intent extra, so rotating the screen will not return us to this directory - getIntent().removeExtra(FileDetailFragment.EXTRA_FILE); + /// Check if mCurrentDir is a directory + if(mCurrentDir != null && !mCurrentDir.isDirectory()) { + mCurrentFile = mCurrentDir; + mCurrentDir = mStorageManager.getFileById(mCurrentDir.getParentId()); + } + + /// Check if mCurrentDir and mCurrentFile are in the current account, and update them + if (mCurrentDir != null) { + mCurrentDir = mStorageManager.getFileByPath(mCurrentDir.getRemotePath()); // mCurrentDir == null if it is not in the current account + } + if (mCurrentFile != null) { + if (mCurrentFile.fileExists()) { + mCurrentFile = mStorageManager.getFileByPath(mCurrentFile.getRemotePath()); // mCurrentFile == null if it is not in the current account + } // else : keep mCurrentFile with the received value; this is currently the case of an upload in progress, when the user presses the status notification in a landscape tablet + } + + /// Default to root if mCurrentDir was not found + if (mCurrentDir == null) { + mCurrentDir = mStorageManager.getFileByPath("/"); // will be NULL if the database was never synchronized } - if (mCurrentDir == null) - mCurrentDir = mStorageManager.getFileByPath("/"); // this will return NULL if the database has not ever synchronized } + + private void initFileDetailsInDualPane() { + if (mDualPane && getSupportFragmentManager().findFragmentByTag(FileDetailFragment.FTAG) == null) { + FragmentTransaction transaction = getSupportFragmentManager().beginTransaction(); + if (mCurrentFile != null) { + transaction.replace(R.id.file_details_container, new FileDetailFragment(mCurrentFile, AccountUtils.getCurrentOwnCloudAccount(this)), FileDetailFragment.FTAG); // empty FileDetailFragment + mCurrentFile = null; + } else { + transaction.replace(R.id.file_details_container, new FileDetailFragment(null, null), FileDetailFragment.FTAG); // empty FileDetailFragment + } + transaction.commit(); + } + } + + + @Override + public void onDestroy() { + super.onDestroy(); + if (mDownloadConnection != null) + unbindService(mDownloadConnection); + if (mUploadConnection != null) + unbindService(mUploadConnection); + } + @Override public boolean onCreateOptionsMenu(Menu menu) { MenuInflater inflater = getSherlock().getMenuInflater(); @@ -227,12 +282,7 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements break; } case R.id.startSync: { - ContentResolver.cancelSync(null, AccountAuthenticator.AUTH_TOKEN_TYPE); // cancel the current synchronizations of any ownCloud account - Bundle bundle = new Bundle(); - bundle.putBoolean(ContentResolver.SYNC_EXTRAS_MANUAL, true); - ContentResolver.requestSync( - AccountUtils.getCurrentOwnCloudAccount(this), - AccountAuthenticator.AUTH_TOKEN_TYPE, bundle); + startSynchronization(); break; } case R.id.action_upload: { @@ -260,6 +310,16 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements return retval; } + private void startSynchronization() { + ContentResolver.cancelSync(null, AccountAuthenticator.AUTH_TOKEN_TYPE); // cancel the current synchronizations of any ownCloud account + Bundle bundle = new Bundle(); + bundle.putBoolean(ContentResolver.SYNC_EXTRAS_MANUAL, true); + ContentResolver.requestSync( + AccountUtils.getCurrentOwnCloudAccount(this), + AccountAuthenticator.AUTH_TOKEN_TYPE, bundle); + } + + @Override public boolean onNavigationItemSelected(int itemPosition, long itemId) { int i = itemPosition; @@ -378,7 +438,7 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements if (fileDetails != null && !fileDetails.isEmpty()) { FragmentTransaction transaction = getSupportFragmentManager().beginTransaction(); transaction.remove(fileDetails); - transaction.add(R.id.file_details_container, new FileDetailFragment(null, null)); + transaction.add(R.id.file_details_container, new FileDetailFragment(null, null), FileDetailFragment.FTAG); transaction.commit(); } } @@ -395,6 +455,15 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements Log.d(getClass().toString(), "onSaveInstanceState() start"); super.onSaveInstanceState(outState); outState.putParcelable(FileDetailFragment.EXTRA_FILE, mCurrentDir); + if (mDualPane) { + FileDetailFragment fragment = (FileDetailFragment) getSupportFragmentManager().findFragmentByTag(FileDetailFragment.FTAG); + if (fragment != null) { + OCFile file = fragment.getDisplayedFile(); + if (file != null) { + outState.putParcelable(FileDetailFragment.EXTRA_FILE, file); + } + } + } Log.d(getClass().toString(), "onSaveInstanceState() end"); } @@ -408,6 +477,9 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements if (mStorageManager == null) { // this is necessary for handling the come back to FileDisplayActivity when the first ownCloud account is created initDataFromCurrentAccount(); + if (mDualPane) { + initFileDetailsInDualPane(); + } } // Listen for sync messages @@ -426,7 +498,7 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements registerReceiver(mDownloadFinishReceiver, downloadIntentFilter); // List current directory - mFileList.listDirectory(mCurrentDir); + mFileList.listDirectory(mCurrentDir); // TODO we should find the way to avoid the need of this (maybe it's not necessary yet; to check) } else { @@ -437,6 +509,7 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements Log.d(getClass().toString(), "onResume() end"); } + @Override protected void onPause() { Log.d(getClass().toString(), "onPause() start"); @@ -457,10 +530,18 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements dismissDialog(DIALOG_SETUP_ACCOUNT); } - getIntent().putExtra(FileDetailFragment.EXTRA_FILE, mCurrentDir); Log.d(getClass().toString(), "onPause() end"); } + + @Override + protected void onPrepareDialog(int id, Dialog dialog, Bundle args) { + if (id == DIALOG_SSL_VALIDATOR && mLastSslUntrustedServerResult != null) { + ((SslValidatorDialog)dialog).updateResult(mLastSslUntrustedServerResult); + } + } + + @Override protected Dialog onCreateDialog(int id) { Dialog dialog = null; @@ -493,7 +574,7 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements PackageInfo pkg; try { pkg = getPackageManager().getPackageInfo(getPackageName(), 0); - builder.setMessage("ownCloud android client\n\nversion: " + pkg.versionName ); + builder.setMessage(String.format(getString(R.string.about_message), pkg.versionName)); builder.setIcon(android.R.drawable.ic_menu_info_details); dialog = builder.create(); } catch (NameNotFoundException e) { @@ -586,6 +667,23 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements dialog = builder.create(); break; } + case DIALOG_SSL_VALIDATOR: { + dialog = SslValidatorDialog.newInstance(this, mLastSslUntrustedServerResult, this); + break; + } + case DIALOG_CERT_NOT_SAVED: { + builder = new AlertDialog.Builder(this); + builder.setMessage(getResources().getString(R.string.ssl_validator_not_saved)); + builder.setCancelable(false); + builder.setPositiveButton(R.string.common_ok, new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + dialog.dismiss(); + }; + }); + dialog = builder.create(); + break; + } default: dialog = null; } @@ -637,13 +735,11 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements private class DirectoryCreator implements Runnable { private String mTargetPath; private Account mAccount; - private AccountManager mAm; private Handler mHandler; public DirectoryCreator(String targetPath, Account account, Handler handler) { mTargetPath = targetPath; mAccount = account; - mAm = (AccountManager) getSystemService(ACCOUNT_SERVICE); mHandler = handler; } @@ -664,7 +760,7 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements mStorageManager.saveFile(newDir); // Display the new folder right away - mFileList.listDirectory(mCurrentDir); + mFileList.listDirectory(); } }); @@ -715,6 +811,7 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements } private class SyncBroadcastReceiver extends BroadcastReceiver { + /** * {@link BroadcastReceiver} to enable syncing feedback in UI */ @@ -745,13 +842,21 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements OCFileListFragment fileListFragment = (OCFileListFragment) getSupportFragmentManager() .findFragmentById(R.id.fileList); if (fileListFragment != null) { - fileListFragment.listDirectory(mCurrentDir); + fileListFragment.listDirectory(mCurrentDir); } } setSupportProgressBarIndeterminateVisibility(inProgress); } + + RemoteOperationResult synchResult = (RemoteOperationResult)intent.getSerializableExtra(FileSyncService.SYNC_RESULT); + if (synchResult != null) { + if (synchResult.getCode().equals(RemoteOperationResult.ResultCode.SSL_RECOVERABLE_PEER_UNVERIFIED)) { + mLastSslUntrustedServerResult = synchResult; + showDialog(DIALOG_SSL_VALIDATOR); + } + } } } @@ -830,7 +935,7 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements if (fileDetails != null && !fileDetails.isEmpty()) { FragmentTransaction transaction = getSupportFragmentManager().beginTransaction(); transaction.remove(fileDetails); - transaction.add(R.id.file_details_container, new FileDetailFragment(null, null)); + transaction.add(R.id.file_details_container, new FileDetailFragment(null, null), FileDetailFragment.FTAG); transaction.commit(); } } @@ -854,7 +959,7 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements } else { // small or medium screen device -> new Activity Intent showDetailsIntent = new Intent(this, FileDetailActivity.class); showDetailsIntent.putExtra(FileDetailFragment.EXTRA_FILE, file); - showDetailsIntent.putExtra(FileDownloader.EXTRA_ACCOUNT, AccountUtils.getCurrentOwnCloudAccount(this)); + showDetailsIntent.putExtra(FileDetailFragment.EXTRA_ACCOUNT, AccountUtils.getCurrentOwnCloudAccount(this)); startActivity(showDetailsIntent); } } @@ -864,12 +969,78 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements * {@inheritDoc} */ @Override + public OCFile getInitialDirectory() { + return mCurrentDir; + } + + + /** + * {@inheritDoc} + */ + @Override public void onFileStateChanged() { OCFileListFragment fileListFragment = (OCFileListFragment) getSupportFragmentManager().findFragmentById(R.id.fileList); if (fileListFragment != null) { fileListFragment.listDirectory(); } } + + + /** + * {@inheritDoc} + */ + @Override + public FileDownloaderBinder getFileDownloaderBinder() { + return mDownloaderBinder; + } + + + /** + * {@inheritDoc} + */ + @Override + public FileUploaderBinder getFileUploaderBinder() { + return mUploaderBinder; + } + + + /** Defines callbacks for service binding, passed to bindService() */ + private class ListServiceConnection implements ServiceConnection { + + @Override + public void onServiceConnected(ComponentName component, IBinder service) { + if (component.equals(new ComponentName(FileDisplayActivity.this, FileDownloader.class))) { + Log.d(TAG, "Download service connected"); + mDownloaderBinder = (FileDownloaderBinder) service; + } else if (component.equals(new ComponentName(FileDisplayActivity.this, FileUploader.class))) { + Log.d(TAG, "Upload service connected"); + mUploaderBinder = (FileUploaderBinder) service; + } else { + return; + } + // a new chance to get the mDownloadBinder through getFileDownloadBinder() - THIS IS A MESS + if (mFileList != null) + mFileList.listDirectory(); + if (mDualPane) { + FileDetailFragment fragment = (FileDetailFragment) getSupportFragmentManager().findFragmentByTag(FileDetailFragment.FTAG); + if (fragment != null) + fragment.updateFileDetails(); + } + } + + @Override + public void onServiceDisconnected(ComponentName component) { + if (component.equals(new ComponentName(FileDisplayActivity.this, FileDownloader.class))) { + Log.d(TAG, "Download service disconnected"); + mDownloaderBinder = null; + } else if (component.equals(new ComponentName(FileDisplayActivity.this, FileUploader.class))) { + Log.d(TAG, "Upload service disconnected"); + mUploaderBinder = null; + } + } + }; + + /** * Launch an intent to request the PIN code to the user before letting him use the app @@ -885,5 +1056,17 @@ public class FileDisplayActivity extends SherlockFragmentActivity implements } } - + + @Override + public void onSavedCertificate() { + startSynchronization(); + } + + + @Override + public void onFailedSavingCertificate() { + showDialog(DIALOG_CERT_NOT_SAVED); + } + + }