Merge changes I608d4b61,Ia7900e75 into pi-dev

* changes:
  Follow up to Ia7900e753b29187a7a7b81f393666687e8b8e04b
  Apply surface parameters in sync with RenderThread
This commit is contained in:
Jorim Jaggi
2018-05-18 11:49:56 +00:00
committed by Android (Google) Code Review
5 changed files with 133 additions and 22 deletions

View File

@@ -790,7 +790,8 @@ public final class ThreadedRenderer {
* @param attachInfo AttachInfo tied to the specified view.
* @param callbacks Callbacks invoked when drawing happens.
*/
void draw(View view, AttachInfo attachInfo, DrawCallbacks callbacks) {
void draw(View view, AttachInfo attachInfo, DrawCallbacks callbacks,
FrameDrawingCallback frameDrawingCallback) {
attachInfo.mIgnoreDirtyState = true;
final Choreographer choreographer = attachInfo.mViewRootImpl.mChoreographer;
@@ -815,6 +816,9 @@ public final class ThreadedRenderer {
}
final long[] frameInfo = choreographer.mFrameInfo.mFrameInfo;
if (frameDrawingCallback != null) {
nSetFrameCallback(mNativeProxy, frameDrawingCallback);
}
int syncResult = nSyncAndDrawFrame(mNativeProxy, frameInfo, frameInfo.length);
if ((syncResult & SYNC_LOST_SURFACE_REWARD_IF_FOUND) != 0) {
setEnabled(false);

View File

@@ -80,6 +80,7 @@ import android.util.SparseBooleanArray;
import android.util.TimeUtils;
import android.util.TypedValue;
import android.view.Surface.OutOfResourcesException;
import android.view.ThreadedRenderer.FrameDrawingCallback;
import android.view.View.AttachInfo;
import android.view.View.FocusDirection;
import android.view.View.MeasureSpec;
@@ -175,6 +176,8 @@ public final class ViewRootImpl implements ViewParent,
static final ArrayList<Runnable> sFirstDrawHandlers = new ArrayList();
static boolean sFirstDrawComplete = false;
private FrameDrawingCallback mNextRtFrameCallback;
/**
* Callback for notifying about global configuration changes.
*/
@@ -967,6 +970,17 @@ public final class ViewRootImpl implements ViewParent,
}
}
/**
* Registers a callback to be executed when the next frame is being drawn on RenderThread. This
* callback will be executed on a RenderThread worker thread, and only used for the next frame
* and thus it will only fire once.
*
* @param callback The callback to register.
*/
public void registerRtFrameCallback(FrameDrawingCallback callback) {
mNextRtFrameCallback = callback;
}
private void enableHardwareAcceleration(WindowManager.LayoutParams attrs) {
mAttachInfo.mHardwareAccelerated = false;
mAttachInfo.mHardwareAccelerationRequested = false;
@@ -3260,7 +3274,8 @@ public final class ViewRootImpl implements ViewParent,
requestDrawWindow();
}
mAttachInfo.mThreadedRenderer.draw(mView, mAttachInfo, this);
mAttachInfo.mThreadedRenderer.draw(mView, mAttachInfo, this, mNextRtFrameCallback);
mNextRtFrameCallback = null;
} else {
// If we get here with a disabled & requested hardware renderer, something went
// wrong (an invalidate posted right before we destroyed the hardware surface

View File

@@ -95,6 +95,7 @@ void DrawFrameTask::run() {
// Grab a copy of everything we need
CanvasContext* context = mContext;
std::function<void(int64_t)> callback = std::move(mFrameCallback);
mFrameCallback = nullptr;
// From this point on anything in "this" is *UNSAFE TO ACCESS*
if (canUnblockUiThread) {

View File

@@ -0,0 +1,101 @@
/*
* Copyright (C) 2018 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License
*/
package com.android.systemui.shared.system;
import android.graphics.Matrix;
import android.graphics.Rect;
import android.view.Surface;
import android.view.SurfaceControl;
import android.view.View;
import android.view.ViewRootImpl;
import java.util.ArrayList;
/**
* Helper class to apply surface transactions in sync with RenderThread.
*/
public class SyncRtSurfaceTransactionApplier {
private final Surface mTargetSurface;
private final ViewRootImpl mTargetViewRootImpl;
private final float[] mTmpFloat9 = new float[9];
/**
* @param targetView The view in the surface that acts as synchronization anchor.
*/
public SyncRtSurfaceTransactionApplier(View targetView) {
mTargetViewRootImpl = targetView != null ? targetView.getViewRootImpl() : null;
mTargetSurface = mTargetViewRootImpl != null ? mTargetViewRootImpl.mSurface : null;
}
/**
* Schedules applying surface parameters on the next frame.
*
* @param params The surface parameters to apply. DO NOT MODIFY the list after passing into
* this method to avoid synchronization issues.
*/
public void scheduleApply(SurfaceParams... params) {
if (mTargetViewRootImpl == null) {
return;
}
mTargetViewRootImpl.registerRtFrameCallback(frame -> {
if (mTargetSurface == null || !mTargetSurface.isValid()) {
return;
}
SurfaceControl.Transaction t = new SurfaceControl.Transaction();
for (int i = params.length - 1; i >= 0; i--) {
SurfaceParams surfaceParams = params[i];
SurfaceControl surface = surfaceParams.surface;
t.deferTransactionUntilSurface(surface, mTargetSurface, frame);
t.setMatrix(surface, surfaceParams.matrix, mTmpFloat9);
t.setWindowCrop(surface, surfaceParams.windowCrop);
t.setAlpha(surface, surfaceParams.alpha);
t.setLayer(surface, surfaceParams.layer);
t.show(surface);
}
t.setEarlyWakeup();
t.apply();
});
}
public static class SurfaceParams {
/**
* Constructs surface parameters to be applied when the current view state gets pushed to
* RenderThread.
*
* @param surface The surface to modify.
* @param alpha Alpha to apply.
* @param matrix Matrix to apply.
* @param windowCrop Crop to apply.
*/
public SurfaceParams(SurfaceControl surface, float alpha, Matrix matrix, Rect windowCrop,
int layer) {
this.surface = surface;
this.alpha = alpha;
this.matrix = new Matrix(matrix);
this.windowCrop = new Rect(windowCrop);
this.layer = layer;
}
final SurfaceControl surface;
final float alpha;
final Matrix matrix;
final Rect windowCrop;
final int layer;
}
}

View File

@@ -28,11 +28,10 @@ import android.view.IRemoteAnimationFinishedCallback;
import android.view.IRemoteAnimationRunner;
import android.view.RemoteAnimationAdapter;
import android.view.RemoteAnimationTarget;
import android.view.Surface;
import android.view.SurfaceControl;
import android.view.ViewRootImpl;
import com.android.systemui.Interpolators;
import com.android.systemui.shared.system.SyncRtSurfaceTransactionApplier;
import com.android.systemui.shared.system.SyncRtSurfaceTransactionApplier.SurfaceParams;
import com.android.systemui.statusbar.ExpandableNotificationRow;
import com.android.systemui.statusbar.NotificationListContainer;
import com.android.systemui.statusbar.StatusBarState;
@@ -41,6 +40,8 @@ import com.android.systemui.statusbar.phone.NotificationPanelView;
import com.android.systemui.statusbar.phone.StatusBar;
import com.android.systemui.statusbar.phone.StatusBarWindowView;
import java.util.ArrayList;
/**
* A class that allows activities to be launched in a seamless way where the notification
* transforms nicely into the starting window.
@@ -81,7 +82,7 @@ public class ActivityLaunchAnimator {
}
AnimationRunner animationRunner = new AnimationRunner(sourceNotification);
return new RemoteAnimationAdapter(animationRunner, ANIMATION_DURATION,
0 /* statusBarTransitionDelay */);
ANIMATION_DURATION - 150 /* statusBarTransitionDelay */);
}
public boolean isAnimationPending() {
@@ -109,12 +110,13 @@ public class ActivityLaunchAnimator {
private final ExpandableNotificationRow mSourceNotification;
private final ExpandAnimationParameters mParams;
private final Rect mWindowCrop = new Rect();
private boolean mLeashShown;
private boolean mInstantCollapsePanel = true;
private final SyncRtSurfaceTransactionApplier mSyncRtTransactionApplier;
public AnimationRunner(ExpandableNotificationRow sourceNofitication) {
mSourceNotification = sourceNofitication;
mParams = new ExpandAnimationParameters();
mSyncRtTransactionApplier = new SyncRtSurfaceTransactionApplier(mSourceNotification);
}
@Override
@@ -240,24 +242,12 @@ public class ActivityLaunchAnimator {
}
private void applyParamsToWindow(RemoteAnimationTarget app) {
SurfaceControl.Transaction t = new SurfaceControl.Transaction();
if (!mLeashShown) {
t.show(app.leash);
mLeashShown = true;
}
Matrix m = new Matrix();
m.postTranslate(0, (float) (mParams.top - app.position.y));
t.setMatrix(app.leash, m, new float[9]);
mWindowCrop.set(mParams.left, 0, mParams.right, mParams.getHeight());
t.setWindowCrop(app.leash, mWindowCrop);
ViewRootImpl viewRootImpl = mSourceNotification.getViewRootImpl();
if (viewRootImpl != null) {
Surface systemUiSurface = viewRootImpl.mSurface;
t.deferTransactionUntilSurface(app.leash, systemUiSurface,
systemUiSurface.getNextFrameNumber());
}
t.setEarlyWakeup();
t.apply();
SurfaceParams params = new SurfaceParams(app.leash, 1f /* alpha */, m, mWindowCrop,
app.prefixOrderIndex);
mSyncRtTransactionApplier.scheduleApply(params);
}
@Override