vg-renderer icon indicating copy to clipboard operation
vg-renderer copied to clipboard

Make Fontstash Optional

Open SnapperTT opened this issue 10 months ago • 7 comments

I use sdl-stb-font (https://github.com/SnapperTT/sdl-stb-font) for font rendering which conflicts with FontStash, so I've put everything FontStash related behind an #include guard. By default nothing is changed but a user may disable Fontstash by setting #define VG_USE_FONTSTASH 0 before including vg.h.

SnapperTT avatar Jan 17 '25 10:01 SnapperTT

Thanks for the PR. I won't merge this at the moment because I don't really see a benefit removing text rendering from the library. I'd consider it if an alternative was submitted.

I'll leave it open in case someone else is interested in your changes and/or uses the library you are using.

jdryg avatar Jan 18 '25 06:01 jdryg

I see. Removing fontstash removes a dependency on both fontstash and stb-truetype which can conflict with other libs.

As for an alternative I don't think its appropriate to make a bunch of #if switches for my library as this may also encourage others to make a massive pile of spaghetti for every text rendering lib out there.

What I think I should do is add a "callback" command to the command buffer to let custom rendering be interleaved with vg-renderer commands. This will allow people to render with any library providing that they write an appropriate callback

SnapperTT avatar Jan 20 '25 04:01 SnapperTT

I have made a draft implementation of a callback mechanism.

A callback function can be registered before initializing a context (this is just a global function pointer for now).

vg::gCustomCallback = &vgCustomCallback;
m_vgCtx = vg::createContext( bgfxh::internal_getDefaultAllocator(), &cfg);
// This is just printf() with extra steps
static void vgCustomCallback(vg::Context* ctx, const uint32_t a, const uint32_t b) {
  Logger::ldbg("vgCustomCallback {} {} {}", fmt::ptr(ctx), a, b);
  }

The callback function can be invoked like any drawing call:

vg::beginPath(m_vgCtx);
vg::roundedRect(m_vgCtx, 200, 200, 400, 200, 16);
vg::fillPath(m_vgCtx, vg::color4ub(28, 130, 234, 232), vg::FillFlags::ConvexAA);
vg::customCallback(m_vgCtx, 123, 456);

An user can use this for drawing text with a custom library or doing any other things in the draw loop (such as runtime profiling).

Is this relevant to your interests?

SnapperTT avatar Jan 20 '25 13:01 SnapperTT

Is this relevant to your interests?

Not right now but it might be useful to somebody else if it's implemented properly.

Does FontStash actually conflicts with your code or you just want to remove it because it's redundant?

What exactly is the custom callback command supposed to do? Is it suppose to generate new geometry (requires VB/IB handles to insert the geometry)? Would it require a special shader for this new geometry?

Does your text rendering library end up producing a bunch of triangles which use a single texture (atlas) for all the glyphs? If yes, have you tried using vg::indexedTriList() to render them?

jdryg avatar Jan 20 '25 15:01 jdryg

These are good questions, thanks

Does FontStash actually conflicts with your code or you just want to remove it because it's redundant?

Yes it conflicts. Both FS and sdl-stb-font use stb-truetype, and there some other things that break too but I don't remember what.

What exactly is the custom callback command supposed to do? Is it suppose to generate new geometry (requires VB/IB handles to insert the geometry)? Would it require a special shader for this new geometry?

A custom callback can do anything from logging or profiling to submitting own geometry with a custom shader.

Does your text rendering library end up producing a bunch of triangles which use a single texture (atlas) for all the glyphs? If yes, have you tried using vg::indexedTriList() to render them?

My text library can render text from multiple atlases as well as draw formatting stuff (strikethrough, underline). It can also cache whole strings as an image and also supports different typefaces (bold, italic, etc) as well as utf-8 strings. Currently it just uses a textured-quad shader with a colour set by a uniform but I intend to write a SDF shader in the future and I also intend to incorporate inline sprite sheet images (think "Gold 🪙: 2000" or "Wood 🪵: 1300").

It has a bgfx backend so invoking it in the callback makes it "just work". I have written a test that renders alpha blended quads with sdl-stb-font text on-top of each other

To answer your question directly, I haven't tried vg::indexedTriList but I also am in no hurry to write another backend to sdl-stb-font.

I guess this can be broken into two parts: one is to make FS optional, and the second is custom callback capability.

SnapperTT avatar Jan 21 '25 13:01 SnapperTT

The callback draw command mechanism sounds cool but I don't currently have the time to work on a proper API.

Since you have a use case, I'd suggest working on it on your own fork, iron out all the details with as many examples of callbacks you might come up with and them submit a PR for review. Including some kind of demo code would also be great once you figure out everything (ideally as a fork of https://github.com/jdryg/bgfx/blob/xx-vg-renderer/examples/xx-vg-renderer/vg-renderer.cpp).

Please keep in mind that any changes to the library should support both immediate (vg::beginPath(), vg::rect(), etc) rendering and command lists (vg::clBeginPath(), vg::clRect(), etc.) with and without tesselation caching.

Also you should keep in mind that if the callbacks change the bound vertex and index buffers, vg (or the callback) should rebind the old buffers.

I'm treating the master branch of this repository as stable so any big API changes should be compatible with the current API before being merged.

Finally, I'd like to point out that I'm not using this version of the library in my own code. This means that I won't be able to immediately test any major changes made to it so I won't be able to provide support to future users if something breaks due to API changes.

jdryg avatar Jan 21 '25 15:01 jdryg

Okay cheers mate. I think this the way forward. I'll keep progressing with my fork and battle test it with my application first to see what issues crop up.

SnapperTT avatar Feb 04 '25 07:02 SnapperTT