we need to wait for vsync when doing the screen-off animation
Bug: 6511421
Change-Id: I7a85a55e66a3a8d9937df575e98a5efec01a634f
diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp
index 35a7fd5..f4779e7 100644
--- a/services/surfaceflinger/SurfaceFlinger.cpp
+++ b/services/surfaceflinger/SurfaceFlinger.cpp
@@ -62,6 +62,7 @@
#include <private/android_filesystem_config.h>
#include <private/gui/SharedBufferStack.h>
+#include <gui/BitTube.h>
#define EGL_VERSION_HW_ANDROID 0x3143
@@ -1845,6 +1846,35 @@
// ---------------------------------------------------------------------------
+class VSyncWaiter {
+ DisplayEventReceiver::Event buffer[4];
+ sp<Looper> looper;
+ sp<IDisplayEventConnection> events;
+ sp<BitTube> eventTube;
+public:
+ VSyncWaiter(const sp<EventThread>& eventThread) {
+ looper = new Looper(true);
+ events = eventThread->createEventConnection();
+ eventTube = events->getDataChannel();
+ looper->addFd(eventTube->getFd(), 0, ALOOPER_EVENT_INPUT, 0, 0);
+ events->requestNextVsync();
+ }
+
+ void wait() {
+ ssize_t n;
+
+ looper->pollOnce(-1);
+ // we don't handle any errors here, it doesn't matter
+ // and we don't want to take the risk to get stuck.
+
+ // drain the events...
+ while ((n = DisplayEventReceiver::getEvents(
+ eventTube, buffer, 4)) > 0) ;
+
+ events->requestNextVsync();
+ }
+};
+
status_t SurfaceFlinger::electronBeamOffAnimationImplLocked()
{
// get screen geometry
@@ -1937,6 +1967,8 @@
}
};
+ VSyncWaiter vsync(mEventThread);
+
// the full animation is 24 frames
char value[PROPERTY_VALUE_MAX];
property_get("debug.sf.electron_frames", value, "24");
@@ -1963,6 +1995,9 @@
const float vg = itg(i);
const float vb = itb(i);
+ // wait for vsync
+ vsync.wait();
+
// clear screen
glColorMask(1,1,1,1);
glClear(GL_COLOR_BUFFER_BIT);
@@ -1998,6 +2033,10 @@
for (int i=0 ; i<nbFrames ; i++) {
const float v = itg(i);
hverts(vtx, v);
+
+ // wait for vsync
+ vsync.wait();
+
glClear(GL_COLOR_BUFFER_BIT);
glColor4f(1-v, 1-v, 1-v, 1);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
@@ -2095,6 +2134,8 @@
}
};
+ VSyncWaiter vsync(mEventThread);
+
// the full animation is 12 frames
int nbFrames = 8;
s_curve_interpolator itr(nbFrames, 7.5f);
@@ -2108,6 +2149,10 @@
for (int i=nbFrames-1 ; i>=0 ; i--) {
const float v = itg(i);
hverts(vtx, v);
+
+ // wait for vsync
+ vsync.wait();
+
glClear(GL_COLOR_BUFFER_BIT);
glColor4f(1-v, 1-v, 1-v, 1);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
@@ -2124,6 +2169,9 @@
const float vg = itg(i);
const float vb = itb(i);
+ // wait for vsync
+ vsync.wait();
+
// clear screen
glColorMask(1,1,1,1);
glClear(GL_COLOR_BUFFER_BIT);