diff options
34 files changed, 416 insertions, 90 deletions
diff --git a/api/current.txt b/api/current.txt index b017f9d2f5b9..b58947d36c0b 100644 --- a/api/current.txt +++ b/api/current.txt @@ -42593,6 +42593,7 @@ package android.view { method public abstract android.view.ActionProvider getActionProvider(); method public abstract android.view.View getActionView(); method public abstract char getAlphabeticShortcut(); + method public default java.lang.CharSequence getContentDescription(); method public abstract int getGroupId(); method public abstract android.graphics.drawable.Drawable getIcon(); method public abstract android.content.Intent getIntent(); @@ -42603,6 +42604,7 @@ package android.view { method public abstract android.view.SubMenu getSubMenu(); method public abstract java.lang.CharSequence getTitle(); method public abstract java.lang.CharSequence getTitleCondensed(); + method public default java.lang.CharSequence getTooltip(); method public abstract boolean hasSubMenu(); method public abstract boolean isActionViewExpanded(); method public abstract boolean isCheckable(); @@ -42615,6 +42617,7 @@ package android.view { method public abstract android.view.MenuItem setAlphabeticShortcut(char); method public abstract android.view.MenuItem setCheckable(boolean); method public abstract android.view.MenuItem setChecked(boolean); + method public default android.view.MenuItem setContentDescription(java.lang.CharSequence); method public abstract android.view.MenuItem setEnabled(boolean); method public abstract android.view.MenuItem setIcon(android.graphics.drawable.Drawable); method public abstract android.view.MenuItem setIcon(int); @@ -42628,6 +42631,7 @@ package android.view { method public abstract android.view.MenuItem setTitle(java.lang.CharSequence); method public abstract android.view.MenuItem setTitle(int); method public abstract android.view.MenuItem setTitleCondensed(java.lang.CharSequence); + method public default android.view.MenuItem setTooltip(java.lang.CharSequence); method public abstract android.view.MenuItem setVisible(boolean); field public static final int SHOW_AS_ACTION_ALWAYS = 2; // 0x2 field public static final int SHOW_AS_ACTION_COLLAPSE_ACTION_VIEW = 8; // 0x8 diff --git a/api/system-current.txt b/api/system-current.txt index a5534deebd93..7a0f24c3c9f9 100644 --- a/api/system-current.txt +++ b/api/system-current.txt @@ -45803,6 +45803,7 @@ package android.view { method public abstract android.view.ActionProvider getActionProvider(); method public abstract android.view.View getActionView(); method public abstract char getAlphabeticShortcut(); + method public default java.lang.CharSequence getContentDescription(); method public abstract int getGroupId(); method public abstract android.graphics.drawable.Drawable getIcon(); method public abstract android.content.Intent getIntent(); @@ -45813,6 +45814,7 @@ package android.view { method public abstract android.view.SubMenu getSubMenu(); method public abstract java.lang.CharSequence getTitle(); method public abstract java.lang.CharSequence getTitleCondensed(); + method public default java.lang.CharSequence getTooltip(); method public abstract boolean hasSubMenu(); method public abstract boolean isActionViewExpanded(); method public abstract boolean isCheckable(); @@ -45825,6 +45827,7 @@ package android.view { method public abstract android.view.MenuItem setAlphabeticShortcut(char); method public abstract android.view.MenuItem setCheckable(boolean); method public abstract android.view.MenuItem setChecked(boolean); + method public default android.view.MenuItem setContentDescription(java.lang.CharSequence); method public abstract android.view.MenuItem setEnabled(boolean); method public abstract android.view.MenuItem setIcon(android.graphics.drawable.Drawable); method public abstract android.view.MenuItem setIcon(int); @@ -45838,6 +45841,7 @@ package android.view { method public abstract android.view.MenuItem setTitle(java.lang.CharSequence); method public abstract android.view.MenuItem setTitle(int); method public abstract android.view.MenuItem setTitleCondensed(java.lang.CharSequence); + method public default android.view.MenuItem setTooltip(java.lang.CharSequence); method public abstract android.view.MenuItem setVisible(boolean); field public static final int SHOW_AS_ACTION_ALWAYS = 2; // 0x2 field public static final int SHOW_AS_ACTION_COLLAPSE_ACTION_VIEW = 8; // 0x8 diff --git a/api/test-current.txt b/api/test-current.txt index 5db134a28964..4118053af2f7 100644 --- a/api/test-current.txt +++ b/api/test-current.txt @@ -42880,6 +42880,7 @@ package android.view { method public abstract android.view.ActionProvider getActionProvider(); method public abstract android.view.View getActionView(); method public abstract char getAlphabeticShortcut(); + method public default java.lang.CharSequence getContentDescription(); method public abstract int getGroupId(); method public abstract android.graphics.drawable.Drawable getIcon(); method public abstract android.content.Intent getIntent(); @@ -42890,6 +42891,7 @@ package android.view { method public abstract android.view.SubMenu getSubMenu(); method public abstract java.lang.CharSequence getTitle(); method public abstract java.lang.CharSequence getTitleCondensed(); + method public default java.lang.CharSequence getTooltip(); method public abstract boolean hasSubMenu(); method public abstract boolean isActionViewExpanded(); method public abstract boolean isCheckable(); @@ -42902,6 +42904,7 @@ package android.view { method public abstract android.view.MenuItem setAlphabeticShortcut(char); method public abstract android.view.MenuItem setCheckable(boolean); method public abstract android.view.MenuItem setChecked(boolean); + method public default android.view.MenuItem setContentDescription(java.lang.CharSequence); method public abstract android.view.MenuItem setEnabled(boolean); method public abstract android.view.MenuItem setIcon(android.graphics.drawable.Drawable); method public abstract android.view.MenuItem setIcon(int); @@ -42915,6 +42918,7 @@ package android.view { method public abstract android.view.MenuItem setTitle(java.lang.CharSequence); method public abstract android.view.MenuItem setTitle(int); method public abstract android.view.MenuItem setTitleCondensed(java.lang.CharSequence); + method public default android.view.MenuItem setTooltip(java.lang.CharSequence); method public abstract android.view.MenuItem setVisible(boolean); field public static final int SHOW_AS_ACTION_ALWAYS = 2; // 0x2 field public static final int SHOW_AS_ACTION_COLLAPSE_ACTION_VIEW = 8; // 0x8 diff --git a/core/java/android/os/HwBinder.java b/core/java/android/os/HwBinder.java index bcc3468724fd..e02549426cb5 100644 --- a/core/java/android/os/HwBinder.java +++ b/core/java/android/os/HwBinder.java @@ -17,6 +17,7 @@ package android.os; import java.util.ArrayList; +import java.util.NoSuchElementException; import libcore.util.NativeAllocationRegistry; /** @hide */ @@ -44,11 +45,13 @@ public abstract class HwBinder implements IHwBinder { public native final void registerService( ArrayList<String> interfaceChain, - String serviceName); + String serviceName) + throws RemoteException; public static native final IHwBinder getService( String iface, - String serviceName); + String serviceName) + throws RemoteException, NoSuchElementException; // Returns address of the "freeFunction". private static native final long native_init(); diff --git a/core/java/android/os/IHwBinder.java b/core/java/android/os/IHwBinder.java index 2a6567989ced..619f4dc631d5 100644 --- a/core/java/android/os/IHwBinder.java +++ b/core/java/android/os/IHwBinder.java @@ -37,6 +37,5 @@ public interface IHwBinder { } public boolean linkToDeath(DeathRecipient recipient, long cookie); - public boolean unlinkToDeath(DeathRecipient recipient); } diff --git a/core/java/android/view/MenuInflater.java b/core/java/android/view/MenuInflater.java index 73ea9ee31bce..f3f3d40213ec 100644 --- a/core/java/android/view/MenuInflater.java +++ b/core/java/android/view/MenuInflater.java @@ -334,6 +334,9 @@ public class MenuInflater { private ActionProvider itemActionProvider; + private CharSequence itemContentDescription; + private CharSequence itemTooltip; + private static final int defaultGroupId = NO_ID; private static final int defaultItemId = NO_ID; private static final int defaultItemCategory = 0; @@ -424,6 +427,10 @@ public class MenuInflater { itemActionProvider = null; } + itemContentDescription = + a.getText(com.android.internal.R.styleable.MenuItem_contentDescription); + itemTooltip = a.getText(com.android.internal.R.styleable.MenuItem_tooltip); + a.recycle(); itemAdded = false; @@ -486,6 +493,9 @@ public class MenuInflater { if (itemActionProvider != null) { item.setActionProvider(itemActionProvider); } + + item.setContentDescription(itemContentDescription); + item.setTooltip(itemTooltip); } public MenuItem addItem() { diff --git a/core/java/android/view/MenuItem.java b/core/java/android/view/MenuItem.java index 9e8b97eade6b..5ced76592756 100644 --- a/core/java/android/view/MenuItem.java +++ b/core/java/android/view/MenuItem.java @@ -599,4 +599,40 @@ public interface MenuItem { * @return This menu item instance for call chaining */ public MenuItem setOnActionExpandListener(OnActionExpandListener listener); + + /** + * Change the content description associated with this menu item. + * + * @param contentDescription The new content description. + */ + default MenuItem setContentDescription(CharSequence contentDescription) { + return this; + } + + /** + * Retrieve the content description associated with this menu item. + * + * @return The content description. + */ + default CharSequence getContentDescription() { + return null; + } + + /** + * Change the tooltip text associated with this menu item. + * + * @param tooltip The new tooltip text. + */ + default MenuItem setTooltip(CharSequence tooltip) { + return this; + } + + /** + * Retrieve the tooltip text associated with this menu item. + * + * @return The tooltip text. + */ + default CharSequence getTooltip() { + return null; + } } diff --git a/core/java/android/view/WindowManagerGlobal.java b/core/java/android/view/WindowManagerGlobal.java index 83fc3623cf20..fc6448ad7eac 100644 --- a/core/java/android/view/WindowManagerGlobal.java +++ b/core/java/android/view/WindowManagerGlobal.java @@ -249,6 +249,19 @@ public final class WindowManagerGlobal { return views; } + public View getWindowView(IBinder windowToken) { + synchronized (mLock) { + final int numViews = mViews.size(); + for (int i = 0; i < numViews; ++i) { + final View view = mViews.get(i); + if (view.getWindowToken() == windowToken) { + return view; + } + } + } + return null; + } + public View getRootView(String name) { synchronized (mLock) { for (int i = mRoots.size() - 1; i >= 0; --i) { diff --git a/core/java/com/android/internal/view/TooltipPopup.java b/core/java/com/android/internal/view/TooltipPopup.java index c5f6356e92b1..ebbbdbb0d6a6 100644 --- a/core/java/com/android/internal/view/TooltipPopup.java +++ b/core/java/com/android/internal/view/TooltipPopup.java @@ -19,13 +19,17 @@ package com.android.internal.view; import android.content.Context; import android.graphics.PixelFormat; import android.graphics.Rect; +import android.util.Slog; import android.view.Gravity; import android.view.LayoutInflater; import android.view.View; import android.view.WindowManager; +import android.view.WindowManagerGlobal; import android.widget.TextView; public class TooltipPopup { + private static final String TAG = "TooltipPopup"; + private final Context mContext; private final View mContentView; @@ -34,6 +38,7 @@ public class TooltipPopup { private final WindowManager.LayoutParams mLayoutParams = new WindowManager.LayoutParams(); private final Rect mTmpDisplayFrame = new Rect(); private final int[] mTmpAnchorPos = new int[2]; + private final int[] mTmpAppPos = new int[2]; public TooltipPopup(Context context) { mContext = context; @@ -124,8 +129,21 @@ public class TooltipPopup { fromTouch ? com.android.internal.R.dimen.tooltip_y_offset_touch : com.android.internal.R.dimen.tooltip_y_offset_non_touch); - anchorView.getWindowVisibleDisplayFrame(mTmpDisplayFrame); - anchorView.getLocationInWindow(mTmpAnchorPos); + // Find the main app window. The popup window will be positioned relative to it. + final View appView = WindowManagerGlobal.getInstance().getWindowView( + anchorView.getApplicationWindowToken()); + if (appView == null) { + Slog.e(TAG, "Cannot find app view"); + return; + } + appView.getWindowVisibleDisplayFrame(mTmpDisplayFrame); + appView.getLocationOnScreen(mTmpAppPos); + + anchorView.getLocationOnScreen(mTmpAnchorPos); + mTmpAnchorPos[0] -= mTmpAppPos[0]; + mTmpAnchorPos[1] -= mTmpAppPos[1]; + // mTmpAnchorPos is now relative to the main app window. + outParams.x = mTmpAnchorPos[0] + offsetX - mTmpDisplayFrame.width() / 2; final int spec = View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED); diff --git a/core/java/com/android/internal/view/menu/ActionMenuItem.java b/core/java/com/android/internal/view/menu/ActionMenuItem.java index ed676bb703e9..c8697ddba029 100644 --- a/core/java/com/android/internal/view/menu/ActionMenuItem.java +++ b/core/java/com/android/internal/view/menu/ActionMenuItem.java @@ -39,23 +39,26 @@ public class ActionMenuItem implements MenuItem { private Intent mIntent; private char mShortcutNumericChar; private char mShortcutAlphabeticChar; - + private Drawable mIconDrawable; private int mIconResId = NO_ICON; - + private Context mContext; - + private MenuItem.OnMenuItemClickListener mClickListener; - + + private CharSequence mContentDescription; + private CharSequence mTooltip; + private static final int NO_ICON = 0; - + private int mFlags = ENABLED; private static final int CHECKABLE = 0x00000001; private static final int CHECKED = 0x00000002; private static final int EXCLUSIVE = 0x00000004; private static final int HIDDEN = 0x00000008; private static final int ENABLED = 0x00000010; - + public ActionMenuItem(Context context, int group, int id, int categoryOrder, int ordering, CharSequence title) { mContext = context; @@ -65,7 +68,7 @@ public class ActionMenuItem implements MenuItem { mOrdering = ordering; mTitle = title; } - + public char getAlphabeticShortcut() { return mShortcutAlphabeticChar; } @@ -274,4 +277,26 @@ public class ActionMenuItem implements MenuItem { // No need to save the listener; ActionMenuItem does not support collapsing items. return this; } + + @Override + public MenuItem setContentDescription(CharSequence contentDescription) { + mContentDescription = contentDescription; + return this; + } + + @Override + public CharSequence getContentDescription() { + return mContentDescription; + } + + @Override + public MenuItem setTooltip(CharSequence tooltip) { + mTooltip = tooltip; + return this; + } + + @Override + public CharSequence getTooltip() { + return mTooltip; + } } diff --git a/core/java/com/android/internal/view/menu/ActionMenuItemView.java b/core/java/com/android/internal/view/menu/ActionMenuItemView.java index af4f77786a5d..4ee59931d831 100644 --- a/core/java/com/android/internal/view/menu/ActionMenuItemView.java +++ b/core/java/com/android/internal/view/menu/ActionMenuItemView.java @@ -119,7 +119,7 @@ public class ActionMenuItemView extends TextView mItemData = itemData; setIcon(itemData.getIcon()); - setTitle(itemData.getTitleForItemView(this)); // Title only takes effect if there is no icon + setTitle(itemData.getTitleForItemView(this)); // Title is only displayed if there is no icon setId(itemData.getItemId()); setVisibility(itemData.isVisible() ? View.VISIBLE : View.GONE); @@ -184,8 +184,22 @@ public class ActionMenuItemView extends TextView setText(visible ? mTitle : null); - // Show the tooltip for items that do not already show text. - setTooltip(visible ? null : mTitle); + final CharSequence contentDescription = mItemData.getContentDescription(); + if (TextUtils.isEmpty(contentDescription)) { + // Use the uncondensed title for content description, but only if the title is not + // shown already. + setContentDescription(visible ? null : mItemData.getTitle()); + } else { + setContentDescription(contentDescription); + } + + final CharSequence tooltip = mItemData.getTooltip(); + if (TextUtils.isEmpty(tooltip)) { + // Use the uncondensed title for tooltip, but only if the title is not shown already. + setTooltip(visible ? null : mItemData.getTitle()); + } else { + setTooltip(tooltip); + } } public void setIcon(Drawable icon) { @@ -221,7 +235,6 @@ public class ActionMenuItemView extends TextView public void setTitle(CharSequence title) { mTitle = title; - setContentDescription(mTitle); updateTextButtonVisibility(); } diff --git a/core/java/com/android/internal/view/menu/IconMenuItemView.java b/core/java/com/android/internal/view/menu/IconMenuItemView.java index 0e0c9b0cf244..f9ebdbc4f0bb 100644 --- a/core/java/com/android/internal/view/menu/IconMenuItemView.java +++ b/core/java/com/android/internal/view/menu/IconMenuItemView.java @@ -22,6 +22,7 @@ import android.content.Context; import android.content.res.TypedArray; import android.graphics.Rect; import android.graphics.drawable.Drawable; +import android.text.TextUtils; import android.util.AttributeSet; import android.view.Gravity; import android.view.SoundEffectConstants; @@ -31,7 +32,7 @@ import android.widget.TextView; import android.text.Layout; /** - * The item view for each item in the {@link IconMenuView}. + * The item view for each item in the {@link IconMenuView}. */ public final class IconMenuItemView extends TextView implements MenuView.ItemView { @@ -104,13 +105,23 @@ public final class IconMenuItemView extends TextView implements MenuView.ItemVie setTitle(title); setIcon(icon); + + if (mItemData != null) { + final CharSequence contentDescription = mItemData.getContentDescription(); + if (TextUtils.isEmpty(contentDescription)) { + setContentDescription(title); + } else { + setContentDescription(contentDescription); + } + setTooltip(mItemData.getTooltip()); + } } - + public void initialize(MenuItemImpl itemData, int menuType) { mItemData = itemData; initialize(itemData.getTitleForItemView(this), itemData.getIcon()); - + setVisibility(itemData.isVisible() ? View.VISIBLE : View.GONE); setEnabled(itemData.isEnabled()); } diff --git a/core/java/com/android/internal/view/menu/ListMenuItemView.java b/core/java/com/android/internal/view/menu/ListMenuItemView.java index 25263932bb75..7c9f70902d05 100644 --- a/core/java/com/android/internal/view/menu/ListMenuItemView.java +++ b/core/java/com/android/internal/view/menu/ListMenuItemView.java @@ -107,13 +107,15 @@ public class ListMenuItemView extends LinearLayout implements MenuView.ItemView mMenuType = menuType; setVisibility(itemData.isVisible() ? View.VISIBLE : View.GONE); - + setTitle(itemData.getTitleForItemView(this)); setCheckable(itemData.isCheckable()); setShortcut(itemData.shouldShowShortcut(), itemData.getShortcut()); setIcon(itemData.getIcon()); setEnabled(itemData.isEnabled()); setSubMenuArrowVisible(itemData.hasSubMenu()); + setContentDescription(itemData.getContentDescription()); + setTooltip(itemData.getTooltip()); } public void setForceShowIcon(boolean forceShow) { diff --git a/core/java/com/android/internal/view/menu/MenuItemImpl.java b/core/java/com/android/internal/view/menu/MenuItemImpl.java index 624c9e24e945..cad027616582 100644 --- a/core/java/com/android/internal/view/menu/MenuItemImpl.java +++ b/core/java/com/android/internal/view/menu/MenuItemImpl.java @@ -90,16 +90,19 @@ public final class MenuItemImpl implements MenuItem { /** * Current use case is for context menu: Extra information linked to the * View that added this item to the context menu. - */ + */ private ContextMenuInfo mMenuInfo; - + + private CharSequence mContentDescription; + private CharSequence mTooltip; + private static String sLanguage; private static String sPrependShortcutLabel; private static String sEnterShortcutLabel; private static String sDeleteShortcutLabel; private static String sSpaceShortcutLabel; - - + + /** * Instantiates this menu item. * @@ -670,4 +673,32 @@ public final class MenuItemImpl implements MenuItem { public boolean isActionViewExpanded() { return mIsActionViewExpanded; } + + @Override + public MenuItem setContentDescription(CharSequence contentDescription) { + mContentDescription = contentDescription; + + mMenu.onItemsChanged(false); + + return this; + } + + @Override + public CharSequence getContentDescription() { + return mContentDescription; + } + + @Override + public MenuItem setTooltip(CharSequence tooltip) { + mTooltip = tooltip; + + mMenu.onItemsChanged(false); + + return this; + } + + @Override + public CharSequence getTooltip() { + return mTooltip; + } } diff --git a/core/java/com/android/internal/widget/FloatingToolbar.java b/core/java/com/android/internal/widget/FloatingToolbar.java index 66042086e925..04e09a85d1bf 100644 --- a/core/java/com/android/internal/widget/FloatingToolbar.java +++ b/core/java/com/android/internal/widget/FloatingToolbar.java @@ -1585,7 +1585,13 @@ public final class FloatingToolbar { } if (menuItem != null) { menuButton.setText(menuItem.getTitle()); - menuButton.setContentDescription(menuItem.getTitle()); + final CharSequence contentDescription = menuItem.getContentDescription(); + if (TextUtils.isEmpty(contentDescription)) { + menuButton.setContentDescription(menuItem.getTitle()); + } else { + menuButton.setContentDescription(contentDescription); + } + menuButton.setTooltip(menuItem.getTooltip()); menuButton.setMinimumWidth(minimumWidth); } return menuButton; @@ -1629,19 +1635,31 @@ public final class FloatingToolbar { * Creates and returns a menu button for the specified menu item. */ private static View createMenuItemButton(Context context, MenuItem menuItem) { + final View menuItemButton; if (isIconOnlyMenuItem(menuItem)) { - View imageMenuItemButton = LayoutInflater.from(context) + menuItemButton = LayoutInflater.from(context) .inflate(R.layout.floating_popup_menu_image_button, null); - ((ImageButton) imageMenuItemButton + ((ImageButton) menuItemButton .findViewById(R.id.floating_toolbar_menu_item_image_button)) .setImageDrawable(menuItem.getIcon()); - return imageMenuItemButton; + final CharSequence tooltip = menuItem.getTooltip(); + if (TextUtils.isEmpty(tooltip)) { + menuItemButton.setTooltip(menuItem.getTitle()); + } else { + menuItemButton.setTooltip(tooltip); + } + } else { + menuItemButton = LayoutInflater.from(context) + .inflate(R.layout.floating_popup_menu_button, null); + ((Button) menuItemButton).setText(menuItem.getTitle()); + menuItemButton.setTooltip(menuItem.getTooltip()); + } + final CharSequence contentDescription = menuItem.getContentDescription(); + if (TextUtils.isEmpty(contentDescription)) { + menuItemButton.setContentDescription(menuItem.getTitle()); + } else { + menuItemButton.setContentDescription(contentDescription); } - - Button menuItemButton = (Button) LayoutInflater.from(context) - .inflate(R.layout.floating_popup_menu_button, null); - menuItemButton.setText(menuItem.getTitle()); - menuItemButton.setContentDescription(menuItem.getTitle()); return menuItemButton; } diff --git a/core/jni/android_os_HwBinder.cpp b/core/jni/android_os_HwBinder.cpp index 81199fa41e1b..20bb885eb578 100644 --- a/core/jni/android_os_HwBinder.cpp +++ b/core/jni/android_os_HwBinder.cpp @@ -39,6 +39,8 @@ using android::AndroidRuntime; using android::hardware::hidl_vec; using android::hardware::hidl_string; +template<typename T> +using Return = android::hardware::Return<T>; #define PACKAGE_PATH "android/os" #define CLASS_NAME "HwBinder" @@ -257,8 +259,6 @@ static void JHwBinder_native_registerService( hidl_vec<hidl_string> interfaceChain; interfaceChain.setToExternal(strings, numInterfaces, true /* shouldOwn */); - using android::hidl::manager::V1_0::IServiceManager; - sp<hardware::IBinder> binder = JHwBinder::GetNativeContext(env, thiz); /* TODO(b/33440494) this is not right */ @@ -268,24 +268,23 @@ static void JHwBinder_native_registerService( if (manager == nullptr) { LOG(ERROR) << "Could not get hwservicemanager."; - signalExceptionForError(env, UNKNOWN_ERROR); + signalExceptionForError(env, UNKNOWN_ERROR, true /* canThrowRemoteException */); return; } - bool ok = manager->add( - interfaceChain, - serviceName, - base); + Return<bool> ret = manager->add(interfaceChain, serviceName, base); env->ReleaseStringUTFChars(serviceNameObj, serviceName); serviceName = NULL; + bool ok = ret.isOk() && ret; + if (ok) { LOG(INFO) << "Starting thread pool."; ::android::hardware::ProcessState::self()->startThreadPool(); } - signalExceptionForError(env, (ok ? OK : UNKNOWN_ERROR)); + signalExceptionForError(env, (ok ? OK : UNKNOWN_ERROR), true /* canThrowRemoteException */); } static jobject JHwBinder_native_getService( @@ -321,13 +320,18 @@ static jobject JHwBinder_native_getService( if (manager == nullptr) { LOG(ERROR) << "Could not get hwservicemanager."; - signalExceptionForError(env, UNKNOWN_ERROR); + signalExceptionForError(env, UNKNOWN_ERROR, true /* canThrowRemoteException */); return NULL; } - sp<hidl::base::V1_0::IBase> base = manager->get(ifaceName, serviceName); + Return<sp<hidl::base::V1_0::IBase>> ret = manager->get(ifaceName, serviceName); + + if (!ret.isOk()) { + signalExceptionForError(env, UNKNOWN_ERROR, true /* canThrowRemoteException */); + } + sp<hardware::IBinder> service = hardware::toBinder< - hidl::base::V1_0::IBase, hidl::base::V1_0::BpBase>(base); + hidl::base::V1_0::IBase, hidl::base::V1_0::BpBase>(ret); env->ReleaseStringUTFChars(ifaceNameObj, ifaceName); ifaceName = NULL; diff --git a/core/res/res/values/attrs.xml b/core/res/res/values/attrs.xml index 05658b018861..37b3ffc48016 100644 --- a/core/res/res/values/attrs.xml +++ b/core/res/res/values/attrs.xml @@ -7009,6 +7009,12 @@ for more info. --> <attr name="actionProviderClass" format="string" /> + <!-- The content description associated with the item. --> + <attr name="contentDescription" format="string" /> + + <!-- The tooltip text associated with the item. --> + <attr name="tooltip" format="string" /> + </declare-styleable> <!-- Attrbitutes for a ActvityChooserView. --> diff --git a/core/res/res/values/styles.xml b/core/res/res/values/styles.xml index 0f756b94a321..ce7ab1626aa0 100644 --- a/core/res/res/values/styles.xml +++ b/core/res/res/values/styles.xml @@ -1290,6 +1290,7 @@ please see styles_device_defaults.xml. <style name="Widget.ActionButton.Overflow"> <item name="src">@drawable/ic_menu_more</item> <item name="contentDescription">@string/action_menu_overflow_description</item> + <item name="tooltip">@string/action_menu_overflow_description</item> </style> <style name="Widget.ActionButton.CloseMode"> diff --git a/core/res/res/values/styles_holo.xml b/core/res/res/values/styles_holo.xml index 8ca12ae66986..12b8164ad001 100644 --- a/core/res/res/values/styles_holo.xml +++ b/core/res/res/values/styles_holo.xml @@ -660,6 +660,7 @@ please see styles_device_defaults.xml. <item name="src">@drawable/ic_menu_moreoverflow_holo_dark</item> <item name="background">?attr/actionBarItemBackground</item> <item name="contentDescription">@string/action_menu_overflow_description</item> + <item name="tooltip">@string/action_menu_overflow_description</item> </style> <style name="Widget.Holo.ActionButton.TextButton" parent="Widget.Holo.ButtonBar.Button" /> @@ -994,6 +995,7 @@ please see styles_device_defaults.xml. <style name="Widget.Holo.Light.ActionButton.Overflow"> <item name="src">@drawable/ic_menu_moreoverflow_holo_light</item> <item name="contentDescription">@string/action_menu_overflow_description</item> + <item name="tooltip">@string/action_menu_overflow_description</item> </style> <style name="Widget.Holo.Light.ActionBar.TabView" parent="Widget.Holo.ActionBar.TabView" /> diff --git a/core/res/res/values/styles_material.xml b/core/res/res/values/styles_material.xml index a1e12d281c95..709200eabff2 100644 --- a/core/res/res/values/styles_material.xml +++ b/core/res/res/values/styles_material.xml @@ -944,6 +944,7 @@ please see styles_device_defaults.xml. <item name="src">@drawable/ic_menu_moreoverflow_material</item> <item name="background">?attr/actionBarItemBackground</item> <item name="contentDescription">@string/action_menu_overflow_description</item> + <item name="tooltip">@string/action_menu_overflow_description</item> <item name="minWidth">@dimen/action_button_min_width_overflow_material</item> <item name="minHeight">@dimen/action_button_min_height_material</item> <item name="paddingStart">@dimen/action_bar_overflow_padding_start_material</item> diff --git a/packages/SettingsLib/res/layout/drawer_category.xml b/packages/SettingsLib/res/layout/drawer_category.xml index 582821bdf6bb..72cfddb1a431 100644 --- a/packages/SettingsLib/res/layout/drawer_category.xml +++ b/packages/SettingsLib/res/layout/drawer_category.xml @@ -26,13 +26,13 @@ android:background="?android:attr/listDivider" /> <TextView + style="@style/TextAppearanceSmall" android:id="@android:id/title" android:layout_width="match_parent" android:layout_height="wrap_content" android:minHeight="48dp" android:paddingTop="16dp" android:paddingBottom="16dp" - android:paddingStart="16dp" - android:textAppearance="?android:attr/textAppearanceSmall" /> + android:paddingStart="16dp" /> </LinearLayout> diff --git a/packages/SettingsLib/res/layout/drawer_item.xml b/packages/SettingsLib/res/layout/drawer_item.xml index e1f1ae5ef706..d492ddfee0fe 100644 --- a/packages/SettingsLib/res/layout/drawer_item.xml +++ b/packages/SettingsLib/res/layout/drawer_item.xml @@ -23,19 +23,22 @@ <ImageView android:id="@android:id/icon" - android:layout_width="72dp" - android:layout_height="24dp" + android:layout_width="@dimen/drawer_icon_size" + android:layout_height="@dimen/drawer_icon_size" + android:layout_marginStart="@dimen/drawer_icon_margin" + android:layout_marginEnd="@dimen/drawer_icon_margin" + android:layout_marginTop="@dimen/drawer_item_top_bottom_margin" + android:layout_marginBottom="@dimen/drawer_item_top_bottom_margin" + android:scaleType="fitCenter" android:layout_gravity="center_vertical" - android:tint="?android:attr/colorAccent" - android:paddingStart="16dp" - android:paddingEnd="32dp" /> + android:tint="?android:attr/colorAccent"/> <TextView + android:textAppearance="@style/TextAppearanceMedium" android:id="@android:id/title" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center_vertical" - android:textColor="?android:attr/colorControlNormal" - android:textAppearance="?android:attr/textAppearanceMedium" /> + android:textColor="?android:attr/colorControlNormal" /> </LinearLayout> diff --git a/packages/SettingsLib/res/layout/drawer_spacer.xml b/packages/SettingsLib/res/layout/drawer_spacer.xml index ee1835d7c231..98120cf904d0 100644 --- a/packages/SettingsLib/res/layout/drawer_spacer.xml +++ b/packages/SettingsLib/res/layout/drawer_spacer.xml @@ -17,4 +17,4 @@ xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/spacer" android:layout_width="match_parent" - android:layout_height="32dp" /> + android:layout_height="@dimen/drawer_spacer_height" /> diff --git a/packages/SettingsLib/res/layout/settings_with_drawer.xml b/packages/SettingsLib/res/layout/settings_with_drawer.xml index abe310a6e38a..af96d8b25e64 100644 --- a/packages/SettingsLib/res/layout/settings_with_drawer.xml +++ b/packages/SettingsLib/res/layout/settings_with_drawer.xml @@ -53,7 +53,7 @@ </LinearLayout> <!-- The navigation drawer --> <ListView android:id="@+id/left_drawer" - android:layout_width="300dp" + android:layout_width="@dimen/drawer_width" android:layout_height="match_parent" android:layout_gravity="start" android:choiceMode="singleChoice" diff --git a/packages/SettingsLib/res/values/dimens.xml b/packages/SettingsLib/res/values/dimens.xml index c3b3cfc47bfd..2e8b30fb5abf 100644 --- a/packages/SettingsLib/res/values/dimens.xml +++ b/packages/SettingsLib/res/values/dimens.xml @@ -51,5 +51,10 @@ <dimen name="usage_graph_dot_size">.75dp</dimen> <dimen name="usage_graph_dot_interval">7dp</dimen> - + <dimen name="drawer_icon_size">24dp</dimen> + <dimen name="normal_icon_size">24dp</dimen> + <dimen name="drawer_icon_margin">24dp</dimen> + <dimen name="drawer_width">300dp</dimen> + <dimen name="drawer_item_top_bottom_margin">4dp</dimen> + <dimen name="drawer_spacer_height">32dp</dimen> </resources> diff --git a/packages/SettingsLib/res/values/styles.xml b/packages/SettingsLib/res/values/styles.xml new file mode 100644 index 000000000000..3f312f4efda3 --- /dev/null +++ b/packages/SettingsLib/res/values/styles.xml @@ -0,0 +1,24 @@ +<!-- + ~ Copyright (C) 2016 The Android Open Source Project + ~ + ~ Licensed under the Apache License, Version 2.0 (the "License"); + ~ you may not use this file except in compliance with the License. + ~ You may obtain a copy of the License at + ~ + ~ http://www.apache.org/licenses/LICENSE-2.0 + ~ + ~ Unless required by applicable law or agreed to in writing, software + ~ distributed under the License is distributed on an "AS IS" BASIS, + ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + ~ See the License for the specific language governing permissions and + ~ limitations under the License + --> + +<resources> + <style name="TextAppearanceSmall"> + <item name="android:textAppearance">?android:attr/textAppearanceSmall</item> + </style> + <style name="TextAppearanceMedium"> + <item name="android:textAppearance">?android:attr/textAppearanceMedium</item> + </style> +</resources> diff --git a/packages/SettingsLib/src/com/android/settingslib/drawer/CategoryManager.java b/packages/SettingsLib/src/com/android/settingslib/drawer/CategoryManager.java index 6ccba92e2e5f..fa5ba73b318f 100644 --- a/packages/SettingsLib/src/com/android/settingslib/drawer/CategoryManager.java +++ b/packages/SettingsLib/src/com/android/settingslib/drawer/CategoryManager.java @@ -72,21 +72,30 @@ public class CategoryManager { } public synchronized DashboardCategory getTilesByCategory(Context context, String categoryKey) { - tryInitCategories(context); + return getTilesByCategory(context, categoryKey, TileUtils.SETTING_PKG); + } + + public synchronized DashboardCategory getTilesByCategory(Context context, String categoryKey, + String settingPkg) { + tryInitCategories(context, settingPkg); return mCategoryByKeyMap.get(categoryKey); } public synchronized List<DashboardCategory> getCategories(Context context) { - tryInitCategories(context); + return getCategories(context, TileUtils.SETTING_PKG); + } + + public synchronized List<DashboardCategory> getCategories(Context context, String settingPkg) { + tryInitCategories(context, settingPkg); return mCategories; } - public synchronized void reloadAllCategories(Context context) { + public synchronized void reloadAllCategories(Context context, String settingPkg) { final boolean forceClearCache = mInterestingConfigChanges.applyNewConfig( context.getResources()); mCategories = null; - tryInitCategories(context, forceClearCache); + tryInitCategories(context, forceClearCache, settingPkg); } public synchronized void updateCategoryFromBlacklist(Set<ComponentName> tileBlacklist) { @@ -104,20 +113,21 @@ public class CategoryManager { } } - private synchronized void tryInitCategories(Context context) { + private synchronized void tryInitCategories(Context context, String settingPkg) { // Keep cached tiles by default. The cache is only invalidated when InterestingConfigChange // happens. - tryInitCategories(context, false /* forceClearCache */); + tryInitCategories(context, false /* forceClearCache */, settingPkg); } - private synchronized void tryInitCategories(Context context, boolean forceClearCache) { + private synchronized void tryInitCategories(Context context, boolean forceClearCache, + String settingPkg) { if (mCategories == null) { if (forceClearCache) { mTileByComponentCache.clear(); } mCategoryByKeyMap.clear(); mCategories = TileUtils.getCategories(context, mTileByComponentCache, - false /* categoryDefinedInManifest */, mExtraAction); + false /* categoryDefinedInManifest */, mExtraAction, settingPkg); for (DashboardCategory category : mCategories) { mCategoryByKeyMap.put(category.key, category); } diff --git a/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerActivity.java b/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerActivity.java index 5041e0dccc26..89ed110d3246 100644 --- a/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerActivity.java +++ b/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerActivity.java @@ -193,8 +193,9 @@ public class SettingsDrawerActivity extends Activity { } if (isDashboardFeatureEnabled()) { final DashboardCategory homepageCategories = CategoryManager.get(this) - .getTilesByCategory(this, CategoryKey.CATEGORY_HOMEPAGE); - return homepageCategories.containsComponent(componentName); + .getTilesByCategory(this, CategoryKey.CATEGORY_HOMEPAGE, getSettingPkg()); + return homepageCategories == + null ? false : homepageCategories.containsComponent(componentName); } else { // Look for a tile that has the same component as incoming intent final List<DashboardCategory> categories = getDashboardCategories(); @@ -210,6 +211,14 @@ public class SettingsDrawerActivity extends Activity { } } + /** + * Gets the name of the intent action of the default setting app. Used to launch setting app + * when Settings Home is clicked. + */ + public String getSettingAction() { + return Settings.ACTION_SETTINGS; + } + public void addCategoryListener(CategoryListener listener) { mCategoryListeners.add(listener); } @@ -274,7 +283,7 @@ public class SettingsDrawerActivity extends Activity { } // TODO: Do this in the background with some loading. if (isDashboardFeatureEnabled()) { - mDrawerAdapter.updateHomepageCategories(); + mDrawerAdapter.updateHomepageCategories(getSettingPkg()); } else { mDrawerAdapter.updateCategories(); } @@ -317,8 +326,9 @@ public class SettingsDrawerActivity extends Activity { public boolean openTile(Tile tile) { closeDrawer(); if (tile == null) { - startActivity(new Intent(Settings.ACTION_SETTINGS).addFlags( - Intent.FLAG_ACTIVITY_CLEAR_TASK)); + Intent intent = new Intent(getSettingAction()).addFlags( + Intent.FLAG_ACTIVITY_CLEAR_TASK); + startActivity(intent); return true; } try { @@ -376,6 +386,10 @@ public class SettingsDrawerActivity extends Activity { } } + public String getSettingPkg() { + return TileUtils.SETTING_PKG; + } + public interface CategoryListener { void onCategoriesChanged(); } @@ -426,7 +440,7 @@ public class SettingsDrawerActivity extends Activity { @Override protected Void doInBackground(Void... params) { - mCategoryManager.reloadAllCategories(SettingsDrawerActivity.this); + mCategoryManager.reloadAllCategories(SettingsDrawerActivity.this, getSettingPkg()); return null; } @@ -437,6 +451,9 @@ public class SettingsDrawerActivity extends Activity { } } + /** + * @return {@code true} if IA (Information Architecture) is enabled. + */ protected boolean isDashboardFeatureEnabled() { return false; } diff --git a/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerAdapter.java b/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerAdapter.java index 602d135dd6c9..75942f93b67b 100644 --- a/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerAdapter.java +++ b/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerAdapter.java @@ -68,9 +68,9 @@ public class SettingsDrawerAdapter extends BaseAdapter { notifyDataSetChanged(); } - public void updateHomepageCategories() { + public void updateHomepageCategories(String settingPkg) { final DashboardCategory category = CategoryManager.get(mActivity) - .getTilesByCategory(mActivity, CategoryKey.CATEGORY_HOMEPAGE); + .getTilesByCategory(mActivity, CategoryKey.CATEGORY_HOMEPAGE, settingPkg); mItems.clear(); // Spacer. mItems.add(null); diff --git a/packages/SettingsLib/src/com/android/settingslib/drawer/TileUtils.java b/packages/SettingsLib/src/com/android/settingslib/drawer/TileUtils.java index a0109e29831a..0cc5ab1900ba 100644 --- a/packages/SettingsLib/src/com/android/settingslib/drawer/TileUtils.java +++ b/packages/SettingsLib/src/com/android/settingslib/drawer/TileUtils.java @@ -147,7 +147,7 @@ public class TileUtils { public static final String META_DATA_PREFERENCE_SUMMARY_URI = "com.android.settings.summary_uri"; - private static final String SETTING_PKG = "com.android.settings"; + public static final String SETTING_PKG = "com.android.settings"; /** * Build a list of DashboardCategory. Each category must be defined in manifest. @@ -167,39 +167,43 @@ public class TileUtils { */ public static List<DashboardCategory> getCategories(Context context, Map<Pair<String, String>, Tile> cache, boolean categoryDefinedInManifest) { - return getCategories(context, cache, categoryDefinedInManifest, null); + return getCategories(context, cache, categoryDefinedInManifest, null, SETTING_PKG); } /** * Build a list of DashboardCategory. * @param categoryDefinedInManifest If true, an dummy activity must exists in manifest to * represent this category (eg: .Settings$DeviceSettings) - * @param extraAction additional intent filter action to be used to build the dashboard + * @param extraAction additional intent filter action to be usetileutild to build the dashboard * categories */ public static List<DashboardCategory> getCategories(Context context, Map<Pair<String, String>, Tile> cache, boolean categoryDefinedInManifest, - String extraAction) { + String extraAction, String settingPkg) { final long startTime = System.currentTimeMillis(); boolean setup = Global.getInt(context.getContentResolver(), Global.DEVICE_PROVISIONED, 0) != 0; ArrayList<Tile> tiles = new ArrayList<>(); - UserManager userManager = UserManager.get(context); + UserManager userManager = (UserManager) context.getSystemService(Context.USER_SERVICE); for (UserHandle user : userManager.getUserProfiles()) { // TODO: Needs much optimization, too many PM queries going on here. if (user.getIdentifier() == ActivityManager.getCurrentUser()) { // Only add Settings for this user. - getTilesForAction(context, user, SETTINGS_ACTION, cache, null, tiles, true); + getTilesForAction(context, user, SETTINGS_ACTION, cache, null, tiles, true, + settingPkg); getTilesForAction(context, user, OPERATOR_SETTINGS, cache, - OPERATOR_DEFAULT_CATEGORY, tiles, false, true); + OPERATOR_DEFAULT_CATEGORY, tiles, false, true, settingPkg); getTilesForAction(context, user, MANUFACTURER_SETTINGS, cache, - MANUFACTURER_DEFAULT_CATEGORY, tiles, false, true); + MANUFACTURER_DEFAULT_CATEGORY, tiles, false, true, settingPkg); } if (setup) { - getTilesForAction(context, user, EXTRA_SETTINGS_ACTION, cache, null, tiles, false); - getTilesForAction(context, user, IA_SETTINGS_ACTION, cache, null, tiles, false); + getTilesForAction(context, user, EXTRA_SETTINGS_ACTION, cache, null, tiles, false, + settingPkg); + getTilesForAction(context, user, IA_SETTINGS_ACTION, cache, null, tiles, false, + settingPkg); if (extraAction != null) { - getTilesForAction(context, user, extraAction, cache, null, tiles, false); + getTilesForAction(context, user, extraAction, cache, null, tiles, false, + settingPkg); } } } @@ -263,18 +267,19 @@ public class TileUtils { private static void getTilesForAction(Context context, UserHandle user, String action, Map<Pair<String, String>, Tile> addedCache, - String defaultCategory, ArrayList<Tile> outTiles, boolean requireSettings) { + String defaultCategory, ArrayList<Tile> outTiles, boolean requireSettings, + String settingPkg) { getTilesForAction(context, user, action, addedCache, defaultCategory, outTiles, - requireSettings, requireSettings); + requireSettings, requireSettings, settingPkg); } private static void getTilesForAction(Context context, UserHandle user, String action, Map<Pair<String, String>, Tile> addedCache, String defaultCategory, ArrayList<Tile> outTiles, boolean requireSettings, - boolean usePriority) { + boolean usePriority, String settingPkg) { Intent intent = new Intent(action); if (requireSettings) { - intent.setPackage(SETTING_PKG); + intent.setPackage(settingPkg); } getTilesForIntent(context, user, intent, addedCache, defaultCategory, outTiles, usePriority, true); diff --git a/packages/SettingsLib/tests/robotests/src/com/android/settingslib/drawer/TileUtilsTest.java b/packages/SettingsLib/tests/robotests/src/com/android/settingslib/drawer/TileUtilsTest.java index eb99cac94e40..d8082c41b5ff 100644 --- a/packages/SettingsLib/tests/robotests/src/com/android/settingslib/drawer/TileUtilsTest.java +++ b/packages/SettingsLib/tests/robotests/src/com/android/settingslib/drawer/TileUtilsTest.java @@ -16,6 +16,8 @@ package com.android.settingslib.drawer; +import android.app.ActivityManager; +import static org.mockito.Mockito.verify; import android.content.IContentProvider; import android.content.ContentResolver; import android.content.Context; @@ -36,6 +38,7 @@ import android.util.ArrayMap; import android.util.Pair; import com.android.settingslib.TestConfig; +import static org.mockito.Mockito.atLeastOnce; import org.junit.Before; import org.junit.Test; @@ -43,6 +46,7 @@ import org.junit.runner.RunWith; import org.mockito.ArgumentMatcher; import org.mockito.Mock; import org.mockito.MockitoAnnotations; +import org.robolectric.shadows.ShadowApplication; import org.robolectric.RobolectricTestRunner; import org.robolectric.RuntimeEnvironment; import org.robolectric.annotation.Config; @@ -59,6 +63,8 @@ import static org.mockito.Matchers.argThat; import static org.mockito.Matchers.eq; import static org.mockito.Mockito.spy; import static org.mockito.Mockito.when; +import org.mockito.ArgumentCaptor; + @RunWith(RobolectricTestRunner.class) @Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) @@ -97,7 +103,7 @@ public class TileUtilsTest { List<Tile> outTiles = new ArrayList<>(); List<ResolveInfo> info = new ArrayList<>(); info.add(newInfo(true, testCategory)); - + Map<Pair<String, String>, Tile> cache = new ArrayMap<>(); when(mPackageManager.queryIntentActivitiesAsUser(eq(intent), anyInt(), anyInt())) .thenReturn(info); @@ -169,12 +175,33 @@ public class TileUtilsTest { }), anyInt(), anyInt())).thenReturn(info); List<DashboardCategory> categoryList = TileUtils.getCategories( - mContext, cache, false /* categoryDefinedInManifest */, testAction); - + mContext, cache, false /* categoryDefinedInManifest */, testAction, + TileUtils.SETTING_PKG); assertThat(categoryList.get(0).tiles.get(0).category).isEqualTo(testCategory); } @Test + public void getCategories_withPackageName() throws Exception { + ArgumentCaptor<Intent> intentCaptor = ArgumentCaptor.forClass(Intent.class); + Map<Pair<String, String>, Tile> cache = new ArrayMap<>(); + Global.putInt(mContext.getContentResolver(), Global.DEVICE_PROVISIONED, 1); + when(mContext.getSystemService(Context.USER_SERVICE)).thenReturn(mUserManager); + List<UserHandle> userHandleList = new ArrayList<>(); + + userHandleList.add(new UserHandle(ActivityManager.getCurrentUser())); + when(mUserManager.getUserProfiles()).thenReturn(userHandleList); + + TileUtils.getCategories( + mContext, cache, false /* categoryDefinedInManifest */, null /* action */, + TileUtils.SETTING_PKG); + verify(mPackageManager, atLeastOnce()).queryIntentActivitiesAsUser( + intentCaptor.capture(), anyInt(), anyInt()); + + assertThat(intentCaptor.getAllValues().get(0).getPackage()) + .isEqualTo(TileUtils.SETTING_PKG); + } + + @Test public void getTilesForIntent_shouldNotProcessInvalidUriContentSystemApp() throws RemoteException { Intent intent = new Intent(); diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java index 760bf54a540c..1f2007af4870 100644 --- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java +++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java @@ -2192,6 +2192,11 @@ public class TaskStackView extends FrameLayout implements TaskStack.TaskStackCal mFocusedTask.dump("", writer); } + int numTaskViews = mTaskViews.size(); + for (int i = 0; i < numTaskViews; i++) { + mTaskViews.get(i).dump(innerPrefix, writer); + } + mLayoutAlgorithm.dump(innerPrefix, writer); mStackScroller.dump(innerPrefix, writer); } diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskView.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskView.java index 2f4ad6a4d7ce..36d5f838a070 100644 --- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskView.java +++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskView.java @@ -58,6 +58,7 @@ import com.android.systemui.recents.misc.Utilities; import com.android.systemui.recents.model.Task; import com.android.systemui.recents.model.TaskStack; +import java.io.PrintWriter; import java.util.ArrayList; /** @@ -715,4 +716,14 @@ public class TaskView extends FixedSizeFrameLayout implements Task.TaskCallbacks setClipViewInStack(true); }); } + + public void dump(String prefix, PrintWriter writer) { + String innerPrefix = prefix + " "; + + writer.print(prefix); writer.print("TaskView"); + writer.print(" mTask="); writer.print(mTask.key.id); + writer.println(); + + mThumbnailView.dump(innerPrefix, writer); + } } diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewThumbnail.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewThumbnail.java index d109807c3ca4..58b929ac690a 100644 --- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewThumbnail.java +++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewThumbnail.java @@ -35,8 +35,11 @@ import android.view.View; import android.view.ViewDebug; import com.android.systemui.R; +import com.android.systemui.recents.misc.Utilities; import com.android.systemui.recents.model.Task; +import java.io.PrintWriter; + /** * The task thumbnail view. It implements an image view that allows for animating the dim and @@ -343,4 +346,15 @@ public class TaskViewThumbnail extends View { mTask = null; setThumbnail(null, null); } + + public void dump(String prefix, PrintWriter writer) { + String innerPrefix = prefix + " "; + + writer.print(prefix); writer.print("TaskViewThumbnail"); + writer.print(" mTaskViewRect="); writer.print(Utilities.dumpRect(mTaskViewRect)); + writer.print(" mThumbnailRect="); writer.print(Utilities.dumpRect(mThumbnailRect)); + writer.print(" mThumbnailScale="); writer.print(mThumbnailScale); + writer.print(" mDimAlpha="); writer.print(mDimAlpha); + writer.println(); + } } |