ActivityChooserView.java revision bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2
151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov/* 251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Copyright (C) 2011 The Android Open Source Project 351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Licensed under the Apache License, Version 2.0 (the "License"); 551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * you may not use this file except in compliance with the License. 651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * You may obtain a copy of the License at 751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * http://www.apache.org/licenses/LICENSE-2.0 951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 1051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Unless required by applicable law or agreed to in writing, software 1151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * distributed under the License is distributed on an "AS IS" BASIS, 1251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * See the License for the specific language governing permissions and 1451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * limitations under the License. 1551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 1651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 1751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovpackage android.widget; 1851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 1951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.content.Context; 2051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.content.Intent; 2151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.content.pm.PackageManager; 2251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.content.pm.ResolveInfo; 23414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganovimport android.content.res.Resources; 2451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.content.res.TypedArray; 2551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.database.DataSetObserver; 2651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.graphics.Canvas; 2751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.graphics.drawable.Drawable; 2851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.util.AttributeSet; 2951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.view.LayoutInflater; 3051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport android.view.View; 318c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganovimport android.view.ViewGroup; 328c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganovimport android.widget.ActivityChooserModel.ActivityChooserModelClient; 3351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 3451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovimport com.android.internal.R; 3551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 3651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov/** 3751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * This class is a view for choosing an activity for handling a given {@link Intent}. 3851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * <p> 3951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * The view is composed of two adjacent buttons: 4051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * <ul> 4151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * <li> 4251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * The left button is an immediate action and allows one click activity choosing. 4351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Tapping this button immediately executes the intent without requiring any further 4451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * user input. Long press on this button shows a popup for changing the default 4551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * activity. 4651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * </li> 4751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * <li> 4851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * The right button is an overflow action and provides an optimized menu 4951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * of additional activities. Tapping this button shows a popup anchored to this 5051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * view, listing the most frequently used activities. This list is initially 5151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * limited to a small number of items in frequency used order. The last item, 5251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * "Show all..." serves as an affordance to display all available activities. 5351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * </li> 5451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * </ul> 5551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * </p> 5651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 5751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @hide 5851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 5951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganovpublic class ActivityChooserView extends ViewGroup implements ActivityChooserModelClient { 6051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 6151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 6251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * An adapter for displaying the activities in an {@link AdapterView}. 6351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 6451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private final ActivityChooserViewAdapter mAdapter; 6551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 6651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 6751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Implementation of various interfaces to avoid publishing them in the APIs. 6851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 6951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private final Callbacks mCallbacks; 7051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 7151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 7251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * The content of this view. 7351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 7451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private final LinearLayout mActivityChooserContent; 7551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 7651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 7751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * The expand activities action button; 78f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov */ 79f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov private final FrameLayout mExpandActivityOverflowButton; 80f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov 81f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov /** 82f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov * The image for the expand activities action button; 8351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 8451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private final ImageView mExpandActivityOverflowButtonImage; 85bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov 86bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov /** 87bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov * The default activities action button; 88bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov */ 89bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov private final FrameLayout mDefaultActivityButton; 90bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov 9151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 9251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * The image for the default activities action button; 9351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 9451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private final ImageView mDefaultActivityButtonImage; 95bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov 96bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov /** 97bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov * The maximal width of the list popup. 98bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov */ 99bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov private final int mListPopupMaxWidth; 100bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov 10151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 10251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Observer for the model data. 103414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov */ 104414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov private final DataSetObserver mModelDataSetOberver = new DataSetObserver() { 105414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov 106414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov @Override 107414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov public void onChanged() { 10876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov super.onChanged(); 10951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mAdapter.notifyDataSetChanged(); 11076559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 11151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov @Override 11276559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov public void onInvalidated() { 11376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov super.onInvalidated(); 11476559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov mAdapter.notifyDataSetInvalidated(); 11576559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 11676559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov }; 11776559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov 11876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov /** 11976559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov * Popup window for showing the activity overflow list. 12076559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov */ 12176559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov private ListPopupWindow mListPopupWindow; 12276559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov 12351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 1248c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov * Listener for the dismissal of the popup/alert. 1258c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov */ 1268c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov private PopupWindow.OnDismissListener mOnDismissListener; 1278c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov 1288c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov /** 1298c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov * Flag whether a default activity currently being selected. 1308c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov */ 1318c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov private boolean mIsSelectingDefaultActivity; 1328c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov 1338c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov /** 1348c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov * The count of activities in the popup. 1358c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov */ 1368c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov private int mInitialActivityCount = ActivityChooserViewAdapter.MAX_ACTIVITY_COUNT_DEFAULT; 13751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 13851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 13951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Flag whether this view is attached to a window. 14051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 14151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private boolean mIsAttachedToWindow; 14251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 14351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 14451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Create a new instance. 14551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 14651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @param context The application environment. 14751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 14851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public ActivityChooserView(Context context) { 14951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov this(context, null); 15051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 15151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 15251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 15351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Create a new instance. 15451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 15551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @param context The application environment. 15651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @param attrs A collection of attributes. 15751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 15851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public ActivityChooserView(Context context, AttributeSet attrs) { 15951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov this(context, attrs, R.attr.actionButtonStyle); 16051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 16151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 16251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 16351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Create a new instance. 16451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 16551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @param context The application environment. 16651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @param attrs A collection of attributes. 16751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @param defStyle The default style to apply to this view. 16851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 16951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public ActivityChooserView(Context context, AttributeSet attrs, int defStyle) { 17051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov super(context, attrs, defStyle); 17151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 17251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov TypedArray attributesArray = context.obtainStyledAttributes(attrs, 17351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov R.styleable.ActivityChooserView, defStyle, 0); 17451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 17551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mInitialActivityCount = attributesArray.getInt( 17651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov R.styleable.ActivityChooserView_initialActivityCount, 17751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov ActivityChooserViewAdapter.MAX_ACTIVITY_COUNT_DEFAULT); 17823f4cc0353615107cc9c19fda9cf96ddd43266e2Adam Powell 17951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov Drawable expandActivityOverflowButtonDrawable = attributesArray.getDrawable( 18051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov R.styleable.ActivityChooserView_expandActivityOverflowButtonDrawable); 18151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 18251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov LayoutInflater inflater = LayoutInflater.from(mContext); 18351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov inflater.inflate(R.layout.activity_chooser_view, this, true); 18451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 18551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mCallbacks = new Callbacks(); 18651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 18751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mActivityChooserContent = (LinearLayout) findViewById(R.id.activity_chooser_view_content); 18851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 18951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mDefaultActivityButton = (FrameLayout) findViewById(R.id.default_activity_button); 19051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mDefaultActivityButton.setOnClickListener(mCallbacks); 19151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mDefaultActivityButton.setOnLongClickListener(mCallbacks); 19251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mDefaultActivityButtonImage = (ImageView) mDefaultActivityButton.findViewById(R.id.image); 19351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 19451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mExpandActivityOverflowButton = (FrameLayout) findViewById(R.id.expand_activities_button); 19551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mExpandActivityOverflowButton.setOnClickListener(mCallbacks); 19651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mExpandActivityOverflowButtonImage = 19751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov (ImageView) mExpandActivityOverflowButton.findViewById(R.id.image); 19851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mExpandActivityOverflowButtonImage.setImageDrawable(expandActivityOverflowButtonDrawable); 19951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 20051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mAdapter = new ActivityChooserViewAdapter(); 201f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov mAdapter.registerDataSetObserver(new DataSetObserver() { 202f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov @Override 20376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov public void onChanged() { 20451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov super.onChanged(); 20551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov updateButtons(); 20651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 20751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov }); 20851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 209f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov Resources resources = context.getResources(); 21051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mListPopupMaxWidth = Math.max(resources.getDisplayMetrics().widthPixels / 2, 211bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov resources.getDimensionPixelSize(com.android.internal.R.dimen.config_prefDialogWidth)); 212bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov } 213bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov 214bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov /** 21551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * {@inheritDoc} 216bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov */ 21751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public void setActivityChooserModel(ActivityChooserModel dataModel) { 218bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov mAdapter.setDataModel(dataModel); 219bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov if (isShowingPopup()) { 220bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov dismissPopup(); 22151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov showPopup(); 22251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 22351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 22451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 22551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 22651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Sets the background for the button that expands the activity 227f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov * overflow list. 22851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 22951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * <strong>Note:</strong> Clients would like to set this drawable 230414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov * as a clue about the action the chosen activity will perform. For 231414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov * example, if share activity is to be chosen the drawable should 232414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov * give a clue that sharing is to be performed. 233414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov * 23451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @param drawable The drawable. 23551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 23651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public void setExpandActivityOverflowButtonDrawable(Drawable drawable) { 23751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mExpandActivityOverflowButtonImage.setImageDrawable(drawable); 23851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 23951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 24051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 24151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Shows the popup window with activities. 24251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 24351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @return True if the popup was shown, false if already showing. 24451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 24551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public boolean showPopup() { 24651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (isShowingPopup() || !mIsAttachedToWindow) { 24751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return false; 24851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 24951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mIsSelectingDefaultActivity = false; 25051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov showPopupUnchecked(mInitialActivityCount); 25151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return true; 25251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 25351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 25451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 25551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Shows the popup no matter if it was already showing. 25651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 25751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @param maxActivityCount The max number of activities to display. 25851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 259bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov private void showPopupUnchecked(int maxActivityCount) { 26051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (mAdapter.getDataModel() == null) { 26151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov throw new IllegalStateException("No data model. Did you call #setDataModel?"); 26251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 26351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 26451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mAdapter.setMaxActivityCount(maxActivityCount); 26551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 26651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov final int activityCount = mAdapter.getActivityCount(); 26751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (maxActivityCount != ActivityChooserViewAdapter.MAX_ACTIVITY_COUNT_UNLIMITED 26876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov && activityCount > maxActivityCount + 1) { 26951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mAdapter.setShowFooterView(true); 27051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } else { 27151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mAdapter.setShowFooterView(false); 27251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 27351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 27451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov ListPopupWindow popupWindow = getListPopupWindow(); 27551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (!popupWindow.isShowing()) { 27651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (mIsSelectingDefaultActivity) { 27751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mAdapter.setShowDefaultActivity(true); 27851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } else { 27951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mAdapter.setShowDefaultActivity(false); 28051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 28151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov final int contentWidth = Math.min(mAdapter.measureContentWidth(), mListPopupMaxWidth); 28276559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov popupWindow.setContentWidth(contentWidth); 28376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov popupWindow.show(); 28451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 28551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 2868c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov 2878c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov /** 28876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov * Dismisses the popup window with activities. 28976559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov * 290f632eaa9d64fb21892cc057ec7444ec157686734Svetoslav Ganov * @return True if dismissed, false if already dismissed. 291f632eaa9d64fb21892cc057ec7444ec157686734Svetoslav Ganov */ 292f632eaa9d64fb21892cc057ec7444ec157686734Svetoslav Ganov public boolean dismissPopup() { 29376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov if (isShowingPopup()) { 294f632eaa9d64fb21892cc057ec7444ec157686734Svetoslav Ganov getListPopupWindow().dismiss(); 29576559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 296f632eaa9d64fb21892cc057ec7444ec157686734Svetoslav Ganov return true; 29776559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 29851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 29976559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov /** 30051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Gets whether the popup window with activities is shown. 30151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 30276559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov * @return True if the popup is shown. 30376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov */ 304efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov public boolean isShowingPopup() { 305efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov return getListPopupWindow().isShowing(); 30676559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 307efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov 30851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov @Override 309414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov protected void onAttachedToWindow() { 310414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov super.onAttachedToWindow(); 31176559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov ActivityChooserModel dataModel = mAdapter.getDataModel(); 31251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (dataModel != null) { 31351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov dataModel.registerObserver(mModelDataSetOberver); 31451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 31551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mIsAttachedToWindow = true; 31651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 31751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 31851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov @Override 31951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov protected void onDetachedFromWindow() { 32051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov super.onDetachedFromWindow(); 32176559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov ActivityChooserModel dataModel = mAdapter.getDataModel(); 32251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (dataModel != null) { 3238c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov dataModel.unregisterObserver(mModelDataSetOberver); 3248c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov } 3258c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov mIsAttachedToWindow = false; 3268c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov } 32751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 32851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov @Override 32951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 33051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mActivityChooserContent.measure(widthMeasureSpec, heightMeasureSpec); 33151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov setMeasuredDimension(mActivityChooserContent.getMeasuredWidth(), 33251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mActivityChooserContent.getMeasuredHeight()); 33351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 33451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 33551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov @Override 33651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov protected void onLayout(boolean changed, int left, int top, int right, int bottom) { 33776559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov mActivityChooserContent.layout(0, 0, right - left, bottom - top); 33851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (getListPopupWindow().isShowing()) { 33951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov showPopupUnchecked(mAdapter.getMaxActivityCount()); 34051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } else { 34151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov dismissPopup(); 34251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 34351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 34451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 34576559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov @Override 34651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov protected void onDraw(Canvas canvas) { 34751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mActivityChooserContent.onDraw(canvas); 34851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 34951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 35051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public ActivityChooserModel getDataModel() { 35151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return mAdapter.getDataModel(); 35251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 35351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 35451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 35576559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov * Sets a listener to receive a callback when the popup is dismissed. 35651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 3578c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov * @param listener The listener to be notified. 3588c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov */ 3598c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov public void setOnDismissListener(PopupWindow.OnDismissListener listener) { 3608c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov mOnDismissListener = listener; 36151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 36251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 36351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 36451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Sets the initial count of items shown in the activities popup 36551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * i.e. the items before the popup is expanded. This is an upper 366f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov * bound since it is not guaranteed that such number of intent 367f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov * handlers exist. 368f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov * 369f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov * @param itemCount The initial popup item count. 370f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov */ 371f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov public void setInitialActivityCount(int itemCount) { 372f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov mInitialActivityCount = itemCount; 373f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov } 374f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov 375f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov /** 37651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Gets the list popup window which is lazily initialized. 37751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * 37851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * @return The popup. 37951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 38076559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov private ListPopupWindow getListPopupWindow() { 38176559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov if (mListPopupWindow == null) { 38276559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov mListPopupWindow = new ListPopupWindow(getContext()); 38376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov mListPopupWindow.setAdapter(mAdapter); 38476559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov mListPopupWindow.setAnchorView(ActivityChooserView.this); 38551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mListPopupWindow.setModal(true); 38651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mListPopupWindow.setOnItemClickListener(mCallbacks); 38751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mListPopupWindow.setOnDismissListener(mCallbacks); 38851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 38951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return mListPopupWindow; 39051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 39151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 39251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 39351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Updates the buttons state. 39451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 39551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private void updateButtons() { 39651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov final int activityCount = mAdapter.getActivityCount(); 39751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (activityCount > 0) { 39851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mDefaultActivityButton.setVisibility(VISIBLE); 39951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (mAdapter.getCount() > 0) { 40051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mExpandActivityOverflowButton.setEnabled(true); 40151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } else { 40251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mExpandActivityOverflowButton.setEnabled(false); 40351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 40451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov ResolveInfo activity = mAdapter.getDefaultActivity(); 40551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov PackageManager packageManager = mContext.getPackageManager(); 40651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mDefaultActivityButtonImage.setImageDrawable(activity.loadIcon(packageManager)); 40751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } else { 40851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mDefaultActivityButton.setVisibility(View.INVISIBLE); 40951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mExpandActivityOverflowButton.setEnabled(false); 41051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 41151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 41251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 41351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov /** 41451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Interface implementation to avoid publishing them in the APIs. 41551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 41651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private class Callbacks implements AdapterView.OnItemClickListener, 41751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov View.OnClickListener, View.OnLongClickListener, PopupWindow.OnDismissListener { 41851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 41951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov // AdapterView#OnItemClickListener 42051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public void onItemClick(AdapterView<?> parent, View view, int position, long id) { 42151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov ActivityChooserViewAdapter adapter = (ActivityChooserViewAdapter) parent.getAdapter(); 42251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov final int itemViewType = adapter.getItemViewType(position); 42351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov switch (itemViewType) { 42451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov case ActivityChooserViewAdapter.ITEM_VIEW_TYPE_FOOTER: { 42551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov showPopupUnchecked(ActivityChooserViewAdapter.MAX_ACTIVITY_COUNT_UNLIMITED); 42651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } break; 42751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov case ActivityChooserViewAdapter.ITEM_VIEW_TYPE_ACTIVITY: { 42851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov dismissPopup(); 42951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (mIsSelectingDefaultActivity) { 43051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov // The item at position zero is the default already. 43151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (position > 0) { 43251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mAdapter.getDataModel().setDefaultActivity(position); 433f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov } 434f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov } else { 435f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov // The first item in the model is default action => adjust index 436f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov Intent launchIntent = mAdapter.getDataModel().chooseActivity(position + 1); 437f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov mContext.startActivity(launchIntent); 438f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov } 439f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov } break; 440f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov default: 44151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov throw new IllegalArgumentException(); 442f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov } 443f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov } 444bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov 44551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov // View.OnClickListener 44651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public void onClick(View view) { 447bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov if (view == mDefaultActivityButton) { 44851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov dismissPopup(); 449f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov ResolveInfo defaultActivity = mAdapter.getDefaultActivity(); 450f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov final int index = mAdapter.getDataModel().getActivityIndex(defaultActivity); 451f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov Intent launchIntent = mAdapter.getDataModel().chooseActivity(index); 452f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov mContext.startActivity(launchIntent); 453f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov } else if (view == mExpandActivityOverflowButton) { 454f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov mIsSelectingDefaultActivity = false; 455f2e754002166b8126e6faf8c494da5835432d572Svetoslav Ganov showPopupUnchecked(mInitialActivityCount); 45651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } else { 45751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov throw new IllegalArgumentException(); 45851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 45951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 46051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 46151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov // OnLongClickListener#onLongClick 46251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov @Override 46376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov public boolean onLongClick(View view) { 46451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (view == mDefaultActivityButton) { 46551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (mAdapter.getCount() > 0) { 46651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mIsSelectingDefaultActivity = true; 46751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov showPopupUnchecked(mInitialActivityCount); 46851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 46951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } else { 47051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov throw new IllegalArgumentException(); 47151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 47251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return true; 47351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 47451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 47551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov // PopUpWindow.OnDismissListener#onDismiss 47676559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov public void onDismiss() { 47776559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov notifyOnDismissListener(); 47876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 47976559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov 48051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private void notifyOnDismissListener() { 481efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov if (mOnDismissListener != null) { 482efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov mOnDismissListener.onDismiss(); 483efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov } 484efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov } 4858c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov } 4868c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov 4878c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov /** 48851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov * Adapter for backing the list of activities shown in the popup. 48951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov */ 49051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private class ActivityChooserViewAdapter extends BaseAdapter { 49151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 49251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public static final int MAX_ACTIVITY_COUNT_UNLIMITED = Integer.MAX_VALUE; 49351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 49451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public static final int MAX_ACTIVITY_COUNT_DEFAULT = 4; 49551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 49651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private static final int ITEM_VIEW_TYPE_ACTIVITY = 0; 497bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov 49851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private static final int ITEM_VIEW_TYPE_FOOTER = 1; 49951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 50051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private static final int ITEM_VIEW_TYPE_COUNT = 3; 50151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 5028c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov private ActivityChooserModel mDataModel; 5038c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov 5048c6c79f0909ceabeb8abe1013648c31c7582b7adSvetoslav Ganov private int mMaxActivityCount = MAX_ACTIVITY_COUNT_DEFAULT; 50551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 50651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private boolean mShowDefaultActivity; 50751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 50851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov private boolean mShowFooterView; 50951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 51051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public void setDataModel(ActivityChooserModel dataModel) { 51151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov ActivityChooserModel oldDataModel = mAdapter.getDataModel(); 51251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (oldDataModel != null && isShown()) { 51351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov oldDataModel.unregisterObserver(mModelDataSetOberver); 51451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 51551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mDataModel = dataModel; 516bfbbcf5677d4a5f8c8f938e4c8a8f86d3c7d74c2Svetoslav Ganov if (dataModel != null && isShown()) { 51751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov dataModel.registerObserver(mModelDataSetOberver); 51851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 51951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov notifyDataSetChanged(); 52051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 52151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 52251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov @Override 52351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public int getItemViewType(int position) { 52451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (mShowFooterView && position == getCount() - 1) { 52551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return ITEM_VIEW_TYPE_FOOTER; 52651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } else { 52751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return ITEM_VIEW_TYPE_ACTIVITY; 52851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 52951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 53051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 53151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov @Override 53251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public int getViewTypeCount() { 53351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return ITEM_VIEW_TYPE_COUNT; 53451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 53551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 53651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public int getCount() { 53751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov int count = 0; 53851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov int activityCount = mDataModel.getActivityCount(); 53951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (!mShowDefaultActivity && mDataModel.getDefaultActivity() != null) { 54051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov activityCount--; 54151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 54251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov count = Math.min(activityCount, mMaxActivityCount); 54351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (mShowFooterView) { 54451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov count++; 54551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 54651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return count; 54751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 54876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov 54951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public Object getItem(int position) { 55076559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov final int itemViewType = getItemViewType(position); 55151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov switch (itemViewType) { 55251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov case ITEM_VIEW_TYPE_FOOTER: 55351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return null; 55451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov case ITEM_VIEW_TYPE_ACTIVITY: 55551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (!mShowDefaultActivity && mDataModel.getDefaultActivity() != null) { 55651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov position++; 55751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 55876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov return mDataModel.getActivity(position); 55951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov default: 560efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov throw new IllegalArgumentException(); 561efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov } 56276559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 56351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 56451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public long getItemId(int position) { 56576559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov return position; 56676559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 56776559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov 56876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov public View getView(int position, View convertView, ViewGroup parent) { 56951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov final int itemViewType = getItemViewType(position); 57076559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov switch (itemViewType) { 57176559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov case ITEM_VIEW_TYPE_FOOTER: 57251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (convertView == null || convertView.getId() != ITEM_VIEW_TYPE_FOOTER) { 57376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov convertView = LayoutInflater.from(getContext()).inflate( 57451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov R.layout.activity_chooser_view_list_item, parent, false); 57551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov convertView.setId(ITEM_VIEW_TYPE_FOOTER); 57651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov TextView titleView = (TextView) convertView.findViewById(R.id.title); 57751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov titleView.setText(mContext.getString( 57876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov R.string.activity_chooser_view_see_all)); 57951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 58051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return convertView; 58151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov case ITEM_VIEW_TYPE_ACTIVITY: 58251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (convertView == null || convertView.getId() != R.id.list_item) { 58351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov convertView = LayoutInflater.from(getContext()).inflate( 58451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov R.layout.activity_chooser_view_list_item, parent, false); 58551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 58651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov PackageManager packageManager = mContext.getPackageManager(); 58751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov // Set the icon 58851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov ImageView iconView = (ImageView) convertView.findViewById(R.id.icon); 58951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov ResolveInfo activity = (ResolveInfo) getItem(position); 59051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov iconView.setImageDrawable(activity.loadIcon(packageManager)); 59151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov // Set the title. 59251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov TextView titleView = (TextView) convertView.findViewById(R.id.title); 59376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov titleView.setText(activity.loadLabel(packageManager)); 59451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov // Highlight the default. 59551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (mShowDefaultActivity && position == 0) { 59651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov convertView.setActivated(true); 59776559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } else { 59851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov convertView.setActivated(false); 59951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 60051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return convertView; 60151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov default: 60251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov throw new IllegalArgumentException(); 60351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 60451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 60551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 60651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public int measureContentWidth() { 60776559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov // The user may have specified some of the target not to be shown but we 60851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov // want to measure all of them since after expansion they should fit. 60976559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov final int oldMaxActivityCount = mMaxActivityCount; 61076559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov mMaxActivityCount = MAX_ACTIVITY_COUNT_UNLIMITED; 61151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 61276559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov int contentWidth = 0; 61351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov View itemView = null; 61451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 61551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov final int widthMeasureSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED); 61651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov final int heightMeasureSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED); 61751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov final int count = getCount(); 61851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 61951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov for (int i = 0; i < count; i++) { 62051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov itemView = getView(i, itemView, null); 62151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov itemView.measure(widthMeasureSpec, heightMeasureSpec); 62251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov contentWidth = Math.max(contentWidth, itemView.getMeasuredWidth()); 62351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 62451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 62551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mMaxActivityCount = oldMaxActivityCount; 62676559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov 62776559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov return contentWidth; 62876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 62976559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov 63076559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov public void setMaxActivityCount(int maxActivityCount) { 63176559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov if (mMaxActivityCount != maxActivityCount) { 63276559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov mMaxActivityCount = maxActivityCount; 63376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov notifyDataSetChanged(); 63476559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 63551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 63651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 63751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public ResolveInfo getDefaultActivity() { 63851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return mDataModel.getDefaultActivity(); 63951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 64051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 64151ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public void setShowFooterView(boolean showFooterView) { 64251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov if (mShowFooterView != showFooterView) { 64351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mShowFooterView = showFooterView; 644414051b8b1e31b69ca622d68f391245f1989500bSvetoslav Ganov notifyDataSetChanged(); 64551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 64651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 64751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 64876559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov public int getActivityCount() { 649efab4e7f59835cb2ea9fdc42cc8fd9ea3771d261Svetoslav Ganov return mDataModel.getActivityCount(); 65076559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov } 65176559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov 65276559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov public int getMaxActivityCount() { 65376559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov return mMaxActivityCount; 65451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 65551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 65651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public ActivityChooserModel getDataModel() { 65751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov return mDataModel; 65851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 65951ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov 66051ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov public void setShowDefaultActivity(boolean showDefaultActivity) { 66176559a65ad9d644f10beacf8895ceb217fdd0aebSvetoslav Ganov if (mShowDefaultActivity != showDefaultActivity) { 66251ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov mShowDefaultActivity = showDefaultActivity; 66351ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov notifyDataSetChanged(); 66451ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 66551ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 66651ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov } 66751ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov} 66851ac0e94a83cfccb5105aa14df1077729a5b4cccSvetoslav Ganov