displaying postscript (or other vector-based graphics)

One of the applications I work on generates a novel graph format, which I initially implemented with the GraphicsContext functions. Unfortunately, this doesn’t scale very well (interactively or not) and the behavior on Linux and Mac is very inconsistent. We would also like to have the ability to use these graphs in other contexts (e.g. web pages, PDFs, etc.) which would require a completely different format. Since the program is relatively simple right now and I have a long list of changes to make, I’m just going to rewrite it, but I wanted to get an opinion on the best way to display the output. Postscript seems like the best format, since I can use the Python Imaging Library to create and convert it, but what are my options for displaying it in wxPython? I couldn’t find much on Google; is there anything better than converting it to a bitmap? I would like to produce something that can scale cleanly when the display window is resized, if possible, but this may be unrealistic.

Alternately, if anyone has used the SVG widget for wxPython and can comment on its stability and features, I’d be interested to hear that. Anything I can do to make this more interactive (e.g. quickly redrawing the screen based on user preferences) would be very helpful.

thanks,

Nat

Nathaniel Echols wrote:

One of the applications I work on generates a novel graph format, which I initially implemented with the GraphicsContext functions. Unfortunately, this doesn't scale very well (interactively or not) and the behavior on Linux and Mac is very inconsistent. We would also like to have the ability to use these graphs in other contexts (e.g. web pages, PDFs, etc.) which would require a completely different format. Since the program is relatively simple right now and I have a long list of changes to make, I'm just going to rewrite it, but I wanted to get an opinion on the best way to display the output. Postscript seems like the best format, since I can use the Python Imaging Library to create and convert it, but what are my options for displaying it in wxPython? I couldn't find much on Google; is there anything better than converting it to a bitmap? I would like to produce something that can scale cleanly when the display window is resized, if possible, but this may be unrealistic.

If you search the archives a bit you'll find the two biggest contenders seem to be matplotlib and floatcanvas with maybe a little numpy thrown in for good measure. And no, I do not use graphs in my wx programs...so hopefully Chris or one of the other's who does this a lot will jump in here.

···

-------------------
Mike Driscoll

Blog: http://blog.pythonlibrary.org

Nathaniel Echols wrote:

One of the applications I work on generates a novel graph format, which I
initially implemented with the GraphicsContext functions. Unfortunately,
this doesn't scale very well (interactively or not) and the behavior on
Linux and Mac is very inconsistent.

I'd be interested in hearing about that -- it should work OK for this kind of thing.

Postscript seems like the best format

PS is getting a bit dated, doesn't support alpha blending, and has never been well supported on Windows.

the Python Imaging Library to create and convert it

I don't think PIL does not create PS -- except maybe just embedding images in it

wxPostscriptDC does, though.

I'd go with SVG or PDF these days.

I would like to produce
something that can scale cleanly when the display window is resized, if
possible, but this may be unrealistic.
Alternately, if anyone has used the SVG widget for wxPython and can comment
on its stability and features, I'd be interested to hear that. Anything I
can do to make this more interactive (e.g. quickly redrawing the screen
based on user preferences) would be very helpful.

I'd be inclined to have a internal representation, and then have one or more "back-ends" to render -- one for rendering on screen: using wxDC or wxGC or maybe a raster rendering lib like Agg or Cairo. Then one (or more) for rending scalable output: PDF or SVG.

I'm not sure what your "novel graph"s are, but I'd take a good look at FloatCanvas2 (a re-write of wx.lib.floatcanvas), and matplotlib and Chaco. If MPL and chaco aren't what you need, you could still use KIVA and/or enable, which Chaco is built on. Kiva supports bitmaps and PDF at least.

-Chris

···

--
Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R (206) 526-6959 voice
7600 Sand Point Way NE (206) 526-6329 fax
Seattle, WA 98115 (206) 526-6317 main reception

Chris.Barker@noaa.gov

Nathaniel Echols wrote:

One of the applications I work on generates a novel graph format, which I initially implemented with the GraphicsContext functions. Unfortunately, this doesn't scale very well (interactively or not) and the behavior on Linux and Mac is very inconsistent.

For a totally consistent result using a GraphicsContext-like API use PyCairo and the wx.lib.graphics module. Since it's Cairo underneath then you should be able to redirect output to any backend that Cairo supports, although I haven't tried anything other than on-screen and PNG files.

···

--
Robin Dunn
Software Craftsman
http://wxPython.org Java give you jitters? Relax with wxPython!

Matplotlib won’t do what I need - but I hadn’t realized that FloatCanvas had the features I was looking for. I will probably need to make most of my layout code toolkit-independent in case we need to output images or PDFs, but using FloatCanvas sounds like a much better solution than displaying a converted bitmap.

thanks,

Nat

···

On Mon, May 4, 2009 at 2:11 PM, Mike Driscoll mike@pythonlibrary.org wrote:

If you search the archives a bit you’ll find the two biggest contenders seem to be matplotlib and floatcanvas with maybe a little numpy thrown in for good measure. And no, I do not use graphs in my wx programs…so hopefully Chris or one of the other’s who does this a lot will jump in here.

Nathaniel Echols wrote:

One of the applications I work on generates a novel graph format, which I

initially implemented with the GraphicsContext functions. Unfortunately,

this doesn’t scale very well (interactively or not) and the behavior on

Linux and Mac is very inconsistent.

I’d be interested in hearing about that – it should work OK for this kind of thing.

The worst problem is drawing thick lines – on Mac, these have flat edges, but on Linux, they’re rounded, which is totally inappropriate for what I’m trying to draw. There may be a better way to do what I need but there were enough other bugs in my implementation that I decided to look for something better. The scaling I simply couldn’t figure out - I tried to redraw when the window was resized but nothing ever worked. (I’m probably making some newbie error - I don’t have much experience with drawing things directly.) I have also had issues placing text correctly due to what appear to be incorrect dimensions being reported.

I’m not sure what your "novel graph"s are, but I’d take a good look at FloatCanvas2 (a re-write of wx.lib.floatcanvas), and matplotlib and Chaco. If MPL and chaco aren’t what you need, you could still use KIVA and/or enable, which Chaco is built on. Kiva supports bitmaps and PDF at least.

I probably should have been clearer about this: it’s several one-dimensional histograms arranged radially and connected by lines - the histograms show the distribution of various statistics in a database, and the connecting lines show where the object being compared to the database falls in each distribution. The shape and size of the resulting object should reflect the quality of the object under consideration (in this case, a protein structure). It probably won’t make a lot of sense unless you’re a crystallographer, but here is more or less what it looks like, minus the rest of the interface:

http://cci.lbl.gov/~nat/img/phenix/polygon_test.png

What we’re trying to do is pretty non-standard, so I doubt matplotlib or chaco will be much help, but it’s also pretty easy to figure out the vector drawing steps.

-Nat

···

On Mon, May 4, 2009 at 2:13 PM, Christopher Barker Chris.Barker@noaa.gov wrote:

Robin Dunn wrote:

For a totally consistent result using a GraphicsContext-like API use PyCairo and the wx.lib.graphics module. Since it's Cairo underneath then you should be able to redirect output to any backend that Cairo supports

which includes PDF, SVG and I think, PS.

This may be a good option.

-Chris

···

--
Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R (206) 526-6959 voice
7600 Sand Point Way NE (206) 526-6329 fax
Seattle, WA 98115 (206) 526-6317 main reception

Chris.Barker@noaa.gov

I don't know... I've been surprised at all the things matplotlib can do (don't
know about Chaco). If I understand your diagram correctly, you need a set
of multicolored lines (colored based on location) and a polygon. Maybe you
could start with this example for multicolored lines:

http://www.scipy.org/Cookbook/Matplotlib/MulticoloredLine

If you run it by the people on the matplotlib mailing list, I would be pretty
surprised if they couldn't help you get a fairly short script that will do it.
Plus it will "can scale cleanly when the display window is resized", as you
wanted, has a built-in toolbar to save it as a .pdf, .png. .ps, .eps,
.svg, etc.,
and can be nicely embedded in a wxPython app.

HTH,
Che

···

On Mon, May 4, 2009 at 7:43 PM, Nathaniel Echols <nathaniel.echols@gmail.com> wrote:

On Mon, May 4, 2009 at 2:13 PM, Christopher Barker <Chris.Barker@noaa.gov> > wrote:

Nathaniel Echols wrote:

One of the applications I work on generates a novel graph format, which I
initially implemented with the GraphicsContext functions. Unfortunately,
this doesn't scale very well (interactively or not) and the behavior on
Linux and Mac is very inconsistent.

I'd be interested in hearing about that -- it should work OK for this kind
of thing.

The worst problem is drawing thick lines -- on Mac, these have flat edges,
but on Linux, they're rounded, which is totally inappropriate for what I'm
trying to draw. There may be a better way to do what I need but there were
enough other bugs in my implementation that I decided to look for something
better. The scaling I simply couldn't figure out - I tried to redraw when
the window was resized but nothing ever worked. (I'm probably making some
newbie error - I don't have much experience with drawing things directly.)
I have also had issues placing text correctly due to what appear to be
incorrect dimensions being reported.

I'm not sure what your "novel graph"s are, but I'd take a good look at
FloatCanvas2 (a re-write of wx.lib.floatcanvas), and matplotlib and Chaco.
If MPL and chaco aren't what you need, you could still use KIVA and/or
enable, which Chaco is built on. Kiva supports bitmaps and PDF at least.

I probably should have been clearer about this: it's several one-dimensional
histograms arranged radially and connected by lines - the histograms show
the distribution of various statistics in a database, and the connecting
lines show where the object being compared to the database falls in each
distribution. The shape and size of the resulting object should reflect the
quality of the object under consideration (in this case, a protein
structure). It probably won't make a lot of sense unless you're a
crystallographer, but here is more or less what it looks like, minus the
rest of the interface:
http://cci.lbl.gov/~nat/img/phenix/polygon_test.png

What we're trying to do is pretty non-standard, so I doubt matplotlib or
chaco will be much help

Nathaniel Echols wrote:

The worst problem is drawing thick lines -- on Mac, these have flat edges, but on Linux, they're rounded,

edges? or do you mean ends? In general, good drawing APIs allow you to specify the end cap style -- though I don't see that in wxGraphicsContext. Cairo has it, as does Kiva.

But maybe wxDC would be fine for you.

> The scaling I simply couldn't figure out - I

tried to redraw when the window was resized but nothing ever worked.

Which is why I wrote FloatCanvas in the first place. I din't want to write that code more than once.

here is more or less what it looks like, minus the rest of the interface:

http://cci.lbl.gov/~nat/img/phenix/polygon_test.png

What we're trying to do is pretty non-standard, so I doubt matplotlib or chaco will be much help, but it's also pretty easy to figure out the vector drawing steps.

Well, both of those allow you to draw basic line, polygons, etc -- you don't need to use their higher level plotting. But what your doing is pretty much FloatCanvas's reason for being.

A note about FloatCanvas1 vs. 2:

FloatCanvas 1 has been around for quie a few years, well before GraphicsContext and alpha blending -- if you don't need those things, it would work well for what you need to do. And you can shoehorn in some GraphicsContext drawing if you want, see:

http://trac.paulmcnett.com/floatcanvas

FloatCanvas2 is a re-write, done as a Google Summer of Code project, and is being maintained by the author. It is more powerful and flexible, and fully supports alpha, etc. However, it is less mature, and I'm not sure it's working right on Mac and GTK at this point, as the developer is only running Windows at the moment.

In short: if FC1 does what you need, it will probably be easier to get it up and running, but if you want more flexibility, FC2 may be the best choice.

Feel free to ask questions about either on the list:

http://mail.paulmcnett.com/cgi-bin/mailman/listinfo/floatcanvas

-Chris

···

--
Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R (206) 526-6959 voice
7600 Sand Point Way NE (206) 526-6329 fax
Seattle, WA 98115 (206) 526-6317 main reception

Chris.Barker@noaa.gov

There's wx.GraphicsPen which is created from wx.Pen which again has a member called SetCap(). See http://docs.wxwidgets.org/stable/wx_wxpen.html#wxpensetcap . There's also wx.Pen.SetJoin.

FloatCanvas2 supports the different join and cap styles with so-called looks, e.g.

myLook = fc.RadialGradientLook( 'pink', (0,0), (0,255,0,128), (0,0), 150, (255,0,255,200), line_style = 'dot', line_width = 10, line_cap = 'butt', line_join = 'bevel' )

fc2 also gives you simple svg output.

As Christopher pointed out fc2 uses wxGraphicsContext internally. Even though GraphicsContext supports a good range of features cross-platform, I'd go with Cairo as Robin suggested in case you decide to roll your own drawing. GraphicsContext has some limitations and problems which Cairo does not seem to have. Plus Cairo has stuff like much better svg handling etc.

-Matthias

···

Am 05.05.2009, 17:36 Uhr, schrieb Christopher Barker <Chris.Barker@noaa.gov>:

Nathaniel Echols wrote:

The worst problem is drawing thick lines -- on Mac, these have flat edges, but on Linux, they're rounded,

edges? or do you mean ends? In general, good drawing APIs allow you to specify the end cap style -- though I don't see that in wxGraphicsContext. Cairo has it, as does Kiva.

Christopher Barker wrote:

Nathaniel Echols wrote:

The worst problem is drawing thick lines -- on Mac, these have flat edges, but on Linux, they're rounded,

edges? or do you mean ends? In general, good drawing APIs allow you to specify the end cap style -- though I don't see that in wxGraphicsContext. Cairo has it, as does Kiva.

It's part of the Pen's properties, but maybe one of the GraphicsContext implementations is not paying attention to it...

···

--
Robin Dunn
Software Craftsman
http://wxPython.org Java give you jitters? Relax with wxPython!