Demetri Pananos
Demetri Pananos

Reputation: 7404

How can I visualize a function value in 3d?

Suppose I have some function, which maps 3 coordinates (x,y,z) to some real number.

How can I visualize the function values on a surface like a sphere?

Ideally, I would map the function's value to a color, and then color the sphere accordingly.

Here is my code to generate a sphere:

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

%matplotlib inline

fig = plt.figure()
ax = fig.gca(projection='3d')
ax.set_aspect("equal")

u = np.linspace(0, 2 * np.pi, 250)
v = np.linspace(0, np.pi, 250)

x =  np.outer(np.cos(u), np.sin(v))
y =  np.outer(np.sin(u), np.sin(v))
z =  np.outer(np.ones(np.size(u)), np.cos(v))
ax.plot_surface(x, y, z, color="w")

How can I edit my code to color it according to some function F(x,y,z)

Upvotes: 1

Views: 145

Answers (2)

ImportanceOfBeingErnest
ImportanceOfBeingErnest

Reputation: 339170

Matplotlib allows to use the facecolor argument to plot_surface to set the color of each polygon in the surface. The argument needs to have the same shape as the input arrays and must consist of valid colors. A way to obtain those colors is a colormap.

Also see this question for details.

Below is a working example code.

import matplotlib.pyplot as plt
from matplotlib import cm
from mpl_toolkits.mplot3d import Axes3D
import numpy as np


u = np.linspace(0, 2 * np.pi, 180)
v = np.linspace(0, np.pi, 90)

x =  np.outer(np.cos(u), np.sin(v))
y =  np.outer(np.sin(u), np.sin(v))
z =  np.outer(np.ones(np.size(u)), np.cos(v))

F = np.sin(x)*y + z
F = (F-F.min())/(F-F.min()).max()
#Set colours and render
fig = plt.figure(figsize=(8, 8))
fig.subplots_adjust(top=1, bottom=0, left=0, right=1)
ax = fig.add_subplot(111, projection='3d')
#use facecolors argument, provide array of same shape as z
# cm.<cmapname>() allows to get rgba color from array.
# array must be normalized between 0 and 1
ax.plot_surface(
    x,y,z,  rstride=1, cstride=1, facecolors=cm.jet(F), alpha=0.9, linewidth=0.9) 
ax.set_xlim([-1,1])
ax.set_ylim([-1,1])
ax.set_zlim([-1,1])
ax.set_aspect("equal")

plt.savefig(__file__+".png")
plt.show()

enter image description here

Upvotes: 1

Pierre de Buyl
Pierre de Buyl

Reputation: 7293

The documentation for surface_plot lists the option facecolors. There is a example that alternates between two colors but you can pass any matplotlib color, including and array of RGB values.

You need to do the mapping yourself from x, y, z to F(x, y, z) to "color", then convert F to a RGB value.

facecolors = plt.cm.Red(F(x,y,z))

should do.

See: http://matplotlib.org/mpl_toolkits/mplot3d/tutorial.html#surface-plots

Upvotes: 1

Related Questions