From 54fa17f667c285a5c9225e238c8132dfe830ef36 Mon Sep 17 00:00:00 2001 From: Chris Craik Date: Wed, 25 Nov 2015 14:14:53 -0800 Subject: Add ListView rendering benchmark Also fixes a bug in DrawRenderNodeOp recording, which was triggered by the new test. Change-Id: I328f2ed908495eb95ca8ce87a365d02650e72cd5 --- libs/hwui/FrameInfoVisualizer.cpp | 31 ++++++++++++++++--------------- 1 file changed, 16 insertions(+), 15 deletions(-) (limited to 'libs/hwui/FrameInfoVisualizer.cpp') diff --git a/libs/hwui/FrameInfoVisualizer.cpp b/libs/hwui/FrameInfoVisualizer.cpp index b416615c20e1..b7dd3b7e2f95 100644 --- a/libs/hwui/FrameInfoVisualizer.cpp +++ b/libs/hwui/FrameInfoVisualizer.cpp @@ -16,6 +16,7 @@ #include "FrameInfoVisualizer.h" #include "OpenGLRenderer.h" +#include "utils/Color.h" #include #include @@ -27,19 +28,19 @@ #define PROFILE_DRAW_THRESHOLD_STROKE_WIDTH 2 #define PROFILE_DRAW_DP_PER_MS 7 +namespace android { +namespace uirenderer { + // Must be NUM_ELEMENTS in size -static const SkColor THRESHOLD_COLOR = 0xff5faa4d; -static const SkColor BAR_FAST_ALPHA = 0x8F000000; -static const SkColor BAR_JANKY_ALPHA = 0xDF000000; +static const SkColor THRESHOLD_COLOR = Color::Green_500; +static const SkColor BAR_FAST_MASK = 0x8FFFFFFF; +static const SkColor BAR_JANKY_MASK = 0xDFFFFFFF; // We could get this from TimeLord and use the actual frame interval, but // this is good enough #define FRAME_THRESHOLD 16 #define FRAME_THRESHOLD_NS 16000000 -namespace android { -namespace uirenderer { - struct BarSegment { FrameInfoIndex start; FrameInfoIndex end; @@ -47,13 +48,13 @@ struct BarSegment { }; static const std::array Bar {{ - { FrameInfoIndex::IntendedVsync, FrameInfoIndex::HandleInputStart, 0x00796B }, - { FrameInfoIndex::HandleInputStart, FrameInfoIndex::PerformTraversalsStart, 0x388E3C }, - { FrameInfoIndex::PerformTraversalsStart, FrameInfoIndex::DrawStart, 0x689F38}, - { FrameInfoIndex::DrawStart, FrameInfoIndex::SyncStart, 0x2196F3}, - { FrameInfoIndex::SyncStart, FrameInfoIndex::IssueDrawCommandsStart, 0x4FC3F7}, - { FrameInfoIndex::IssueDrawCommandsStart, FrameInfoIndex::SwapBuffers, 0xF44336}, - { FrameInfoIndex::SwapBuffers, FrameInfoIndex::FrameCompleted, 0xFF9800}, + { FrameInfoIndex::IntendedVsync, FrameInfoIndex::HandleInputStart, Color::Teal_700 }, + { FrameInfoIndex::HandleInputStart, FrameInfoIndex::PerformTraversalsStart, Color::Green_700 }, + { FrameInfoIndex::PerformTraversalsStart, FrameInfoIndex::DrawStart, Color::LightGreen_700 }, + { FrameInfoIndex::DrawStart, FrameInfoIndex::SyncStart, Color::Blue_500 }, + { FrameInfoIndex::SyncStart, FrameInfoIndex::IssueDrawCommandsStart, Color::LightBlue_300 }, + { FrameInfoIndex::IssueDrawCommandsStart, FrameInfoIndex::SwapBuffers, Color::Red_500}, + { FrameInfoIndex::SwapBuffers, FrameInfoIndex::FrameCompleted, Color::Orange_500}, }}; static int dpToPx(int dp, float density) { @@ -197,9 +198,9 @@ void FrameInfoVisualizer::drawGraph(OpenGLRenderer* canvas) { SkPaint paint; for (size_t i = 0; i < Bar.size(); i++) { nextBarSegment(Bar[i].start, Bar[i].end); - paint.setColor(Bar[i].color | BAR_FAST_ALPHA); + paint.setColor(Bar[i].color & BAR_FAST_MASK); canvas->drawRects(mFastRects.get(), mNumFastRects * 4, &paint); - paint.setColor(Bar[i].color | BAR_JANKY_ALPHA); + paint.setColor(Bar[i].color & BAR_JANKY_MASK); canvas->drawRects(mJankyRects.get(), mNumJankyRects * 4, &paint); } } -- cgit v1.2.3-59-g8ed1b From 1dfa0704964c17e45775b9e01f1fa0b1a10774f7 Mon Sep 17 00:00:00 2001 From: Chris Craik Date: Fri, 4 Mar 2016 15:59:24 -0800 Subject: Support GPU profiling vis in new pipeline bug:27353099 Change-Id: I905c1a998d9a9e2097c047dab9de87a70d7a370e --- libs/hwui/BakedOpRenderer.cpp | 44 ++++++++++++++++++++++++-------- libs/hwui/BakedOpRenderer.h | 10 ++++++++ libs/hwui/FrameInfoVisualizer.cpp | 35 +++++++++++++------------ libs/hwui/FrameInfoVisualizer.h | 12 ++++++--- libs/hwui/renderthread/CanvasContext.cpp | 18 +++++++++++-- 5 files changed, 87 insertions(+), 32 deletions(-) (limited to 'libs/hwui/FrameInfoVisualizer.cpp') diff --git a/libs/hwui/BakedOpRenderer.cpp b/libs/hwui/BakedOpRenderer.cpp index c14738469058..98493d73776e 100644 --- a/libs/hwui/BakedOpRenderer.cpp +++ b/libs/hwui/BakedOpRenderer.cpp @@ -135,17 +135,7 @@ void BakedOpRenderer::endFrame(const Rect& repaintRect) { mRenderState.stencil().disable(); } - mCaches.clearGarbage(); - mCaches.pathCache.trim(); - mCaches.tessellationCache.trim(); - -#if DEBUG_MEMORY_USAGE - mCaches.dumpMemoryUsage(); -#else - if (Properties::debugLevel & kDebugMemory) { - mCaches.dumpMemoryUsage(); - } -#endif + // Note: we leave FBO 0 renderable here, for post-frame-content decoration } void BakedOpRenderer::setViewport(uint32_t width, uint32_t height) { @@ -179,6 +169,38 @@ Texture* BakedOpRenderer::getTexture(const SkBitmap* bitmap) { return texture; } +void BakedOpRenderer::drawRects(const float* rects, int count, const SkPaint* paint) { + std::vector vertices; + vertices.reserve(count); + Vertex* vertex = vertices.data(); + + for (int index = 0; index < count; index += 4) { + float l = rects[index + 0]; + float t = rects[index + 1]; + float r = rects[index + 2]; + float b = rects[index + 3]; + + Vertex::set(vertex++, l, t); + Vertex::set(vertex++, r, t); + Vertex::set(vertex++, l, b); + Vertex::set(vertex++, r, b); + } + + LOG_ALWAYS_FATAL_IF(mRenderTarget.frameBufferId != 0, "decoration only supported for FBO 0"); + // TODO: Currently assume full FBO damage, due to FrameInfoVisualizer::unionDirty. + // Should should scissor safely. + mRenderState.scissor().setEnabled(false); + Glop glop; + GlopBuilder(mRenderState, mCaches, &glop) + .setRoundRectClipState(nullptr) + .setMeshIndexedQuads(vertices.data(), count / 4) + .setFillPaint(*paint, 1.0f) + .setTransform(Matrix4::identity(), TransformFlags::None) + .setModelViewIdentityEmptyBounds() + .build(); + mRenderState.render(glop, mRenderTarget.orthoMatrix); +} + // clears and re-fills stencil with provided rendertarget space quads, // and then put stencil into test mode void BakedOpRenderer::setupStencilQuads(std::vector& quadVertices, diff --git a/libs/hwui/BakedOpRenderer.h b/libs/hwui/BakedOpRenderer.h index 55ea93531bc7..4b652553b6b9 100644 --- a/libs/hwui/BakedOpRenderer.h +++ b/libs/hwui/BakedOpRenderer.h @@ -85,6 +85,16 @@ public: bool offscreenRenderTarget() { return mRenderTarget.offscreenBuffer != nullptr; } void dirtyRenderTarget(const Rect& dirtyRect); bool didDraw() const { return mHasDrawn; } + + uint32_t getViewportWidth() const { return mRenderTarget.viewportWidth; } + uint32_t getViewportHeight() const { return mRenderTarget.viewportHeight; } + + // simple draw methods, to be used for end frame decoration + void drawRect(float left, float top, float right, float bottom, const SkPaint* paint) { + float ltrb[4] = { left, top, right, bottom }; + drawRects(ltrb, 4, paint); + } + void drawRects(const float* rects, int count, const SkPaint* paint); private: void setViewport(uint32_t width, uint32_t height); void clearColorBuffer(const Rect& clearRect); diff --git a/libs/hwui/FrameInfoVisualizer.cpp b/libs/hwui/FrameInfoVisualizer.cpp index b7dd3b7e2f95..adadd32a2fc0 100644 --- a/libs/hwui/FrameInfoVisualizer.cpp +++ b/libs/hwui/FrameInfoVisualizer.cpp @@ -15,7 +15,11 @@ */ #include "FrameInfoVisualizer.h" +#if HWUI_NEW_OPS +#include "BakedOpRenderer.h" +#else #include "OpenGLRenderer.h" +#endif #include "utils/Color.h" #include @@ -88,7 +92,7 @@ void FrameInfoVisualizer::unionDirty(SkRect* dirty) { } } -void FrameInfoVisualizer::draw(OpenGLRenderer* canvas) { +void FrameInfoVisualizer::draw(ContentRenderer* renderer) { RETURN_IF_DISABLED(); if (mShowDirtyRegions) { @@ -96,7 +100,7 @@ void FrameInfoVisualizer::draw(OpenGLRenderer* canvas) { if (mFlashToggle) { SkPaint paint; paint.setColor(0x7fff0000); - canvas->drawRect(mDirtyRegion.fLeft, mDirtyRegion.fTop, + renderer->drawRect(mDirtyRegion.fLeft, mDirtyRegion.fTop, mDirtyRegion.fRight, mDirtyRegion.fBottom, &paint); } } @@ -111,9 +115,9 @@ void FrameInfoVisualizer::draw(OpenGLRenderer* canvas) { info.markSwapBuffers(); info.markFrameCompleted(); - initializeRects(canvas->getViewportHeight(), canvas->getViewportWidth()); - drawGraph(canvas); - drawThreshold(canvas); + initializeRects(renderer->getViewportHeight(), renderer->getViewportWidth()); + drawGraph(renderer); + drawThreshold(renderer); } } @@ -194,27 +198,26 @@ void FrameInfoVisualizer::nextBarSegment(FrameInfoIndex start, FrameInfoIndex en } } -void FrameInfoVisualizer::drawGraph(OpenGLRenderer* canvas) { +void FrameInfoVisualizer::drawGraph(ContentRenderer* renderer) { SkPaint paint; for (size_t i = 0; i < Bar.size(); i++) { nextBarSegment(Bar[i].start, Bar[i].end); paint.setColor(Bar[i].color & BAR_FAST_MASK); - canvas->drawRects(mFastRects.get(), mNumFastRects * 4, &paint); + renderer->drawRects(mFastRects.get(), mNumFastRects * 4, &paint); paint.setColor(Bar[i].color & BAR_JANKY_MASK); - canvas->drawRects(mJankyRects.get(), mNumJankyRects * 4, &paint); + renderer->drawRects(mJankyRects.get(), mNumJankyRects * 4, &paint); } } -void FrameInfoVisualizer::drawThreshold(OpenGLRenderer* canvas) { +void FrameInfoVisualizer::drawThreshold(ContentRenderer* renderer) { SkPaint paint; paint.setColor(THRESHOLD_COLOR); - paint.setStrokeWidth(mThresholdStroke); - - float pts[4]; - pts[0] = 0.0f; - pts[1] = pts[3] = canvas->getViewportHeight() - (FRAME_THRESHOLD * mVerticalUnit); - pts[2] = canvas->getViewportWidth(); - canvas->drawLines(pts, 4, &paint); + float yLocation = renderer->getViewportHeight() - (FRAME_THRESHOLD * mVerticalUnit); + renderer->drawRect(0.0f, + yLocation - mThresholdStroke/2, + renderer->getViewportWidth(), + yLocation + mThresholdStroke/2, + &paint); } bool FrameInfoVisualizer::consumeProperties() { diff --git a/libs/hwui/FrameInfoVisualizer.h b/libs/hwui/FrameInfoVisualizer.h index cf877c4d8827..83adf1985c72 100644 --- a/libs/hwui/FrameInfoVisualizer.h +++ b/libs/hwui/FrameInfoVisualizer.h @@ -28,7 +28,13 @@ namespace android { namespace uirenderer { +#if HWUI_NEW_OPS +class BakedOpRenderer; +typedef BakedOpRenderer ContentRenderer; +#else class OpenGLRenderer; +typedef OpenGLRenderer ContentRenderer; +#endif // TODO: This is a bit awkward as it needs to match the thing in CanvasContext // A better abstraction here would be nice but iterators are painful @@ -46,7 +52,7 @@ public: void setDensity(float density); void unionDirty(SkRect* dirty); - void draw(OpenGLRenderer* canvas); + void draw(ContentRenderer* renderer); void dumpData(int fd); @@ -56,8 +62,8 @@ private: void initializeRects(const int baseline, const int width); void nextBarSegment(FrameInfoIndex start, FrameInfoIndex end); - void drawGraph(OpenGLRenderer* canvas); - void drawThreshold(OpenGLRenderer* canvas); + void drawGraph(ContentRenderer* renderer); + void drawThreshold(ContentRenderer* renderer); inline float durationMS(size_t index, FrameInfoIndex start, FrameInfoIndex end) { float duration = mFrameSource[index].duration(start, end) * 0.000001f; diff --git a/libs/hwui/renderthread/CanvasContext.cpp b/libs/hwui/renderthread/CanvasContext.cpp index 249d83f50627..a496b4966456 100644 --- a/libs/hwui/renderthread/CanvasContext.cpp +++ b/libs/hwui/renderthread/CanvasContext.cpp @@ -348,12 +348,26 @@ void CanvasContext::draw() { FrameBuilder frameBuilder(mLayerUpdateQueue, dirty, frame.width(), frame.height(), mRenderNodes, mLightGeometry, mContentDrawBounds, &Caches::getInstance()); mLayerUpdateQueue.clear(); - BakedOpRenderer renderer(Caches::getInstance(), mRenderThread.renderState(), + auto&& caches = Caches::getInstance(); + BakedOpRenderer renderer(caches, mRenderThread.renderState(), mOpaque, mLightInfo); - // TODO: profiler().draw(mCanvas); frameBuilder.replayBakedOps(renderer); + profiler().draw(&renderer); bool drew = renderer.didDraw(); + // post frame cleanup + caches.clearGarbage(); + caches.pathCache.trim(); + caches.tessellationCache.trim(); + +#if DEBUG_MEMORY_USAGE + mCaches.dumpMemoryUsage(); +#else + if (CC_UNLIKELY(Properties::debugLevel & kDebugMemory)) { + caches.dumpMemoryUsage(); + } +#endif + #else mCanvas->prepareDirty(frame.width(), frame.height(), dirty.fLeft, dirty.fTop, dirty.fRight, dirty.fBottom, mOpaque); -- cgit v1.2.3-59-g8ed1b