0

I have a data set which maps a tuple of phi and theta to a value which represents the strength of the signal. I want to plot these on a sphere. I simply followed a demo from matplotlib and adjusted the code to my use case.

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

fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')

u = phi
v = theta
vals =vals/vals.max()
Map = cm.coolwarm
facecolors = Map(vals[:])

x = 10 * np.outer(np.cos(u), np.sin(v))

y = 10 * np.outer(np.sin(u), np.sin(v))

z = 10 * np.outer(np.ones(np.size(u)), np.cos(v))

ax.plot_surface(x, y, z, rstride=1, cstride=1, cmap=cm.coolwarm,
                       linewidth=0, antialiased=False, facecolors=facecolors)

plt.show()

This generates an error message IndexError: index 4 is out of bounds for axis 0 with size 4. I also looked into the source code, which seems to indicate to me that facecolors isn't formatted correctly, but I'm struggling to figure out, what formatting is needed exactly.

Trenton McKinney
  • 56,955
  • 33
  • 144
  • 158
SourBitter
  • 157
  • 2
  • 11

1 Answers1

6

If your question is: "How to get rid of this IndexError?", I modified your code and now it works. plot_surface takes X,Y,Z and facecolors as 2D arrays of corresponding values on a 2D grid. Facecolors in your case weren't and this was the source of your error.

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

fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')

u, v = np.mgrid[0:np.pi:50j, 0:2*np.pi:50j]

strength = u
norm=colors.Normalize(vmin = np.min(strength),
                      vmax = np.max(strength), clip = False)

x = 10 * np.sin(u) * np.cos(v)
y = 10 * np.sin(u) * np.sin(v)
z = 10 * np.cos(u)

ax.plot_surface(x, y, z, rstride=1, cstride=1, cmap=cm.coolwarm,
                       linewidth=0, antialiased=False,
                       facecolors=cm.coolwarm(norm(strength)))

plt.show()

image

However, if your data is not on a 2D grid you are in trouble. Additionally if your grid is not regular the sphere you plot will look irregular as well. So if your question is: "How to plot a heatmap on a sphere?", there is already such a question and solution here using Basemap package produces this result:

enter image description here

Trenton McKinney
  • 56,955
  • 33
  • 144
  • 158
Noidea
  • 1,405
  • 11
  • 17