1fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck/*
2fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * Copyright (C) 2014 The Android Open Source Project
3fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck *
4fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * Licensed under the Apache License, Version 2.0 (the "License");
5fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * you may not use this file except in compliance with the License.
6fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * You may obtain a copy of the License at
7fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck *
8fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck *      http://www.apache.org/licenses/LICENSE-2.0
9fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck *
10fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * Unless required by applicable law or agreed to in writing, software
11fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * distributed under the License is distributed on an "AS IS" BASIS,
12fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * See the License for the specific language governing permissions and
14fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * limitations under the License.
15fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck */
164c9e59d03c2bca38001225b79d01740b8999adfbJohn Reck#include "FrameInfoVisualizer.h"
17fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
181dfa0704964c17e45775b9e01f1fa0b1a10774f7Chris Craik#include "BakedOpRenderer.h"
19de97307362c26b64e2376b21ccde8414088cdc8bMatt Sarett#include "IProfileRenderer.h"
2054fa17f667c285a5c9225e238c8132dfe830ef36Chris Craik#include "utils/Color.h"
21fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
224c9e59d03c2bca38001225b79d01740b8999adfbJohn Reck#include <cutils/compiler.h>
23bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck#include <array>
24fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
251bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck#define RETURN_IF_PROFILING_DISABLED() \
261bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    if (CC_LIKELY(mType == ProfileType::None)) return
271bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck#define RETURN_IF_DISABLED() \
281bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    if (CC_LIKELY(mType == ProfileType::None && !mShowDirtyRegions)) return
29fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
30fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define PROFILE_DRAW_WIDTH 3
31fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define PROFILE_DRAW_THRESHOLD_STROKE_WIDTH 2
32fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define PROFILE_DRAW_DP_PER_MS 7
33fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
3454fa17f667c285a5c9225e238c8132dfe830ef36Chris Craiknamespace android {
3554fa17f667c285a5c9225e238c8132dfe830ef36Chris Craiknamespace uirenderer {
3654fa17f667c285a5c9225e238c8132dfe830ef36Chris Craik
37fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck// Must be NUM_ELEMENTS in size
3854fa17f667c285a5c9225e238c8132dfe830ef36Chris Craikstatic const SkColor THRESHOLD_COLOR = Color::Green_500;
3954fa17f667c285a5c9225e238c8132dfe830ef36Chris Craikstatic const SkColor BAR_FAST_MASK = 0x8FFFFFFF;
4054fa17f667c285a5c9225e238c8132dfe830ef36Chris Craikstatic const SkColor BAR_JANKY_MASK = 0xDFFFFFFF;
41fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
42fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck// We could get this from TimeLord and use the actual frame interval, but
43fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck// this is good enough
44fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define FRAME_THRESHOLD 16
4541300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck#define FRAME_THRESHOLD_NS 16000000
46fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
47bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reckstruct BarSegment {
48bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck    FrameInfoIndex start;
49bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck    FrameInfoIndex end;
50bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck    SkColor color;
51bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck};
52bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck
531bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reckstatic const std::array<BarSegment, 7> Bar{{
541bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck        {FrameInfoIndex::IntendedVsync, FrameInfoIndex::HandleInputStart, Color::Teal_700},
551bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck        {FrameInfoIndex::HandleInputStart, FrameInfoIndex::PerformTraversalsStart,
561bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck         Color::Green_700},
571bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck        {FrameInfoIndex::PerformTraversalsStart, FrameInfoIndex::DrawStart, Color::LightGreen_700},
581bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck        {FrameInfoIndex::DrawStart, FrameInfoIndex::SyncStart, Color::Blue_500},
591bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck        {FrameInfoIndex::SyncStart, FrameInfoIndex::IssueDrawCommandsStart, Color::LightBlue_300},
601bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck        {FrameInfoIndex::IssueDrawCommandsStart, FrameInfoIndex::SwapBuffers, Color::Red_500},
611bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck        {FrameInfoIndex::SwapBuffers, FrameInfoIndex::FrameCompleted, Color::Orange_500},
62bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck}};
63bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck
64fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckstatic int dpToPx(int dp, float density) {
651bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    return (int)(dp * density + 0.5f);
66fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
67fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
681bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John ReckFrameInfoVisualizer::FrameInfoVisualizer(FrameInfoSource& source) : mFrameSource(source) {
69fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    setDensity(1);
70fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
71fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
724c9e59d03c2bca38001225b79d01740b8999adfbJohn ReckFrameInfoVisualizer::~FrameInfoVisualizer() {
73fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    destroyData();
74fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
75fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
764c9e59d03c2bca38001225b79d01740b8999adfbJohn Reckvoid FrameInfoVisualizer::setDensity(float density) {
77fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    if (CC_UNLIKELY(mDensity != density)) {
78fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck        mDensity = density;
79fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck        mVerticalUnit = dpToPx(PROFILE_DRAW_DP_PER_MS, density);
80fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck        mThresholdStroke = dpToPx(PROFILE_DRAW_THRESHOLD_STROKE_WIDTH, density);
81fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    }
82fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
83fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
844c9e59d03c2bca38001225b79d01740b8999adfbJohn Reckvoid FrameInfoVisualizer::unionDirty(SkRect* dirty) {
85fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    RETURN_IF_DISABLED();
86fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    // Not worth worrying about minimizing the dirty region for debugging, so just
87fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    // dirty the entire viewport.
88fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    if (dirty) {
8923d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck        mDirtyRegion = *dirty;
90fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck        dirty->setEmpty();
91fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    }
92fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
93fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
94de97307362c26b64e2376b21ccde8414088cdc8bMatt Sarettvoid FrameInfoVisualizer::draw(IProfileRenderer& renderer) {
9523d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck    RETURN_IF_DISABLED();
9623d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck
9723d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck    if (mShowDirtyRegions) {
9823d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck        mFlashToggle = !mFlashToggle;
9923d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck        if (mFlashToggle) {
10023d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck            SkPaint paint;
10123d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck            paint.setColor(0x7fff0000);
1021bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            renderer.drawRect(mDirtyRegion.fLeft, mDirtyRegion.fTop, mDirtyRegion.fRight,
1031bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                              mDirtyRegion.fBottom, paint);
10423d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck        }
105fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    }
106fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
1072507c34d91bb0d722b6012e85cb47387b2aa6873Chris Craik    if (mType == ProfileType::Bars) {
10841300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        // Patch up the current frame to pretend we ended here. CanvasContext
10941300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        // will overwrite these values with the real ones after we return.
11041300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        // This is a bit nicer looking than the vague green bar, as we have
11141300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        // valid data for almost all the stages and a very good idea of what
11241300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        // the issue stage will look like, too
11341300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        FrameInfo& info = mFrameSource.back();
11441300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        info.markSwapBuffers();
11541300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        info.markFrameCompleted();
11641300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck
117de97307362c26b64e2376b21ccde8414088cdc8bMatt Sarett        initializeRects(renderer.getViewportHeight(), renderer.getViewportWidth());
1181dfa0704964c17e45775b9e01f1fa0b1a10774f7Chris Craik        drawGraph(renderer);
1191dfa0704964c17e45775b9e01f1fa0b1a10774f7Chris Craik        drawThreshold(renderer);
12023d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck    }
121fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
122fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
1234c9e59d03c2bca38001225b79d01740b8999adfbJohn Reckvoid FrameInfoVisualizer::createData() {
12441300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    if (mFastRects.get()) return;
125fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
12641300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    mFastRects.reset(new float[mFrameSource.capacity() * 4]);
12741300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    mJankyRects.reset(new float[mFrameSource.capacity() * 4]);
128fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
129fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
1304c9e59d03c2bca38001225b79d01740b8999adfbJohn Reckvoid FrameInfoVisualizer::destroyData() {
13141300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    mFastRects.reset(nullptr);
13241300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    mJankyRects.reset(nullptr);
133fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
134fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
13541300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reckvoid FrameInfoVisualizer::initializeRects(const int baseline, const int width) {
13641300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    // Target the 95% mark for the current frame
13741300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    float right = width * .95;
13841300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    float baseLineWidth = right / mFrameSource.capacity();
13941300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    mNumFastRects = 0;
14041300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    mNumJankyRects = 0;
14141300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    int fast_i = 0, janky_i = 0;
142bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck    // Set the bottom of all the shapes to the baseline
14341300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    for (int fi = mFrameSource.size() - 1; fi >= 0; fi--) {
14441300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        if (mFrameSource[fi][FrameInfoIndex::Flags] & FrameInfoFlags::SkippedFrame) {
14541300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            continue;
14641300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        }
14741300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        float lineWidth = baseLineWidth;
14841300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        float* rect;
14941300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        int ri;
150bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck        // Rects are LTRB
15141300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        if (mFrameSource[fi].totalDuration() <= FRAME_THRESHOLD_NS) {
15241300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            rect = mFastRects.get();
15341300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            ri = fast_i;
15441300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            fast_i += 4;
15541300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            mNumFastRects++;
15641300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        } else {
15741300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            rect = mJankyRects.get();
15841300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            ri = janky_i;
15941300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            janky_i += 4;
16041300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            mNumJankyRects++;
16141300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            lineWidth *= 2;
16241300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        }
16341300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck
16441300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        rect[ri + 0] = right - lineWidth;
16541300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        rect[ri + 1] = baseline;
16641300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        rect[ri + 2] = right;
16741300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        rect[ri + 3] = baseline;
16841300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        right -= lineWidth;
169bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck    }
170fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
171fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
172bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reckvoid FrameInfoVisualizer::nextBarSegment(FrameInfoIndex start, FrameInfoIndex end) {
17341300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    int fast_i = (mNumFastRects - 1) * 4;
1741bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    int janky_i = (mNumJankyRects - 1) * 4;
1751bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    ;
17641300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck    for (size_t fi = 0; fi < mFrameSource.size(); fi++) {
1771b54fb27ac48495ed0b33868fda5776fb49fe0f3Chris Craik        if (mFrameSource[fi][FrameInfoIndex::Flags] & FrameInfoFlags::SkippedFrame) {
178bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck            continue;
179bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck        }
180bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck
18141300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        float* rect;
18241300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        int ri;
18341300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        // Rects are LTRB
18441300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        if (mFrameSource[fi].totalDuration() <= FRAME_THRESHOLD_NS) {
18541300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            rect = mFastRects.get();
18641300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            ri = fast_i;
18741300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            fast_i -= 4;
18841300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        } else {
18941300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            rect = mJankyRects.get();
19041300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            ri = janky_i;
19141300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck            janky_i -= 4;
19241300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        }
19341300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck
194bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck        // Set the bottom to the old top (build upwards)
19541300274cf8efde2ca95d3c767b214d1edb97f8dJohn Reck        rect[ri + 3] = rect[ri + 1];
196bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck        // Move the top up by the duration
197be3fba05e823f740f65b2679929347dc3dd282adJohn Reck        rect[ri + 1] -= mVerticalUnit * durationMS(fi, start, end);
198fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    }
199fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
200fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
201de97307362c26b64e2376b21ccde8414088cdc8bMatt Sarettvoid FrameInfoVisualizer::drawGraph(IProfileRenderer& renderer) {
202fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    SkPaint paint;
203bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck    for (size_t i = 0; i < Bar.size(); i++) {
204bf3c602284f9a344faf185c3a5e94a264ba44c4fJohn Reck        nextBarSegment(Bar[i].start, Bar[i].end);
20554fa17f667c285a5c9225e238c8132dfe830ef36Chris Craik        paint.setColor(Bar[i].color & BAR_FAST_MASK);
206de97307362c26b64e2376b21ccde8414088cdc8bMatt Sarett        renderer.drawRects(mFastRects.get(), mNumFastRects * 4, paint);
20754fa17f667c285a5c9225e238c8132dfe830ef36Chris Craik        paint.setColor(Bar[i].color & BAR_JANKY_MASK);
208de97307362c26b64e2376b21ccde8414088cdc8bMatt Sarett        renderer.drawRects(mJankyRects.get(), mNumJankyRects * 4, paint);
209fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    }
210fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
211fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
212de97307362c26b64e2376b21ccde8414088cdc8bMatt Sarettvoid FrameInfoVisualizer::drawThreshold(IProfileRenderer& renderer) {
213fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    SkPaint paint;
214fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    paint.setColor(THRESHOLD_COLOR);
215de97307362c26b64e2376b21ccde8414088cdc8bMatt Sarett    float yLocation = renderer.getViewportHeight() - (FRAME_THRESHOLD * mVerticalUnit);
2161bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    renderer.drawRect(0.0f, yLocation - mThresholdStroke / 2, renderer.getViewportWidth(),
2171bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                      yLocation + mThresholdStroke / 2, paint);
218fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
219fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
2204c9e59d03c2bca38001225b79d01740b8999adfbJohn Reckbool FrameInfoVisualizer::consumeProperties() {
22123d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck    bool changed = false;
2222507c34d91bb0d722b6012e85cb47387b2aa6873Chris Craik    ProfileType newType = Properties::getProfileType();
223fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    if (newType != mType) {
224fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck        mType = newType;
2252507c34d91bb0d722b6012e85cb47387b2aa6873Chris Craik        if (mType == ProfileType::None) {
226fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck            destroyData();
227fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck        } else {
228fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck            createData();
229fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck        }
23023d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck        changed = true;
231fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    }
2322507c34d91bb0d722b6012e85cb47387b2aa6873Chris Craik
2332507c34d91bb0d722b6012e85cb47387b2aa6873Chris Craik    bool showDirty = Properties::showDirtyRegions;
23423d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck    if (showDirty != mShowDirtyRegions) {
23523d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck        mShowDirtyRegions = showDirty;
23623d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck        changed = true;
23723d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck    }
23823d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck    return changed;
239fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
240fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
2414c9e59d03c2bca38001225b79d01740b8999adfbJohn Reckvoid FrameInfoVisualizer::dumpData(int fd) {
24223d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck    RETURN_IF_PROFILING_DISABLED();
243fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
244fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    // This method logs the last N frames (where N is <= mDataSize) since the
245fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    // last call to dumpData(). In other words if there's a dumpData(), draw frame,
246fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    // dumpData(), the last dumpData() should only log 1 frame.
247fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
24847f5c3a234c5c201ef640489af3ff25b5eec6652John Reck    dprintf(fd, "\n\tDraw\tPrepare\tProcess\tExecute\n");
249fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
2504c9e59d03c2bca38001225b79d01740b8999adfbJohn Reck    for (size_t i = 0; i < mFrameSource.size(); i++) {
2511b54fb27ac48495ed0b33868fda5776fb49fe0f3Chris Craik        if (mFrameSource[i][FrameInfoIndex::IntendedVsync] <= mLastFrameLogged) {
252fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck            continue;
253fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck        }
2541b54fb27ac48495ed0b33868fda5776fb49fe0f3Chris Craik        mLastFrameLogged = mFrameSource[i][FrameInfoIndex::IntendedVsync];
25547f5c3a234c5c201ef640489af3ff25b5eec6652John Reck        dprintf(fd, "\t%3.2f\t%3.2f\t%3.2f\t%3.2f\n",
256be3fba05e823f740f65b2679929347dc3dd282adJohn Reck                durationMS(i, FrameInfoIndex::IntendedVsync, FrameInfoIndex::SyncStart),
257be3fba05e823f740f65b2679929347dc3dd282adJohn Reck                durationMS(i, FrameInfoIndex::SyncStart, FrameInfoIndex::IssueDrawCommandsStart),
258be3fba05e823f740f65b2679929347dc3dd282adJohn Reck                durationMS(i, FrameInfoIndex::IssueDrawCommandsStart, FrameInfoIndex::SwapBuffers),
259be3fba05e823f740f65b2679929347dc3dd282adJohn Reck                durationMS(i, FrameInfoIndex::SwapBuffers, FrameInfoIndex::FrameCompleted));
260fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck    }
261fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck}
262fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck
263fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} /* namespace uirenderer */
264fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} /* namespace android */
265