Currently imsave (implemented in the image.py file) only deals with greyscale single-plane images, i.e. 2D arrays, and in my defence, it's in the docstring, so I wouldn't call it a bug. However, it's a reasonable expectation that it support rgb and rgba since it is basically a thin wrapper around figimage.

My first try at this was to change the line

fig = Figure(figsize=arr.shape[::-1], dpi=1, frameon=False)

to

fig = Figure(figsize=(arr.shape[1],arr.shape[0]), dpi=1, frameon=False)

since we just want to take the first two shape values.

(note figsize=arr.shape[:2][::-1] also works)

This may be all you need. My tests (in the attached test.py) appear to work. However, I don't think it's what you want. By default, figimage even expects NxMx3 and NxMx4 arrays to be float arrays nominally ranging from 0-1. What you probably want is a raw RGB mapping where pixel planes are unsigned 8 bit values. I thought calling figimage with a norm=no_norm(0,255) instance achieved this but it doesn't work as I expect. So the first question is, what is the expected behaviour here, and a follow-up is does anyone here understand how to do the colour mapping to achieve it?

Gary

Stéfan van der Walt wrote:
Hey all,

2009/2/10 Andrew Straw <straw...@astraw.com>:
Gary Ruben wrote:
Hi Andrew,

I don't have commit access. If you would check it in, that would be great.
Committed to the trunk in r6899... Thanks!

And, sheesh, SourceForge's SVN server is slooow today for me, although
it seems to have finally improved.

While trying to write a matplotlib plugin for scikits.image, we
noticed that `imsave` isn't currently working (that goes for the one
in Ubuntu [0.99 I think] as well as the latest SVN):

Traceback (most recent call last):
  File "test_imsave.py", line 6, in <module>
    plt.imsave('test.jpg', img)
  File "/Users/stefan/lib/python2.6/site-packages/matplotlib/pyplot.py",
line 1412, in imsave
    return _imsave(*args, **kwargs)
  File "/Users/stefan/lib/python2.6/site-packages/matplotlib/image.py",
line 1025, in imsave
    fig = Figure(figsize=arr.shape[::-1], dpi=1, frameon=False)
  File "/Users/stefan/lib/python2.6/site-packages/matplotlib/figure.py",
line 180, in __init__
    self.bbox_inches = Bbox.from_bounds(0, 0, *figsize)
TypeError: from_bounds() takes exactly 4 arguments (5 given)

The commands needed to reproduce the error are:

import matplotlib.pyplot as plt
import numpy as np

img = np.ones((50, 50, 3), dtype=np.uint8)

plt.imsave('test.jpg', img)

Regards
Stéfan

def imsave(fname, arr, vmin=None, vmax=None, cmap=None, format=None, 
origin=None):
    """
    Saves a 2D :class:`numpy.array` as an image with one pixel per element.
    The output formats available depend on the backend being used.

    Arguments:
      *fname*:
        A string containing a path to a filename, or a Python file-like object.
        If *format* is *None* and *fname* is a string, the output
        format is deduced from the extension of the filename.
      *arr*:
        A 2D array.
    Keyword arguments:
      *vmin*/*vmax*: [ None | scalar ]
        *vmin* and *vmax* set the color scaling for the image by fixing the
        values that map to the colormap color limits. If either *vmin* or *vmax*
        is None, that limit is determined from the *arr* min/max value.
      *cmap*:
        cmap is a colors.Colormap instance, eg cm.jet.
        If None, default to the rc image.cmap value.
      *format*:
        One of the file extensions supported by the active
        backend.  Most backends support png, pdf, ps, eps and svg.
      *origin*
        [ 'upper' | 'lower' ] Indicates where the [0,0] index of
        the array is in the upper left or lower left corner of
        the axes. Defaults to the rc image.origin value.
    """
    from matplotlib.backends.backend_agg import FigureCanvasAgg as FigureCanvas
    from matplotlib.figure import Figure

    fig = Figure(figsize=arr.shape[::-1], dpi=1, frameon=False)
    canvas = FigureCanvas(fig)
    fig.figimage(arr, cmap=cmap, vmin=vmin, vmax=vmax, origin=origin)
    fig.savefig(fname, dpi=1, format=format)


def newimsave(fname, arr, vmin=None, vmax=None, cmap=None, format=None, 
origin=None):
    from matplotlib.backends.backend_agg import FigureCanvasAgg as FigureCanvas
    from matplotlib.figure import Figure

    fig = Figure(figsize=arr.shape[:2][::-1], dpi=1, frameon=False)
    canvas = FigureCanvas(fig)
    fig.figimage(arr, cmap=cmap, vmin=vmin, vmax=vmax, origin=origin)
    fig.savefig(fname, dpi=1, format=format)
import numpy as np
import matplotlib.pyplot as plt
from my_plottools import newimsave

arr = np.empty((20,20,3),dtype=np.uint16)
arr[...,0] = np.tri(20)*255/3
arr[...,1] = arr[:,::-1,0]
arr[...,2] = arr[::-1,:,0]

newimsave(r'd:\temp\test1.png', arr)

arr = np.empty((20,30,3),dtype=np.uint16)
arr[...,0] = np.outer(np.linspace(0,255,20), np.ones(30))
arr[...,1] = np.outer(np.ones(20), np.linspace(0,255,30))
arr[...,2] = np.outer(np.linspace(0,np.sqrt(255),20), 
np.linspace(0,np.sqrt(255),30))
# arr[...,3] = np.mgrid[0,0:255:20]

newimsave(r'd:\temp\test2.png', arr)

arr = np.empty((20,30,4),dtype=np.uint16)
arr[...,0] = np.outer(np.linspace(0,255,20), np.ones(30))
arr[...,1] = np.outer(np.ones(20), np.linspace(0,255,30))
arr[...,2] = np.outer(np.linspace(0,np.sqrt(255),20), 
np.linspace(0,np.sqrt(255),30))
arr[...,3] = np.outer(np.linspace(0,255,20), 
np.hstack((np.zeros(15),np.ones(15))))

newimsave(r'd:\temp\test3.png', arr)
------------------------------------------------------------------------------
Let Crystal Reports handle the reporting - Free Crystal Reports 2008 30-Day 
trial. Simplify your report design, integration and deployment - and focus on 
what you do best, core application coding. Discover what's new with
Crystal Reports now.  http://p.sf.net/sfu/bobj-july
_______________________________________________
Matplotlib-devel mailing list
Matplotlib-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel

Reply via email to