MediaRouteButton.java revision fa0c1799716878268ad8705818bb2cbe47338c9d
111417b1cfde8f1749905f2d735623af9214148afJeff Brown/* 211417b1cfde8f1749905f2d735623af9214148afJeff Brown * Copyright (C) 2013 The Android Open Source Project 311417b1cfde8f1749905f2d735623af9214148afJeff Brown * 411417b1cfde8f1749905f2d735623af9214148afJeff Brown * Licensed under the Apache License, Version 2.0 (the "License"); 511417b1cfde8f1749905f2d735623af9214148afJeff Brown * you may not use this file except in compliance with the License. 611417b1cfde8f1749905f2d735623af9214148afJeff Brown * You may obtain a copy of the License at 711417b1cfde8f1749905f2d735623af9214148afJeff Brown * 811417b1cfde8f1749905f2d735623af9214148afJeff Brown * http://www.apache.org/licenses/LICENSE-2.0 911417b1cfde8f1749905f2d735623af9214148afJeff Brown * 1011417b1cfde8f1749905f2d735623af9214148afJeff Brown * Unless required by applicable law or agreed to in writing, software 1111417b1cfde8f1749905f2d735623af9214148afJeff Brown * distributed under the License is distributed on an "AS IS" BASIS, 1211417b1cfde8f1749905f2d735623af9214148afJeff Brown * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1311417b1cfde8f1749905f2d735623af9214148afJeff Brown * See the License for the specific language governing permissions and 1411417b1cfde8f1749905f2d735623af9214148afJeff Brown * limitations under the License. 1511417b1cfde8f1749905f2d735623af9214148afJeff Brown */ 1611417b1cfde8f1749905f2d735623af9214148afJeff Brown 1711417b1cfde8f1749905f2d735623af9214148afJeff Brownpackage android.support.v7.app; 1811417b1cfde8f1749905f2d735623af9214148afJeff Brown 1911417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.app.Activity; 2011417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.content.Context; 2111417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.content.ContextWrapper; 2211417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.content.res.TypedArray; 2311417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.graphics.Canvas; 2411417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.graphics.Rect; 2511417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.graphics.drawable.Drawable; 26429c3b17b88ebd8c4512e9179fd9d48333c0979eTor Norbyeimport android.support.annotation.NonNull; 2711417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.support.v4.app.FragmentActivity; 2811417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.support.v4.app.FragmentManager; 2911417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.support.v4.graphics.drawable.DrawableCompat; 3011417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.support.v4.view.GravityCompat; 3111417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.support.v7.media.MediaRouter; 3211417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.support.v7.media.MediaRouteSelector; 3311417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.support.v7.mediarouter.R; 3411417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.text.TextUtils; 3511417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.util.AttributeSet; 3611417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.util.Log; 3711417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.view.Gravity; 3811417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.view.HapticFeedbackConstants; 3911417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.view.SoundEffectConstants; 4011417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.view.View; 4111417b1cfde8f1749905f2d735623af9214148afJeff Brownimport android.widget.Toast; 4211417b1cfde8f1749905f2d735623af9214148afJeff Brown 4311417b1cfde8f1749905f2d735623af9214148afJeff Brown/** 4411417b1cfde8f1749905f2d735623af9214148afJeff Brown * The media route button allows the user to select routes and to control the 4511417b1cfde8f1749905f2d735623af9214148afJeff Brown * currently selected route. 469942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * <p> 479942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * The application must specify the kinds of routes that the user should be allowed 489942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * to select by specifying a {@link MediaRouteSelector selector} with the 499942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * {@link #setRouteSelector} method. 509942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * </p><p> 519942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * When the default route is selected or when the currently selected route does not 529942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * match the {@link #getRouteSelector() selector}, the button will appear in 539942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * an inactive state indicating that the application is not connected to a 549942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * route of the kind that it wants to use. Clicking on the button opens 559942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * a {@link MediaRouteChooserDialog} to allow the user to select a route. 569942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * If no non-default routes match the selector and it is not possible for an active 579942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * scan to discover any matching routes, then the button is disabled and cannot 589942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * be clicked. 599942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * </p><p> 609942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * When a non-default route is selected that matches the selector, the button will 619942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * appear in an active state indicating that the application is connected 629942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * to a route of the kind that it wants to use. The button may also appear 639942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * in an intermediary connecting state if the route is in the process of connecting 649942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * to the destination but has not yet completed doing so. In either case, clicking 659942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * on the button opens a {@link MediaRouteControllerDialog} to allow the user 669942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * to control or disconnect from the current route. 679942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * </p> 6811417b1cfde8f1749905f2d735623af9214148afJeff Brown * 6911417b1cfde8f1749905f2d735623af9214148afJeff Brown * <h3>Prerequisites</h3> 7011417b1cfde8f1749905f2d735623af9214148afJeff Brown * <p> 7111417b1cfde8f1749905f2d735623af9214148afJeff Brown * To use the media route button, the activity must be a subclass of 7211417b1cfde8f1749905f2d735623af9214148afJeff Brown * {@link FragmentActivity} from the <code>android.support.v4</code> 7311417b1cfde8f1749905f2d735623af9214148afJeff Brown * support library. Refer to support library documentation for details. 7411417b1cfde8f1749905f2d735623af9214148afJeff Brown * </p> 7511417b1cfde8f1749905f2d735623af9214148afJeff Brown * 7611417b1cfde8f1749905f2d735623af9214148afJeff Brown * @see MediaRouteActionProvider 7711417b1cfde8f1749905f2d735623af9214148afJeff Brown * @see #setRouteSelector 7811417b1cfde8f1749905f2d735623af9214148afJeff Brown */ 7911417b1cfde8f1749905f2d735623af9214148afJeff Brownpublic class MediaRouteButton extends View { 8011417b1cfde8f1749905f2d735623af9214148afJeff Brown private static final String TAG = "MediaRouteButton"; 8111417b1cfde8f1749905f2d735623af9214148afJeff Brown 8211417b1cfde8f1749905f2d735623af9214148afJeff Brown private static final String CHOOSER_FRAGMENT_TAG = 8311417b1cfde8f1749905f2d735623af9214148afJeff Brown "android.support.v7.mediarouter:MediaRouteChooserDialogFragment"; 8411417b1cfde8f1749905f2d735623af9214148afJeff Brown private static final String CONTROLLER_FRAGMENT_TAG = 8511417b1cfde8f1749905f2d735623af9214148afJeff Brown "android.support.v7.mediarouter:MediaRouteControllerDialogFragment"; 8611417b1cfde8f1749905f2d735623af9214148afJeff Brown 8711417b1cfde8f1749905f2d735623af9214148afJeff Brown private final MediaRouter mRouter; 8811417b1cfde8f1749905f2d735623af9214148afJeff Brown private final MediaRouterCallback mCallback; 8911417b1cfde8f1749905f2d735623af9214148afJeff Brown 9011417b1cfde8f1749905f2d735623af9214148afJeff Brown private MediaRouteSelector mSelector = MediaRouteSelector.EMPTY; 91eff7719415542ba819054863b0995f07742a7a8aJeff Brown private MediaRouteDialogFactory mDialogFactory = MediaRouteDialogFactory.getDefault(); 9211417b1cfde8f1749905f2d735623af9214148afJeff Brown 9311417b1cfde8f1749905f2d735623af9214148afJeff Brown private boolean mAttachedToWindow; 9411417b1cfde8f1749905f2d735623af9214148afJeff Brown 9511417b1cfde8f1749905f2d735623af9214148afJeff Brown private Drawable mRemoteIndicator; 9611417b1cfde8f1749905f2d735623af9214148afJeff Brown private boolean mRemoteActive; 9711417b1cfde8f1749905f2d735623af9214148afJeff Brown private boolean mCheatSheetEnabled; 9811417b1cfde8f1749905f2d735623af9214148afJeff Brown private boolean mIsConnecting; 9911417b1cfde8f1749905f2d735623af9214148afJeff Brown 10011417b1cfde8f1749905f2d735623af9214148afJeff Brown private int mMinWidth; 10111417b1cfde8f1749905f2d735623af9214148afJeff Brown private int mMinHeight; 10211417b1cfde8f1749905f2d735623af9214148afJeff Brown 10311417b1cfde8f1749905f2d735623af9214148afJeff Brown // The checked state is used when connected to a remote route. 10411417b1cfde8f1749905f2d735623af9214148afJeff Brown private static final int[] CHECKED_STATE_SET = { 10511417b1cfde8f1749905f2d735623af9214148afJeff Brown android.R.attr.state_checked 10611417b1cfde8f1749905f2d735623af9214148afJeff Brown }; 10711417b1cfde8f1749905f2d735623af9214148afJeff Brown 10811417b1cfde8f1749905f2d735623af9214148afJeff Brown // The checkable state is used while connecting to a remote route. 10911417b1cfde8f1749905f2d735623af9214148afJeff Brown private static final int[] CHECKABLE_STATE_SET = { 11011417b1cfde8f1749905f2d735623af9214148afJeff Brown android.R.attr.state_checkable 11111417b1cfde8f1749905f2d735623af9214148afJeff Brown }; 11211417b1cfde8f1749905f2d735623af9214148afJeff Brown 11311417b1cfde8f1749905f2d735623af9214148afJeff Brown public MediaRouteButton(Context context) { 11411417b1cfde8f1749905f2d735623af9214148afJeff Brown this(context, null); 11511417b1cfde8f1749905f2d735623af9214148afJeff Brown } 11611417b1cfde8f1749905f2d735623af9214148afJeff Brown 11711417b1cfde8f1749905f2d735623af9214148afJeff Brown public MediaRouteButton(Context context, AttributeSet attrs) { 11811417b1cfde8f1749905f2d735623af9214148afJeff Brown this(context, attrs, R.attr.mediaRouteButtonStyle); 11911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 12011417b1cfde8f1749905f2d735623af9214148afJeff Brown 12111417b1cfde8f1749905f2d735623af9214148afJeff Brown public MediaRouteButton(Context context, AttributeSet attrs, int defStyleAttr) { 12294be6100218126ce6a08bf1f56209578500b361fRoboErik super(MediaRouterThemeHelper.createThemedContext(context), attrs, defStyleAttr); 12311417b1cfde8f1749905f2d735623af9214148afJeff Brown context = getContext(); 12411417b1cfde8f1749905f2d735623af9214148afJeff Brown 12511417b1cfde8f1749905f2d735623af9214148afJeff Brown mRouter = MediaRouter.getInstance(context); 12611417b1cfde8f1749905f2d735623af9214148afJeff Brown mCallback = new MediaRouterCallback(); 12711417b1cfde8f1749905f2d735623af9214148afJeff Brown 12811417b1cfde8f1749905f2d735623af9214148afJeff Brown TypedArray a = context.obtainStyledAttributes(attrs, 12911417b1cfde8f1749905f2d735623af9214148afJeff Brown R.styleable.MediaRouteButton, defStyleAttr, 0); 13011417b1cfde8f1749905f2d735623af9214148afJeff Brown setRemoteIndicatorDrawable(a.getDrawable( 13111417b1cfde8f1749905f2d735623af9214148afJeff Brown R.styleable.MediaRouteButton_externalRouteEnabledDrawable)); 13211417b1cfde8f1749905f2d735623af9214148afJeff Brown mMinWidth = a.getDimensionPixelSize( 13311417b1cfde8f1749905f2d735623af9214148afJeff Brown R.styleable.MediaRouteButton_android_minWidth, 0); 13411417b1cfde8f1749905f2d735623af9214148afJeff Brown mMinHeight = a.getDimensionPixelSize( 13511417b1cfde8f1749905f2d735623af9214148afJeff Brown R.styleable.MediaRouteButton_android_minHeight, 0); 13611417b1cfde8f1749905f2d735623af9214148afJeff Brown a.recycle(); 13711417b1cfde8f1749905f2d735623af9214148afJeff Brown 13811417b1cfde8f1749905f2d735623af9214148afJeff Brown setClickable(true); 13911417b1cfde8f1749905f2d735623af9214148afJeff Brown setLongClickable(true); 14011417b1cfde8f1749905f2d735623af9214148afJeff Brown } 14111417b1cfde8f1749905f2d735623af9214148afJeff Brown 14211417b1cfde8f1749905f2d735623af9214148afJeff Brown /** 14311417b1cfde8f1749905f2d735623af9214148afJeff Brown * Gets the media route selector for filtering the routes that the user can 14411417b1cfde8f1749905f2d735623af9214148afJeff Brown * select using the media route chooser dialog. 14511417b1cfde8f1749905f2d735623af9214148afJeff Brown * 14611417b1cfde8f1749905f2d735623af9214148afJeff Brown * @return The selector, never null. 14711417b1cfde8f1749905f2d735623af9214148afJeff Brown */ 148429c3b17b88ebd8c4512e9179fd9d48333c0979eTor Norbye @NonNull 14911417b1cfde8f1749905f2d735623af9214148afJeff Brown public MediaRouteSelector getRouteSelector() { 15011417b1cfde8f1749905f2d735623af9214148afJeff Brown return mSelector; 15111417b1cfde8f1749905f2d735623af9214148afJeff Brown } 15211417b1cfde8f1749905f2d735623af9214148afJeff Brown 15311417b1cfde8f1749905f2d735623af9214148afJeff Brown /** 15411417b1cfde8f1749905f2d735623af9214148afJeff Brown * Sets the media route selector for filtering the routes that the user can 15511417b1cfde8f1749905f2d735623af9214148afJeff Brown * select using the media route chooser dialog. 15611417b1cfde8f1749905f2d735623af9214148afJeff Brown * 15711417b1cfde8f1749905f2d735623af9214148afJeff Brown * @param selector The selector, must not be null. 15811417b1cfde8f1749905f2d735623af9214148afJeff Brown */ 15911417b1cfde8f1749905f2d735623af9214148afJeff Brown public void setRouteSelector(MediaRouteSelector selector) { 16011417b1cfde8f1749905f2d735623af9214148afJeff Brown if (selector == null) { 16111417b1cfde8f1749905f2d735623af9214148afJeff Brown throw new IllegalArgumentException("selector must not be null"); 16211417b1cfde8f1749905f2d735623af9214148afJeff Brown } 16311417b1cfde8f1749905f2d735623af9214148afJeff Brown 16411417b1cfde8f1749905f2d735623af9214148afJeff Brown if (!mSelector.equals(selector)) { 16511417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mAttachedToWindow) { 1669942d40d0d952b03b583fe66f434676793697aa2Jeff Brown if (!mSelector.isEmpty()) { 1679942d40d0d952b03b583fe66f434676793697aa2Jeff Brown mRouter.removeCallback(mCallback); 1689942d40d0d952b03b583fe66f434676793697aa2Jeff Brown } 1699942d40d0d952b03b583fe66f434676793697aa2Jeff Brown if (!selector.isEmpty()) { 1709942d40d0d952b03b583fe66f434676793697aa2Jeff Brown mRouter.addCallback(selector, mCallback); 1719942d40d0d952b03b583fe66f434676793697aa2Jeff Brown } 17211417b1cfde8f1749905f2d735623af9214148afJeff Brown } 1739942d40d0d952b03b583fe66f434676793697aa2Jeff Brown mSelector = selector; 17411417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshRoute(); 17511417b1cfde8f1749905f2d735623af9214148afJeff Brown } 17611417b1cfde8f1749905f2d735623af9214148afJeff Brown } 17711417b1cfde8f1749905f2d735623af9214148afJeff Brown 17811417b1cfde8f1749905f2d735623af9214148afJeff Brown /** 179eff7719415542ba819054863b0995f07742a7a8aJeff Brown * Gets the media route dialog factory to use when showing the route chooser 180eff7719415542ba819054863b0995f07742a7a8aJeff Brown * or controller dialog. 181eff7719415542ba819054863b0995f07742a7a8aJeff Brown * 182eff7719415542ba819054863b0995f07742a7a8aJeff Brown * @return The dialog factory, never null. 183eff7719415542ba819054863b0995f07742a7a8aJeff Brown */ 184429c3b17b88ebd8c4512e9179fd9d48333c0979eTor Norbye @NonNull 185eff7719415542ba819054863b0995f07742a7a8aJeff Brown public MediaRouteDialogFactory getDialogFactory() { 186eff7719415542ba819054863b0995f07742a7a8aJeff Brown return mDialogFactory; 187eff7719415542ba819054863b0995f07742a7a8aJeff Brown } 188eff7719415542ba819054863b0995f07742a7a8aJeff Brown 189eff7719415542ba819054863b0995f07742a7a8aJeff Brown /** 190eff7719415542ba819054863b0995f07742a7a8aJeff Brown * Sets the media route dialog factory to use when showing the route chooser 191eff7719415542ba819054863b0995f07742a7a8aJeff Brown * or controller dialog. 192eff7719415542ba819054863b0995f07742a7a8aJeff Brown * 193eff7719415542ba819054863b0995f07742a7a8aJeff Brown * @param factory The dialog factory, must not be null. 194eff7719415542ba819054863b0995f07742a7a8aJeff Brown */ 195429c3b17b88ebd8c4512e9179fd9d48333c0979eTor Norbye public void setDialogFactory(@NonNull MediaRouteDialogFactory factory) { 196eff7719415542ba819054863b0995f07742a7a8aJeff Brown if (factory == null) { 197eff7719415542ba819054863b0995f07742a7a8aJeff Brown throw new IllegalArgumentException("factory must not be null"); 198eff7719415542ba819054863b0995f07742a7a8aJeff Brown } 199eff7719415542ba819054863b0995f07742a7a8aJeff Brown 200eff7719415542ba819054863b0995f07742a7a8aJeff Brown mDialogFactory = factory; 201eff7719415542ba819054863b0995f07742a7a8aJeff Brown } 202eff7719415542ba819054863b0995f07742a7a8aJeff Brown 203eff7719415542ba819054863b0995f07742a7a8aJeff Brown /** 20411417b1cfde8f1749905f2d735623af9214148afJeff Brown * Show the route chooser or controller dialog. 20511417b1cfde8f1749905f2d735623af9214148afJeff Brown * <p> 2069942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * If the default route is selected or if the currently selected route does 2079942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * not match the {@link #getRouteSelector selector}, then shows the route chooser dialog. 2089942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * Otherwise, shows the route controller dialog to offer the user 20911417b1cfde8f1749905f2d735623af9214148afJeff Brown * a choice to disconnect from the route or perform other control actions 21011417b1cfde8f1749905f2d735623af9214148afJeff Brown * such as setting the route's volume. 2119942d40d0d952b03b583fe66f434676793697aa2Jeff Brown * </p><p> 212eff7719415542ba819054863b0995f07742a7a8aJeff Brown * The application can customize the dialogs by calling {@link #setDialogFactory} 213eff7719415542ba819054863b0995f07742a7a8aJeff Brown * to provide a customized dialog factory. 21411417b1cfde8f1749905f2d735623af9214148afJeff Brown * </p> 21511417b1cfde8f1749905f2d735623af9214148afJeff Brown * 21611417b1cfde8f1749905f2d735623af9214148afJeff Brown * @return True if the dialog was actually shown. 21711417b1cfde8f1749905f2d735623af9214148afJeff Brown * 21811417b1cfde8f1749905f2d735623af9214148afJeff Brown * @throws IllegalStateException if the activity is not a subclass of 21911417b1cfde8f1749905f2d735623af9214148afJeff Brown * {@link FragmentActivity}. 22011417b1cfde8f1749905f2d735623af9214148afJeff Brown */ 22111417b1cfde8f1749905f2d735623af9214148afJeff Brown public boolean showDialog() { 22211417b1cfde8f1749905f2d735623af9214148afJeff Brown if (!mAttachedToWindow) { 22311417b1cfde8f1749905f2d735623af9214148afJeff Brown return false; 22411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 22511417b1cfde8f1749905f2d735623af9214148afJeff Brown 22611417b1cfde8f1749905f2d735623af9214148afJeff Brown final FragmentManager fm = getFragmentManager(); 22711417b1cfde8f1749905f2d735623af9214148afJeff Brown if (fm == null) { 22811417b1cfde8f1749905f2d735623af9214148afJeff Brown throw new IllegalStateException("The activity must be a subclass of FragmentActivity"); 22911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 23011417b1cfde8f1749905f2d735623af9214148afJeff Brown 2319942d40d0d952b03b583fe66f434676793697aa2Jeff Brown MediaRouter.RouteInfo route = mRouter.getSelectedRoute(); 2329942d40d0d952b03b583fe66f434676793697aa2Jeff Brown if (route.isDefault() || !route.matchesSelector(mSelector)) { 23311417b1cfde8f1749905f2d735623af9214148afJeff Brown if (fm.findFragmentByTag(CHOOSER_FRAGMENT_TAG) != null) { 23411417b1cfde8f1749905f2d735623af9214148afJeff Brown Log.w(TAG, "showDialog(): Route chooser dialog already showing!"); 23511417b1cfde8f1749905f2d735623af9214148afJeff Brown return false; 23611417b1cfde8f1749905f2d735623af9214148afJeff Brown } 237eff7719415542ba819054863b0995f07742a7a8aJeff Brown MediaRouteChooserDialogFragment f = 238eff7719415542ba819054863b0995f07742a7a8aJeff Brown mDialogFactory.onCreateChooserDialogFragment(); 23911417b1cfde8f1749905f2d735623af9214148afJeff Brown f.setRouteSelector(mSelector); 24011417b1cfde8f1749905f2d735623af9214148afJeff Brown f.show(fm, CHOOSER_FRAGMENT_TAG); 24111417b1cfde8f1749905f2d735623af9214148afJeff Brown } else { 24211417b1cfde8f1749905f2d735623af9214148afJeff Brown if (fm.findFragmentByTag(CONTROLLER_FRAGMENT_TAG) != null) { 24311417b1cfde8f1749905f2d735623af9214148afJeff Brown Log.w(TAG, "showDialog(): Route controller dialog already showing!"); 24411417b1cfde8f1749905f2d735623af9214148afJeff Brown return false; 24511417b1cfde8f1749905f2d735623af9214148afJeff Brown } 246eff7719415542ba819054863b0995f07742a7a8aJeff Brown MediaRouteControllerDialogFragment f = 247eff7719415542ba819054863b0995f07742a7a8aJeff Brown mDialogFactory.onCreateControllerDialogFragment(); 24811417b1cfde8f1749905f2d735623af9214148afJeff Brown f.show(fm, CONTROLLER_FRAGMENT_TAG); 24911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 25011417b1cfde8f1749905f2d735623af9214148afJeff Brown return true; 25111417b1cfde8f1749905f2d735623af9214148afJeff Brown } 25211417b1cfde8f1749905f2d735623af9214148afJeff Brown 25311417b1cfde8f1749905f2d735623af9214148afJeff Brown private FragmentManager getFragmentManager() { 25411417b1cfde8f1749905f2d735623af9214148afJeff Brown Activity activity = getActivity(); 25511417b1cfde8f1749905f2d735623af9214148afJeff Brown if (activity instanceof FragmentActivity) { 25611417b1cfde8f1749905f2d735623af9214148afJeff Brown return ((FragmentActivity)activity).getSupportFragmentManager(); 25711417b1cfde8f1749905f2d735623af9214148afJeff Brown } 25811417b1cfde8f1749905f2d735623af9214148afJeff Brown return null; 25911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 26011417b1cfde8f1749905f2d735623af9214148afJeff Brown 26111417b1cfde8f1749905f2d735623af9214148afJeff Brown private Activity getActivity() { 26211417b1cfde8f1749905f2d735623af9214148afJeff Brown // Gross way of unwrapping the Activity so we can get the FragmentManager 26311417b1cfde8f1749905f2d735623af9214148afJeff Brown Context context = getContext(); 26411417b1cfde8f1749905f2d735623af9214148afJeff Brown while (context instanceof ContextWrapper) { 26511417b1cfde8f1749905f2d735623af9214148afJeff Brown if (context instanceof Activity) { 26611417b1cfde8f1749905f2d735623af9214148afJeff Brown return (Activity)context; 26711417b1cfde8f1749905f2d735623af9214148afJeff Brown } 26811417b1cfde8f1749905f2d735623af9214148afJeff Brown context = ((ContextWrapper)context).getBaseContext(); 26911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 27011417b1cfde8f1749905f2d735623af9214148afJeff Brown return null; 27111417b1cfde8f1749905f2d735623af9214148afJeff Brown } 27211417b1cfde8f1749905f2d735623af9214148afJeff Brown 27311417b1cfde8f1749905f2d735623af9214148afJeff Brown /** 27411417b1cfde8f1749905f2d735623af9214148afJeff Brown * Sets whether to enable showing a toast with the content descriptor of the 27511417b1cfde8f1749905f2d735623af9214148afJeff Brown * button when the button is long pressed. 27611417b1cfde8f1749905f2d735623af9214148afJeff Brown */ 27711417b1cfde8f1749905f2d735623af9214148afJeff Brown void setCheatSheetEnabled(boolean enable) { 27811417b1cfde8f1749905f2d735623af9214148afJeff Brown mCheatSheetEnabled = enable; 27911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 28011417b1cfde8f1749905f2d735623af9214148afJeff Brown 28111417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 28211417b1cfde8f1749905f2d735623af9214148afJeff Brown public boolean performClick() { 28311417b1cfde8f1749905f2d735623af9214148afJeff Brown // Send the appropriate accessibility events and call listeners 28411417b1cfde8f1749905f2d735623af9214148afJeff Brown boolean handled = super.performClick(); 28511417b1cfde8f1749905f2d735623af9214148afJeff Brown if (!handled) { 28611417b1cfde8f1749905f2d735623af9214148afJeff Brown playSoundEffect(SoundEffectConstants.CLICK); 28711417b1cfde8f1749905f2d735623af9214148afJeff Brown } 28811417b1cfde8f1749905f2d735623af9214148afJeff Brown return showDialog() || handled; 28911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 29011417b1cfde8f1749905f2d735623af9214148afJeff Brown 29111417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 29211417b1cfde8f1749905f2d735623af9214148afJeff Brown public boolean performLongClick() { 29311417b1cfde8f1749905f2d735623af9214148afJeff Brown if (super.performLongClick()) { 29411417b1cfde8f1749905f2d735623af9214148afJeff Brown return true; 29511417b1cfde8f1749905f2d735623af9214148afJeff Brown } 29611417b1cfde8f1749905f2d735623af9214148afJeff Brown 29711417b1cfde8f1749905f2d735623af9214148afJeff Brown if (!mCheatSheetEnabled) { 29811417b1cfde8f1749905f2d735623af9214148afJeff Brown return false; 29911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 30011417b1cfde8f1749905f2d735623af9214148afJeff Brown 30111417b1cfde8f1749905f2d735623af9214148afJeff Brown final CharSequence contentDesc = getContentDescription(); 30211417b1cfde8f1749905f2d735623af9214148afJeff Brown if (TextUtils.isEmpty(contentDesc)) { 30311417b1cfde8f1749905f2d735623af9214148afJeff Brown // Don't show the cheat sheet if we have no description 30411417b1cfde8f1749905f2d735623af9214148afJeff Brown return false; 30511417b1cfde8f1749905f2d735623af9214148afJeff Brown } 30611417b1cfde8f1749905f2d735623af9214148afJeff Brown 30711417b1cfde8f1749905f2d735623af9214148afJeff Brown final int[] screenPos = new int[2]; 30811417b1cfde8f1749905f2d735623af9214148afJeff Brown final Rect displayFrame = new Rect(); 30911417b1cfde8f1749905f2d735623af9214148afJeff Brown getLocationOnScreen(screenPos); 31011417b1cfde8f1749905f2d735623af9214148afJeff Brown getWindowVisibleDisplayFrame(displayFrame); 31111417b1cfde8f1749905f2d735623af9214148afJeff Brown 31211417b1cfde8f1749905f2d735623af9214148afJeff Brown final Context context = getContext(); 31311417b1cfde8f1749905f2d735623af9214148afJeff Brown final int width = getWidth(); 31411417b1cfde8f1749905f2d735623af9214148afJeff Brown final int height = getHeight(); 31511417b1cfde8f1749905f2d735623af9214148afJeff Brown final int midy = screenPos[1] + height / 2; 31611417b1cfde8f1749905f2d735623af9214148afJeff Brown final int screenWidth = context.getResources().getDisplayMetrics().widthPixels; 31711417b1cfde8f1749905f2d735623af9214148afJeff Brown 31811417b1cfde8f1749905f2d735623af9214148afJeff Brown Toast cheatSheet = Toast.makeText(context, contentDesc, Toast.LENGTH_SHORT); 31911417b1cfde8f1749905f2d735623af9214148afJeff Brown if (midy < displayFrame.height()) { 32011417b1cfde8f1749905f2d735623af9214148afJeff Brown // Show along the top; follow action buttons 32111417b1cfde8f1749905f2d735623af9214148afJeff Brown cheatSheet.setGravity(Gravity.TOP | GravityCompat.END, 32211417b1cfde8f1749905f2d735623af9214148afJeff Brown screenWidth - screenPos[0] - width / 2, height); 32311417b1cfde8f1749905f2d735623af9214148afJeff Brown } else { 32411417b1cfde8f1749905f2d735623af9214148afJeff Brown // Show along the bottom center 32511417b1cfde8f1749905f2d735623af9214148afJeff Brown cheatSheet.setGravity(Gravity.BOTTOM | Gravity.CENTER_HORIZONTAL, 0, height); 32611417b1cfde8f1749905f2d735623af9214148afJeff Brown } 32711417b1cfde8f1749905f2d735623af9214148afJeff Brown cheatSheet.show(); 32811417b1cfde8f1749905f2d735623af9214148afJeff Brown performHapticFeedback(HapticFeedbackConstants.LONG_PRESS); 32911417b1cfde8f1749905f2d735623af9214148afJeff Brown return true; 33011417b1cfde8f1749905f2d735623af9214148afJeff Brown } 33111417b1cfde8f1749905f2d735623af9214148afJeff Brown 33211417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 33311417b1cfde8f1749905f2d735623af9214148afJeff Brown protected int[] onCreateDrawableState(int extraSpace) { 33411417b1cfde8f1749905f2d735623af9214148afJeff Brown final int[] drawableState = super.onCreateDrawableState(extraSpace + 1); 33511417b1cfde8f1749905f2d735623af9214148afJeff Brown 33611417b1cfde8f1749905f2d735623af9214148afJeff Brown // Technically we should be handling this more completely, but these 33711417b1cfde8f1749905f2d735623af9214148afJeff Brown // are implementation details here. Checkable is used to express the connecting 33811417b1cfde8f1749905f2d735623af9214148afJeff Brown // drawable state and it's mutually exclusive with check for the purposes 33911417b1cfde8f1749905f2d735623af9214148afJeff Brown // of state selection here. 34011417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mIsConnecting) { 34111417b1cfde8f1749905f2d735623af9214148afJeff Brown mergeDrawableStates(drawableState, CHECKABLE_STATE_SET); 34211417b1cfde8f1749905f2d735623af9214148afJeff Brown } else if (mRemoteActive) { 34311417b1cfde8f1749905f2d735623af9214148afJeff Brown mergeDrawableStates(drawableState, CHECKED_STATE_SET); 34411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 34511417b1cfde8f1749905f2d735623af9214148afJeff Brown return drawableState; 34611417b1cfde8f1749905f2d735623af9214148afJeff Brown } 34711417b1cfde8f1749905f2d735623af9214148afJeff Brown 34811417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 34911417b1cfde8f1749905f2d735623af9214148afJeff Brown protected void drawableStateChanged() { 35011417b1cfde8f1749905f2d735623af9214148afJeff Brown super.drawableStateChanged(); 35111417b1cfde8f1749905f2d735623af9214148afJeff Brown 35211417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mRemoteIndicator != null) { 35311417b1cfde8f1749905f2d735623af9214148afJeff Brown int[] myDrawableState = getDrawableState(); 35411417b1cfde8f1749905f2d735623af9214148afJeff Brown mRemoteIndicator.setState(myDrawableState); 35511417b1cfde8f1749905f2d735623af9214148afJeff Brown invalidate(); 35611417b1cfde8f1749905f2d735623af9214148afJeff Brown } 35711417b1cfde8f1749905f2d735623af9214148afJeff Brown } 35811417b1cfde8f1749905f2d735623af9214148afJeff Brown 359fa0c1799716878268ad8705818bb2cbe47338c9dP.Y. Laligand /** 360fa0c1799716878268ad8705818bb2cbe47338c9dP.Y. Laligand * Sets a drawable to use as the remote route indicator. 361fa0c1799716878268ad8705818bb2cbe47338c9dP.Y. Laligand */ 362fa0c1799716878268ad8705818bb2cbe47338c9dP.Y. Laligand public void setRemoteIndicatorDrawable(Drawable d) { 36311417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mRemoteIndicator != null) { 36411417b1cfde8f1749905f2d735623af9214148afJeff Brown mRemoteIndicator.setCallback(null); 36511417b1cfde8f1749905f2d735623af9214148afJeff Brown unscheduleDrawable(mRemoteIndicator); 36611417b1cfde8f1749905f2d735623af9214148afJeff Brown } 36711417b1cfde8f1749905f2d735623af9214148afJeff Brown mRemoteIndicator = d; 36811417b1cfde8f1749905f2d735623af9214148afJeff Brown if (d != null) { 36911417b1cfde8f1749905f2d735623af9214148afJeff Brown d.setCallback(this); 37011417b1cfde8f1749905f2d735623af9214148afJeff Brown d.setState(getDrawableState()); 37111417b1cfde8f1749905f2d735623af9214148afJeff Brown d.setVisible(getVisibility() == VISIBLE, false); 37211417b1cfde8f1749905f2d735623af9214148afJeff Brown } 37311417b1cfde8f1749905f2d735623af9214148afJeff Brown 37411417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshDrawableState(); 37511417b1cfde8f1749905f2d735623af9214148afJeff Brown } 37611417b1cfde8f1749905f2d735623af9214148afJeff Brown 37711417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 37811417b1cfde8f1749905f2d735623af9214148afJeff Brown protected boolean verifyDrawable(Drawable who) { 37911417b1cfde8f1749905f2d735623af9214148afJeff Brown return super.verifyDrawable(who) || who == mRemoteIndicator; 38011417b1cfde8f1749905f2d735623af9214148afJeff Brown } 38111417b1cfde8f1749905f2d735623af9214148afJeff Brown 38211417b1cfde8f1749905f2d735623af9214148afJeff Brown //@Override defined in v11 38311417b1cfde8f1749905f2d735623af9214148afJeff Brown public void jumpDrawablesToCurrentState() { 38411417b1cfde8f1749905f2d735623af9214148afJeff Brown // We can't call super to handle the background so we do it ourselves. 38511417b1cfde8f1749905f2d735623af9214148afJeff Brown //super.jumpDrawablesToCurrentState(); 38611417b1cfde8f1749905f2d735623af9214148afJeff Brown if (getBackground() != null) { 38711417b1cfde8f1749905f2d735623af9214148afJeff Brown DrawableCompat.jumpToCurrentState(getBackground()); 38811417b1cfde8f1749905f2d735623af9214148afJeff Brown } 38911417b1cfde8f1749905f2d735623af9214148afJeff Brown 39011417b1cfde8f1749905f2d735623af9214148afJeff Brown // Handle our own remote indicator. 39111417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mRemoteIndicator != null) { 39211417b1cfde8f1749905f2d735623af9214148afJeff Brown DrawableCompat.jumpToCurrentState(mRemoteIndicator); 39311417b1cfde8f1749905f2d735623af9214148afJeff Brown } 39411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 39511417b1cfde8f1749905f2d735623af9214148afJeff Brown 39611417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 39711417b1cfde8f1749905f2d735623af9214148afJeff Brown public void setVisibility(int visibility) { 39811417b1cfde8f1749905f2d735623af9214148afJeff Brown super.setVisibility(visibility); 39911417b1cfde8f1749905f2d735623af9214148afJeff Brown 40011417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mRemoteIndicator != null) { 40111417b1cfde8f1749905f2d735623af9214148afJeff Brown mRemoteIndicator.setVisible(getVisibility() == VISIBLE, false); 40211417b1cfde8f1749905f2d735623af9214148afJeff Brown } 40311417b1cfde8f1749905f2d735623af9214148afJeff Brown } 40411417b1cfde8f1749905f2d735623af9214148afJeff Brown 40511417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 40611417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onAttachedToWindow() { 40711417b1cfde8f1749905f2d735623af9214148afJeff Brown super.onAttachedToWindow(); 40811417b1cfde8f1749905f2d735623af9214148afJeff Brown 40911417b1cfde8f1749905f2d735623af9214148afJeff Brown mAttachedToWindow = true; 4109942d40d0d952b03b583fe66f434676793697aa2Jeff Brown if (!mSelector.isEmpty()) { 4119942d40d0d952b03b583fe66f434676793697aa2Jeff Brown mRouter.addCallback(mSelector, mCallback); 41211417b1cfde8f1749905f2d735623af9214148afJeff Brown } 4139942d40d0d952b03b583fe66f434676793697aa2Jeff Brown refreshRoute(); 41411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 41511417b1cfde8f1749905f2d735623af9214148afJeff Brown 41611417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 41711417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onDetachedFromWindow() { 41811417b1cfde8f1749905f2d735623af9214148afJeff Brown mAttachedToWindow = false; 4199942d40d0d952b03b583fe66f434676793697aa2Jeff Brown if (!mSelector.isEmpty()) { 4209942d40d0d952b03b583fe66f434676793697aa2Jeff Brown mRouter.removeCallback(mCallback); 4219942d40d0d952b03b583fe66f434676793697aa2Jeff Brown } 42211417b1cfde8f1749905f2d735623af9214148afJeff Brown 42311417b1cfde8f1749905f2d735623af9214148afJeff Brown super.onDetachedFromWindow(); 42411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 42511417b1cfde8f1749905f2d735623af9214148afJeff Brown 42611417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 42711417b1cfde8f1749905f2d735623af9214148afJeff Brown protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 42811417b1cfde8f1749905f2d735623af9214148afJeff Brown final int widthSize = MeasureSpec.getSize(widthMeasureSpec); 42911417b1cfde8f1749905f2d735623af9214148afJeff Brown final int heightSize = MeasureSpec.getSize(heightMeasureSpec); 43011417b1cfde8f1749905f2d735623af9214148afJeff Brown final int widthMode = MeasureSpec.getMode(widthMeasureSpec); 43111417b1cfde8f1749905f2d735623af9214148afJeff Brown final int heightMode = MeasureSpec.getMode(heightMeasureSpec); 43211417b1cfde8f1749905f2d735623af9214148afJeff Brown 43311417b1cfde8f1749905f2d735623af9214148afJeff Brown final int minWidth = Math.max(mMinWidth, 43411417b1cfde8f1749905f2d735623af9214148afJeff Brown mRemoteIndicator != null ? mRemoteIndicator.getIntrinsicWidth() : 0); 43511417b1cfde8f1749905f2d735623af9214148afJeff Brown final int minHeight = Math.max(mMinHeight, 43611417b1cfde8f1749905f2d735623af9214148afJeff Brown mRemoteIndicator != null ? mRemoteIndicator.getIntrinsicHeight() : 0); 43711417b1cfde8f1749905f2d735623af9214148afJeff Brown 43811417b1cfde8f1749905f2d735623af9214148afJeff Brown int width; 43911417b1cfde8f1749905f2d735623af9214148afJeff Brown switch (widthMode) { 44011417b1cfde8f1749905f2d735623af9214148afJeff Brown case MeasureSpec.EXACTLY: 44111417b1cfde8f1749905f2d735623af9214148afJeff Brown width = widthSize; 44211417b1cfde8f1749905f2d735623af9214148afJeff Brown break; 44311417b1cfde8f1749905f2d735623af9214148afJeff Brown case MeasureSpec.AT_MOST: 44411417b1cfde8f1749905f2d735623af9214148afJeff Brown width = Math.min(widthSize, minWidth + getPaddingLeft() + getPaddingRight()); 44511417b1cfde8f1749905f2d735623af9214148afJeff Brown break; 44611417b1cfde8f1749905f2d735623af9214148afJeff Brown default: 44711417b1cfde8f1749905f2d735623af9214148afJeff Brown case MeasureSpec.UNSPECIFIED: 44811417b1cfde8f1749905f2d735623af9214148afJeff Brown width = minWidth + getPaddingLeft() + getPaddingRight(); 44911417b1cfde8f1749905f2d735623af9214148afJeff Brown break; 45011417b1cfde8f1749905f2d735623af9214148afJeff Brown } 45111417b1cfde8f1749905f2d735623af9214148afJeff Brown 45211417b1cfde8f1749905f2d735623af9214148afJeff Brown int height; 45311417b1cfde8f1749905f2d735623af9214148afJeff Brown switch (heightMode) { 45411417b1cfde8f1749905f2d735623af9214148afJeff Brown case MeasureSpec.EXACTLY: 45511417b1cfde8f1749905f2d735623af9214148afJeff Brown height = heightSize; 45611417b1cfde8f1749905f2d735623af9214148afJeff Brown break; 45711417b1cfde8f1749905f2d735623af9214148afJeff Brown case MeasureSpec.AT_MOST: 45811417b1cfde8f1749905f2d735623af9214148afJeff Brown height = Math.min(heightSize, minHeight + getPaddingTop() + getPaddingBottom()); 45911417b1cfde8f1749905f2d735623af9214148afJeff Brown break; 46011417b1cfde8f1749905f2d735623af9214148afJeff Brown default: 46111417b1cfde8f1749905f2d735623af9214148afJeff Brown case MeasureSpec.UNSPECIFIED: 46211417b1cfde8f1749905f2d735623af9214148afJeff Brown height = minHeight + getPaddingTop() + getPaddingBottom(); 46311417b1cfde8f1749905f2d735623af9214148afJeff Brown break; 46411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 46511417b1cfde8f1749905f2d735623af9214148afJeff Brown 46611417b1cfde8f1749905f2d735623af9214148afJeff Brown setMeasuredDimension(width, height); 46711417b1cfde8f1749905f2d735623af9214148afJeff Brown } 46811417b1cfde8f1749905f2d735623af9214148afJeff Brown 46911417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 47011417b1cfde8f1749905f2d735623af9214148afJeff Brown protected void onDraw(Canvas canvas) { 47111417b1cfde8f1749905f2d735623af9214148afJeff Brown super.onDraw(canvas); 47211417b1cfde8f1749905f2d735623af9214148afJeff Brown 47311417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mRemoteIndicator != null) { 47411417b1cfde8f1749905f2d735623af9214148afJeff Brown final int left = getPaddingLeft(); 47511417b1cfde8f1749905f2d735623af9214148afJeff Brown final int right = getWidth() - getPaddingRight(); 47611417b1cfde8f1749905f2d735623af9214148afJeff Brown final int top = getPaddingTop(); 47711417b1cfde8f1749905f2d735623af9214148afJeff Brown final int bottom = getHeight() - getPaddingBottom(); 47811417b1cfde8f1749905f2d735623af9214148afJeff Brown 47911417b1cfde8f1749905f2d735623af9214148afJeff Brown final int drawWidth = mRemoteIndicator.getIntrinsicWidth(); 48011417b1cfde8f1749905f2d735623af9214148afJeff Brown final int drawHeight = mRemoteIndicator.getIntrinsicHeight(); 48111417b1cfde8f1749905f2d735623af9214148afJeff Brown final int drawLeft = left + (right - left - drawWidth) / 2; 48211417b1cfde8f1749905f2d735623af9214148afJeff Brown final int drawTop = top + (bottom - top - drawHeight) / 2; 48311417b1cfde8f1749905f2d735623af9214148afJeff Brown 48411417b1cfde8f1749905f2d735623af9214148afJeff Brown mRemoteIndicator.setBounds(drawLeft, drawTop, 48511417b1cfde8f1749905f2d735623af9214148afJeff Brown drawLeft + drawWidth, drawTop + drawHeight); 48611417b1cfde8f1749905f2d735623af9214148afJeff Brown mRemoteIndicator.draw(canvas); 48711417b1cfde8f1749905f2d735623af9214148afJeff Brown } 48811417b1cfde8f1749905f2d735623af9214148afJeff Brown } 48911417b1cfde8f1749905f2d735623af9214148afJeff Brown 49011417b1cfde8f1749905f2d735623af9214148afJeff Brown private void refreshRoute() { 49111417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mAttachedToWindow) { 4929942d40d0d952b03b583fe66f434676793697aa2Jeff Brown final MediaRouter.RouteInfo route = mRouter.getSelectedRoute(); 4939942d40d0d952b03b583fe66f434676793697aa2Jeff Brown final boolean isRemote = !route.isDefault() && route.matchesSelector(mSelector); 4949942d40d0d952b03b583fe66f434676793697aa2Jeff Brown final boolean isConnecting = isRemote && route.isConnecting(); 49511417b1cfde8f1749905f2d735623af9214148afJeff Brown 49611417b1cfde8f1749905f2d735623af9214148afJeff Brown boolean needsRefresh = false; 49711417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mRemoteActive != isRemote) { 49811417b1cfde8f1749905f2d735623af9214148afJeff Brown mRemoteActive = isRemote; 49911417b1cfde8f1749905f2d735623af9214148afJeff Brown needsRefresh = true; 50011417b1cfde8f1749905f2d735623af9214148afJeff Brown } 50111417b1cfde8f1749905f2d735623af9214148afJeff Brown if (mIsConnecting != isConnecting) { 50211417b1cfde8f1749905f2d735623af9214148afJeff Brown mIsConnecting = isConnecting; 50311417b1cfde8f1749905f2d735623af9214148afJeff Brown needsRefresh = true; 50411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 50511417b1cfde8f1749905f2d735623af9214148afJeff Brown 50611417b1cfde8f1749905f2d735623af9214148afJeff Brown if (needsRefresh) { 50711417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshDrawableState(); 50811417b1cfde8f1749905f2d735623af9214148afJeff Brown } 50911417b1cfde8f1749905f2d735623af9214148afJeff Brown 51011417b1cfde8f1749905f2d735623af9214148afJeff Brown setEnabled(mRouter.isRouteAvailable(mSelector, 511d11aa1784335270b8d85e385f2c8be79ee6a586cJeff Brown MediaRouter.AVAILABILITY_FLAG_IGNORE_DEFAULT_ROUTE)); 51211417b1cfde8f1749905f2d735623af9214148afJeff Brown } 51311417b1cfde8f1749905f2d735623af9214148afJeff Brown } 51411417b1cfde8f1749905f2d735623af9214148afJeff Brown 51511417b1cfde8f1749905f2d735623af9214148afJeff Brown private final class MediaRouterCallback extends MediaRouter.Callback { 51611417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 51711417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onRouteAdded(MediaRouter router, MediaRouter.RouteInfo info) { 51811417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshRoute(); 51911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 52011417b1cfde8f1749905f2d735623af9214148afJeff Brown 52111417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 52211417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onRouteRemoved(MediaRouter router, MediaRouter.RouteInfo info) { 52311417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshRoute(); 52411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 52511417b1cfde8f1749905f2d735623af9214148afJeff Brown 52611417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 52711417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onRouteChanged(MediaRouter router, MediaRouter.RouteInfo info) { 52811417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshRoute(); 52911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 53011417b1cfde8f1749905f2d735623af9214148afJeff Brown 53111417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 53211417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onRouteSelected(MediaRouter router, MediaRouter.RouteInfo info) { 53311417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshRoute(); 53411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 53511417b1cfde8f1749905f2d735623af9214148afJeff Brown 53611417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 53711417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onRouteUnselected(MediaRouter router, MediaRouter.RouteInfo info) { 53811417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshRoute(); 53911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 54011417b1cfde8f1749905f2d735623af9214148afJeff Brown 54111417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 54211417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onProviderAdded(MediaRouter router, MediaRouter.ProviderInfo provider) { 54311417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshRoute(); 54411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 54511417b1cfde8f1749905f2d735623af9214148afJeff Brown 54611417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 54711417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onProviderRemoved(MediaRouter router, MediaRouter.ProviderInfo provider) { 54811417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshRoute(); 54911417b1cfde8f1749905f2d735623af9214148afJeff Brown } 55011417b1cfde8f1749905f2d735623af9214148afJeff Brown 55111417b1cfde8f1749905f2d735623af9214148afJeff Brown @Override 55211417b1cfde8f1749905f2d735623af9214148afJeff Brown public void onProviderChanged(MediaRouter router, MediaRouter.ProviderInfo provider) { 55311417b1cfde8f1749905f2d735623af9214148afJeff Brown refreshRoute(); 55411417b1cfde8f1749905f2d735623af9214148afJeff Brown } 55511417b1cfde8f1749905f2d735623af9214148afJeff Brown } 55611417b1cfde8f1749905f2d735623af9214148afJeff Brown} 557