blob: 0725926be4810c2f084c87e4dd8d1f8be921f1b9 [file] [log] [blame]
Lloyd Pique32cbe282018-10-19 13:09:22 -07001/*
2 * Copyright 2019 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#include <android-base/stringprintf.h>
18#include <compositionengine/CompositionEngine.h>
Lloyd Pique3d0c02e2018-10-19 18:38:12 -070019#include <compositionengine/DisplayColorProfile.h>
Lloyd Piquecc01a452018-12-04 17:24:00 -080020#include <compositionengine/LayerFE.h>
Lloyd Pique31cb2942018-10-19 17:23:03 -070021#include <compositionengine/RenderSurface.h>
Lloyd Pique32cbe282018-10-19 13:09:22 -070022#include <compositionengine/impl/Output.h>
Lloyd Piquecc01a452018-12-04 17:24:00 -080023#include <compositionengine/impl/OutputLayer.h>
Lloyd Pique32cbe282018-10-19 13:09:22 -070024#include <ui/DebugUtils.h>
25
Lloyd Piquefeb73d72018-12-04 17:23:44 -080026namespace android::compositionengine {
27
28Output::~Output() = default;
29
30namespace impl {
Lloyd Pique32cbe282018-10-19 13:09:22 -070031
32Output::Output(const CompositionEngine& compositionEngine)
33 : mCompositionEngine(compositionEngine) {}
34
35Output::~Output() = default;
36
37const CompositionEngine& Output::getCompositionEngine() const {
38 return mCompositionEngine;
39}
40
41bool Output::isValid() const {
Lloyd Pique3d0c02e2018-10-19 18:38:12 -070042 return mDisplayColorProfile && mDisplayColorProfile->isValid() && mRenderSurface &&
43 mRenderSurface->isValid();
Lloyd Pique32cbe282018-10-19 13:09:22 -070044}
45
46const std::string& Output::getName() const {
47 return mName;
48}
49
50void Output::setName(const std::string& name) {
51 mName = name;
52}
53
54void Output::setCompositionEnabled(bool enabled) {
55 if (mState.isEnabled == enabled) {
56 return;
57 }
58
59 mState.isEnabled = enabled;
60 dirtyEntireOutput();
61}
62
63void Output::setProjection(const ui::Transform& transform, int32_t orientation, const Rect& frame,
64 const Rect& viewport, const Rect& scissor, bool needsFiltering) {
65 mState.transform = transform;
66 mState.orientation = orientation;
67 mState.scissor = scissor;
68 mState.frame = frame;
69 mState.viewport = viewport;
70 mState.needsFiltering = needsFiltering;
71
72 dirtyEntireOutput();
73}
74
Lloyd Pique31cb2942018-10-19 17:23:03 -070075// TODO(lpique): Rename setSize() once more is moved.
76void Output::setBounds(const ui::Size& size) {
77 mRenderSurface->setDisplaySize(size);
78 // TODO(lpique): Rename mState.size once more is moved.
79 mState.bounds = Rect(mRenderSurface->getSize());
Lloyd Pique32cbe282018-10-19 13:09:22 -070080
81 dirtyEntireOutput();
82}
83
Lloyd Piqueef36b002019-01-23 17:52:04 -080084void Output::setLayerStackFilter(uint32_t layerStackId, bool isInternal) {
85 mState.layerStackId = layerStackId;
86 mState.layerStackInternal = isInternal;
Lloyd Pique32cbe282018-10-19 13:09:22 -070087
88 dirtyEntireOutput();
89}
90
91void Output::setColorTransform(const mat4& transform) {
Lloyd Pique77f79a22019-04-29 15:55:40 -070092 if (mState.colorTransformMat == transform) {
93 return;
94 }
95
Lloyd Pique32cbe282018-10-19 13:09:22 -070096 const bool isIdentity = (transform == mat4());
Lloyd Piqueef958122019-02-05 18:00:12 -080097 const auto newColorTransform =
Lloyd Pique32cbe282018-10-19 13:09:22 -070098 isIdentity ? HAL_COLOR_TRANSFORM_IDENTITY : HAL_COLOR_TRANSFORM_ARBITRARY_MATRIX;
Lloyd Piqueef958122019-02-05 18:00:12 -080099
Lloyd Piqueef958122019-02-05 18:00:12 -0800100 mState.colorTransform = newColorTransform;
Alec Mouric7e8ce82019-04-02 12:28:05 -0700101 mState.colorTransformMat = transform;
Lloyd Piqueef958122019-02-05 18:00:12 -0800102
103 dirtyEntireOutput();
Lloyd Pique32cbe282018-10-19 13:09:22 -0700104}
105
106void Output::setColorMode(ui::ColorMode mode, ui::Dataspace dataspace,
Lloyd Piquef5275482019-01-29 18:42:42 -0800107 ui::RenderIntent renderIntent,
108 ui::Dataspace colorSpaceAgnosticDataspace) {
109 ui::Dataspace targetDataspace =
110 getDisplayColorProfile()->getTargetDataspace(mode, dataspace,
111 colorSpaceAgnosticDataspace);
112
Lloyd Piqueef958122019-02-05 18:00:12 -0800113 if (mState.colorMode == mode && mState.dataspace == dataspace &&
Lloyd Piquef5275482019-01-29 18:42:42 -0800114 mState.renderIntent == renderIntent && mState.targetDataspace == targetDataspace) {
Lloyd Piqueef958122019-02-05 18:00:12 -0800115 return;
116 }
117
Lloyd Pique32cbe282018-10-19 13:09:22 -0700118 mState.colorMode = mode;
119 mState.dataspace = dataspace;
120 mState.renderIntent = renderIntent;
Lloyd Piquef5275482019-01-29 18:42:42 -0800121 mState.targetDataspace = targetDataspace;
Lloyd Pique32cbe282018-10-19 13:09:22 -0700122
Lloyd Pique31cb2942018-10-19 17:23:03 -0700123 mRenderSurface->setBufferDataspace(dataspace);
124
Lloyd Pique32cbe282018-10-19 13:09:22 -0700125 ALOGV("Set active color mode: %s (%d), active render intent: %s (%d)",
126 decodeColorMode(mode).c_str(), mode, decodeRenderIntent(renderIntent).c_str(),
127 renderIntent);
Lloyd Piqueef958122019-02-05 18:00:12 -0800128
129 dirtyEntireOutput();
Lloyd Pique32cbe282018-10-19 13:09:22 -0700130}
131
132void Output::dump(std::string& out) const {
133 using android::base::StringAppendF;
134
135 StringAppendF(&out, " Composition Output State: [\"%s\"]", mName.c_str());
136
137 out.append("\n ");
138
139 dumpBase(out);
140}
141
142void Output::dumpBase(std::string& out) const {
143 mState.dump(out);
Lloyd Pique31cb2942018-10-19 17:23:03 -0700144
Lloyd Pique3d0c02e2018-10-19 18:38:12 -0700145 if (mDisplayColorProfile) {
146 mDisplayColorProfile->dump(out);
147 } else {
148 out.append(" No display color profile!\n");
149 }
150
Lloyd Pique31cb2942018-10-19 17:23:03 -0700151 if (mRenderSurface) {
152 mRenderSurface->dump(out);
153 } else {
154 out.append(" No render surface!\n");
155 }
Lloyd Pique37c2c9b2018-12-04 17:25:10 -0800156
Lloyd Pique207def92019-02-28 16:09:52 -0800157 android::base::StringAppendF(&out, "\n %zu Layers\b", mOutputLayersOrderedByZ.size());
Lloyd Pique37c2c9b2018-12-04 17:25:10 -0800158 for (const auto& outputLayer : mOutputLayersOrderedByZ) {
159 if (!outputLayer) {
160 continue;
161 }
162 outputLayer->dump(out);
163 }
Lloyd Pique31cb2942018-10-19 17:23:03 -0700164}
165
Lloyd Pique3d0c02e2018-10-19 18:38:12 -0700166compositionengine::DisplayColorProfile* Output::getDisplayColorProfile() const {
167 return mDisplayColorProfile.get();
168}
169
170void Output::setDisplayColorProfile(std::unique_ptr<compositionengine::DisplayColorProfile> mode) {
171 mDisplayColorProfile = std::move(mode);
172}
173
174void Output::setDisplayColorProfileForTest(
175 std::unique_ptr<compositionengine::DisplayColorProfile> mode) {
176 mDisplayColorProfile = std::move(mode);
177}
178
Lloyd Pique31cb2942018-10-19 17:23:03 -0700179compositionengine::RenderSurface* Output::getRenderSurface() const {
180 return mRenderSurface.get();
181}
182
183void Output::setRenderSurface(std::unique_ptr<compositionengine::RenderSurface> surface) {
184 mRenderSurface = std::move(surface);
185 mState.bounds = Rect(mRenderSurface->getSize());
186
187 dirtyEntireOutput();
188}
189
190void Output::setRenderSurfaceForTest(std::unique_ptr<compositionengine::RenderSurface> surface) {
191 mRenderSurface = std::move(surface);
Lloyd Pique32cbe282018-10-19 13:09:22 -0700192}
193
194const OutputCompositionState& Output::getState() const {
195 return mState;
196}
197
198OutputCompositionState& Output::editState() {
199 return mState;
200}
201
Alec Mourie7d1d4a2019-02-05 01:13:46 +0000202Region Output::getDirtyRegion(bool repaintEverything) const {
203 Region dirty(mState.viewport);
204 if (!repaintEverything) {
205 dirty.andSelf(mState.dirtyRegion);
Lloyd Pique32cbe282018-10-19 13:09:22 -0700206 }
207 return dirty;
208}
209
Lloyd Piqueef36b002019-01-23 17:52:04 -0800210bool Output::belongsInOutput(uint32_t layerStackId, bool internalOnly) const {
211 // The layerStackId's must match, and also the layer must not be internal
212 // only when not on an internal output.
213 return (layerStackId == mState.layerStackId) && (!internalOnly || mState.layerStackInternal);
Lloyd Pique32cbe282018-10-19 13:09:22 -0700214}
215
Lloyd Piquecc01a452018-12-04 17:24:00 -0800216compositionengine::OutputLayer* Output::getOutputLayerForLayer(
217 compositionengine::Layer* layer) const {
218 for (const auto& outputLayer : mOutputLayersOrderedByZ) {
219 if (outputLayer && &outputLayer->getLayer() == layer) {
220 return outputLayer.get();
221 }
222 }
223 return nullptr;
224}
225
226std::unique_ptr<compositionengine::OutputLayer> Output::getOrCreateOutputLayer(
Lloyd Pique07e33212018-12-18 16:33:37 -0800227 std::optional<DisplayId> displayId, std::shared_ptr<compositionengine::Layer> layer,
228 sp<compositionengine::LayerFE> layerFE) {
Lloyd Piquecc01a452018-12-04 17:24:00 -0800229 for (auto& outputLayer : mOutputLayersOrderedByZ) {
230 if (outputLayer && &outputLayer->getLayer() == layer.get()) {
231 return std::move(outputLayer);
232 }
233 }
Lloyd Pique07e33212018-12-18 16:33:37 -0800234 return createOutputLayer(mCompositionEngine, displayId, *this, layer, layerFE);
Lloyd Piquecc01a452018-12-04 17:24:00 -0800235}
236
237void Output::setOutputLayersOrderedByZ(OutputLayers&& layers) {
238 mOutputLayersOrderedByZ = std::move(layers);
239}
240
241const Output::OutputLayers& Output::getOutputLayersOrderedByZ() const {
242 return mOutputLayersOrderedByZ;
243}
244
Lloyd Pique32cbe282018-10-19 13:09:22 -0700245void Output::dirtyEntireOutput() {
246 mState.dirtyRegion.set(mState.bounds);
247}
248
Lloyd Piquefeb73d72018-12-04 17:23:44 -0800249} // namespace impl
250} // namespace android::compositionengine