All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.robolectric.shadows.ShadowPausedSystemClock Maven / Gradle / Ivy

package org.robolectric.shadows;

import static android.os.Build.VERSION_CODES.JELLY_BEAN_MR1;
import static android.os.Build.VERSION_CODES.P;

import android.os.SystemClock;
import java.time.DateTimeException;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
import javax.annotation.concurrent.GuardedBy;
import org.robolectric.annotation.HiddenApi;
import org.robolectric.annotation.Implementation;
import org.robolectric.annotation.Implements;
import org.robolectric.annotation.LooperMode;
import org.robolectric.annotation.Resetter;

/**
 * A shadow SystemClock used when {@link LooperMode.Mode#PAUSED} is active.
 *
 * 

In this variant, there is just one global system time controlled by this class. The current * time is fixed in place, and manually advanced by calling {@link * SystemClock#setCurrentTimeMillis(long)} * *

{@link SystemClock#uptimeMillis()} and {@link SystemClock#currentThreadTimeMillis()} are * identical. * *

This class should not be referenced directly. Use ShadowSystemClock instead. */ @Implements( value = SystemClock.class, isInAndroidSdk = false, shadowPicker = ShadowSystemClock.Picker.class) public class ShadowPausedSystemClock extends ShadowSystemClock { private static final long INITIAL_TIME = 100; private static final int MILLIS_PER_NANO = 1000000; @GuardedBy("ShadowPausedSystemClock.class") private static long currentTimeMillis = INITIAL_TIME; private static final List listeners = new CopyOnWriteArrayList<>(); // hopefully temporary list of clock listeners that are NOT cleared between tests // This is needed to accomodate Loopers which are not reset between tests private static final List staticListeners = new CopyOnWriteArrayList<>(); /** * Callback for clock updates */ interface Listener { void onClockAdvanced(); } static void addListener(Listener listener) { listeners.add(listener); } static void removeListener(Listener listener) { listeners.remove(listener); staticListeners.remove(listener); } static void addStaticListener(Listener listener) { staticListeners.add(listener); } /** Advances the current time by given millis, without sleeping the current thread/ */ @Implementation protected static void sleep(long millis) { synchronized (ShadowPausedSystemClock.class) { currentTimeMillis += millis; } informListeners(); } private static void informListeners() { for (Listener listener : listeners) { listener.onClockAdvanced(); } for (Listener listener : staticListeners) { listener.onClockAdvanced(); } } /** * Sets the current wall time. * *

Currently does not perform any permission checks. * * @return false if specified time is less than current time. */ @Implementation protected static boolean setCurrentTimeMillis(long millis) { synchronized (ShadowPausedSystemClock.class) { if (currentTimeMillis > millis) { return false; } else if (currentTimeMillis == millis) { return true; } else { currentTimeMillis = millis; } } informListeners(); return true; } @Implementation protected static synchronized long uptimeMillis() { return currentTimeMillis; } @Implementation protected static long elapsedRealtime() { return uptimeMillis(); } @Implementation(minSdk = JELLY_BEAN_MR1) protected static long elapsedRealtimeNanos() { return elapsedRealtime() * MILLIS_PER_NANO; } @Implementation protected static long currentThreadTimeMillis() { return uptimeMillis(); } @HiddenApi @Implementation protected static long currentThreadTimeMicro() { return uptimeMillis() * 1000; } @HiddenApi @Implementation protected static long currentTimeMicro() { return currentThreadTimeMicro(); } @Implementation(minSdk = P) @HiddenApi protected static synchronized long currentNetworkTimeMillis() { if (networkTimeAvailable) { return currentTimeMillis; } else { throw new DateTimeException("Network time not available"); } } @Resetter public static synchronized void reset() { currentTimeMillis = INITIAL_TIME; ShadowSystemClock.reset(); listeners.clear(); } }





© 2015 - 2025 Weber Informatics LLC | Privacy Policy