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

Commit 14ebd1a7 authored by Chia-I Wu's avatar Chia-I Wu Committed by Luca Stefani
Browse files

surfaceflinger: improve RenderArea needsFiltering

Compare source crop (instead of the logical render area) against
physical render area to decide whether filtering is required.  This
allows us to get rid of Layer::setFiltering.

As a result, captureLayers for Recents no longer enables filtering.
Screenshots under landscape mode no longer enables filtering.

Bug: 113041375
Test: take screenshot, rotate screen, screencap
Change-Id: Ida95fdfec3a0dde7a19adf35c91bf3d570bab6bb
Merged-In: Ida95fdfec3a0dde7a19adf35c91bf3d570bab6bb
parent 0ddca9c2
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -206,7 +206,7 @@ void BufferLayer::onDraw(const RenderArea& renderArea, const Region& clip,

    if (!blackOutLayer) {
        // TODO: we could be more subtle with isFixedSize()
        const bool useFiltering = getFiltering() || needsFiltering(renderArea) || isFixedSize();
        const bool useFiltering = needsFiltering(renderArea) || isFixedSize();

        // Query the texture matrix given our current filtering mode.
        float textureMatrix[16];
+14 −1
Original line number Diff line number Diff line
@@ -355,7 +355,20 @@ public:
    int getHeight() const override { return mDevice->getHeight(); }
    int getWidth() const override { return mDevice->getWidth(); }
    bool isSecure() const override { return mDevice->isSecure(); }
    bool needsFiltering() const override { return mDevice->needsFiltering(); }

    bool needsFiltering() const override {
        if (mDevice->needsFiltering()) {
            return true;
        }

        const Rect sourceCrop = getSourceCrop();
        int width = sourceCrop.width();
        int height = sourceCrop.height();
        if (getRotationFlags() & Transform::ROT_90) {
            std::swap(width, height);
        }
        return width != getReqWidth() || height != getReqHeight();
    }

    Rect getSourceCrop() const override {
        const int orientation = mDevice->getInstallOrientation();
+0 −9
Original line number Diff line number Diff line
@@ -88,7 +88,6 @@ Layer::Layer(SurfaceFlinger* flinger, const sp<Client>& client, const String8& n
        mCurrentOpacity(true),
        mCurrentFrameNumber(0),
        mFrameLatencyNeeded(false),
        mFiltering(false),
        mNeedsFiltering(false),
        mProtectedByApp(false),
        mClientRef(client),
@@ -790,14 +789,6 @@ bool Layer::addSyncPoint(const std::shared_ptr<SyncPoint>& point) {
    return true;
}

void Layer::setFiltering(bool filtering) {
    mFiltering = filtering;
}

bool Layer::getFiltering() const {
    return mFiltering;
}

// ----------------------------------------------------------------------------
// local state
// ----------------------------------------------------------------------------
+0 −5
Original line number Diff line number Diff line
@@ -530,9 +530,6 @@ public:
    // -----------------------------------------------------------------------

    void clearWithOpenGL(const RenderArea& renderArea) const;
    void setFiltering(bool filtering);
    bool getFiltering() const;


    inline const State& getDrawingState() const { return mDrawingState; }
    inline const State& getCurrentState() const { return mCurrentState; }
@@ -755,8 +752,6 @@ protected:
    bool mCurrentOpacity;
    std::atomic<uint64_t> mCurrentFrameNumber;
    bool mFrameLatencyNeeded;
    // Whether filtering is forced on or not
    bool mFiltering;
    // Whether filtering is needed b/c of the drawingstate
    bool mNeedsFiltering;

+8 −13
Original line number Diff line number Diff line
@@ -4923,6 +4923,7 @@ status_t SurfaceFlinger::captureLayers(const sp<IBinder>& layerHandleBinder,
              : RenderArea(reqWidth, reqHeight, CaptureFill::CLEAR),
                mLayer(layer),
                mCrop(crop),
                mNeedsFiltering(false),
                mFlinger(flinger),
                mChildrenOnly(childrenOnly) {}
        const Transform& getTransform() const override { return mTransform; }
@@ -4933,7 +4934,7 @@ status_t SurfaceFlinger::captureLayers(const sp<IBinder>& layerHandleBinder,
        int getHeight() const override { return mLayer->getDrawingState().active.h; }
        int getWidth() const override { return mLayer->getDrawingState().active.w; }
        bool isSecure() const override { return false; }
        bool needsFiltering() const override { return false; }
        bool needsFiltering() const override { return mNeedsFiltering; }
        Rect getSourceCrop() const override {
            if (mCrop.isEmpty()) {
                return getBounds();
@@ -4954,6 +4955,11 @@ status_t SurfaceFlinger::captureLayers(const sp<IBinder>& layerHandleBinder,
        };

        void render(std::function<void()> drawLayers) override {
            const Rect sourceCrop = getSourceCrop();
            // no need to check rotation because there is none
            mNeedsFiltering = sourceCrop.width() != getReqWidth() ||
                sourceCrop.height() != getReqHeight();

            if (!mChildrenOnly) {
                mTransform = mLayer->getTransform().inverse();
                drawLayers();
@@ -4976,6 +4982,7 @@ status_t SurfaceFlinger::captureLayers(const sp<IBinder>& layerHandleBinder,
        // layer which has no properties set and which does not draw.
        sp<ContainerLayer> screenshotParentLayer;
        Transform mTransform;
        bool mNeedsFiltering;

        SurfaceFlinger* mFlinger;
        const bool mChildrenOnly;
@@ -5114,7 +5121,6 @@ void SurfaceFlinger::renderScreenImplLocked(const RenderArea& renderArea,
    auto& engine(getRenderEngine());

    // get screen geometry
    const auto raWidth = renderArea.getWidth();
    const auto raHeight = renderArea.getHeight();

    const auto reqWidth = renderArea.getReqWidth();
@@ -5122,15 +5128,6 @@ void SurfaceFlinger::renderScreenImplLocked(const RenderArea& renderArea,
    const auto sourceCrop = renderArea.getSourceCrop();
    const auto rotation = renderArea.getRotationFlags();

    bool filtering = false;
    if (primaryDisplayOrientation & DisplayState::eOrientationSwapMask) {
        filtering = static_cast<int32_t>(reqWidth) != raHeight ||
                static_cast<int32_t>(reqHeight) != raWidth;
    } else {
        filtering = static_cast<int32_t>(reqWidth) != raWidth ||
                static_cast<int32_t>(reqHeight) != raHeight;
    }

    // assume ColorMode::SRGB / RenderIntent::COLORIMETRIC
    engine.setOutputDataSpace(Dataspace::SRGB);
    engine.setDisplayMaxLuminance(DisplayDevice::sDefaultMaxLumiance);
@@ -5148,9 +5145,7 @@ void SurfaceFlinger::renderScreenImplLocked(const RenderArea& renderArea,
    engine.clearWithColor(0, 0, 0, alpha);

    traverseLayers([&](Layer* layer) {
        if (filtering) layer->setFiltering(true);
        layer->draw(renderArea, useIdentityTransform);
        if (filtering) layer->setFiltering(false);
    });
}