TabScrollView.java revision fe25199a6f975c67d28afcc1de56b0f987b66cd8
1fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb/* 2fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * Copyright (C) 2010 The Android Open Source Project 3fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * 4fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * Licensed under the Apache License, Version 2.0 (the "License"); 5fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * you may not use this file except in compliance with the License. 6fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * You may obtain a copy of the License at 7fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * 8fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * http://www.apache.org/licenses/LICENSE-2.0 9fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * 10fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * Unless required by applicable law or agreed to in writing, software 11fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * distributed under the License is distributed on an "AS IS" BASIS, 12fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * See the License for the specific language governing permissions and 14fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * limitations under the License. 15fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb */ 16fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 17fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolbpackage com.android.browser; 18fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 19fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolbimport android.content.Context; 20fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolbimport android.util.AttributeSet; 21fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolbimport android.view.View; 22fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolbimport android.widget.HorizontalScrollView; 23fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolbimport android.widget.LinearLayout; 24fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 25fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb/** 26fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * custom view for displaying tabs in the tabbed title bar 27fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb */ 28fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolbpublic class TabScrollView extends HorizontalScrollView { 29fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 30fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb private Context mContext; 31fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 32fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb private LinearLayout mContentView; 33fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 34fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb private int mSelected; 35fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 36fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb /** 37fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * @param context 38fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * @param attrs 39fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * @param defStyle 40fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb */ 41fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb public TabScrollView(Context context, AttributeSet attrs, int defStyle) { 42fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb super(context, attrs, defStyle); 43fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb init(context); 44fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 45fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 46fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb /** 47fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * @param context 48fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * @param attrs 49fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb */ 50fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb public TabScrollView(Context context, AttributeSet attrs) { 51fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb super(context, attrs); 52fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb init(context); 53fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 54fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 55fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb /** 56fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb * @param context 57fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb */ 58fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb public TabScrollView(Context context) { 59fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb super(context); 60fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb init(context); 61fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 62fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 63fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb private void init(Context ctx) { 64fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mContext = ctx; 65fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb setHorizontalScrollBarEnabled(false); 66fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mContentView = new LinearLayout(mContext); 67fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mContentView.setOrientation(LinearLayout.HORIZONTAL); 68fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mContentView.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT, 69fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb LayoutParams.WRAP_CONTENT)); 70fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb addView(mContentView); 71fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mSelected = -1; 72fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 73fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 74fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb @Override 75fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb protected void onLayout(boolean changed, int left, int top, int right, int bottom) { 76fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb super.onLayout(changed, left, top, right, bottom); 77fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb ensureChildVisible(getSelectedTab()); 78fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 79fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 80fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb void setSelectedTab(int position) { 81fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb View v = getSelectedTab(); 82fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb if (v != null) { 83fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb v.setSelected(false); 84fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 85fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mSelected = position; 86fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb v = getSelectedTab(); 87fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb if (v != null) { 88fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb v.setSelected(true); 89fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 90fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb requestLayout(); 91fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 92fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 93fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb View getSelectedTab() { 94fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb if ((mSelected >= 0) && (mSelected < mContentView.getChildCount())) { 95fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb return mContentView.getChildAt(mSelected); 96fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } else { 97fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb return null; 98fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 99fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 100fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 101fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb void clearTabs() { 102fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mContentView.removeAllViews(); 103fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 104fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 105fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb void addTab(View tab) { 106fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mContentView.addView(tab); 107fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb tab.setSelected(false); 108fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 109fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 110fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb void addTab(View tab, int pos) { 111fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mContentView.addView(tab, pos); 112fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb tab.setSelected(false); 113fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 114fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 115fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb void removeTab(View tab) { 116fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb mContentView.removeView(tab); 117fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 118fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 119fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb void ensureChildVisible(View child) { 120fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb if (child != null) { 121fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb int childl = child.getLeft(); 122fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb int childr = childl + child.getWidth(); 123fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb int viewl = getScrollX(); 124fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb int viewr = viewl + getWidth(); 125fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb if (childl < viewl) { 126fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb // need scrolling to left 127fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb scrollTo(childl, 0); 128fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } else if (childr > viewr) { 129fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb // need scrolling to right 130fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb scrollTo(childr - viewr + viewl, 0); 131fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 132fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 133fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb } 134fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 135fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb 136fe25199a6f975c67d28afcc1de56b0f987b66cd8Michael Kolb} 137