The following code produces a circular pattern:
import numpy as np
import matplotlib.pyplot as mp
def sphere_depth(x, y, depth, radius):
squ = x**2 + y**2
rsqu = radius**2
squ[squ > rsqu] = rsqu
res = np.sqrt(rsqu - squ)
res -= (radius - depth)
res[res < 0.] = 0.
return res
y_pix = x_pix = 100.
c_steps = 10
x, y = np.mgrid[0:x_pix:1, 0:y_pix:1]
z = sphere_depth(x - x_pix / 2, y - y_pix / 2, 5., 100.)
lvls = np.linspace(z.min(), z.max(), c_steps)
mp.close(1)
fig = mp.figure(1)
mp.axes([0, 0, 1, 1], frameon=False)
mp.contourf(x, y, z, cmap=mp.cm.gray, levels=lvls)
mp.axis('off')
mp.savefig("test.png")
The colormap is set to "gray" and I expect that the minimum value corresponds to black and the maximum value to white. While the later is true, the former doesn't hold for this example. The lowest value is rather dark gray. This can be adjusted when increasing c_steps
, but I need to have a very coarse grained gray color map. Thanks for any ideas how to start with a black color and end with white.
contourf
behaves a bit differently thanimshow
orpcolormesh
in this case. It's deliberate for consistency withcontour
, and due to the way the levels are defined.The color for each level range is defined by the midpoint of that range. (Also, your center contour isn't actually completely white, but it's visually identical to it.)
To specify that you want the first interval filled with "pure" black, set
vmin=mean(lvls[:1])
in your example.As an example, based on your excellent example in your question:
Just for comparison, here's the image from your original example:
It's subtle, but the first one has "pure" black at the edges, and the second one doesn't.