-
Notifications
You must be signed in to change notification settings - Fork 2.2k
feat(extensions): TerrainExtension GlobeView support #10251
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
Changes from 21 commits
0a45963
59cd841
34d4813
b3d4ecf
92f63bb
444afe7
5a6627e
20765c0
408bc0a
abeed1a
7dd49ce
95b48f3
9352f89
6f4e2b2
0d3cbe2
5aafcb7
c2a667e
b4f4a44
03d9af3
7e0522b
aca1243
600cb82
c520bde
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -67,10 +67,21 @@ uniform sampler2D terrain_map; | |||||||||||
| export const terrainModule = { | ||||||||||||
| name: 'terrain', | ||||||||||||
| dependencies: [project], | ||||||||||||
| // eslint-disable-next-line prefer-template | ||||||||||||
| vs: uniformBlock + /* glsl */ 'out vec3 commonPos;', | ||||||||||||
| // eslint-disable-next-line prefer-template | ||||||||||||
| fs: uniformBlock + /* glsl */ 'in vec3 commonPos;', | ||||||||||||
| vs: `${uniformBlock} | ||||||||||||
| out vec3 commonPos; | ||||||||||||
| // In globe mode, absolute Mercator position for terrain FBO UV lookups | ||||||||||||
| out vec2 terrainMercPos; | ||||||||||||
| out float terrainHeight; | ||||||||||||
|
|
||||||||||||
| vec2 terrain_globe_to_mercator(vec3 globePosition) { | ||||||||||||
| float D = length(globePosition); | ||||||||||||
| float sinLat = clamp(globePosition.z / D, -0.999998, 0.999998); | ||||||||||||
| float x = atan(globePosition.x, -globePosition.y); | ||||||||||||
| float y = atanh(sinLat); | ||||||||||||
| return (vec2(x, y) + PI) * WORLD_SCALE; | ||||||||||||
| } | ||||||||||||
| `, | ||||||||||||
| fs: `${uniformBlock}in vec2 terrainMercPos;\nin float terrainHeight;`, | ||||||||||||
| inject: { | ||||||||||||
| 'vs:#main-start': /* glsl */ ` | ||||||||||||
| if (terrain.mode == TERRAIN_MODE_SKIP) { | ||||||||||||
|
|
@@ -80,32 +91,45 @@ if (terrain.mode == TERRAIN_MODE_SKIP) { | |||||||||||
| `, | ||||||||||||
| 'vs:DECKGL_FILTER_GL_POSITION': /* glsl */ ` | ||||||||||||
| commonPos = geometry.position.xyz; | ||||||||||||
| terrainHeight = commonPos.z + project.commonOrigin.z; | ||||||||||||
| if (project.projectionMode == PROJECTION_MODE_GLOBE) { | ||||||||||||
| terrainMercPos = terrain_globe_to_mercator(commonPos); | ||||||||||||
| terrainHeight = length(commonPos) - GLOBE_RADIUS; | ||||||||||||
| } else { | ||||||||||||
| terrainMercPos = commonPos.xy; | ||||||||||||
| } | ||||||||||||
| if (terrain.mode == TERRAIN_MODE_WRITE_HEIGHT_MAP) { | ||||||||||||
| vec2 texCoords = (commonPos.xy - terrain.bounds.xy) / terrain.bounds.zw; | ||||||||||||
| vec2 texCoords = (terrainMercPos - terrain.bounds.xy) / terrain.bounds.zw; | ||||||||||||
| position = vec4(texCoords * 2.0 - 1.0, 0.0, 1.0); | ||||||||||||
| commonPos.z += project.commonOrigin.z; | ||||||||||||
| } | ||||||||||||
| if (terrain.mode == TERRAIN_MODE_USE_HEIGHT_MAP) { | ||||||||||||
| vec3 anchor = geometry.worldPosition; | ||||||||||||
| anchor.z = 0.0; | ||||||||||||
| vec3 anchorCommon = project_position(anchor); | ||||||||||||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. OK, so if I understand correctly you're basically forcing if (project.projectionMode == PROJECTION_MODE_WEB_MERCATOR) {A natural question that comes to mind is that if we are going to hardcode a projection, then why Mercator? Sure it works well for
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Perhaps related, I have been feeling that if we extend layers to take a "deformation" when generating geometry, such as a deformation UV grid for BitmapLayer than we could generalize that to support any projection. |
||||||||||||
| vec2 texCoords = (anchorCommon.xy - terrain.bounds.xy) / terrain.bounds.zw; | ||||||||||||
| vec2 anchorMercPos = project.projectionMode == PROJECTION_MODE_GLOBE | ||||||||||||
| ? terrain_globe_to_mercator(anchorCommon) | ||||||||||||
| : anchorCommon.xy; | ||||||||||||
| vec2 texCoords = (anchorMercPos - terrain.bounds.xy) / terrain.bounds.zw; | ||||||||||||
| if (texCoords.x >= 0.0 && texCoords.y >= 0.0 && texCoords.x <= 1.0 && texCoords.y <= 1.0) { | ||||||||||||
| float terrainZ = texture(terrain_map, texCoords).r; | ||||||||||||
| geometry.position.z += terrainZ; | ||||||||||||
| if (project.projectionMode == PROJECTION_MODE_GLOBE) { | ||||||||||||
| geometry.position.xyz += normalize(geometry.position.xyz) * terrainZ; | ||||||||||||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
Result
|
||||||||||||
| } else { | ||||||||||||
| geometry.position.z += terrainZ; | ||||||||||||
| } | ||||||||||||
| position = project_common_position_to_clipspace(geometry.position); | ||||||||||||
| } | ||||||||||||
| } | ||||||||||||
| `, | ||||||||||||
| 'fs:#main-start': /* glsl */ ` | ||||||||||||
| if (terrain.mode == TERRAIN_MODE_WRITE_HEIGHT_MAP) { | ||||||||||||
| fragColor = vec4(commonPos.z, 0.0, 0.0, 1.0); | ||||||||||||
| fragColor = vec4(terrainHeight, 0.0, 0.0, 1.0); | ||||||||||||
| return; | ||||||||||||
| } | ||||||||||||
| `, | ||||||||||||
| 'fs:DECKGL_FILTER_COLOR': /* glsl */ ` | ||||||||||||
| if ((terrain.mode == TERRAIN_MODE_USE_COVER) || (terrain.mode == TERRAIN_MODE_USE_COVER_ONLY)) { | ||||||||||||
| vec2 texCoords = (commonPos.xy - terrain.bounds.xy) / terrain.bounds.zw; | ||||||||||||
| vec2 texCoords = (terrainMercPos - terrain.bounds.xy) / terrain.bounds.zw; | ||||||||||||
| vec4 pixel = texture(terrain_map, texCoords); | ||||||||||||
| if (terrain.mode == TERRAIN_MODE_USE_COVER_ONLY) { | ||||||||||||
| color = pixel; | ||||||||||||
|
|
@@ -173,7 +197,7 @@ if ((terrain.mode == TERRAIN_MODE_USE_COVER) || (terrain.mode == TERRAIN_MODE_US | |||||||||||
| return { | ||||||||||||
| mode, | ||||||||||||
| terrain_map: sampler, | ||||||||||||
| // Convert bounds to the common space, as [minX, minY, width, height] | ||||||||||||
| // Convert bounds to common space, as [minX, minY, width, height] | ||||||||||||
| bounds: bounds | ||||||||||||
| ? [ | ||||||||||||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I worry this will introduce precision issues |
||||||||||||
| bounds[0] - commonOrigin[0], | ||||||||||||
|
|
||||||||||||

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.
General commentary: It's not obvious that billboarded layers need
cullMode: 'none'to work onGlobeView.I think it'd be good practice to add a remark on layer docs that need this until deck offers an automatic solution.
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.
Kinda related to #10262 @ibgreen