1/* 2 * Copyright 2014 Google Inc. 3 * 4 * Use of this source code is governed by a BSD-style license that can be 5 * found in the LICENSE file. 6 */ 7 8#include "Test.h" 9 10#include "SkRecord.h" 11#include "SkRecorder.h" 12#include "SkRecords.h" 13 14#include "SkEmptyShader.h" 15 16#define COUNT(T) + 1 17static const int kRecordTypes = SK_RECORD_TYPES(COUNT); 18#undef COUNT 19 20// Tallies the types of commands it sees into a histogram. 21class Tally { 22public: 23 Tally() { sk_bzero(&fHistogram, sizeof(fHistogram)); } 24 25 template <typename T> 26 void operator()(const T&) { ++fHistogram[T::kType]; } 27 28 template <typename T> 29 int count() const { return fHistogram[T::kType]; } 30 31 void apply(const SkRecord& record) { 32 for (unsigned i = 0; i < record.count(); i++) { 33 record.visit<void>(i, *this); 34 } 35 } 36 37private: 38 int fHistogram[kRecordTypes]; 39}; 40 41DEF_TEST(Recorder, r) { 42 SkRecord record; 43 SkRecorder recorder(&record, 1920, 1080); 44 45 recorder.drawRect(SkRect::MakeWH(10, 10), SkPaint()); 46 47 Tally tally; 48 tally.apply(record); 49 REPORTER_ASSERT(r, 1 == tally.count<SkRecords::DrawRect>()); 50} 51 52// Regression test for leaking refs held by optional arguments. 53DEF_TEST(Recorder_RefLeaking, r) { 54 // We use SaveLayer to test: 55 // - its SkRect argument is optional and SkRect is POD. Just testing that that works. 56 // - its SkPaint argument is optional and SkPaint is not POD. The bug was here. 57 58 SkRect bounds = SkRect::MakeWH(320, 240); 59 SkPaint paint; 60 paint.setShader(SkNEW(SkEmptyShader))->unref(); 61 62 REPORTER_ASSERT(r, paint.getShader()->unique()); 63 { 64 SkRecord record; 65 SkRecorder recorder(&record, 1920, 1080); 66 recorder.saveLayer(&bounds, &paint); 67 REPORTER_ASSERT(r, !paint.getShader()->unique()); 68 } 69 REPORTER_ASSERT(r, paint.getShader()->unique()); 70} 71