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

CPU-Side, Alternative Equivalent? #8

Open
KTRosenberg opened this issue May 1, 2023 · 4 comments
Open

CPU-Side, Alternative Equivalent? #8

KTRosenberg opened this issue May 1, 2023 · 4 comments

Comments

@KTRosenberg
Copy link

This is more of a discussion than a suggestion for the library, but in general, I love how this library has variable-width strokes and colors, which are great for working with a stylus.
However, my particular use case really needs a CPU-side solution, and in C / C++ no less.
Somehow I have been unable to find a library that supports the above and I'm wondering if you could offer suggestions for where to find something like that, or references for how to build it or adapt it from existing solutions. In short, it's strange, but variable-width and color per-vertex polycurves seem very rare.

@rreusser
Copy link
Owner

rreusser commented May 2, 2023

Hmm, I wonder if may Matt DesLauriers' libraries like polyline-normals (which depends on polyline-miter-util)or extruded-polyline would be of use. They're not C/C++, but some of the internals like the miter function would be pretty easy to translate.

Ideally you'd be able to find a higher level library which would save you some of this trouble, but if you have pretty particular needs, then sooner or later you probably need to break things down into triangles, at which point this approach of computing miters and triangulating lines is pretty general.

Glad to offer further advice, but that's just a few initial thoughts.

@KTRosenberg
Copy link
Author

Hmm, I wonder if may Matt DesLauriers' libraries like polyline-normals (which depends on polyline-miter-util)or extruded-polyline would be of use. They're not C/C++, but some of the internals like the miter function would be pretty easy to translate.

Ideally you'd be able to find a higher level library which would save you some of this trouble, but if you have pretty particular needs, then sooner or later you probably need to break things down into triangles, at which point this approach of computing miters and triangulating lines is pretty general.

Glad to offer further advice, but that's just a few initial thoughts.

I was also thinking of hacking something like nanovg to see if just applying different widths per-vertex, but the problem I anticipate is that the varying widths might start creating broken triangles. I could be wrong about that, however.
One of the other issues is that because the input points (user stylus input) tend to be close-together, that might also lead to floating-point precision errors.

In any case, I’ll take a look at the libraries you linked too. Thanks!

@rreusser
Copy link
Owner

rreusser commented May 3, 2023

Yes, if line width varies significantly and/or is large, then things can go slightly wrong. Or at least the varying width won't look smooth. I don't have great advice there, though I suspect there's probably pretty good precedent out there on accurate nontrivial line rendering.

And if points are close together, it may benefit from line simplification before drawing lines. For example, this line simplification module is simple, very fast, and should be easy to translate to C/C++: https://mourner.github.io/simplify-js/

@KTRosenberg
Copy link
Author

I haven't found such a precedent, but it probably exists, yes. Simplifying the lines does make sense if I can get the parameters right. My system has an infinite zoom, but that's probably part of the issue. A greater zoom means that points in screen space can get extremely close together in world space. I could dynamically set the tolerance of e.g. RDP, or maybe there is a way to force points to be in some convenient scale behind the scenes while drawing. A "dumb" way of doing this might be just to multiply by a constant like 1024 and then divide after I've done the one-time computations. This might introduce error in other ways though. I'd also need to account for the fact that the camera can zoom while the curve is being drawn.
Nanovg and others apply some dynamic alpha blending for curves that are below a width in size.

By the way, in the extruded-polyline library you linked, I noticed that the width is computed as some kind of average between points (if I understood it correctly), so that's interesting.

Overall, it's too bad regl lines doesn't have a simpler form that might be easier to port. If it's doable on the GPU, it's doable on the CPU. There's just a lot of dependencies here.

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

No branches or pull requests

2 participants