Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a0530caa authored by Riddle Hsu's avatar Riddle Hsu Committed by Xiang Wang
Browse files

Apply override scale from entry points on client

This provides a sandbox-like scaled environment on client side.

- This prevents the metrics and config from being scaled multiple
  times because the entry points are only called from server side,
  there won't have reentrancy for applying the scale.
- App's configuration callback method can get scaled config.
- If override scale is enabled, the legacy compat mode will be
  skipped. That avoids mixing different approaches of scaling.
  - Legacy compat mode is to simulate a 320dp x 480dp screen
    size with density 160 (the surface scale and config scale
    are different).
  - Override scale is to downscale the app for better performance
    (the surface scale and config scale are the same).

Bug: 238416387
Bug: 240335717
Test: atest ActivityThreadTest#testOverrideScale
Test: atest CtsWindowManagerDeviceTestCases:CompatScaleTests
Test: am compat enable DOWNSCALED $pkg
      am compat enable DOWNSCALE_50 $pkg
Change-Id: I0ddf333996f229063511273f8aeb3867c9ba8bda
parent 56fe9580
Loading
Loading
Loading
Loading
+8 −0
Original line number Diff line number Diff line
@@ -1177,9 +1177,16 @@ public final class ActivityThread extends ClientTransactionHandler
            data.mSerializedSystemFontMap = serializedSystemFontMap;
            data.startRequestedElapsedTime = startRequestedElapsedTime;
            data.startRequestedUptime = startRequestedUptime;
            updateCompatOverrideScale(compatInfo);
            CompatibilityInfo.applyOverrideScaleIfNeeded(config);
            sendMessage(H.BIND_APPLICATION, data);
        }

        private void updateCompatOverrideScale(CompatibilityInfo info) {
            CompatibilityInfo.setOverrideInvertedScale(
                    info.hasOverrideScaling() ? info.applicationInvertedScale : 1f);
        }

        public final void runIsolatedEntryPoint(String entryPoint, String[] entryPointArgs) {
            SomeArgs args = SomeArgs.obtain();
            args.arg1 = entryPoint;
@@ -1756,6 +1763,7 @@ public final class ActivityThread extends ClientTransactionHandler
            UpdateCompatibilityData ucd = new UpdateCompatibilityData();
            ucd.pkg = pkg;
            ucd.info = info;
            updateCompatOverrideScale(info);
            sendMessage(H.UPDATE_PACKAGE_COMPATIBILITY_INFO, ucd);
        }

+20 −3
Original line number Diff line number Diff line
@@ -462,13 +462,30 @@ public class WindowConfiguration implements Parcelable, Comparable<WindowConfigu

    /** @hide */
    public void scale(float scale) {
        mBounds.scale(scale);
        mMaxBounds.scale(scale);
        scaleBounds(scale, mBounds);
        scaleBounds(scale, mMaxBounds);
        if (mAppBounds != null) {
            mAppBounds.scale(scale);
            scaleBounds(scale, mAppBounds);
        }
    }

    /**
     * Size based scaling. This avoid inconsistent length when rounding 4 sides.
     * E.g. left=12, right=18, scale=0.8. The scaled width can be:
     *   int((right - left) * scale + 0.5) = int(4.8 + 0.5) = 5
     * But with rounding both left and right, the width will be inconsistent:
     *   int(right * scale + 0.5) - int(left * scale + 0.5) = int(14.9) - int(10.1) = 4
     * @hide
     */
    private static void scaleBounds(float scale, Rect bounds) {
        final int w = bounds.width();
        final int h = bounds.height();
        bounds.left = (int) (bounds.left * scale + .5f);
        bounds.top = (int) (bounds.top * scale + .5f);
        bounds.right = bounds.left + (int) (w * scale + .5f);
        bounds.bottom = bounds.top + (int) (h * scale + .5f);
    }

    /**
     * Copies the fields from delta into this Configuration object, keeping
     * track of which ones have changed. Any undefined fields in {@code delta}
+2 −0
Original line number Diff line number Diff line
@@ -23,6 +23,7 @@ import android.annotation.NonNull;
import android.annotation.Nullable;
import android.app.ActivityThread.ActivityClientRecord;
import android.app.ClientTransactionHandler;
import android.content.res.CompatibilityInfo;
import android.content.res.Configuration;
import android.os.IBinder;
import android.os.Parcel;
@@ -40,6 +41,7 @@ public class ActivityConfigurationChangeItem extends ActivityTransactionItem {

    @Override
    public void preExecute(android.app.ClientTransactionHandler client, IBinder token) {
        CompatibilityInfo.applyOverrideScaleIfNeeded(mConfiguration);
        // Notify the client of an upcoming change in the token configuration. This ensures that
        // batches of config change items only process the newest configuration.
        client.updatePendingActivityConfiguration(token, mConfiguration);
+2 −0
Original line number Diff line number Diff line
@@ -23,6 +23,7 @@ import android.annotation.Nullable;
import android.app.ActivityThread.ActivityClientRecord;
import android.app.ClientTransactionHandler;
import android.app.ResultInfo;
import android.content.res.CompatibilityInfo;
import android.os.IBinder;
import android.os.Parcel;
import android.os.Trace;
@@ -56,6 +57,7 @@ public class ActivityRelaunchItem extends ActivityTransactionItem {

    @Override
    public void preExecute(ClientTransactionHandler client, IBinder token) {
        CompatibilityInfo.applyOverrideScaleIfNeeded(mConfig);
        mActivityClientRecord = client.prepareRelaunchActivity(token, mPendingResults,
                mPendingNewIntents, mConfigChanges, mConfig, mPreserveWindow);
    }
+2 −0
Original line number Diff line number Diff line
@@ -18,6 +18,7 @@ package android.app.servertransaction;

import android.annotation.Nullable;
import android.app.ClientTransactionHandler;
import android.content.res.CompatibilityInfo;
import android.content.res.Configuration;
import android.os.IBinder;
import android.os.Parcel;
@@ -34,6 +35,7 @@ public class ConfigurationChangeItem extends ClientTransactionItem {

    @Override
    public void preExecute(android.app.ClientTransactionHandler client, IBinder token) {
        CompatibilityInfo.applyOverrideScaleIfNeeded(mConfiguration);
        client.updatePendingConfiguration(mConfiguration);
    }

Loading