Ime in gestural mode will have ime switcher and down arrow

When in gestural mode, the navigation bar will inset the ime window
higher to raise up revealing the original height of the navigation bar.
In place will be the (alt) back button (pointing down), the handle and
ime switcher (if should be shown).

Fixes: 128928130
Bug: 113952590
Bug: 112934365
Test: manual
Change-Id: I28cc4def846cb09eb2d7ab00d12561f0c198dbbc
This commit is contained in:
Matthew Ng
2019-04-03 13:52:57 -07:00
committed by Winson Chung
parent 2fec69813c
commit f03c3a6398
12 changed files with 129 additions and 27 deletions

View File

@@ -37,16 +37,10 @@
android:paddingStart="@dimen/navigation_key_padding"
android:paddingEnd="@dimen/navigation_key_padding"
/>
<com.android.systemui.statusbar.policy.KeyButtonView
android:id="@+id/ime_switcher"
<include layout="@layout/ime_switcher"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="0"
android:scaleType="center"
android:visibility="invisible"
android:contentDescription="@string/accessibility_ime_switch_button"
android:paddingStart="@dimen/navigation_key_padding"
android:paddingEnd="@dimen/navigation_key_padding"
/>
<com.android.systemui.statusbar.policy.KeyButtonView
android:id="@+id/rotate_suggestion"

View File

@@ -21,5 +21,7 @@
android:layout_width="@dimen/navigation_home_handle_width"
android:layout_height="match_parent"
android:layout_weight="0"
android:paddingStart="@dimen/navigation_key_padding"
android:paddingEnd="@dimen/navigation_key_padding"
/>

View File

@@ -0,0 +1,28 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2019 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
-->
<com.android.systemui.statusbar.policy.KeyButtonView
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/ime_switcher"
android:layout_width="@dimen/navigation_key_width"
android:layout_height="match_parent"
android:layout_weight="0"
android:contentDescription="@string/accessibility_ime_switch_button"
android:scaleType="center"
android:paddingStart="@dimen/navigation_key_padding"
android:paddingEnd="@dimen/navigation_key_padding"
/>

View File

@@ -35,13 +35,13 @@
android:visibility="invisible"
android:contentDescription="@string/accessibility_menu"
/>
<com.android.systemui.statusbar.policy.KeyButtonView
android:id="@+id/ime_switcher"
<include layout="@layout/ime_switcher"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:visibility="invisible"
android:contentDescription="@string/accessibility_ime_switch_button"
android:scaleType="centerInside"
android:visibility="invisible"
android:paddingStart="0dp"
android:paddingEnd="0dp"
/>
<com.android.systemui.statusbar.policy.KeyButtonView
android:id="@+id/rotate_suggestion"

View File

@@ -330,7 +330,7 @@
<!-- Nav bar button default ordering/layout -->
<string name="config_navBarLayout" translatable="false">left[.5W],back[1WC];home;recent[1WC],right[.5W]</string>
<string name="config_navBarLayoutQuickstep" translatable="false">back[1.7WC];home;contextual[1.7WC]</string>
<string name="config_navBarLayoutHandle" translatable="false">";home_handle;"</string>
<string name="config_navBarLayoutHandle" translatable="false">back[1.7WC];home_handle;ime_switcher[1.7WC]</string>
<bool name="quick_settings_show_full_alarm">false</bool>

View File

@@ -51,6 +51,9 @@ public class ContextualButton extends ButtonDispatcher {
* Reload the drawable from resource id, should reapply the previous dark intensity.
*/
public void updateIcon() {
if (getCurrentView() == null || !getCurrentView().isAttachedToWindow()) {
return;
}
final KeyButtonDrawable currentDrawable = getImageDrawable();
KeyButtonDrawable drawable = getNewDrawable();
if (currentDrawable != null) {

View File

@@ -112,23 +112,24 @@ public class ContextualButtonGroup extends ButtonDispatcher {
* their icons for their buttons.
*/
public void updateIcons() {
if (getCurrentView() == null || !getCurrentView().isAttachedToWindow()) {
return;
}
for (ButtonData data : mButtonData) {
data.button.updateIcon();
}
}
public void dump(PrintWriter pw) {
View view = getCurrentView();
pw.println("ContextualButtonGroup {");
pw.println(" getVisibleContextButton(): " + getVisibleContextButton());
pw.println(" isVisible(): " + isVisible());
pw.println(" attached(): " + (view != null && view.isAttachedToWindow()));
pw.println(" mButtonData [ ");
for (int i = mButtonData.size() - 1; i >= 0; --i) {
final ButtonData data = mButtonData.get(i);
view = data.button.getCurrentView();
pw.println(" " + i + ": markedVisible=" + data.markedVisible
+ " visible=" + data.button.getVisibility()
+ " attached=" + (view != null && view.isAttachedToWindow())
+ " alpha=" + data.button.getAlpha());
}
pw.println(" ]");

View File

@@ -202,7 +202,9 @@ public class NavigationBarFragment extends LifecycleFragment implements Callback
@Override
public void onBackButtonAlphaChanged(float alpha, boolean animate) {
final ButtonDispatcher backButton = mNavigationBarView.getBackButton();
if (QuickStepContract.isGesturalMode(getContext())) {
final boolean useAltBack =
(mNavigationIconHints & StatusBarManager.NAVIGATION_HINT_BACK_ALT) != 0;
if (QuickStepContract.isGesturalMode(getContext()) && !useAltBack) {
// If property was changed to hide/show back button, going home will trigger
// launcher to to change the back button alpha to reflect property change
backButton.setVisibility(View.GONE);

View File

@@ -68,6 +68,7 @@ public class NavigationBarInflaterView extends FrameLayout
public static final String LEFT = "left";
public static final String RIGHT = "right";
public static final String CONTEXTUAL = "contextual";
public static final String IME_SWITCHER = "ime_switcher";
public static final String GRAVITY_SEPARATOR = ";";
public static final String BUTTON_SEPARATOR = ",";
@@ -164,17 +165,21 @@ public class NavigationBarInflaterView extends FrameLayout
@Override
public void onTuningChanged(String key, String newValue) {
if (NAV_BAR_VIEWS.equals(key)) {
if (!Objects.equals(mCurrentLayout, newValue)) {
mUsingCustomLayout = newValue != null;
clearViews();
inflateLayout(newValue);
}
setNavigationBarLayout(newValue);
} else if (NAV_BAR_LEFT.equals(key) || NAV_BAR_RIGHT.equals(key)) {
clearViews();
inflateLayout(mCurrentLayout);
}
}
public void setNavigationBarLayout(String layoutValue) {
if (!Objects.equals(mCurrentLayout, layoutValue)) {
mUsingCustomLayout = layoutValue != null;
clearViews();
inflateLayout(layoutValue);
}
}
public void onLikelyDefaultLayoutChange() {
// Don't override custom layouts
if (mUsingCustomLayout) return;
@@ -401,6 +406,8 @@ public class NavigationBarInflaterView extends FrameLayout
v = inflater.inflate(R.layout.contextual, parent, false);
} else if (HOME_HANDLE.equals(button)) {
v = inflater.inflate(R.layout.home_handle, parent, false);
} else if (IME_SWITCHER.equals(button)) {
v = inflater.inflate(R.layout.ime_switcher, parent, false);
} else if (button.startsWith(KEY)) {
String uri = extractImage(button);
int code = extractKeycode(button);

View File

@@ -21,7 +21,6 @@ import static android.view.WindowManagerPolicyConstants.NAV_BAR_INVALID;
import static com.android.systemui.shared.system.NavigationBarCompat.FLAG_SHOW_OVERVIEW_BUTTON;
import static com.android.systemui.statusbar.phone.BarTransitions.MODE_OPAQUE;
import static com.android.systemui.statusbar.phone.NavigationBarInflaterView.NAV_BAR_VIEWS;
import android.animation.LayoutTransition;
import android.animation.LayoutTransition.TransitionListener;
@@ -35,6 +34,7 @@ import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.pm.ParceledListSlice;
import android.content.res.Configuration;
import android.graphics.Canvas;
import android.graphics.Point;
@@ -48,6 +48,8 @@ import android.util.Log;
import android.util.Slog;
import android.util.SparseArray;
import android.view.Display;
import android.view.IPinnedStackController;
import android.view.IPinnedStackListener;
import android.view.MotionEvent;
import android.view.Surface;
import android.view.View;
@@ -133,6 +135,7 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
private boolean mUseCarModeUi = false;
private boolean mInCarMode = false;
private boolean mDockedStackExists;
private boolean mImeVisible;
private final SparseArray<ButtonDispatcher> mButtonDispatchers = new SparseArray<>();
private final ContextualButtonGroup mContextualButtonGroup;
@@ -234,6 +237,45 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
}
};
private final IPinnedStackListener.Stub mImeChangedListener = new IPinnedStackListener.Stub() {
@Override
public void onListenerRegistered(IPinnedStackController controller) {
}
@Override
public void onImeVisibilityChanged(boolean imeVisible, int imeHeight) {
post(() -> {
// TODO remove this and do below when mNavigationIconHints changes
if (imeVisible) {
getBackButton().setVisibility(VISIBLE);
reloadNavIcons();
} else {
getImeSwitchButton().setVisibility(GONE);
}
mImeVisible = imeVisible;
updateWindowTouchable();
});
}
@Override
public void onShelfVisibilityChanged(boolean shelfVisible, int shelfHeight) {
}
@Override
public void onMinimizedStateChanged(boolean isMinimized) {
}
@Override
public void onMovementBoundsChanged(Rect insetBounds, Rect normalBounds,
Rect animatingBounds, boolean fromImeAdjustment, boolean fromShelfAdjustment,
int displayRotation) {
}
@Override
public void onActionsChanged(ParceledListSlice actions) {
}
};
private BroadcastReceiver mOverlaysChangedReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
@@ -472,6 +514,11 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
return;
}
if (QuickStepContract.isGesturalMode(getContext())) {
drawable.setRotation(degrees);
return;
}
// Animate the back button's rotation to the new degrees and only in portrait move up the
// back button to line up with the other buttons
float targetY = !mOverviewProxyService.shouldShowSwipeUpUI() && !mIsVertical && useAltBack
@@ -574,8 +621,8 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
// Always disable recents when alternate car mode UI is active and for secondary displays.
boolean disableRecent = isRecentsButtonDisabled();
boolean disableBack = QuickStepContract.isGesturalMode(getContext())
|| (((mDisabledFlags & View.STATUS_BAR_DISABLE_BACK) != 0) && !useAltBack);
boolean disableBack = !useAltBack && (QuickStepContract.isGesturalMode(getContext())
|| ((mDisabledFlags & View.STATUS_BAR_DISABLE_BACK) != 0));
// When screen pinning, don't hide back and home when connected service or back and
// recents buttons when disconnected from launcher service in screen pinning mode,
@@ -715,6 +762,11 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
setWindowFlag(WindowManager.LayoutParams.FLAG_SLIPPERY, slippery);
}
public void updateWindowTouchable() {
boolean touchable = mImeVisible || !QuickStepContract.isGesturalMode(getContext());
setWindowFlag(WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE, !touchable);
}
private void setWindowFlag(int flags, boolean enable) {
final ViewGroup navbarView = ((ViewGroup) getParent());
if (navbarView == null) {
@@ -734,7 +786,7 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
}
private void onOverlaysChanged() {
mNavigationInflaterView.onTuningChanged(NAV_BAR_VIEWS, null);
mNavigationInflaterView.setNavigationBarLayout(null);
// Color adaption is tied with showing home handle, only avaliable if visible
if (QuickStepContract.isGesturalMode(getContext())) {
@@ -1062,6 +1114,15 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
filter.addDataScheme("package");
getContext().registerReceiver(mOverlaysChangedReceiver, filter);
mEdgeBackGestureHandler.onNavBarAttached();
if (QuickStepContract.isGesturalMode(getContext())) {
try {
WindowManagerWrapper.getInstance().addPinnedStackListener(mImeChangedListener);
} catch (RemoteException e) {
Log.e(TAG, "Failed to register pinned stack listener", e);
}
}
updateWindowTouchable();
}
@Override
@@ -1078,6 +1139,8 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
getContext().unregisterReceiver(mOverlaysChangedReceiver);
mEdgeBackGestureHandler.onNavBarDetached();
WindowManagerWrapper.getInstance().removePinnedStackListener(mImeChangedListener);
}
private void setUpSwipeUpOnboarding(boolean connectedToOverviewProxy) {

View File

@@ -36,6 +36,7 @@ import com.android.systemui.SysuiTestCase;
import com.android.systemui.statusbar.policy.KeyButtonDrawable;
import org.junit.Before;
import org.junit.Ignore;
import org.junit.Test;
import org.junit.runner.RunWith;
@@ -173,6 +174,7 @@ public class NavigationBarContextTest extends SysuiTestCase {
}
@Test
@Ignore("b/112934365")
public void testUpdateIconsDarkIntensity() throws Exception {
final int unusedColor = 0;
final Drawable d = mock(Drawable.class);

View File

@@ -16,7 +16,6 @@
package com.android.server.wm;
import static android.app.WindowConfiguration.ACTIVITY_TYPE_HOME;
import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD;
import static android.view.WindowManagerPolicyConstants.NAV_BAR_BOTTOM;
import static android.view.WindowManagerPolicyConstants.NAV_BAR_LEFT;
@@ -91,7 +90,7 @@ public class NavigationBarExperiments {
* @param w the window that is being offset by experiment
*/
public void offsetWindowFramesForNavBar(int navPosition, WindowState w) {
if (w.getAttrs().type != TYPE_INPUT_METHOD && w.getActivityType() != ACTIVITY_TYPE_HOME) {
if (w.getAttrs().type != TYPE_INPUT_METHOD) {
return;
}
@@ -102,6 +101,7 @@ public class NavigationBarExperiments {
int navHeight = getNavigationBarFrameHeight() - getNavigationBarHeight();
if (navHeight > 0) {
cf.bottom -= navHeight;
windowFrames.mStableFrame.bottom -= navHeight;
}
break;
case NAV_BAR_LEFT: