Change appearance of notifications to light theme.

Change-Id: Ic15e96582d6b46b4dc195b1c7c0cef38f25f0d38
This commit is contained in:
Jorim Jaggi
2014-02-25 15:38:45 +01:00
parent 35eb23cb10
commit 39fa59fc49
20 changed files with 1439 additions and 18 deletions

View File

@@ -611,6 +611,13 @@ public class Notification implements Parcelable
*/
public static final String EXTRA_AS_HEADS_UP = "headsup";
/**
* Extra added from {@link Notification.Builder} to indicate that the remote views were inflated
* from the builder, as opposed to being created directly from the application.
* @hide
*/
public static final String EXTRA_BUILDER_REMOTE_VIEWS = "android.builderRemoteViews";
/**
* Value for {@link #EXTRA_AS_HEADS_UP}.
* @hide
@@ -1273,6 +1280,7 @@ public class Notification implements Parcelable
private boolean mShowWhen = true;
private int mVisibility = VISIBILITY_PRIVATE;
private Notification mPublicVersion = null;
private boolean mQuantumTheme;
/**
* Constructs a new Builder with the defaults:
@@ -1300,6 +1308,9 @@ public class Notification implements Parcelable
mWhen = System.currentTimeMillis();
mAudioStreamType = STREAM_DEFAULT;
mPriority = PRIORITY_DEFAULT;
// TODO: Decide on targetSdk from calling app whether to use quantum theme.
mQuantumTheme = true;
}
/**
@@ -1807,7 +1818,7 @@ public class Notification implements Parcelable
contentView.setImageViewBitmap(R.id.icon, mLargeIcon);
smallIconImageViewId = R.id.right_icon;
}
if (mPriority < PRIORITY_LOW) {
if (!mQuantumTheme && mPriority < PRIORITY_LOW) {
contentView.setInt(R.id.icon,
"setBackgroundResource", R.drawable.notification_template_icon_low_bg);
contentView.setInt(R.id.status_bar_latest_event_content,
@@ -1921,7 +1932,7 @@ public class Notification implements Parcelable
if (mContentView != null) {
return mContentView;
} else {
return applyStandardTemplate(R.layout.notification_template_base, true); // no more special large_icon flavor
return applyStandardTemplate(getBaseLayoutResource(), true); // no more special large_icon flavor
}
}
@@ -1942,21 +1953,21 @@ public class Notification implements Parcelable
private RemoteViews makeBigContentView() {
if (mActions.size() == 0) return null;
return applyStandardTemplateWithActions(R.layout.notification_template_big_base);
return applyStandardTemplateWithActions(getBigBaseLayoutResource());
}
private RemoteViews makeHEadsUpContentView() {
private RemoteViews makeHeadsUpContentView() {
if (mActions.size() == 0) return null;
return applyStandardTemplateWithActions(R.layout.notification_template_big_base);
return applyStandardTemplateWithActions(getBigBaseLayoutResource());
}
private RemoteViews generateActionButton(Action action) {
final boolean tombstone = (action.actionIntent == null);
RemoteViews button = new RemoteViews(mContext.getPackageName(),
tombstone ? R.layout.notification_action_tombstone
: R.layout.notification_action);
tombstone ? getActionTombstoneLayoutResource()
: getActionLayoutResource());
button.setTextViewCompoundDrawablesRelative(R.id.action0, action.icon, 0, 0, 0);
button.setTextViewText(R.id.action0, action.title);
if (!tombstone) {
@@ -1992,7 +2003,7 @@ public class Notification implements Parcelable
n.defaults = mDefaults;
n.flags = mFlags;
n.bigContentView = makeBigContentView();
n.headsUpContentView = makeHEadsUpContentView();
n.headsUpContentView = makeHeadsUpContentView();
if (mLedOnMs != 0 || mLedOffMs != 0) {
n.flags |= FLAG_SHOW_LIGHTS;
}
@@ -2037,6 +2048,7 @@ public class Notification implements Parcelable
extras.putBoolean(EXTRA_PROGRESS_INDETERMINATE, mProgressIndeterminate);
extras.putBoolean(EXTRA_SHOW_CHRONOMETER, mUseChronometer);
extras.putBoolean(EXTRA_SHOW_WHEN, mShowWhen);
extras.putBoolean(EXTRA_BUILDER_REMOTE_VIEWS, mContentView == null);
if (mLargeIcon != null) {
extras.putParcelable(EXTRA_LARGE_ICON, mLargeIcon);
}
@@ -2080,6 +2092,49 @@ public class Notification implements Parcelable
build().cloneInto(n, true);
return n;
}
private int getBaseLayoutResource() {
return mQuantumTheme
? R.layout.notification_template_quantum_base
: R.layout.notification_template_base;
}
private int getBigBaseLayoutResource() {
return mQuantumTheme
? R.layout.notification_template_quantum_big_base
: R.layout.notification_template_big_base;
}
private int getBigPictureLayoutResource() {
return mQuantumTheme
? R.layout.notification_template_quantum_big_picture
: R.layout.notification_template_big_picture;
}
private int getBigTextLayoutResource() {
return mQuantumTheme
? R.layout.notification_template_quantum_big_text
: R.layout.notification_template_big_text;
}
private int getInboxLayoutResource() {
return mQuantumTheme
? R.layout.notification_template_quantum_inbox
: R.layout.notification_template_inbox;
}
private int getActionLayoutResource() {
return mQuantumTheme
? R.layout.notification_quantum_action
: R.layout.notification_action;
}
private int getActionTombstoneLayoutResource() {
return mQuantumTheme
? R.layout.notification_quantum_action_tombstone
: R.layout.notification_action_tombstone;
}
}
/**
@@ -2249,7 +2304,7 @@ public class Notification implements Parcelable
}
private RemoteViews makeBigContentView() {
RemoteViews contentView = getStandardView(R.layout.notification_template_big_picture);
RemoteViews contentView = getStandardView(mBuilder.getBigPictureLayoutResource());
contentView.setImageViewBitmap(R.id.big_picture, mPicture);
@@ -2348,7 +2403,7 @@ public class Notification implements Parcelable
final boolean hadThreeLines = (mBuilder.mContentText != null && mBuilder.mSubText != null);
mBuilder.mContentText = null;
RemoteViews contentView = getStandardView(R.layout.notification_template_big_text);
RemoteViews contentView = getStandardView(mBuilder.getBigTextLayoutResource());
if (hadThreeLines) {
// vertical centering
@@ -2442,7 +2497,7 @@ public class Notification implements Parcelable
private RemoteViews makeBigContentView() {
// Remove the content text so line3 disappears unless you have a summary
mBuilder.mContentText = null;
RemoteViews contentView = getStandardView(R.layout.notification_template_inbox);
RemoteViews contentView = getStandardView(mBuilder.getInboxLayoutResource());
contentView.setViewVisibility(R.id.text2, View.GONE);

View File

@@ -315,6 +315,24 @@ public class ColorStateList implements Parcelable {
return mDefaultColor;
}
/**
* Return the states in this {@link ColorStateList}.
* @return the states in this {@link ColorStateList}
* @hide
*/
public int[][] getStates() {
return mStateSpecs;
}
/**
* Return the colors in this {@link ColorStateList}.
* @return the colors in this {@link ColorStateList}
* @hide
*/
public int[] getColors() {
return mColors;
}
@Override
public String toString() {
return "ColorStateList{" +

View File

@@ -0,0 +1,21 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="#ffffffff" />
<corners android:radius="2dp" />
</shape>

View File

@@ -0,0 +1,21 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true" android:drawable="@drawable/notification_quantum_press" />
<item android:state_pressed="false" android:drawable="@drawable/notification_quantum_background" />
</selector>

View File

@@ -0,0 +1,21 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="#ffcccccc" />
<corners android:radius="2dp" />
</shape>

View File

@@ -0,0 +1,31 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<Button xmlns:android="http://schemas.android.com/apk/res/android"
style="?android:attr/borderlessButtonStyle"
android:id="@+id/action0"
android:layout_width="0dp"
android:layout_height="48dp"
android:layout_weight="1"
android:gravity="start|center_vertical"
android:drawablePadding="8dp"
android:paddingStart="8dp"
android:textColor="#555555"
android:textSize="14dp"
android:singleLine="true"
android:ellipsize="end"
/>

View File

@@ -0,0 +1,30 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright (C) 2014 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.
-->
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/actions"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:visibility="gone"
android:layout_marginBottom="8dp"
android:showDividers="middle"
android:divider="?android:attr/listDivider"
android:dividerPadding="12dp"
>
<!-- actions will be added here -->
</LinearLayout>

View File

@@ -0,0 +1,33 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<Button xmlns:android="http://schemas.android.com/apk/res/android"
style="?android:attr/borderlessButtonStyle"
android:id="@+id/action0"
android:layout_width="0dp"
android:layout_height="48dp"
android:layout_weight="1"
android:gravity="start|center_vertical"
android:drawablePadding="8dp"
android:paddingStart="8dp"
android:textColor="#555555"
android:textSize="14dp"
android:singleLine="true"
android:ellipsize="end"
android:alpha="0.5"
android:enabled="false"
/>

View File

@@ -0,0 +1,137 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:internal="http://schemas.android.com/apk/prv/res/android"
android:background="@android:drawable/notification_quantum_bg"
android:id="@+id/status_bar_latest_event_content"
android:layout_width="match_parent"
android:layout_height="64dp"
internal:layout_minHeight="64dp"
internal:layout_maxHeight="64dp"
>
<ImageView android:id="@+id/icon"
android:layout_width="@dimen/notification_large_icon_width"
android:layout_height="@dimen/notification_large_icon_height"
android:scaleType="center"
/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="fill_vertical"
android:layout_marginStart="@dimen/notification_large_icon_width"
android:minHeight="@dimen/notification_large_icon_height"
android:orientation="vertical"
android:paddingEnd="8dp"
android:paddingTop="2dp"
android:paddingBottom="2dp"
android:gravity="top"
>
<LinearLayout
android:id="@+id/line1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingTop="6dp"
android:layout_marginStart="8dp"
android:orientation="horizontal"
>
<TextView android:id="@+id/title"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:singleLine="true"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
android:layout_weight="1"
/>
<ViewStub android:id="@+id/time"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="0"
android:visibility="gone"
android:layout="@layout/notification_template_part_time"
/>
<ViewStub android:id="@+id/chronometer"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="0"
android:visibility="gone"
android:layout="@layout/notification_template_part_chronometer"
/>
</LinearLayout>
<TextView android:id="@+id/text2"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Line2"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="-2dp"
android:layout_marginBottom="-2dp"
android:layout_marginStart="8dp"
android:singleLine="true"
android:fadingEdge="horizontal"
android:ellipsize="marquee"
android:visibility="gone"
/>
<ProgressBar
android:id="@android:id/progress"
android:layout_width="match_parent"
android:layout_height="12dp"
android:layout_marginStart="8dp"
android:visibility="gone"
style="?android:attr/progressBarStyleHorizontal"
/>
<LinearLayout
android:id="@+id/line3"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center_vertical"
android:layout_marginStart="8dp"
>
<TextView android:id="@+id/text"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:layout_gravity="center"
android:singleLine="true"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
/>
<TextView android:id="@+id/info"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Info"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_weight="0"
android:singleLine="true"
android:gravity="center"
android:paddingStart="8dp"
/>
<ImageView android:id="@+id/right_icon"
android:layout_width="16dp"
android:layout_height="16dp"
android:layout_gravity="center"
android:layout_weight="0"
android:layout_marginStart="8dp"
android:scaleType="centerInside"
android:visibility="gone"
android:drawableAlpha="153"
/>
</LinearLayout>
</LinearLayout>
</FrameLayout>

View File

@@ -0,0 +1,167 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:internal="http://schemas.android.com/apk/prv/res/android"
android:background="@android:drawable/notification_quantum_bg"
android:id="@+id/status_bar_latest_event_content"
android:layout_width="match_parent"
android:layout_height="wrap_content"
internal:layout_minHeight="65dp"
internal:layout_maxHeight="unbounded"
>
<ImageView android:id="@+id/icon"
android:layout_width="@dimen/notification_large_icon_width"
android:layout_height="@dimen/notification_large_icon_height"
android:scaleType="center"
/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="fill_vertical"
android:minHeight="@dimen/notification_large_icon_height"
android:orientation="vertical"
android:gravity="top"
>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginStart="@dimen/notification_large_icon_width"
android:minHeight="@dimen/notification_large_icon_height"
android:paddingTop="2dp"
android:orientation="vertical"
>
<LinearLayout
android:id="@+id/line1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingTop="6dp"
android:layout_marginEnd="8dp"
android:layout_marginStart="8dp"
android:orientation="horizontal"
>
<TextView android:id="@+id/title"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:singleLine="true"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
android:layout_weight="1"
/>
<ViewStub android:id="@+id/time"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="0"
android:visibility="gone"
android:layout="@layout/notification_template_part_time"
/>
<ViewStub android:id="@+id/chronometer"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="0"
android:visibility="gone"
android:layout="@layout/notification_template_part_chronometer"
/>
</LinearLayout>
<TextView android:id="@+id/text2"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Line2"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="-2dp"
android:layout_marginBottom="-2dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:fadingEdge="horizontal"
android:ellipsize="marquee"
android:visibility="gone"
/>
<TextView android:id="@+id/big_text"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="false"
android:visibility="gone"
/>
<LinearLayout
android:id="@+id/line3"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:orientation="horizontal"
android:gravity="center_vertical"
>
<TextView android:id="@+id/text"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:layout_gravity="center"
android:singleLine="true"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
/>
<TextView android:id="@+id/info"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Info"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_weight="0"
android:singleLine="true"
android:gravity="center"
android:paddingStart="8dp"
/>
<ImageView android:id="@+id/right_icon"
android:layout_width="16dp"
android:layout_height="16dp"
android:layout_gravity="center"
android:layout_weight="0"
android:layout_marginStart="8dp"
android:scaleType="centerInside"
android:visibility="gone"
android:drawableAlpha="153"
/>
</LinearLayout>
<ProgressBar
android:id="@android:id/progress"
android:layout_width="match_parent"
android:layout_height="12dp"
android:layout_marginBottom="8dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:visibility="gone"
style="?android:attr/progressBarStyleHorizontal"
/>
</LinearLayout>
<ImageView
android:layout_width="match_parent"
android:layout_height="1dp"
android:id="@+id/action_divider"
android:visibility="gone"
android:background="?android:attr/dividerHorizontal" />
<include
layout="@layout/notification_quantum_action_list"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginStart="@dimen/notification_large_icon_width"
/>
</LinearLayout>
</FrameLayout>

View File

@@ -0,0 +1,62 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:internal="http://schemas.android.com/apk/prv/res/android"
android:background="@android:drawable/notification_quantum_bg"
android:id="@+id/status_bar_latest_event_content"
android:layout_width="match_parent"
android:layout_height="match_parent"
internal:layout_minHeight="65dp"
internal:layout_maxHeight="unbounded"
>
<ImageView
android:id="@+id/big_picture"
android:layout_width="match_parent"
android:layout_height="192dp"
android:layout_marginTop="64dp"
android:layout_gravity="bottom"
android:scaleType="centerCrop"
/>
<ImageView
android:layout_width="match_parent"
android:layout_height="6dp"
android:layout_marginTop="64dp"
android:scaleType="fitXY"
android:src="@drawable/title_bar_shadow"
/>
<include layout="@layout/notification_template_quantum_base"
android:layout_width="match_parent"
android:layout_height="wrap_content"
/>
<FrameLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="208dp"
android:paddingStart="64dp"
android:layout_gravity="bottom"
android:background="#CCEEEEEE"
>
<include
layout="@layout/notification_quantum_action_list"
android:id="@+id/actions"
android:layout_gravity="bottom"
android:layout_width="match_parent"
android:layout_height="wrap_content"
/>
</FrameLayout>
</FrameLayout>

View File

@@ -0,0 +1,182 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:internal="http://schemas.android.com/apk/prv/res/android"
android:background="@android:drawable/notification_quantum_bg"
android:id="@+id/status_bar_latest_event_content"
android:layout_width="match_parent"
android:layout_height="wrap_content"
internal:layout_minHeight="65dp"
internal:layout_maxHeight="unbounded"
>
<ImageView android:id="@+id/icon"
android:layout_width="@dimen/notification_large_icon_width"
android:layout_height="@dimen/notification_large_icon_height"
android:scaleType="center"
/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="fill_vertical"
android:layout_marginStart="@dimen/notification_large_icon_width"
android:orientation="vertical"
android:paddingTop="0dp"
android:paddingBottom="2dp"
android:gravity="top"
>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:minHeight="@dimen/notification_large_icon_height"
android:orientation="vertical"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:layout_weight="1"
>
<LinearLayout
android:id="@+id/line1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingTop="8dp"
android:orientation="horizontal"
android:layout_gravity="top"
android:layout_weight="0"
>
<TextView android:id="@+id/title"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:singleLine="true"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
android:layout_weight="1"
/>
<ViewStub android:id="@+id/time"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="0"
android:visibility="gone"
android:layout="@layout/notification_template_part_time"
/>
<ViewStub android:id="@+id/chronometer"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="0"
android:visibility="gone"
android:layout="@layout/notification_template_part_chronometer"
/>
</LinearLayout>
<TextView android:id="@+id/text2"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Line2"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="-2dp"
android:layout_marginBottom="-2dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:fadingEdge="horizontal"
android:ellipsize="marquee"
android:layout_weight="0"
android:visibility="gone"
/>
<ProgressBar
android:id="@android:id/progress"
android:layout_width="match_parent"
android:layout_height="12dp"
android:layout_marginBottom="8dp"
android:layout_marginEnd="8dp"
android:visibility="gone"
android:layout_weight="0"
style="?android:attr/progressBarStyleHorizontal"
/>
<TextView android:id="@+id/big_text"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginBottom="10dp"
android:layout_marginEnd="8dp"
android:singleLine="false"
android:visibility="gone"
android:maxLines="8"
android:ellipsize="end"
android:layout_weight="1"
/>
</LinearLayout>
<ImageView
android:layout_width="match_parent"
android:layout_height="1dip"
android:id="@+id/action_divider"
android:visibility="gone"
android:background="?android:attr/dividerHorizontal" />
<include
layout="@layout/notification_quantum_action_list"
android:layout_width="match_parent"
android:layout_height="0dp"
android:visibility="gone"
android:layout_weight="1"
/>
<ImageView
android:layout_width="match_parent"
android:layout_height="1dp"
android:id="@+id/overflow_divider"
android:layout_marginBottom="8dp"
android:visibility="visible"
android:background="?android:attr/dividerHorizontal" />
<LinearLayout
android:id="@+id/line3"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginStart="8dp"
android:layout_marginBottom="8dp"
android:layout_marginEnd="8dp"
android:orientation="horizontal"
android:layout_weight="0"
android:gravity="center_vertical"
>
<TextView android:id="@+id/text"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:layout_gravity="center"
android:singleLine="true"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
/>
<TextView android:id="@+id/info"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Info"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_weight="0"
android:singleLine="true"
android:gravity="center"
android:paddingStart="8dp"
/>
<ImageView android:id="@+id/right_icon"
android:layout_width="16dp"
android:layout_height="16dp"
android:layout_gravity="center"
android:layout_weight="0"
android:layout_marginStart="8dp"
android:scaleType="centerInside"
android:visibility="gone"
android:drawableAlpha="153"
/>
</LinearLayout>
</LinearLayout>
</FrameLayout>

View File

@@ -0,0 +1,266 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:internal="http://schemas.android.com/apk/prv/res/android"
android:id="@+id/status_bar_latest_event_content"
android:background="@android:drawable/notification_quantum_bg"
android:layout_width="match_parent"
android:layout_height="wrap_content"
internal:layout_minHeight="65dp"
internal:layout_maxHeight="unbounded"
>
<ImageView android:id="@+id/icon"
android:layout_width="@dimen/notification_large_icon_width"
android:layout_height="@dimen/notification_large_icon_height"
android:scaleType="center"
/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="fill_vertical"
android:layout_marginStart="@dimen/notification_large_icon_width"
android:minHeight="@dimen/notification_large_icon_height"
android:orientation="vertical"
android:paddingTop="0dp"
android:paddingBottom="2dp"
android:gravity="top"
>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:minHeight="@dimen/notification_large_icon_height"
android:paddingTop="2dp"
android:orientation="vertical"
>
<LinearLayout
android:id="@+id/line1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:paddingTop="6dp"
android:orientation="horizontal"
android:layout_weight="0"
>
<TextView android:id="@+id/title"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:singleLine="true"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
android:layout_weight="1"
/>
<ViewStub android:id="@+id/time"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="0"
android:visibility="gone"
android:layout="@layout/notification_template_part_time"
/>
<ViewStub android:id="@+id/chronometer"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="0"
android:visibility="gone"
android:layout="@layout/notification_template_part_chronometer"
/>
</LinearLayout>
<TextView android:id="@+id/text2"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Line2"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="-2dp"
android:layout_marginBottom="-2dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:fadingEdge="horizontal"
android:ellipsize="marquee"
android:visibility="gone"
android:layout_weight="0"
/>
<ProgressBar
android:id="@android:id/progress"
android:layout_width="match_parent"
android:layout_height="12dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:visibility="gone"
android:layout_weight="0"
style="?android:attr/progressBarStyleHorizontal"
/>
<TextView android:id="@+id/inbox_text0"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:ellipsize="end"
android:visibility="gone"
android:layout_weight="1"
/>
<TextView android:id="@+id/inbox_text1"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:ellipsize="end"
android:visibility="gone"
android:layout_weight="1"
/>
<TextView android:id="@+id/inbox_text2"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:ellipsize="end"
android:visibility="gone"
android:layout_weight="1"
/>
<TextView android:id="@+id/inbox_text3"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:ellipsize="end"
android:visibility="gone"
android:layout_weight="1"
/>
<TextView android:id="@+id/inbox_text4"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginStart="8dp"
android:singleLine="true"
android:ellipsize="end"
android:visibility="gone"
android:layout_weight="1"
/>
<TextView android:id="@+id/inbox_text5"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:ellipsize="end"
android:visibility="gone"
android:layout_weight="1"
/>
<TextView android:id="@+id/inbox_text6"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:ellipsize="end"
android:visibility="gone"
android:layout_weight="1"
/>
<TextView android:id="@+id/inbox_more"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:singleLine="true"
android:ellipsize="end"
android:visibility="gone"
android:layout_weight="1"
android:text="@android:string/ellipsis"
/>
<FrameLayout
android:id="@+id/inbox_end_pad"
android:layout_width="match_parent"
android:layout_height="8dip"
android:visibility="gone"
android:layout_weight="0"
/>
</LinearLayout>
<ImageView
android:layout_width="match_parent"
android:layout_height="1dip"
android:id="@+id/action_divider"
android:visibility="gone"
android:background="?android:attr/dividerHorizontal" />
<include
layout="@layout/notification_quantum_action_list"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="0"
/>
<ImageView
android:layout_width="match_parent"
android:layout_height="1dip"
android:id="@+id/overflow_divider"
android:visibility="visible"
android:background="?android:attr/dividerHorizontal" />
<LinearLayout
android:id="@+id/line3"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="8dp"
android:layout_marginStart="8dp"
android:layout_marginBottom="8dp"
android:layout_marginEnd="8dp"
android:orientation="horizontal"
android:layout_weight="0"
android:gravity="center_vertical"
>
<TextView android:id="@+id/text"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:layout_gravity="center"
android:singleLine="true"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
/>
<TextView android:id="@+id/info"
android:textAppearance="@style/TextAppearance.StatusBar.Quantum.EventContent.Info"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_weight="0"
android:singleLine="true"
android:gravity="center"
android:paddingStart="8dp"
/>
<ImageView android:id="@+id/right_icon"
android:layout_width="16dp"
android:layout_height="16dp"
android:layout_gravity="center"
android:layout_weight="0"
android:layout_marginStart="8dp"
android:scaleType="centerInside"
android:visibility="gone"
android:drawableAlpha="153"
/>
</LinearLayout>
</LinearLayout>
</FrameLayout>

View File

@@ -271,6 +271,33 @@ please see styles_device_defaults.xml.
<item name="android:textColor">#CCCCCC</item>
</style>
<style name="TextAppearance.StatusBar.Quantum">
</style>
<style name="TextAppearance.StatusBar.Quantum.EventContent">
<item name="android:textColor">#888888</item>
<item name="android:textSize">@dimen/notification_text_size</item>
</style>
<style name="TextAppearance.StatusBar.Quantum.EventContent.Title">
<item name="android:textColor">#000000</item>
<item name="android:fontFamily">sans-serif-light</item>
<item name="android:textSize">@dimen/notification_title_text_size</item>
<item name="android:textStyle">bold</item>
</style>
<style name="TextAppearance.StatusBar.Quantum.EventContent.Line2">
<item name="android:textSize">@dimen/notification_subtext_size</item>
</style>
<style name="TextAppearance.StatusBar.Quantum.EventContent.Info">
<item name="android:textSize">@dimen/notification_subtext_size</item>
<item name="android:textColor">#888888</item>
</style>
<style name="TextAppearance.StatusBar.Quantum.EventContent.Time">
<item name="android:textSize">@dimen/notification_subtext_size</item>
<item name="android:textColor">#888888</item>
</style>
<style name="TextAppearance.StatusBar.Quantum.EventContent.Emphasis">
<item name="android:textColor">#555555</item>
</style>
<style name="TextAppearance.Small.CalendarViewWeekDayView">
<item name="android:textStyle">bold</item>
</style>

View File

@@ -1627,7 +1627,16 @@
<java-symbol type="integer" name="config_maxResolverActivityColumns" />
<java-symbol type="array" name="config_notificationScorers" />
<!-- From SystemUI -->
<java-symbol type="layout" name="notification_quantum_action" />
<java-symbol type="layout" name="notification_quantum_action_list" />
<java-symbol type="layout" name="notification_quantum_action_tombstone" />
<java-symbol type="layout" name="notification_template_quantum_base" />
<java-symbol type="layout" name="notification_template_quantum_big_base" />
<java-symbol type="layout" name="notification_template_quantum_big_picture" />
<java-symbol type="layout" name="notification_template_quantum_big_text" />
<java-symbol type="layout" name="notification_template_quantum_inbox" />
<!-- From SystemUI -->
<java-symbol type="anim" name="push_down_in" />
<java-symbol type="anim" name="push_down_out" />
<java-symbol type="anim" name="push_up_in" />

View File

@@ -0,0 +1,22 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="oval">
<solid
android:color="@color/notification_icon_legacy_bg_color"/>
</shape>

View File

@@ -0,0 +1,21 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright (C) 2014 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
-->
<inset xmlns:android="http://schemas.android.com/apk/res/android"
android:drawable="@drawable/notification_icon_legacy_bg" android:insetBottom="8dp"
android:insetLeft="8dp" android:insetRight="8dp" android:insetTop="8dp"
android:visible="true"/>

View File

@@ -39,6 +39,8 @@
<color name="status_bar_clock_color">#FFFFFFFF</color>
<drawable name="notification_item_background_color">#ff111111</drawable>
<drawable name="notification_item_background_color_pressed">#ff454545</drawable>
<color name="notification_icon_legacy_bg_color">#ff4285F4</color>
<color name="notification_action_legacy_color_filter">#ff555555</color>
<!-- Tint color for inactive Quick Settings icons. -->
<color name="ic_qs_off">#ff404040</color>

View File

@@ -0,0 +1,82 @@
/*
* Copyright (C) 2014 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
*/
package com.android.systemui;
import android.graphics.Bitmap;
/**
* Utility class for image analysis and processing.
*/
public class ImageUtils {
// Amount (max is 255) that two channels can differ before the color is no longer "gray".
private static final int TOLERANCE = 20;
// Alpha amount for which values below are considered transparent.
private static final int ALPHA_TOLERANCE = 50;
private int[] mTempBuffer;
/**
* Checks whether a bitmap is grayscale. Grayscale here means "very close to a perfect
* gray".
*/
public boolean isGrayscale(Bitmap bitmap) {
final int height = bitmap.getHeight();
final int width = bitmap.getWidth();
int size = height*width;
ensureBufferSize(size);
bitmap.getPixels(mTempBuffer, 0, width, 0, 0, width, height);
for (int i = 0; i < size; i++) {
if (!isGrayscale(mTempBuffer[i])) {
return false;
}
}
return true;
}
/**
* Makes sure that {@code mTempBuffer} has at least length {@code size}.
*/
private void ensureBufferSize(int size) {
if (mTempBuffer == null || mTempBuffer.length < size) {
mTempBuffer = new int[size];
}
}
/**
* Classifies a color as grayscale or not. Grayscale here means "very close to a perfect
* gray"; if all three channels are approximately equal, this will return true.
*
* Note that really transparent colors are always grayscale.
*/
public boolean isGrayscale(int color) {
int alpha = 0xFF & (color >> 24);
if (alpha < ALPHA_TOLERANCE) {
return true;
}
int r = 0xFF & (color >> 16);
int g = 0xFF & (color >> 8);
int b = 0xFF & color;
return Math.abs(r - g) < TOLERANCE
&& Math.abs(r - b) < TOLERANCE
&& Math.abs(g - b) < TOLERANCE;
}
}

View File

@@ -28,9 +28,15 @@ import android.content.IntentFilter;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageManager.NameNotFoundException;
import android.content.res.ColorStateList;
import android.content.res.Configuration;
import android.database.ContentObserver;
import android.graphics.Color;
import android.graphics.PorterDuff;
import android.graphics.Rect;
import android.graphics.drawable.AnimationDrawable;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.net.Uri;
import android.os.Build;
import android.os.Handler;
@@ -44,9 +50,13 @@ import android.provider.Settings;
import android.service.dreams.DreamService;
import android.service.dreams.IDreamManager;
import android.service.notification.StatusBarNotification;
import android.text.SpannableStringBuilder;
import android.text.Spanned;
import android.text.TextUtils;
import android.text.style.TextAppearanceSpan;
import android.util.Log;
import android.util.SparseBooleanArray;
import android.view.ContextThemeWrapper;
import android.view.Display;
import android.view.IWindowManager;
import android.view.LayoutInflater;
@@ -57,6 +67,7 @@ import android.view.ViewGroup;
import android.view.ViewGroup.LayoutParams;
import android.view.WindowManager;
import android.view.WindowManagerGlobal;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.PopupMenu;
@@ -67,6 +78,7 @@ import com.android.internal.statusbar.IStatusBarService;
import com.android.internal.statusbar.StatusBarIcon;
import com.android.internal.statusbar.StatusBarIconList;
import com.android.internal.widget.SizeAdaptiveLayout;
import com.android.systemui.ImageUtils;
import com.android.systemui.R;
import com.android.systemui.RecentsComponent;
import com.android.systemui.SearchPanelView;
@@ -76,6 +88,7 @@ import com.android.systemui.statusbar.policy.NotificationRowLayout;
import java.util.ArrayList;
import java.util.Locale;
import java.util.Stack;
public abstract class BaseStatusBar extends SystemUI implements
CommandQueue.Callbacks {
@@ -140,6 +153,8 @@ public abstract class BaseStatusBar extends SystemUI implements
// public mode, private notifications, etc
private boolean mLockscreenPublicMode = false;
private final SparseBooleanArray mUsersAllowingPrivateNotifications = new SparseBooleanArray();
private Context mLightThemeContext;
private ImageUtils mImageUtils = new ImageUtils();
// UI-specific methods
@@ -261,6 +276,8 @@ public abstract class BaseStatusBar extends SystemUI implements
true,
mLockscreenSettingsObserver,
UserHandle.USER_ALL);
mLightThemeContext = new RemoteViewsThemeContextWrapper(mContext,
android.R.style.Theme_Holo_Light);
mBarService = IStatusBarService.Stub.asInterface(
ServiceManager.getService(Context.STATUS_BAR_SERVICE));
@@ -412,6 +429,158 @@ public abstract class BaseStatusBar extends SystemUI implements
}
}
private void processLegacyHoloNotification(StatusBarNotification sbn, View content) {
// TODO: Also skip processing if it is a holo-style notification.
// If the notification is custom, we can't process it.
if (!sbn.getNotification().extras.getBoolean(Notification.EXTRA_BUILDER_REMOTE_VIEWS)) {
return;
}
processLegacyHoloLargeIcon(content);
processLegacyHoloActions(content);
processLegacyNotificationIcon(content);
processLegacyTextViews(content);
}
/**
* @return the context to be used for the inflation of the specified {@code sbn}; this is
* dependent whether the notification is quantum-style or holo-style
*/
private Context getInflationContext(StatusBarNotification sbn) {
// TODO: Adjust this logic when we change the theme of the status bar windows.
if (sbn.getNotification().extras.getBoolean(Notification.EXTRA_BUILDER_REMOTE_VIEWS)) {
return mLightThemeContext;
} else {
return mContext;
}
}
private void processLegacyNotificationIcon(View content) {
View v = content.findViewById(com.android.internal.R.id.right_icon);
if (v != null & v instanceof ImageView) {
ImageView iv = (ImageView) v;
Drawable d = iv.getDrawable();
if (isMonochrome(d)) {
d.mutate();
d.setColorFilter(mLightThemeContext.getResources().getColor(
R.color.notification_action_legacy_color_filter), PorterDuff.Mode.MULTIPLY);
}
}
}
private void processLegacyHoloLargeIcon(View content) {
View v = content.findViewById(com.android.internal.R.id.icon);
if (v != null & v instanceof ImageView) {
ImageView iv = (ImageView) v;
if (isMonochrome(iv.getDrawable())) {
iv.setBackground(mLightThemeContext.getResources().getDrawable(
R.drawable.notification_icon_legacy_bg_inset));
}
}
}
private boolean isMonochrome(Drawable d) {
if (d == null) {
return false;
} else if (d instanceof BitmapDrawable) {
BitmapDrawable bd = (BitmapDrawable) d;
return bd.getBitmap() != null && mImageUtils.isGrayscale(bd.getBitmap());
} else if (d instanceof AnimationDrawable) {
AnimationDrawable ad = (AnimationDrawable) d;
int count = ad.getNumberOfFrames();
return count > 0 && isMonochrome(ad.getFrame(0));
} else {
return false;
}
}
private void processLegacyHoloActions(View content) {
View v = content.findViewById(com.android.internal.R.id.actions);
if (v != null & v instanceof ViewGroup) {
ViewGroup vg = (ViewGroup) v;
int childCount = vg.getChildCount();
for (int i = 0; i < childCount; i++) {
View child = vg.getChildAt(i);
if (child instanceof Button) {
Button button = (Button) child;
Drawable[] compoundDrawables = button.getCompoundDrawablesRelative();
if (isMonochrome(compoundDrawables[0])) {
Drawable d = compoundDrawables[0];
d.mutate();
d.setColorFilter(mLightThemeContext.getResources().getColor(
R.color.notification_action_legacy_color_filter),
PorterDuff.Mode.MULTIPLY);
}
}
}
}
}
private void processLegacyTextViews(View content) {
Stack<View> viewStack = new Stack<View>();
viewStack.push(content);
while(!viewStack.isEmpty()) {
View current = viewStack.pop();
if(current instanceof ViewGroup){
ViewGroup currentGroup = (ViewGroup) current;
int numChildren = currentGroup.getChildCount();
for(int i=0;i<numChildren;i++){
viewStack.push(currentGroup.getChildAt(i));
}
}
if (current instanceof TextView) {
processLegacyTextView((TextView) current);
}
}
}
private void processLegacyTextView(TextView textView) {
if (textView.getText() instanceof Spanned) {
Spanned ss = (Spanned) textView.getText();
Object[] spans = ss.getSpans(0, ss.length(), Object.class);
SpannableStringBuilder builder = new SpannableStringBuilder(ss.toString());
for (Object span : spans) {
Object resultSpan = span;
if (span instanceof TextAppearanceSpan) {
resultSpan = processTextAppearanceSpan((TextAppearanceSpan) span);
}
builder.setSpan(resultSpan, ss.getSpanStart(span), ss.getSpanEnd(span),
ss.getSpanFlags(span));
}
textView.setText(builder);
}
}
private TextAppearanceSpan processTextAppearanceSpan(TextAppearanceSpan span) {
ColorStateList colorStateList = span.getTextColor();
if (colorStateList != null) {
int[] colors = colorStateList.getColors();
boolean changed = false;
for (int i = 0; i < colors.length; i++) {
if (mImageUtils.isGrayscale(colors[i])) {
colors[i] = processColor(colors[i]);
changed = true;
}
}
if (changed) {
return new TextAppearanceSpan(
span.getFamily(), span.getTextStyle(), span.getTextSize(),
new ColorStateList(colorStateList.getStates(), colors),
span.getLinkTextColor());
}
}
return span;
}
private int processColor(int color) {
return Color.argb(Color.alpha(color),
255 - Color.red(color),
255 - Color.green(color),
255 - Color.blue(color));
}
private void startApplicationDetailsActivity(String packageName) {
Intent intent = new Intent(Settings.ACTION_APPLICATION_DETAILS_SETTINGS,
Uri.fromParts("package", packageName, null));
@@ -748,9 +917,11 @@ public abstract class BaseStatusBar extends SystemUI implements
View contentViewLocal = null;
View bigContentViewLocal = null;
try {
contentViewLocal = contentView.apply(mContext, expanded, mOnClickHandler);
contentViewLocal = contentView.apply(getInflationContext(sbn), expanded,
mOnClickHandler);
if (bigContentView != null) {
bigContentViewLocal = bigContentView.apply(mContext, expanded, mOnClickHandler);
bigContentViewLocal = bigContentView.apply(getInflationContext(sbn), expanded,
mOnClickHandler);
}
}
catch (RuntimeException e) {
@@ -780,7 +951,7 @@ public abstract class BaseStatusBar extends SystemUI implements
View publicViewLocal = null;
if (publicNotification != null) {
try {
publicViewLocal = publicNotification.contentView.apply(mContext,
publicViewLocal = publicNotification.contentView.apply(getInflationContext(sbn),
expandedPublic, mOnClickHandler);
if (publicViewLocal != null) {
@@ -831,6 +1002,13 @@ public abstract class BaseStatusBar extends SystemUI implements
row.setDrawingCacheEnabled(true);
applyLegacyRowBackground(sbn, content);
processLegacyHoloNotification(sbn, contentViewLocal);
if (bigContentViewLocal != null) {
processLegacyHoloNotification(sbn, bigContentViewLocal);
}
if (publicViewLocal != null) {
processLegacyHoloNotification(sbn, publicViewLocal);
}
if (MULTIUSER_DEBUG) {
TextView debug = (TextView) row.findViewById(R.id.debug_info);
@@ -1245,12 +1423,17 @@ public abstract class BaseStatusBar extends SystemUI implements
: null;
// Reapply the RemoteViews
contentView.reapply(mContext, entry.expanded, mOnClickHandler);
contentView.reapply(getInflationContext(notification), entry.expanded, mOnClickHandler);
processLegacyHoloNotification(notification, entry.expanded);
if (bigContentView != null && entry.getBigContentView() != null) {
bigContentView.reapply(mContext, entry.getBigContentView(), mOnClickHandler);
bigContentView.reapply(getInflationContext(notification), entry.getBigContentView(),
mOnClickHandler);
processLegacyHoloNotification(notification, entry.getBigContentView());
}
if (publicContentView != null && entry.getPublicContentView() != null) {
publicContentView.reapply(mContext, entry.getPublicContentView(), mOnClickHandler);
publicContentView.reapply(getInflationContext(notification),
entry.getPublicContentView(), mOnClickHandler);
processLegacyHoloNotification(notification, entry.getPublicContentView());
}
// update the contentIntent
final PendingIntent contentIntent = notification.getNotification().contentIntent;
@@ -1330,4 +1513,35 @@ public abstract class BaseStatusBar extends SystemUI implements
}
mContext.unregisterReceiver(mBroadcastReceiver);
}
/**
* A custom context theme wrapper that applies a platform theme to a created package context.
* This is useful if you want to inflate {@link RemoteViews} with a custom theme (normally, the
* theme used there is the default platform theme).
*/
private static class RemoteViewsThemeContextWrapper extends ContextThemeWrapper {
private int mThemeRes;
private RemoteViewsThemeContextWrapper(Context base, int themeres) {
super(base, themeres);
mThemeRes = themeres;
}
@Override
public Context createPackageContextAsUser(String packageName, int flags, UserHandle user)
throws NameNotFoundException {
Context c = super.createPackageContextAsUser(packageName, flags, user);
c.setTheme(mThemeRes);
return c;
}
@Override
public Context createPackageContext(String packageName, int flags)
throws NameNotFoundException {
Context c = super.createPackageContext(packageName, flags);
c.setTheme(mThemeRes);
return c;
}
}
}