trying to get screen coordinates for bars

Hi, I'm trying to generate a barplot and subsequently dumping it to a
PNG file and making an HTML imagemap out of it. I've pasted my code
below.

The problem is that the coordinates I need to supply for the imagemap
don't seem to be correct.

I'm getting the screen coordinates using:

coords = []
for rectangle in b:

    vertices = rectangle.get_verts()

    top_left = get_top_left(vertices)
    lower_right = get_lower_right(vertices)

    trans = rectangle.get_transform()
    top_left = trans.xy_tup(top_left)
    lower_right = trans.xy_tup(lower_right)

    coords.append( (top_left, lower_right) )

However when I use these coordinates as the top left and lower right
coordinates of each bar in the imagemap, they don't line up properly
with the regions of the bars. The top left coordinate is always a bit
below the top edge of the bar and shifted to the left.

[ In the code below I transform the screen coordinates from the plot to
the HTML coordinate system (0,0 is the top left) ]

The code below, when run, generates an HTML file called junk.html. If
you view it in a browser and look at the status line it will be apparent
that the 5th bar doesn't get any region assigned to it.

Any pointers to a solution would be much appreciated.

Thanks,

--8<--------------------------------------------------------

import random, sys
from pylab import *
from matplotlib.figure import Figure
from matplotlib.patches import Polygon
from matplotlib.backends.backend_agg import FigureCanvasAgg

def get_top_left(v):
    return v[1]

def get_lower_right(v):
    return v[3]
    
obs = [random.random() for x in range(0,5)]
x = range(0,5)

imgwidth = None
imgheight = None

fig = Figure(figsize=(4,4))
ax = fig.add_subplot(1,1,1 )
b = ax.bar(x, obs)

canvas = FigureCanvasAgg(fig)
canvas.print_figure("junk.png", dpi=100)
imgwidth = fig.get_figwidth() * 100
imgheight = fig.get_figheight() * 100

# get coords for the bars of this plot
coords = []
for rectangle in b:

    vertices = rectangle.get_verts()

    top_left = get_top_left(vertices)
    lower_right = get_lower_right(vertices)

    trans = rectangle.get_transform()
    top_left = trans.xy_tup(top_left)
    lower_right = trans.xy_tup(lower_right)

    print top_left, " <-> ", lower_right

    coords.append( (top_left, lower_right) )

f = open('junk.html', 'w')
f.write("""
<html>
<body>
<img src="junk.png" ismap usemap='#points' width="%d" height="%d">
<map name="points"> """ % (imgwidth, imgheight))

cnt = 1
for tl, lr in coords:
    f.write("""
    <area shape="rect" coords="%d,%d %d,%d" href="http://junk%d.com", alt="Cell %d">\n""" % \
            (tl[0], imgheight-tl[1], lr[0], imgheight-lr[1], cnt, cnt))
    cnt += 1
f.write("""</map></body></html>""")
f.close()

···

-------------------------------------------------------------------
Rajarshi Guha <rguha@...139...>
GPG Fingerprint: 0CCA 8EE2 2EEB 25E2 AB04 06F7 1BB9 E634 9B87 56EE
-------------------------------------------------------------------
"A fractal is by definition a set for which the Hausdorff Besicovitch
dimension strictly exceeds the topological dimension."
-- Mandelbrot, "The Fractal Geometry of Nature"

The trick is that you want the image coordinates in *screen* coordinates, not
printer coordinates. The image coordinates will be screen coordinates if you
obtain the imgheight/imgwidth by multipying the figure height/width by 80,
not 100. The DPI won't matter if you are manually setting the height/width
in the img tag. Alternatively, you could set dpi=80 and skip the
imgheight/imgwidth entries altogether (and reformat the vertices correctly
for the imagemap input without using the imgheight...). If for some reason
you want the displayed image to be larger/smaller than the selected size
(here 4inx4in), multiply the matplotlib coordinates by the ratio of the
image scaling factor and 80. Ie in your example, multiply the coordinates by
100./80. to obtain the correct coordinates for the image size that you have
chosen (here 400pix/400pix instead of the 'natural' size of 320x320 based
upon the PNG being a 4"x4" image).

Matt

Rajarshi Guha-3 wrote:

···

Hi, I'm trying to generate a barplot and subsequently dumping it to a
PNG file and making an HTML imagemap out of it. I've pasted my code
below.

The problem is that the coordinates I need to supply for the imagemap
don't seem to be correct.

I'm getting the screen coordinates using:

coords =
for rectangle in b:

    vertices = rectangle.get_verts()

    top_left = get_top_left(vertices)
    lower_right = get_lower_right(vertices)

    trans = rectangle.get_transform()
    top_left = trans.xy_tup(top_left)
    lower_right = trans.xy_tup(lower_right)

    coords.append( (top_left, lower_right) )

--
View this message in context: http://www.nabble.com/trying-to-get-screen-coordinates-for-bars-tf3280553.html#a9150522
Sent from the matplotlib - users mailing list archive at Nabble.com.