It would be great though if the docstring was more help:
This is a typical problem we encounter in documenting pylab functions.
As you know, pylab is basically a pass-though interface to the
underlying matplotlib objects. In this case pylab.arrow calls
matplotlib.axes.Axes.arrow which creates a
matplotlib.patches.FancyArrow instance. If we're not careful (and in
this case we were not) it is easy to leave an un- or under-documented
pylab function docstring. I copied the relevant documentation from
the FancyArrow class into the Axes.arrow docstring, which pylab.arrow
reuses. It now reads:
ARROW(x, y, dx, dy, **kwargs)
Draws arrow on specified axis from (x,y) to (x+dx,y+dy).
keyword arguments **kwargs:
* length_includes_head: True if head is counted in
calculating the length.
* shape: ['full', 'left', 'right']
* overhang: distance that the arrow is swept back (0
overhang means triangular shape).
* head_starts_at_zero: if True, the head starts being drawn
at coordinate 0 instead of ending at coordinate 0.
Sometimes with matplotlib it's not RTFM, but RTFSC (read the *&$%&U
source code). I don't mean this glibly, since we want the user
experience to "just work"(TM) but I do mention it because it is one of
the benefits of using open-source software. If you are using a pylab
function like pylab.arrow and do not understand how to use it, you
have the option of grokking the source code for pylab.arrow. Here it
# This function was autogenerated by boilerplate.py. Do not edit as
# changes will be lost
def arrow(*args, **kwargs):
# allow callers to override the hold state by passing hold=True|False
b = ishold()
h = popd(kwargs, 'hold', None)
if h is not None:
ret = gca().arrow(*args, **kwargs)
if Axes.arrow.__doc__ is not None:
arrow.__doc__ = _shift_string(Axes.arrow.__doc__) + """
Addition kwargs: hold = [True|False] overrides default hold state"""
As the comment above indicates, most of this is boilerplate and is in
fact auto-generated. The crucial part is
ret = gca().arrow(*args, **kwargs)
[note we are using pass-through arguments and keyword arguments which
is why our docstrings sometimes suck]. If you know just enough
matplotlib internals, you'll know that gca ("get current axes")
returns the current matplotlib.axes.Axes object, and thus the relevant
method is Axes.arrow. Opening up axes.py, and searching for 'def
arrow' you'll find
def arrow(self, x, y, dx, dy, **kwargs):
a = FancyArrow(x, y, dx, dy, **kwargs)
So all Axes.arrow does is create a FancyArrow, add it to the Axes, and
returns it. If you go to the top of the file axes.py, you'll find an
import line indicating where FancyArrow comes from
from patches import Patch, Rectangle, ..., FancyArrow, ...
so FancyArrow is coming from matplotlib.patches. We're almost there.
Open up patches.py, search for 'class FancyArrow', and you arrive at
the real player:
"""Like Arrow, but lets you set head width and head height
def __init__(self, x, y, dx, dy, width=0.001,
head_width=None, head_length=None, shape='full',
"""Returns a new Arrow.
length_includes_head: True if head is counted in calculating
shape: ['full', 'left', 'right']
overhang: distance that the arrow is swept back (0 overhang means
head_starts_at_zero: if True, the head starts being drawn at
coordinate 0 instead of ending at coordinate 0. """ if
head_width is None: head_width = 3 * width
That's what I did to answer your question (not knowing anything much
about how Rob Knight worked his fancy arrow magic). I don't mention
this to discourage you from asking these kinds of questions: quite the
opposite since your question helps us fix the doc strings and user
interface. But I wanted to describe the approach that matplotlib
developers, none of whom have an intimate understanding of all of the
parts of this code, take when trying to understand how things (should)