SearchPanelView.java revision 9a720f5eb6c67b581df22f4ecb498cebb459babe
19066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/*
29066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Copyright (C) 2012 The Android Open Source Project
39066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
49066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
59066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * you may not use this file except in compliance with the License.
69066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * You may obtain a copy of the License at
79066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
89066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
99066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Unless required by applicable law or agreed to in writing, software
119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * See the License for the specific language governing permissions and
149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * limitations under the License.
159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */
169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1768f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrookpackage com.android.systemui;
189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
198bcbebd4178b2e9aca9ee3bd9e1e12c42e74c8dbAdam Powellimport android.animation.LayoutTransition;
208bcbebd4178b2e9aca9ee3bd9e1e12c42e74c8dbAdam Powellimport android.app.ActivityOptions;
21206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.app.SearchManager;
22206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.content.ActivityNotFoundException;
23206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.content.ComponentName;
24206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.content.Context;
25206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.content.Intent;
2668f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrookimport android.content.pm.PackageManager;
279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.util.AttributeSet;
28206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.util.Slog;
29206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.view.MotionEvent;
30206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.view.View;
31206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.view.ViewGroup;
32206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport android.view.ViewTreeObserver;
3350f34d14f6dd3411fdbdb6a7b8b285c2b8fdbf5cSvetoslav Ganovimport android.view.ViewTreeObserver.OnPreDrawListener;
34e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganovimport android.widget.FrameLayout;
359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport com.android.internal.widget.multiwaveview.MultiWaveView;
379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport com.android.internal.widget.multiwaveview.MultiWaveView.OnTriggerListener;
38206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport com.android.systemui.R;
399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport com.android.systemui.recent.StatusBarTouchProxy;
409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport com.android.systemui.statusbar.BaseStatusBar;
41206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport com.android.systemui.statusbar.CommandQueue;
42206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport com.android.systemui.statusbar.phone.PhoneStatusBar;
439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport com.android.systemui.statusbar.tablet.StatusBarPanel;
44206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganovimport com.android.systemui.statusbar.tablet.TabletStatusBar;
45206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectpublic class SearchPanelView extends FrameLayout implements
47206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        StatusBarPanel {
48e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov    private static final int SEARCH_PANEL_HOLD_DURATION = 500;
49206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    static final String TAG = "SearchPanelView";
50206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    static final boolean DEBUG = TabletStatusBar.DEBUG || PhoneStatusBar.DEBUG || false;
519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private final Context mContext;
5268f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook    private BaseStatusBar mBar;
534bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov    private StatusBarTouchProxy mStatusBarTouchProxy;
544bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov
554bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov    private boolean mShowing;
564bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov    private View mSearchTargetsContainer;
574bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov    private MultiWaveView mMultiWaveView;
584bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov
594bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov    public SearchPanelView(Context context, AttributeSet attrs) {
604bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov        this(context, attrs, 0);
614bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov    }
624bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov
634bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov    public SearchPanelView(Context context, AttributeSet attrs, int defStyle) {
644bfd794475e6fb34c9dfa83d4302e9db365a3709Svetoslav Ganov        super(context, attrs, defStyle);
6568f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        mContext = context;
6668f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        mSearchManager = (SearchManager) mContext.getSystemService(Context.SEARCH_SERVICE);
6768f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        if (mSearchManager == null) {
68fdf6db6748b32f620a7f68b13a67c38b4e59e5edTom Taylor            Slog.w(TAG, "Search manager not available");
6968f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        }
70e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov    }
71e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov
72e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov    private SearchManager mSearchManager;
73e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov
74e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov    // This code should be the same as that used in LockScreen.java
75206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    public boolean isAssistantAvailable() {
7668f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        Intent intent = getAssistIntent();
77206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        return intent == null ? false
789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                : mContext.getPackageManager().queryIntentActivities(intent,
7968f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook                        PackageManager.MATCH_DEFAULT_ONLY).size() > 0;
80206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
8168f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook
82206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    private Intent getAssistIntent() {
839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        Intent intent = null;
84206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        SearchManager searchManager = getSearchManager();
85206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        if (searchManager != null) {
86206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            ComponentName globalSearchActivity = searchManager.getGlobalSearchActivity();
87206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            if (globalSearchActivity != null) {
88fdf6db6748b32f620a7f68b13a67c38b4e59e5edTom Taylor                intent = new Intent(Intent.ACTION_ASSIST);
89206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                intent.setPackage(globalSearchActivity.getPackageName());
90206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            } else {
91206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                Slog.w(TAG, "No global search activity");
92206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            }
93206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        } else {
94206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            Slog.w(TAG, "No SearchManager");
95206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
96206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        return intent;
97206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
98206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
99206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    private SearchManager getSearchManager() {
100206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        if (mSearchManager == null) {
101206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            mSearchManager = (SearchManager) mContext.getSystemService(Context.SEARCH_SERVICE);
102206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
103206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        return mSearchManager;
104206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
105206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
106206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    private void startAssistActivity() {
107206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        // Close Recent Apps if needed
108206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        mBar.animateCollapse(CommandQueue.FLAG_EXCLUDE_SEARCH_PANEL);
109206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        // Launch Assist
110206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        Intent intent = getAssistIntent();
111206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        try {
112206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            ActivityOptions opts = ActivityOptions.makeCustomAnimation(mContext,
113206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                    R.anim.search_launch_enter, R.anim.search_launch_exit);
114206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
115206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            mContext.startActivity(intent, opts.toBundle());
116206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        } catch (ActivityNotFoundException e) {
117206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            Slog.w(TAG, "Activity not found for " + intent.getAction());
118206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
119206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
120206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
121206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    final MultiWaveView.OnTriggerListener mMultiWaveViewListener
122206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            = new MultiWaveView.OnTriggerListener() {
123e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov
124e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov        private boolean mWaitingForLaunch;
125206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
126206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        public void onGrabbed(View v, int handle) {
127206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
128206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
129f0ef665299d795df7905897e1c337e37891dafefJean-Baptiste Queru        public void onReleased(View v, int handle) {
130206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
131206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
132206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        public void onGrabbedStateChange(View v, int handle) {
133e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov            if (!mWaitingForLaunch && OnTriggerListener.NO_HANDLE == handle) {
134206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                mBar.hideSearchPanel();
135206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            }
136206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
137206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
1389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        public void onTrigger(View v, final int target) {
1399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            final int resId = mMultiWaveView.getResourceIdForTarget(target);
1409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            switch (resId) {
141206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                case com.android.internal.R.drawable.ic_lockscreen_search:
142206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                    mWaitingForLaunch = true;
143206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                    startAssistActivity();
144206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                    postDelayed(new Runnable() {
145206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                        public void run() {
146206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                            mWaitingForLaunch = false;
147206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                            mBar.hideSearchPanel();
148206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                        }
149206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                    }, SEARCH_PANEL_HOLD_DURATION);
150206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                break;
151206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            }
152206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
153206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
154206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        public void onFinishFinalAnimation() {
155206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
156206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    };
157206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
158206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    @Override
159206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    protected void onFinishInflate() {
1609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        super.onFinishInflate();
161206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
162206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        mSearchTargetsContainer = findViewById(R.id.search_panel_container);
163206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        mStatusBarTouchProxy = (StatusBarTouchProxy) findViewById(R.id.status_bar_touch_proxy);
1649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // TODO: fetch views
16568f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        mMultiWaveView = (MultiWaveView) findViewById(R.id.multi_wave_view);
16668f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        mMultiWaveView.setOnTriggerListener(mMultiWaveViewListener);
16768f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook    }
16868f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook
169e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov    private boolean pointInside(int x, int y, View v) {
17068f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        final int l = v.getLeft();
17168f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        final int r = v.getRight();
17268f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        final int t = v.getTop();
17368f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        final int b = v.getBottom();
174e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov        return x >= l && x < r && y >= t && y < b;
17568f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook    }
17668f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook
17768f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook    public boolean isInContentArea(int x, int y) {
17868f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        if (pointInside(x, y, mSearchTargetsContainer)) {
179e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov            return true;
18068f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        } else if (mStatusBarTouchProxy != null &&
18168f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook                pointInside(x, y, mStatusBarTouchProxy)) {
182206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            return true;
18368f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        } else {
184cedc446684e94c9971c38c3206f1f224314bda2aSvetoslav Ganov            return false;
18550f34d14f6dd3411fdbdb6a7b8b285c2b8fdbf5cSvetoslav Ganov        }
18650f34d14f6dd3411fdbdb6a7b8b285c2b8fdbf5cSvetoslav Ganov    }
18750f34d14f6dd3411fdbdb6a7b8b285c2b8fdbf5cSvetoslav Ganov
18850f34d14f6dd3411fdbdb6a7b8b285c2b8fdbf5cSvetoslav Ganov    private final OnPreDrawListener mPreDrawListener = new ViewTreeObserver.OnPreDrawListener() {
18950f34d14f6dd3411fdbdb6a7b8b285c2b8fdbf5cSvetoslav Ganov        public boolean onPreDraw() {
190206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            getViewTreeObserver().removeOnPreDrawListener(this);
191206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            mMultiWaveView.resumeAnimations();
192206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            return false;
193206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
1949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    };
195fdf6db6748b32f620a7f68b13a67c38b4e59e5edTom Taylor
196206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    public void show(final boolean show, boolean animate) {
197206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        if (!show) {
198206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            final LayoutTransition transitioner = animate ? createLayoutTransitioner() : null;
199e9730bf3d2dcbea1879f24c18aaf9810ac57084cSvetoslav Ganov            ((ViewGroup)mSearchTargetsContainer).setLayoutTransition(transitioner);
200fdf6db6748b32f620a7f68b13a67c38b4e59e5edTom Taylor        }
20168f2f547f56f239b60d13b2b62a08a65874f6662Paul Westbrook        mShowing = show;
202206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        if (show) {
203206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            if (getVisibility() != View.VISIBLE) {
204206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                setVisibility(View.VISIBLE);
205206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                // Don't start the animation until we've created the layer, which is done
206206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                // right before we are drawn
207206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                mMultiWaveView.suspendAnimations();
208206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov                getViewTreeObserver().addOnPreDrawListener(mPreDrawListener);
209206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            }
210206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            setFocusable(true);
211206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            setFocusableInTouchMode(true);
212206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            requestFocus();
213206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        } else {
214206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            setVisibility(View.INVISIBLE);
215206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
216206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
217206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
218206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    public void hide(boolean animate) {
219206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        if (mBar != null) {
220206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            // This will indirectly cause show(false, ...) to get called
221206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            mBar.animateCollapse(CommandQueue.FLAG_EXCLUDE_NONE);
222206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        } else {
223206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            setVisibility(View.INVISIBLE);
224206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
225206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
226206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
227206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    /**
228206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov     * We need to be aligned at the bottom.  LinearLayout can't do this, so instead,
229206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov     * let LinearLayout do all the hard work, and then shift everything down to the bottom.
230206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov     */
231206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    @Override
232206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    protected void onLayout(boolean changed, int l, int t, int r, int b) {
233206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        super.onLayout(changed, l, t, r, b);
234206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        // setPanelHeight(mSearchTargetsContainer.getHeight());
235206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
236206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
237206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    @Override
238206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    public boolean dispatchHoverEvent(MotionEvent event) {
239206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        // Ignore hover events outside of this panel bounds since such events
240206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        // generate spurious accessibility events with the panel content when
241206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        // tapping outside of it, thus confusing the user.
242206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        final int x = (int) event.getX();
243206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        final int y = (int) event.getY();
244206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        if (x >= 0 && x < getWidth() && y >= 0 && y < getHeight()) {
245206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            return super.dispatchHoverEvent(event);
246206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
247206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        return true;
248206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
249206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
250206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    /**
251206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov     * Whether the panel is showing, or, if it's animating, whether it will be
252206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov     * when the animation is done.
253206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov     */
254206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    public boolean isShowing() {
255206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        return mShowing;
256206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
257206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
258206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    public void setBar(BaseStatusBar bar) {
259206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        mBar = bar;
260206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
261206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
262206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    public void setStatusBarView(final View statusBarView) {
263206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        if (mStatusBarTouchProxy != null) {
264206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov            mStatusBarTouchProxy.setStatusBar(statusBarView);
265206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov//            mMultiWaveView.setOnTouchListener(new OnTouchListener() {
266206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov//                public boolean onTouch(View v, MotionEvent event) {
267206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov//                    return statusBarView.onTouchEvent(event);
268206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov//                }
269206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov//            });
270206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        }
271206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
272206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov
273206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    private LayoutTransition createLayoutTransitioner() {
274206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        LayoutTransition transitioner = new LayoutTransition();
275206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        transitioner.setDuration(200);
276206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        transitioner.setStartDelay(LayoutTransition.CHANGE_DISAPPEARING, 0);
277206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        transitioner.setAnimator(LayoutTransition.DISAPPEARING, null);
278206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov        return transitioner;
279206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov    }
280206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov}
281206316a61f904ea0a6b106137dd7715a2c246d4cSvetoslav Ganov