Home | History | Annotate | Download | only in surfaceflinger
      1 /*
      2  * Copyright (C) 2007 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 // #define LOG_NDEBUG 0
     18 #undef LOG_TAG
     19 #define LOG_TAG "ColorLayer"
     20 
     21 #include <stdint.h>
     22 #include <stdlib.h>
     23 #include <sys/types.h>
     24 
     25 #include <compositionengine/CompositionEngine.h>
     26 #include <compositionengine/Display.h>
     27 #include <compositionengine/Layer.h>
     28 #include <compositionengine/LayerCreationArgs.h>
     29 #include <compositionengine/OutputLayer.h>
     30 #include <compositionengine/impl/LayerCompositionState.h>
     31 #include <compositionengine/impl/OutputLayerCompositionState.h>
     32 #include <renderengine/RenderEngine.h>
     33 #include <ui/GraphicBuffer.h>
     34 #include <utils/Errors.h>
     35 #include <utils/Log.h>
     36 
     37 #include "ColorLayer.h"
     38 #include "DisplayDevice.h"
     39 #include "SurfaceFlinger.h"
     40 
     41 namespace android {
     42 // ---------------------------------------------------------------------------
     43 
     44 ColorLayer::ColorLayer(const LayerCreationArgs& args)
     45       : Layer(args),
     46         mCompositionLayer{mFlinger->getCompositionEngine().createLayer(
     47                 compositionengine::LayerCreationArgs{this})} {}
     48 
     49 ColorLayer::~ColorLayer() = default;
     50 
     51 bool ColorLayer::prepareClientLayer(const RenderArea& renderArea, const Region& clip,
     52                                     bool useIdentityTransform, Region& clearRegion,
     53                                     const bool supportProtectedContent,
     54                                     renderengine::LayerSettings& layer) {
     55     Layer::prepareClientLayer(renderArea, clip, useIdentityTransform, clearRegion,
     56                               supportProtectedContent, layer);
     57     half4 color(getColor());
     58     half3 solidColor(color.r, color.g, color.b);
     59     layer.source.solidColor = solidColor;
     60     return true;
     61 }
     62 
     63 bool ColorLayer::isVisible() const {
     64     return !isHiddenByPolicy() && getAlpha() > 0.0f;
     65 }
     66 
     67 bool ColorLayer::setColor(const half3& color) {
     68     if (mCurrentState.color.r == color.r && mCurrentState.color.g == color.g &&
     69         mCurrentState.color.b == color.b) {
     70         return false;
     71     }
     72 
     73     mCurrentState.sequence++;
     74     mCurrentState.color.r = color.r;
     75     mCurrentState.color.g = color.g;
     76     mCurrentState.color.b = color.b;
     77     mCurrentState.modified = true;
     78     setTransactionFlags(eTransactionNeeded);
     79     return true;
     80 }
     81 
     82 bool ColorLayer::setDataspace(ui::Dataspace dataspace) {
     83     if (mCurrentState.dataspace == dataspace) {
     84         return false;
     85     }
     86 
     87     mCurrentState.sequence++;
     88     mCurrentState.dataspace = dataspace;
     89     mCurrentState.modified = true;
     90     setTransactionFlags(eTransactionNeeded);
     91     return true;
     92 }
     93 
     94 void ColorLayer::setPerFrameData(const sp<const DisplayDevice>& display,
     95                                  const ui::Transform& transform, const Rect& viewport,
     96                                  int32_t /* supportedPerFrameMetadata */,
     97                                  const ui::Dataspace targetDataspace) {
     98     RETURN_IF_NO_HWC_LAYER(display);
     99 
    100     Region visible = transform.transform(visibleRegion.intersect(viewport));
    101 
    102     const auto outputLayer = findOutputLayerForDisplay(display);
    103     LOG_FATAL_IF(!outputLayer || !outputLayer->getState().hwc);
    104 
    105     auto& hwcLayer = (*outputLayer->getState().hwc).hwcLayer;
    106 
    107     auto error = hwcLayer->setVisibleRegion(visible);
    108     if (error != HWC2::Error::None) {
    109         ALOGE("[%s] Failed to set visible region: %s (%d)", mName.string(),
    110               to_string(error).c_str(), static_cast<int32_t>(error));
    111         visible.dump(LOG_TAG);
    112     }
    113     outputLayer->editState().visibleRegion = visible;
    114 
    115     setCompositionType(display, Hwc2::IComposerClient::Composition::SOLID_COLOR);
    116 
    117     const ui::Dataspace dataspace =
    118             isColorSpaceAgnostic() && targetDataspace != ui::Dataspace::UNKNOWN ? targetDataspace
    119                                                                                 : mCurrentDataSpace;
    120     error = hwcLayer->setDataspace(dataspace);
    121     if (error != HWC2::Error::None) {
    122         ALOGE("[%s] Failed to set dataspace %d: %s (%d)", mName.string(), dataspace,
    123               to_string(error).c_str(), static_cast<int32_t>(error));
    124     }
    125 
    126     auto& layerCompositionState = getCompositionLayer()->editState().frontEnd;
    127     layerCompositionState.dataspace = mCurrentDataSpace;
    128 
    129     half4 color = getColor();
    130     error = hwcLayer->setColor({static_cast<uint8_t>(std::round(255.0f * color.r)),
    131                                 static_cast<uint8_t>(std::round(255.0f * color.g)),
    132                                 static_cast<uint8_t>(std::round(255.0f * color.b)), 255});
    133     if (error != HWC2::Error::None) {
    134         ALOGE("[%s] Failed to set color: %s (%d)", mName.string(), to_string(error).c_str(),
    135               static_cast<int32_t>(error));
    136     }
    137     layerCompositionState.color = {static_cast<uint8_t>(std::round(255.0f * color.r)),
    138                                    static_cast<uint8_t>(std::round(255.0f * color.g)),
    139                                    static_cast<uint8_t>(std::round(255.0f * color.b)), 255};
    140 
    141     // Clear out the transform, because it doesn't make sense absent a source buffer
    142     error = hwcLayer->setTransform(HWC2::Transform::None);
    143     if (error != HWC2::Error::None) {
    144         ALOGE("[%s] Failed to clear transform: %s (%d)", mName.string(), to_string(error).c_str(),
    145               static_cast<int32_t>(error));
    146     }
    147     outputLayer->editState().bufferTransform = static_cast<Hwc2::Transform>(0);
    148 
    149     error = hwcLayer->setColorTransform(getColorTransform());
    150     if (error != HWC2::Error::None) {
    151         ALOGE("[%s] Failed to setColorTransform: %s (%d)", mName.string(),
    152                 to_string(error).c_str(), static_cast<int32_t>(error));
    153     }
    154     layerCompositionState.colorTransform = getColorTransform();
    155 
    156     error = hwcLayer->setSurfaceDamage(surfaceDamageRegion);
    157     if (error != HWC2::Error::None) {
    158         ALOGE("[%s] Failed to set surface damage: %s (%d)", mName.string(),
    159               to_string(error).c_str(), static_cast<int32_t>(error));
    160         surfaceDamageRegion.dump(LOG_TAG);
    161     }
    162     layerCompositionState.surfaceDamage = surfaceDamageRegion;
    163 }
    164 
    165 void ColorLayer::commitTransaction(const State& stateToCommit) {
    166     Layer::commitTransaction(stateToCommit);
    167     mCurrentDataSpace = mDrawingState.dataspace;
    168 }
    169 
    170 std::shared_ptr<compositionengine::Layer> ColorLayer::getCompositionLayer() const {
    171     return mCompositionLayer;
    172 }
    173 
    174 // ---------------------------------------------------------------------------
    175 
    176 }; // namespace android
    177