Index: content/public/android/java/src/org/chromium/content/browser/VSyncMonitor.java |
diff --git a/content/public/android/java/src/org/chromium/content/browser/VSyncMonitor.java b/content/public/android/java/src/org/chromium/content/browser/VSyncMonitor.java |
deleted file mode 100644 |
index ce9f36dfd45b08e18b8ff184894575ac105f6f47..0000000000000000000000000000000000000000 |
--- a/content/public/android/java/src/org/chromium/content/browser/VSyncMonitor.java |
+++ /dev/null |
@@ -1,224 +0,0 @@ |
-// Copyright 2012 The Chromium Authors. All rights reserved. |
-// Use of this source code is governed by a BSD-style license that can be |
-// found in the LICENSE file. |
- |
-package org.chromium.content.browser; |
- |
-import android.content.Context; |
-import android.os.Build; |
-import android.os.Handler; |
-import android.view.Choreographer; |
-import android.view.WindowManager; |
- |
-import org.chromium.base.TraceEvent; |
- |
-/** |
- * Notifies clients of the default displays's vertical sync pulses. |
- * This class works in "burst" mode: once the update is requested, the listener will be |
- * called MAX_VSYNC_COUNT times on the vertical sync pulses (on JB) or on every refresh |
- * period (on ICS, see below), unless stop() is called. |
- * On ICS, VSyncMonitor relies on setVSyncPointForICS() being called to set a reasonable |
- * approximation of a vertical sync starting point; see also http://crbug.com/156397. |
- */ |
-public class VSyncMonitor { |
- private static final long NANOSECONDS_PER_SECOND = 1000000000; |
- private static final long NANOSECONDS_PER_MILLISECOND = 1000000; |
- private static final long NANOSECONDS_PER_MICROSECOND = 1000; |
- public static final int MAX_AUTO_ONVSYNC_COUNT = 5; |
- |
- /** |
- * VSync listener class |
- */ |
- public interface Listener { |
- /** |
- * Called very soon after the start of the display's vertical sync period. |
- * @param monitor The VSyncMonitor that triggered the signal. |
- * @param vsyncTimeMicros Absolute frame time in microseconds. |
- */ |
- public void onVSync(VSyncMonitor monitor, long vsyncTimeMicros); |
- } |
- |
- private Listener mListener; |
- |
- // Display refresh rate as reported by the system. |
- private final long mRefreshPeriodNano; |
- |
- private boolean mHaveRequestInFlight; |
- private int mTriggerNextVSyncCount; |
- |
- // Choreographer is used to detect vsync on >= JB. |
- private final Choreographer mChoreographer; |
- private final Choreographer.FrameCallback mVSyncFrameCallback; |
- |
- // On ICS we just post a task through the handler (http://crbug.com/156397) |
- private final Runnable mVSyncRunnableCallback; |
- private long mGoodStartingPointNano; |
- private long mLastPostedNano; |
- |
- // If the monitor is activated after having been idle, we synthesize the first vsync to reduce |
- // latency. |
- private final Handler mHandler = new Handler(); |
- private final Runnable mSyntheticVSyncRunnable; |
- private long mLastVSyncCpuTimeNano; |
- |
- public VSyncMonitor(Context context, VSyncMonitor.Listener listener) { |
- this(context, listener, true); |
- } |
- |
- VSyncMonitor(Context context, VSyncMonitor.Listener listener, boolean enableJBVSync) { |
- mListener = listener; |
- float refreshRate = ((WindowManager) context.getSystemService(Context.WINDOW_SERVICE)) |
- .getDefaultDisplay().getRefreshRate(); |
- if (refreshRate <= 0) refreshRate = 60; |
- mRefreshPeriodNano = (long) (NANOSECONDS_PER_SECOND / refreshRate); |
- mTriggerNextVSyncCount = 0; |
- |
- if (enableJBVSync && Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) { |
- // Use Choreographer on JB+ to get notified of vsync. |
- mChoreographer = Choreographer.getInstance(); |
- mVSyncFrameCallback = new Choreographer.FrameCallback() { |
- @Override |
- public void doFrame(long frameTimeNanos) { |
- TraceEvent.begin("VSync"); |
- mGoodStartingPointNano = frameTimeNanos; |
- onVSyncCallback(frameTimeNanos, getCurrentNanoTime()); |
- TraceEvent.end("VSync"); |
- } |
- }; |
- mVSyncRunnableCallback = null; |
- } else { |
- // On ICS we just hope that running tasks is relatively predictable. |
- mChoreographer = null; |
- mVSyncFrameCallback = null; |
- mVSyncRunnableCallback = new Runnable() { |
- @Override |
- public void run() { |
- TraceEvent.begin("VSyncTimer"); |
- final long currentTime = getCurrentNanoTime(); |
- onVSyncCallback(currentTime, currentTime); |
- TraceEvent.end("VSyncTimer"); |
- } |
- }; |
- mLastPostedNano = 0; |
- } |
- mSyntheticVSyncRunnable = new Runnable() { |
- @Override |
- public void run() { |
- TraceEvent.begin("VSyncSynthetic"); |
- final long currentTime = getCurrentNanoTime(); |
- onVSyncCallback(estimateLastVSyncTime(currentTime), currentTime); |
- TraceEvent.end("VSyncSynthetic"); |
- } |
- }; |
- mGoodStartingPointNano = getCurrentNanoTime(); |
- } |
- |
- /** |
- * Returns the time interval between two consecutive vsync pulses in microseconds. |
- */ |
- public long getVSyncPeriodInMicroseconds() { |
- return mRefreshPeriodNano / NANOSECONDS_PER_MICROSECOND; |
- } |
- |
- /** |
- * Determine whether a true vsync signal is available on this platform. |
- */ |
- public boolean isVSyncSignalAvailable() { |
- return mChoreographer != null; |
- } |
- |
- /** |
- * Stop reporting vsync events. Note that at most one pending vsync event can still be delivered |
- * after this function is called. |
- */ |
- public void stop() { |
- mTriggerNextVSyncCount = 0; |
- } |
- |
- /** |
- * Unregister the listener. |
- * No vsync events will be reported afterwards. |
- */ |
- public void unregisterListener() { |
- stop(); |
- mListener = null; |
- } |
- |
- /** |
- * Request to be notified of the closest display vsync events. |
- * Listener.onVSync() will be called soon after the upcoming vsync pulses. |
- * It will be called at most MAX_AUTO_ONVSYNC_COUNT times unless requestUpdate() is called. |
- */ |
- public void requestUpdate() { |
- mTriggerNextVSyncCount = MAX_AUTO_ONVSYNC_COUNT; |
- postCallback(); |
- } |
- |
- /** |
- * Set the best guess of the point in the past when the vsync has happened. |
- * @param goodStartingPointNano Known vsync point in the past. |
- */ |
- public void setVSyncPointForICS(long goodStartingPointNano) { |
- mGoodStartingPointNano = goodStartingPointNano; |
- } |
- |
- private long getCurrentNanoTime() { |
- return System.nanoTime(); |
- } |
- |
- private void onVSyncCallback(long frameTimeNanos, long currentTimeNanos) { |
- assert mHaveRequestInFlight; |
- mHaveRequestInFlight = false; |
- mLastVSyncCpuTimeNano = currentTimeNanos; |
- if (mTriggerNextVSyncCount >= 0) { |
- mTriggerNextVSyncCount--; |
- postCallback(); |
- } |
- if (mListener != null) { |
- mListener.onVSync(this, frameTimeNanos / NANOSECONDS_PER_MICROSECOND); |
- } |
- } |
- |
- private void postCallback() { |
- if (mHaveRequestInFlight) return; |
- mHaveRequestInFlight = true; |
- if (postSyntheticVSync()) return; |
- if (isVSyncSignalAvailable()) { |
- mChoreographer.postFrameCallback(mVSyncFrameCallback); |
- } else { |
- postRunnableCallback(); |
- } |
- } |
- |
- private boolean postSyntheticVSync() { |
- final long currentTime = getCurrentNanoTime(); |
- // Only trigger a synthetic vsync if we've been idle for long enough and the upcoming real |
- // vsync is more than half a frame away. |
- if (currentTime - mLastVSyncCpuTimeNano < 2 * mRefreshPeriodNano) return false; |
- if (currentTime - estimateLastVSyncTime(currentTime) > mRefreshPeriodNano / 2) return false; |
- mHandler.post(mSyntheticVSyncRunnable); |
- return true; |
- } |
- |
- private long estimateLastVSyncTime(long currentTime) { |
- final long lastRefreshTime = mGoodStartingPointNano + |
- ((currentTime - mGoodStartingPointNano) / mRefreshPeriodNano) * mRefreshPeriodNano; |
- return lastRefreshTime; |
- } |
- |
- private void postRunnableCallback() { |
- assert !isVSyncSignalAvailable(); |
- final long currentTime = getCurrentNanoTime(); |
- final long lastRefreshTime = estimateLastVSyncTime(currentTime); |
- long delay = (lastRefreshTime + mRefreshPeriodNano) - currentTime; |
- assert delay > 0 && delay <= mRefreshPeriodNano; |
- |
- if (currentTime + delay <= mLastPostedNano + mRefreshPeriodNano / 2) { |
- delay += mRefreshPeriodNano; |
- } |
- |
- mLastPostedNano = currentTime + delay; |
- if (delay == 0) mHandler.post(mVSyncRunnableCallback); |
- else mHandler.postDelayed(mVSyncRunnableCallback, delay / NANOSECONDS_PER_MILLISECOND); |
- } |
-} |