3

Completely new to the site and to rather new to Python as well, so help and hints appreciated.

I've got some data of (x,y) forming several nearly circle-shaped curves around a center. But for the sake of the example, I just created some (x,y) forming circles.

Now, I want to plot those and fill the space between those Polygons with color according to, let's say some (z) values obtained by a function so that every "ring" has its own shade.

Here is, what I've figured out by now.

import matplotlib.pyplot as plt
import numpy as np
from math import sin, cos
from matplotlib.patches import Polygon
from matplotlib.collections import PatchCollection

r = np.array([0.1, 0.2, 0.3, 0.4, 0.5 ,0.6, 0.7, 0.8, 0.9, 1.0])

fig, ax = plt.subplots(1)
ax.set_xlim([-1.1, 1.1])
ax.set_ylim([-1.1, 1.1])

x=[]
y=[]
patches = []
colors=np.array([0.9,0.8, 0.1, 0.1, 0.1, 0.4, 0.2,0.8,0.1, 0.9])




for radius in r:
    for phi in np.linspace(0, 360, 200, endpoint=True):
        x.append(radius*cos(np.deg2rad(phi)))
        y.append(radius*sin(np.deg2rad(phi)))
    points = np.vstack([x,y]).T
    polygon = Polygon(points,False)
    patches.append(polygon)

p = PatchCollection(patches, cmap="Blues" )
p.set_array(colors)

ax.add_collection(p)

plt.show()

Giving me: rings

  1. I wonder why there is this horizontal line on the right side, this makes me believe I dont understand what my code does.
  2. It has not done the trick as all of the ring-segments have the same color instead of having different shades.

I thought the p.set_array(colors) would do the trick as I have found it in the example even though I have no idea what set_array() does as the documentation does not give away a lot.

If there is a completely different approach, feel free to tell me anyway.

Marsl
  • 285
  • 1
  • 10

1 Answers1

1

You need to add the circles from the biggest to the smallest, so they won't run over each other.

I used plot a circle with pyplot and http://matplotlib.org/users/colormaps.html

import matplotlib.pyplot as plt
import numpy as np
import matplotlib.cm as cm

r = np.arange(1, 0, -0.1)

fig, ax = plt.subplots(1)
ax.set_xlim([-1.1, 1.1])
ax.set_ylim([-1.1, 1.1])

color_vec = np.array([0.9, 0.8, 0.1, 0.1, 0.1, 0.4, 0.2, 0.8, 0.1, 0.9])
colors = cm.get_cmap("Blues")(color_vec)

for i, radius in enumerate(r):
    circle = plt.Circle((0, 0), radius, color=colors[i])
    ax.add_artist(circle)

plt.show()

if you need the patches:

import matplotlib.pyplot as plt
import numpy as np
from matplotlib.patches import Polygon
from matplotlib.collections import PatchCollection

r = np.arange(1, 0, -0.1)

fig, ax = plt.subplots(1)
ax.set_xlim([-1.1, 1.1])
ax.set_ylim([-1.1, 1.1])
patches = []

colors = np.array([0.9, 0.8, 0.1, 0.1, 0.1, 0.4, 0.2, 0.8, 0.1, 0.9])

phi = np.linspace(0, 2*np.pi, 200)
for radius in r:
    x = radius * np.cos(phi)
    y = radius * np.sin(phi)
    points = np.vstack([x, y]).T
    polygon = Polygon(points, False)
    patches.append(polygon)

p = PatchCollection(patches, cmap="Blues")
p.set_array(colors)

ax.add_collection(p)

plt.show()
Community
  • 1
  • 1
Ophir Carmi
  • 2,701
  • 1
  • 23
  • 42
  • Yes, I need the patches and i finally figured out myself that overlap was the problem. However, if i simply reverse the radius array in my own code by r=r[::-1], it doesn't work for me, even though it should be technically the same thing as you did there. How to determine the order of drawing in a PatchCollection (I found zorder for single patches already) – Marsl Aug 29 '16 at 19:47