[automerge] Force draw during a blast sync and disable rt animations 2p: 7b7dabc218
Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/17390711 Bug: 200284684 Change-Id: Iafaeb33579f46ec47bdf40f550f09cb71c17b982
This commit is contained in:
@@ -817,12 +817,7 @@ public final class ViewRootImpl implements ViewParent,
|
|||||||
private final SurfaceSyncer mSurfaceSyncer = new SurfaceSyncer();
|
private final SurfaceSyncer mSurfaceSyncer = new SurfaceSyncer();
|
||||||
private int mLastSyncId = -1;
|
private int mLastSyncId = -1;
|
||||||
private SurfaceSyncer.SyncBufferCallback mSyncBufferCallback;
|
private SurfaceSyncer.SyncBufferCallback mSyncBufferCallback;
|
||||||
|
private int mNumSyncsInProgress = 0;
|
||||||
/**
|
|
||||||
* Keeps track of the last frame number that was attempted to draw. Should only be accessed on
|
|
||||||
* the RenderThread.
|
|
||||||
*/
|
|
||||||
private long mRtLastAttemptedDrawFrameNum = 0;
|
|
||||||
|
|
||||||
private HashSet<ScrollCaptureCallback> mRootScrollCaptureCallbacks;
|
private HashSet<ScrollCaptureCallback> mRootScrollCaptureCallbacks;
|
||||||
|
|
||||||
@@ -4250,7 +4245,7 @@ public final class ViewRootImpl implements ViewParent,
|
|||||||
mHasPendingTransactions = false;
|
mHasPendingTransactions = false;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
boolean canUseAsync = draw(fullRedrawNeeded);
|
boolean canUseAsync = draw(fullRedrawNeeded, usingAsyncReport && mSyncBuffer);
|
||||||
if (usingAsyncReport && !canUseAsync) {
|
if (usingAsyncReport && !canUseAsync) {
|
||||||
mAttachInfo.mThreadedRenderer.setFrameCallback(null);
|
mAttachInfo.mThreadedRenderer.setFrameCallback(null);
|
||||||
usingAsyncReport = false;
|
usingAsyncReport = false;
|
||||||
@@ -4410,7 +4405,7 @@ public final class ViewRootImpl implements ViewParent,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean draw(boolean fullRedrawNeeded) {
|
private boolean draw(boolean fullRedrawNeeded, boolean forceDraw) {
|
||||||
Surface surface = mSurface;
|
Surface surface = mSurface;
|
||||||
if (!surface.isValid()) {
|
if (!surface.isValid()) {
|
||||||
return false;
|
return false;
|
||||||
@@ -4547,6 +4542,9 @@ public final class ViewRootImpl implements ViewParent,
|
|||||||
|
|
||||||
useAsyncReport = true;
|
useAsyncReport = true;
|
||||||
|
|
||||||
|
if (forceDraw) {
|
||||||
|
mAttachInfo.mThreadedRenderer.forceDrawNextFrame();
|
||||||
|
}
|
||||||
mAttachInfo.mThreadedRenderer.draw(mView, mAttachInfo, this);
|
mAttachInfo.mThreadedRenderer.draw(mView, mAttachInfo, this);
|
||||||
} else {
|
} else {
|
||||||
// If we get here with a disabled & requested hardware renderer, something went
|
// If we get here with a disabled & requested hardware renderer, something went
|
||||||
@@ -10870,9 +10868,28 @@ public final class ViewRootImpl implements ViewParent,
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public final SurfaceSyncer.SyncTarget mSyncTarget = this::readyToSync;
|
public final SurfaceSyncer.SyncTarget mSyncTarget = new SurfaceSyncer.SyncTarget() {
|
||||||
|
@Override
|
||||||
|
public void onReadyToSync(SurfaceSyncer.SyncBufferCallback syncBufferCallback) {
|
||||||
|
readyToSync(syncBufferCallback);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onSyncComplete() {
|
||||||
|
mHandler.postAtFrontOfQueue(() -> {
|
||||||
|
if (--mNumSyncsInProgress == 0 && mAttachInfo.mThreadedRenderer != null) {
|
||||||
|
HardwareRenderer.setRtAnimationsEnabled(true);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
private void readyToSync(SurfaceSyncer.SyncBufferCallback syncBufferCallback) {
|
private void readyToSync(SurfaceSyncer.SyncBufferCallback syncBufferCallback) {
|
||||||
|
mNumSyncsInProgress++;
|
||||||
|
if (mAttachInfo.mThreadedRenderer != null) {
|
||||||
|
HardwareRenderer.setRtAnimationsEnabled(false);
|
||||||
|
}
|
||||||
|
|
||||||
if (mSyncBufferCallback != null) {
|
if (mSyncBufferCallback != null) {
|
||||||
Log.d(mTag, "Already set sync for the next draw.");
|
Log.d(mTag, "Already set sync for the next draw.");
|
||||||
mSyncBufferCallback.onBufferReady(null);
|
mSyncBufferCallback.onBufferReady(null);
|
||||||
|
|||||||
@@ -21,15 +21,16 @@ import android.annotation.Nullable;
|
|||||||
import android.annotation.UiThread;
|
import android.annotation.UiThread;
|
||||||
import android.os.Handler;
|
import android.os.Handler;
|
||||||
import android.os.Looper;
|
import android.os.Looper;
|
||||||
|
import android.util.ArraySet;
|
||||||
import android.util.Log;
|
import android.util.Log;
|
||||||
import android.util.SparseArray;
|
import android.util.SparseArray;
|
||||||
import android.view.SurfaceControl.Transaction;
|
import android.view.SurfaceControl.Transaction;
|
||||||
import android.view.SurfaceView;
|
import android.view.SurfaceView;
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
|
import android.view.ViewRootImpl;
|
||||||
|
|
||||||
import com.android.internal.annotations.GuardedBy;
|
import com.android.internal.annotations.GuardedBy;
|
||||||
|
|
||||||
import java.util.HashSet;
|
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.function.Consumer;
|
import java.util.function.Consumer;
|
||||||
import java.util.function.Supplier;
|
import java.util.function.Supplier;
|
||||||
@@ -99,7 +100,9 @@ public class SurfaceSyncer {
|
|||||||
Handler handler = new Handler(Looper.myLooper());
|
Handler handler = new Handler(Looper.myLooper());
|
||||||
return setupSync(transaction -> {
|
return setupSync(transaction -> {
|
||||||
transaction.apply();
|
transaction.apply();
|
||||||
handler.post(onComplete);
|
if (onComplete != null) {
|
||||||
|
handler.post(onComplete);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -171,7 +174,11 @@ public class SurfaceSyncer {
|
|||||||
*/
|
*/
|
||||||
@UiThread
|
@UiThread
|
||||||
public boolean addToSync(int syncId, @NonNull View view) {
|
public boolean addToSync(int syncId, @NonNull View view) {
|
||||||
return addToSync(syncId, view.getViewRootImpl().mSyncTarget);
|
ViewRootImpl viewRoot = view.getViewRootImpl();
|
||||||
|
if (viewRoot == null) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return addToSync(syncId, viewRoot.mSyncTarget);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -232,9 +239,17 @@ public class SurfaceSyncer {
|
|||||||
* and {@link SyncBufferCallback#onBufferReady(Transaction)} in order for this Syncable
|
* and {@link SyncBufferCallback#onBufferReady(Transaction)} in order for this Syncable
|
||||||
* to be marked as complete.
|
* to be marked as complete.
|
||||||
*
|
*
|
||||||
|
* Always invoked on the thread that initiated the call to
|
||||||
|
* {@link #addToSync(int, SyncTarget)}
|
||||||
|
*
|
||||||
* @param syncBufferCallback A SyncBufferCallback that the caller must invoke onBufferReady
|
* @param syncBufferCallback A SyncBufferCallback that the caller must invoke onBufferReady
|
||||||
*/
|
*/
|
||||||
void onReadyToSync(SyncBufferCallback syncBufferCallback);
|
void onReadyToSync(SyncBufferCallback syncBufferCallback);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* There's no guarantee about the thread this callback is invoked on.
|
||||||
|
*/
|
||||||
|
default void onSyncComplete() {}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -260,11 +275,13 @@ public class SurfaceSyncer {
|
|||||||
private final Object mLock = new Object();
|
private final Object mLock = new Object();
|
||||||
|
|
||||||
@GuardedBy("mLock")
|
@GuardedBy("mLock")
|
||||||
private final Set<Integer> mPendingSyncs = new HashSet<>();
|
private final Set<Integer> mPendingSyncs = new ArraySet<>();
|
||||||
@GuardedBy("mLock")
|
@GuardedBy("mLock")
|
||||||
private final Transaction mTransaction = sTransactionFactory.get();
|
private final Transaction mTransaction = sTransactionFactory.get();
|
||||||
@GuardedBy("mLock")
|
@GuardedBy("mLock")
|
||||||
private boolean mSyncReady;
|
private boolean mSyncReady;
|
||||||
|
@GuardedBy("mLock")
|
||||||
|
private final Set<SyncTarget> mSyncTargets = new ArraySet<>();
|
||||||
|
|
||||||
private final int mSyncId;
|
private final int mSyncId;
|
||||||
private final Consumer<Transaction> mSyncRequestCompleteCallback;
|
private final Consumer<Transaction> mSyncRequestCompleteCallback;
|
||||||
@@ -290,6 +307,7 @@ public class SurfaceSyncer {
|
|||||||
|
|
||||||
synchronized (mLock) {
|
synchronized (mLock) {
|
||||||
mPendingSyncs.add(syncBufferCallback.hashCode());
|
mPendingSyncs.add(syncBufferCallback.hashCode());
|
||||||
|
mSyncTargets.add(syncTarget);
|
||||||
}
|
}
|
||||||
syncTarget.onReadyToSync(syncBufferCallback);
|
syncTarget.onReadyToSync(syncBufferCallback);
|
||||||
}
|
}
|
||||||
@@ -314,6 +332,11 @@ public class SurfaceSyncer {
|
|||||||
if (DEBUG) {
|
if (DEBUG) {
|
||||||
Log.d(TAG, "Successfully finished sync id=" + mSyncId);
|
Log.d(TAG, "Successfully finished sync id=" + mSyncId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (SyncTarget syncTarget : mSyncTargets) {
|
||||||
|
syncTarget.onSyncComplete();
|
||||||
|
}
|
||||||
|
mSyncTargets.clear();
|
||||||
mSyncRequestCompleteCallback.accept(mTransaction);
|
mSyncRequestCompleteCallback.accept(mTransaction);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,14 +1,11 @@
|
|||||||
package com.android.systemui.animation
|
package com.android.systemui.animation
|
||||||
|
|
||||||
import android.app.ActivityManager
|
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import android.window.SurfaceSyncer
|
import android.window.SurfaceSyncer
|
||||||
|
|
||||||
/** A util class to synchronize 2 view roots. */
|
/** A util class to synchronize 2 view roots. */
|
||||||
// TODO(b/200284684): Remove this class.
|
// TODO(b/200284684): Remove this class.
|
||||||
object ViewRootSync {
|
object ViewRootSync {
|
||||||
// TODO(b/217621394): Remove special handling for low-RAM devices after animation sync is fixed
|
|
||||||
private val forceDisableSynchronization = ActivityManager.isLowRamDeviceStatic()
|
|
||||||
private var surfaceSyncer: SurfaceSyncer? = null
|
private var surfaceSyncer: SurfaceSyncer? = null
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -23,8 +20,7 @@ object ViewRootSync {
|
|||||||
otherView: View,
|
otherView: View,
|
||||||
then: () -> Unit
|
then: () -> Unit
|
||||||
) {
|
) {
|
||||||
if (forceDisableSynchronization ||
|
if (!view.isAttachedToWindow || view.viewRootImpl == null ||
|
||||||
!view.isAttachedToWindow || view.viewRootImpl == null ||
|
|
||||||
!otherView.isAttachedToWindow || otherView.viewRootImpl == null ||
|
!otherView.isAttachedToWindow || otherView.viewRootImpl == null ||
|
||||||
view.viewRootImpl == otherView.viewRootImpl) {
|
view.viewRootImpl == otherView.viewRootImpl) {
|
||||||
// No need to synchronize if either the touch surface or dialog view is not attached
|
// No need to synchronize if either the touch surface or dialog view is not attached
|
||||||
|
|||||||
Reference in New Issue
Block a user