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

Slope and aspect #7415

Merged
merged 29 commits into from
Feb 4, 2019
Merged

Slope and aspect #7415

merged 29 commits into from
Feb 4, 2019

Conversation

spencerparkin
Copy link
Contributor

This pull request adds aspect (an angle) to the czm_MaterialInput structure and converts the slope member of this structure to an angle.

The following images show the same region (Mt. Superior in Utah), the first shows aspect coloring, the second shows slope coloring.

aspect
slope

There may be just a few small kinks to work out, but I thought it a good idea to start the pull request so that you guys can get excited about this new feature. I already have a use for it in one of my personal Cesium-based projects.

@cesium-concierge
Copy link

cesium-concierge commented Dec 14, 2018

Thank you so much for the pull request @spencerparkin! I noticed this is your first pull request and I wanted to say welcome to the Cesium community!

The Pull Request Guidelines is a handy reference for making sure your PR gets accepted quickly, so make sure to skim that.

  • ❌ Missing CONTRIBUTORS.md entry.
  • ❌ Missing CLA.
  • CHANGES.md was not updated.
    • If this change updates the public API in any way, please add a bullet point to CHANGES.md.

Reviewers, don't forget to make sure that:

  • Cesium Viewer works.
  • Works in 2D/CV.
  • Works (or fails gracefully) in IE11.

I am a bot who helps you make Cesium awesome! Contributions to my configuration are welcome.

🌍 🌎 🌏

@spencerparkin
Copy link
Contributor Author

spencerparkin commented Dec 14, 2018

Here is Half-Dome colored by aspect...
aspect

Here is Half-Dome colored by slope...
slope

I think that the slope coloring looks better now that the parameter is linearized.

@hpinkos
Copy link
Contributor

hpinkos commented Dec 14, 2018

Looks awesome @spencerparkin! Please send us over a Contributor License Agreement when you get a chance so we can review and merge this =)

@OmarShehata
Copy link
Contributor

Just for context this was also requested here: https://groups.google.com/d/msg/cesium-dev/s2Dr9YFG2fE/rY8LketHAAAJ

@spencerparkin
Copy link
Contributor Author

spencerparkin commented Dec 17, 2018

One thought that occurred to me over the weekend is that if the shaders are compiled on-demand at run-time, then we can probably turn slope/aspect features on/off at run-time using pre-processor directives. This might be a good optimization for applications that don't care about slope or aspect, or just aspect. On the other hand, maybe the additions to the vertex shader are negligible across all applications; I don't know. Note that it is faster to do trig functions in the vertex shader rather in the pixel shader, if you're going to do them at all.

Sent the CLA.

@pjcozzi
Copy link
Contributor

pjcozzi commented Dec 21, 2018

@spencerparkin thanks again for contributing, we received your CLA!

@spencerparkin
Copy link
Contributor Author

spencerparkin commented Dec 26, 2018

Following is a screen-shot of a web-app I'm working on that takes advantage of the slope and aspect feature of this pull request. Here I'm showing Gobbler's Knob under the current avalanche forecast.

screenshot

@spencerparkin
Copy link
Contributor Author

Here's a working version of the app if anyone wants to give it a go...

https://utah-ava-map.herokuapp.com/

There is a lot of room for improvement, but this is the basic idea.

I'm not sure how many people would have to use this app before Heroku started charging my credit card. It's something that makes me feel uneasy, actually.

@OmarShehata
Copy link
Contributor

@spencerparkin that looks pretty awesome! Thanks for sharing that. Are those polygon/entities on top of the terrain?

For Heroku, if you're on the free plan, it shouldn't charge you once you exceed the maximum, the app just stops working.

When you use all your free dyno hours for a given month, all free apps on your account will be forced to sleep for the rest of the month.

Source.

@spencerparkin
Copy link
Contributor Author

@OmarShehata, thanks, and thanks for that info; that's good to know.

No, I'm not adding any polygons or entities to the scene. I'm just providing my own pixel shader for the terrain. You can see the details here.

@pjcozzi
Copy link
Contributor

pjcozzi commented Dec 27, 2018

One thought that occurred to me over the weekend is that if the shaders are compiled on-demand at run-time, then we can probably turn slope/aspect features on/off at run-time using pre-processor directives. This might be a good optimization for applications that don't care about slope or aspect, or just aspect. On the other hand, maybe the additions to the vertex shader are negligible across all applications; I don't know. Note that it is faster to do trig functions in the vertex shader rather in the pixel shader, if you're going to do them at all.

Yes, good idea, please do this as it is a common GLSL optimization that we follow throughout CesiumJS.

@pjcozzi
Copy link
Contributor

pjcozzi commented Dec 27, 2018

@lilleyse could you please review and decide if the breaking change is OK in this case since it likely won't break anyone in practice? I also noticed several coding style inconsistencies but I'm sure you will flag them.

@spencerparkin thanks again for contributing and sharing the link to your app, great job! As we discussed offline, we would be pleased to showcase it when you are ready. Also please allow @lilleyse a few weeks to review as he is quite busy.

@pjcozzi
Copy link
Contributor

pjcozzi commented Dec 27, 2018

One thought that occurred to me over the weekend...

Yes, good idea, please do this as it is a common GLSL optimization that we follow throughout CesiumJS.

Actually given that the whole material block is protected by APPLY_MATERIAL, I don't know if it is a big enough deal. @lilleyse can advise.

@cesium-concierge
Copy link

Thanks again for your contribution @spencerparkin!

No one has commented on this pull request in 30 days. Maintainers, can you review, merge or close to keep things tidy?

I'm going to re-bump this in 30 days. If you'd like me to stop, just comment with @cesium-concierge stop. If you want me to start again, just delete the comment.

@hpinkos
Copy link
Contributor

hpinkos commented Jan 30, 2019

@lilleyse will you have time to review this soon?

@jasonbeverage could you do an initial review?

@jasonbeverage
Copy link
Contributor

Unfortunately I haven't been keeping up with this commit. I played with the demo and it looked really great, so I'll leave it in Sean's able hands to do an official review and blessing :)

@hpinkos
Copy link
Contributor

hpinkos commented Jan 31, 2019

Thanks @jasonbeverage !

vec3 ellipsoidNormal = normalize(position3DWC.xyz);
v_slope = abs(dot(ellipsoidNormal, finalNormal));
v_height = height;
vec3 northPolePositionMC = vec3(0.0, 0.0, 6356752.3142451793);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might be better to use czm_getWgs84EllipsoidEC().radii.z rather than hardcoding

vec3 normal_projected = v_normalMC - normal_rejected; // This is the terrain normal projected onto the tangent plane.
vec3 aspect_vector = normalize(normal_projected); // This is our unit-length heading in the tangent space. (Aspect direction.)
v_aspect = acos(dot(aspect_vector, vectorEastMC)); // Finally, here is the aspect angle.
v_height = height; // Store height.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A couple style notes:

  • Try to reduce the number of comments and avoid informal language like "we". The code self-documents itself pretty well so maybe just a summary above the code and comments whenever lines aren't obvious is enough.
  • Except for varyings (v_aspect etc), use camel case for variable names.

czm_material czm_getMaterial(czm_materialInput materialInput)
{
czm_material material = czm_getDefaultMaterial(materialInput);
vec4 rampColor = texture2D(image, vec2(materialInput.aspect / (2.0 * 3.1415926536), 0.5));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Use czm_pi here.

@@ -3,7 +3,7 @@ uniform sampler2D image;
czm_material czm_getMaterial(czm_materialInput materialInput)
{
czm_material material = czm_getDefaultMaterial(materialInput);
vec4 rampColor = texture2D(image, vec2(materialInput.slope, 0.5));
vec4 rampColor = texture2D(image, vec2(materialInput.slope / (3.1415926536 / 2.0), 0.5));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

czm_pi here as well.

// There is one final matter to clear up. Our aspect is in [0,pi), but we need it to be in [0,2pi).
float determ = dot(cross(vectorEastMC, aspect_vector), ellipsoidNormal); // Calculate a 3x3 determinant.
if(determ < 0.0) // GLSL shouldn't actually have to do a branching operation here.
v_aspect = 2.0 * 3.1415926536 - v_aspect;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Alternatively use czm_branchFreeTernary

v_aspect = czm_branchFreeTernary(determ < 0.0, 2.0 * czm_pi - v_aspect, v_aspect)

@lilleyse
Copy link
Contributor

@spencerparkin this looks great overall. I left mainly style comments. I also pushed a small style commit: d137096.

Could you add a test? It will look similar to renders a globe with a SlopeRamp

@lilleyse could you please review and decide if the breaking change is OK in this case since it likely won't break anyone in practice?

The breaking change is ok with me.

Actually given that the whole material block is protected by APPLY_MATERIAL, I don't know if it is a big enough deal. @lilleyse can advise.

Yeah, for that reason I think it is fine as it is.

@spencerparkin
Copy link
Contributor Author

@lilleyse i made some changes and tested them. Thanks for reviewing. Please let me know if I've missed anything.

Copy link
Contributor

@lilleyse lilleyse left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks @spencerparkin, just quick suggestions for the comments.

v_slope = abs(dot(ellipsoidNormal, finalNormal));
float northPoleZ = czm_getWgs84EllipsoidEC().radii.z;
vec3 northPolePositionMC = vec3(0.0, 0.0, northPoleZ);
vec3 ellipsoidNormal = normalize(v_positionMC); // TODO: For a sphere this is correct, but not generally for an ellipsoid!
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The comment is fine, but remove the TODO.

Usually if there is something actionable we would write up an issue, but in this case I think it's ok to remove the TODO and not write an issue.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

okay @lilleyse, i deleted the "TODO" prefix.

vec3 northPolePositionMC = vec3(0.0, 0.0, northPoleZ);
vec3 ellipsoidNormal = normalize(v_positionMC); // TODO: For a sphere this is correct, but not generally for an ellipsoid!
vec3 vectorEastMC = normalize(cross(northPolePositionMC - v_positionMC, ellipsoidNormal));
float dotProd = abs(dot(ellipsoidNormal, v_normalMC)); // Why absolute value here? What about overhanging terrain? (e.g., an arch.)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since the terrain system is 2.5D (one height value per x,y coordinate) I don't think the comment necessarily applies.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

okay @lilleyse, i deleted the comment

@lilleyse
Copy link
Contributor

lilleyse commented Feb 4, 2019

Great! Thanks again @spencerparkin!

@lilleyse lilleyse merged commit cee1a3a into CesiumGS:master Feb 4, 2019
@cesium-concierge
Copy link

Congratulations on closing the issue! I found these Cesium forum links in the comments above:

https://groups.google.com/d/msg/cesium-dev/s2Dr9YFG2fE/rY8LketHAAAJ

If this issue affects any of these threads, please post a comment like the following:

The issue at #7415 has just been closed and may resolve your issue. Look for the change in the next stable release of Cesium or get it now in the master branch on GitHub https://github.com/AnalyticalGraphicsInc/cesium.

@Modestgentleman
Copy link

我想问一下可不可以通过在地形上画面,使画面的一部分显示坡度与坡向?还有能不能拿到画面部分内的所有高程数据?

@spencerparkin
Copy link
Contributor Author

spencerparkin commented Jul 22, 2019 via email

@Modestgentleman
Copy link

I'm sorry to return your information so late.The analysis of topographic gradient and slope direction scope for globa material.How to Act on local material?

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

Successfully merging this pull request may close these issues.

8 participants