diff options
| author | 2019-03-20 23:48:20 -0700 | |
|---|---|---|
| committer | 2019-03-20 23:48:20 -0700 | |
| commit | 445c7b36406aecd467d1444d63add110a320fefc (patch) | |
| tree | e81b0c1918ae3dffe9101f03f30e5a56e5abadc8 /services/surfaceflinger/SurfaceFlinger.cpp | |
| parent | c754cfcdc720045940c2e0073e4d3d1f80d5019e (diff) | |
| parent | 3b14b7db6fb94e2cd812bf15a72723839aa756c4 (diff) | |
Merge changes from topic "RenderArea"
am: 3b14b7db6f
Change-Id: I6eea9c398eae9b8f67e20eb115e644bb0f7dd481
Diffstat (limited to 'services/surfaceflinger/SurfaceFlinger.cpp')
| -rw-r--r-- | services/surfaceflinger/SurfaceFlinger.cpp | 162 |
1 files changed, 63 insertions, 99 deletions
diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp index 4ec1e7f166..78d751a212 100644 --- a/services/surfaceflinger/SurfaceFlinger.cpp +++ b/services/surfaceflinger/SurfaceFlinger.cpp @@ -75,6 +75,7 @@ #include "LayerVector.h" #include "MonitoredProducer.h" #include "SurfaceFlinger.h" +#include "Transform.h" #include "clz.h" #include "DisplayHardware/ComposerHal.h" @@ -112,6 +113,27 @@ using ui::Hdr; using ui::RenderIntent; namespace { + +#pragma clang diagnostic push +#pragma clang diagnostic error "-Wswitch-enum" + +Transform::orientation_flags fromSurfaceComposerRotation(ISurfaceComposer::Rotation rotation) { + switch (rotation) { + case ISurfaceComposer::eRotateNone: + return Transform::ROT_0; + case ISurfaceComposer::eRotate90: + return Transform::ROT_90; + case ISurfaceComposer::eRotate180: + return Transform::ROT_180; + case ISurfaceComposer::eRotate270: + return Transform::ROT_270; + } + ALOGE("Invalid rotation passed to captureScreen(): %d\n", rotation); + return Transform::ROT_0; +} + +#pragma clang diagnostic pop + class ConditionalLock { public: ConditionalLock(Mutex& mutex, bool lock) : mMutex(mutex), mLocked(lock) { @@ -144,7 +166,7 @@ bool SurfaceFlinger::useVrFlinger; int64_t SurfaceFlinger::maxFrameBufferAcquiredBuffers; // TODO(courtneygo): Rename hasWideColorDisplay to clarify its actual meaning. bool SurfaceFlinger::hasWideColorDisplay; - +int SurfaceFlinger::primaryDisplayOrientation = DisplayState::eOrientationDefault; std::string getHwcServiceName() { char value[PROPERTY_VALUE_MAX] = {}; @@ -278,19 +300,19 @@ SurfaceFlinger::SurfaceFlinger() : SurfaceFlinger(SkipInitialization) { switch (primaryDisplayOrientation) { case V1_1::DisplayOrientation::ORIENTATION_90: - mPrimaryDisplayOrientation = DisplayState::eOrientation90; + SurfaceFlinger::primaryDisplayOrientation = DisplayState::eOrientation90; break; case V1_1::DisplayOrientation::ORIENTATION_180: - mPrimaryDisplayOrientation = DisplayState::eOrientation180; + SurfaceFlinger::primaryDisplayOrientation = DisplayState::eOrientation180; break; case V1_1::DisplayOrientation::ORIENTATION_270: - mPrimaryDisplayOrientation = DisplayState::eOrientation270; + SurfaceFlinger::primaryDisplayOrientation = DisplayState::eOrientation270; break; default: - mPrimaryDisplayOrientation = DisplayState::eOrientationDefault; + SurfaceFlinger::primaryDisplayOrientation = DisplayState::eOrientationDefault; break; } - ALOGV("Primary Display Orientation is set to %2d.", mPrimaryDisplayOrientation); + ALOGV("Primary Display Orientation is set to %2d.", SurfaceFlinger::primaryDisplayOrientation); mPrimaryDispSync.init(SurfaceFlinger::hasSyncFramework, SurfaceFlinger::dispSyncPresentTimeOffset); @@ -952,7 +974,7 @@ status_t SurfaceFlinger::getDisplayConfigs(const sp<IBinder>& display, info.secure = true; if (type == DisplayDevice::DISPLAY_PRIMARY && - mPrimaryDisplayOrientation & DisplayState::eOrientationSwapMask) { + primaryDisplayOrientation & DisplayState::eOrientationSwapMask) { std::swap(info.w, info.h); } @@ -2395,6 +2417,9 @@ sp<DisplayDevice> SurfaceFlinger::setupNewDisplayDeviceInternal( nativeWindow->setSwapInterval(nativeWindow.get(), 0); } + const int displayInstallOrientation = state.type == DisplayDevice::DISPLAY_PRIMARY ? + primaryDisplayOrientation : DisplayState::eOrientationDefault; + // virtual displays are always considered enabled auto initialPowerMode = (state.type >= DisplayDevice::DISPLAY_VIRTUAL) ? HWC_POWER_MODE_NORMAL : HWC_POWER_MODE_OFF; @@ -2402,7 +2427,7 @@ sp<DisplayDevice> SurfaceFlinger::setupNewDisplayDeviceInternal( sp<DisplayDevice> hw = new DisplayDevice(this, state.type, hwcId, state.isSecure, display, nativeWindow, dispSurface, std::move(renderSurface), displayWidth, displayHeight, - hasWideColorGamut, hdrCapabilities, + displayInstallOrientation, hasWideColorGamut, hdrCapabilities, supportedPerFrameMetadata, hwcColorModes, initialPowerMode); if (maxFrameBufferAcquiredBuffers >= 3) { @@ -4832,20 +4857,24 @@ status_t SurfaceFlinger::captureScreen(const sp<IBinder>& display, sp<GraphicBuf if (CC_UNLIKELY(display == 0)) return BAD_VALUE; - const sp<const DisplayDevice> device(getDisplayDeviceLocked(display)); - if (CC_UNLIKELY(device == 0)) return BAD_VALUE; + auto renderAreaRotation = fromSurfaceComposerRotation(rotation); - const Rect& dispScissor = device->getScissor(); - if (!dispScissor.isEmpty()) { - sourceCrop.set(dispScissor); - // adb shell screencap will default reqWidth and reqHeight to zeros. + sp<DisplayDevice> device; + { + Mutex::Autolock _l(mStateLock); + + device = getDisplayDeviceLocked(display); + if (!device) return BAD_VALUE; + + // set the requested width/height to the logical display viewport size + // by default if (reqWidth == 0 || reqHeight == 0) { reqWidth = uint32_t(device->getViewport().width()); reqHeight = uint32_t(device->getViewport().height()); } } - DisplayRenderArea renderArea(device, sourceCrop, reqHeight, reqWidth, rotation); + DisplayRenderArea renderArea(device, sourceCrop, reqWidth, reqHeight, renderAreaRotation); auto traverseLayers = std::bind(std::mem_fn(&SurfaceFlinger::traverseLayersInDisplay), this, device, minLayerZ, maxLayerZ, std::placeholders::_1); @@ -4861,9 +4890,10 @@ status_t SurfaceFlinger::captureLayers(const sp<IBinder>& layerHandleBinder, public: LayerRenderArea(SurfaceFlinger* flinger, const sp<Layer>& layer, const Rect crop, int32_t reqWidth, int32_t reqHeight, bool childrenOnly) - : RenderArea(reqHeight, reqWidth, CaptureFill::CLEAR), + : RenderArea(reqWidth, reqHeight, CaptureFill::CLEAR), mLayer(layer), mCrop(crop), + mNeedsFiltering(false), mFlinger(flinger), mChildrenOnly(childrenOnly) {} const Transform& getTransform() const override { return mTransform; } @@ -4874,7 +4904,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(); @@ -4895,6 +4925,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(); @@ -4917,6 +4952,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; @@ -4951,6 +4987,14 @@ status_t SurfaceFlinger::captureLayers(const sp<IBinder>& layerHandleBinder, int32_t reqWidth = crop.width() * frameScale; int32_t reqHeight = crop.height() * frameScale; + // really small crop or frameScale + if (reqWidth <= 0) { + reqWidth = 1; + } + if (reqHeight <= 0) { + reqHeight = 1; + } + LayerRenderArea renderArea(this, parent, crop, reqWidth, reqHeight, childrenOnly); auto traverseLayers = [parent, childrenOnly](const LayerVector::Visitor& visitor) { @@ -4972,8 +5016,6 @@ status_t SurfaceFlinger::captureScreenCommon(RenderArea& renderArea, bool useIdentityTransform) { ATRACE_CALL(); - renderArea.updateDimensions(mPrimaryDisplayOrientation); - const uint32_t usage = GRALLOC_USAGE_SW_READ_OFTEN | GRALLOC_USAGE_SW_WRITE_OFTEN | GRALLOC_USAGE_HW_RENDER | GRALLOC_USAGE_HW_TEXTURE; *outBuffer = new GraphicBuffer(renderArea.getReqWidth(), renderArea.getReqHeight(), @@ -5049,57 +5091,12 @@ 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(); const auto reqHeight = renderArea.getReqHeight(); - Rect sourceCrop = renderArea.getSourceCrop(); - - bool filtering = false; - if (mPrimaryDisplayOrientation & 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; - } - - // if a default or invalid sourceCrop is passed in, set reasonable values - if (sourceCrop.width() == 0 || sourceCrop.height() == 0 || !sourceCrop.isValid()) { - sourceCrop.setLeftTop(Point(0, 0)); - sourceCrop.setRightBottom(Point(raWidth, raHeight)); - } else if (mPrimaryDisplayOrientation != DisplayState::eOrientationDefault) { - Transform tr; - uint32_t flags = 0x00; - switch (mPrimaryDisplayOrientation) { - case DisplayState::eOrientation90: - flags = Transform::ROT_90; - break; - case DisplayState::eOrientation180: - flags = Transform::ROT_180; - break; - case DisplayState::eOrientation270: - flags = Transform::ROT_270; - break; - } - tr.set(flags, raWidth, raHeight); - sourceCrop = tr.transform(sourceCrop); - } - - // ensure that sourceCrop is inside screen - if (sourceCrop.left < 0) { - ALOGE("Invalid crop rect: l = %d (< 0)", sourceCrop.left); - } - if (sourceCrop.right > raWidth) { - ALOGE("Invalid crop rect: r = %d (> %d)", sourceCrop.right, raWidth); - } - if (sourceCrop.top < 0) { - ALOGE("Invalid crop rect: t = %d (< 0)", sourceCrop.top); - } - if (sourceCrop.bottom > raHeight) { - ALOGE("Invalid crop rect: b = %d (> %d)", sourceCrop.bottom, raHeight); - } + const auto sourceCrop = renderArea.getSourceCrop(); + const auto rotation = renderArea.getRotationFlags(); // assume ColorMode::SRGB / RenderIntent::COLORIMETRIC engine.setOutputDataSpace(Dataspace::SRGB); @@ -5108,37 +5105,6 @@ void SurfaceFlinger::renderScreenImplLocked(const RenderArea& renderArea, // make sure to clear all GL error flags engine.checkErrors(); - Transform::orientation_flags rotation = renderArea.getRotationFlags(); - if (mPrimaryDisplayOrientation != DisplayState::eOrientationDefault) { - // convert hw orientation into flag presentation - // here inverse transform needed - uint8_t hw_rot_90 = 0x00; - uint8_t hw_flip_hv = 0x00; - switch (mPrimaryDisplayOrientation) { - case DisplayState::eOrientation90: - hw_rot_90 = Transform::ROT_90; - hw_flip_hv = Transform::ROT_180; - break; - case DisplayState::eOrientation180: - hw_flip_hv = Transform::ROT_180; - break; - case DisplayState::eOrientation270: - hw_rot_90 = Transform::ROT_90; - break; - } - - // transform flags operation - // 1) flip H V if both have ROT_90 flag - // 2) XOR these flags - uint8_t rotation_rot_90 = rotation & Transform::ROT_90; - uint8_t rotation_flip_hv = rotation & Transform::ROT_180; - if (rotation_rot_90 & hw_rot_90) { - rotation_flip_hv = (~rotation_flip_hv) & Transform::ROT_180; - } - rotation = static_cast<Transform::orientation_flags> - ((rotation_rot_90 ^ hw_rot_90) | (rotation_flip_hv ^ hw_flip_hv)); - } - // set-up our viewport engine.setViewportAndProjection(reqWidth, reqHeight, sourceCrop, raHeight, yswap, rotation); @@ -5149,9 +5115,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); }); } |