Join GitHub today
GitHub is home to over 40 million developers working together to host and review code, manage projects, and build software together.
Sign upFeature Suggestion: Add perspective size attenuation option to LineMaterial #16912
Conversation
This comment has been minimized.
This comment has been minimized.
Can you please see #11349 (comment) and explain again what you are proposing here? |
This comment has been minimized.
This comment has been minimized.
|
@WestLangley
It's true that zooming in the camera to the scene can cause a line to be large but that's the case with any 3d model and just the nature of perspective I feel. I think it should be up to the application developer to choose the right approach for their work and handle any problematic corner cases they may run into if any arise. For my use case I'd like the lines to feel more situated in world space by enabling perspective attenuation. I just made a couple quick changes to enable attenuation in the shader but I'll make any changes to the implementation that you'd like to see. And as mentioned above I'd probably rename the field on the material to |
This comment has been minimized.
This comment has been minimized.
|
My feeling is that lines are used to render perspective; they are not drawn in perspective. So I am not a big fan of this idea. But to continue the discussion, adding That means you will now have the following use cases to support:
|
This comment has been minimized.
This comment has been minimized.
|
I understand what you're saying and I definitely agree that that's a big use case but there are others that require specifying the width in world units. For comparison Unity's
I agree and I haven't tested with an orthographic camera so I'll get that done. If I put the time in to implement and test this fully with the updates we discussed will you support the change? |
This comment has been minimized.
This comment has been minimized.
|
Rethinking the use cases, there is no need for a
So you only need a I would not object as long as the shader code is modified in a clear manner -- and is correct. |
This comment has been minimized.
This comment has been minimized.
|
@WestLangley I've made the changes. When This is true even with orthographic cameras because if we consider lineWidth to be specified in world units then we should expect that a line would be the same size as a 1 unit wide block if I'm tempted to suggest that PointsMaterial should behave the same way but that can be discussed another day. |
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
|
Oof you're right -- thanks for the catch. I believe I've fixed it by deriving the line direction in screen space rather than world space. I think it looks much better now. Before After And showing that a line with a world-units width of 1 is the same width as a unit cube: At extremely skewed angles the endcaps will still have a bit of an odd look but I don't think there's much that can be done about that (Unity's LineRenderer exhibits the same behavior). |
This comment has been minimized.
This comment has been minimized.
Implementing a feature that clearly is not correct will lead to complaints. I think the correct math can be implemented with some additional effort. I would then be more supportive of this feature request. |
This comment has been minimized.
This comment has been minimized.
I'll put a bit more time into it and see what I can come up with -- any resources or direction you have on it would be greatly appreciated. And just so we're on the same page am I to understand that "correct" here means the line strip should look like a capsule when viewed from all angles?
As an aside would this be alleviated if proper docs were written for the Line2 example? Generally my feeling is that limitations like this are okay as long as they're declared up front and a user knows what to expect. Most graphics cheats break down at some point and I feel it's just a matter of knowing what those limitations are and how to avoid them. The transparency artifacts that appear on the line, for example, would also benefit from being explained up front a bit, too. Thanks again! |
This comment has been minimized.
This comment has been minimized.
No, it should look like a projected 3D capsule -- at least in theory.
No, it is only alleviated if the projection is correct. |
This comment has been minimized.
This comment has been minimized.
|
I've updated the shader such that a line segment looks like a projected capsule: Every resource I found indicated that the aforementioned artifacts are inherent with the projected quad technique so the render approach is now a bit more complicated. When rendering with world units the quad is projected such that the the area will cover where the capsule is projected. Then the fragment shader does a ray-line distance check and discards a pixel if the ray is too far from the line. Here's the new demo: https://rawgit.com/gkjohnson/three.js/161915d/examples/webgl_lines_fat.html The ray-line-distance check is referenced from Paul Bourke's write up on topic, which I can add an inline reference to if you want. Thanks for the push! |
This comment has been minimized.
This comment has been minimized.
|
@gkjohnson This definitely is the correct look. Thanks for doing this. Note that in most use cases, 99% of what is rendered are the lines themselves; the end-caps are a small part. The lines can be rendered with two triangles. Unless there is a gotcha that I am missing, that should be doable -- and a far superior approach to computing the distance to a line for every texel. I think is would involve a minimal change to the program, although I admit I have not tried it. Would you be willing to try? I can share some of the calculations I have made. You have convinced me that size attenuation is a nice feature. |
This comment has been minimized.
This comment has been minimized.
|
@WestLangley Awesome! Yeah it's definitely more computationally intensive than the other approach. I can look into what it might take to implement what you're suggesting but as it is there are cases where the center quad has pixels discarded because they aren't intersecting the capsule. It's definitely the case that the quad could have a tighter containment around the capsule, though. Here are some pictures illustrating the what's happening -- the green and yellow quads are the endcap tris while the magenta one are the line "body" tris you're talking about: Looking perpendicular to the line: And looking at a skewed angle: The magenta triangles are no longer centered along the line being drawn. Instead they are situated at the forward edge of the capsules surface to ensure the whole projected capsule area is contained. Clearly there are cases where the endcap quads aren't being used at all, though, and that could probably be improved. Hopefully that makes sense -- I'm definitely open to hearing what kinds of changes you're imagining, as well! I'm also interested in whether or not the logic in the shader is clear otherwise I can add some more clarifying comments or try to explain it better. |
This comment has been minimized.
This comment has been minimized.
dyarosla
commented
Jan 10, 2020
|
@gkjohnson first of all, AMAZING work + shader! Is there any chance you can elaborate on the camera clipping part of the shader? Is there a way to not make it an estimate? I’ve tried to port the logic to C# + Unity and its only this part that sometimes gives me trouble in the final output on specifically lines close to the camera. |








gkjohnson commentedJun 26, 2019
•
edited
Adds a
screenSpaceWidthuniform toLineMaterialwhich enables or disables a consistent screen space thickness. This is similar to thesizeAttenuationuniform onPointsMaterial.For testing:
https://rawgit.com/gkjohnson/three.js/a2f48e05/examples/webgl_lines_fat.html
@WestLangley