skia2/gm/fontregen.cpp
Brian Salomon 9fa47cc1c6 Make class members that are static constexpr also be inline.
This is in prep for compiling with -std=c++14 and -Wno-c++17-extensions
when building with clang. Chrome has encountered problems with
third_party headers that are included both in Skia and other Chrome
sources that produce different code based on whether preprocessor macros
indicate a C++14 or C++17 compilation.

In C++17 they are already inline implicitly. When compiling with C++14
we can get linker errors unless they're explicitly inlined or defined
outside the class. With -Wno-c++17-extensions we can explicitly inline
them in the C++14 build because the warning that would be generated
about using a C++17 language extension is suppressed.

We cannot do this in public headers because we support compiling with
C++14 without suppressing the C++17 language extension warnings.

Bug: chromium:1257145
Change-Id: Iaf5f4c62a398f98dd4ca9b7dfb86f2d5cab21d66
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/457498
Reviewed-by: Ben Wagner <bungeman@google.com>
Reviewed-by: Herb Derby <herb@google.com>
Commit-Queue: Brian Salomon <bsalomon@google.com>
2021-10-11 16:22:59 +00:00

164 lines
5.1 KiB
C++

/*
* Copyright 2018 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
// GM to stress TextBlob regeneration and the GPU font cache
// It's not necessary to run this with CPU configs
//
// The point here is to draw a set of text that will fit in one Plot, and then some large
// text. After a flush we draw the first set of text again with a slightly different color,
// and then enough new large text to spill the entire atlas. What *should* happen is that
// the Plot with the first set of text will not get overwritten by the new large text.
#include "gm/gm.h"
#include "include/core/SkCanvas.h"
#include "include/core/SkColor.h"
#include "include/core/SkFont.h"
#include "include/core/SkFontMgr.h"
#include "include/core/SkFontStyle.h"
#include "include/core/SkFontTypes.h"
#include "include/core/SkPaint.h"
#include "include/core/SkRefCnt.h"
#include "include/core/SkScalar.h"
#include "include/core/SkSize.h"
#include "include/core/SkString.h"
#include "include/core/SkTextBlob.h"
#include "include/core/SkTypeface.h"
#include "include/core/SkTypes.h"
#include "include/gpu/GrContextOptions.h"
#include "include/gpu/GrDirectContext.h"
#include "include/gpu/GrRecordingContext.h"
#include "include/private/GrTypesPriv.h"
#include "include/private/SkTemplates.h"
#include "src/gpu/GrDirectContextPriv.h"
#include "tools/ToolUtils.h"
static sk_sp<SkTextBlob> make_blob(const SkString& text, const SkFont& font) {
size_t len = text.size();
SkAutoTArray<SkScalar> pos(len);
SkAutoTArray<SkGlyphID> glyphs(len);
font.textToGlyphs(text.c_str(), len, SkTextEncoding::kUTF8, glyphs.get(), len);
font.getXPos(glyphs.get(), len, pos.get());
return SkTextBlob::MakeFromPosTextH(text.c_str(), len, pos.get(), 0, font);
}
class FontRegenGM : public skiagm::GM {
void modifyGrContextOptions(GrContextOptions* options) override {
options->fGlyphCacheTextureMaximumBytes = 0;
options->fAllowMultipleGlyphCacheTextures = GrContextOptions::Enable::kNo;
}
SkString onShortName() override { return SkString("fontregen"); }
SkISize onISize() override { return {kSize, kSize}; }
void onOnceBeforeDraw() override {
this->setBGColor(SK_ColorLTGRAY);
auto tf = ToolUtils::create_portable_typeface("sans-serif", SkFontStyle::Normal());
static const SkString kTexts[] = {
SkString("abcdefghijklmnopqrstuvwxyz"),
SkString("ABCDEFGHI"),
SkString("NOPQRSTUV")
};
SkFont font;
font.setEdging(SkFont::Edging::kAntiAlias);
font.setSubpixel(false);
font.setSize(80);
font.setTypeface(tf);
fBlobs[0] = make_blob(kTexts[0], font);
font.setSize(162);
fBlobs[1] = make_blob(kTexts[1], font);
fBlobs[2] = make_blob(kTexts[2], font);
}
DrawResult onDraw(SkCanvas* canvas, SkString* errorMsg) override {
auto dContext = GrAsDirectContext(canvas->recordingContext());
if (!dContext) {
*errorMsg = "GPU-specific";
return DrawResult::kSkip;
}
SkPaint paint;
paint.setColor(SK_ColorBLACK);
canvas->drawTextBlob(fBlobs[0], 10, 80, paint);
canvas->drawTextBlob(fBlobs[1], 10, 225, paint);
dContext->flushAndSubmit();
paint.setColor(0xFF010101);
canvas->drawTextBlob(fBlobs[0], 10, 305, paint);
canvas->drawTextBlob(fBlobs[2], 10, 465, paint);
// Debugging tool for GPU.
static const bool kShowAtlas = false;
if (kShowAtlas) {
auto img = dContext->priv().testingOnly_getFontAtlasImage(kA8_GrMaskFormat);
canvas->drawImage(img, 200, 0);
}
return DrawResult::kOk;
}
private:
inline static constexpr int kSize = 512;
sk_sp<SkTextBlob> fBlobs[3];
using INHERITED = GM;
};
//////////////////////////////////////////////////////////////////////////////
DEF_GM(return new FontRegenGM())
///////////////////////////////////////////////////////////////////////////////
class BadAppleGM : public skiagm::GM {
SkString onShortName() override { return SkString("badapple"); }
SkISize onISize() override { return {kSize, kSize}; }
void onOnceBeforeDraw() override {
this->setBGColor(SK_ColorWHITE);
auto fm = SkFontMgr::RefDefault();
static const SkString kTexts[] = {
SkString("Meet"),
SkString("iPad Pro"),
};
SkFont font;
font.setEdging(SkFont::Edging::kSubpixelAntiAlias);
font.setSubpixel(true);
font.setSize(256);
fBlobs[0] = make_blob(kTexts[0], font);
fBlobs[1] = make_blob(kTexts[1], font);
}
void onDraw(SkCanvas* canvas) override {
SkPaint paint;
paint.setColor(0xFF111111);
canvas->drawTextBlob(fBlobs[0], 10, 260, paint);
canvas->drawTextBlob(fBlobs[1], 10, 500, paint);
}
private:
inline static constexpr int kSize = 512;
sk_sp<SkTextBlob> fBlobs[3];
using INHERITED = GM;
};
//////////////////////////////////////////////////////////////////////////////
DEF_GM(return new BadAppleGM())