Repository: nilearn/nilearn

Issue:
view_img save_as_html should set the HTML title
When calling save_as_html, it would be great if it used the title of the plot (if any given) to set the html's page title.


Discussion:

Sure, I can open a PR


Resolving patch:
diff --git a/nilearn/plotting/html_connectome.py b/nilearn/plotting/html_connectome.py
--- a/nilearn/plotting/html_connectome.py
+++ b/nilearn/plotting/html_connectome.py
@@ -81,7 +81,9 @@ def _make_connectome_html(connectome_info, embed_js=True):
     as_json = json.dumps(plot_info)
     as_html = get_html_template(
         'connectome_plot_template.html').safe_substitute(
-            {'INSERT_CONNECTOME_JSON_HERE': as_json})
+            {'INSERT_CONNECTOME_JSON_HERE': as_json,
+             'INSERT_PAGE_TITLE_HERE': (
+                 connectome_info["title"] or "Connectome plot")})
     as_html = add_js_lib(as_html, embed_js=embed_js)
     return ConnectomeView(as_html)
 
diff --git a/nilearn/plotting/html_stat_map.py b/nilearn/plotting/html_stat_map.py
--- a/nilearn/plotting/html_stat_map.py
+++ b/nilearn/plotting/html_stat_map.py
@@ -296,6 +296,8 @@ def _json_view_to_html(json_view):
     width, height = _json_view_size(json_view['params'])
 
     # Populate all missing keys with html-ready data
+    json_view["INSERT_PAGE_TITLE_HERE"] = json_view[
+        "params"]["title"] or "Slice viewer"
     json_view['params'] = json.dumps(json_view['params'])
     js_dir = os.path.join(os.path.dirname(__file__), 'data', 'js')
     with open(os.path.join(js_dir, 'jquery.min.js')) as f:
diff --git a/nilearn/plotting/html_surface.py b/nilearn/plotting/html_surface.py
--- a/nilearn/plotting/html_surface.py
+++ b/nilearn/plotting/html_surface.py
@@ -121,7 +121,8 @@ def full_brain_info(volume_img, mesh='fsaverage5', threshold=None,
 def _fill_html_template(info, embed_js=True):
     as_json = json.dumps(info)
     as_html = get_html_template('surface_plot_template.html').safe_substitute(
-        {'INSERT_STAT_MAP_JSON_HERE': as_json})
+        {'INSERT_STAT_MAP_JSON_HERE': as_json,
+         'INSERT_PAGE_TITLE_HERE': info["title"] or "Surface plot"})
     as_html = add_js_lib(as_html, embed_js=embed_js)
     return SurfaceView(as_html)
 


Test patch:
diff --git a/nilearn/plotting/tests/test_html_connectome.py b/nilearn/plotting/tests/test_html_connectome.py
--- a/nilearn/plotting/tests/test_html_connectome.py
+++ b/nilearn/plotting/tests/test_html_connectome.py
@@ -60,11 +60,11 @@ def test_view_connectome():
     check_html(html, False, 'connectome-plot')
     html = html_connectome.view_connectome(adj, coord, '85.3%',
                                            title="SOME_TITLE")
-    check_html(html, False, 'connectome-plot')
+    check_html(html, False, 'connectome-plot', title="SOME_TITLE")
     assert "SOME_TITLE" in html.html
     html = html_connectome.view_connectome(adj, coord, '85.3%',
                                            linewidth=8.5, node_size=4.2)
-    check_html(html, False, 'connectome-plot')
+    check_html(html, False, 'connectome-plot', title="Connectome plot")
     html = html_connectome.view_connectome(
         adj, coord, '85.3%', linewidth=8.5, node_size=np.arange(len(coord)))
     check_html(html, False, 'connectome-plot')
diff --git a/nilearn/plotting/tests/test_html_stat_map.py b/nilearn/plotting/tests/test_html_stat_map.py
--- a/nilearn/plotting/tests/test_html_stat_map.py
+++ b/nilearn/plotting/tests/test_html_stat_map.py
@@ -14,12 +14,14 @@
 from ..._utils.compat import _basestring
 
 
-def _check_html(html_view):
+def _check_html(html_view, title=None):
     """ Check the presence of some expected code in the html viewer
     """
     assert isinstance(html_view, html_stat_map.StatMapView)
     assert "var brain =" in str(html_view)
     assert "overlayImg" in str(html_view)
+    if title is not None:
+        assert "<title>{}</title>".format(title) in str(html_view)
 
 
 def _simulate_img(affine=np.eye(4)):
@@ -305,9 +307,10 @@ def test_view_img():
         # Create a fake functional image by resample the template
         img = image.resample_img(mni, target_affine=3 * np.eye(3))
         html_view = html_stat_map.view_img(img)
-        _check_html(html_view)
-        html_view = html_stat_map.view_img(img, threshold='95%')
-        _check_html(html_view)
+        _check_html(html_view, title="Slice viewer")
+        html_view = html_stat_map.view_img(img, threshold='95%',
+                                           title="SOME_TITLE")
+        _check_html(html_view, title="SOME_TITLE")
         html_view = html_stat_map.view_img(img, bg_img=mni)
         _check_html(html_view)
         html_view = html_stat_map.view_img(img, bg_img=None)
diff --git a/nilearn/plotting/tests/test_html_surface.py b/nilearn/plotting/tests/test_html_surface.py
--- a/nilearn/plotting/tests/test_html_surface.py
+++ b/nilearn/plotting/tests/test_html_surface.py
@@ -92,10 +92,12 @@ def test_fill_html_template():
     info = html_surface.one_mesh_info(
         surf_map, fsaverage['pial_right'], '90%', black_bg=True,
         bg_map=fsaverage['sulc_right'])
+    info["title"] = None
     html = html_surface._fill_html_template(info, embed_js=False)
     check_html(html)
     assert "jquery.min.js" in html.html
     info = html_surface.full_brain_info(img)
+    info["title"] = None
     html = html_surface._fill_html_template(info)
     check_html(html)
     assert "* plotly.js (gl3d - minified) v1." in html.html
@@ -107,11 +109,11 @@ def test_view_surf():
     surf_map = mesh[0][:, 0]
     html = html_surface.view_surf(fsaverage['pial_right'], surf_map,
                                   fsaverage['sulc_right'], '90%')
-    check_html(html)
+    check_html(html, title="Surface plot")
     html = html_surface.view_surf(fsaverage['pial_right'], surf_map,
                                   fsaverage['sulc_right'], .3,
                                   title="SOME_TITLE")
-    check_html(html)
+    check_html(html, title="SOME_TITLE")
     assert "SOME_TITLE" in html.html
     html = html_surface.view_surf(fsaverage['pial_right'])
     check_html(html)
diff --git a/nilearn/plotting/tests/test_js_plotting_utils.py b/nilearn/plotting/tests/test_js_plotting_utils.py
--- a/nilearn/plotting/tests/test_js_plotting_utils.py
+++ b/nilearn/plotting/tests/test_js_plotting_utils.py
@@ -213,7 +213,8 @@ def test_mesh_to_plotly():
             js_plotting_utils.decode(plotly[key], '<i4'), triangles[:, i])
 
 
-def check_html(html, check_selects=True, plot_div_id='surface-plot'):
+def check_html(html, check_selects=True, plot_div_id='surface-plot',
+               title=None):
     fd, tmpfile = tempfile.mkstemp()
     try:
         os.close(fd)
@@ -237,6 +238,8 @@ def check_html(html, check_selects=True, plot_div_id='surface-plot'):
     assert (html.width, html.height) == (3, 17)
     assert 'width="3" height="17"' in html.get_iframe()
     assert 'width="33" height="37"' in html.get_iframe(33, 37)
+    if title is not None:
+        assert "<title>{}</title>".format(title) in str(html)
     if not LXML_INSTALLED:
         return
     root = etree.HTML(html.html.encode('utf-8'),