From 26c932ea37148f4d336e6a69adf057bf8ddcb09e Mon Sep 17 00:00:00 2001 From: Roman Birg Date: Wed, 4 May 2016 13:51:55 -0700 Subject: SystemUI: implement properly saving tile locations Use new persisted key which does not use the tiles' ID (which changes usually across reboots with every tile). When the Custom tile service comes up, it will update the placeholder tiles created with their real values and the order is preserved properly. Ticket: CYNGNOS-2530 Change-Id: I5e75c739553969f1d92c249f521a476259fe0cd6 Signed-off-by: Roman Birg --- .../src/com/android/systemui/qs/QSDragPanel.java | 159 ++++++++++++--------- .../android/systemui/qs/tiles/CustomQSTile.java | 30 +++- .../android/systemui/statusbar/CustomTileData.java | 2 +- .../systemui/statusbar/phone/PhoneStatusBar.java | 4 +- .../systemui/statusbar/phone/QSTileHost.java | 15 +- 5 files changed, 132 insertions(+), 78 deletions(-) (limited to 'packages/SystemUI/src/com/android/systemui') diff --git a/packages/SystemUI/src/com/android/systemui/qs/QSDragPanel.java b/packages/SystemUI/src/com/android/systemui/qs/QSDragPanel.java index a6a824a..ce2d94c 100644 --- a/packages/SystemUI/src/com/android/systemui/qs/QSDragPanel.java +++ b/packages/SystemUI/src/com/android/systemui/qs/QSDragPanel.java @@ -68,6 +68,7 @@ import org.cyanogenmod.internal.util.QSConstants; import org.cyanogenmod.internal.util.QSUtils; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.Iterator; @@ -1901,7 +1902,8 @@ public class QSDragPanel extends QSPanel implements View.OnDragListener, View.On final Iterator i = tiles.iterator(); while (i.hasNext()) { final String spec = i.next(); - if (QSUtils.isStaticQsTile(spec) || QSUtils.isDynamicQsTile(spec)) { + if (QSUtils.isStaticQsTile(spec) + || QSUtils.isDynamicQsTile(extractTileTagFromSpec(spec))) { List packageList = mPackageTileMap.get(PACKAGE_ANDROID); packageList.add(spec); } else { @@ -1919,13 +1921,14 @@ public class QSDragPanel extends QSPanel implements View.OnDragListener, View.On if (entry.getValue() instanceof Boolean) { if ((Boolean)entry.getValue()) { final String key = entry.getKey(); - if (QSUtils.isDynamicQsTile(key)) { + if (QSUtils.isDynamicQsTile(extractTileTagFromSpec(key))) { mPackageTileMap.get(PACKAGE_ANDROID).add(key); } else { final String customTilePackage = getCustomTilePackage(key); List packageList = mPackageTileMap.get(customTilePackage); if (packageList == null) { - mPackageTileMap.put(customTilePackage, packageList = new ArrayList<>()); + mPackageTileMap.put(customTilePackage, + packageList = new ArrayList<>()); } packageList.add(key); @@ -1939,8 +1942,95 @@ public class QSDragPanel extends QSPanel implements View.OnDragListener, View.On } private String getCustomTilePackage(String spec) { - StatusBarPanelCustomTile sbc = mHost.getCustomTileData().get(spec).sbc; - return sbc.getPackage(); + if (mHost.getCustomTileData().get(spec) != null) { + StatusBarPanelCustomTile sbc = mHost.getCustomTileData().get(spec).sbc; + return sbc.getPackage(); + } else { + return extractPackageFromCustomTileSpec(spec); + } + } + + private static String extractPackageFromCustomTileSpec(String spec) { + if (spec != null && !spec.isEmpty()) { + final String[] split = spec.split("\\|"); + if (split != null && split.length > 2) { + return split[1]; + } + } + return null; + } + + private static String extractTileTagFromSpec(String spec) { + if (spec != null && !spec.isEmpty()) { + final String[] split = spec.split("\\|"); + if (split != null && split.length == 5) { + /** for {@link cyanogenmod.app.StatusBarPanelCustomTile#key() **/ + return split[3]; + } else if (split != null && split.length == 3) { + /** for {@link cyanogenmod.app.StatusBarPanelCustomTile#persistableKey()} **/ + return split[2]; + } + } + return null; + } + + private Drawable getQSTileIcon(String spec) { + if (QSUtils.isDynamicQsTile(spec)) { + return QSTile.ResourceIcon.get( + QSUtils.getDynamicQSTileResIconId(mContext, UserHandle.myUserId(), spec)) + .getDrawable(mContext); + } else if (QSUtils.isStaticQsTile(spec)) { + final int res = QSTileHost.getIconResource(spec); + if (res != 0) { + return QSTile.ResourceIcon.get(res).getDrawable(mContext); + } else { + return mContext.getPackageManager().getDefaultActivityIcon(); + } + } else { + QSTile tile = mHost.getTile(spec); + if (tile != null) { + QSTile.State state = tile.getState(); + if (state != null && state.icon != null) { + return state.icon.getDrawable(mContext); + } + } + return getPackageDrawable(getCustomTilePackage(spec)); + } + } + + private String getPackageLabel(String packageName) { + try { + return mContext.getPackageManager().getApplicationLabel( + mContext.getPackageManager().getApplicationInfo(packageName, 0)).toString(); + } catch (PackageManager.NameNotFoundException e) { + e.printStackTrace(); + } + return null; + } + + private Drawable getPackageDrawable(String packageName) { + try { + return mContext.getPackageManager().getApplicationIcon(packageName); + } catch (PackageManager.NameNotFoundException e) { + e.printStackTrace(); + } + return null; + } + + private String getQSTileLabel(String spec) { + if (QSUtils.isStaticQsTile(spec)) { + int resource = QSTileHost.getLabelResource(spec); + if (resource != 0) { + return mContext.getText(resource).toString(); + } else { + return spec; + } + } else if (QSUtils.isDynamicQsTile(extractTileTagFromSpec(spec))) { + return QSUtils.getDynamicQSTileLabel(mContext, + UserHandle.myUserId(), extractTileTagFromSpec(spec)); + } else { + return getPackageLabel(getCustomTilePackage(spec)); + } } @Override @@ -2042,65 +2132,6 @@ public class QSDragPanel extends QSPanel implements View.OnDragListener, View.On return child; } - private String getQSTileLabel(String spec) { - if (QSUtils.isStaticQsTile(spec)) { - int resource = QSTileHost.getLabelResource(spec); - if (resource != 0) { - return mContext.getText(resource).toString(); - } else { - return spec; - } - } else if (QSUtils.isDynamicQsTile(spec)) { - return QSUtils.getDynamicQSTileLabel(mContext, - UserHandle.myUserId(), spec); - } else { - return getPackageLabel(getCustomTilePackage(spec)); - } - } - - private Drawable getQSTileIcon(String spec) { - if (QSUtils.isDynamicQsTile(spec)) { - return QSTile.ResourceIcon.get( - QSUtils.getDynamicQSTileResIconId(mContext, UserHandle.myUserId(), spec)) - .getDrawable(mContext); - } else if (QSUtils.isStaticQsTile(spec)) { - final int res = QSTileHost.getIconResource(spec); - if (res != 0) { - return QSTile.ResourceIcon.get(res).getDrawable(mContext); - } else { - return mContext.getPackageManager().getDefaultActivityIcon(); - } - } else { - QSTile tile = mHost.getTile(spec); - if (tile != null) { - QSTile.State state = tile.getState(); - if (state != null && state.icon != null) { - return state.icon.getDrawable(mContext); - } - } - return getPackageDrawable(getCustomTilePackage(spec)); - } - } - - private String getPackageLabel(String packageName) { - try { - return mContext.getPackageManager().getApplicationLabel( - mContext.getPackageManager().getApplicationInfo(packageName, 0)).toString(); - } catch (PackageManager.NameNotFoundException e) { - e.printStackTrace(); - } - return null; - } - - private Drawable getPackageDrawable(String packageName) { - try { - return mContext.getPackageManager().getApplicationIcon(packageName); - } catch (PackageManager.NameNotFoundException e) { - e.printStackTrace(); - } - return null; - } - @Override public boolean isChildSelectable(int groupPosition, int childPosition) { return true; diff --git a/packages/SystemUI/src/com/android/systemui/qs/tiles/CustomQSTile.java b/packages/SystemUI/src/com/android/systemui/qs/tiles/CustomQSTile.java index ca9bed4..40c7184 100644 --- a/packages/SystemUI/src/com/android/systemui/qs/tiles/CustomQSTile.java +++ b/packages/SystemUI/src/com/android/systemui/qs/tiles/CustomQSTile.java @@ -32,15 +32,12 @@ import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.AdapterView; -import android.widget.FrameLayout; import android.widget.ImageView; import android.widget.LinearLayout; import android.widget.ListView; import android.widget.RemoteViews; import android.widget.TextView; -import com.android.internal.logging.MetricsLogger; - import com.android.systemui.qs.QSDetailItemsGrid; import com.android.systemui.qs.QSDetailItemsList; import cyanogenmod.app.CustomTile; @@ -65,6 +62,13 @@ public class CustomQSTile extends QSTile { private CustomQSDetailAdapter mDetailAdapter; private boolean mCollapsePanel; private boolean mUserRemoved; + private String mPersistedPlaceHolderKey; + + public CustomQSTile(Host host, String persistedSpec) { + super(host); + mTile = null; + mPersistedPlaceHolderKey = persistedSpec; + } public CustomQSTile(Host host, StatusBarPanelCustomTile tile) { super(host); @@ -72,8 +76,16 @@ public class CustomQSTile extends QSTile { mUserRemoved = getIsUserRemovedPersisted(); } + private String getPersistableKey() { + if (mPersistedPlaceHolderKey != null) { + return mPersistedPlaceHolderKey; + } else { + return getTile().persistableKey(); + } + } + private boolean getIsUserRemovedPersisted() { - return getCustomQSTilePrefs(mContext).getBoolean(getTile().getKey(), false); + return getCustomQSTilePrefs(mContext).getBoolean(getPersistableKey(), false); } public boolean isUserRemoved() { @@ -83,9 +95,9 @@ public class CustomQSTile extends QSTile { public void setUserRemoved(boolean removed) { if (mUserRemoved != removed) { if (removed) { - getCustomQSTilePrefs(mContext).edit().putBoolean(getTile().getKey(), true).apply(); + getCustomQSTilePrefs(mContext).edit().putBoolean(getPersistableKey(), true).apply(); } else { - getCustomQSTilePrefs(mContext).edit().remove(getTile().getKey()).apply(); + getCustomQSTilePrefs(mContext).edit().remove(getPersistableKey()).apply(); } mUserRemoved = removed; refreshState(); @@ -167,8 +179,14 @@ public class CustomQSTile extends QSTile { protected void handleUpdateState(State state, Object arg) { if (arg instanceof StatusBarPanelCustomTile) { mTile = (StatusBarPanelCustomTile) arg; + mPersistedPlaceHolderKey = null; mUserRemoved = getIsUserRemovedPersisted(); } + if (mTile == null) { + state.visible = false; + // nothing to show, it's a place holder for now + return; + } final CustomTile customTile = mTile.getCustomTile(); state.contentDescription = customTile.contentDescription; state.label = customTile.label; diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/CustomTileData.java b/packages/SystemUI/src/com/android/systemui/statusbar/CustomTileData.java index 4be7292..42974ba 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/CustomTileData.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/CustomTileData.java @@ -29,7 +29,7 @@ public class CustomTileData { public final StatusBarPanelCustomTile sbc; public Entry(StatusBarPanelCustomTile sbc) { - this.key = sbc.getKey(); + this.key = sbc.persistableKey(); this.sbc = sbc; } } diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java index be6feca..9a73aff 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java @@ -1489,7 +1489,7 @@ public class PhoneStatusBar extends BaseStatusBar implements DemoMode, @Override public void run() { boolean isUpdate = mQSPanel.getHost().getCustomTileData() - .get(sbc.getKey()) != null; + .get(sbc.persistableKey()) != null; if (isUpdate) { mQSPanel.getHost().updateCustomTile(sbc); } else { @@ -1505,7 +1505,7 @@ public class PhoneStatusBar extends BaseStatusBar implements DemoMode, mHandler.post(new Runnable() { @Override public void run() { - mQSPanel.getHost().removeCustomTileSysUi(sbc.getKey()); + mQSPanel.getHost().removeCustomTileSysUi(sbc.persistableKey()); } }); } diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/QSTileHost.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/QSTileHost.java index 2c68c62..53310dd 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/QSTileHost.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/QSTileHost.java @@ -372,7 +372,12 @@ public class QSTileHost implements QSTile.Host, Tunable { else if (tileSpec.equals("battery_saver")) return new BatterySaverTile(this); else if (tileSpec.equals("caffeine")) return new CaffeineTile(this); else if (tileSpec.startsWith(IntentTile.PREFIX)) return IntentTile.create(this,tileSpec); - else throw new IllegalArgumentException("Bad tile spec: " + tileSpec); + else if (TextUtils.split(tileSpec, "\\|").length == 3) { + /** restores placeholder for + * {@link cyanogenmod.app.StatusBarPanelCustomTile#persistableKey()} **/ + return new CustomQSTile(this, tileSpec); + } else + throw new IllegalArgumentException("Bad tile spec: " + tileSpec); } protected List loadTileSpecs(String tileList) { @@ -498,8 +503,8 @@ public class QSTileHost implements QSTile.Host, Tunable { void updateCustomTile(StatusBarPanelCustomTile sbc) { synchronized (mTiles) { - if (mTiles.containsKey(sbc.getKey())) { - QSTile tile = mTiles.get(sbc.getKey()); + if (mTiles.containsKey(sbc.persistableKey())) { + QSTile tile = mTiles.get(sbc.persistableKey()); if (tile instanceof CustomQSTile) { CustomQSTile qsTile = (CustomQSTile) tile; qsTile.update(sbc); @@ -511,8 +516,8 @@ public class QSTileHost implements QSTile.Host, Tunable { void addCustomTile(StatusBarPanelCustomTile sbc) { synchronized (mTiles) { mCustomTileData.add(new CustomTileData.Entry(sbc)); - mTileSpecs.add(sbc.getKey()); - mTiles.put(sbc.getKey(), new CustomQSTile(this, sbc)); + mTileSpecs.add(sbc.persistableKey()); + mTiles.put(sbc.persistableKey(), new CustomQSTile(this, sbc)); if (mCallback != null) { mCallback.onTilesChanged(); } -- cgit v1.1