Matplotlib 3D plot use colormap

frankgut picture frankgut · Aug 13, 2015 · Viewed 10.3k times · Source

I am trying to use ax.scatter to plot a 3D scattering plot. I've read the data from a fits file and stored data from three column into x,y,z. And I have made sure x,y,z data are the same size. z has been normolized between 0 and 1.

import numpy as np
import matplotlib
from matplotlib import pylab,mlab,pyplot,cm
plt = pyplot
import pyfits as pf
from mpl_toolkits.mplot3d import Axes3D
import fitsio

data = fitsio.read("xxx.fits")

x=data["x"]
y=data["y"]
z=data["z"]
z = (z-np.nanmin(z)) /(np.nanmax(z) - np.nanmin(z))

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

cmap=cm.ScalarMappable(norm=z, cmap=plt.get_cmap('hot'))
ax.scatter(x,y,z,zdir=u'z',cmap=cmap)

ax.set_xlabel('x')
ax.set_ylabel('y')
ax.set_zlabel('z')
plt.show()

What I am trying to achieve is use color to indicate the of size of z. Like higher value of z will get darker color. But I am keep getting a plot without the colormap I want, they are all the same default blue color. What did I do wrong? Thanks.

Answer

tmdavison picture tmdavison · Aug 13, 2015

You can use the c keyword in the scatter command, to tell it how to color the points.

You don't need to set zdir, as that is for when you are plotting a 2d set

As @Lenford pointed out, you can use cmap='hot' in this case too, since you have already normalized your data.

I've modified your example to use some random data rather than your fits file.

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

x = np.random.rand(100)
y = np.random.rand(100)
z = np.random.rand(100)

z = (z-np.nanmin(z)) /(np.nanmax(z) - np.nanmin(z))

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

ax.scatter(x,y,z,cmap='hot',c=z)

ax.set_xlabel('x')
ax.set_ylabel('y')
ax.set_zlabel('z')
plt.show()

enter image description here