From 3b230077dc53c1f83aa6e9b70585148d8193dd82 Mon Sep 17 00:00:00 2001 From: Jason Monk Date: Fri, 29 May 2015 11:11:29 -0400 Subject: Tuner: Let Status bar be tuned Also fix a crash in the QSTuner Bug: 21192440 Change-Id: Ideb8e34b93a4b456d758266dfc06545e7f7ab109 --- packages/SystemUI/res/values/strings.xml | 15 ++++++ packages/SystemUI/res/xml/tuner_prefs.xml | 63 ++++++++++++++++++---- .../systemui/statusbar/SignalClusterView.java | 45 ++++++++++++++-- .../systemui/statusbar/StatusBarIconView.java | 15 +++++- .../statusbar/phone/StatusBarIconController.java | 57 +++++++++++++++++++- .../src/com/android/systemui/tuner/QsTuner.java | 55 +++++++++++++++---- .../android/systemui/tuner/StatusBarSwitch.java | 58 ++++++++++++++++++++ 7 files changed, 279 insertions(+), 29 deletions(-) create mode 100644 packages/SystemUI/src/com/android/systemui/tuner/StatusBarSwitch.java diff --git a/packages/SystemUI/res/values/strings.xml b/packages/SystemUI/res/values/strings.xml index d96ed96..6af69d2 100644 --- a/packages/SystemUI/res/values/strings.xml +++ b/packages/SystemUI/res/values/strings.xml @@ -1034,6 +1034,21 @@ Quick Settings + + Status bar + + + Ethernet + + + Alarm + + + Work profile + + + Airplane mode + Add tile diff --git a/packages/SystemUI/res/xml/tuner_prefs.xml b/packages/SystemUI/res/xml/tuner_prefs.xml index 135cc82..4e9a407 100644 --- a/packages/SystemUI/res/xml/tuner_prefs.xml +++ b/packages/SystemUI/res/xml/tuner_prefs.xml @@ -15,16 +15,61 @@ --> + android:title="@string/system_ui_tuner"> - + - + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/SignalClusterView.java b/packages/SystemUI/src/com/android/systemui/statusbar/SignalClusterView.java index a66f8ec..02e196e 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/SignalClusterView.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/SignalClusterView.java @@ -18,10 +18,13 @@ package com.android.systemui.statusbar; import android.content.Context; import android.content.res.ColorStateList; +import android.database.ContentObserver; import android.graphics.Color; import android.graphics.PorterDuff; import android.graphics.drawable.Animatable; import android.graphics.drawable.Drawable; +import android.os.Handler; +import android.provider.Settings; import android.telephony.SubscriptionInfo; import android.util.AttributeSet; import android.util.Log; @@ -33,6 +36,7 @@ import android.widget.ImageView; import android.widget.LinearLayout; import com.android.systemui.R; +import com.android.systemui.statusbar.phone.StatusBarIconController; import com.android.systemui.statusbar.policy.NetworkController.IconState; import com.android.systemui.statusbar.policy.NetworkControllerImpl; import com.android.systemui.statusbar.policy.SecurityController; @@ -49,6 +53,11 @@ public class SignalClusterView static final String TAG = "SignalClusterView"; static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG); + private static final String SLOT_AIRPLANE = "airplane"; + private static final String SLOT_MOBILE = "mobile"; + private static final String SLOT_WIFI = "wifi"; + private static final String SLOT_ETHERNET = "ethernet"; + NetworkControllerImpl mNC; SecurityController mSC; @@ -81,6 +90,11 @@ public class SignalClusterView private int mEndPadding; private int mEndPaddingNothingVisible; + private boolean mBlockAirplane; + private boolean mBlockMobile; + private boolean mBlockWifi; + private boolean mBlockEthernet; + public SignalClusterView(Context context) { this(context, null); } @@ -91,6 +105,14 @@ public class SignalClusterView public SignalClusterView(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); + readBlacklist(); + } + + private void readBlacklist() { + mBlockAirplane = StatusBarIconController.isBlocked(getContext(), SLOT_AIRPLANE); + mBlockMobile = StatusBarIconController.isBlocked(getContext(), SLOT_MOBILE); + mBlockWifi = StatusBarIconController.isBlocked(getContext(), SLOT_WIFI); + mBlockEthernet = StatusBarIconController.isBlocked(getContext(), SLOT_ETHERNET); } public void setNetworkController(NetworkControllerImpl nc) { @@ -141,6 +163,9 @@ public class SignalClusterView apply(); applyIconTint(); + getContext().getContentResolver().registerContentObserver( + Settings.Secure.getUriFor(StatusBarIconController.ICON_BLACKLIST), false, + mBlacklistObserver); } @Override @@ -153,6 +178,7 @@ public class SignalClusterView mAirplane = null; mMobileSignalGroup.removeAllViews(); mMobileSignalGroup = null; + getContext().getContentResolver().unregisterContentObserver(mBlacklistObserver); super.onDetachedFromWindow(); } @@ -172,7 +198,7 @@ public class SignalClusterView @Override public void setWifiIndicators(boolean enabled, IconState statusIcon, IconState qsIcon, boolean activityIn, boolean activityOut, String description) { - mWifiVisible = statusIcon.visible; + mWifiVisible = statusIcon.visible && !mBlockWifi; mWifiStrengthId = statusIcon.icon; mWifiDescription = statusIcon.contentDescription; @@ -184,7 +210,7 @@ public class SignalClusterView int qsType, boolean activityIn, boolean activityOut, String typeContentDescription, String description, boolean isWide, int subId) { PhoneState state = getOrInflateState(subId); - state.mMobileVisible = statusIcon.visible; + state.mMobileVisible = statusIcon.visible && !mBlockMobile; state.mMobileStrengthId = statusIcon.icon; state.mMobileTypeId = statusType; state.mMobileDescription = statusIcon.contentDescription; @@ -196,7 +222,7 @@ public class SignalClusterView @Override public void setEthernetIndicators(IconState state) { - mEthernetVisible = state.visible; + mEthernetVisible = state.visible && !mBlockEthernet; mEthernetIconId = state.icon; mEthernetDescription = state.contentDescription; @@ -205,7 +231,7 @@ public class SignalClusterView @Override public void setNoSims(boolean show) { - mNoSimsVisible = show; + mNoSimsVisible = show && !mBlockMobile; } @Override @@ -244,7 +270,7 @@ public class SignalClusterView @Override public void setIsAirplaneMode(IconState icon) { - mIsAirplaneMode = icon.visible; + mIsAirplaneMode = icon.visible && !mBlockAirplane; mAirplaneIconId = icon.icon; mAirplaneContentDescription = icon.contentDescription; @@ -502,5 +528,14 @@ public class SignalClusterView setTint(mMobileType, tint); } } + + private final ContentObserver mBlacklistObserver = new ContentObserver(new Handler()) { + public void onChange(boolean selfChange) { + readBlacklist(); + // Re-register to get new callbacks. + mNC.removeSignalCallback(SignalClusterView.this); + mNC.addSignalCallback(SignalClusterView.this); + }; + }; } diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/StatusBarIconView.java b/packages/SystemUI/src/com/android/systemui/statusbar/StatusBarIconView.java index 3294e15..baac8ac 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/StatusBarIconView.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/StatusBarIconView.java @@ -18,7 +18,6 @@ package com.android.systemui.statusbar; import android.app.Notification; import android.content.Context; -import android.content.pm.PackageManager; import android.content.res.Resources; import android.graphics.Canvas; import android.graphics.Paint; @@ -49,10 +48,17 @@ public class StatusBarIconView extends AnimatedImageView { private int mNumberY; private String mNumberText; private Notification mNotification; + private final boolean mBlocked; public StatusBarIconView(Context context, String slot, Notification notification) { + this(context, slot, notification, false); + } + + public StatusBarIconView(Context context, String slot, Notification notification, + boolean blocked) { super(context); final Resources res = context.getResources(); + mBlocked = blocked; mSlot = slot; mNumberPain = new Paint(); mNumberPain.setTextAlign(Paint.Align.CENTER); @@ -80,6 +86,7 @@ public class StatusBarIconView extends AnimatedImageView { public StatusBarIconView(Context context, AttributeSet attrs) { super(context, attrs); + mBlocked = false; final Resources res = context.getResources(); final int outerBounds = res.getDimensionPixelSize(R.dimen.status_bar_icon_size); final int imageBounds = res.getDimensionPixelSize(R.dimen.status_bar_icon_drawing_size); @@ -148,7 +155,7 @@ public class StatusBarIconView extends AnimatedImageView { invalidate(); } if (!visibilityEquals) { - setVisibility(icon.visible ? VISIBLE : GONE); + setVisibility(icon.visible && !mBlocked ? VISIBLE : GONE); } return true; } @@ -281,4 +288,8 @@ public class StatusBarIconView extends AnimatedImageView { return "StatusBarIconView(slot=" + mSlot + " icon=" + mIcon + " notification=" + mNotification + ")"; } + + public String getSlot() { + return mSlot; + } } diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarIconController.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarIconController.java index 45da297..a268077 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarIconController.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarIconController.java @@ -20,10 +20,14 @@ import android.animation.ArgbEvaluator; import android.animation.ValueAnimator; import android.content.Context; import android.content.res.ColorStateList; +import android.database.ContentObserver; import android.graphics.Color; import android.os.Bundle; import android.os.Handler; import android.os.SystemClock; +import android.provider.Settings; +import android.text.TextUtils; +import android.util.ArraySet; import android.view.View; import android.view.ViewGroup; import android.view.animation.AnimationUtils; @@ -53,6 +57,8 @@ public class StatusBarIconController { public static final long DEFAULT_TINT_ANIMATION_DURATION = 120; + public static final String ICON_BLACKLIST = "icon_blacklist"; + private Context mContext; private PhoneStatusBar mPhoneStatusBar; private Interpolator mLinearOutSlowIn; @@ -89,6 +95,8 @@ public class StatusBarIconController { private long mTransitionDeferringStartTime; private long mTransitionDeferringDuration; + private final ArraySet mIconBlacklist; + private final Runnable mTransitionDeferringDoneRunnable = new Runnable() { @Override public void run() { @@ -118,7 +126,12 @@ public class StatusBarIconController { mDarkModeIconColorSingleTone = context.getColor(R.color.dark_mode_icon_color_single_tone); mLightModeIconColorSingleTone = context.getColor(R.color.light_mode_icon_color_single_tone); mHandler = new Handler(); + mIconBlacklist = getIconBlacklist(context); updateResources(); + + context.getContentResolver().registerContentObserver( + Settings.Secure.getUriFor(StatusBarIconController.ICON_BLACKLIST), false, + mBlacklistObserver); } public void updateResources() { @@ -130,11 +143,12 @@ public class StatusBarIconController { } public void addSystemIcon(String slot, int index, int viewIndex, StatusBarIcon icon) { - StatusBarIconView view = new StatusBarIconView(mContext, slot, null); + boolean blocked = mIconBlacklist.contains(slot); + StatusBarIconView view = new StatusBarIconView(mContext, slot, null, blocked); view.set(icon); mStatusIcons.addView(view, viewIndex, new LinearLayout.LayoutParams( ViewGroup.LayoutParams.WRAP_CONTENT, mIconSize)); - view = new StatusBarIconView(mContext, slot, null); + view = new StatusBarIconView(mContext, slot, null, blocked); view.set(icon); mStatusIconsKeyguard.addView(view, viewIndex, new LinearLayout.LayoutParams( ViewGroup.LayoutParams.WRAP_CONTENT, mIconSize)); @@ -414,4 +428,43 @@ public class StatusBarIconController { } mTransitionPending = false; } + + private final ContentObserver mBlacklistObserver = new ContentObserver(new Handler()) { + public void onChange(boolean selfChange) { + mIconBlacklist.clear(); + mIconBlacklist.addAll(getIconBlacklist(mContext)); + ArrayList views = new ArrayList(); + // Get all the current views. + for (int i = 0; i < mStatusIcons.getChildCount(); i++) { + views.add((StatusBarIconView) mStatusIcons.getChildAt(i)); + } + // Remove all the icons. + for (int i = views.size() - 1; i >= 0; i--) { + removeSystemIcon(views.get(i).getSlot(), i, i); + } + // Add them all back + for (int i = 0; i < views.size(); i++) { + addSystemIcon(views.get(i).getSlot(), i, i, views.get(i).getStatusBarIcon()); + } + } + }; + + public static ArraySet getIconBlacklist(Context context) { + String blackListStr = Settings.Secure.getString(context.getContentResolver(), + ICON_BLACKLIST); + ArraySet ret = new ArraySet(); + if (blackListStr != null) { + String[] blacklist = blackListStr.split(","); + for (String slot : blacklist) { + if (!TextUtils.isEmpty(slot)) { + ret.add(slot); + } + } + } + return ret; + } + + public static boolean isBlocked(Context context, String slot) { + return getIconBlacklist(context).contains(slot); + } } diff --git a/packages/SystemUI/src/com/android/systemui/tuner/QsTuner.java b/packages/SystemUI/src/com/android/systemui/tuner/QsTuner.java index 90c1897..9f593fc 100644 --- a/packages/SystemUI/src/com/android/systemui/tuner/QsTuner.java +++ b/packages/SystemUI/src/com/android/systemui/tuner/QsTuner.java @@ -22,6 +22,7 @@ import android.content.Context; import android.content.DialogInterface; import android.os.Bundle; import android.provider.Settings.Secure; +import android.text.TextUtils; import android.util.Log; import android.view.DragEvent; import android.view.LayoutInflater; @@ -32,7 +33,6 @@ import android.view.MotionEvent; import android.view.View; import android.view.View.OnClickListener; import android.view.View.OnDragListener; -import android.view.View.OnLongClickListener; import android.view.View.OnTouchListener; import android.view.ViewGroup; import android.widget.EditText; @@ -47,6 +47,7 @@ import com.android.systemui.qs.QSTile.ResourceIcon; import com.android.systemui.qs.QSTileView; import com.android.systemui.qs.tiles.IntentTile; import com.android.systemui.statusbar.phone.QSTileHost; +import com.android.systemui.statusbar.policy.SecurityController; import java.util.List; @@ -174,7 +175,7 @@ public class QsTuner extends Fragment implements Callback { public CustomHost(Context context) { super(context, null, null, null, null, null, null, null, null, null, - null, null, null); + null, null, new BlankSecurityController()); } @Override @@ -215,15 +216,8 @@ public class QsTuner extends Fragment implements Callback { } private void setTiles(List tiles) { - StringBuilder builder = new StringBuilder(); - for (int i = 0; i < tiles.size(); i++) { - if (builder.length() != 0) { - builder.append(','); - } - builder.append(tiles.get(i)); - } - Secure.putStringForUser(getContext().getContentResolver(), - TILES_SETTING, builder.toString(), mUserTracker.getCurrentUserId()); + Secure.putStringForUser(getContext().getContentResolver(), TILES_SETTING, + TextUtils.join(",", tiles), mUserTracker.getCurrentUserId()); } public void showAddDialog() { @@ -282,6 +276,45 @@ public class QsTuner extends Fragment implements Callback { } return true; } + + private static class BlankSecurityController implements SecurityController { + @Override + public boolean hasDeviceOwner() { + return false; + } + + @Override + public boolean hasProfileOwner() { + return false; + } + + @Override + public String getDeviceOwnerName() { + return null; + } + + @Override + public String getProfileOwnerName() { + return null; + } + + @Override + public boolean isVpnEnabled() { + return false; + } + + @Override + public void onUserSwitched(int newUserId) { + } + + @Override + public void addCallback(SecurityControllerCallback callback) { + } + + @Override + public void removeCallback(SecurityControllerCallback callback) { + } + } } private static class DraggableTile extends QSTile diff --git a/packages/SystemUI/src/com/android/systemui/tuner/StatusBarSwitch.java b/packages/SystemUI/src/com/android/systemui/tuner/StatusBarSwitch.java new file mode 100644 index 0000000..8158a68 --- /dev/null +++ b/packages/SystemUI/src/com/android/systemui/tuner/StatusBarSwitch.java @@ -0,0 +1,58 @@ +/* + * Copyright (C) 2015 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.tuner; + +import android.content.ContentResolver; +import android.content.Context; +import android.preference.SwitchPreference; +import android.provider.Settings; +import android.text.TextUtils; +import android.util.AttributeSet; + +import com.android.systemui.statusbar.phone.StatusBarIconController; + +import java.util.Set; + +public class StatusBarSwitch extends SwitchPreference { + + public StatusBarSwitch(Context context, AttributeSet attrs) { + super(context, attrs); + setChecked(!StatusBarIconController.isBlocked(getContext(), getKey())); + } + + @Override + protected boolean persistBoolean(boolean value) { + Set blacklist = StatusBarIconController.getIconBlacklist(getContext()); + if (!value) { + // If not enabled add to blacklist. + if (!blacklist.contains(getKey())) { + blacklist.add(getKey()); + setList(blacklist); + } + } else { + if (blacklist != null && blacklist.remove(getKey())) { + setList(blacklist); + } + } + return true; + } + + private void setList(Set blacklist) { + ContentResolver contentResolver = getContext().getContentResolver(); + Settings.Secure.putString(contentResolver, StatusBarIconController.ICON_BLACKLIST, + TextUtils.join(",", blacklist)); + } +} -- cgit v1.1