14a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck/*
24a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck * Copyright (C) 2015 The Android Open Source Project
34a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck *
44a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck * Licensed under the Apache License, Version 2.0 (the "License");
54a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck * you may not use this file except in compliance with the License.
64a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck * You may obtain a copy of the License at
74a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck *
84a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck *      http://www.apache.org/licenses/LICENSE-2.0
94a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck *
104a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck * Unless required by applicable law or agreed to in writing, software
114a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck * distributed under the License is distributed on an "AS IS" BASIS,
124a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
134a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck * See the License for the specific language governing permissions and
144a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck * limitations under the License.
154a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck */
164a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
170418afa362630e69bd853121770b115750ee46a4John Reck#include <benchmark/benchmark.h>
184a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
194a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck#include "DisplayList.h"
20b565df13a9e5c7b1d7d93bdfa4a793752d66d3ccChris Craik#include "RecordingCanvas.h"
218160f20b0aca8c6595d4b385d673f59b6bcd16a4Chris Craik#include "tests/common/TestUtils.h"
224a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
234a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reckusing namespace android;
244a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reckusing namespace android::uirenderer;
254a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
260418afa362630e69bd853121770b115750ee46a4John Reckvoid BM_DisplayList_alloc(benchmark::State& benchState) {
270418afa362630e69bd853121770b115750ee46a4John Reck    while (benchState.KeepRunning()) {
28003cc3dec8e2a92e51086fbcd5ee1bb236efa701Chris Craik        auto displayList = new DisplayList();
290418afa362630e69bd853121770b115750ee46a4John Reck        benchmark::DoNotOptimize(displayList);
30003cc3dec8e2a92e51086fbcd5ee1bb236efa701Chris Craik        delete displayList;
314a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    }
324a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck}
330418afa362630e69bd853121770b115750ee46a4John ReckBENCHMARK(BM_DisplayList_alloc);
344a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
350418afa362630e69bd853121770b115750ee46a4John Reckvoid BM_DisplayList_alloc_theoretical(benchmark::State& benchState) {
360418afa362630e69bd853121770b115750ee46a4John Reck    while (benchState.KeepRunning()) {
37003cc3dec8e2a92e51086fbcd5ee1bb236efa701Chris Craik        auto displayList = new char[sizeof(DisplayList)];
380418afa362630e69bd853121770b115750ee46a4John Reck        benchmark::DoNotOptimize(displayList);
39003cc3dec8e2a92e51086fbcd5ee1bb236efa701Chris Craik        delete[] displayList;
404a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    }
414a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck}
420418afa362630e69bd853121770b115750ee46a4John ReckBENCHMARK(BM_DisplayList_alloc_theoretical);
434a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
440418afa362630e69bd853121770b115750ee46a4John Reckvoid BM_DisplayListCanvas_record_empty(benchmark::State& benchState) {
4506152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    std::unique_ptr<Canvas> canvas(Canvas::create_recording_canvas(100, 100));
4606152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    delete canvas->finishRecording();
474a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
480418afa362630e69bd853121770b115750ee46a4John Reck    while (benchState.KeepRunning()) {
4906152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->resetRecording(100, 100);
5006152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        benchmark::DoNotOptimize(canvas.get());
5106152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        delete canvas->finishRecording();
524a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    }
534a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck}
540418afa362630e69bd853121770b115750ee46a4John ReckBENCHMARK(BM_DisplayListCanvas_record_empty);
554a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
560418afa362630e69bd853121770b115750ee46a4John Reckvoid BM_DisplayListCanvas_record_saverestore(benchmark::State& benchState) {
5706152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    std::unique_ptr<Canvas> canvas(Canvas::create_recording_canvas(100, 100));
5806152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    delete canvas->finishRecording();
594a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
600418afa362630e69bd853121770b115750ee46a4John Reck    while (benchState.KeepRunning()) {
6106152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->resetRecording(100, 100);
6206152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->save(SaveFlags::MatrixClip);
6306152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->save(SaveFlags::MatrixClip);
6406152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        benchmark::DoNotOptimize(canvas.get());
6506152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->restore();
6606152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->restore();
6706152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        delete canvas->finishRecording();
684a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    }
694a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck}
700418afa362630e69bd853121770b115750ee46a4John ReckBENCHMARK(BM_DisplayListCanvas_record_saverestore);
714a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
720418afa362630e69bd853121770b115750ee46a4John Reckvoid BM_DisplayListCanvas_record_translate(benchmark::State& benchState) {
7306152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    std::unique_ptr<Canvas> canvas(Canvas::create_recording_canvas(100, 100));
7406152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    delete canvas->finishRecording();
754a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
760418afa362630e69bd853121770b115750ee46a4John Reck    while (benchState.KeepRunning()) {
7706152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->resetRecording(100, 100);
7806152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->scale(10, 10);
7906152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        benchmark::DoNotOptimize(canvas.get());
8006152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        delete canvas->finishRecording();
814a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    }
824a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck}
830418afa362630e69bd853121770b115750ee46a4John ReckBENCHMARK(BM_DisplayListCanvas_record_translate);
844a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
85b36af87f8275f4b982906f88193ec27600f2746aChris Craik/**
86b36af87f8275f4b982906f88193ec27600f2746aChris Craik * Simulate a simple view drawing a background, overlapped by an image.
87b36af87f8275f4b982906f88193ec27600f2746aChris Craik *
88b36af87f8275f4b982906f88193ec27600f2746aChris Craik * Note that the recording commands are intentionally not perfectly efficient, as the
89b36af87f8275f4b982906f88193ec27600f2746aChris Craik * View system frequently produces unneeded save/restores.
90b36af87f8275f4b982906f88193ec27600f2746aChris Craik */
910418afa362630e69bd853121770b115750ee46a4John Reckvoid BM_DisplayListCanvas_record_simpleBitmapView(benchmark::State& benchState) {
9206152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    std::unique_ptr<Canvas> canvas(Canvas::create_recording_canvas(100, 100));
9306152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    delete canvas->finishRecording();
94b36af87f8275f4b982906f88193ec27600f2746aChris Craik
95b36af87f8275f4b982906f88193ec27600f2746aChris Craik    SkPaint rectPaint;
96aed7f58fb05a25ce2112829e77c0eb5dd268e8a7sergeyv    sk_sp<Bitmap> iconBitmap(TestUtils::createBitmap(80, 80));
97b36af87f8275f4b982906f88193ec27600f2746aChris Craik
980418afa362630e69bd853121770b115750ee46a4John Reck    while (benchState.KeepRunning()) {
9906152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->resetRecording(100, 100);
100b36af87f8275f4b982906f88193ec27600f2746aChris Craik        {
10106152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev            canvas->save(SaveFlags::MatrixClip);
10206152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev            canvas->drawRect(0, 0, 100, 100, rectPaint);
10306152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev            canvas->restore();
104b36af87f8275f4b982906f88193ec27600f2746aChris Craik        }
105b36af87f8275f4b982906f88193ec27600f2746aChris Craik        {
10606152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev            canvas->save(SaveFlags::MatrixClip);
10706152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev            canvas->translate(10, 10);
108aed7f58fb05a25ce2112829e77c0eb5dd268e8a7sergeyv            canvas->drawBitmap(*iconBitmap, 0, 0, nullptr);
10906152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev            canvas->restore();
110b36af87f8275f4b982906f88193ec27600f2746aChris Craik        }
11106152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        benchmark::DoNotOptimize(canvas.get());
11206152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        delete canvas->finishRecording();
113b36af87f8275f4b982906f88193ec27600f2746aChris Craik    }
114b36af87f8275f4b982906f88193ec27600f2746aChris Craik}
1150418afa362630e69bd853121770b115750ee46a4John ReckBENCHMARK(BM_DisplayListCanvas_record_simpleBitmapView);
116b36af87f8275f4b982906f88193ec27600f2746aChris Craik
1174a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reckclass NullClient: public CanvasStateClient {
1184a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    void onViewportInitialized() override {}
1194a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    void onSnapshotRestored(const Snapshot& removed, const Snapshot& restored) {}
1204a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    GLuint getTargetFbo() const override { return 0; }
1214a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck};
1224a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
1230418afa362630e69bd853121770b115750ee46a4John Reckvoid BM_CanvasState_saverestore(benchmark::State& benchState) {
1244a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    NullClient client;
1254a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    CanvasState state(client);
1264a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    state.initializeSaveStack(100, 100, 0, 0, 100, 100, Vector3());
1274a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
1280418afa362630e69bd853121770b115750ee46a4John Reck    while (benchState.KeepRunning()) {
129eecff56fed5dd5206acfbc5007b4912081b36d3bFlorin Malita        state.save(SaveFlags::MatrixClip);
130eecff56fed5dd5206acfbc5007b4912081b36d3bFlorin Malita        state.save(SaveFlags::MatrixClip);
1310418afa362630e69bd853121770b115750ee46a4John Reck        benchmark::DoNotOptimize(&state);
1324a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck        state.restore();
1334a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck        state.restore();
1344a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    }
1354a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck}
1360418afa362630e69bd853121770b115750ee46a4John ReckBENCHMARK(BM_CanvasState_saverestore);
1374a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
1380418afa362630e69bd853121770b115750ee46a4John Reckvoid BM_CanvasState_init(benchmark::State& benchState) {
1394a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    NullClient client;
1404a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    CanvasState state(client);
1414a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    state.initializeSaveStack(100, 100, 0, 0, 100, 100, Vector3());
1424a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
1430418afa362630e69bd853121770b115750ee46a4John Reck    while (benchState.KeepRunning()) {
1444a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck        state.initializeSaveStack(100, 100, 0, 0, 100, 100, Vector3());
1450418afa362630e69bd853121770b115750ee46a4John Reck        benchmark::DoNotOptimize(&state);
1464a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    }
1474a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck}
1480418afa362630e69bd853121770b115750ee46a4John ReckBENCHMARK(BM_CanvasState_init);
1494a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
1500418afa362630e69bd853121770b115750ee46a4John Reckvoid BM_CanvasState_translate(benchmark::State& benchState) {
1514a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    NullClient client;
1524a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    CanvasState state(client);
1534a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    state.initializeSaveStack(100, 100, 0, 0, 100, 100, Vector3());
1544a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck
1550418afa362630e69bd853121770b115750ee46a4John Reck    while (benchState.KeepRunning()) {
1564a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck        state.translate(5, 5, 0);
1570418afa362630e69bd853121770b115750ee46a4John Reck        benchmark::DoNotOptimize(&state);
1584a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck        state.translate(-5, -5, 0);
1594a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck    }
1604a4bc892e826849bd58606d99408f1bfbceddc3bJohn Reck}
1610418afa362630e69bd853121770b115750ee46a4John ReckBENCHMARK(BM_CanvasState_translate);
162dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck
163dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reckvoid BM_DisplayListCanvas_basicViewGroupDraw(benchmark::State& benchState) {
164dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck    sp<RenderNode> child = TestUtils::createNode(50, 50, 100, 100,
165dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck            [](auto& props, auto& canvas) {
166260ab726486317496bc12a57d599ea96dcde3284Mike Reed        canvas.drawColor(0xFFFFFFFF, SkBlendMode::kSrcOver);
167dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck    });
168dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck
16906152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    std::unique_ptr<Canvas> canvas(Canvas::create_recording_canvas(100, 100));
17006152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev    delete canvas->finishRecording();
171dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck
172dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck    while (benchState.KeepRunning()) {
17306152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->resetRecording(200, 200);
17406152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->setHighContrastText(false);
17506152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->translate(0, 0); // mScrollX, mScrollY
176dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck
177dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck        // Clip to padding
178dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck        // Can expect ~25% of views to have clip to padding with a non-null padding
17906152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        int clipRestoreCount = canvas->save(SaveFlags::MatrixClip);
1806c67f1d04591f44bccb476d715a005ad5bbdf840Mike Reed        canvas->clipRect(1, 1, 199, 199, SkClipOp::kIntersect);
181dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck
18206152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->insertReorderBarrier(true);
183dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck
184dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck        // Draw child loop
1857b4d85018722ee67bdc70c169ff61e40d5ae7924Martijn Coenen        for (int i = 0; i < benchState.range(0); i++) {
18606152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev            canvas->drawRenderNode(child.get());
187dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck        }
188dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck
18906152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->insertReorderBarrier(false);
19006152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        canvas->restoreToCount(clipRestoreCount);
191dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck
19206152cdd06da50762716cd455dcf7ab0117f25b0Stan Iliev        delete canvas->finishRecording();
193dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck    }
194dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn Reck}
195dcf3203ca6f9acf0923c19dea17d5e50067df2ceJohn ReckBENCHMARK(BM_DisplayListCanvas_basicViewGroupDraw)->Arg(1)->Arg(5)->Arg(10);
196