summaryrefslogtreecommitdiffstats
path: root/packages/DocumentsUI
diff options
context:
space:
mode:
authorJeff Sharkey <jsharkey@android.com>2013-09-03 14:17:06 -0700
committerJeff Sharkey <jsharkey@android.com>2013-09-03 14:17:10 -0700
commitded77187ef53341765fcab8e29cda94810fc2ca5 (patch)
treeb74b3dc22c9f256764492559547a4f51a69be2db /packages/DocumentsUI
parent9c104ab454de23628b5751db44ef08221d20dc86 (diff)
downloadframeworks_base-ded77187ef53341765fcab8e29cda94810fc2ca5.zip
frameworks_base-ded77187ef53341765fcab8e29cda94810fc2ca5.tar.gz
frameworks_base-ded77187ef53341765fcab8e29cda94810fc2ca5.tar.bz2
Updated documents UX around action bar.
Change action bar to match current design; drawer is always available and navigation dropdown is used to interact with current traversal path in hierarchy. On first launch, show recents with drawer expanded. On subsequent launches, resume from last location with drawer closed. If last location root isn't applicable, then behave like initial launch. Move sort order into action bar submenu. Delete documents using contract. Use unstable provider when inflating DocumentInfo from Uri. Bug: 10330219, 10510851 Change-Id: I6e94637d70ebca156a6c5d50272e878156d0dd62
Diffstat (limited to 'packages/DocumentsUI')
-rw-r--r--packages/DocumentsUI/res/layout/item_title.xml9
-rw-r--r--packages/DocumentsUI/res/menu/activity.xml17
-rw-r--r--packages/DocumentsUI/src/com/android/documentsui/DirectoryFragment.java9
-rw-r--r--packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java134
-rw-r--r--packages/DocumentsUI/src/com/android/documentsui/model/DocumentInfo.java38
-rw-r--r--packages/DocumentsUI/src/com/android/documentsui/model/DocumentStack.java4
6 files changed, 107 insertions, 104 deletions
diff --git a/packages/DocumentsUI/res/layout/item_title.xml b/packages/DocumentsUI/res/layout/item_title.xml
index fe6c14d..eab3839 100644
--- a/packages/DocumentsUI/res/layout/item_title.xml
+++ b/packages/DocumentsUI/res/layout/item_title.xml
@@ -29,13 +29,4 @@
android:textAppearance="?android:attr/textAppearanceMedium"
android:textAlignment="viewStart" />
- <TextView
- android:id="@android:id/summary"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:singleLine="true"
- android:ellipsize="marquee"
- android:textAppearance="?android:attr/textAppearanceSmall"
- android:textAlignment="viewStart" />
-
</LinearLayout>
diff --git a/packages/DocumentsUI/res/menu/activity.xml b/packages/DocumentsUI/res/menu/activity.xml
index 575336c..e182159 100644
--- a/packages/DocumentsUI/res/menu/activity.xml
+++ b/packages/DocumentsUI/res/menu/activity.xml
@@ -28,6 +28,23 @@
android:actionViewClass="android.widget.SearchView"
android:imeOptions="actionSearch" />
<item
+ android:id="@+id/menu_sort"
+ android:title="@string/menu_sort"
+ android:icon="@drawable/ic_menu_sort"
+ android:showAsAction="always">
+ <menu>
+ <item
+ android:id="@+id/menu_sort_name"
+ android:title="@string/sort_name" />
+ <item
+ android:id="@+id/menu_sort_date"
+ android:title="@string/sort_date" />
+ <item
+ android:id="@+id/menu_sort_size"
+ android:title="@string/sort_size" />
+ </menu>
+ </item>
+ <item
android:id="@+id/menu_grid"
android:title="@string/menu_grid"
android:icon="@drawable/ic_menu_grid"
diff --git a/packages/DocumentsUI/src/com/android/documentsui/DirectoryFragment.java b/packages/DocumentsUI/src/com/android/documentsui/DirectoryFragment.java
index 5b23ca5..1220137 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/DirectoryFragment.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/DirectoryFragment.java
@@ -397,13 +397,8 @@ public class DirectoryFragment extends Fragment {
continue;
}
- try {
- if (resolver.delete(doc.uri, null, null) != 1) {
- Log.w(TAG, "Failed to delete " + doc);
- hadTrouble = true;
- }
- } catch (Exception e) {
- Log.w(TAG, "Failed to delete " + doc + ": " + e);
+ if (!DocumentsContract.deleteDocument(resolver, doc.uri)) {
+ Log.w(TAG, "Failed to delete " + doc);
hadTrouble = true;
}
}
diff --git a/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java b/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java
index f569f5a..4da6567 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java
@@ -32,7 +32,6 @@ import android.app.FragmentManager;
import android.content.ActivityNotFoundException;
import android.content.ClipData;
import android.content.ComponentName;
-import android.content.ContentProviderClient;
import android.content.ContentResolver;
import android.content.ContentValues;
import android.content.Intent;
@@ -65,6 +64,8 @@ import com.android.documentsui.model.DocumentStack;
import com.android.documentsui.model.DurableUtils;
import com.android.documentsui.model.RootInfo;
+import libcore.io.IoUtils;
+
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.Arrays;
@@ -81,6 +82,8 @@ public class DocumentsActivity extends Activity {
private static final String EXTRA_STATE = "state";
+ private boolean mIgnoreNextNavigation;
+
private RootsCache mRoots;
private State mState;
@@ -192,10 +195,20 @@ public class DocumentsActivity extends Activity {
} catch (IOException e) {
Log.w(TAG, "Failed to resume", e);
} finally {
- cursor.close();
+ IoUtils.closeQuietly(cursor);
+ }
+
+ // If restored root isn't valid, fall back to recents
+ final RootInfo root = getCurrentRoot();
+ final List<RootInfo> matchingRoots = mRoots.getMatchingRoots(mState);
+ if (!matchingRoots.contains(root)) {
+ mState.stack.clear();
}
- mDrawerLayout.openDrawer(mRootsContainer);
+ // Only open drawer when showing recents
+ if (mState.stack.isRecents()) {
+ mDrawerLayout.openDrawer(mRootsContainer);
+ }
}
}
@@ -245,6 +258,14 @@ public class DocumentsActivity extends Activity {
actionBar.setDisplayShowHomeEnabled(true);
+ if (mState.action == ACTION_MANAGE) {
+ actionBar.setDisplayHomeAsUpEnabled(false);
+ mDrawerToggle.setDrawerIndicatorEnabled(false);
+ } else {
+ actionBar.setDisplayHomeAsUpEnabled(true);
+ mDrawerToggle.setDrawerIndicatorEnabled(true);
+ }
+
if (mDrawerLayout.isDrawerOpen(mRootsContainer)) {
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
actionBar.setIcon(new ColorDrawable());
@@ -254,33 +275,19 @@ public class DocumentsActivity extends Activity {
} else if (mState.action == ACTION_CREATE) {
actionBar.setTitle(R.string.title_save);
}
-
- actionBar.setDisplayHomeAsUpEnabled(true);
- mDrawerToggle.setDrawerIndicatorEnabled(true);
-
} else {
final RootInfo root = getCurrentRoot();
actionBar.setIcon(root != null ? root.loadIcon(this) : null);
- if (mRoots.isRecentsRoot(root)) {
+ if (mState.stack.size() <= 1) {
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
actionBar.setTitle(root.title);
} else {
+ mIgnoreNextNavigation = true;
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_LIST);
actionBar.setTitle(null);
- actionBar.setListNavigationCallbacks(mSortAdapter, mSortListener);
- actionBar.setSelectedNavigationItem(mState.sortOrder);
- }
-
- if (mState.stack.size() > 1) {
- actionBar.setDisplayHomeAsUpEnabled(true);
- mDrawerToggle.setDrawerIndicatorEnabled(false);
- } else if (mState.action == ACTION_MANAGE) {
- actionBar.setDisplayHomeAsUpEnabled(false);
- mDrawerToggle.setDrawerIndicatorEnabled(false);
- } else {
- actionBar.setDisplayHomeAsUpEnabled(true);
- mDrawerToggle.setDrawerIndicatorEnabled(true);
+ actionBar.setListNavigationCallbacks(mStackAdapter, mStackListener);
+ actionBar.setSelectedNavigationItem(mStackAdapter.getCount() - 1);
}
}
}
@@ -328,13 +335,20 @@ public class DocumentsActivity extends Activity {
final MenuItem createDir = menu.findItem(R.id.menu_create_dir);
final MenuItem search = menu.findItem(R.id.menu_search);
- final MenuItem grid = menu.findItem(R.id.menu_grid);
+ final MenuItem sort = menu.findItem(R.id.menu_sort);
+ final MenuItem sortSize = menu.findItem(R.id.menu_sort_size);
+ final MenuItem grid = menu.findItem(R.id.menu_grid);
final MenuItem list = menu.findItem(R.id.menu_list);
final MenuItem settings = menu.findItem(R.id.menu_settings);
grid.setVisible(mState.mode != MODE_GRID);
list.setVisible(mState.mode != MODE_LIST);
+ // No sorting in recents
+ sort.setVisible(cwd != null);
+ // Only sort by size when visible
+ sortSize.setVisible(mState.showSize);
+
final boolean searchVisible;
if (mState.action == ACTION_CREATE) {
createDir.setVisible(cwd != null && cwd.isCreateSupported());
@@ -375,6 +389,18 @@ public class DocumentsActivity extends Activity {
return true;
} else if (id == R.id.menu_search) {
return false;
+ } else if (id == R.id.menu_sort_name) {
+ mState.sortOrder = State.SORT_ORDER_DISPLAY_NAME;
+ updateDisplayState();
+ return true;
+ } else if (id == R.id.menu_sort_date) {
+ mState.sortOrder = State.SORT_ORDER_LAST_MODIFIED;
+ updateDisplayState();
+ return true;
+ } else if (id == R.id.menu_sort_size) {
+ mState.sortOrder = State.SORT_ORDER_SIZE;
+ updateDisplayState();
+ return true;
} else if (id == R.id.menu_grid) {
// TODO: persist explicit user mode for cwd
mState.mode = MODE_GRID;
@@ -421,25 +447,15 @@ public class DocumentsActivity extends Activity {
updateActionBar();
}
- // TODO: support additional sort orders
- private BaseAdapter mSortAdapter = new BaseAdapter() {
+ private BaseAdapter mStackAdapter = new BaseAdapter() {
@Override
public int getCount() {
- return mState.showSize ? 3 : 2;
+ return mState.stack.size();
}
@Override
- public Object getItem(int position) {
- switch (position) {
- case 0:
- return getText(R.string.sort_name);
- case 1:
- return getText(R.string.sort_date);
- case 2:
- return getText(R.string.sort_size);
- default:
- return null;
- }
+ public DocumentInfo getItem(int position) {
+ return mState.stack.get(mState.stack.size() - position - 1);
}
@Override
@@ -455,17 +471,15 @@ public class DocumentsActivity extends Activity {
}
final TextView title = (TextView) convertView.findViewById(android.R.id.title);
- final TextView summary = (TextView) convertView.findViewById(android.R.id.summary);
+ final DocumentInfo doc = getItem(position);
- if (mState.stack.size() > 0) {
- title.setText(mState.stack.getTitle(mRoots));
+ if (position == 0) {
+ final RootInfo root = getCurrentRoot();
+ title.setText(root.title);
} else {
- // No directory means recents
- title.setText(R.string.root_recent);
+ title.setText(doc.displayName);
}
- summary.setText((String) getItem(position));
-
return convertView;
}
@@ -477,17 +491,31 @@ public class DocumentsActivity extends Activity {
}
final TextView text1 = (TextView) convertView.findViewById(android.R.id.text1);
- text1.setText((String) getItem(position));
+ final DocumentInfo doc = getItem(position);
+
+ if (position == 0) {
+ final RootInfo root = getCurrentRoot();
+ text1.setText(root.title);
+ } else {
+ text1.setText(doc.displayName);
+ }
return convertView;
}
};
- private OnNavigationListener mSortListener = new OnNavigationListener() {
+ private OnNavigationListener mStackListener = new OnNavigationListener() {
@Override
public boolean onNavigationItemSelected(int itemPosition, long itemId) {
- mState.sortOrder = itemPosition;
- updateDisplayState();
+ if (mIgnoreNextNavigation) {
+ mIgnoreNextNavigation = false;
+ return false;
+ }
+
+ while (mState.stack.size() > itemPosition + 1) {
+ mState.stack.pop();
+ }
+ onCurrentDirectoryChanged();
return true;
}
};
@@ -629,16 +657,12 @@ public class DocumentsActivity extends Activity {
final DocumentInfo cwd = getCurrentDirectory();
final String authority = cwd.uri.getAuthority();
- final ContentProviderClient client = getContentResolver()
- .acquireUnstableContentProviderClient(authority);
- try {
- final Uri childUri = DocumentsContract.createDocument(
- getContentResolver(), cwd.uri, mimeType, displayName);
+ final Uri childUri = DocumentsContract.createDocument(
+ getContentResolver(), cwd.uri, mimeType, displayName);
+ if (childUri != null) {
onFinished(childUri);
- } catch (Exception e) {
+ } else {
Toast.makeText(this, R.string.save_error, Toast.LENGTH_SHORT).show();
- } finally {
- ContentProviderClient.closeQuietly(client);
}
}
diff --git a/packages/DocumentsUI/src/com/android/documentsui/model/DocumentInfo.java b/packages/DocumentsUI/src/com/android/documentsui/model/DocumentInfo.java
index 7721bcc..9874265 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/model/DocumentInfo.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/model/DocumentInfo.java
@@ -16,6 +16,7 @@
package com.android.documentsui.model;
+import android.content.ContentProviderClient;
import android.content.ContentResolver;
import android.content.Context;
import android.content.pm.PackageManager;
@@ -26,7 +27,6 @@ import android.net.Uri;
import android.provider.DocumentsContract;
import android.provider.DocumentsContract.Document;
-import com.android.documentsui.RecentsProvider;
import com.android.documentsui.RootCursorWrapper;
import libcore.io.IoUtils;
@@ -117,41 +117,12 @@ public class DocumentInfo implements Durable {
return doc;
}
- @Deprecated
- public static DocumentInfo fromRecentOpenCursor(ContentResolver resolver, Cursor recentCursor)
- throws FileNotFoundException {
- final Uri uri = Uri.parse(getCursorString(recentCursor, RecentsProvider.COL_URI));
- final long lastModified = getCursorLong(recentCursor, RecentsProvider.COL_TIMESTAMP);
-
- Cursor cursor = null;
- try {
- cursor = resolver.query(uri, null, null, null, null);
- if (!cursor.moveToFirst()) {
- throw new FileNotFoundException("Missing details for " + uri);
- }
-
- final DocumentInfo doc = new DocumentInfo();
- doc.uri = uri;
- doc.mimeType = getCursorString(cursor, Document.COLUMN_MIME_TYPE);
- doc.displayName = getCursorString(cursor, Document.COLUMN_DISPLAY_NAME);
- doc.lastModified = lastModified;
- doc.flags = getCursorInt(cursor, Document.COLUMN_FLAGS)
- & Document.FLAG_SUPPORTS_THUMBNAIL;
- doc.summary = getCursorString(cursor, Document.COLUMN_SUMMARY);
- doc.size = getCursorLong(cursor, Document.COLUMN_SIZE);
- doc.icon = getCursorInt(cursor, Document.COLUMN_ICON);
- return doc;
- } catch (Throwable t) {
- throw asFileNotFoundException(t);
- } finally {
- IoUtils.closeQuietly(cursor);
- }
- }
-
public static DocumentInfo fromUri(ContentResolver resolver, Uri uri) throws FileNotFoundException {
+ final ContentProviderClient client = resolver.acquireUnstableContentProviderClient(
+ uri.getAuthority());
Cursor cursor = null;
try {
- cursor = resolver.query(uri, null, null, null, null);
+ cursor = client.query(uri, null, null, null, null);
if (!cursor.moveToFirst()) {
throw new FileNotFoundException("Missing details for " + uri);
}
@@ -169,6 +140,7 @@ public class DocumentInfo implements Durable {
throw asFileNotFoundException(t);
} finally {
IoUtils.closeQuietly(cursor);
+ ContentProviderClient.closeQuietly(client);
}
}
diff --git a/packages/DocumentsUI/src/com/android/documentsui/model/DocumentStack.java b/packages/DocumentsUI/src/com/android/documentsui/model/DocumentStack.java
index 64631ab..33a1376 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/model/DocumentStack.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/model/DocumentStack.java
@@ -45,6 +45,10 @@ public class DocumentStack extends LinkedList<DocumentInfo> implements Durable {
}
}
+ public boolean isRecents() {
+ return size() == 0;
+ }
+
@Override
public void reset() {
clear();