diff options
12 files changed, 131 insertions, 67 deletions
diff --git a/api/current.txt b/api/current.txt index ac3948f..d4e23f3 100644 --- a/api/current.txt +++ b/api/current.txt @@ -17974,6 +17974,7 @@ package android.os { method public static boolean isExternalStorageRemovable(); field public static java.lang.String DIRECTORY_ALARMS; field public static java.lang.String DIRECTORY_DCIM; + field public static java.lang.String DIRECTORY_DOCUMENTS; field public static java.lang.String DIRECTORY_DOWNLOADS; field public static java.lang.String DIRECTORY_MOVIES; field public static java.lang.String DIRECTORY_MUSIC; @@ -20811,10 +20812,9 @@ package android.provider { field public static final java.lang.String COLUMN_MIME_TYPE = "mime_type"; field public static final java.lang.String COLUMN_SIZE = "_size"; field public static final java.lang.String COLUMN_SUMMARY = "summary"; - field public static final int FLAG_DIR_PREFERS_GRID = 32; // 0x20 - field public static final int FLAG_DIR_PREFERS_LAST_MODIFIED = 64; // 0x40 + field public static final int FLAG_DIR_PREFERS_GRID = 16; // 0x10 + field public static final int FLAG_DIR_PREFERS_LAST_MODIFIED = 32; // 0x20 field public static final int FLAG_DIR_SUPPORTS_CREATE = 8; // 0x8 - field public static final int FLAG_DIR_SUPPORTS_SEARCH = 16; // 0x10 field public static final int FLAG_SUPPORTS_DELETE = 4; // 0x4 field public static final int FLAG_SUPPORTS_THUMBNAIL = 1; // 0x1 field public static final int FLAG_SUPPORTS_WRITE = 2; // 0x2 @@ -20832,9 +20832,11 @@ package android.provider { field public static final java.lang.String COLUMN_SUMMARY = "summary"; field public static final java.lang.String COLUMN_TITLE = "title"; field public static final int FLAG_ADVANCED = 4; // 0x4 + field public static final int FLAG_EMPTY = 32; // 0x20 field public static final int FLAG_LOCAL_ONLY = 2; // 0x2 field public static final int FLAG_SUPPORTS_CREATE = 1; // 0x1 field public static final int FLAG_SUPPORTS_RECENTS = 8; // 0x8 + field public static final int FLAG_SUPPORTS_SEARCH = 16; // 0x10 field public static final int ROOT_TYPE_DEVICE = 3; // 0x3 field public static final int ROOT_TYPE_SERVICE = 1; // 0x1 field public static final int ROOT_TYPE_SHORTCUT = 2; // 0x2 diff --git a/core/java/android/os/Environment.java b/core/java/android/os/Environment.java index c6e8c3e..5b36bca 100644 --- a/core/java/android/os/Environment.java +++ b/core/java/android/os/Environment.java @@ -460,7 +460,13 @@ public class Environment { * top-level public directory, as this convention makes no sense elsewhere. */ public static String DIRECTORY_DCIM = "DCIM"; - + + /** + * Standard directory in which to place documents that have been created by + * the user. + */ + public static String DIRECTORY_DOCUMENTS = "Documents"; + /** * Get a top-level public external storage directory for placing files of * a particular type. This is where the user will typically place and diff --git a/core/java/android/provider/DocumentsContract.java b/core/java/android/provider/DocumentsContract.java index 37ce065..231e6a6 100644 --- a/core/java/android/provider/DocumentsContract.java +++ b/core/java/android/provider/DocumentsContract.java @@ -64,9 +64,9 @@ public final class DocumentsContract { // content://com.example/root/ // content://com.example/root/sdcard/ // content://com.example/root/sdcard/recent/ + // content://com.example/root/sdcard/search/?query=pony // content://com.example/document/12/ // content://com.example/document/12/children/ - // content://com.example/document/12/search/?query=pony private DocumentsContract() { } @@ -174,7 +174,6 @@ public final class DocumentsContract { * @see #FLAG_SUPPORTS_THUMBNAIL * @see #FLAG_DIR_PREFERS_GRID * @see #FLAG_DIR_SUPPORTS_CREATE - * @see #FLAG_DIR_SUPPORTS_SEARCH */ public static final String COLUMN_FLAGS = "flags"; @@ -241,16 +240,6 @@ public final class DocumentsContract { public static final int FLAG_DIR_SUPPORTS_CREATE = 1 << 3; /** - * Flag indicating that a directory supports search. Only valid when - * {@link #COLUMN_MIME_TYPE} is {@link #MIME_TYPE_DIR}. - * - * @see #COLUMN_FLAGS - * @see DocumentsProvider#querySearchDocuments(String, String, - * String[]) - */ - public static final int FLAG_DIR_SUPPORTS_SEARCH = 1 << 4; - - /** * Flag indicating that a directory prefers its contents be shown in a * larger format grid. Usually suitable when a directory contains mostly * pictures. Only valid when {@link #COLUMN_MIME_TYPE} is @@ -258,7 +247,7 @@ public final class DocumentsContract { * * @see #COLUMN_FLAGS */ - public static final int FLAG_DIR_PREFERS_GRID = 1 << 5; + public static final int FLAG_DIR_PREFERS_GRID = 1 << 4; /** * Flag indicating that a directory prefers its contents be sorted by @@ -267,7 +256,7 @@ public final class DocumentsContract { * * @see #COLUMN_FLAGS */ - public static final int FLAG_DIR_PREFERS_LAST_MODIFIED = 1 << 6; + public static final int FLAG_DIR_PREFERS_LAST_MODIFIED = 1 << 5; } /** @@ -306,9 +295,12 @@ public final class DocumentsContract { * <p> * Type: INTEGER (int) * + * @see #FLAG_ADVANCED + * @see #FLAG_EMPTY * @see #FLAG_LOCAL_ONLY * @see #FLAG_SUPPORTS_CREATE - * @see #FLAG_ADVANCED + * @see #FLAG_SUPPORTS_RECENTS + * @see #FLAG_SUPPORTS_SEARCH */ public static final String COLUMN_FLAGS = "flags"; @@ -422,6 +414,27 @@ public final class DocumentsContract { * @see DocumentsContract#buildRecentDocumentsUri(String, String) */ public static final int FLAG_SUPPORTS_RECENTS = 1 << 3; + + /** + * Flag indicating that this root supports search. + * + * @see #COLUMN_FLAGS + * @see DocumentsProvider#querySearchDocuments(String, String, + * String[]) + */ + public static final int FLAG_SUPPORTS_SEARCH = 1 << 4; + + /** + * Flag indicating that this root is currently empty. This may be used + * to hide the root when opening documents, but the root will still be + * shown when creating documents and {@link #FLAG_SUPPORTS_CREATE} is + * also set. + * + * @see #COLUMN_FLAGS + * @see DocumentsProvider#querySearchDocuments(String, String, + * String[]) + */ + public static final int FLAG_EMPTY = 1 << 5; } /** @@ -493,9 +506,9 @@ public final class DocumentsContract { } /** - * Build Uri representing the recently modified documents of a specific - * root. When queried, a provider will return zero or more rows with columns - * defined by {@link Document}. + * Build Uri representing the recently modified documents of a specific root + * in a document provider. When queried, a provider will return zero or more + * rows with columns defined by {@link Document}. * * @see DocumentsProvider#queryRecentDocuments(String, String[]) * @see #getRootId(Uri) @@ -538,21 +551,17 @@ public final class DocumentsContract { /** * Build Uri representing a search for matching documents under a specific - * directory in a document provider. When queried, a provider will return - * zero or more rows with columns defined by {@link Document}. + * root in a document provider. When queried, a provider will return zero or + * more rows with columns defined by {@link Document}. * - * @param parentDocumentId the document to return children for, which must - * be both a directory with MIME type of - * {@link Document#MIME_TYPE_DIR} and have - * {@link Document#FLAG_DIR_SUPPORTS_SEARCH} set. * @see DocumentsProvider#querySearchDocuments(String, String, String[]) - * @see #getDocumentId(Uri) + * @see #getRootId(Uri) * @see #getSearchDocumentsQuery(Uri) */ public static Uri buildSearchDocumentsUri( - String authority, String parentDocumentId, String query) { + String authority, String rootId, String query) { return new Uri.Builder().scheme(ContentResolver.SCHEME_CONTENT).authority(authority) - .appendPath(PATH_DOCUMENT).appendPath(parentDocumentId).appendPath(PATH_SEARCH) + .appendPath(PATH_ROOT).appendPath(rootId).appendPath(PATH_SEARCH) .appendQueryParameter(PARAM_QUERY, query).build(); } diff --git a/core/java/android/provider/DocumentsProvider.java b/core/java/android/provider/DocumentsProvider.java index d801827..bc4e28b 100644 --- a/core/java/android/provider/DocumentsProvider.java +++ b/core/java/android/provider/DocumentsProvider.java @@ -75,9 +75,9 @@ public abstract class DocumentsProvider extends ContentProvider { private static final int MATCH_ROOTS = 1; private static final int MATCH_ROOT = 2; private static final int MATCH_RECENT = 3; - private static final int MATCH_DOCUMENT = 4; - private static final int MATCH_CHILDREN = 5; - private static final int MATCH_SEARCH = 6; + private static final int MATCH_SEARCH = 4; + private static final int MATCH_DOCUMENT = 5; + private static final int MATCH_CHILDREN = 6; private String mAuthority; @@ -94,9 +94,9 @@ public abstract class DocumentsProvider extends ContentProvider { mMatcher.addURI(mAuthority, "root", MATCH_ROOTS); mMatcher.addURI(mAuthority, "root/*", MATCH_ROOT); mMatcher.addURI(mAuthority, "root/*/recent", MATCH_RECENT); + mMatcher.addURI(mAuthority, "root/*/search", MATCH_SEARCH); mMatcher.addURI(mAuthority, "document/*", MATCH_DOCUMENT); mMatcher.addURI(mAuthority, "document/*/children", MATCH_CHILDREN); - mMatcher.addURI(mAuthority, "document/*/search", MATCH_SEARCH); // Sanity check our setup if (!info.exported) { @@ -176,13 +176,12 @@ public abstract class DocumentsProvider extends ContentProvider { } /** - * Return documents that that match the given query, starting the search at - * the given directory. + * Return documents that that match the given query. * - * @param parentDocumentId the directory to start search at. + * @param rootId the root to search under. */ @SuppressWarnings("unused") - public Cursor querySearchDocuments(String parentDocumentId, String query, String[] projection) + public Cursor querySearchDocuments(String rootId, String query, String[] projection) throws FileNotFoundException { throw new UnsupportedOperationException("Search not supported"); } @@ -267,6 +266,9 @@ public abstract class DocumentsProvider extends ContentProvider { return queryRoots(projection); case MATCH_RECENT: return queryRecentDocuments(getRootId(uri), projection); + case MATCH_SEARCH: + return querySearchDocuments( + getRootId(uri), getSearchDocumentsQuery(uri), projection); case MATCH_DOCUMENT: return queryDocument(getDocumentId(uri), projection); case MATCH_CHILDREN: @@ -276,9 +278,6 @@ public abstract class DocumentsProvider extends ContentProvider { } else { return queryChildDocuments(getDocumentId(uri), projection, sortOrder); } - case MATCH_SEARCH: - return querySearchDocuments( - getDocumentId(uri), getSearchDocumentsQuery(uri), projection); default: throw new UnsupportedOperationException("Unsupported Uri " + uri); } diff --git a/packages/DocumentsUI/src/com/android/documentsui/DirectoryFragment.java b/packages/DocumentsUI/src/com/android/documentsui/DirectoryFragment.java index b2981db..aee865b 100644 --- a/packages/DocumentsUI/src/com/android/documentsui/DirectoryFragment.java +++ b/packages/DocumentsUI/src/com/android/documentsui/DirectoryFragment.java @@ -125,9 +125,8 @@ public class DirectoryFragment extends Fragment { show(fm, TYPE_NORMAL, root, doc, null); } - public static void showSearch( - FragmentManager fm, RootInfo root, DocumentInfo doc, String query) { - show(fm, TYPE_SEARCH, root, doc, query); + public static void showSearch(FragmentManager fm, RootInfo root, String query) { + show(fm, TYPE_SEARCH, root, null, query); } public static void showRecentsOpen(FragmentManager fm) { @@ -205,7 +204,7 @@ public class DirectoryFragment extends Fragment { context, mType, root, doc, contentsUri, state.userSortOrder); case TYPE_SEARCH: contentsUri = DocumentsContract.buildSearchDocumentsUri( - doc.authority, doc.documentId, query); + root.authority, root.rootId, query); if (state.action == ACTION_MANAGE) { contentsUri = DocumentsContract.setManageMode(contentsUri); } @@ -274,7 +273,7 @@ public class DirectoryFragment extends Fragment { final RootInfo root = getArguments().getParcelable(EXTRA_ROOT); final DocumentInfo doc = getArguments().getParcelable(EXTRA_DOC); - if (root != null) { + if (root != null && doc != null) { final Uri stateUri = RecentsProvider.buildState( root.authority, root.rootId, doc.documentId); final ContentValues values = new ContentValues(); diff --git a/packages/DocumentsUI/src/com/android/documentsui/DirectoryLoader.java b/packages/DocumentsUI/src/com/android/documentsui/DirectoryLoader.java index 334e262..8627ecf 100644 --- a/packages/DocumentsUI/src/com/android/documentsui/DirectoryLoader.java +++ b/packages/DocumentsUI/src/com/android/documentsui/DirectoryLoader.java @@ -32,6 +32,7 @@ import android.database.Cursor; import android.net.Uri; import android.os.CancellationSignal; import android.os.OperationCanceledException; +import android.provider.DocumentsContract; import android.provider.DocumentsContract.Document; import android.util.Log; @@ -42,6 +43,8 @@ import com.android.documentsui.model.RootInfo; import libcore.io.IoUtils; +import java.io.FileNotFoundException; + class DirectoryResult implements AutoCloseable { ContentProviderClient client; Cursor cursor; @@ -64,7 +67,7 @@ public class DirectoryLoader extends AsyncTaskLoader<DirectoryResult> { private final int mType; private final RootInfo mRoot; - private final DocumentInfo mDoc; + private DocumentInfo mDoc; private final Uri mUri; private final int mUserSortOrder; @@ -97,6 +100,19 @@ public class DirectoryLoader extends AsyncTaskLoader<DirectoryResult> { int userMode = State.MODE_UNKNOWN; + // Use default document when searching + if (mType == DirectoryFragment.TYPE_SEARCH) { + final Uri docUri = DocumentsContract.buildDocumentUri( + mRoot.authority, mRoot.documentId); + try { + mDoc = DocumentInfo.fromUri(resolver, docUri); + } catch (FileNotFoundException e) { + Log.w(TAG, "Failed to query", e); + result.exception = e; + return result; + } + } + // Pick up any custom modes requested by user Cursor cursor = null; try { @@ -157,7 +173,7 @@ public class DirectoryLoader extends AsyncTaskLoader<DirectoryResult> { result.cursor = cursor; } catch (Exception e) { - Log.d(TAG, "Failed to query", e); + Log.w(TAG, "Failed to query", e); result.exception = e; ContentProviderClient.closeQuietly(result.client); } finally { diff --git a/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java b/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java index eb51fb5..b1e51a0 100644 --- a/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java +++ b/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java @@ -45,6 +45,7 @@ import android.net.Uri; import android.os.Bundle; import android.os.Parcel; import android.provider.DocumentsContract; +import android.provider.DocumentsContract.Root; import android.support.v4.app.ActionBarDrawerToggle; import android.support.v4.view.GravityCompat; import android.support.v4.widget.DrawerLayout; @@ -442,6 +443,8 @@ public class DocumentsActivity extends Activity { super.onPrepareOptionsMenu(menu); final FragmentManager fm = getFragmentManager(); + + final RootInfo root = getCurrentRoot(); final DocumentInfo cwd = getCurrentDirectory(); final MenuItem createDir = menu.findItem(R.id.menu_create_dir); @@ -503,7 +506,9 @@ public class DocumentsActivity extends Activity { SaveFragment.get(fm).setSaveEnabled(cwd != null && cwd.isCreateSupported()); } else { createDir.setVisible(false); - searchVisible = cwd != null && cwd.isSearchSupported(); + + searchVisible = root != null + && ((root.flags & Root.FLAG_SUPPORTS_SEARCH) != 0); } // TODO: close any search in-progress when hiding @@ -722,7 +727,7 @@ public class DocumentsActivity extends Activity { } else { if (mState.currentSearch != null) { // Ongoing search - DirectoryFragment.showSearch(fm, root, cwd, mState.currentSearch); + DirectoryFragment.showSearch(fm, root, mState.currentSearch); } else { // Normal boring directory DirectoryFragment.showNormal(fm, root, cwd); diff --git a/packages/DocumentsUI/src/com/android/documentsui/RootsCache.java b/packages/DocumentsUI/src/com/android/documentsui/RootsCache.java index b48674cf..4d313e8 100644 --- a/packages/DocumentsUI/src/com/android/documentsui/RootsCache.java +++ b/packages/DocumentsUI/src/com/android/documentsui/RootsCache.java @@ -176,6 +176,7 @@ public class RootsCache { final boolean supportsCreate = (root.flags & Root.FLAG_SUPPORTS_CREATE) != 0; final boolean advanced = (root.flags & Root.FLAG_ADVANCED) != 0; final boolean localOnly = (root.flags & Root.FLAG_LOCAL_ONLY) != 0; + final boolean empty = (root.flags & Root.FLAG_EMPTY) != 0; // Exclude read-only devices when creating if (state.action == State.ACTION_CREATE && !supportsCreate) continue; @@ -183,6 +184,8 @@ public class RootsCache { if (!state.showAdvanced && advanced) continue; // Exclude non-local devices when local only if (state.localOnly && !localOnly) continue; + // Only show empty roots when creating + if (state.action != State.ACTION_CREATE && empty) continue; // Only include roots that serve requested content final boolean overlap = diff --git a/packages/DocumentsUI/src/com/android/documentsui/model/DocumentInfo.java b/packages/DocumentsUI/src/com/android/documentsui/model/DocumentInfo.java index c69103e..ab55d94 100644 --- a/packages/DocumentsUI/src/com/android/documentsui/model/DocumentInfo.java +++ b/packages/DocumentsUI/src/com/android/documentsui/model/DocumentInfo.java @@ -188,10 +188,6 @@ public class DocumentInfo implements Durable, Parcelable { return (flags & Document.FLAG_DIR_SUPPORTS_CREATE) != 0; } - public boolean isSearchSupported() { - return (flags & Document.FLAG_DIR_SUPPORTS_SEARCH) != 0; - } - public boolean isThumbnailSupported() { return (flags & Document.FLAG_SUPPORTS_THUMBNAIL) != 0; } diff --git a/packages/DocumentsUI/src/com/android/documentsui/model/RootInfo.java b/packages/DocumentsUI/src/com/android/documentsui/model/RootInfo.java index b5a198c..1afc80a 100644 --- a/packages/DocumentsUI/src/com/android/documentsui/model/RootInfo.java +++ b/packages/DocumentsUI/src/com/android/documentsui/model/RootInfo.java @@ -161,15 +161,21 @@ public class RootInfo implements Durable, Parcelable { // TODO: remove these special case icons if ("com.android.externalstorage.documents".equals(authority)) { - derivedIcon = R.drawable.ic_root_sdcard; + if ("documents".equals(rootId)) { + derivedIcon = R.drawable.ic_doc_text; + } else { + derivedIcon = R.drawable.ic_root_sdcard; + } } if ("com.android.providers.downloads.documents".equals(authority)) { derivedIcon = R.drawable.ic_root_download; } if ("com.android.providers.media.documents".equals(authority)) { - if ("image".equals(rootId)) { + if ("images_root".equals(rootId)) { derivedIcon = R.drawable.ic_doc_image; - } else if ("audio".equals(rootId)) { + } else if ("videos_root".equals(rootId)) { + derivedIcon = R.drawable.ic_doc_video; + } else if ("audio_root".equals(rootId)) { derivedIcon = R.drawable.ic_doc_audio; } } diff --git a/packages/ExternalStorageProvider/res/values/strings.xml b/packages/ExternalStorageProvider/res/values/strings.xml index 0eaf500a..f1c1ade 100644 --- a/packages/ExternalStorageProvider/res/values/strings.xml +++ b/packages/ExternalStorageProvider/res/values/strings.xml @@ -15,6 +15,11 @@ --> <resources> + <!-- Title of the external storage application [CHAR LIMIT=32] --> <string name="app_label">External Storage</string> + + <!-- Title for documents backend that offers internal storage. [CHAR LIMIT=24] --> <string name="root_internal_storage">Internal storage</string> + <!-- Title for documents backend that offers documents. [CHAR LIMIT=24] --> + <string name="root_documents">Documents</string> </resources> diff --git a/packages/ExternalStorageProvider/src/com/android/externalstorage/ExternalStorageProvider.java b/packages/ExternalStorageProvider/src/com/android/externalstorage/ExternalStorageProvider.java index ada3ad7..3e2cd15 100644 --- a/packages/ExternalStorageProvider/src/com/android/externalstorage/ExternalStorageProvider.java +++ b/packages/ExternalStorageProvider/src/com/android/externalstorage/ExternalStorageProvider.java @@ -62,7 +62,6 @@ public class ExternalStorageProvider extends DocumentsProvider { public String rootId; public int rootType; public int flags; - public int icon; public String title; public String docId; } @@ -85,9 +84,10 @@ public class ExternalStorageProvider extends DocumentsProvider { mIdToPath.put(rootId, path); final RootInfo root = new RootInfo(); - root.rootId = "primary"; + root.rootId = rootId; root.rootType = Root.ROOT_TYPE_DEVICE; - root.flags = Root.FLAG_SUPPORTS_CREATE | Root.FLAG_LOCAL_ONLY | Root.FLAG_ADVANCED; + root.flags = Root.FLAG_SUPPORTS_CREATE | Root.FLAG_LOCAL_ONLY | Root.FLAG_ADVANCED + | Root.FLAG_SUPPORTS_SEARCH; root.title = getContext().getString(R.string.root_internal_storage); root.docId = getDocIdForFile(path); mRoots.add(root); @@ -96,6 +96,25 @@ public class ExternalStorageProvider extends DocumentsProvider { throw new IllegalStateException(e); } + try { + final String rootId = "documents"; + final File path = Environment.getExternalStoragePublicDirectory( + Environment.DIRECTORY_DOCUMENTS); + mIdToPath.put(rootId, path); + + final RootInfo root = new RootInfo(); + root.rootId = rootId; + root.rootType = Root.ROOT_TYPE_SHORTCUT; + root.flags = Root.FLAG_SUPPORTS_CREATE | Root.FLAG_LOCAL_ONLY + | Root.FLAG_SUPPORTS_SEARCH; + root.title = getContext().getString(R.string.root_documents); + root.docId = getDocIdForFile(path); + mRoots.add(root); + mIdToRoot.put(rootId, root); + } catch (FileNotFoundException e) { + throw new IllegalStateException(e); + } + return true; } @@ -146,6 +165,9 @@ public class ExternalStorageProvider extends DocumentsProvider { if (target == null) { throw new FileNotFoundException("No root for " + tag); } + if (!target.exists()) { + target.mkdirs(); + } target = new File(target, path); if (!target.exists()) { throw new FileNotFoundException("Missing file for " + docId + " at " + target); @@ -163,9 +185,6 @@ public class ExternalStorageProvider extends DocumentsProvider { int flags = 0; - if (file.isDirectory()) { - flags |= Document.FLAG_DIR_SUPPORTS_SEARCH; - } if (file.isDirectory() && file.canWrite()) { flags |= Document.FLAG_DIR_SUPPORTS_CREATE; } @@ -200,7 +219,6 @@ public class ExternalStorageProvider extends DocumentsProvider { row.add(Root.COLUMN_ROOT_ID, root.rootId); row.add(Root.COLUMN_ROOT_TYPE, root.rootType); row.add(Root.COLUMN_FLAGS, root.flags); - row.add(Root.COLUMN_ICON, root.icon); row.add(Root.COLUMN_TITLE, root.title); row.add(Root.COLUMN_DOCUMENT_ID, root.docId); row.add(Root.COLUMN_AVAILABLE_BYTES, path.getFreeSpace()); @@ -260,10 +278,10 @@ public class ExternalStorageProvider extends DocumentsProvider { } @Override - public Cursor querySearchDocuments(String parentDocumentId, String query, String[] projection) + public Cursor querySearchDocuments(String rootId, String query, String[] projection) throws FileNotFoundException { final MatrixCursor result = new MatrixCursor(resolveDocumentProjection(projection)); - final File parent = getFileForDocId(parentDocumentId); + final File parent = mIdToPath.get(rootId); final LinkedList<File> pending = new LinkedList<File>(); pending.add(parent); |