blob: 83ac89689942b548891965bdafbe07cdb8dfb1b2 [file] [log] [blame]
Adam Powellf8ac6b72011-05-23 18:14:09 -07001/*
2 * Copyright (C) 2011 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16package com.android.internal.widget;
17
Adam Powellb8139af2012-04-19 13:52:46 -070018import com.android.internal.view.ActionBarPolicy;
Adam Powellfaa6ffa2011-08-08 14:48:02 -070019
Adam Powellf6ce6a92011-06-29 10:25:01 -070020import android.animation.Animator;
21import android.animation.ObjectAnimator;
22import android.animation.TimeInterpolator;
Adam Powellf8ac6b72011-05-23 18:14:09 -070023import android.app.ActionBar;
24import android.content.Context;
Adam Powellfaa6ffa2011-08-08 14:48:02 -070025import android.content.res.Configuration;
Adam Powellf8ac6b72011-05-23 18:14:09 -070026import android.graphics.drawable.Drawable;
27import android.text.TextUtils.TruncateAt;
28import android.view.Gravity;
29import android.view.View;
30import android.view.ViewGroup;
Adam Powell05c82772011-11-21 17:14:56 -080031import android.view.ViewParent;
Adam Powellf6ce6a92011-06-29 10:25:01 -070032import android.view.animation.DecelerateInterpolator;
Adam Powellf5645cb2011-08-10 22:49:02 -070033import android.widget.AdapterView;
34import android.widget.BaseAdapter;
Adam Powellf8ac6b72011-05-23 18:14:09 -070035import android.widget.HorizontalScrollView;
36import android.widget.ImageView;
37import android.widget.LinearLayout;
Adam Powellf5645cb2011-08-10 22:49:02 -070038import android.widget.ListView;
39import android.widget.Spinner;
Adam Powellf8ac6b72011-05-23 18:14:09 -070040import android.widget.TextView;
41
Adam Powellf5645cb2011-08-10 22:49:02 -070042/**
43 * This widget implements the dynamic action bar tab behavior that can change
44 * across different configurations or circumstances.
45 */
46public class ScrollingTabContainerView extends HorizontalScrollView
Adam Powellc4e57e22012-02-24 19:24:26 -080047 implements AdapterView.OnItemClickListener {
Adam Powellf5645cb2011-08-10 22:49:02 -070048 private static final String TAG = "ScrollingTabContainerView";
Adam Powellf8ac6b72011-05-23 18:14:09 -070049 Runnable mTabSelector;
50 private TabClickListener mTabClickListener;
51
52 private LinearLayout mTabLayout;
Adam Powellf5645cb2011-08-10 22:49:02 -070053 private Spinner mTabSpinner;
54 private boolean mAllowCollapse;
Adam Powellf8ac6b72011-05-23 18:14:09 -070055
56 int mMaxTabWidth;
Adam Powellb8139af2012-04-19 13:52:46 -070057 int mStackedTabMaxWidth;
Adam Powellf5645cb2011-08-10 22:49:02 -070058 private int mContentHeight;
59 private int mSelectedTabIndex;
Adam Powellf8ac6b72011-05-23 18:14:09 -070060
Adam Powellf6ce6a92011-06-29 10:25:01 -070061 protected Animator mVisibilityAnim;
62 protected final VisibilityAnimListener mVisAnimListener = new VisibilityAnimListener();
63
64 private static final TimeInterpolator sAlphaInterpolator = new DecelerateInterpolator();
65
66 private static final int FADE_DURATION = 200;
67
Adam Powellf8ac6b72011-05-23 18:14:09 -070068 public ScrollingTabContainerView(Context context) {
69 super(context);
70 setHorizontalScrollBarEnabled(false);
Adam Powellf5645cb2011-08-10 22:49:02 -070071
Adam Powellb8139af2012-04-19 13:52:46 -070072 ActionBarPolicy abp = ActionBarPolicy.get(context);
73 setContentHeight(abp.getTabContainerHeight());
74 mStackedTabMaxWidth = abp.getStackedTabMaxWidth();
Adam Powellaf6b97e2011-08-11 17:40:57 -070075
Adam Powellf5645cb2011-08-10 22:49:02 -070076 mTabLayout = createTabLayout();
77 addView(mTabLayout, new ViewGroup.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
78 ViewGroup.LayoutParams.MATCH_PARENT));
Adam Powellf8ac6b72011-05-23 18:14:09 -070079 }
80
81 @Override
82 public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
83 final int widthMode = MeasureSpec.getMode(widthMeasureSpec);
Adam Powellf5645cb2011-08-10 22:49:02 -070084 final boolean lockedExpanded = widthMode == MeasureSpec.EXACTLY;
85 setFillViewport(lockedExpanded);
Adam Powellf8ac6b72011-05-23 18:14:09 -070086
Adam Powellf5645cb2011-08-10 22:49:02 -070087 final int childCount = mTabLayout.getChildCount();
Adam Powellf8ac6b72011-05-23 18:14:09 -070088 if (childCount > 1 &&
89 (widthMode == MeasureSpec.EXACTLY || widthMode == MeasureSpec.AT_MOST)) {
90 if (childCount > 2) {
91 mMaxTabWidth = (int) (MeasureSpec.getSize(widthMeasureSpec) * 0.4f);
92 } else {
93 mMaxTabWidth = MeasureSpec.getSize(widthMeasureSpec) / 2;
94 }
Adam Powellb8139af2012-04-19 13:52:46 -070095 mMaxTabWidth = Math.min(mMaxTabWidth, mStackedTabMaxWidth);
Adam Powellf8ac6b72011-05-23 18:14:09 -070096 } else {
97 mMaxTabWidth = -1;
98 }
99
Adam Powellaf6b97e2011-08-11 17:40:57 -0700100 heightMeasureSpec = MeasureSpec.makeMeasureSpec(mContentHeight, MeasureSpec.EXACTLY);
Adam Powellf5645cb2011-08-10 22:49:02 -0700101
102 final boolean canCollapse = !lockedExpanded && mAllowCollapse;
103
104 if (canCollapse) {
105 // See if we should expand
106 mTabLayout.measure(MeasureSpec.UNSPECIFIED, heightMeasureSpec);
107 if (mTabLayout.getMeasuredWidth() > MeasureSpec.getSize(widthMeasureSpec)) {
108 performCollapse();
109 } else {
110 performExpand();
111 }
112 } else {
113 performExpand();
114 }
115
116 final int oldWidth = getMeasuredWidth();
Adam Powellf8ac6b72011-05-23 18:14:09 -0700117 super.onMeasure(widthMeasureSpec, heightMeasureSpec);
Adam Powellf5645cb2011-08-10 22:49:02 -0700118 final int newWidth = getMeasuredWidth();
119
120 if (lockedExpanded && oldWidth != newWidth) {
121 // Recenter the tab display if we're at a new (scrollable) size.
122 setTabSelected(mSelectedTabIndex);
123 }
124 }
125
126 /**
127 * Indicates whether this view is collapsed into a dropdown menu instead
128 * of traditional tabs.
129 * @return true if showing as a spinner
130 */
131 private boolean isCollapsed() {
132 return mTabSpinner != null && mTabSpinner.getParent() == this;
133 }
134
135 public void setAllowCollapse(boolean allowCollapse) {
136 mAllowCollapse = allowCollapse;
137 }
138
139 private void performCollapse() {
140 if (isCollapsed()) return;
141
142 if (mTabSpinner == null) {
143 mTabSpinner = createSpinner();
144 }
145 removeView(mTabLayout);
146 addView(mTabSpinner, new ViewGroup.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
147 ViewGroup.LayoutParams.MATCH_PARENT));
148 if (mTabSpinner.getAdapter() == null) {
149 mTabSpinner.setAdapter(new TabAdapter());
150 }
151 if (mTabSelector != null) {
152 removeCallbacks(mTabSelector);
153 mTabSelector = null;
154 }
155 mTabSpinner.setSelection(mSelectedTabIndex);
156 }
157
158 private boolean performExpand() {
159 if (!isCollapsed()) return false;
160
161 removeView(mTabSpinner);
162 addView(mTabLayout, new ViewGroup.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
163 ViewGroup.LayoutParams.MATCH_PARENT));
164 setTabSelected(mTabSpinner.getSelectedItemPosition());
165 return false;
Adam Powellf8ac6b72011-05-23 18:14:09 -0700166 }
167
168 public void setTabSelected(int position) {
Adam Powellf5645cb2011-08-10 22:49:02 -0700169 mSelectedTabIndex = position;
Adam Powellf8ac6b72011-05-23 18:14:09 -0700170 final int tabCount = mTabLayout.getChildCount();
171 for (int i = 0; i < tabCount; i++) {
172 final View child = mTabLayout.getChildAt(i);
173 final boolean isSelected = i == position;
174 child.setSelected(isSelected);
175 if (isSelected) {
176 animateToTab(position);
177 }
178 }
179 }
180
Adam Powell45c0b192011-07-28 15:11:57 -0700181 public void setContentHeight(int contentHeight) {
Adam Powellf5645cb2011-08-10 22:49:02 -0700182 mContentHeight = contentHeight;
Adam Powell45c0b192011-07-28 15:11:57 -0700183 requestLayout();
184 }
185
Adam Powellf5645cb2011-08-10 22:49:02 -0700186 private LinearLayout createTabLayout() {
187 final LinearLayout tabLayout = new LinearLayout(getContext(), null,
188 com.android.internal.R.attr.actionBarTabBarStyle);
189 tabLayout.setMeasureWithLargestChildEnabled(true);
Adam Powellb8139af2012-04-19 13:52:46 -0700190 tabLayout.setGravity(Gravity.CENTER);
Adam Powellf5645cb2011-08-10 22:49:02 -0700191 tabLayout.setLayoutParams(new LinearLayout.LayoutParams(
192 LinearLayout.LayoutParams.WRAP_CONTENT, LinearLayout.LayoutParams.MATCH_PARENT));
193 return tabLayout;
194 }
195
196 private Spinner createSpinner() {
197 final Spinner spinner = new Spinner(getContext(), null,
198 com.android.internal.R.attr.actionDropDownStyle);
199 spinner.setLayoutParams(new LinearLayout.LayoutParams(
200 LinearLayout.LayoutParams.WRAP_CONTENT, LinearLayout.LayoutParams.MATCH_PARENT));
Adam Powellc4e57e22012-02-24 19:24:26 -0800201 spinner.setOnItemClickListenerInt(this);
Adam Powellf5645cb2011-08-10 22:49:02 -0700202 return spinner;
203 }
204
Adam Powellfaa6ffa2011-08-08 14:48:02 -0700205 @Override
206 protected void onConfigurationChanged(Configuration newConfig) {
207 super.onConfigurationChanged(newConfig);
208
Adam Powellb8139af2012-04-19 13:52:46 -0700209 ActionBarPolicy abp = ActionBarPolicy.get(getContext());
Adam Powellfaa6ffa2011-08-08 14:48:02 -0700210 // Action bar can change size on configuration changes.
211 // Reread the desired height from the theme-specified style.
Adam Powellb8139af2012-04-19 13:52:46 -0700212 setContentHeight(abp.getTabContainerHeight());
213 mStackedTabMaxWidth = abp.getStackedTabMaxWidth();
Adam Powellfaa6ffa2011-08-08 14:48:02 -0700214 }
215
Adam Powellf6ce6a92011-06-29 10:25:01 -0700216 public void animateToVisibility(int visibility) {
217 if (mVisibilityAnim != null) {
218 mVisibilityAnim.cancel();
219 }
220 if (visibility == VISIBLE) {
221 if (getVisibility() != VISIBLE) {
222 setAlpha(0);
223 }
224 ObjectAnimator anim = ObjectAnimator.ofFloat(this, "alpha", 1);
225 anim.setDuration(FADE_DURATION);
226 anim.setInterpolator(sAlphaInterpolator);
227
228 anim.addListener(mVisAnimListener.withFinalVisibility(visibility));
229 anim.start();
230 } else {
231 ObjectAnimator anim = ObjectAnimator.ofFloat(this, "alpha", 0);
232 anim.setDuration(FADE_DURATION);
233 anim.setInterpolator(sAlphaInterpolator);
234
235 anim.addListener(mVisAnimListener.withFinalVisibility(visibility));
236 anim.start();
237 }
238 }
239
Adam Powellf5645cb2011-08-10 22:49:02 -0700240 public void animateToTab(final int position) {
Adam Powellf8ac6b72011-05-23 18:14:09 -0700241 final View tabView = mTabLayout.getChildAt(position);
242 if (mTabSelector != null) {
243 removeCallbacks(mTabSelector);
244 }
245 mTabSelector = new Runnable() {
246 public void run() {
247 final int scrollPos = tabView.getLeft() - (getWidth() - tabView.getWidth()) / 2;
248 smoothScrollTo(scrollPos, 0);
249 mTabSelector = null;
250 }
251 };
252 post(mTabSelector);
253 }
254
Adam Powellf5645cb2011-08-10 22:49:02 -0700255 @Override
256 public void onAttachedToWindow() {
257 super.onAttachedToWindow();
258 if (mTabSelector != null) {
259 // Re-post the selector we saved
260 post(mTabSelector);
Adam Powellf8ac6b72011-05-23 18:14:09 -0700261 }
262 }
263
Adam Powellf8ac6b72011-05-23 18:14:09 -0700264 @Override
265 public void onDetachedFromWindow() {
266 super.onDetachedFromWindow();
267 if (mTabSelector != null) {
268 removeCallbacks(mTabSelector);
269 }
270 }
271
Adam Powellf5645cb2011-08-10 22:49:02 -0700272 private TabView createTabView(ActionBar.Tab tab, boolean forAdapter) {
273 final TabView tabView = new TabView(getContext(), tab, forAdapter);
274 if (forAdapter) {
275 tabView.setBackgroundDrawable(null);
276 tabView.setLayoutParams(new ListView.LayoutParams(ListView.LayoutParams.MATCH_PARENT,
277 mContentHeight));
278 } else {
279 tabView.setFocusable(true);
Adam Powellf8ac6b72011-05-23 18:14:09 -0700280
Adam Powellf5645cb2011-08-10 22:49:02 -0700281 if (mTabClickListener == null) {
282 mTabClickListener = new TabClickListener();
283 }
284 tabView.setOnClickListener(mTabClickListener);
Adam Powellf8ac6b72011-05-23 18:14:09 -0700285 }
Adam Powellf8ac6b72011-05-23 18:14:09 -0700286 return tabView;
287 }
288
289 public void addTab(ActionBar.Tab tab, boolean setSelected) {
Adam Powellf5645cb2011-08-10 22:49:02 -0700290 TabView tabView = createTabView(tab, false);
Adam Powellf8ac6b72011-05-23 18:14:09 -0700291 mTabLayout.addView(tabView, new LinearLayout.LayoutParams(0,
292 LayoutParams.MATCH_PARENT, 1));
Adam Powellf5645cb2011-08-10 22:49:02 -0700293 if (mTabSpinner != null) {
294 ((TabAdapter) mTabSpinner.getAdapter()).notifyDataSetChanged();
295 }
Adam Powellf8ac6b72011-05-23 18:14:09 -0700296 if (setSelected) {
297 tabView.setSelected(true);
298 }
Adam Powellf5645cb2011-08-10 22:49:02 -0700299 if (mAllowCollapse) {
300 requestLayout();
301 }
Adam Powellf8ac6b72011-05-23 18:14:09 -0700302 }
303
304 public void addTab(ActionBar.Tab tab, int position, boolean setSelected) {
Adam Powellf5645cb2011-08-10 22:49:02 -0700305 final TabView tabView = createTabView(tab, false);
Adam Powellf8ac6b72011-05-23 18:14:09 -0700306 mTabLayout.addView(tabView, position, new LinearLayout.LayoutParams(
307 0, LayoutParams.MATCH_PARENT, 1));
Adam Powellf5645cb2011-08-10 22:49:02 -0700308 if (mTabSpinner != null) {
309 ((TabAdapter) mTabSpinner.getAdapter()).notifyDataSetChanged();
310 }
Adam Powellf8ac6b72011-05-23 18:14:09 -0700311 if (setSelected) {
312 tabView.setSelected(true);
313 }
Adam Powellf5645cb2011-08-10 22:49:02 -0700314 if (mAllowCollapse) {
315 requestLayout();
316 }
Adam Powellf8ac6b72011-05-23 18:14:09 -0700317 }
318
319 public void updateTab(int position) {
320 ((TabView) mTabLayout.getChildAt(position)).update();
Adam Powellf5645cb2011-08-10 22:49:02 -0700321 if (mTabSpinner != null) {
322 ((TabAdapter) mTabSpinner.getAdapter()).notifyDataSetChanged();
323 }
324 if (mAllowCollapse) {
325 requestLayout();
326 }
Adam Powellf8ac6b72011-05-23 18:14:09 -0700327 }
328
329 public void removeTabAt(int position) {
Adam Powellf5645cb2011-08-10 22:49:02 -0700330 mTabLayout.removeViewAt(position);
331 if (mTabSpinner != null) {
332 ((TabAdapter) mTabSpinner.getAdapter()).notifyDataSetChanged();
333 }
334 if (mAllowCollapse) {
335 requestLayout();
Adam Powellf8ac6b72011-05-23 18:14:09 -0700336 }
337 }
338
339 public void removeAllTabs() {
Adam Powellf5645cb2011-08-10 22:49:02 -0700340 mTabLayout.removeAllViews();
341 if (mTabSpinner != null) {
342 ((TabAdapter) mTabSpinner.getAdapter()).notifyDataSetChanged();
Adam Powellf8ac6b72011-05-23 18:14:09 -0700343 }
Adam Powellf5645cb2011-08-10 22:49:02 -0700344 if (mAllowCollapse) {
345 requestLayout();
346 }
347 }
348
349 @Override
Adam Powellc4e57e22012-02-24 19:24:26 -0800350 public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
Adam Powellf5645cb2011-08-10 22:49:02 -0700351 TabView tabView = (TabView) view;
352 tabView.getTab().select();
353 }
354
Adam Powellf8ac6b72011-05-23 18:14:09 -0700355 private class TabView extends LinearLayout {
356 private ActionBar.Tab mTab;
357 private TextView mTextView;
358 private ImageView mIconView;
359 private View mCustomView;
360
Adam Powellf5645cb2011-08-10 22:49:02 -0700361 public TabView(Context context, ActionBar.Tab tab, boolean forList) {
Adam Powellf8ac6b72011-05-23 18:14:09 -0700362 super(context, null, com.android.internal.R.attr.actionBarTabStyle);
363 mTab = tab;
364
Adam Powellf5645cb2011-08-10 22:49:02 -0700365 if (forList) {
366 setGravity(Gravity.LEFT | Gravity.CENTER_VERTICAL);
367 }
368
369 update();
370 }
371
372 public void bindTab(ActionBar.Tab tab) {
373 mTab = tab;
Adam Powellf8ac6b72011-05-23 18:14:09 -0700374 update();
375 }
376
377 @Override
378 public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
379 super.onMeasure(widthMeasureSpec, heightMeasureSpec);
380
381 // Re-measure if we went beyond our maximum size.
382 if (mMaxTabWidth > 0 && getMeasuredWidth() > mMaxTabWidth) {
383 super.onMeasure(MeasureSpec.makeMeasureSpec(mMaxTabWidth, MeasureSpec.EXACTLY),
384 heightMeasureSpec);
385 }
386 }
387
388 public void update() {
389 final ActionBar.Tab tab = mTab;
390 final View custom = tab.getCustomView();
391 if (custom != null) {
Adam Powell05c82772011-11-21 17:14:56 -0800392 final ViewParent customParent = custom.getParent();
393 if (customParent != this) {
394 if (customParent != null) ((ViewGroup) customParent).removeView(custom);
395 addView(custom);
396 }
Adam Powellf8ac6b72011-05-23 18:14:09 -0700397 mCustomView = custom;
398 if (mTextView != null) mTextView.setVisibility(GONE);
399 if (mIconView != null) {
400 mIconView.setVisibility(GONE);
401 mIconView.setImageDrawable(null);
402 }
403 } else {
404 if (mCustomView != null) {
405 removeView(mCustomView);
406 mCustomView = null;
407 }
408
409 final Drawable icon = tab.getIcon();
410 final CharSequence text = tab.getText();
411
412 if (icon != null) {
413 if (mIconView == null) {
414 ImageView iconView = new ImageView(getContext());
415 LayoutParams lp = new LayoutParams(LayoutParams.WRAP_CONTENT,
416 LayoutParams.WRAP_CONTENT);
417 lp.gravity = Gravity.CENTER_VERTICAL;
418 iconView.setLayoutParams(lp);
419 addView(iconView, 0);
420 mIconView = iconView;
421 }
422 mIconView.setImageDrawable(icon);
423 mIconView.setVisibility(VISIBLE);
424 } else if (mIconView != null) {
425 mIconView.setVisibility(GONE);
426 mIconView.setImageDrawable(null);
427 }
428
429 if (text != null) {
430 if (mTextView == null) {
431 TextView textView = new TextView(getContext(), null,
432 com.android.internal.R.attr.actionBarTabTextStyle);
Adam Powellf8ac6b72011-05-23 18:14:09 -0700433 textView.setEllipsize(TruncateAt.END);
434 LayoutParams lp = new LayoutParams(LayoutParams.WRAP_CONTENT,
435 LayoutParams.WRAP_CONTENT);
436 lp.gravity = Gravity.CENTER_VERTICAL;
437 textView.setLayoutParams(lp);
438 addView(textView);
439 mTextView = textView;
440 }
441 mTextView.setText(text);
442 mTextView.setVisibility(VISIBLE);
Adam Powell251df772011-06-14 20:24:34 -0700443 } else if (mTextView != null) {
Adam Powellf8ac6b72011-05-23 18:14:09 -0700444 mTextView.setVisibility(GONE);
Adam Powell251df772011-06-14 20:24:34 -0700445 mTextView.setText(null);
Adam Powellf8ac6b72011-05-23 18:14:09 -0700446 }
Adam Powell94e56ef2011-09-06 21:22:22 -0700447
Adam Powell65d57042011-09-08 12:18:14 -0700448 if (mIconView != null) {
449 mIconView.setContentDescription(tab.getContentDescription());
450 }
Adam Powellf8ac6b72011-05-23 18:14:09 -0700451 }
452 }
453
454 public ActionBar.Tab getTab() {
455 return mTab;
456 }
457 }
458
Adam Powellf5645cb2011-08-10 22:49:02 -0700459 private class TabAdapter extends BaseAdapter {
460 @Override
461 public int getCount() {
462 return mTabLayout.getChildCount();
463 }
464
465 @Override
466 public Object getItem(int position) {
467 return ((TabView) mTabLayout.getChildAt(position)).getTab();
468 }
469
470 @Override
471 public long getItemId(int position) {
472 return position;
473 }
474
475 @Override
476 public View getView(int position, View convertView, ViewGroup parent) {
477 if (convertView == null) {
478 convertView = createTabView((ActionBar.Tab) getItem(position), true);
479 } else {
480 ((TabView) convertView).bindTab((ActionBar.Tab) getItem(position));
481 }
482 return convertView;
483 }
484 }
485
Adam Powellf8ac6b72011-05-23 18:14:09 -0700486 private class TabClickListener implements OnClickListener {
487 public void onClick(View view) {
488 TabView tabView = (TabView) view;
489 tabView.getTab().select();
490 final int tabCount = mTabLayout.getChildCount();
491 for (int i = 0; i < tabCount; i++) {
492 final View child = mTabLayout.getChildAt(i);
493 child.setSelected(child == view);
494 }
495 }
496 }
Adam Powellf6ce6a92011-06-29 10:25:01 -0700497
498 protected class VisibilityAnimListener implements Animator.AnimatorListener {
499 private boolean mCanceled = false;
500 private int mFinalVisibility;
501
502 public VisibilityAnimListener withFinalVisibility(int visibility) {
503 mFinalVisibility = visibility;
504 return this;
505 }
506
507 @Override
508 public void onAnimationStart(Animator animation) {
509 setVisibility(VISIBLE);
510 mVisibilityAnim = animation;
511 mCanceled = false;
512 }
513
514 @Override
515 public void onAnimationEnd(Animator animation) {
516 if (mCanceled) return;
517
518 mVisibilityAnim = null;
519 setVisibility(mFinalVisibility);
520 }
521
522 @Override
523 public void onAnimationCancel(Animator animation) {
524 mCanceled = true;
525 }
526
527 @Override
528 public void onAnimationRepeat(Animator animation) {
529 }
530 }
Adam Powellf8ac6b72011-05-23 18:14:09 -0700531}