grass.jupyter: Created attracting and elegant legend feature for rasters in InteractiveMap.#7077
grass.jupyter: Created attracting and elegant legend feature for rasters in InteractiveMap.#7077shahid-rahaman wants to merge 7 commits intoOSGeo:mainfrom
Conversation
f0b4776 to
e568a16
Compare
|
Reproducible code examples and screenshots? |
@wenzeslaus Sorry for late reply, I have updated the description. I have been facing some dev system crash. Is there any standard way to setup dev environment? I somehow did but it was quirky, I installed grass from local repo by ./configure>make -j10> sudo make install, but it throws few errors sometimes due to which I cannot run local test/checks as it is not installed properly. Am I missing something or is there any documentation to setup dev enviroment? |
wenzeslaus
left a comment
There was a problem hiding this comment.
Well, the legend in screenshots does look attractive and elegant.
Anyway, you should still make the title shorter and more technical.
More work is needed here and I did not test myself yet, but I like the direction here.
|
@wenzeslaus Thanks for your time, I understand there are some preferred approach for GRASS, I used python core logics and module to make it work, like "subprocess", I had used it several times personally. However, I will try align the code with the existing dependencies and preferred approach. |
|
Please, sync up to the main branch. Then, the following link will allow reviewers to test without the need to have the changes locally: |
|
I didn't get any legend on mobile. |
939dcaf to
cbb28e3
Compare
| from branca.element import MacroElement | ||
| import folium | ||
| from folium.map import MacroElement | ||
| from jinja2 import Template |
There was a problem hiding this comment.
@wenzeslaus You earlier worried about these dependencies, but both of them are the dependencies of of folium itself See.
Folium has the following dependencies, all of which are installed automatically with the above installation commands:
branca, Jinja2, Numpy ,Requests
However, I avoided branca, as it is not very active but we can use jinja as it is already installed. Folium internally calles Template() method of jinja to create Template object. And this object is essential as it further calls for module attribute associate with this object. So, far it is working fine as expected as per my observation.
There was a problem hiding this comment.
This looks good. While it is not bulletproof, transitive vs direct dependency makes as difference.
@wenzeslaus I have not checked it on the phones yet. I am not sure if phones allows html code to be injected the same way. Although, in chrome dev tool when I toggle the device to be iphone 12 or responsive, I see the legend there. So, I think it is the not the resolution problem. |
|
@wenzeslaus Any update here? |
wenzeslaus
left a comment
There was a problem hiding this comment.
I like this and I get the legend in Binder at least with a desktop. However, there is couple of issues here:
- Now, I always get a viridis. The logic is wrong.
- The gradient values taken from GRASS may not work as is with CSS as visible in the image - at least in Firefox (see above).
- Your previous examples were much better. Also add geology. Make them copy-pastable to the notebooked used in Binder. Test your result as if you would be a user. Use a tutorial.
- See my other comments.
Just a heads-up that this starts to feel like interacting with AI. Please, review our AI policy in the contributing file.
| colors = [item["color"] for item in color_maps] | ||
| css_gradient = ", ".join(colors) | ||
| # Setting some interval ticks to compare values relatively. | ||
| info = tools.r_info(map=raster, format='json') |
There was a problem hiding this comment.
Explore what you get with the r_colors_out call, r_info, and r_univar for the range of values for different computational regions (after changing the extent by g_region/g.region user-level call to change the extent which will change what values are considered). This influenced whether or not the r_info call here appropriate.
There was a problem hiding this comment.
Dont' get me wrong, I am not defensive, I do checkout r_colors and r_info without seeing the nature of returned values of APIs we cannot frame a code, I am not a seasonal dev, I am quite new and a GSoC aspirant. Although, trying to give my best hit and not to leave any stone unturned. I see the relevant parts of docs as I progress. I do use LLMs to understand code snippets sometimes as it is not practical to tag maintainers for every queries. Correct me if I said something wrong.
regards
@wenzeslaus Thanks for review. Very first thing I don't trust AI generated code they are very often poorly strcutured and redundant. Although I use LLMs for code review and guidance, like where to find the appropriate info in the documentation. Now, lets, come to your concerns.
But I dont know why binder shows "rainbow" colors as you have not provided any color arguments and default is "viridis". And there is indeed a bug I am working on that is when a color scheme is applied it is somehow saved in cache or something(I am not sure yet) but when you refresh the same cell it renders the rasters with desired colors. I should see some binder usage.
|
The geology map in that sample dataset has colors already set (it may be indeed rainbow). Importantly, the resulting color table is not a gradient one. The values are categorical. Run r.report to understand more about this specific data. Compare to elevation. Aspect may be yet a little different.
viridis is used as a default internally. No work from users or in your code is needed. I hope this clarifies that.
The color table is saved with the data in the GRASS project, so in a way, r.colors call modifies the data (or let's say visualization metadata), so that's why you should not be using it in the code (you should have an example which uses that, though). Generate new data with r.surf.fractal to get an example for that use case. |
@wenzeslaus In the meantime, I observed binder itself behaves little quirky. Forget about the add_legend method for now and kindly see the snippet below. m = InteractiveMap(height = 500, width = 1000)
raster = "elevation"
gs.run_command('r.colors', map=raster, color='magma')
m.add_raster(raster)
m.show()
m = InteractiveMap(height = 500, width = 1000)
raster = "elevation"
gs.run_command('r.colors', map=raster, color='viridis')
m.add_raster(raster)
m.show()
No matter what color scheme I choose it never updates the rendering for any rasters, although add_legend method works fine it generates as per any given color scheme. Firefox SS you shared worked fine in my end. Am I missing something? |
382ebd8 to
5ce1fd6
Compare
|
@wenzeslaus I have tried changes as per your suggestion. But first see this comment.
|
| finished += color_width | ||
| colors.extend(color) | ||
|
|
||
| css_gradient = ", ".join(colors) |
There was a problem hiding this comment.
It only contains the colors used in the rendering. No interpolation to fill and make smoother transition.
| minv = float(info["min"]) | ||
| maxv = float(info["max"]) | ||
| num_ticks = len(color_maps) if len(color_maps) < 7 else 6 | ||
| ticks = [minv + i * (maxv - minv) / (num_ticks - 1) for i in range(num_ticks)] if num_ticks > 1 else [minv] |
There was a problem hiding this comment.
For some rasters like roadsmajor, it returns only one data which earlier caused ZeroDivisionErro, I also address that.
|
@wenzeslaus If we call this add_legend via add_raster via arguemnt, I think that would be more succinct and dynamic. For instance we can do as following with add_raster. def add_raster(self, name, title=None, legend=False, **kwargs)if user enters legend arguement with it's locaation like bottomright, we can all add_legend with such arguemnt. |
|
@wenzeslaus Any updates? Is it fine to tag you every alternative day? I am not sure if disturbing you. |





Created legend feature for rasters with easy to use commands. Gave it a transparent glass frost look for better UX.
@wenzeslaus If looks good to you, I will write the tests for the corresponding entities.
Let me know if requires any adjustments.
For instance, use it like below.
You can use any colors like sepia, rainbow, etc. apart from viridis and magma.
regards