Skip to content

Commit 81a6f65

Browse files
committed
copying over example notebooks part 1
1 parent fb78f3e commit 81a6f65

25 files changed

Lines changed: 8252 additions & 24 deletions

docs/advanced_guide.rst

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,13 @@
11
Advanced guide
22
==============
3+
4+
.. toctree::
5+
:maxdepth: 1
6+
7+
advanced_guide/flask
8+
advanced_guide/choropleth with Jenks natural breaks optimization
9+
advanced_guide/colormaps
10+
advanced_guide/world_copy
11+
advanced_guide/custom_panes
12+
advanced_guide/geodedetic_image_overlay
13+
advanced_guide/custom_tiles
Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
# Integrating Jenks Natural Break Optimization with choropleth
2+
3+
Choropleths provide an easy way to visually see data distributions across geography. By default, folium uses the breaks created by numpy.histogram (np.histogram), which generally creates an evenly spaced quantiles.
4+
5+
This works well enough for evenly distributed data, but for unevenly distributed data, these even quantiles can obscure more than they show. To demonstrate this, I have created maps showing the labor force of each US state.
6+
7+
The data was taken from the county-level data and aggregated. Since our geographic data does not have areas representing Puerto Rico or the United States as a whole, I removed those entries while keeping Washington, D.C. in our data set. Already, looking at the first five states alphabetically, we can see that Alaska (AK) has a work force roughly 2% the size of California (CA).
8+
9+
```{code-cell} ipython3
10+
import folium
11+
import numpy as np
12+
import pandas as pd
13+
import json
14+
import requests
15+
```
16+
17+
```{code-cell} ipython3
18+
url = (
19+
"https://raw.githubusercontent.com/python-visualization/folium/main/examples/data"
20+
)
21+
us_states = f"{url}/us-states.json"
22+
23+
geo_json_data = json.loads(requests.get(us_states).text)
24+
25+
county_data = pd.read_csv(f"{url}/us_county_data.csv")
26+
clf = 'Civilian_labor_force_2011'
27+
labor_force = county_data[['State', clf]][
28+
(county_data[clf].str.strip()!='') & (~county_data['State'].isin(['PR', 'US']))
29+
]
30+
labor_force[clf] = labor_force[clf].astype(int)
31+
labor_force = labor_force.groupby('State').sum().reset_index()
32+
33+
labor_force.head()
34+
```
35+
36+
Using default breaks, most states are represented as being part of the bottom quantile. This distribution is similar to what we might expect if US states follow a Power Law or a Zipf distribution.
37+
38+
```{code-cell} ipython3
39+
m = folium.Map(location=[38, -96], zoom_start=4)
40+
41+
folium.Choropleth(
42+
geo_data=geo_json_data,
43+
data=labor_force,
44+
columns=['State', clf],
45+
key_on='id',
46+
fill_color='RdBu',
47+
).add_to(m)
48+
49+
m
50+
```
51+
52+
However, when using Jenks natural Breaks Optimization, we now see more granular detail at the bottom of the distribution, where most of our states are located. The upper western states (Idaho, Montana, Wyoming and the Dakotas) are distinguished from their Midwestern and Mountain West neighbors to the south. Gradations in the deep south between Mississippi and Alabama provide more visual information than in the previous map. Overall, this is a richer representation of the data distribution.
53+
54+
One notable drawback of this representation is the legend. Because the lower bins are smaller, the numerical values overlap, making them unreadable.
55+
56+
```{code-cell} ipython3
57+
m = folium.Map(location=[38, -96], zoom_start=4)
58+
59+
choropleth = folium.Choropleth(
60+
geo_data=geo_json_data,
61+
data=labor_force,
62+
columns=['State', clf],
63+
key_on='id',
64+
fill_color='RdBu',
65+
use_jenks=True,
66+
)
67+
choropleth.add_to(m)
68+
69+
choropleth.color_scale.width = 800
70+
71+
m
72+
```

docs/advanced_guide/colormaps.md

Lines changed: 192 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,192 @@
1+
# Using `folium.colormap`
2+
3+
**A few examples of how to use `folium.colormap` in choropleths.**
4+
5+
Let's load a GeoJSON file, and try to choropleth it.
6+
7+
```{code-cell} ipython3
8+
import json
9+
10+
import folium
11+
import pandas as pd
12+
import requests
13+
14+
15+
url = (
16+
"https://raw.githubusercontent.com/python-visualization/folium/main/examples/data"
17+
)
18+
us_states = f"{url}/us-states.json"
19+
US_Unemployment_Oct2012 = f"{url}/US_Unemployment_Oct2012.csv"
20+
21+
geo_json_data = json.loads(requests.get(us_states).text)
22+
unemployment = pd.read_csv(US_Unemployment_Oct2012)
23+
24+
unemployment_dict = unemployment.set_index("State")["Unemployment"]
25+
```
26+
27+
## Self-defined
28+
29+
You can build a choropleth in using a self-defined function.
30+
It has to output an hexadecimal color string of the form `#RRGGBB` or `#RRGGBBAA`.
31+
32+
```{code-cell} ipython3
33+
def my_color_function(feature):
34+
"""Maps low values to green and high values to red."""
35+
if unemployment_dict[feature["id"]] > 6.5:
36+
return "#ff0000"
37+
else:
38+
return "#008000"
39+
```
40+
41+
```{code-cell} ipython3
42+
m = folium.Map([43, -100], tiles="cartodbpositron", zoom_start=4)
43+
44+
folium.GeoJson(
45+
geo_json_data,
46+
style_function=lambda feature: {
47+
"fillColor": my_color_function(feature),
48+
"color": "black",
49+
"weight": 2,
50+
"dashArray": "5, 5",
51+
},
52+
).add_to(m)
53+
54+
m
55+
```
56+
57+
## StepColormap
58+
59+
But to help you define your colormap, we've embedded `StepColormap` in `folium.colormap`.
60+
61+
You can simply define the colors you want, and the `index` (*thresholds*) that correspond.
62+
63+
```{code-cell} ipython3
64+
import branca.colormap as cm
65+
66+
step = cm.StepColormap(
67+
["green", "yellow", "red"], vmin=3, vmax=10, index=[3, 4, 8, 10], caption="step"
68+
)
69+
70+
step
71+
```
72+
73+
```{code-cell} ipython3
74+
m = folium.Map([43, -100], tiles="cartodbpositron", zoom_start=4)
75+
76+
folium.GeoJson(
77+
geo_json_data,
78+
style_function=lambda feature: {
79+
"fillColor": step(unemployment_dict[feature["id"]]),
80+
"color": "black",
81+
"weight": 2,
82+
"dashArray": "5, 5",
83+
},
84+
).add_to(m)
85+
86+
m
87+
```
88+
89+
If you specify no index, colors will be set uniformly.
90+
91+
```{code-cell} ipython3
92+
cm.StepColormap(["r", "y", "g", "c", "b", "m"])
93+
```
94+
95+
## LinearColormap
96+
97+
But sometimes, you would prefer to have a *continuous* set of colors. This can be done by `LinearColormap`.
98+
99+
```{code-cell} ipython3
100+
linear = cm.LinearColormap(["green", "yellow", "red"], vmin=3, vmax=10)
101+
102+
linear
103+
```
104+
105+
```{code-cell} ipython3
106+
m = folium.Map([43, -100], tiles="cartodbpositron", zoom_start=4)
107+
108+
folium.GeoJson(
109+
geo_json_data,
110+
style_function=lambda feature: {
111+
"fillColor": linear(unemployment_dict[feature["id"]]),
112+
"color": "black",
113+
"weight": 2,
114+
"dashArray": "5, 5",
115+
},
116+
).add_to(m)
117+
118+
m
119+
```
120+
121+
Again, you can set the `index` if you want something irregular.
122+
123+
```{code-cell} ipython3
124+
cm.LinearColormap(["red", "orange", "yellow", "green"], index=[0, 0.1, 0.9, 1.0])
125+
```
126+
127+
If you want to transform a linear map into a *step* one, you can use the method `to_step`.
128+
129+
```{code-cell} ipython3
130+
linear.to_step(6)
131+
```
132+
133+
You can also use more sophisticated rules to create the thresholds.
134+
135+
```{code-cell} ipython3
136+
linear.to_step(
137+
n=6,
138+
data=[30.6, 50, 51, 52, 53, 54, 55, 60, 70, 100],
139+
method="quantiles",
140+
round_method="int",
141+
)
142+
```
143+
144+
And the opposite is also possible with `to_linear`.
145+
146+
```{code-cell} ipython3
147+
step.to_linear()
148+
```
149+
150+
## Built-in
151+
152+
For convenience, we provide a (small) set of built-in linear colormaps, in `folium.colormap.linear`.
153+
154+
```{code-cell} ipython3
155+
cm.linear.OrRd_09
156+
```
157+
158+
You can also use them to generate regular `StepColormap`.
159+
160+
```{code-cell} ipython3
161+
cm.linear.PuBuGn_09.to_step(12)
162+
```
163+
164+
Of course, you may need to scale the colormaps to your bounds. This is doable with `.scale`.
165+
166+
```{code-cell} ipython3
167+
cm.linear.YlGnBu_09.scale(3, 12)
168+
```
169+
170+
```{code-cell} ipython3
171+
cm.linear.RdGy_11.to_step(10).scale(5, 100)
172+
```
173+
174+
At last, if you want to check them all, simply ask for `linear` in the notebook.
175+
176+
```{code-cell} ipython3
177+
cm.linear
178+
```
179+
180+
## Draw a `ColorMap` on a map
181+
182+
By the way, a ColorMap is also a Folium `Element` that you can draw on a map.
183+
184+
```{code-cell} ipython3
185+
m = folium.Map(tiles="cartodbpositron")
186+
187+
colormap = cm.linear.Set1_09.scale(0, 35).to_step(10)
188+
colormap.caption = "A colormap caption"
189+
m.add_child(colormap)
190+
191+
m
192+
```
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
# Panes and CustomPane
2+
3+
Panes are used to control the ordering of layers on the map. You can customise
4+
them using the `CustomPane` class.
5+
6+
For more info on the panes Leaflet has, see https://leafletjs.com/reference.html#map-pane.
7+
8+
First we'll load geojson data to use in the examples:
9+
10+
```{code-cell} ipython3
11+
import json
12+
13+
import folium
14+
import requests
15+
16+
url = (
17+
"https://raw.githubusercontent.com/python-visualization/folium/main/examples/data"
18+
)
19+
us_states = f"{url}/us-states.json"
20+
geo_json_data = json.loads(requests.get(us_states).text)
21+
22+
style_function = lambda x: {"fillOpacity": 0.8}
23+
```
24+
25+
## Map without custom pane
26+
27+
We'll make an example to show how the GeoJson we add hides any labels
28+
underneath.
29+
30+
```{code-cell} ipython3
31+
m = folium.Map([43, -100], zoom_start=4, tiles="stamentoner")
32+
33+
folium.GeoJson(geo_json_data, style_function=style_function).add_to(m)
34+
35+
m
36+
```
37+
38+
## Map with custom pane
39+
40+
Now we'll create a custom pane and add a tile layer that contains only labels.
41+
The labels will show on top off the geojson.
42+
43+
```{code-cell} ipython3
44+
m = folium.Map([43, -100], zoom_start=4, tiles="stamentonerbackground")
45+
46+
folium.GeoJson(geo_json_data, style_function=style_function).add_to(m)
47+
48+
folium.map.CustomPane("labels").add_to(m)
49+
50+
# Final layer associated to custom pane via the appropriate kwarg
51+
folium.TileLayer("stamentonerlabels", pane="labels").add_to(m)
52+
53+
m
54+
```

0 commit comments

Comments
 (0)