Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Binding TypefaceFontProvider #293

Open
wants to merge 5 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 13 additions & 0 deletions src/skia/Paragraph.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
#include "modules/skparagraph/include/Paragraph.h"
#include "modules/skparagraph/include/ParagraphBuilder.h"
#include "modules/skparagraph/include/ParagraphStyle.h"
#include "modules/skparagraph/include/TypefaceFontProvider.h"
#include <pybind11/stl.h>

using namespace skia::textlayout;
Expand All @@ -15,6 +16,7 @@ py::class_<ParagraphBuilder> paragraph_builder(m, "textlayout_ParagraphBuilder")
py::class_<ParagraphStyle> paragraph_style(m, "textlayout_ParagraphStyle");
py::class_<TextStyle> text_style(m, "textlayout_TextStyle");
py::class_<Paragraph> paragraph(m, "textlayout_Paragraph");
py::class_<TypefaceFontProvider, sk_sp<TypefaceFontProvider>, SkFontMgr> typeface_font_provider(m, "textlayout_TypefaceFontProvider");

py::enum_<TextAlign>(m, "textlayout_TextAlign", R"docstring(
)docstring")
Expand Down Expand Up @@ -202,12 +204,23 @@ paragraph
py::arg("canvas"), py::arg("x"), py::arg("y"))
;

typeface_font_provider
.def(py::init())
.def("registerTypeface",
py::overload_cast<sk_sp<SkTypeface>>(&TypefaceFontProvider::registerTypeface),
py::arg("typeface"))
.def("registerTypeface",
py::overload_cast<sk_sp<SkTypeface>, const SkString&>(&TypefaceFontProvider::registerTypeface),
py::arg("typeface"), py::arg("alias"))
;

py::object SimpleNamespace = py::module_::import("types").attr("SimpleNamespace");
m.attr("textlayout") = SimpleNamespace();
m.attr("textlayout").attr("FontCollection") = m.attr("textlayout_FontCollection");
m.attr("textlayout").attr("ParagraphBuilder") = m.attr("textlayout_ParagraphBuilder");
m.attr("textlayout").attr("ParagraphStyle") = m.attr("textlayout_ParagraphStyle");
m.attr("textlayout").attr("Paragraph") = m.attr("textlayout_Paragraph");
m.attr("textlayout").attr("TypefaceFontProvider") = m.attr("textlayout_TypefaceFontProvider");
m.attr("textlayout").attr("TextStyle") = m.attr("textlayout_TextStyle");
m.attr("textlayout").attr("TextAlign") = m.attr("textlayout_TextAlign");
m.attr("textlayout").attr("TextDecoration") = m.attr("textlayout_TextDecoration");
Expand Down
4 changes: 4 additions & 0 deletions src/skia/TextBlob.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,10 @@ py::class_<SkTextBlob::Iter::Run>(iter, "Run")

iter
.def(py::init<const SkTextBlob&>())
.def("__iter__",
[] (SkTextBlob::Iter& it) {
return it;
})
.def("__next__",
[] (SkTextBlob::Iter& it) {
SkTextBlob::Iter::Run run;
Expand Down
47 changes: 47 additions & 0 deletions tests/test_paragraph.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,26 @@
import skia
import pytest


@pytest.fixture(scope='module')
def non_text_typeface():
import sys
import os
if sys.platform.startswith("linux"):
if os.path.exists("/usr/share/fonts/truetype/noto/NotoColorEmoji.ttf"): # Ubuntu CI
# Ubuntu is weird - the font is on disk but not accessible to fontconfig
# - Possibly https://bugs.launchpad.net/bugs/2054924
return skia.Typeface.MakeFromFile("/usr/share/fonts/truetype/noto/NotoColorEmoji.ttf")
elif os.path.exists("/usr/share/fonts/google-noto-color-emoji-fonts/NotoColorEmoji.ttf"): # Fedora
return skia.Typeface.MakeFromFile("/usr/share/fonts/google-noto-color-emoji-fonts/NotoColorEmoji.ttf")
else:
pytest.skip("Not in Ubuntu CI")
if sys.platform.startswith("darwin"):
return skia.Typeface("Apple Color Emoji")
if sys.platform.startswith("win"):
return skia.Typeface("Segoe UI Emoji") # COLRv0


@pytest.fixture(scope='session')
def textlayout_font_collection():
return skia.textlayout.FontCollection()
Expand Down Expand Up @@ -61,3 +81,30 @@ def test_Paragraph_linebreak(paragraph_builder, textlayout_text_style, textlayou
paragraph = builder.Build()
paragraph.layout(300)
assert (paragraph.Height > 0) and (paragraph.Height > paragraph.LongestLine * 2)


@pytest.fixture(scope='session')
def typeface_font_provider():
return skia.textlayout.TypefaceFontProvider()

def test_textlayout_TypefaceFontProvider_init(typeface_font_provider):
assert isinstance(typeface_font_provider, skia.textlayout_TypefaceFontProvider)
assert typeface_font_provider.countFamilies() == 0

def test_textlayout_TypefaceFontProvider_registerTypeface0(typeface_font_provider, non_text_typeface):
typeface_any = skia.Typeface("Text")
assert typeface_font_provider.registerTypeface(typeface_any) == 1
assert typeface_font_provider.countFamilies() == 1
assert typeface_font_provider.registerTypeface(non_text_typeface) == 1
assert typeface_font_provider.countFamilies() == 2
# TypefaceFontProvider can detect duplicates.
typeface_any_two = skia.Typeface("Text")
assert typeface_font_provider.registerTypeface(typeface_any_two) == 1
assert typeface_font_provider.countFamilies() == 2

def test_textlayout_TypefaceFontProvider_registerTypeface1(typeface_font_provider, non_text_typeface):
typeface_any = skia.Typeface("Text")
assert typeface_font_provider.registerTypeface(typeface_any, "Not Text") == 1
assert typeface_font_provider.countFamilies() == 3
assert typeface_font_provider.registerTypeface(non_text_typeface, "Not Emoji") == 1
assert typeface_font_provider.countFamilies() == 4
Loading