Loading packages/SystemUI/src/com/android/systemui/qs/tileimpl/QSTileImpl.java +17 −5 Original line number Diff line number Diff line Loading @@ -17,9 +17,10 @@ package com.android.systemui.qs.tileimpl; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_QS_CLICK; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_QS_LONG_PRESS; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_QS_SECONDARY_CLICK; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_CONTEXT; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_IS_FULL_QS; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_QS_POSITION; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_QS_VALUE; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_STATUS_BAR_STATE; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.TYPE_ACTION; import static com.android.settingslib.RestrictedLockUtils.EnforcedAdmin; Loading Loading @@ -52,6 +53,7 @@ import com.android.systemui.plugins.qs.QSTile.State; import com.android.systemui.qs.PagedTileLayout.TilePage; import com.android.systemui.qs.QSHost; import com.android.systemui.qs.QuickStatusBarHeader; import com.android.systemui.statusbar.StatusBarStateController; import java.util.ArrayList; Loading @@ -61,6 +63,8 @@ import java.util.ArrayList; * State management done on a looper provided by the host. Tiles should update state in * handleUpdateState. Callbacks affecting state should use refreshState to trigger another * state update pass on tile looper. * * @param <TState> see above */ public abstract class QSTileImpl<TState extends State> implements QSTile { protected final String TAG = "Tile." + getClass().getSimpleName(); Loading @@ -76,6 +80,8 @@ public abstract class QSTileImpl<TState extends State> implements QSTile { protected final Handler mUiHandler = new Handler(Looper.getMainLooper()); private final ArraySet<Object> mListeners = new ArraySet<>(); private final MetricsLogger mMetricsLogger = Dependency.get(MetricsLogger.class); private final StatusBarStateController mStatusBarStateController = Dependency.get(StatusBarStateController.class); private final ArrayList<Callback> mCallbacks = new ArrayList<>(); private final Object mStaleListener = new Object(); Loading Loading @@ -172,17 +178,23 @@ public abstract class QSTileImpl<TState extends State> implements QSTile { } public void click() { mMetricsLogger.write(populate(new LogMaker(ACTION_QS_CLICK).setType(TYPE_ACTION))); mMetricsLogger.write(populate(new LogMaker(ACTION_QS_CLICK).setType(TYPE_ACTION) .addTaggedData(FIELD_STATUS_BAR_STATE, mStatusBarStateController.getState()))); mHandler.sendEmptyMessage(H.CLICK); } public void secondaryClick() { mMetricsLogger.write(populate(new LogMaker(ACTION_QS_SECONDARY_CLICK).setType(TYPE_ACTION))); mMetricsLogger.write(populate(new LogMaker(ACTION_QS_SECONDARY_CLICK).setType(TYPE_ACTION) .addTaggedData(FIELD_STATUS_BAR_STATE, mStatusBarStateController.getState()))); mHandler.sendEmptyMessage(H.SECONDARY_CLICK); } public void longClick() { mMetricsLogger.write(populate(new LogMaker(ACTION_QS_LONG_PRESS).setType(TYPE_ACTION))); mMetricsLogger.write(populate(new LogMaker(ACTION_QS_LONG_PRESS).setType(TYPE_ACTION) .addTaggedData(FIELD_STATUS_BAR_STATE, mStatusBarStateController.getState()))); mHandler.sendEmptyMessage(H.LONG_CLICK); Prefs.putInt( Loading @@ -196,7 +208,7 @@ public abstract class QSTileImpl<TState extends State> implements QSTile { logMaker.addTaggedData(FIELD_QS_VALUE, ((BooleanState) mState).value ? 1 : 0); } return logMaker.setSubtype(getMetricsCategory()) .addTaggedData(FIELD_CONTEXT, mIsFullQs) .addTaggedData(FIELD_IS_FULL_QS, mIsFullQs) .addTaggedData(FIELD_QS_POSITION, mHost.indexOf(mTileSpec)); } Loading packages/SystemUI/tests/src/com/android/systemui/qs/tileimpl/QSTileImplTest.java +53 −2 Original line number Diff line number Diff line Loading @@ -19,8 +19,10 @@ import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_QS_SECONDARY_CLICK; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_QS_POSITION; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_QS_VALUE; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_STATUS_BAR_STATE; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.TYPE_ACTION; import static org.junit.Assert.assertEquals; import static org.mockito.ArgumentMatchers.any; import static org.mockito.ArgumentMatchers.anyInt; import static org.mockito.ArgumentMatchers.eq; Loading @@ -37,7 +39,6 @@ import static java.lang.Thread.sleep; import android.content.Intent; import android.metrics.LogMaker; import android.support.test.filters.SmallTest; import android.support.test.InstrumentationRegistry; import android.testing.AndroidTestingRunner; import android.testing.TestableLooper; import android.testing.TestableLooper.RunWithLooper; Loading @@ -48,12 +49,17 @@ import com.android.systemui.SysuiTestCase; import com.android.systemui.plugins.qs.QSTile; import com.android.systemui.qs.QSHost; import com.android.systemui.qs.QSTileHost; import com.android.systemui.statusbar.StatusBarState; import com.android.systemui.statusbar.StatusBarStateController; import org.junit.Before; import org.junit.Ignore; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.ArgumentCaptor; import org.mockito.ArgumentMatcher; import org.mockito.Captor; import org.mockito.MockitoAnnotations; @RunWith(AndroidTestingRunner.class) @RunWithLooper Loading @@ -65,13 +71,20 @@ public class QSTileImplTest extends SysuiTestCase { private TileImpl mTile; private QSTileHost mHost; private MetricsLogger mMetricsLogger; private StatusBarStateController mStatusBarStateController; @Captor private ArgumentCaptor<LogMaker> mLogCaptor; @Before public void setup() throws Exception { MockitoAnnotations.initMocks(this); String spec = "spec"; mTestableLooper = TestableLooper.get(this); mDependency.injectTestDependency(Dependency.BG_LOOPER, mTestableLooper.getLooper()); mMetricsLogger = mDependency.injectMockDependency(MetricsLogger.class); mStatusBarStateController = mDependency.injectMockDependency(StatusBarStateController.class); mHost = mock(QSTileHost.class); when(mHost.indexOf(spec)).thenReturn(POSITION); when(mHost.getContext()).thenReturn(mContext.getBaseContext()); Loading @@ -87,12 +100,30 @@ public class QSTileImplTest extends SysuiTestCase { verify(mMetricsLogger).write(argThat(new TileLogMatcher(ACTION_QS_CLICK))); } @Test public void testClick_Metrics_Status_Bar_Status() { when(mStatusBarStateController.getState()).thenReturn(StatusBarState.SHADE); mTile.click(); verify(mMetricsLogger).write(mLogCaptor.capture()); assertEquals(StatusBarState.SHADE, mLogCaptor.getValue() .getTaggedData(FIELD_STATUS_BAR_STATE)); } @Test public void testSecondaryClick_Metrics() { mTile.secondaryClick(); verify(mMetricsLogger).write(argThat(new TileLogMatcher(ACTION_QS_SECONDARY_CLICK))); } @Test public void testSecondaryClick_Metrics_Status_Bar_Status() { when(mStatusBarStateController.getState()).thenReturn(StatusBarState.KEYGUARD); mTile.secondaryClick(); verify(mMetricsLogger).write(mLogCaptor.capture()); assertEquals(StatusBarState.KEYGUARD, mLogCaptor.getValue() .getTaggedData(FIELD_STATUS_BAR_STATE)); } @Test public void testLongClick_Metrics() { mTile.longClick(); Loading @@ -100,7 +131,27 @@ public class QSTileImplTest extends SysuiTestCase { } @Test public void testPopulate() { public void testLongClick_Metrics_Status_Bar_Status() { when(mStatusBarStateController.getState()).thenReturn(StatusBarState.SHADE_LOCKED); mTile.click(); verify(mMetricsLogger).write(mLogCaptor.capture()); assertEquals(StatusBarState.SHADE_LOCKED, mLogCaptor.getValue() .getTaggedData(FIELD_STATUS_BAR_STATE)); } @Test public void testPopulateWithLockedScreen() { LogMaker maker = mock(LogMaker.class); when(maker.setSubtype(anyInt())).thenReturn(maker); when(maker.addTaggedData(anyInt(), any())).thenReturn(maker); mTile.getState().value = true; mTile.populate(maker); verify(maker).addTaggedData(eq(FIELD_QS_VALUE), eq(1)); verify(maker).addTaggedData(eq(FIELD_QS_POSITION), eq(POSITION)); } @Test public void testPopulateWithUnlockedScreen() { LogMaker maker = mock(LogMaker.class); when(maker.setSubtype(anyInt())).thenReturn(maker); when(maker.addTaggedData(anyInt(), any())).thenReturn(maker); Loading proto/src/metrics_constants/metrics_constants.proto +12 −0 Original line number Diff line number Diff line Loading @@ -6609,6 +6609,18 @@ message MetricsEvent { // OS: Q DIALOG_DISABLE_DEVELOPMENT_OPTIONS = 1591; // Tag for an ACTION: QS -> Tile click / Secondary click / long press // indicating the StatusBarState when menu was pulled down // CATEGORY: QUICK_SETTINGS // OS: Q FIELD_STATUS_BAR_STATE = 1592; // Tag for an ACTION: QS -> Tile click / Secondary click / long press // indicating whether current state is full QS // CATEGORY: QUICK_SETTINGS // OS: Q FIELD_IS_FULL_QS = 1593; // ---- End Q Constants, all Q constants go above this line ---- // Add new aosp constants above this line. Loading Loading
packages/SystemUI/src/com/android/systemui/qs/tileimpl/QSTileImpl.java +17 −5 Original line number Diff line number Diff line Loading @@ -17,9 +17,10 @@ package com.android.systemui.qs.tileimpl; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_QS_CLICK; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_QS_LONG_PRESS; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_QS_SECONDARY_CLICK; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_CONTEXT; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_IS_FULL_QS; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_QS_POSITION; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_QS_VALUE; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_STATUS_BAR_STATE; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.TYPE_ACTION; import static com.android.settingslib.RestrictedLockUtils.EnforcedAdmin; Loading Loading @@ -52,6 +53,7 @@ import com.android.systemui.plugins.qs.QSTile.State; import com.android.systemui.qs.PagedTileLayout.TilePage; import com.android.systemui.qs.QSHost; import com.android.systemui.qs.QuickStatusBarHeader; import com.android.systemui.statusbar.StatusBarStateController; import java.util.ArrayList; Loading @@ -61,6 +63,8 @@ import java.util.ArrayList; * State management done on a looper provided by the host. Tiles should update state in * handleUpdateState. Callbacks affecting state should use refreshState to trigger another * state update pass on tile looper. * * @param <TState> see above */ public abstract class QSTileImpl<TState extends State> implements QSTile { protected final String TAG = "Tile." + getClass().getSimpleName(); Loading @@ -76,6 +80,8 @@ public abstract class QSTileImpl<TState extends State> implements QSTile { protected final Handler mUiHandler = new Handler(Looper.getMainLooper()); private final ArraySet<Object> mListeners = new ArraySet<>(); private final MetricsLogger mMetricsLogger = Dependency.get(MetricsLogger.class); private final StatusBarStateController mStatusBarStateController = Dependency.get(StatusBarStateController.class); private final ArrayList<Callback> mCallbacks = new ArrayList<>(); private final Object mStaleListener = new Object(); Loading Loading @@ -172,17 +178,23 @@ public abstract class QSTileImpl<TState extends State> implements QSTile { } public void click() { mMetricsLogger.write(populate(new LogMaker(ACTION_QS_CLICK).setType(TYPE_ACTION))); mMetricsLogger.write(populate(new LogMaker(ACTION_QS_CLICK).setType(TYPE_ACTION) .addTaggedData(FIELD_STATUS_BAR_STATE, mStatusBarStateController.getState()))); mHandler.sendEmptyMessage(H.CLICK); } public void secondaryClick() { mMetricsLogger.write(populate(new LogMaker(ACTION_QS_SECONDARY_CLICK).setType(TYPE_ACTION))); mMetricsLogger.write(populate(new LogMaker(ACTION_QS_SECONDARY_CLICK).setType(TYPE_ACTION) .addTaggedData(FIELD_STATUS_BAR_STATE, mStatusBarStateController.getState()))); mHandler.sendEmptyMessage(H.SECONDARY_CLICK); } public void longClick() { mMetricsLogger.write(populate(new LogMaker(ACTION_QS_LONG_PRESS).setType(TYPE_ACTION))); mMetricsLogger.write(populate(new LogMaker(ACTION_QS_LONG_PRESS).setType(TYPE_ACTION) .addTaggedData(FIELD_STATUS_BAR_STATE, mStatusBarStateController.getState()))); mHandler.sendEmptyMessage(H.LONG_CLICK); Prefs.putInt( Loading @@ -196,7 +208,7 @@ public abstract class QSTileImpl<TState extends State> implements QSTile { logMaker.addTaggedData(FIELD_QS_VALUE, ((BooleanState) mState).value ? 1 : 0); } return logMaker.setSubtype(getMetricsCategory()) .addTaggedData(FIELD_CONTEXT, mIsFullQs) .addTaggedData(FIELD_IS_FULL_QS, mIsFullQs) .addTaggedData(FIELD_QS_POSITION, mHost.indexOf(mTileSpec)); } Loading
packages/SystemUI/tests/src/com/android/systemui/qs/tileimpl/QSTileImplTest.java +53 −2 Original line number Diff line number Diff line Loading @@ -19,8 +19,10 @@ import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_QS_SECONDARY_CLICK; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_QS_POSITION; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_QS_VALUE; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.FIELD_STATUS_BAR_STATE; import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.TYPE_ACTION; import static org.junit.Assert.assertEquals; import static org.mockito.ArgumentMatchers.any; import static org.mockito.ArgumentMatchers.anyInt; import static org.mockito.ArgumentMatchers.eq; Loading @@ -37,7 +39,6 @@ import static java.lang.Thread.sleep; import android.content.Intent; import android.metrics.LogMaker; import android.support.test.filters.SmallTest; import android.support.test.InstrumentationRegistry; import android.testing.AndroidTestingRunner; import android.testing.TestableLooper; import android.testing.TestableLooper.RunWithLooper; Loading @@ -48,12 +49,17 @@ import com.android.systemui.SysuiTestCase; import com.android.systemui.plugins.qs.QSTile; import com.android.systemui.qs.QSHost; import com.android.systemui.qs.QSTileHost; import com.android.systemui.statusbar.StatusBarState; import com.android.systemui.statusbar.StatusBarStateController; import org.junit.Before; import org.junit.Ignore; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.ArgumentCaptor; import org.mockito.ArgumentMatcher; import org.mockito.Captor; import org.mockito.MockitoAnnotations; @RunWith(AndroidTestingRunner.class) @RunWithLooper Loading @@ -65,13 +71,20 @@ public class QSTileImplTest extends SysuiTestCase { private TileImpl mTile; private QSTileHost mHost; private MetricsLogger mMetricsLogger; private StatusBarStateController mStatusBarStateController; @Captor private ArgumentCaptor<LogMaker> mLogCaptor; @Before public void setup() throws Exception { MockitoAnnotations.initMocks(this); String spec = "spec"; mTestableLooper = TestableLooper.get(this); mDependency.injectTestDependency(Dependency.BG_LOOPER, mTestableLooper.getLooper()); mMetricsLogger = mDependency.injectMockDependency(MetricsLogger.class); mStatusBarStateController = mDependency.injectMockDependency(StatusBarStateController.class); mHost = mock(QSTileHost.class); when(mHost.indexOf(spec)).thenReturn(POSITION); when(mHost.getContext()).thenReturn(mContext.getBaseContext()); Loading @@ -87,12 +100,30 @@ public class QSTileImplTest extends SysuiTestCase { verify(mMetricsLogger).write(argThat(new TileLogMatcher(ACTION_QS_CLICK))); } @Test public void testClick_Metrics_Status_Bar_Status() { when(mStatusBarStateController.getState()).thenReturn(StatusBarState.SHADE); mTile.click(); verify(mMetricsLogger).write(mLogCaptor.capture()); assertEquals(StatusBarState.SHADE, mLogCaptor.getValue() .getTaggedData(FIELD_STATUS_BAR_STATE)); } @Test public void testSecondaryClick_Metrics() { mTile.secondaryClick(); verify(mMetricsLogger).write(argThat(new TileLogMatcher(ACTION_QS_SECONDARY_CLICK))); } @Test public void testSecondaryClick_Metrics_Status_Bar_Status() { when(mStatusBarStateController.getState()).thenReturn(StatusBarState.KEYGUARD); mTile.secondaryClick(); verify(mMetricsLogger).write(mLogCaptor.capture()); assertEquals(StatusBarState.KEYGUARD, mLogCaptor.getValue() .getTaggedData(FIELD_STATUS_BAR_STATE)); } @Test public void testLongClick_Metrics() { mTile.longClick(); Loading @@ -100,7 +131,27 @@ public class QSTileImplTest extends SysuiTestCase { } @Test public void testPopulate() { public void testLongClick_Metrics_Status_Bar_Status() { when(mStatusBarStateController.getState()).thenReturn(StatusBarState.SHADE_LOCKED); mTile.click(); verify(mMetricsLogger).write(mLogCaptor.capture()); assertEquals(StatusBarState.SHADE_LOCKED, mLogCaptor.getValue() .getTaggedData(FIELD_STATUS_BAR_STATE)); } @Test public void testPopulateWithLockedScreen() { LogMaker maker = mock(LogMaker.class); when(maker.setSubtype(anyInt())).thenReturn(maker); when(maker.addTaggedData(anyInt(), any())).thenReturn(maker); mTile.getState().value = true; mTile.populate(maker); verify(maker).addTaggedData(eq(FIELD_QS_VALUE), eq(1)); verify(maker).addTaggedData(eq(FIELD_QS_POSITION), eq(POSITION)); } @Test public void testPopulateWithUnlockedScreen() { LogMaker maker = mock(LogMaker.class); when(maker.setSubtype(anyInt())).thenReturn(maker); when(maker.addTaggedData(anyInt(), any())).thenReturn(maker); Loading
proto/src/metrics_constants/metrics_constants.proto +12 −0 Original line number Diff line number Diff line Loading @@ -6609,6 +6609,18 @@ message MetricsEvent { // OS: Q DIALOG_DISABLE_DEVELOPMENT_OPTIONS = 1591; // Tag for an ACTION: QS -> Tile click / Secondary click / long press // indicating the StatusBarState when menu was pulled down // CATEGORY: QUICK_SETTINGS // OS: Q FIELD_STATUS_BAR_STATE = 1592; // Tag for an ACTION: QS -> Tile click / Secondary click / long press // indicating whether current state is full QS // CATEGORY: QUICK_SETTINGS // OS: Q FIELD_IS_FULL_QS = 1593; // ---- End Q Constants, all Q constants go above this line ---- // Add new aosp constants above this line. Loading