Preliminary work on Material Transitions

-> Early exploration of AllApps Hero transition with
   circular reveal
-> Stripping a bunch of dead code from AppsCustomizeTabHost
-> Moved background scrim to DragLayer
-> Removed "SMALL" state from workspace: replaced with
   NORMAL_HIDDEN and OVERVIEW_HIDDEN. This is mainly to
   reduce the overall usage of the z-space model between
   allapps/widgets and workspace. There are vestigial
   remains of this model, mainly due to the overview
   mode, and a bit for spring-loaded.

Change-Id: If2302a24394f0ec66621f01ffa2fc4934aa10c3f
diff --git a/src/com/android/launcher3/AppsCustomizeTabHost.java b/src/com/android/launcher3/AppsCustomizeTabHost.java
index c6455c2..334d8b6 100644
--- a/src/com/android/launcher3/AppsCustomizeTabHost.java
+++ b/src/com/android/launcher3/AppsCustomizeTabHost.java
@@ -38,35 +38,20 @@
 
 import java.util.ArrayList;
 
-public class AppsCustomizeTabHost extends TabHost implements LauncherTransitionable,
-        TabHost.OnTabChangeListener, Insettable  {
+public class AppsCustomizeTabHost extends FrameLayout implements LauncherTransitionable, Insettable  {
     static final String LOG_TAG = "AppsCustomizeTabHost";
 
     private static final String APPS_TAB_TAG = "APPS";
     private static final String WIDGETS_TAB_TAG = "WIDGETS";
 
-    private final LayoutInflater mLayoutInflater;
-    private ViewGroup mTabs;
-    private ViewGroup mTabsContainer;
-    private AppsCustomizePagedView mAppsCustomizePane;
-    private FrameLayout mAnimationBuffer;
-    private LinearLayout mContent;
+    private AppsCustomizePagedView mPagedView;
+    private View mContent;
+    private boolean mInTransition = false;
 
-    private boolean mInTransition;
-    private boolean mTransitioningToWorkspace;
-    private boolean mResetAfterTransition;
-    private Runnable mRelayoutAndMakeVisible;
     private final Rect mInsets = new Rect();
 
     public AppsCustomizeTabHost(Context context, AttributeSet attrs) {
         super(context, attrs);
-        mLayoutInflater = LayoutInflater.from(context);
-        mRelayoutAndMakeVisible = new Runnable() {
-                public void run() {
-                    mTabs.requestLayout();
-                    mTabsContainer.setAlpha(1f);
-                }
-            };
     }
 
     /**
@@ -76,17 +61,17 @@
      * tabs manually).
      */
     void setContentTypeImmediate(AppsCustomizePagedView.ContentType type) {
-        setOnTabChangedListener(null);
-        onTabChangedStart();
-        onTabChangedEnd(type);
-        setCurrentTabByTag(getTabTagForContentType(type));
-        setOnTabChangedListener(this);
+        mPagedView.setContentType(type);
+    }
+
+    public void setCurrentTabFromContent(AppsCustomizePagedView.ContentType type) {
+        setContentTypeImmediate(type);
     }
 
     @Override
     public void setInsets(Rect insets) {
         mInsets.set(insets);
-        FrameLayout.LayoutParams flp = (LayoutParams) mContent.getLayoutParams();
+        LayoutParams flp = (LayoutParams) mContent.getLayoutParams();
         flp.topMargin = insets.top;
         flp.bottomMargin = insets.bottom;
         flp.leftMargin = insets.left;
@@ -99,212 +84,12 @@
      */
     @Override
     protected void onFinishInflate() {
-        // Setup the tab host
-        setup();
-
-        final ViewGroup tabsContainer = (ViewGroup) findViewById(R.id.tabs_container);
-        final TabWidget tabs = getTabWidget();
-        final AppsCustomizePagedView appsCustomizePane = (AppsCustomizePagedView)
-                findViewById(R.id.apps_customize_pane_content);
-        mTabs = tabs;
-        mTabsContainer = tabsContainer;
-        mAppsCustomizePane = appsCustomizePane;
-        mAnimationBuffer = (FrameLayout) findViewById(R.id.animation_buffer);
-        mContent = (LinearLayout) findViewById(R.id.apps_customize_content);
-        if (tabs == null || mAppsCustomizePane == null) throw new Resources.NotFoundException();
-
-        // Configure the tabs content factory to return the same paged view (that we change the
-        // content filter on)
-        TabContentFactory contentFactory = new TabContentFactory() {
-            public View createTabContent(String tag) {
-                return appsCustomizePane;
-            }
-        };
-
-        // Create the tabs
-        TextView tabView;
-        String label;
-        label = getContext().getString(R.string.all_apps_button_label);
-        tabView = (TextView) mLayoutInflater.inflate(R.layout.tab_widget_indicator, tabs, false);
-        tabView.setText(label);
-        tabView.setContentDescription(label);
-        addTab(newTabSpec(APPS_TAB_TAG).setIndicator(tabView).setContent(contentFactory));
-        label = getContext().getString(R.string.widgets_tab_label);
-        tabView = (TextView) mLayoutInflater.inflate(R.layout.tab_widget_indicator, tabs, false);
-        tabView.setText(label);
-        tabView.setContentDescription(label);
-        addTab(newTabSpec(WIDGETS_TAB_TAG).setIndicator(tabView).setContent(contentFactory));
-        setOnTabChangedListener(this);
-
-        // Setup the key listener to jump between the last tab view and the market icon
-        AppsCustomizeTabKeyEventListener keyListener = new AppsCustomizeTabKeyEventListener();
-        View lastTab = tabs.getChildTabViewAt(tabs.getTabCount() - 1);
-        lastTab.setOnKeyListener(keyListener);
-        View shopButton = findViewById(R.id.market_button);
-        shopButton.setOnKeyListener(keyListener);
-
-        // Hide the tab bar until we measure
-        mTabsContainer.setAlpha(0f);
+        mPagedView = (AppsCustomizePagedView) findViewById(R.id.apps_customize_pane_content);
+        mContent = findViewById(R.id.content);
     }
 
-    @Override
-    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
-        boolean remeasureTabWidth = (mTabs.getLayoutParams().width <= 0);
-        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
-
-        // Set the width of the tab list to the content width
-        if (remeasureTabWidth) {
-            int contentWidth = mAppsCustomizePane.getPageContentWidth();
-            if (contentWidth > 0 && mTabs.getLayoutParams().width != contentWidth) {
-                // Set the width and show the tab bar
-                mTabs.getLayoutParams().width = contentWidth;
-                mRelayoutAndMakeVisible.run();
-            }
-
-            super.onMeasure(widthMeasureSpec, heightMeasureSpec);
-        }
-    }
-
-     public boolean onInterceptTouchEvent(MotionEvent ev) {
-         // If we are mid transitioning to the workspace, then intercept touch events here so we
-         // can ignore them, otherwise we just let all apps handle the touch events.
-         if (mInTransition && mTransitioningToWorkspace) {
-             return true;
-         }
-         return super.onInterceptTouchEvent(ev);
-     };
-
-    @Override
-    public boolean onTouchEvent(MotionEvent event) {
-        // Allow touch events to fall through to the workspace if we are transitioning there
-        if (mInTransition && mTransitioningToWorkspace) {
-            return super.onTouchEvent(event);
-        }
-
-        // Intercept all touch events up to the bottom of the AppsCustomizePane so they do not fall
-        // through to the workspace and trigger showWorkspace()
-        if (event.getY() < mAppsCustomizePane.getBottom()) {
-            return true;
-        }
-        return super.onTouchEvent(event);
-    }
-
-    private void onTabChangedStart() {
-    }
-
-    private void reloadCurrentPage() {
-        mAppsCustomizePane.loadAssociatedPages(mAppsCustomizePane.getCurrentPage());
-        mAppsCustomizePane.requestFocus();
-    }
-
-    private void onTabChangedEnd(AppsCustomizePagedView.ContentType type) {
-        int bgAlpha = (int) (255 * (getResources().getInteger(
-            R.integer.config_appsCustomizeSpringLoadedBgAlpha) / 100f));
-        setBackgroundColor(Color.argb(bgAlpha, 0, 0, 0));
-        mAppsCustomizePane.setContentType(type);
-    }
-
-    @Override
-    public void onTabChanged(String tabId) {
-        final AppsCustomizePagedView.ContentType type = getContentTypeForTabTag(tabId);
-
-        // Animate the changing of the tab content by fading pages in and out
-        final Resources res = getResources();
-        final int duration = res.getInteger(R.integer.config_tabTransitionDuration);
-
-        // We post a runnable here because there is a delay while the first page is loading and
-        // the feedback from having changed the tab almost feels better than having it stick
-        post(new Runnable() {
-            @Override
-            public void run() {
-                if (mAppsCustomizePane.getMeasuredWidth() <= 0 ||
-                        mAppsCustomizePane.getMeasuredHeight() <= 0) {
-                    reloadCurrentPage();
-                    return;
-                }
-
-                // Take the visible pages and re-parent them temporarily to mAnimatorBuffer
-                // and then cross fade to the new pages
-                int[] visiblePageRange = new int[2];
-                mAppsCustomizePane.getVisiblePages(visiblePageRange);
-                if (visiblePageRange[0] == -1 && visiblePageRange[1] == -1) {
-                    // If we can't get the visible page ranges, then just skip the animation
-                    reloadCurrentPage();
-                    return;
-                }
-                ArrayList<View> visiblePages = new ArrayList<View>();
-                for (int i = visiblePageRange[0]; i <= visiblePageRange[1]; i++) {
-                    visiblePages.add(mAppsCustomizePane.getPageAt(i));
-                }
-
-                // We want the pages to be rendered in exactly the same way as they were when
-                // their parent was mAppsCustomizePane -- so set the scroll on mAnimationBuffer
-                // to be exactly the same as mAppsCustomizePane, and below, set the left/top
-                // parameters to be correct for each of the pages
-                mAnimationBuffer.scrollTo(mAppsCustomizePane.getScrollX(), 0);
-
-                // mAppsCustomizePane renders its children in reverse order, so
-                // add the pages to mAnimationBuffer in reverse order to match that behavior
-                for (int i = visiblePages.size() - 1; i >= 0; i--) {
-                    View child = visiblePages.get(i);
-                    if (child instanceof AppsCustomizeCellLayout) {
-                        ((AppsCustomizeCellLayout) child).resetChildrenOnKeyListeners();
-                    } else if (child instanceof PagedViewGridLayout) {
-                        ((PagedViewGridLayout) child).resetChildrenOnKeyListeners();
-                    }
-                    PagedViewWidget.setDeletePreviewsWhenDetachedFromWindow(false);
-                    mAppsCustomizePane.removeView(child);
-                    PagedViewWidget.setDeletePreviewsWhenDetachedFromWindow(true);
-                    mAnimationBuffer.setAlpha(1f);
-                    mAnimationBuffer.setVisibility(View.VISIBLE);
-                    LayoutParams p = new FrameLayout.LayoutParams(child.getMeasuredWidth(),
-                            child.getMeasuredHeight());
-                    p.setMargins((int) child.getLeft(), (int) child.getTop(), 0, 0);
-                    mAnimationBuffer.addView(child, p);
-                }
-
-                // Toggle the new content
-                onTabChangedStart();
-                onTabChangedEnd(type);
-
-                // Animate the transition
-                ObjectAnimator outAnim = LauncherAnimUtils.ofFloat(mAnimationBuffer, "alpha", 0f);
-                outAnim.addListener(new AnimatorListenerAdapter() {
-                    private void clearAnimationBuffer() {
-                        mAnimationBuffer.setVisibility(View.GONE);
-                        PagedViewWidget.setRecyclePreviewsWhenDetachedFromWindow(false);
-                        mAnimationBuffer.removeAllViews();
-                        PagedViewWidget.setRecyclePreviewsWhenDetachedFromWindow(true);
-                    }
-                    @Override
-                    public void onAnimationEnd(Animator animation) {
-                        clearAnimationBuffer();
-                    }
-                    @Override
-                    public void onAnimationCancel(Animator animation) {
-                        clearAnimationBuffer();
-                    }
-                });
-                ObjectAnimator inAnim = LauncherAnimUtils.ofFloat(mAppsCustomizePane, "alpha", 1f);
-                inAnim.addListener(new AnimatorListenerAdapter() {
-                    @Override
-                    public void onAnimationEnd(Animator animation) {
-                        reloadCurrentPage();
-                    }
-                });
-
-                final AnimatorSet animSet = LauncherAnimUtils.createAnimatorSet();
-                animSet.playTogether(outAnim, inAnim);
-                animSet.setDuration(duration);
-                animSet.start();
-            }
-        });
-    }
-
-    public void setCurrentTabFromContent(AppsCustomizePagedView.ContentType type) {
-        setOnTabChangedListener(null);
-        setCurrentTabByTag(getTabTagForContentType(type));
-        setOnTabChangedListener(this);
+    public String getContentTag() {
+        return getTabTagForContentType(mPagedView.getContentType());
     }
 
     /**
@@ -343,44 +128,41 @@
     }
 
     void reset() {
-        if (mInTransition) {
-            // Defer to after the transition to reset
-            mResetAfterTransition = true;
-        } else {
-            // Reset immediately
-            mAppsCustomizePane.reset();
+        // Reset immediately
+        mPagedView.reset();
+    }
+
+    public void onWindowVisible() {
+        if (getVisibility() == VISIBLE) {
+            mContent.setVisibility(VISIBLE);
+            // We unload the widget previews when the UI is hidden, so need to reload pages
+            // Load the current page synchronously, and the neighboring pages asynchronously
+            mPagedView.loadAssociatedPages(mPagedView.getCurrentPage(), true);
+            mPagedView.loadAssociatedPages(mPagedView.getCurrentPage());
         }
     }
 
-    private void enableAndBuildHardwareLayer() {
-        // isHardwareAccelerated() checks if we're attached to a window and if that
-        // window is HW accelerated-- we were sometimes not attached to a window
-        // and buildLayer was throwing an IllegalStateException
-        if (isHardwareAccelerated()) {
-            // Turn on hardware layers for performance
-            setLayerType(LAYER_TYPE_HARDWARE, null);
-
-            // force building the layer, so you don't get a blip early in an animation
-            // when the layer is created layer
-            buildLayer();
-        }
+    public void onTrimMemory() {
+        mContent.setVisibility(GONE);
+        // Clear the widget pages of all their subviews - this will trigger the widget previews
+        // to delete their bitmaps
+        mPagedView.clearAllWidgetPages();
     }
 
     @Override
     public View getContent() {
-        View appsCustomizeContent = mAppsCustomizePane.getContent();
-        if (appsCustomizeContent != null) {
-            return appsCustomizeContent;
-        }
-        return mContent;
+        return mPagedView;
+    }
+
+    public boolean isInTransition() {
+        return mInTransition;
     }
 
     /* LauncherTransitionable overrides */
     @Override
     public void onLauncherTransitionPrepare(Launcher l, boolean animated, boolean toWorkspace) {
-        mAppsCustomizePane.onLauncherTransitionPrepare(l, animated, toWorkspace);
+        mPagedView.onLauncherTransitionPrepare(l, animated, toWorkspace);
         mInTransition = true;
-        mTransitioningToWorkspace = toWorkspace;
 
         if (toWorkspace) {
             // Going from All Apps -> Workspace
@@ -391,52 +173,43 @@
 
             // Make sure the current page is loaded (we start loading the side pages after the
             // transition to prevent slowing down the animation)
-            mAppsCustomizePane.loadAssociatedPages(mAppsCustomizePane.getCurrentPage(), true);
-        }
-
-        if (mResetAfterTransition) {
-            mAppsCustomizePane.reset();
-            mResetAfterTransition = false;
+            // TODO: revisit this
+            mPagedView.loadAssociatedPages(mPagedView.getCurrentPage(), true);
         }
     }
 
     @Override
     public void onLauncherTransitionStart(Launcher l, boolean animated, boolean toWorkspace) {
-        mAppsCustomizePane.onLauncherTransitionStart(l, animated, toWorkspace);
-        if (animated) {
+        mPagedView.onLauncherTransitionStart(l, animated, toWorkspace);
+        if (animated && !Utilities.isLmp()) {
             enableAndBuildHardwareLayer();
         }
-
-        // Dismiss the workspace cling
-        l.getLauncherClings().dismissWorkspaceCling(null);
     }
 
     @Override
     public void onLauncherTransitionStep(Launcher l, float t) {
-        mAppsCustomizePane.onLauncherTransitionStep(l, t);
+        mPagedView.onLauncherTransitionStep(l, t);
     }
 
     @Override
     public void onLauncherTransitionEnd(Launcher l, boolean animated, boolean toWorkspace) {
-        mAppsCustomizePane.onLauncherTransitionEnd(l, animated, toWorkspace);
+        mPagedView.onLauncherTransitionEnd(l, animated, toWorkspace);
         mInTransition = false;
-        if (animated) {
+        if (animated && !Utilities.isLmp()) {
             setLayerType(LAYER_TYPE_NONE, null);
         }
 
         if (!toWorkspace) {
-            // Show the all apps cling (if not already shown)
-            mAppsCustomizePane.showAllAppsCling();
             // Make sure adjacent pages are loaded (we wait until after the transition to
             // prevent slowing down the animation)
-            mAppsCustomizePane.loadAssociatedPages(mAppsCustomizePane.getCurrentPage());
+            mPagedView.loadAssociatedPages(mPagedView.getCurrentPage());
 
             // Opening apps, need to announce what page we are on.
             AccessibilityManager am = (AccessibilityManager)
                     getContext().getSystemService(Context.ACCESSIBILITY_SERVICE);
             if (am.isEnabled()) {
                 // Notify the user when the page changes
-                announceForAccessibility(mAppsCustomizePane.getCurrentPageDescription());
+                announceForAccessibility(mPagedView.getCurrentPageDescription());
             }
 
             // Going from Workspace -> All Apps
@@ -469,24 +242,19 @@
         }
     }
 
-    public void onWindowVisible() {
-        if (getVisibility() == VISIBLE) {
-            mContent.setVisibility(VISIBLE);
-            // We unload the widget previews when the UI is hidden, so need to reload pages
-            // Load the current page synchronously, and the neighboring pages asynchronously
-            mAppsCustomizePane.loadAssociatedPages(mAppsCustomizePane.getCurrentPage(), true);
-            mAppsCustomizePane.loadAssociatedPages(mAppsCustomizePane.getCurrentPage());
+    private void enableAndBuildHardwareLayer() {
+        // isHardwareAccelerated() checks if we're attached to a window and if that
+        // window is HW accelerated-- we were sometimes not attached to a window
+        // and buildLayer was throwing an IllegalStateException
+        if (isHardwareAccelerated()) {
+            // Turn on hardware layers for performance
+            setLayerType(LAYER_TYPE_HARDWARE, null);
+
+            // force building the layer, so you don't get a blip early in an animation
+            // when the layer is created layer
+            buildLayer();
         }
     }
 
-    public void onTrimMemory() {
-        mContent.setVisibility(GONE);
-        // Clear the widget pages of all their subviews - this will trigger the widget previews
-        // to delete their bitmaps
-        mAppsCustomizePane.clearAllWidgetPages();
-    }
 
-    boolean isTransitioning() {
-        return mInTransition;
-    }
 }