How to make 3D-surface plots in Python
Plotly Studio: Transform any dataset into an interactive data application in minutes with AI. Sign up for early access now.
Topographical 3D Surface Plot¶In [1]:
import plotly.graph_objects as go import pandas as pd # Read data from a csv z_data = pd.read_csv('https://raw.githubusercontent.com/plotly/datasets/master/api_docs/mt_bruno_elevation.csv') fig = go.Figure(data=[go.Surface(z=z_data.values)]) fig.update_layout(title=dict(text='Mt Bruno Elevation'), autosize=False, width=500, height=500, margin=dict(l=65, r=50, b=65, t=90)) fig.show()Passing x and y data to 3D Surface Plot¶
If you do not specify x
and y
coordinates, integer indices are used for the x
and y
axis. You can also pass x
and y
values to go.Surface
.
In [2]:
import plotly.graph_objects as go import pandas as pd import numpy as np # Read data from a csv z_data = pd.read_csv('https://raw.githubusercontent.com/plotly/datasets/master/api_docs/mt_bruno_elevation.csv') z = z_data.values sh_0, sh_1 = z.shape x, y = np.linspace(0, 1, sh_0), np.linspace(0, 1, sh_1) fig = go.Figure(data=[go.Surface(z=z, x=x, y=y)]) fig.update_layout(title=dict(text='Mt Bruno Elevation'), autosize=False, width=500, height=500, margin=dict(l=65, r=50, b=65, t=90)) fig.show()Surface Plot With Contours¶
Display and customize contour data for each axis using the contours
attribute (reference).
In [3]:
import plotly.graph_objects as go import pandas as pd # Read data from a csv z_data = pd.read_csv('https://raw.githubusercontent.com/plotly/datasets/master/api_docs/mt_bruno_elevation.csv') fig = go.Figure(data=[go.Surface(z=z_data.values)]) fig.update_traces(contours_z=dict(show=True, usecolormap=True, highlightcolor="limegreen", project_z=True)) fig.update_layout(title=dict(text='Mt Bruno Elevation'), autosize=False, scene_camera_eye=dict(x=1.87, y=0.88, z=-0.64), width=500, height=500, margin=dict(l=65, r=50, b=65, t=90) ) fig.show()Configure Surface Contour Levels¶
This example shows how to slice the surface graph on the desired position for each of x, y and z axis. contours.x.start sets the starting contour level value, end
sets the end of it, and size
sets the step between each contour level.
In [4]:
import plotly.graph_objects as go fig = go.Figure(go.Surface( contours = { "x": {"show": True, "start": 1.5, "end": 2, "size": 0.04, "color":"white"}, "z": {"show": True, "start": 0.5, "end": 0.8, "size": 0.05} }, x = [1,2,3,4,5], y = [1,2,3,4,5], z = [ [0, 1, 0, 1, 0], [1, 0, 1, 0, 1], [0, 1, 0, 1, 0], [1, 0, 1, 0, 1], [0, 1, 0, 1, 0] ])) fig.update_layout( scene = { "xaxis": {"nticks": 20}, "zaxis": {"nticks": 4}, 'camera_eye': {"x": 0, "y": -1, "z": 0.5}, "aspectratio": {"x": 1, "y": 1, "z": 0.2} }) fig.show()Multiple 3D Surface Plots¶
In [5]:
import plotly.graph_objects as go import numpy as np z1 = np.array([ [8.83,8.89,8.81,8.87,8.9,8.87], [8.89,8.94,8.85,8.94,8.96,8.92], [8.84,8.9,8.82,8.92,8.93,8.91], [8.79,8.85,8.79,8.9,8.94,8.92], [8.79,8.88,8.81,8.9,8.95,8.92], [8.8,8.82,8.78,8.91,8.94,8.92], [8.75,8.78,8.77,8.91,8.95,8.92], [8.8,8.8,8.77,8.91,8.95,8.94], [8.74,8.81,8.76,8.93,8.98,8.99], [8.89,8.99,8.92,9.1,9.13,9.11], [8.97,8.97,8.91,9.09,9.11,9.11], [9.04,9.08,9.05,9.25,9.28,9.27], [9,9.01,9,9.2,9.23,9.2], [8.99,8.99,8.98,9.18,9.2,9.19], [8.93,8.97,8.97,9.18,9.2,9.18] ]) z2 = z1 + 1 z3 = z1 - 1 fig = go.Figure(data=[ go.Surface(z=z1), go.Surface(z=z2, showscale=False, opacity=0.9), go.Surface(z=z3, showscale=False, opacity=0.9) ]) fig.show()Setting the Surface Color¶
You can use the surfacecolor
attribute to define the color of the surface of your figure. In this example, the surface color represents the distance from the origin, rather than the default, which is the z
value.
In [6]:
import plotly.graph_objects as go from plotly.subplots import make_subplots # Equation of ring cyclide # see https://en.wikipedia.org/wiki/Dupin_cyclide import numpy as np a, b, d = 1.32, 1., 0.8 c = a**2 - b**2 u, v = np.mgrid[0:2*np.pi:100j, 0:2*np.pi:100j] x = (d * (c - a * np.cos(u) * np.cos(v)) + b**2 * np.cos(u)) / (a - c * np.cos(u) * np.cos(v)) y = b * np.sin(u) * (a - d*np.cos(v)) / (a - c * np.cos(u) * np.cos(v)) z = b * np.sin(v) * (c*np.cos(u) - d) / (a - c * np.cos(u) * np.cos(v)) fig = make_subplots(rows=1, cols=2, specs=[[{'is_3d': True}, {'is_3d': True}]], subplot_titles=['Color corresponds to z', 'Color corresponds to distance to origin'], ) fig.add_trace(go.Surface(x=x, y=y, z=z, colorbar_x=-0.07), 1, 1) fig.add_trace(go.Surface(x=x, y=y, z=z, surfacecolor=x**2 + y**2 + z**2), 1, 2) fig.update_layout(title_text="Ring cyclide") fig.show()What About Dash?¶
Dash is an open-source framework for building analytical applications, with no Javascript required, and it is tightly integrated with the Plotly graphing library.
Learn about how to install Dash at https://dash.plot.ly/installation.
Everywhere in this page that you see fig.show()
, you can display the same figure in a Dash application by passing it to the figure
argument of the Graph
component from the built-in dash_core_components
package like this:
import plotly.graph_objects as go # or plotly.express as px fig = go.Figure() # or any Plotly Express function e.g. px.bar(...) # fig.add_trace( ... ) # fig.update_layout( ... ) from dash import Dash, dcc, html app = Dash() app.layout = html.Div([ dcc.Graph(figure=fig) ]) app.run(debug=True, use_reloader=False) # Turn off reloader if inside Jupyter
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4