sdk
sdk copied to clipboard
Specification + Zig Code is not quite enough to reimplement in C
For the record, I just wrote 4500 lines of C++ code to parse SVGs using a peephole parser and a 64 byte capture window. It parses top down, rendering and tossing as it goes. It uses my graphics library's new vector drawing canvas.
With that said, I think it's fair to say I'm pretty good at reading specs and code if I managed that.
However, try as I might, I cannot produce an implementation in C++ based on your documentation and SDK code.
The Zig is I'm assuming complete and functional. The problem is most of the pertinent stuff is buried in layers of local functions and other things that make the code less clear than it maybe could be,
Ideally, your reference implementation would be in C. That would fulfill a much wider audience than Zig, which is a boutique language.
Now, I'm not sure where to go from here. I was planning on helping you integrate what SVGO does into your own converter app, but I can't do that if I don't understand the TVG binary format. (I'm not bothering with the text format because I don't need it, but understanding the binary format fully will give me a complete picture of TinyVG's capabilities)
Do you know C++? (no STL, it's very Cish code) - if so would you be willing to review some parsing code to tell me where I went wrong reading your specs?
I'm sorry but they're just not clear enough, and neither is the code (at least for a non-zig coder, like most coders)
If I can get it right, I'll give you a C or C++ reference implementation.
nevermind I think I'm past the hump. I'll post a reference implementation when it's complete.
Could you please write which parts you had problems with understanding?
I misinterpreted the sizes array that comes with the path segments. It was my fault. I missed the part about each count being +1, and was only doing that for the overall count itself, not the subcounts, leading my whole binary mess to be off. Naturally, I didn't figure that out despite banging on it until after I posted this.
I did run into another issue. You do even-odds for your overlap on your rendering. My canvas control can set even-odd vs non-zero but not for overlapping regions. It follows the behavior of SVG more or less. Unfortunately, it's based on plutovg and I don't know enough about the rasterization code to modify it to accept an even-odd overlap handling scenario.
Therefore, I've had to scrap TVG support for now. I do however, have it 80% implemented in C++ using my vector canvas, it just doesn't render a lot of things correctly due to the above.
I am currently working on a major update of my graphics library, but I may be able to squeeze in time to do a reference implementation at least of the parsing, in C.
I should add, the primary help I've found from the TVGT format is debugging my my TVG binary handling code!
I did run into another issue. You do even-odds for your overlap on your rendering. My canvas control can set even-odd vs non-zero but not for overlapping regions. It follows the behavior of SVG more or less. Unfortunately, it's based on plutovg and I don't know enough about the rasterization code to modify it to accept an even-odd overlap handling scenario.
That should be standard behaviour of SVG tho. Self-overlapping paths do cancel themselves out and a SVG renderer should be able to handle this.
If that's the case then something else is going on that I do not understand.
This renders correctly for me with my SVG code, but when I render the TVG version, the inside of the Os, and the B are filled in, like it's not chopping out inner sections. I'd show you a render, but I'm busy tearing apart my rasterizer in order to optimize it.
Your pathing in the final TVG is much different than in the SVG from what I can tell so I can't compare my debug sessions, but I'm kind of relying on the fact that I wrote both the SVG and TVG code back to back so they're pretty similar, given the different formats involved. Edit: I should be clear that I'm using the same rasterizer for both - only the parsing code is different.
So with all that said, I am at a loss.
i'll try taking a look soon. feel free to join the Discord channel for further debugging :)