Skip to content

Canvas draw text on path#329

Merged
HinTak merged 9 commits intoskia-python:mainfrom
HinTak:canvas_draw_text_on_path
Jun 4, 2025
Merged

Canvas draw text on path#329
HinTak merged 9 commits intoskia-python:mainfrom
HinTak:canvas_draw_text_on_path

Conversation

@HinTak
Copy link
Collaborator

@HinTak HinTak commented May 29, 2025

Upstream removed it around m70, but SkiaSharp decided to add their own implementation back. Found this out asking copilot to port the sdl2 example code to gtk4 . It volunteered to give me more interesting demo on skia drawing onto opengl, and somehow it assumes that skia-python has the same api as skia m6X, or skiasharp.

Fixes #326

HinTak added 7 commits May 29, 2025 16:51
They were originally at:

include/utils/SkTextOnPath.h
src/utils/SkTextOnPath.cpp

From 0fdc53f9ffc6c8a25d551fb49de6f77f2a2fb5e6 Mon Sep 17 00:00:00 2001
From: Mike Reed <[email protected]>
Date: Mon, 27 Aug 2018 13:00:37 -0400
Subject: [PATCH] textonpath util

Bug: skia:7554
Change-Id: Ifff3030f9d7be24146b5230bbf0e47f73000adfd
Reviewed-on: https://skia-review.googlesource.com/141460
Commit-Queue: Mike Reed <[email protected]>
Reviewed-by: Mike Reed <[email protected]>
From 1eb9af90291ea09dd1fa16af9fbba71c666c95ad Mon Sep 17 00:00:00 2001
From: Mike Reed <[email protected]>
Date: Mon, 1 Oct 2018 12:16:59 -0400
Subject: [PATCH] delete textonpath code -- not used anywhere

Bug: skia:
Change-Id: Ib645f7c140f87123429170a0bf6f7ed86ce53b3f
Reviewed-on: https://skia-review.googlesource.com/158224
Reviewed-by: Florin Malita <[email protected]>
Commit-Queue: Mike Reed <[email protected]>
- SkPaint no longer containing anything to do with fonts; passing extra SkFont
  argument in. (and all those "paint.getTextAlign()" related code is gone)
- SkTextToPathIter is also gone around ~m76 - it used the old SkPaint's
  font to work out glyphs and advances anyway, so this part is new, using
  SkFont.textToGlyphs() and SkFont.getWidths().
- SkFont.getPath() has different calling conventions from
  SkTextToPathIter.next()
Adjust prototype

The main part of fixing skia-python#326
@HinTak
Copy link
Collaborator Author

HinTak commented May 29, 2025

@kyamagu this is mainly upstream code adjusted to work with current - the main adjustment is at 0c8b6b4 . I have very little doubt that the original code works, so it is probably a mistake of mine - the testing code is at https://github.com/HinTak/skia-python-examples/blob/main/draw_text_on_path.py . I am finding that once in a while it does not draw anything, or rather, a very thin line at the very beginning of where the text should be. It happens once in a while, have not seem it in the equivalent c code; but since almost all of this is on the c side, it is likely because i don't understand how skia does delayed drawings. The tmp.setInVolatile is original; I wonder if I should do a flush before getting back to python, or something.

Fixes building on window 2022 with MSVC++ 14
@HinTak HinTak mentioned this pull request May 29, 2025
@kyamagu
Copy link
Collaborator

kyamagu commented May 30, 2025

Right, this spurious bug seems to be about the timing of the actual rendering. Is this happening in a specific platform/runtime?

@HinTak
Copy link
Collaborator Author

HinTak commented May 30, 2025

It is not limited to cpu canvas (dumping to png) - happens to gpu canvas too. draw_text_on_path does it on a cpu raster. The GTK4_superadvancedGL sample does it on a GPU canvas.

Other path drawing are not affected, so the problem seems to be somewhat internal to this c++ code. Maybe I should look at why upstream add tmp.setInVolatile .

@HinTak
Copy link
Collaborator Author

HinTak commented May 30, 2025

It is on fedora 42, my desktop.

@kyamagu
Copy link
Collaborator

kyamagu commented May 30, 2025

If it is happening in the Python environment, I would suspect that a certain C++ struct that should persist on rendering disappears when the context is turned back to Python. The visitor object is suspicious in this respect.

@HinTak
Copy link
Collaborator Author

HinTak commented May 30, 2025

@kyamagu thanks for the suggestion. The visitor construct is original, but it is interesting that copilot did not go that route. The copilot generated code is in my skia-c-examples repo - it is more like it has that part inlined. The current skia-python code is rather original google code revived / adapted with reference to the AI code, mostly because (1) there are too many mysterious / unexplained decisions in the AI code (2) copyright-wise I am not sure where it comes from. So I think there are two ways of going about it: actually put the Google code in a small harness and run it to see if graphics disappears - and valgrind etc could do that. (2) for the time being, I can try putting a canvas.flush() just before returning to python. That should work if it is just python<->c interaction. I am not too happy doing that as it just covers up the problem - there are a lot of caching involved in skia, fonts/glyphs, and paths, and one should let skia does it.

Hopefully one of them should work

@HinTak
Copy link
Collaborator Author

HinTak commented May 30, 2025

I like the look of the Google code much better - as I said, the AI code looks like it has things inlined, so it is a lot longer with multiple sections which look very similar. (And one does not know the difference between those similar sections). The AI code probably comes from skiasharp somehow.

@HinTak
Copy link
Collaborator Author

HinTak commented May 30, 2025

@kyamagu thanks for the time - it is a simple stupid mistake: an uninitialized variable which is zero in c but gets a random value when inside skia-python. Both valgrind & the compiler (with -Wall -O3 spotted it when taken outside skia-python.

@HinTak HinTak merged commit 9d42121 into skia-python:main Jun 4, 2025
18 checks passed
@HinTak HinTak deleted the canvas_draw_text_on_path branch June 4, 2025 02:16
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Adding SKCanvas.DrawTextOnPath back.

2 participants