Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit b89dd9bc authored by TreeHugger Robot's avatar TreeHugger Robot Committed by Android (Google) Code Review
Browse files

Merge "Play charging feedback on a background thread" into tm-dev

parents 601853b5 241f7283
Loading
Loading
Loading
Loading
+35 −17
Original line number Diff line number Diff line
@@ -64,6 +64,8 @@ import com.android.server.policy.WindowManagerPolicy;
import com.android.server.statusbar.StatusBarManagerInternal;

import java.io.PrintWriter;
import java.util.concurrent.Executor;
import java.util.concurrent.atomic.AtomicBoolean;

/**
 * Sends broadcasts about important power state changes.
@@ -133,6 +135,7 @@ public class Notifier {
    private final DisplayManagerInternal mDisplayManagerInternal;

    private final NotifierHandler mHandler;
    private final Executor mBackgroundExecutor;
    private final Intent mScreenOnIntent;
    private final Intent mScreenOffIntent;

@@ -169,9 +172,12 @@ public class Notifier {
    // True if a user activity message should be sent.
    private boolean mUserActivityPending;

    private final AtomicBoolean mIsPlayingChargingStartedFeedback = new AtomicBoolean(false);

    public Notifier(Looper looper, Context context, IBatteryStats batteryStats,
            SuspendBlocker suspendBlocker, WindowManagerPolicy policy,
            FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector) {
            FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector,
            Executor backgroundExecutor) {
        mContext = context;
        mBatteryStats = batteryStats;
        mAppOps = mContext.getSystemService(AppOpsManager.class);
@@ -188,6 +194,7 @@ public class Notifier {
        mVibrator = mContext.getSystemService(Vibrator.class);

        mHandler = new NotifierHandler(looper);
        mBackgroundExecutor = backgroundExecutor;
        mScreenOnIntent = new Intent(Intent.ACTION_SCREEN_ON);
        mScreenOnIntent.addFlags(
                Intent.FLAG_RECEIVER_REGISTERED_ONLY | Intent.FLAG_RECEIVER_FOREGROUND
@@ -824,11 +831,20 @@ public class Notifier {
            return;
        }

        if (!mIsPlayingChargingStartedFeedback.compareAndSet(false, true)) {
            // there's already a charging started feedback Runnable scheduled to run on the
            // background thread, so let's not execute another
            return;
        }

        // vibrate & play sound on a background thread
        mBackgroundExecutor.execute(() -> {
            // vibrate
            final boolean vibrate = Settings.Secure.getIntForUser(mContext.getContentResolver(),
                    Settings.Secure.CHARGING_VIBRATION_ENABLED, 1, userId) != 0;
            if (vibrate) {
            mVibrator.vibrate(CHARGING_VIBRATION_EFFECT, HARDWARE_FEEDBACK_VIBRATION_ATTRIBUTES);
                mVibrator.vibrate(CHARGING_VIBRATION_EFFECT,
                        HARDWARE_FEEDBACK_VIBRATION_ATTRIBUTES);
            }

            // play sound
@@ -843,6 +859,8 @@ public class Notifier {
                    sfx.play();
                }
            }
            mIsPlayingChargingStartedFeedback.set(false);
        });
    }

    private void showWirelessChargingStarted(int batteryLevel, @UserIdInt int userId) {
+6 −3
Original line number Diff line number Diff line
@@ -140,6 +140,7 @@ import java.util.Arrays;
import java.util.List;
import java.util.NoSuchElementException;
import java.util.Objects;
import java.util.concurrent.Executor;

/**
 * The power manager service is responsible for coordinating power management
@@ -905,10 +906,11 @@ public final class PowerManagerService extends SystemService
    static class Injector {
        Notifier createNotifier(Looper looper, Context context, IBatteryStats batteryStats,
                SuspendBlocker suspendBlocker, WindowManagerPolicy policy,
                FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector) {
                FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector,
                Executor backgroundExecutor) {
            return new Notifier(
                    looper, context, batteryStats, suspendBlocker, policy, faceDownDetector,
                    screenUndimDetector);
                    screenUndimDetector, backgroundExecutor);
        }

        SuspendBlocker createSuspendBlocker(PowerManagerService service, String name) {
@@ -1227,7 +1229,8 @@ public final class PowerManagerService extends SystemService
            mBatteryStats = BatteryStatsService.getService();
            mNotifier = mInjector.createNotifier(Looper.getMainLooper(), mContext, mBatteryStats,
                    mInjector.createSuspendBlocker(this, "PowerManagerService.Broadcasts"),
                    mPolicy, mFaceDownDetector, mScreenUndimDetector);
                    mPolicy, mFaceDownDetector, mScreenUndimDetector,
                    BackgroundThread.getExecutor());

            mPowerGroups.append(Display.DEFAULT_DISPLAY_GROUP,
                    new PowerGroup(WAKEFULNESS_AWAKE, mPowerGroupWakefulnessChangeListener,
+4 −1
Original line number Diff line number Diff line
@@ -67,6 +67,8 @@ import com.android.server.power.batterysaver.BatterySaverStateMachine;
import com.android.server.power.batterysaver.BatterySavingStats;
import com.android.server.testutils.OffsettableClock;

import java.util.concurrent.Executor;

import org.junit.After;
import org.junit.Before;
import org.junit.Test;
@@ -164,7 +166,8 @@ public class PowerManagerServiceMockingTest {
            @Override
            Notifier createNotifier(Looper looper, Context context, IBatteryStats batteryStats,
                    SuspendBlocker suspendBlocker, WindowManagerPolicy policy,
                    FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector) {
                    FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector,
                    Executor executor) {
                return mNotifierMock;
            }

+41 −2
Original line number Diff line number Diff line
@@ -16,6 +16,8 @@

package com.android.server.power;

import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.ArgumentMatchers.anyString;
@@ -56,6 +58,8 @@ import org.junit.Test;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;

import java.util.concurrent.Executor;

/**
 * Tests for {@link com.android.server.power.Notifier}
 */
@@ -79,6 +83,7 @@ public class NotifierTest {
    private Context mContextSpy;
    private Resources mResourcesSpy;
    private TestLooper mTestLooper = new TestLooper();
    private FakeExecutor mTestExecutor = new FakeExecutor();
    private Notifier mNotifier;

    @Before
@@ -107,6 +112,7 @@ public class NotifierTest {
        // WHEN wired charging starts
        mNotifier.onWiredChargingStarted(USER_ID);
        mTestLooper.dispatchAll();
        mTestExecutor.simulateAsyncExecutionOfLastCommand();

        // THEN the device vibrates once
        verify(mVibrator, times(1)).vibrate(any(), any(VibrationAttributes.class));
@@ -122,6 +128,7 @@ public class NotifierTest {
        // WHEN wired charging starts
        mNotifier.onWiredChargingStarted(USER_ID);
        mTestLooper.dispatchAll();
        mTestExecutor.simulateAsyncExecutionOfLastCommand();

        // THEN the device doesn't vibrate
        verify(mVibrator, never()).vibrate(any(), any(VibrationAttributes.class));
@@ -137,6 +144,7 @@ public class NotifierTest {
        // WHEN wireless charging starts
        mNotifier.onWirelessChargingStarted(5, USER_ID);
        mTestLooper.dispatchAll();
        mTestExecutor.simulateAsyncExecutionOfLastCommand();

        // THEN the device vibrates once
        verify(mVibrator, times(1)).vibrate(any(), any(VibrationAttributes.class));
@@ -152,6 +160,7 @@ public class NotifierTest {
        // WHEN wireless charging starts
        mNotifier.onWirelessChargingStarted(5, USER_ID);
        mTestLooper.dispatchAll();
        mTestExecutor.simulateAsyncExecutionOfLastCommand();

        // THEN the device doesn't vibrate
        verify(mVibrator, never()).vibrate(any(), any(VibrationAttributes.class));
@@ -170,6 +179,7 @@ public class NotifierTest {
        // WHEN wired charging starts
        mNotifier.onWiredChargingStarted(USER_ID);
        mTestLooper.dispatchAll();
        mTestExecutor.simulateAsyncExecutionOfLastCommand();

        // THEN the device doesn't vibrate
        verify(mVibrator, never()).vibrate(any(), any(VibrationAttributes.class));
@@ -186,6 +196,7 @@ public class NotifierTest {
        // WHEN wireless charging starts
        mNotifier.onWirelessChargingStarted(5, USER_ID);
        mTestLooper.dispatchAll();
        mTestExecutor.simulateAsyncExecutionOfLastCommand();

        // THEN the charging animation is triggered
        verify(mStatusBarManagerInternal, times(1)).showChargingAnimation(5);
@@ -202,6 +213,7 @@ public class NotifierTest {
        // WHEN wireless charging starts
        mNotifier.onWirelessChargingStarted(5, USER_ID);
        mTestLooper.dispatchAll();
        mTestExecutor.simulateAsyncExecutionOfLastCommand();

        // THEN the charging animation never gets called
        verify(mStatusBarManagerInternal, never()).showChargingAnimation(anyInt());
@@ -211,7 +223,8 @@ public class NotifierTest {
        @Override
        Notifier createNotifier(Looper looper, Context context, IBatteryStats batteryStats,
                SuspendBlocker suspendBlocker, WindowManagerPolicy policy,
                FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector) {
                FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector,
                Executor backgroundExecutor) {
            return mNotifierMock;
        }

@@ -300,6 +313,32 @@ public class NotifierTest {
                mInjector.createSuspendBlocker(mService, "testBlocker"),
                null,
                null,
                null);
                null,
                mTestExecutor);
    }

    private static class FakeExecutor implements Executor {
        private Runnable mLastCommand;

        @Override
        public void execute(Runnable command) {
            assertNull(mLastCommand);
            assertNotNull(command);
            mLastCommand = command;
        }

        public Runnable getAndResetLastCommand() {
            Runnable toReturn = mLastCommand;
            mLastCommand = null;
            return toReturn;
        }

        public void simulateAsyncExecutionOfLastCommand() {
            Runnable toRun = getAndResetLastCommand();
            if (toRun != null) {
                toRun.run();
            }
        }
    }

}
+3 −1
Original line number Diff line number Diff line
@@ -109,6 +109,7 @@ import org.mockito.stubbing.Answer;

import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.Executor;
import java.util.concurrent.atomic.AtomicReference;

/**
@@ -220,7 +221,8 @@ public class PowerManagerServiceTest {
            @Override
            Notifier createNotifier(Looper looper, Context context, IBatteryStats batteryStats,
                    SuspendBlocker suspendBlocker, WindowManagerPolicy policy,
                    FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector) {
                    FaceDownDetector faceDownDetector, ScreenUndimDetector screenUndimDetector,
                    Executor executor) {
                return mNotifierMock;
            }