From: masensio Date: Mon, 24 Feb 2014 12:33:23 +0000 (+0100) Subject: Merge branch 'develop' into send_file_pr311_with_develop X-Git-Tag: oc-android-1.5.5~22^2~16 X-Git-Url: http://git.linex4red.de/pub/Android/ownCloud.git/commitdiff_plain/af1f880b27f12c95703c37077e8074a9c9851df8?hp=4852ca8dd4578abbd651907aa3065af0dfaf2b4c Merge branch 'develop' into send_file_pr311_with_develop --- diff --git a/.gitmodules b/.gitmodules index 12d15b6e..f0ca8721 100644 --- a/.gitmodules +++ b/.gitmodules @@ -3,4 +3,4 @@ url = git://github.com/JakeWharton/ActionBarSherlock.git [submodule "owncloud-android-library"] path = owncloud-android-library - url = git@github.com:owncloud/android-library.git + url = git://github.com/owncloud/android-library.git diff --git a/AndroidManifest.xml b/AndroidManifest.xml index 465dec84..c92af064 100644 --- a/AndroidManifest.xml +++ b/AndroidManifest.xml @@ -18,8 +18,8 @@ along with this program. If not, see . --> + android:versionCode="105004" + android:versionName="1.5.4" xmlns:android="http://schemas.android.com/apk/res/android"> @@ -80,12 +80,10 @@ - + - - - + + + diff --git a/oc_jb_workaround/AndroidManifest.xml b/oc_jb_workaround/AndroidManifest.xml index ea251057..4bc25bae 100644 --- a/oc_jb_workaround/AndroidManifest.xml +++ b/oc_jb_workaround/AndroidManifest.xml @@ -1,8 +1,8 @@ + android:versionCode="0100013" + android:versionName="1.0.13" > ownCloud owncloud Owncloud_ - / + ownCloud @@ -39,11 +39,11 @@ true - false + true false - false - false - https://owncloud.com/mobile/help + true + true + http://owncloud.com/mobile/help "mailto:" "mailto:apps@owncloud.com" diff --git a/res/values/strings.xml b/res/values/strings.xml index af816994..60e4ecab 100644 --- a/res/values/strings.xml +++ b/res/values/strings.xml @@ -100,7 +100,7 @@ Contents of %1$d files could not be sync\'ed (%2$d conflicts) Some local files were forgotten %1$d files out of the %2$s directory could not be copied into - As of version 1.3.16, files uploaded from this device are copied into the local %1$s folder to prevent data loss when a single file is synced with multiple accounts.\n\nDue to this change, all files uploaded in previous versions of this app were copied into the %2$s folder. However, an error prevented the completion of this operation during account synchronization. You may either leave the file(s) as is and remove the link to %3$s, or move the file(s) into the %1$s directory and retain the link to %4$s.\n\nListed below are the local file(s), and the the remote file(s) in %5$s they were linked to. + As of version 1.3.16, files uploaded from this device are copied into the local %1$s folder to prevent data loss when a single file is synced with multiple accounts.\n\nDue to this change, all files uploaded in previous versions of this app were copied into the %2$s folder. However, an error prevented the completion of this operation during account synchronization. You may either leave the file(s) as is and remove the link to %3$s, or move the file(s) into the %1$s directory and retain the link to %4$s.\n\nListed below are the local file(s), and the remote file(s) in %5$s they were linked to. Folder %1$s does not exist anymore "Move all" "All files were moved" @@ -252,6 +252,9 @@ An error occurred while trying to share this file or folder Unable to unshare this file or folder. It does not exist. An error occurred while trying to unshare this file or folder - + Send + + Copy link + Copied to clipboard diff --git a/src/com/owncloud/android/authentication/AuthenticatorActivity.java b/src/com/owncloud/android/authentication/AuthenticatorActivity.java index 65b94c4f..b59ac6e7 100644 --- a/src/com/owncloud/android/authentication/AuthenticatorActivity.java +++ b/src/com/owncloud/android/authentication/AuthenticatorActivity.java @@ -36,7 +36,6 @@ import android.support.v4.app.Fragment; import android.text.Editable; import android.text.InputType; import android.text.TextWatcher; -import android.util.Log; import android.view.KeyEvent; import android.view.MotionEvent; import android.view.View; @@ -95,6 +94,7 @@ implements OnRemoteOperationListener, OnSslValidatorListener, OnFocusChangeList private static final String KEY_AUTH_MESSAGE_TEXT = "AUTH_MESSAGE_TEXT"; private static final String KEY_HOST_URL_TEXT = "HOST_URL_TEXT"; private static final String KEY_OC_VERSION = "OC_VERSION"; + private static final String KEY_OC_VERSION_STRING = "OC_VERSION_STRING"; private static final String KEY_ACCOUNT = "ACCOUNT"; private static final String KEY_SERVER_VALID = "SERVER_VALID"; private static final String KEY_SERVER_CHECKED = "SERVER_CHECKED"; @@ -106,7 +106,7 @@ implements OnRemoteOperationListener, OnSslValidatorListener, OnFocusChangeList private static final String KEY_AUTH_STATUS_TEXT = "AUTH_STATUS_TEXT"; private static final String KEY_AUTH_STATUS_ICON = "AUTH_STATUS_ICON"; private static final String KEY_REFRESH_BUTTON_ENABLED = "KEY_REFRESH_BUTTON_ENABLED"; - private static final String KEY_IS_SHARED_SUPPORTED = "KEY_IS_SHARE_SUPPORTED"; + //private static final String KEY_IS_SHARED_SUPPORTED = "KEY_IS_SHARE_SUPPORTED"; private static final String AUTH_ON = "on"; private static final String AUTH_OFF = "off"; @@ -124,7 +124,6 @@ implements OnRemoteOperationListener, OnSslValidatorListener, OnFocusChangeList private String mHostBaseUrl; private OwnCloudVersion mDiscoveredVersion; - private boolean mIsSharedSupported; private String mAuthMessageText; private int mAuthMessageVisibility, mServerStatusText, mServerStatusIcon; @@ -235,20 +234,19 @@ implements OnRemoteOperationListener, OnSslValidatorListener, OnFocusChangeList mServerIsChecked = false; mIsSslConn = false; mAuthStatusText = mAuthStatusIcon = 0; - mIsSharedSupported = false; /// retrieve extras from intent mAccount = getIntent().getExtras().getParcelable(EXTRA_ACCOUNT); - if (mAccount != null) { + if (mAccount != null) { String ocVersion = mAccountMgr.getUserData(mAccount, Constants.KEY_OC_VERSION); + String ocVersionString = mAccountMgr.getUserData(mAccount, Constants.KEY_OC_VERSION_STRING); if (ocVersion != null) { - mDiscoveredVersion = new OwnCloudVersion(ocVersion); + mDiscoveredVersion = new OwnCloudVersion(ocVersion, ocVersionString); } mHostBaseUrl = normalizeUrl(mAccountMgr.getUserData(mAccount, Constants.KEY_OC_BASE_URL)); mHostUrlInput.setText(mHostBaseUrl); String userName = mAccount.name.substring(0, mAccount.name.lastIndexOf('@')); - mUsernameInput.setText(userName); - mIsSharedSupported = Boolean.getBoolean(mAccountMgr.getUserData(mAccount, Constants.KEY_SUPPORTS_SHARE_API)); + mUsernameInput.setText(userName); } initAuthorizationMethod(); // checks intent and setup.xml to determine mCurrentAuthorizationMethod @@ -276,9 +274,9 @@ implements OnRemoteOperationListener, OnSslValidatorListener, OnFocusChangeList /// server data String ocVersion = savedInstanceState.getString(KEY_OC_VERSION); - mIsSharedSupported = savedInstanceState.getBoolean(KEY_IS_SHARED_SUPPORTED, false); + String ocVersionString = savedInstanceState.getString(KEY_OC_VERSION_STRING); if (ocVersion != null) { - mDiscoveredVersion = new OwnCloudVersion(ocVersion); + mDiscoveredVersion = new OwnCloudVersion(ocVersion, ocVersionString); } mHostBaseUrl = savedInstanceState.getString(KEY_HOST_URL_TEXT); @@ -453,10 +451,10 @@ implements OnRemoteOperationListener, OnSslValidatorListener, OnFocusChangeList /// server data if (mDiscoveredVersion != null) { - outState.putString(KEY_OC_VERSION, mDiscoveredVersion.toString()); + outState.putString(KEY_OC_VERSION, mDiscoveredVersion.getVersion()); + outState.putString(KEY_OC_VERSION_STRING, mDiscoveredVersion.getVersionString()); } outState.putString(KEY_HOST_URL_TEXT, mHostBaseUrl); - outState.putBoolean(KEY_IS_SHARED_SUPPORTED, mIsSharedSupported); /// account data, if updating if (mAccount != null) { @@ -591,7 +589,6 @@ implements OnRemoteOperationListener, OnSslValidatorListener, OnFocusChangeList mServerIsValid = false; mServerIsChecked = false; - mIsSharedSupported = false; mOkButton.setEnabled(false); mDiscoveredVersion = null; hideRefreshButton(); @@ -906,9 +903,6 @@ implements OnRemoteOperationListener, OnSslValidatorListener, OnFocusChangeList /// allow or not the user try to access the server mOkButton.setEnabled(mServerIsValid); - /// retrieve if is supported the Share API - mIsSharedSupported = operation.isSharedSupported(); - } // else nothing ; only the last check operation is considered; // multiple can be triggered if the user amends a URL before a previous check can be triggered } @@ -1298,10 +1292,11 @@ implements OnRemoteOperationListener, OnSslValidatorListener, OnFocusChangeList if (isOAuth || isSaml) { mAccountMgr.setAuthToken(mAccount, mAuthTokenType, mAuthToken); } - /// add user data to the new account; TODO probably can be done in the last parameter addAccountExplicitly, or in KEY_USERDATA - mAccountMgr.setUserData(mAccount, Constants.KEY_OC_VERSION, mDiscoveredVersion.toString()); + /// add user data to the new account; TODO probably can be done in the last parameter addAccountExplicitly, or in KEY_USERDATA + mAccountMgr.setUserData(mAccount, Constants.KEY_OC_VERSION, mDiscoveredVersion.getVersion()); + mAccountMgr.setUserData(mAccount, Constants.KEY_OC_VERSION_STRING, mDiscoveredVersion.getVersionString()); mAccountMgr.setUserData(mAccount, Constants.KEY_OC_BASE_URL, mHostBaseUrl); - mAccountMgr.setUserData(mAccount, Constants.KEY_SUPPORTS_SHARE_API, Boolean.toString(mIsSharedSupported)); + if (isSaml) { mAccountMgr.setUserData(mAccount, Constants.KEY_SUPPORTS_SAML_WEB_SSO, "TRUE"); } else if (isOAuth) { diff --git a/src/com/owncloud/android/datamodel/FileDataStorageManager.java b/src/com/owncloud/android/datamodel/FileDataStorageManager.java index a65833cd..5abdd892 100644 --- a/src/com/owncloud/android/datamodel/FileDataStorageManager.java +++ b/src/com/owncloud/android/datamodel/FileDataStorageManager.java @@ -858,8 +858,33 @@ public class FileDataStorageManager { return share; } - public OCShare getShareByPath(String path) { - Cursor c = getShareCursorForValue(ProviderTableMeta.OCSHARES_PATH, path); + public OCShare getFirstShareByPathAndType(String path, ShareType type) { + Cursor c = null; + if (getContentResolver() != null) { + c = getContentResolver().query( + ProviderTableMeta.CONTENT_URI_SHARE, + null, + ProviderTableMeta.OCSHARES_PATH + "=? AND " + + ProviderTableMeta.OCSHARES_SHARE_TYPE + "=? AND " + + ProviderTableMeta.OCSHARES_ACCOUNT_OWNER + "=?", + new String[] { path, Integer.toString(type.getValue()), mAccount.name }, + null); + } else { + try { + c = getContentProviderClient().query( + ProviderTableMeta.CONTENT_URI_SHARE, + null, + ProviderTableMeta.OCSHARES_PATH + "=? AND " + + ProviderTableMeta.OCSHARES_SHARE_TYPE + "=? AND " + + ProviderTableMeta.OCSHARES_ACCOUNT_OWNER + "=?", + new String[] { path, Integer.toString(type.getValue()), mAccount.name }, + null); + + } catch (RemoteException e) { + Log_OC.e(TAG, "Could not get file details: " + e.getMessage()); + c = null; + } + } OCShare share = null; if (c.moveToFirst()) { share = createShareInstance(c); diff --git a/src/com/owncloud/android/files/FileOperationsHelper.java b/src/com/owncloud/android/files/FileOperationsHelper.java index f77767d4..5b74dc89 100644 --- a/src/com/owncloud/android/files/FileOperationsHelper.java +++ b/src/com/owncloud/android/files/FileOperationsHelper.java @@ -28,11 +28,13 @@ import android.widget.Toast; import com.owncloud.android.R; import com.owncloud.android.datamodel.OCFile; + import com.owncloud.android.lib.common.accounts.AccountUtils.Constants; import com.owncloud.android.lib.common.network.WebdavUtils; +import com.owncloud.android.lib.resources.status.OwnCloudVersion; import com.owncloud.android.services.OperationsService; import com.owncloud.android.ui.activity.FileActivity; -import com.owncloud.android.ui.dialog.ActivityChooserDialog; +import com.owncloud.android.ui.dialog.ShareLinkToDialog; import com.owncloud.android.utils.Log_OC; /** @@ -88,7 +90,7 @@ public class FileOperationsHelper { String link = "https://fake.url"; Intent intent = createShareWithLinkIntent(link); String[] packagesToExclude = new String[] { callerActivity.getPackageName() }; - DialogFragment chooserDialog = ActivityChooserDialog.newInstance(intent, packagesToExclude, file); + DialogFragment chooserDialog = ShareLinkToDialog.newInstance(intent, packagesToExclude, file); chooserDialog.show(callerActivity.getSupportFragmentManager(), FTAG_CHOOSER_DIALOG); } else { @@ -135,7 +137,11 @@ public class FileOperationsHelper { public boolean isSharedSupported(FileActivity callerActivity) { if (callerActivity.getAccount() != null) { AccountManager accountManager = AccountManager.get(callerActivity); - return Boolean.parseBoolean(accountManager.getUserData(callerActivity.getAccount(), Constants.KEY_SUPPORTS_SHARE_API)); + + String version = accountManager.getUserData(callerActivity.getAccount(), Constants.KEY_OC_VERSION); + String versionString = accountManager.getUserData(callerActivity.getAccount(), Constants.KEY_OC_VERSION_STRING); + return (new OwnCloudVersion(version, versionString)).isSharedSupported(); + //return Boolean.parseBoolean(accountManager.getUserData(callerActivity.getAccount(), OwnCloudAccount.Constants.KEY_SUPPORTS_SHARE_API)); } return false; } @@ -171,7 +177,7 @@ public class FileOperationsHelper { // Show dialog, without the own app String[] packagesToExclude = new String[] { callerActivity.getPackageName() }; - DialogFragment chooserDialog = ActivityChooserDialog.newInstance(sendIntent, packagesToExclude, file); + DialogFragment chooserDialog = ShareLinkToDialog.newInstance(sendIntent, packagesToExclude, file); chooserDialog.show(callerActivity.getSupportFragmentManager(), FTAG_CHOOSER_DIALOG); } else { diff --git a/src/com/owncloud/android/files/services/FileObserverService.java b/src/com/owncloud/android/files/services/FileObserverService.java index fa1fec24..c6753896 100644 --- a/src/com/owncloud/android/files/services/FileObserverService.java +++ b/src/com/owncloud/android/files/services/FileObserverService.java @@ -22,6 +22,7 @@ import java.io.File; import java.util.HashMap; import java.util.Map; +import com.owncloud.android.MainApp; import com.owncloud.android.datamodel.FileDataStorageManager; import com.owncloud.android.datamodel.OCFile; import com.owncloud.android.db.ProviderMeta.ProviderTableMeta; @@ -141,7 +142,7 @@ public class FileObserverService extends Service { null); if (c == null || !c.moveToFirst()) return; AccountManager acm = AccountManager.get(this); - Account[] accounts = acm.getAccounts(); + Account[] accounts = acm.getAccountsByType(MainApp.getAccountType()); do { Account account = null; for (Account a : accounts) diff --git a/src/com/owncloud/android/files/services/FileUploader.java b/src/com/owncloud/android/files/services/FileUploader.java index 6fc33277..2f963562 100644 --- a/src/com/owncloud/android/files/services/FileUploader.java +++ b/src/com/owncloud/android/files/services/FileUploader.java @@ -253,7 +253,11 @@ public class FileUploader extends Service implements OnDatatransferProgressListe } } - OwnCloudVersion ocv = new OwnCloudVersion(AccountManager.get(this).getUserData(account, Constants.KEY_OC_VERSION)); + AccountManager aMgr = AccountManager.get(this); + String version = aMgr.getUserData(account, Constants.KEY_OC_VERSION); + String versionString = aMgr.getUserData(account, Constants.KEY_OC_VERSION_STRING); + OwnCloudVersion ocv = new OwnCloudVersion(version, versionString); + boolean chunked = FileUploader.chunkedUploadIsSupported(ocv); AbstractList requestedUploads = new Vector(); String uploadKey = null; diff --git a/src/com/owncloud/android/operations/SynchronizeFolderOperation.java b/src/com/owncloud/android/operations/SynchronizeFolderOperation.java index ac1acea3..5d957071 100644 --- a/src/com/owncloud/android/operations/SynchronizeFolderOperation.java +++ b/src/com/owncloud/android/operations/SynchronizeFolderOperation.java @@ -37,15 +37,18 @@ import android.content.Intent; import com.owncloud.android.datamodel.FileDataStorageManager; import com.owncloud.android.datamodel.OCFile; + import com.owncloud.android.lib.common.OwnCloudClient; import com.owncloud.android.lib.resources.shares.OCShare; import com.owncloud.android.lib.common.operations.RemoteOperation; import com.owncloud.android.lib.common.operations.RemoteOperationResult; import com.owncloud.android.lib.common.operations.RemoteOperationResult.ResultCode; import com.owncloud.android.lib.resources.shares.GetRemoteSharesForFileOperation; +import com.owncloud.android.lib.resources.files.FileUtils; import com.owncloud.android.lib.resources.files.ReadRemoteFileOperation; import com.owncloud.android.lib.resources.files.ReadRemoteFolderOperation; import com.owncloud.android.lib.resources.files.RemoteFile; + import com.owncloud.android.syncadapter.FileSyncAdapter; import com.owncloud.android.utils.FileStorageUtils; import com.owncloud.android.utils.Log_OC; @@ -101,7 +104,7 @@ public class SynchronizeFolderOperation extends RemoteOperation { private boolean mSyncFullAccount; /** 'True' means that Share resources bound to the files into the folder should be refreshed also */ - private boolean mRefreshShares; + private boolean mIsShareSupported; /** 'True' means that the remote folder changed from last synchronization and should be fetched */ private boolean mRemoteFolderChanged; @@ -122,14 +125,14 @@ public class SynchronizeFolderOperation extends RemoteOperation { public SynchronizeFolderOperation( OCFile folder, long currentSyncTime, boolean syncFullAccount, - boolean refreshShares, + boolean isShareSupported, FileDataStorageManager dataStorageManager, Account account, Context context ) { mLocalFolder = folder; mCurrentSyncTime = currentSyncTime; mSyncFullAccount = syncFullAccount; - mRefreshShares = refreshShares; + mIsShareSupported = isShareSupported; mStorageManager = dataStorageManager; mAccount = account; mContext = context; @@ -171,6 +174,10 @@ public class SynchronizeFolderOperation extends RemoteOperation { mConflictsFound = 0; mForgottenLocalFiles.clear(); + if (FileUtils.PATH_SEPARATOR.equals(mLocalFolder.getRemotePath()) && !mSyncFullAccount) { + updateOCVersion(client); + } + result = checkForChanges(client); if (result.isSuccess()) { @@ -185,7 +192,7 @@ public class SynchronizeFolderOperation extends RemoteOperation { sendLocalBroadcast(EVENT_SINGLE_FOLDER_CONTENTS_SYNCED, mLocalFolder.getRemotePath(), result); } - if (result.isSuccess() && mRefreshShares) { + if (result.isSuccess() && mIsShareSupported) { RemoteOperationResult shareResult = refreshSharesForFolder(client); if (shareResult.getCode() != ResultCode.FILE_NOT_FOUND) { result = shareResult; @@ -200,6 +207,16 @@ public class SynchronizeFolderOperation extends RemoteOperation { } + + private void updateOCVersion(OwnCloudClient client) { + UpdateOCVersionOperation update = new UpdateOCVersionOperation(mAccount, mContext); + RemoteOperationResult result = update.execute(client); + if (result.isSuccess()) { + mIsShareSupported = update.getOCVersion().isSharedSupported(); + } + } + + private RemoteOperationResult checkForChanges(OwnCloudClient client) { mRemoteFolderChanged = false; RemoteOperationResult result = null; diff --git a/src/com/owncloud/android/operations/UnshareLinkOperation.java b/src/com/owncloud/android/operations/UnshareLinkOperation.java index 218573e0..77ca8227 100644 --- a/src/com/owncloud/android/operations/UnshareLinkOperation.java +++ b/src/com/owncloud/android/operations/UnshareLinkOperation.java @@ -20,12 +20,15 @@ package com.owncloud.android.operations; import android.content.Context; import com.owncloud.android.datamodel.OCFile; + import com.owncloud.android.lib.common.OwnCloudClient; import com.owncloud.android.lib.common.operations.RemoteOperationResult; import com.owncloud.android.lib.common.operations.RemoteOperationResult.ResultCode; import com.owncloud.android.lib.resources.files.ExistenceCheckRemoteOperation; import com.owncloud.android.lib.resources.shares.OCShare; import com.owncloud.android.lib.resources.shares.RemoveRemoteShareOperation; +import com.owncloud.android.lib.resources.shares.ShareType; + import com.owncloud.android.operations.common.SyncOperation; import com.owncloud.android.utils.Log_OC; @@ -53,7 +56,7 @@ public class UnshareLinkOperation extends SyncOperation { RemoteOperationResult result = null; // Get Share for a file - OCShare share = getStorageManager().getShareByPath(mRemotePath); + OCShare share = getStorageManager().getFirstShareByPathAndType(mRemotePath, ShareType.PUBLIC_LINK); if (share != null) { RemoveRemoteShareOperation operation = new RemoveRemoteShareOperation((int) share.getIdRemoteShared()); diff --git a/src/com/owncloud/android/operations/UpdateOCVersionOperation.java b/src/com/owncloud/android/operations/UpdateOCVersionOperation.java index 22fdc934..c878ede4 100644 --- a/src/com/owncloud/android/operations/UpdateOCVersionOperation.java +++ b/src/com/owncloud/android/operations/UpdateOCVersionOperation.java @@ -47,11 +47,13 @@ public class UpdateOCVersionOperation extends RemoteOperation { private Account mAccount; private Context mContext; + private OwnCloudVersion mOwnCloudVersion; public UpdateOCVersionOperation(Account account, Context context) { mAccount = account; mContext = context; + mOwnCloudVersion = null; } @@ -74,10 +76,15 @@ public class UpdateOCVersionOperation extends RemoteOperation { if (response != null) { JSONObject json = new JSONObject(response); if (json != null && json.getString("version") != null) { - OwnCloudVersion ocver = new OwnCloudVersion(json.getString("version")); - if (ocver.isVersionValid()) { - accountMngr.setUserData(mAccount, Constants.KEY_OC_VERSION, ocver.toString()); - Log_OC.d(TAG, "Got new OC version " + ocver.toString()); + + String version = json.getString("version"); + String versionstring = json.getString("versionstring"); + mOwnCloudVersion = new OwnCloudVersion(version, versionstring); + if (mOwnCloudVersion.isVersionValid()) { + accountMngr.setUserData(mAccount, Constants.KEY_OC_VERSION, mOwnCloudVersion.getVersion()); + accountMngr.setUserData(mAccount, Constants.KEY_OC_VERSION_STRING, mOwnCloudVersion.getVersionString()); + Log_OC.d(TAG, "Got new OC version " + mOwnCloudVersion.toString()); + result = new RemoteOperationResult(ResultCode.OK); } else { @@ -107,4 +114,9 @@ public class UpdateOCVersionOperation extends RemoteOperation { return result; } + + public OwnCloudVersion getOCVersion() { + return mOwnCloudVersion; + } + } diff --git a/src/com/owncloud/android/syncadapter/FileSyncAdapter.java b/src/com/owncloud/android/syncadapter/FileSyncAdapter.java index c0b9b0d1..349f1370 100644 --- a/src/com/owncloud/android/syncadapter/FileSyncAdapter.java +++ b/src/com/owncloud/android/syncadapter/FileSyncAdapter.java @@ -110,7 +110,7 @@ public class FileSyncAdapter extends AbstractOwnCloudSyncAdapter { private SyncResult mSyncResult; /** 'True' means that the server supports the share API */ - private boolean mIsSharedSupported; + private boolean mIsShareSupported; /** @@ -156,9 +156,6 @@ public class FileSyncAdapter extends AbstractOwnCloudSyncAdapter { this.setContentProviderClient(providerClient); this.setStorageManager(new FileDataStorageManager(account, providerClient)); - AccountManager accountManager = getAccountManager(); - mIsSharedSupported = Boolean.parseBoolean(accountManager.getUserData(account, Constants.KEY_SUPPORTS_SHARE_API)); - try { this.initClientForCurrentAccount(); } catch (IOException e) { @@ -235,6 +232,8 @@ public class FileSyncAdapter extends AbstractOwnCloudSyncAdapter { RemoteOperationResult result = update.execute(getClient()); if (!result.isSuccess()) { mLastFailedResult = result; + } else { + mIsShareSupported = update.getOCVersion().isSharedSupported(); } } @@ -269,7 +268,7 @@ public class FileSyncAdapter extends AbstractOwnCloudSyncAdapter { SynchronizeFolderOperation synchFolderOp = new SynchronizeFolderOperation( folder, mCurrentSyncTime, true, - mIsSharedSupported, + mIsShareSupported, getStorageManager(), getAccount(), getContext() diff --git a/src/com/owncloud/android/ui/activity/CopyToClipboardActivity.java b/src/com/owncloud/android/ui/activity/CopyToClipboardActivity.java new file mode 100644 index 00000000..7c546412 --- /dev/null +++ b/src/com/owncloud/android/ui/activity/CopyToClipboardActivity.java @@ -0,0 +1,66 @@ +/* ownCloud Android client application + * Copyright (C) 2012-2014 ownCloud Inc. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2, + * as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * + */ + +package com.owncloud.android.ui.activity; + +import com.owncloud.android.R; + +import android.app.Activity; +import android.content.ClipData; +import android.content.Intent; +import android.os.Build; +import android.os.Bundle; +import android.text.ClipboardManager; +import android.widget.Toast; + +/** + * Activity copying the text of the received Intent into the system clibpoard. + * + * @author David A. Velasco + */ +@SuppressWarnings("deprecation") +public class CopyToClipboardActivity extends Activity { + + @Override + public void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + + // get the clipboard system service + ClipboardManager clipboardManager = (ClipboardManager) this.getSystemService(CLIPBOARD_SERVICE); + + // get the text to copy into the clipboard + Intent intent = getIntent(); + CharSequence text = intent.getCharSequenceExtra(Intent.EXTRA_TEXT); + + // and put the text the clipboard + if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.HONEYCOMB) { + // API level >= 11 -> modern Clipboard + ClipData clip = ClipData.newPlainText("ownCloud was here", text); + ((android.content.ClipboardManager)clipboardManager).setPrimaryClip(clip); + + } else { + // API level >= 11 -> legacy Clipboard + clipboardManager.setText(text); + } + + // alert the user that the text is in the clipboard and we're done + Toast.makeText(this, R.string.clipboard_text_copied, Toast.LENGTH_SHORT).show(); + + finish(); + } + +} diff --git a/src/com/owncloud/android/ui/dialog/ActivityChooserDialog.java b/src/com/owncloud/android/ui/dialog/ActivityChooserDialog.java deleted file mode 100644 index 71d67604..00000000 --- a/src/com/owncloud/android/ui/dialog/ActivityChooserDialog.java +++ /dev/null @@ -1,174 +0,0 @@ -/* ownCloud Android client application - * Copyright (C) 2012-2014 ownCloud Inc. - * - * This program is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2, - * as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see . - * - */ - -package com.owncloud.android.ui.dialog; - -import java.util.Arrays; -import java.util.Collections; -import java.util.Iterator; -import java.util.List; - -import android.app.AlertDialog; -import android.app.Dialog; -import android.content.ComponentName; -import android.content.Context; -import android.content.DialogInterface; -import android.content.Intent; -import android.content.pm.ActivityInfo; -import android.content.pm.PackageManager; -import android.content.pm.ResolveInfo; -import android.os.Bundle; -import android.view.LayoutInflater; -import android.view.View; -import android.view.ViewGroup; -import android.widget.ArrayAdapter; -import android.widget.ImageView; -import android.widget.TextView; - -import com.actionbarsherlock.app.SherlockDialogFragment; -import com.owncloud.android.R; -import com.owncloud.android.datamodel.OCFile; -import com.owncloud.android.files.FileOperationsHelper; -import com.owncloud.android.ui.activity.FileActivity; -import com.owncloud.android.utils.Log_OC; - -/** - * Dialog showing a list activities able to resolve a given Intent, - * filtering out the activities matching give package names. - * - * @author David A. Velasco - */ -public class ActivityChooserDialog extends SherlockDialogFragment { - - private final static String TAG = ActivityChooserDialog.class.getSimpleName(); - private final static String ARG_INTENT = ActivityChooserDialog.class.getSimpleName() + ".ARG_INTENT"; - private final static String ARG_PACKAGES_TO_EXCLUDE = ActivityChooserDialog.class.getSimpleName() + ".ARG_PACKAGES_TO_EXCLUDE"; - private final static String ARG_FILE_TO_SHARE = ActivityChooserDialog.class.getSimpleName() + ".FILE_TO_SHARE"; - - private ActivityAdapter mAdapter; - private OCFile mFile; - private Intent mIntent; - - public static ActivityChooserDialog newInstance(Intent intent, String[] packagesToExclude, OCFile fileToShare) { - ActivityChooserDialog f = new ActivityChooserDialog(); - Bundle args = new Bundle(); - args.putParcelable(ARG_INTENT, intent); - args.putStringArray(ARG_PACKAGES_TO_EXCLUDE, packagesToExclude); - args.putParcelable(ARG_FILE_TO_SHARE, fileToShare); - f.setArguments(args); - return f; - } - - public ActivityChooserDialog() { - super(); - Log_OC.d(TAG, "constructor"); - } - - @Override - public Dialog onCreateDialog(Bundle savedInstanceState) { - mIntent = getArguments().getParcelable(ARG_INTENT); - String[] packagesToExclude = getArguments().getStringArray(ARG_PACKAGES_TO_EXCLUDE); - List packagesToExcludeList = Arrays.asList(packagesToExclude != null ? packagesToExclude : new String[0]); - mFile = getArguments().getParcelable(ARG_FILE_TO_SHARE); - - PackageManager pm= getSherlockActivity().getPackageManager(); - List activities = pm.queryIntentActivities(mIntent, PackageManager.MATCH_DEFAULT_ONLY); - Iterator it = activities.iterator(); - ResolveInfo resolveInfo; - while (it.hasNext()) { - resolveInfo = it.next(); - if (packagesToExcludeList.contains(resolveInfo.activityInfo.packageName.toLowerCase())) { - it.remove(); - } - } - Collections.sort(activities, new ResolveInfo.DisplayNameComparator(pm)); - mAdapter = new ActivityAdapter(getSherlockActivity(), pm, activities); - - boolean sendAction = mIntent.getBooleanExtra(Intent.ACTION_SEND, false); - - if (sendAction) { - - return new AlertDialog.Builder(getSherlockActivity()) - .setTitle(R.string.activity_chooser_title) - .setAdapter(mAdapter, new DialogInterface.OnClickListener() { - @Override - public void onClick(DialogInterface dialog, int which) { - // Add the information of the chosen activity to the intent to send - ResolveInfo chosen = mAdapter.getItem(which); - ActivityInfo actInfo = chosen.activityInfo; - ComponentName name=new ComponentName(actInfo.applicationInfo.packageName, actInfo.name); - mIntent.setComponent(name); - - // Send the file - ((FileActivity)getSherlockActivity()).startActivity(mIntent); - - } - }) - .create(); - } else { - return new AlertDialog.Builder(getSherlockActivity()) - .setTitle(R.string.activity_chooser_send_file_title) - .setAdapter(mAdapter, new DialogInterface.OnClickListener() { - @Override - public void onClick(DialogInterface dialog, int which) { - // Add the information of the chosen activity to the intent to send - ResolveInfo chosen = mAdapter.getItem(which); - ActivityInfo actInfo = chosen.activityInfo; - ComponentName name=new ComponentName(actInfo.applicationInfo.packageName, actInfo.name); - mIntent.setComponent(name); - - // Create a new share resource - FileOperationsHelper foh = new FileOperationsHelper(); - foh.shareFileWithLinkToApp(mFile, mIntent, (FileActivity)getSherlockActivity()); - } - }) - .create(); - } - } - - - class ActivityAdapter extends ArrayAdapter { - - private PackageManager mPackageManager; - - ActivityAdapter(Context context, PackageManager pm, List apps) { - super(context, R.layout.activity_row, apps); - this.mPackageManager = pm; - } - - @Override - public View getView(int position, View convertView, ViewGroup parent) { - if (convertView == null) { - convertView = newView(parent); - } - bindView(position, convertView); - return convertView; - } - - private View newView(ViewGroup parent) { - return(((LayoutInflater)getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.activity_row, parent, false)); - } - - private void bindView(int position, View row) { - TextView label = (TextView) row.findViewById(R.id.title); - label.setText(getItem(position).loadLabel(mPackageManager)); - ImageView icon = (ImageView) row.findViewById(R.id.icon); - icon.setImageDrawable(getItem(position).loadIcon(mPackageManager)); - } - } - -} diff --git a/src/com/owncloud/android/ui/dialog/ShareLinkToDialog.java b/src/com/owncloud/android/ui/dialog/ShareLinkToDialog.java new file mode 100644 index 00000000..68e1485b --- /dev/null +++ b/src/com/owncloud/android/ui/dialog/ShareLinkToDialog.java @@ -0,0 +1,183 @@ +/* ownCloud Android client application + * Copyright (C) 2012-2014 ownCloud Inc. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2, + * as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * + */ + +package com.owncloud.android.ui.dialog; + +import java.util.Arrays; +import java.util.Collections; +import java.util.Iterator; +import java.util.List; + +import android.app.AlertDialog; +import android.app.Dialog; +import android.content.ComponentName; +import android.content.Context; +import android.content.DialogInterface; +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.content.pm.PackageManager; +import android.content.pm.ResolveInfo; +import android.os.Bundle; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.ArrayAdapter; +import android.widget.ImageView; +import android.widget.TextView; + +import com.actionbarsherlock.app.SherlockDialogFragment; +import com.owncloud.android.R; +import com.owncloud.android.datamodel.OCFile; +import com.owncloud.android.files.FileOperationsHelper; +import com.owncloud.android.ui.activity.CopyToClipboardActivity; +import com.owncloud.android.ui.activity.FileActivity; +import com.owncloud.android.utils.Log_OC; + +/** + * Dialog showing a list activities able to resolve a given Intent, + * filtering out the activities matching give package names. + * + * @author David A. Velasco + */ +public class ShareLinkToDialog extends SherlockDialogFragment { + + private final static String TAG = ShareLinkToDialog.class.getSimpleName(); + private final static String ARG_INTENT = ShareLinkToDialog.class.getSimpleName() + ".ARG_INTENT"; + private final static String ARG_PACKAGES_TO_EXCLUDE = ShareLinkToDialog.class.getSimpleName() + ".ARG_PACKAGES_TO_EXCLUDE"; + private final static String ARG_FILE_TO_SHARE = ShareLinkToDialog.class.getSimpleName() + ".FILE_TO_SHARE"; + + private ActivityAdapter mAdapter; + private OCFile mFile; + private Intent mIntent; + + public static ShareLinkToDialog newInstance(Intent intent, String[] packagesToExclude, OCFile fileToShare) { + ShareLinkToDialog f = new ShareLinkToDialog(); + Bundle args = new Bundle(); + args.putParcelable(ARG_INTENT, intent); + args.putStringArray(ARG_PACKAGES_TO_EXCLUDE, packagesToExclude); + args.putParcelable(ARG_FILE_TO_SHARE, fileToShare); + f.setArguments(args); + return f; + } + + public ShareLinkToDialog() { + super(); + Log_OC.d(TAG, "constructor"); + } + + @Override + public Dialog onCreateDialog(Bundle savedInstanceState) { + mIntent = getArguments().getParcelable(ARG_INTENT); + String[] packagesToExclude = getArguments().getStringArray(ARG_PACKAGES_TO_EXCLUDE); + List packagesToExcludeList = Arrays.asList(packagesToExclude != null ? packagesToExclude : new String[0]); + mFile = getArguments().getParcelable(ARG_FILE_TO_SHARE); + + PackageManager pm= getSherlockActivity().getPackageManager(); + List activities = pm.queryIntentActivities(mIntent, PackageManager.MATCH_DEFAULT_ONLY); + Iterator it = activities.iterator(); + ResolveInfo resolveInfo; + while (it.hasNext()) { + resolveInfo = it.next(); + if (packagesToExcludeList.contains(resolveInfo.activityInfo.packageName.toLowerCase())) { + it.remove(); + } + } + + // add activity for copy to clipboard + Intent copyToClipboardIntent = new Intent(getSherlockActivity(), CopyToClipboardActivity.class); + List copyToClipboard = pm.queryIntentActivities(copyToClipboardIntent, 0); + if (!copyToClipboard.isEmpty()) { + activities.add(copyToClipboard.get(0)); + } + + Collections.sort(activities, new ResolveInfo.DisplayNameComparator(pm)); + mAdapter = new ActivityAdapter(getSherlockActivity(), pm, activities); + + boolean sendAction = mIntent.getBooleanExtra(Intent.ACTION_SEND, false); + + if (sendAction) { + + return new AlertDialog.Builder(getSherlockActivity()) + .setTitle(R.string.activity_chooser_send_file_title) + .setAdapter(mAdapter, new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + // Add the information of the chosen activity to the intent to send + ResolveInfo chosen = mAdapter.getItem(which); + ActivityInfo actInfo = chosen.activityInfo; + ComponentName name=new ComponentName(actInfo.applicationInfo.packageName, actInfo.name); + mIntent.setComponent(name); + + // Send the file + ((FileActivity)getSherlockActivity()).startActivity(mIntent); + + } + }) + .create(); + } else { + return new AlertDialog.Builder(getSherlockActivity()) + .setTitle(R.string.activity_chooser_title) + .setAdapter(mAdapter, new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + // Add the information of the chosen activity to the intent to send + ResolveInfo chosen = mAdapter.getItem(which); + ActivityInfo actInfo = chosen.activityInfo; + ComponentName name=new ComponentName(actInfo.applicationInfo.packageName, actInfo.name); + mIntent.setComponent(name); + + // Create a new share resource + FileOperationsHelper foh = new FileOperationsHelper(); + foh.shareFileWithLinkToApp(mFile, mIntent, (FileActivity)getSherlockActivity()); + } + }) + .create(); + } + } + + + class ActivityAdapter extends ArrayAdapter { + + private PackageManager mPackageManager; + + ActivityAdapter(Context context, PackageManager pm, List apps) { + super(context, R.layout.activity_row, apps); + this.mPackageManager = pm; + } + + @Override + public View getView(int position, View convertView, ViewGroup parent) { + if (convertView == null) { + convertView = newView(parent); + } + bindView(position, convertView); + return convertView; + } + + private View newView(ViewGroup parent) { + return(((LayoutInflater)getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.activity_row, parent, false)); + } + + private void bindView(int position, View row) { + TextView label = (TextView) row.findViewById(R.id.title); + label.setText(getItem(position).loadLabel(mPackageManager)); + ImageView icon = (ImageView) row.findViewById(R.id.icon); + icon.setImageDrawable(getItem(position).loadIcon(mPackageManager)); + } + } + +}