-
Notifications
You must be signed in to change notification settings - Fork 3.5k
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
Polylines on terrain via Primitive API #6615
Conversation
…hed), enabled debugging false shadow volume
@likangning93, thanks for the pull request! Maintainers, we have a signed CLA from @likangning93, so you can review this at any time.
I am a bot who helps you make Cesium awesome! Contributions to my configuration are welcome. 🌍 🌎 🌏 |
componentDatatype: ComponentDatatype.FLOAT, | ||
componentsPerAttribute: 3, | ||
normalize: false, | ||
value : [lengthSoFar, segmentLength, totalLength] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why aren't most of these vertex attributes? If it's per segment, it should be a vertex attribute and if it's per polyline then it should be in the batch table. We do the same thing for billboards and other polylines. Yes, you're duplicating data but it cuts down texture reads in the shader. We only started adding more to the batch table when we ran out of vertex attributes (guaranteed to be at least 8).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The other polylines are using 13 vertex attributes so expect the maximum to be at least 16.
// An object that, on setting an attribute, will set all the instances' attributes. | ||
var userAttributeNames = ['width', 'show']; | ||
var userAttributeCount = userAttributeNames.length; | ||
function InstanceAttributeSynchronizer(batchTable, firstInstanceIndex, lastInstanceIndex, batchTableAttributeIndices) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Once you remove the per segment data from the batch table, you can remove this too.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You could also move most of the code from GroundLineSegmentGeometry
to GroundPolylineGeometry
and remove decompose
.
attribute vec3 position3DLow; | ||
attribute float batchId; | ||
|
||
varying vec4 v_startPlaneEC; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You should probably limit the number of varyings to 8. MAX_VARYING_VECTORS
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Never mind, the fragment shader only uses 7.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I can trim it down... the polyline material shaders also swallow a couple varyings that don't show in the FS.
This is kind of inevitable for shadow-volume-type algorithms... part of the motivation for a single-pass algorithm was possible hybridization with @pjcozzi's wall-based algorithm, and I think it's also worth exploring if the per-fragment terrain slope can help us with this. We were hoping those could be "future work" if the current smearing is acceptable in most use cases though. |
Aaaaand there we go, I'm nerd sniped... right now we're doing per-fragment point-plane distances, hence the smearing problem. But if we took the local terrain slope into account (which we can already compute pretty reliably for ground primitive materials) we could do ray-plane distance checks, I think this could work! Will definitely take some fiddling though, I'll leave that until after I've addressed existing PR comments... [EDIT] or maybe even until after this PR and the followup Entity API integration is done... motivation! |
@bagnell ideally we'd want to do this per-segment, unlike Some concerns about the additional cost on worker spinup, but does this happen very frequently? |
Ah, OK. You can definitely move it to a worker. Worker spin up only happens once on the first post message. One thing you can do in the future is group line segments by terrain tile. This would reduce the number of times you need to get the min/max heights. Right now, with that many segments, it wouldn't be bad. If we ever need to query a server for the min/max heights, you don't want to make that many HTTP requests. |
…it asynchronous createGeometry worker functions [ci skip]
…on terrain [ci skip]
@bagnell there's a problem with polylines that have large bounding volumes:
|
tears I need to take a deeper look, but has there been any discussion of letting it take fully generic attributes? I might end up giving that a try... |
It's a little tricky. I'm not sure there's a generic way to figure out what the value is at the new vertex that works for every kind of attribute. For example, mines a boolean attribute so you can't interpolate it, you need to decide what the new value should be based on what the other vertices of the triangle are |
Playing with fire a little bit, but if the boolean is true for the top cap and false for the bottom cap of the geometry you might still be able to just interpolate and clamp and expect this to just work because the IDL should be splitting bottoms and tops instead of walls? I guess it's still tricky since there might not be a good way to indicate a clampable bool for safety, but it seems like it might interpolate okay? The attributes in here are fortunately (painfully...) identical for each vertex in a triangle, so barycentric interpolation is actually overkill :P Wonder how far I could get by having |
Erm, clarification. Splitting walls, but vertically instead of horizontally if that makes sense.
So if the values at V0 and V1 are the same, |
This is partially my fault, I noticed some weirdness with crossing segments in CV as well, but I think part of this is also a problem with the depth buffer in 2D. Debug views seem to show the depth values drop off moving west-to-east towards the IDL, varying with view distance. The effect is worse if there's things drawn over a wider range of longitudes (wider rectangle). |
9ec479d
to
81a23c8
Compare
I'm getting noticeable performance improvements on Windows/Nvidia and Linux/Intel, will test Windows/Intel soon. Hopeful. [EDIT] nice performance boost for Windows/Intel too, in both Chrome and Edge. |
… add simple Sandcastle example for Ground Polyline materials
335d58a
to
403e500
Compare
@bagnell please do a final review and merge. It would be nice to get this into master soon so it is well before the release. |
} | ||
|
||
// Update each geometry for framestate.scene3DOnly = true | ||
geometryInstance.geometry._scene3DOnly = frameState.scene3DOnly; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why not do the same thing for projection?
attribute float batchId; | ||
|
||
varying vec3 v_forwardDirectionEC; | ||
varying vec3 v_texcoordNormalization_and_halfWidth; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Remove the underscores.
This crashes in IE. |
This is happening in Chrome too, it's because we're permitting much steeper angles now before breaking the miter. So the problem is that the solution for this thing doesn't actually work: It works almost okay for the two volumes on either side of the sharp turn, but the next set of volumes don't have enough information to avoid overdraw. In other words, it was only fixing a part of the original overdrawn region. Here's what the original overdrawn region can look like for very steep angles: Note that there are 3 regions of overdraw here, with only one region (the furthest to the right) exclusively involving the two segments immediately adjacent to the turn. Only that region is getting resolved correctly by my solution, leaving overdraw in all other areas: This problem becomes much less noticeable when Resolving this completely might require giving those longer rectangular regions information about the turn, which is another pile of vertex attributes (definitely some high precision ones) and could be kind of terrible. |
@bagnell up-to-date and passing |
daa7e4b
to
3ec30e3
Compare
Opening a PR to indicate that this is "stable" enough to preview and for preliminary review, but there's still a decent amount of work to be done.
Features:
PolylineMaterialAppearance
Implementation notes:
More details in #2172 (comment).
We're using a single-pass, globe-depth-based algorithm.
For each line segment in the polyline we generate a geometry instance volume that has several planes encoded in the batch table. For each fragment on the volume, we look up the globe depth to compute a terrain position in eyespace and clip this position based on the planes from the batch table.The planes are also used to compute the position's distance from the center and ends of the line for material support.
Due to the batch table dependence and mapping of attributes from multiple instances to a single pick ID, this PR introduces a newPrimitive
type,GroundPolylinePrimitive
.There's also a new user-facing geometry,
GroundPolylineGeometry
, that doesn't actually have acreateGeometry
function but rather gets decomposed into individual volumes that are then used to generate vertex buffers and attributes.This is a little troublesome for asynchronous geometry sinceGroundPolylineGeometry
's computation currently happens on the main thread, with the worker threads mostly just converting chunks of this into the combined vertex buffer. In practice this doesn't seem to be a huge problem, but it's something we should talk about.For each line segment in the polyline we generate a volume with vertex attributes that describe the line segment using a series of planes. For each fragment on the volume, we look up the globe depth to compute a terrain position in eyespace and clip this position based on the planes from the vertex attributes.
The planes are also used to compute the position's distance from the center and ends of the line for material support.
The planes differ between 2D and 3D, and I haven't figured out yet how to interpolate them for morphing, so there's a new
Primitive
type that issues draw commands with different shaders for 2D and morph. When morphing we actually just draw the volumes themselves with materials, which seems acceptable because the camera goes so far away during the morph anyway.TODO:
GroundPrimitives
Couple Post-PR roadmap items: