.. only:: html

    .. note::
        :class: sphx-glr-download-link-note

        Click :ref:`here <sphx_glr_download_auto_examples_01_plotting_plot_surface_projection_strategies.py>`     to download the full example code or to run this example in your browser via Binder
    .. rst-class:: sphx-glr-example-title

    .. _sphx_glr_auto_examples_01_plotting_plot_surface_projection_strategies.py:

Technical point: Illustration of the volume to surface sampling schemes
=======================================================================

In nilearn, :func:`nilearn.surface.vol_to_surf` allows us to measure values of
a 3d volume at the nodes of a cortical mesh, transforming it into surface data.
This data can then be plotted with :func:`nilearn.plotting.plot_surf_stat_map`
for example.

This script shows, on a toy example, where samples are drawn around each mesh
vertex. Image values are interpolated at each sample location, then these
samples are averaged to produce a value for the vertex.

Three strategies are available to choose sample locations: they can be spread
between corresponding nodes when we have two nested surfaces (e.g. a white
matter and a pial surface), along the normal at each node, or inside a ball
around each node. Don't worry too much about choosing one or the other: they
take a similar amount of time and give almost identical results for most
images. If you do have both pial and white matter surfaces (as for the
fsaverage and fsaverage5 surfaces fetched by `nilearn.datasets`) we recommend
passing both to `vol_to_surf`.


.. code-block:: default


    import numpy as np

    import matplotlib
    from matplotlib import pyplot as plt
    from mpl_toolkits.mplot3d import Axes3D

    from nilearn.surface import surface
    from nilearn.plotting import show









Build a mesh (of a cylinder)
#####################################################################


.. code-block:: default


    N_Z = 5
    N_T = 10
    u, v = np.mgrid[:N_T, :N_Z]
    triangulation = matplotlib.tri.Triangulation(u.flatten(), v.flatten())
    angles = u.flatten() * 2 * np.pi / N_T
    x, y = np.cos(angles), np.sin(angles)
    z = v.flatten() * 2 / N_Z

    mesh = [np.asarray([x, y, z]).T, triangulation.triangles]
    inner_mesh = [[.7, .7, 1.] * mesh[0], triangulation.triangles]









Get the locations from which vol_to_surf would draw its samples
########################################################################


.. code-block:: default


    nested_sample_points = surface._sample_locations_between_surfaces(
        mesh, inner_mesh, np.eye(4))

    line_sample_points = surface._line_sample_locations(
        mesh, np.eye(4), segment_half_width=.2, n_points=6)

    ball_sample_points = surface._ball_sample_locations(
        mesh, np.eye(4), ball_radius=.15, n_points=20)









Plot the mesh and the sample locations
#####################################################################


.. code-block:: default


    fig = plt.figure()
    ax = plt.subplot(projection='3d')
    ax.view_init(67, -42)
    ax.plot_trisurf(x, y, z, triangles=triangulation.triangles, alpha=.6)
    ax.plot_trisurf(*inner_mesh[0].T, triangles=triangulation.triangles)
    ax.scatter(*nested_sample_points.T, color='r')

    for sample_points in [line_sample_points, ball_sample_points]:
        fig = plt.figure()
        ax = plt.subplot(projection='3d')
        ax.view_init(67, -42)
        ax.plot_trisurf(x, y, z, triangles=triangulation.triangles)
        ax.scatter(*sample_points.T, color='r')




.. rst-class:: sphx-glr-horizontal


    *

      .. image:: /auto_examples/01_plotting/images/sphx_glr_plot_surface_projection_strategies_001.png
          :alt: plot surface projection strategies
          :class: sphx-glr-multi-img

    *

      .. image:: /auto_examples/01_plotting/images/sphx_glr_plot_surface_projection_strategies_002.png
          :alt: plot surface projection strategies
          :class: sphx-glr-multi-img

    *

      .. image:: /auto_examples/01_plotting/images/sphx_glr_plot_surface_projection_strategies_003.png
          :alt: plot surface projection strategies
          :class: sphx-glr-multi-img





Adjust the sample locations
#####################################################################
 For "line" and nested surfaces, the depth parameter allows ajusting the
 position of samples along the line


.. code-block:: default


    nested_sample_points = surface._sample_locations_between_surfaces(
        mesh, inner_mesh, np.eye(4), depth=[-.5, 0., .8, 1., 1.2])
    fig = plt.figure()
    ax = plt.subplot(projection='3d')
    ax.view_init(67, -42)
    ax.plot_trisurf(x, y, z, triangles=triangulation.triangles, alpha=.6)
    ax.plot_trisurf(*inner_mesh[0].T, triangles=triangulation.triangles)
    ax.scatter(*nested_sample_points.T, color='r')

    show()



.. image:: /auto_examples/01_plotting/images/sphx_glr_plot_surface_projection_strategies_004.png
    :alt: plot surface projection strategies
    :class: sphx-glr-single-img






.. rst-class:: sphx-glr-timing

   **Total running time of the script:** ( 0 minutes  0.703 seconds)


.. _sphx_glr_download_auto_examples_01_plotting_plot_surface_projection_strategies.py:


.. only :: html

 .. container:: sphx-glr-footer
    :class: sphx-glr-footer-example


  .. container:: binder-badge

    .. image:: images/binder_badge_logo.svg
      :target: https://mybinder.org/v2/gh/nilearn/nilearn.github.io/master?filepath=examples/auto_examples/01_plotting/plot_surface_projection_strategies.ipynb
      :alt: Launch binder
      :width: 150 px


  .. container:: sphx-glr-download sphx-glr-download-python

     :download:`Download Python source code: plot_surface_projection_strategies.py <plot_surface_projection_strategies.py>`



  .. container:: sphx-glr-download sphx-glr-download-jupyter

     :download:`Download Jupyter notebook: plot_surface_projection_strategies.ipynb <plot_surface_projection_strategies.ipynb>`


.. only:: html

 .. rst-class:: sphx-glr-signature

    `Gallery generated by Sphinx-Gallery <https://sphinx-gallery.github.io>`_