Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit e4697e7

Browse files
author
apodemus
committed
add Annulus patch
1 parent bc97294 commit e4697e7

1 file changed

Lines changed: 96 additions & 2 deletions

File tree

lib/matplotlib/patches.py

Lines changed: 96 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1552,9 +1552,103 @@ def get_angle(self):
15521552
angle = property(get_angle, set_angle)
15531553

15541554

1555-
class Circle(Ellipse):
1556-
"""A circle patch."""
15571555

1556+
class Annulus(Patch):
1557+
"""
1558+
An elliptical annulus.
1559+
"""
1560+
1561+
def __str__(self):
1562+
if self.a == self.b:
1563+
fmt = "Annulus(xy=(%s, %s), r=%s, width=%s, angle=%s)"
1564+
pars = (self.center[0], self.center[1],
1565+
self.a, self.width, self.angle)
1566+
else:
1567+
fmt = "Annulus(xy=(%s, %s), a=%s, b=%s, width=%s, angle=%s)"
1568+
pars = (self.center[0], self.center[1],
1569+
self.a, self.b, self.width, self.angle)
1570+
return fmt % pars
1571+
1572+
@docstring.dedent_interpd
1573+
def __init__(self, xy, r, width, angle=0.0, **kwargs):
1574+
"""
1575+
*xy*
1576+
center of annulus
1577+
1578+
*r*
1579+
if float:
1580+
radius of the outer circle
1581+
if array-like of size 2:
1582+
semi-major and -minor axes of outer ellipse
1583+
1584+
*width*
1585+
width of the annulus
1586+
1587+
*angle*
1588+
rotation in degrees (anti-clockwise)
1589+
1590+
Valid kwargs are:
1591+
%(Patch)s
1592+
"""
1593+
Patch.__init__(self, **kwargs)
1594+
1595+
if np.size(r) == 2:
1596+
self.a, self.b = r
1597+
elif np.size(r) == 1:
1598+
self.a = self.b = float(r)
1599+
else:
1600+
raise ValueError(
1601+
'r parameter should be either float, or sequence of size 2')
1602+
1603+
if min(self.a, self.b) <= width:
1604+
raise ValueError(
1605+
'Width should be smaller than semi-minor axis')
1606+
1607+
self.center = xy
1608+
self.width = width
1609+
self.angle = angle
1610+
self._path = None
1611+
# Note: This cannot be calculated until this is added to an Axes
1612+
self._patch_transform = transforms.IdentityTransform()
1613+
1614+
def _transform_verts(self, verts, a, b):
1615+
center = (self.convert_xunits(self.center[0]),
1616+
self.convert_yunits(self.center[1]))
1617+
a = self.convert_xunits(a)
1618+
b = self.convert_yunits(b)
1619+
tr = transforms.Affine2D() \
1620+
.scale(a, b) \
1621+
.rotate_deg(self.angle) \
1622+
.translate(*center)
1623+
1624+
return tr.transform(verts)
1625+
1626+
def _recompute_path(self):
1627+
1628+
# circular arc
1629+
arc = Path.arc(0, 360)
1630+
1631+
# annulus needs to draw the outer ring
1632+
# followed by a reversed and scaled inner ring
1633+
a, b, w = self.a, self.b, self.width
1634+
v1 = self._transform_verts(arc.vertices, a, b)
1635+
v2 = self._transform_verts(arc.vertices[::-1], a - w, b - w)
1636+
v = np.vstack([v1, v2, v1[0, :], (0, 0)])
1637+
c = np.hstack([arc.codes, arc.codes, Path.MOVETO, Path.CLOSEPOLY])
1638+
c[len(arc.codes)] = Path.MOVETO
1639+
1640+
self._path = Path(v, c)
1641+
1642+
def get_path(self):
1643+
if self._path is None:
1644+
self._recompute_path()
1645+
return self._path
1646+
1647+
1648+
class Circle(Ellipse):
1649+
"""
1650+
A circle patch.
1651+
"""
15581652
def __str__(self):
15591653
pars = self.center[0], self.center[1], self.radius
15601654
fmt = "Circle(xy=(%g, %g), radius=%g)"

0 commit comments

Comments
 (0)