Merge "Update hierarchical folders; implement this "the right way"" into jb-ub-mail
diff --git a/res/layout/child_folder_item.xml b/res/layout/child_folder_item.xml
new file mode 100644
index 0000000..70793e4
--- /dev/null
+++ b/res/layout/child_folder_item.xml
@@ -0,0 +1,80 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+     Copyright (C) 2012 Google Inc.
+     Licensed to The Android Open Source Project.
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<com.android.mail.ui.FolderItemView
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_height="wrap_content"
+    android:layout_width="match_parent"
+    android:minHeight="@dimen/folder_list_minimum_height"
+    android:background="@drawable/folder_item"
+    android:paddingLeft="48dp">
+
+    <ImageView
+        android:id="@+id/folder_parent_icon"
+        android:layout_width="16dip"
+        android:layout_height="16dip"
+        android:layout_alignParentBottom="true"
+        android:layout_alignParentRight="true"
+        android:visibility="gone"
+        android:src="@drawable/folder_parent_icon" />
+
+    <ImageView
+        android:id="@+id/folder_box"
+        style="@style/FolderItemIcon"
+        android:layout_alignParentLeft="true"
+        android:layout_alignParentTop="true" />
+
+    <TextView
+        android:id="@+id/unread"
+        style="@style/UnreadCount"
+        android:layout_marginRight="@dimen/folder_list_item_right_margin"
+        android:layout_alignWithParentIfMissing="true"
+        android:layout_alignParentRight="true"
+        android:layout_toLeftOf="@id/folder_parent_icon"
+        android:textColor="@color/folder_name_color_primary_invertible" />
+
+    <RelativeLayout
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:layout_centerVertical="true"
+        android:layout_toLeftOf="@id/unread"
+        android:layout_marginLeft="@dimen/folder_list_item_left_margin"
+        android:layout_marginTop="@dimen/folder_swatch_height"
+        android:layout_marginBottom="@dimen/folder_swatch_height">
+
+        <TextView
+            android:id="@+id/name"
+            android:layout_height="wrap_content"
+            android:layout_width="match_parent"
+            android:maxLines="2"
+            android:ellipsize="end"
+            android:textColor="@color/folder_name_color_primary_invertible"
+            android:textAppearance="?android:attr/textAppearanceMedium" />
+
+        <TextView
+            android:id="@+id/description"
+            android:layout_height="wrap_content"
+            android:layout_width="match_parent"
+            android:layout_below="@id/name"
+            android:textColor="@color/folder_name_color_primary_invertible"
+            android:textAppearance="?android:attr/textAppearanceSmall"
+            android:visibility="gone" />
+
+    </RelativeLayout>
+
+</com.android.mail.ui.FolderItemView>
\ No newline at end of file
diff --git a/res/layout/folder_list_with_parent.xml b/res/layout/folder_list_with_parent.xml
deleted file mode 100644
index 8f548f4..0000000
--- a/res/layout/folder_list_with_parent.xml
+++ /dev/null
@@ -1,64 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!--
-     Copyright (C) 2012 Google Inc.
-     Licensed to The Android Open Source Project.
-
-     Licensed under the Apache License, Version 2.0 (the "License");
-     you may not use this file except in compliance with the License.
-     You may obtain a copy of the License at
-
-          http://www.apache.org/licenses/LICENSE-2.0
-
-     Unless required by applicable law or agreed to in writing, software
-     distributed under the License is distributed on an "AS IS" BASIS,
-     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-     See the License for the specific language governing permissions and
-     limitations under the License.
--->
-
-<RelativeLayout  xmlns:android="http://schemas.android.com/apk/res/android"
-    android:layout_width="match_parent"
-    android:layout_height="match_parent">
-
-    <RelativeLayout
-        android:layout_width="match_parent"
-        android:layout_height="?android:attr/listPreferredItemHeight"
-        android:layout_alignParentTop="true"
-        android:layout_marginLeft="@dimen/folder_list_item_left_margin"
-        android:id="@+id/parent_folder"
-        android:background="?android:attr/selectableItemBackground"
-        android:addStatesFromChildren="true"
-        android:gravity="center_vertical"
-        android:layout_gravity="center_vertical" >
-
-        <TextView
-            android:id="@+id/parent_folder_name"
-            android:layout_height="wrap_content"
-            android:layout_width="match_parent"
-            android:maxLines="2"
-            android:ellipsize="end"
-            android:textColor="@color/folder_name_color_primary_invertible"
-            android:textAppearance="?android:attr/textAppearanceMedium"/>
-
-    </RelativeLayout>
-
-    <FrameLayout
-        android:layout_width="match_parent"
-        android:layout_height="wrap_content"
-        android:layout_below="@id/parent_folder">
-        <ListView
-            android:id="@android:id/list"
-            android:layout_width="match_parent"
-            android:layout_height="match_parent"
-            android:cacheColorHint="@android:color/transparent"
-            android:drawSelectorOnTop="false"
-            android:fadingEdge="none"
-            android:paddingLeft="32dip" />
-
-        <TextView android:id="@+id/empty_view"
-            android:visibility="gone"
-            android:layout_width="match_parent"
-            android:layout_height="wrap_content"
-            android:text="@string/folders_activity_instructions"/>
-    </FrameLayout>
-</RelativeLayout>
diff --git a/src/com/android/mail/ui/AbstractActivityController.java b/src/com/android/mail/ui/AbstractActivityController.java
index 32a27a3..626ffea 100644
--- a/src/com/android/mail/ui/AbstractActivityController.java
+++ b/src/com/android/mail/ui/AbstractActivityController.java
@@ -456,6 +456,11 @@
         }
     }
 
+    @Override
+    public void onFolderSelected(Folder folder, boolean childView) {
+        onFolderChanged(folder);
+    }
+
     /**
      * Update the recent folders. This only needs to be done once when accessing a new folder.
      */
diff --git a/src/com/android/mail/ui/FolderItemView.java b/src/com/android/mail/ui/FolderItemView.java
index 09fc51c..5432a31 100644
--- a/src/com/android/mail/ui/FolderItemView.java
+++ b/src/com/android/mail/ui/FolderItemView.java
@@ -111,11 +111,11 @@
         mFolderParentIcon = (ImageView) findViewById(R.id.folder_parent_icon);
     }
 
-    public void bind(Folder folder, DropHandler dropHandler) {
+    public void bind(Folder folder, DropHandler dropHandler, boolean showParentIcon) {
         mFolder = folder;
         mDropHandler = dropHandler;
         mFolderTextView.setText(folder.name);
-        if (mFolder.hasChildren) {
+        if (mFolder.hasChildren && showParentIcon) {
             mFolderParentIcon.setVisibility(View.VISIBLE);
         }
         final int count = getFolderItemCount();
diff --git a/src/com/android/mail/ui/FolderListFragment.java b/src/com/android/mail/ui/FolderListFragment.java
index 912f7d7..a3ceb43 100644
--- a/src/com/android/mail/ui/FolderListFragment.java
+++ b/src/com/android/mail/ui/FolderListFragment.java
@@ -30,6 +30,7 @@
 import android.view.View;
 import android.view.View.OnClickListener;
 import android.view.ViewGroup;
+import android.widget.ArrayAdapter;
 import android.widget.ListView;
 import android.widget.SimpleCursorAdapter;
 import android.widget.TextView;
@@ -43,7 +44,7 @@
  * The folder list UI component.
  */
 public final class FolderListFragment extends ListFragment implements
-        LoaderManager.LoaderCallbacks<Cursor>, ViewMode.ModeChangeListener, OnClickListener {
+        LoaderManager.LoaderCallbacks<Cursor>, ViewMode.ModeChangeListener {
     private static final String LOG_TAG = new LogUtils().getLogTag();
 
     private ControllableActivity mActivity;
@@ -114,7 +115,7 @@
             // Activity is finishing, just bail.
             return;
         }
-        selectFolder(mActivity.getCurrentFolder());
+        selectInitialFolder(mActivity.getCurrentFolder());
         getLoaderManager().initLoader(FOLDER_LOADER_ID, Bundle.EMPTY, this);
     }
 
@@ -129,8 +130,7 @@
         final Bundle args = getArguments();
         mFolderListUri = Uri.parse(args.getString(ARG_FOLDER_URI));
         mParentFolder = (Folder) args.getParcelable(ARG_PARENT_FOLDER);
-        View rootView = inflater.inflate(mParentFolder != null ?
-                R.layout.folder_list_with_parent : R.layout.folder_list, null);
+        View rootView = inflater.inflate(R.layout.folder_list, null);
         mListView = (ListView) rootView.findViewById(android.R.id.list);
         mListView.setHeaderDividersEnabled(false);
         mListView.setChoiceMode(ListView.CHOICE_MODE_SINGLE);
@@ -139,9 +139,7 @@
         mListView.setSaveEnabled(false);
 
         if (mParentFolder != null) {
-            TextView parentFolderView = (TextView) rootView.findViewById(R.id.parent_folder_name);
-            parentFolderView.setText(mParentFolder.name);
-            parentFolderView.setOnClickListener(this);
+            mSelectedFolder = mParentFolder;
         }
         return rootView;
     }
@@ -159,10 +157,15 @@
     }
 
     public void viewFolder(int position) {
-        mFolderListCursor.moveToPosition(position);
-        mSelectedFolder = new Folder(mFolderListCursor);
+        Object item = getListAdapter().getItem(position);
+        Folder folder;
+        if (item instanceof Folder) {
+            folder = (Folder) item;
+        } else {
+            folder = new Folder((Cursor) item);
+        }
         // Go to the conversation list for this folder.
-        mListener.onFolderSelected(mSelectedFolder, mParentFolder != null);
+        mListener.onFolderSelected(folder, mParentFolder != null);
     }
 
     @Override
@@ -179,8 +182,13 @@
     @Override
     public void onLoadFinished(Loader<Cursor> loader, Cursor data) {
         mFolderListCursor = data;
-        setListAdapter(new FolderListAdapter(mActivity.getActivityContext(),
+        if (mParentFolder != null) {
+            setListAdapter(new HierarchicalFolderListAdapter(mActivity.getActivityContext(),
+                    mFolderListCursor, mParentFolder));
+        } else {
+            setListAdapter(new FolderListAdapter(mActivity.getActivityContext(),
                 R.layout.folder_item, mFolderListCursor, null, null));
+        }
     }
 
     @Override
@@ -205,7 +213,57 @@
             }
             getCursor().moveToPosition(position);
             Folder folder = new Folder(getCursor());
-            folderItemView.bind(folder, mDropHandler);
+            folderItemView.bind(folder, mDropHandler, true);
+            if (mSelectedFolder != null && folder.uri.equals(mSelectedFolder.uri)) {
+                getListView().setItemChecked(position, true);
+            }
+            Folder.setFolderBlockColor(folder, folderItemView.findViewById(R.id.folder_box));
+            return folderItemView;
+        }
+    }
+
+    private class HierarchicalFolderListAdapter extends ArrayAdapter<Folder> {
+
+        private static final int PARENT = 0;
+        private static final int CHILD = 1;
+        private final Uri mParentUri;
+
+        public HierarchicalFolderListAdapter(Context context, Cursor c, Folder parentFolder) {
+            super(context, R.layout.folder_item);
+            mParentUri = parentFolder.uri;
+            add(parentFolder);
+            if (c != null && c.getCount() > 0) {
+                c.moveToFirst();
+                do {
+                    add(new Folder(c));
+                } while (c.moveToNext());
+            }
+        }
+
+        @Override
+        public int getViewTypeCount() {
+            // Child and Parent
+            return 2;
+        }
+
+        public int getItemViewType(int position) {
+            Folder f = this.getItem(position);
+            return f.uri.equals(mParentUri) ? PARENT : CHILD;
+        }
+
+        @Override
+        public View getView(int position, View convertView, ViewGroup parent) {
+            FolderItemView folderItemView;
+            Folder folder = getItem(position);
+            boolean isParent = folder.uri.equals(mParentUri);
+            if (convertView != null) {
+                folderItemView = (FolderItemView) convertView;
+            } else {
+                int resId = isParent ? R.layout.folder_item : R.layout.child_folder_item;
+                folderItemView = (FolderItemView) LayoutInflater.from(
+                        mActivity.getActivityContext()).inflate(resId, null);
+            }
+            folderItemView.bind(folder, mDropHandler, false);
             if (mSelectedFolder != null && folder.uri.equals(mSelectedFolder.uri)) {
                 getListView().setItemChecked(position, true);
             }
@@ -219,18 +277,10 @@
         // Listen on mode changes, when we move to Folder list mode, change accordingly.
     }
 
-    public void selectFolder(Folder folder) {
+    public void selectInitialFolder(Folder folder) {
         mSelectedFolder = folder;
     }
 
-    @Override
-    public void onClick(View v) {
-        if (v.getId() == R.id.parent_folder_name && mParentFolder != null) {
-            mSelectedFolder = mParentFolder;
-            mListener.onFolderSelected(mSelectedFolder, mParentFolder != null);
-        }
-    }
-
     public interface FolderListSelectionListener {
         public void onFolderSelected(Folder folder, boolean viewingChildren);
     }
diff --git a/src/com/android/mail/ui/OnePaneController.java b/src/com/android/mail/ui/OnePaneController.java
index 7c580bb..bb22c3a 100644
--- a/src/com/android/mail/ui/OnePaneController.java
+++ b/src/com/android/mail/ui/OnePaneController.java
@@ -332,6 +332,7 @@
 
     @Override
     public void onFolderSelected(Folder folder, boolean childView) {
+        super.onFolderSelected(folder, childView);
         if (!childView && folder.hasChildren) {
             // Replace this fragment with a new FolderListFragment
             // showing this folder's children if we are not already looking
@@ -348,7 +349,6 @@
             // folder setting so that the folder will be re-loaded/ shown.
             mFolder = null;
         }
-        super.onFolderChanged(folder);
     }
 
     private boolean isTransactionIdValid(int id) {
diff --git a/src/com/android/mail/ui/TwoPaneController.java b/src/com/android/mail/ui/TwoPaneController.java
index f2672a3..5c10842 100644
--- a/src/com/android/mail/ui/TwoPaneController.java
+++ b/src/com/android/mail/ui/TwoPaneController.java
@@ -101,9 +101,6 @@
         // Since we are showing the folder list, we are at the start of the view
         // stack.
         resetActionBarIcon();
-        if (getCurrentListContext() != null) {
-            folderListFragment.selectFolder(getCurrentListContext().folder);
-        }
     }
 
     @Override
@@ -161,12 +158,13 @@
         super.onFolderChanged(folder);
         final FolderListFragment folderList = getFolderListFragment();
         if (folderList != null) {
-            folderList.selectFolder(folder);
+            folderList.selectInitialFolder(folder);
         }
     }
 
     @Override
     public void onFolderSelected(Folder folder, boolean childView) {
+        super.onFolderSelected(folder, childView);
         if (!childView && folder.hasChildren) {
             // Replace this fragment with a new FolderListFragment
             // showing this folder's children if we are not already looking
@@ -178,9 +176,8 @@
         }
         final FolderListFragment folderList = getFolderListFragment();
         if (folderList != null) {
-            folderList.selectFolder(folder);
+            folderList.selectInitialFolder(folder);
         }
-        super.onFolderChanged(folder);
     }
 
     @Override