Change toolbar color dynamically based on scroll offset for S.
Bug: 192600648
Test: manual
Change-Id: Ia4c80856c0e345be3f7614cfe6923daf8eb56db1
diff --git a/res/values-v31/dimens.xml b/res/values-v31/dimens.xml
new file mode 100644
index 0000000..15a7814
--- /dev/null
+++ b/res/values-v31/dimens.xml
@@ -0,0 +1,19 @@
+<!--
+ ~ Copyright (C) 2021 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>
+ <dimen name="action_bar_elevation">0dp</dimen>
+ <dimen name="action_bar_margin">0dp</dimen>
+</resources>
diff --git a/res/values/colors.xml b/res/values/colors.xml
index 1a4d3bc..9828762 100644
--- a/res/values/colors.xml
+++ b/res/values/colors.xml
@@ -52,4 +52,5 @@
<color name="list_divider_color">#1f000000</color>
<color name="list_item_selected_background_color">?android:colorSecondary</color>
+ <color name="color_surface_header">@color/app_background_color</color>
</resources>
diff --git a/res/values/overlayable.xml b/res/values/overlayable.xml
index 0b334d2..31b3747 100644
--- a/res/values/overlayable.xml
+++ b/res/values/overlayable.xml
@@ -41,6 +41,7 @@
<!-- START COLOR -->
<item type="color" name="primary"/>
<item type="color" name="list_item_selected_background_color"/>
+ <item type="color" name="color_surface_header"/>
<!-- END COLOR -->
<!-- START DIMEN -->
diff --git a/src/com/android/documentsui/BaseActivity.java b/src/com/android/documentsui/BaseActivity.java
index 5efb9a9..b4ab5bd 100644
--- a/src/com/android/documentsui/BaseActivity.java
+++ b/src/com/android/documentsui/BaseActivity.java
@@ -167,6 +167,11 @@
mNavigator = new NavigationViewManager(this, mDrawer, mState, this, breadcrumb,
profileTabsContainer, DocumentsApplication.getUserIdManager(this));
+ AppBarLayout appBarLayout = findViewById(R.id.app_bar);
+ if (appBarLayout != null) {
+ appBarLayout.addOnOffsetChangedListener(mNavigator);
+ }
+
SearchManagerListener searchListener = new SearchManagerListener() {
/**
* Called when search results changed. Refreshes the content of the directory. It
diff --git a/src/com/android/documentsui/NavigationViewManager.java b/src/com/android/documentsui/NavigationViewManager.java
index b09b3c0..83979ab 100644
--- a/src/com/android/documentsui/NavigationViewManager.java
+++ b/src/com/android/documentsui/NavigationViewManager.java
@@ -19,20 +19,27 @@
import static com.android.documentsui.base.SharedMinimal.VERBOSE;
import android.content.res.Resources;
+import android.content.res.TypedArray;
import android.graphics.Outline;
+import android.graphics.drawable.ColorDrawable;
import android.graphics.drawable.Drawable;
import android.util.Log;
import android.view.View;
import android.view.ViewOutlineProvider;
+import android.view.Window;
+import android.view.WindowManager;
import android.widget.FrameLayout;
+import androidx.annotation.ColorRes;
import androidx.annotation.Nullable;
import androidx.appcompat.widget.Toolbar;
+import androidx.core.content.ContextCompat;
import com.android.documentsui.base.RootInfo;
import com.android.documentsui.base.State;
import com.android.documentsui.base.UserId;
import com.android.documentsui.dirlist.AnimationView;
+import com.android.documentsui.util.VersionUtils;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.appbar.CollapsingToolbarLayout;
@@ -42,12 +49,13 @@
/**
* A facade over the portions of the app and drawer toolbars.
*/
-public class NavigationViewManager {
+public class NavigationViewManager implements AppBarLayout.OnOffsetChangedListener {
private static final String TAG = "NavigationViewManager";
private final DrawerController mDrawer;
private final Toolbar mToolbar;
+ private final BaseActivity mActivity;
private final View mHeader;
private final State mState;
private final NavigationViewManager.Environment mEnv;
@@ -61,6 +69,7 @@
private final boolean mShowSearchBar;
private boolean mIsActionModeActivated = false;
+ private @ColorRes int mDefaultStatusBarColorResId;
public NavigationViewManager(
BaseActivity activity,
@@ -71,6 +80,7 @@
View tabLayoutContainer,
UserIdManager userIdManager) {
+ mActivity = activity;
mToolbar = activity.findViewById(R.id.toolbar);
mHeader = activity.findViewById(R.id.directory_header);
mDrawer = drawer;
@@ -93,6 +103,15 @@
mDefaultOutlineProvider = mToolbar.getOutlineProvider();
mShowSearchBar = activity.getResources().getBoolean(R.bool.show_search_bar);
+ final int[] styledAttrs = {android.R.attr.statusBarColor};
+ TypedArray a = mActivity.obtainStyledAttributes(styledAttrs);
+ mDefaultStatusBarColorResId = a.getResourceId(0, -1);
+ if (mDefaultStatusBarColorResId == -1) {
+ Log.w(TAG, "Retrieve statusBarColorResId from theme failed, assigned default");
+ mDefaultStatusBarColorResId = R.color.app_background_color;
+ }
+ a.recycle();
+
final Resources resources = mToolbar.getResources();
final int radius = resources.getDimensionPixelSize(R.dimen.search_bar_radius);
final int marginStart =
@@ -108,6 +127,36 @@
};
}
+ @Override
+ public void onOffsetChanged(AppBarLayout appBarLayout, int offset) {
+ if (!VersionUtils.isAtLeastS()) {
+ return;
+ }
+
+ // For S+ Only. Change toolbar color dynamically based on scroll offset.
+ // Usually this can be done in xml using app:contentScrim and app:statusBarScrim, however
+ // in our case since we also put directory_header.xml inside the CollapsingToolbarLayout,
+ // the scrim will also cover the directory header. Long term need to think about how to
+ // move directory_header out of the AppBarLayout.
+
+ Window window = mActivity.getWindow();
+ View actionBar = window.getDecorView().findViewById(R.id.action_mode_bar);
+ int dynamicHeaderColor = ContextCompat.getColor(mActivity,
+ offset == 0 ? mDefaultStatusBarColorResId : R.color.color_surface_header);
+ if (actionBar != null) {
+ // Action bar needs to be updated separately for selection mode.
+ actionBar.setBackgroundColor(dynamicHeaderColor);
+ }
+
+ window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
+ window.setStatusBarColor(dynamicHeaderColor);
+ if (shouldShowSearchBar()) {
+ // Do not change search bar background.
+ } else {
+ mToolbar.setBackground(new ColorDrawable(dynamicHeaderColor));
+ }
+ }
+
public void setSearchBarClickListener(View.OnClickListener listener) {
mSearchBarView.setOnClickListener(listener);
}