[matplotlib-devel] scatter and alpha settings

2008-10-06 Thread Gregor Thalhammer
Dear developers,

in matplotlib 0.98.3 I discoverd that in scatter individual alpha 
settings (by giving a list of rgba values) are ignered. Here an example 
that show this behaviour: All points show the same alpha value as given 
by the alpha keyword argument. (Omitting it equals to the setting alpha=1).


from pylab import *

x = [1,2,3]
y = [1,2,3]

c = [[1,0,0, 0.0],
 [1,0,0, 0.5],
 [1,0,0, 1.0]]

gca()
cla()
scatter(x,y, c=c, s = 200, alpha = 0.5)
draw()
show()


I had a look at the sources. In axes.py/scatter I simply removed the line

collection.set_alpha(alpha)

The recent svn version also contains this line.
With this change it worked as expected, also e.g. for the case of a 
single color for all points,

scatter(x,y, c = 'r', alpha = 0.5)

Gregor


-
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


[matplotlib-devel] unexpected behaviour of get_xlim

2008-10-10 Thread Gregor Thalhammer
Dear developers,

the following example shows a somewhat unexpected behaviour of the 
get_xlim() method of an axis object: it returns a view to the internal 
data structure used to store the data limits. Because of this saving and 
restoring the data limits failed in this example (I am using matplotlib 
0.98.3):

from pylab import *
plot([0,1], [0,1]) #create some plot
ax = gca() #keep reference to axis
#after some time, I want to change the plot content, but keep the data 
limits
xlimits = ax.get_xlim() #save limits
print xlimits
ax.clear()#first clear axis, then
plot([1,2], [1,2])#create new plot content
ax.set_xlim(xlimits)  #does _not_ restore old limits
print xlimits #since saved xlimits also changed

Now I know that I have to use

xlimits = ax.get_xlim().copy()

if I want to save the data limits.

Is this really an intended behaviour? Wouldn't it be better if 
get_xlim() already returns a copy? Or could at least the documentation 
be updated to mention this pitfall?

Gregor



-
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] navigation toolbar keyboard shortcuts patch

2008-10-17 Thread Gregor Thalhammer
Paul Ivanov schrieb:
> Hi,
>
> I'm a big fan of keyboard shortcuts, so I decided to add these guys to
> lib/matplotlib/backend_bases.py   
>
> I'm not sure if this is too much, and maybe these should be configurable
> down the line, but here's my first stab at it, what do you all think?
>
> in the same order as they appear in the toolbar:
> 'h' or 'r' for Home/Reset
> left arrow or 'z' or backspace for Back
> right arrow and 'x' for Forward
> 'p' for pan axes with right, zoom with left mode toggle
> 'o' for z*o*om to rectangle mode toggle
> 's' for save
>   
I like this idea very much. What I would like to see is panning 
associated with the space bar, like it's done in Adobe Acrobat: panning 
is only activated _while_ you press space. I think this is more 
difficult to implement. Once I had a quick look at it and abandonded 
this project, it was too complicated for me. Perhaps you can manage this?

> 'z' and 'x' I borrowed from the Opera browser, very handy to for
> righties who can have their left hand on the keyboard while using the mouse.
>   
On german keyboards y and z are exchanged. Having these keys 
configurable would be handy.

Gregor

-
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] [Matplotlib-users] Crosshai cursor or Selector with matplotlib.backends.backend_wxagg

2008-11-11 Thread Gregor Thalhammer
[EMAIL PROTECTED] schrieb:
> Dear all,
>
> after looking around for a plotting library I found Matplotlib and I tried to 
> create a gray scale image in a wxpython application. Looks good!
>
> Now I have to find a line in the image with mainly vertical orientation. To 
> do this a crosshair cursor would be fine. In Pylab I found a SpanSelector 
> which also looks promising. 
>
> Unfortunately I failed in adding a crosshair cursor or a SpanSelector into my 
> wxpython application figure.
>
>   
try

from matplotlib.widgets import Cursor
help(Cursor)

If this is not enough, I have once written a Crosshair very similar to 
SpanSelector - but I don't have it at hand at the moment.

Gregor

-
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] help request: wx, tk, qt backend leave event

2008-12-02 Thread Gregor Thalhammer

John Hunter schrieb:

I recently added support for a figure/axes enter/leave event.  The
figure enter and axes enter/leave are easy to do with nothing new in
the backends, just using the native mpl events.  The figure leave
event is harder, because when a user leaves a figure and activates
another window, mpl gets no events.

To correct this, I added a leave_notify_event method to
backend_bases.FigureCanvasBase (note this is not an mpl Event) but
when called it will trigger a callback to those registered to the
figure_leave_event with the last event that occurred in the window.

I added support for this in gtk by connecting the the gtk signal
'leave_notify_event' to the mpl backend method leave_notify_event.  If
you know something about tk, wx or qt event handling, could you add a
similar method to the appropriate backend?  You can follow the example
in backend_gtk.


You can test with examples/event_handling/figure_axes_enter_leave.py

Thanks,
JDH
I attached a patch for the wx backend. Nearly everything has already 
been implemented. Instead of the new 'leave_notify_event' leaving the 
figure triggered a fake motion_event. I changed this.


If a mouse button is pressed while leaving the figure the behaviour is 
somewhat strange. First, a figure_leave_event is emitted. Then, further 
moving the mouse outside the figure a new figure_enter_event is created. 
This is the case since all mouse events, also movements outside the 
window, are captured as long as a mouse button is pressed. This is a 
very convenient behaviour for panning/zooming. However, when finally 
releasing the mouse button no figure_leave_event is triggered. With the 
GTK backend such an event is created.

So what should be the desired behaviour?

Gregor
Index: backend_wx.py
===
--- backend_wx.py   (revision 6465)
+++ backend_wx.py   (working copy)
@@ -1263,10 +1263,10 @@
 FigureCanvasBase.motion_notify_event(self, x, y, guiEvent=evt)
 
 def _onLeave(self, evt):
-"""Mouse has left the window; fake a motion event."""
+"""Mouse has left the window."""
 
 evt.Skip()
-FigureCanvasBase.motion_notify_event(self, -1, -1, guiEvent=evt)
+FigureCanvasBase.leave_notify_event(self, guiEvent = evt)
 
 
 
-
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] help request: wx, tk, qt backend leave event

2008-12-03 Thread Gregor Thalhammer
>
> Can you update, repatch wx to use it (and Darren qt)?
>

I attached a patch that emits a enter_notify_event if the mouse enters the
figure. Now the example behaves correctly.

Gregor
Index: backend_wx.py
===
--- backend_wx.py	(Revision 6482)
+++ backend_wx.py	(Arbeitskopie)
@@ -743,6 +743,7 @@
 bind(self, wx.EVT_LEFT_UP, self._onLeftButtonUp)
 bind(self, wx.EVT_MOTION, self._onMotion)
 bind(self, wx.EVT_LEAVE_WINDOW, self._onLeave)
+bind(self, wx.EVT_ENTER_WINDOW, self._onEnter)
 bind(self, wx.EVT_IDLE, self._onIdle)
 self.SetBackgroundStyle(wx.BG_STYLE_CUSTOM)
 
@@ -1268,7 +1269,11 @@
 evt.Skip()
 FigureCanvasBase.leave_notify_event(self, guiEvent = evt)
 
+def _onEnter(self, evt):
+"""Mouse has entered the window."""
+FigureCanvasBase.enter_notify_event(self, guiEvent = evt)
 
+
 
 #
 # The following functions and classes are for pylab compatibility
-
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] help request: wx, tk, qt backend leave event

2008-12-03 Thread Gregor Thalhammer
2008/12/2 Darren Dale <[EMAIL PROTECTED]>

>
>
> On Tue, Dec 2, 2008 at 10:41 AM, John Hunter <[EMAIL PROTECTED]> wrote:
>
>> On Tue, Dec 2, 2008 at 8:34 AM, Gregor Thalhammer
>> <[EMAIL PROTECTED]> wrote:
>>
>> > If a mouse button is pressed while leaving the figure the behaviour is
>> > somewhat strange. First, a figure_leave_event is emitted. Then, further
>> > moving the mouse outside the figure a new figure_enter_event is created.
>> > This is the case since all mouse events, also movements outside the
>> window,
>> > are captured as long as a mouse button is pressed. This is a very
>> convenient
>> > behaviour for panning/zooming. However, when finally releasing the mouse
>> > button no figure_leave_event is triggered. With the GTK backend such an
>> > event is created.
>> > So what should be the desired behaviour?
>>
>> Ahh, I hadn't considered this problem.  It arises because I am using
>> mpl location events to trigger the figure enter event.  The solution
>> is to use the gui event for the figure enter event too -- basically
>> the gui needs to call the canvas.enter_notify_event.  I added your
>> patch and modified gtk to handle the enter_notify_event in svn r6468.
>> Can you update, repatch wx to use it (and Darren qt)?
>
>
> This is done for qt and qt4. In qt, if you hold the  button, leave the
> figure, enter the second figure, and release the button, the old  figure
> receives the leave event, but the new figure does not receive the enter
> event. This seems like an issue with qt3, the new figure does receive the
> enter event with qt4.
>

with the patched wx backend I observe the same behaviour. The second figure
does not recieve an enter event. This might be because the wx backend
captures the mouse if a button is pressed, i.e., all mouse events are
redirected to the first figure.

> I noticed that if one moves the cursor rapidly through the figure and
axes, some events are not captured. For example, the cursor is in an axes
but the last event the axes received was a leave event. I'm not sure how
that could be improved, do you see it as well?

Exactly this behaviour I can't see with the wx backend. Did I understood
correctly: You manage to place the mouse within an axis, without having
received a enter event?

With all backends (Wx, GTK, Qt) I manage to leave the figure, without
leaving an axis. Either I move very fast, or  I stack the figures on screen
so that I can leave an axis without touching the space around. We could emit
axes_leave_events (to all axes of the figure, or do we keep record which
axes has been entered recently?) before emitting a figure_leave_event, or
leave this to the users implementation of the figure_leave_event callback.
The first solution might lead to a lot of undesired redraws of the figure
when leaving the figure if several axes are contained in the figure and each
leave_axes callback issues a redraw, like in the example.

Gregor
-
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


[matplotlib-devel] scatter and alpha

2008-12-12 Thread Gregor Thalhammer
I found that in scatter plots the alpha values given by individual 
entries in the color list are ignored. Here an example that shows 
different combinations of color and alpha arguments:


x = [1,2,3]
y = array([1,1,1])

c = [[1,0,0, 0.0],
[1,0,0, 0.5],
[1,0,0, 1.0]]

scatter(x, y, s = 200, c = 'r')
scatter(x, y + 1, s = 200, c = c)
scatter(x, y + 2, s = 200, c = c, alpha = 0.5)
scatter(x, y + 3, s = 200, c = 'g', alpha = 0.5)

Looking at the source in axes.py/scatter I found that replacing the 
default value for the alpha keyword argument in the function header of 
scatter from alpha=1.0 to alpha=None fixes this problem. Additionally, I 
had to replace


collection.set_alpha(alpha)

by

if alpha is not None:
   collection.set_alpha(alpha)

See also the attached diff file.

Gregor
Index: axes.py
===
--- axes.py (revision 6590)
+++ axes.py (working copy)


@@ -4873,7 +4872,7 @@
 medians=medians, fliers=fliers)
 
 def scatter(self, x, y, s=20, c='b', marker='o', cmap=None, norm=None,
-vmin=None, vmax=None, alpha=1.0, linewidths=None,
+vmin=None, vmax=None, alpha=None, linewidths=None,
 faceted=True, verts=None,
 **kwargs):
 """
@@ -5136,7 +5135,8 @@
 transOffset = self.transData,
 )
 collection.set_transform(mtransforms.IdentityTransform())
-collection.set_alpha(alpha)
+if alpha is not None:
+collection.set_alpha(alpha)
 collection.update(kwargs)
 
 if colors is None:
--
SF.Net email is Sponsored by MIX09, March 18-20, 2009 in Las Vegas, Nevada.
The future of the web can't happen without you.  Join us at MIX09 to help
pave the way to the Next Web now. Learn more and register at
http://ad.doubleclick.net/clk;208669438;13503038;i?http://2009.visitmix.com/___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


[matplotlib-devel] plot([], [], drawstyle = 'steps') fails

2009-02-23 Thread Gregor Thalhammer
Hi all,

sorry, only reporting, no bugfix. I just discovered that an empty plot 
with drawstyle 'steps', 'steps-pre', 'steps-mid' and 'steps-post' fails. 
I am using matplotlib 0.98.5.2.

Example

plot([], [], drawstyle = 'steps')

...
C:\Python25\lib\site-packages\matplotlib\lines.pyc in 
_draw_steps_pre(self, renderer, gc, path, trans)
784 def _draw_steps_pre(self, renderer, gc, path, trans):
785 vertices = self._xy
--> 786 steps = ma.zeros((2*len(vertices)-1, 2), np.float_)
787
788 steps[0::2, 0], steps[1::2, 0] = vertices[:, 0], 
vertices[:-1, 0
]
...

ValueError: negative dimensions are not allowed

Gregor





--
Open Source Business Conference (OSBC), March 24-25, 2009, San Francisco, CA
-OSBC tackles the biggest issue in open source: Open Sourcing the Enterprise
-Strategies to boost innovation and cut costs with open source participation
-Receive a $600 discount off the registration fee with the source code: SFAD
http://p.sf.net/sfu/XcvMzF8H
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] [Numpy-discussion] glumpy, fast opengl visualization

2010-01-27 Thread Gregor Thalhammer
2010/1/25 Nicolas Rougier :
>
>
> Hello,
>
> This is an update about glumpy, a fast-OpenGL based numpy visualization.
> I modified the code such that the only dependencies are PyOpenGL and
> IPython (for interactive sessions). You will also need matplotlib and
> scipy for some demos.
>
> Sources: hg clone http://glumpy.googlecode.com/hg/ glumpy
> No installation required, you can run all demos inplace.
>
> Homepage: http://code.google.com/p/glumpy/
>
Hi Nicolas,

thank you for providing glumpy. I started using it for my own project.
The previous, pyglet based version of glumpy worked flawlessly on my
system (WinXP). I want to report about problems with the latest
version.
1.) On Windows glumpy fails on importing the Python termios module,
since it is for Unix platforms only.
2.) Resolving this, the demos start, but are mostly not usable, since
mouse scroll events and passive mouse motions events are not created.
This might be a problem of the glut implementation on Windows (I am
using PyOpenGL 3.0.1b2). Who knows?
3.) On OpenSuse11.1 the demos fail at 'glCreateProgram'. The demos
used to work with the previous version. I use the Intel Q45 graphics
chipset.

In the future I might spend some time on this problems and I would
like to contribute to glumpy, even if it's only testing on platforms
available to me.

Gregor

--
The Planet: dedicated and managed hosting, cloud storage, colocation
Stay online with enterprise data centers and the best network in the business
Choose flexible plans and management services without long-term contracts
Personal 24x7 support from experience hosting pros just a phone call away.
http://p.sf.net/sfu/theplanet-com
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


[matplotlib-devel] weird outline with fill

2006-08-18 Thread Gregor Thalhammer
Hi,

I am using matplotlib 87.4 and I encountered a problem with fill. The outlines
of the filled region look weird when using the TkAgg backend. Same applies when
saved to a png file, so this seems to be a problem of all *Agg backends. The PS
backend is fine. Here is a somewhat longer example, that shows this behaviour.
For comparison, drawing the same outlines with plot gives a perfectly smooth
result.


from pylab import *
clf()
x = linspace(0,1, 100)
y1 = x**2
y2 = 1.03*y1
xx = concatenate((x, x[::-1]))
yy = concatenate((y1, y2[::-1]))
fillh = fill(xx, yy, ec = 'k', lw = 0.4)
fillh = fillh[0]
fillh.set_fill(False)
ph = plot(x, y1+0.1, 'k-',
 x, y2+0.1, 'k-', lw = 0.4)
savefig('jaggyfill.png', dpi = 150)
savefig('jaggyfill.eps')
show()

The more points I use, the worse the result. I create a png file since I need
alpha filling, eps doesn't support this. Creating a high resolution png and
downscaling improves the result, but this is tedious and time consuming. Any
help is appreciated!

Thanks in advance

Gregor Thalhammer

PS. Is this the right place to discuss such problems?



-
Using Tomcat but need to do more? Need to support web services, security?
Get stuff done quickly with pre-integrated technology to make your job easier
Download IBM WebSphere Application Server v.1.0.1 based on Apache Geronimo
http://sel.as-us.falkag.net/sel?cmd=lnk&kid=120709&bid=263057&dat=121642
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


[matplotlib-devel] Unnecessary rerendering in wx/wxagg backends

2008-03-31 Thread Gregor Thalhammer
Dear developers,

I discovered that in backend_wx.py in _onPaint(), the callback function 
for repainting a matplotlib figure, every time a repaint is done also 
the bitmap is rerendered:

backend_wx.py/_onPaint():
...
# Render to the bitmap
self.draw(repaint=False)
...

This also affects the behaviour of the wxagg backend. Rerendering and 
therefore also repainting gets quite slow if, e.g., images are included 
in the figure. I can see this by simply dragging another window across 
the matplotlibfigure. Commenting out the rerendering I get a much 
smoother behaviour. I could not observe problems except that sometimes 
some parts of the figure are not properly repainted if the matplotlib 
figure is in the background (I only tested the wxagg backend). Therefore 
it seems that this rerendering every time a repaint is performed is not 
really necessary and should be avoided.

I tested this on matplotlib 0.91.2 on WinXP, Python 2.5, wx 2.8.7. I 
checked that in the current svn version the _onPaint() function is 
unchanged.

Gregor

-
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://ad.doubleclick.net/clk;164216239;13503038;w?http://sf.net/marketplace
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] Unnecessary rerendering in wx/wxagg backends

2008-04-07 Thread Gregor Thalhammer
Here I attached diff files of my changes, compared to matplotlib-0.91.2 
release.


Gregor Thalhammer
--- Kopie von backend_wx.py Mon Mar 31 10:28:22 2008
+++ backend_wx.py   Sun Apr  6 10:23:09 2008
@@ -752,11 +752,14 @@
 self._isRealized = False
 self._isConfigured = False
 self._printQued = []
+self._need_rerender = True
 
 if wx.VERSION_STRING >= '2.5':
 # Event handlers 2.5
 self.Bind(wx.EVT_SIZE, self._onSize)
 self.Bind(wx.EVT_PAINT, self._onPaint)
+#self.Bind(wx.EVT_ERASE_BACKGROUND, self._onEraseBackground)
+#self.Bind(wx.EVT_IDLE, self._onIdle)
 self.Bind(wx.EVT_KEY_DOWN, self._onKeyDown)
 self.Bind(wx.EVT_KEY_UP, self._onKeyUp)
 self.Bind(wx.EVT_RIGHT_DOWN, self._onRightButtonDown)
@@ -952,7 +955,8 @@
 self.renderer = RendererWx(self.bitmap, self.figure.dpi)
 self.figure.draw(self.renderer)
 if repaint:
-self.gui_repaint()
+self.Refresh()
+#gui_repaint()
 
 def _get_imagesave_wildcards(self):
 'return the wildcard string for the filesave dialog'
@@ -1067,7 +1071,8 @@
 self.print_figure(fname, dpi, facecolor, edgecolor)
 self._printQued = []
 
-
+def _onEraseBackground(self, evt):
+pass
 
 def _onPaint(self, evt):
 """
@@ -1078,12 +1083,22 @@
 if not self._isRealized:
 self.realize()
 
-# Render to the bitmap
-#self.draw(repaint=False)
+#only recreate bitmap if needed
+if self._need_rerender:
+self.draw(repaint=False)
+self._need_rerender = False
+
+#repaint only damaged parts of window
+dc = wx.PaintDC(self)
+source = wx.MemoryDC(self.bitmap)
+box = self.UpdateRegion.Box
+dc.Blit(box.X, box.Y, box.Width, box.Height,
+source,
+box.X, box.Y)
+source.SelectObject(wx.NullBitmap) #needed?
 
-# Update the display using a PaintDC
-self.gui_repaint(drawDC=wx.PaintDC(self))
-evt.Skip()
+def _onIdle(self, evt):
+print "OnIdle"
 
 def _onSize(self, evt):
 """
--- Kopie von backend_wxagg.py  Fri Jan 11 21:39:09 2008
+++ backend_wxagg.pySun Apr  6 11:24:27 2008
@@ -58,42 +58,28 @@
 Render the figure using agg.
 """
 DEBUG_MSG("draw()", 1, self)
+
 FigureCanvasAgg.draw(self)
 
 self.bitmap = _convert_agg_to_wx_bitmap(self.get_renderer(), None)
 if repaint:
-self.gui_repaint()
+self.Refresh(eraseBackground = False)
+self.Update()
 
 def blit(self, bbox=None):
-"""
-Transfer the region of the agg buffer defined by bbox to the display.
-If bbox is None, the entire buffer is transferred.
-"""
+self.bitmap = _convert_agg_to_wx_bitmap(self.get_renderer(), None)
+
 if bbox is None:
-self.bitmap = _convert_agg_to_wx_bitmap(self.get_renderer(), None)
-self.gui_repaint()
-return
-
-l, b, w, h = bbox.get_bounds()
-r = l + w
-t = b + h
-x = int(l)
-y = int(self.bitmap.GetHeight() - t)
-
-srcBmp = _convert_agg_to_wx_bitmap(self.get_renderer(), None)
-srcDC = wx.MemoryDC()
-srcDC.SelectObject(srcBmp)
-
-destDC = wx.MemoryDC()
-destDC.SelectObject(self.bitmap)
-
-destDC.BeginDrawing()
-destDC.Blit(x, y, int(w), int(h), srcDC, x, y)
-destDC.EndDrawing()
-
-destDC.SelectObject(wx.NullBitmap)
-srcDC.SelectObject(wx.NullBitmap)
-self.gui_repaint()
+self.Refresh(eraseBackground = False)
+else:
+l, b, w, h = bbox.get_bounds()
+x = int(l)
+y = int(self.bitmap.GetHeight() - (b+h))
+w = int(w)
+h = int(h)
+self.RefreshRect(wx.Rect(x, y, w, h),
+ eraseBackground = False)
+self.Update() #needed?
 
 filetypes = FigureCanvasAgg.filetypes
 
-
This SF.net email is sponsored by the 2008 JavaOne(SM) Conference 
Register now and save $200. Hurry, offer ends at 11:59 p.m., 
Monday, April 7! Use priority code J8TLD2. 
http://ad.doubleclick.net/clk;198757673;13503038;p?http://java.sun.com/javaone___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] Unnecessary rerendering in wx/wxagg backends

2008-04-07 Thread Gregor Thalhammer
I continued to work on this issue. Thanks for Chris Barker for pointing 
me into the right direction. I also had a look at other gui backends, 
and, among other, backend_qtagg.py seems to contain a proper (more or 
less, see other postings of Ted Drain) implementation of double buffered 
drawing that avoids unnecessary rerendering of the bitmap. Following 
this example, I applied following changes to backend_wx.py and 
backend_wxagg.py

backend_wx.py:

in __init__(...) added line:

self._need_rerender = True

changed _onPaint(...) to following (note: removed evt.Skip() at end!)

def _onPaint(self, evt):
"""
Called when wxPaintEvt is generated
"""
DEBUG_MSG("_onPaint()", 1, self)
if not self._isRealized:
self.realize()
#only recreate bitmap if needed
if self._need_rerender:
self.draw(repaint=False)
self._need_rerender = False
#repaint only damaged parts of window
dc = wx.PaintDC(self)
source = wx.MemoryDC(self.bitmap)
box = self.UpdateRegion.Box
dc.Blit(box.X, box.Y, box.Width, box.Height,
source,
box.X, box.Y)
source.SelectObject(wx.NullBitmap) #needed?

By these change in onPaint a rerendering of the bitmap is done only if
needed (in fact, this is needed only once after the figure is shown
for the first time). I moved code from gui_repaint() into
_onPaint. Calls to gui_repaint() in other methods (e.g., draw) might now be
replaced by

self.Refresh()
self.Update() #this is optional, leeds to an immediate repaint

in backend_wxagg.py I changed the draw and blit methods in this sense:

def draw(self, repaint=True):
"""
Render the figure using agg.
"""
DEBUG_MSG("draw()", 1, self)
   
FigureCanvasAgg.draw(self)
self.bitmap = _convert_agg_to_wx_bitmap(self.get_renderer(), None)
if repaint:
self.Refresh(eraseBackground = False)
self.Update()
def blit(self, bbox=None):
self.bitmap = _convert_agg_to_wx_bitmap(self.get_renderer(), None)
   
if bbox is None:
self.Refresh(eraseBackground = False)
else:
l, b, w, h = bbox.get_bounds()
x = int(l)
y = int(self.bitmap.GetHeight() - (b+h))
w = int(w)
h = int(h)
self.RefreshRect(wx.Rect(x, y, w, h),
 eraseBackground = False)
self.Update() #needed?


I tested these changes with WinXP, python2.5, matplotlib 0.91.2,
wxWidgets2.8.7 with several scripts from the matplotlib/examples and I
could not observe a misbehaviour.

I had to add some calls to figure.canvas.draw in my mpl-embedded-in-wx
application, e.g., after changing a colormap range, to give a
immediate change on screen. Before due to the frequent rerendering I
didn't notice that these statements were missing.

As Chris Barker noticed, Figure.draw() does not lead to a repainting
of the window on screen. This seems to be intended. Instead one should
use pylab.draw() or Figure.canvas.draw().

I thought about a more substantial rewrite of the Wx/WxAgg backend,
similar to the QtAgg backend, but (for the moment) I wanted to try
only simple changes. Anyhow, the Wx backend seems to be in some
aspects outdated (uses old style wx methods, e.g. ToolBar.AddTool) and
is even not fully functional (image support missing). What are the
plans for the future? What about the politics of supporting older
versions of wxWidgets?

Gregor Thalhammer

Christopher Barker schrieb:
> Erik Tollerud wrote:
>   
>> I tested this on 0.91.2 on Ubuntu Gutsy, and wx 2.8.7.1, and found
>> that when I bring up a new window, I see a black canvas and it doesn't
>> draw any of the matplotlib objects until I do something like resizing
>> that must explicitly call a draw at some point.
>> 
>
> yup, same here.
>
> I'm using wxAgg, and FigureCanvas.draw() just doesn't seem to be getting 
> called when I call Figure.draw()
>
> It looks like it's designed to work the other way -- the Window needs to 
> call self.figure.draw(self.renderer) when it wants the image drawn. 
> There is an efficiency to this, as the figure doesn't get rendered until 
> the GUI toolkit needs it. However, having it re-render on every Paint 
> call isn't right either.
>
> So how should this work? I'd like to be able to call Figure.draw(), and 
> have the figure re-draw itself - but then it needs to be able to tell 
> the backend Canvas that it needs to be drawn.
>
> It seems that the figure needs to keep a flag that indicated when it is 
> "dirty", then the paint handler could check that, and call draw if need 
> be. Is there one already?
>
> This 

Re: [matplotlib-devel] Unnecessary rerendering in wx/wxagg backends

2008-04-14 Thread Gregor Thalhammer
Hi Christopher,

thanks for your valueable feedback. I am proceeding slowly, but steadily.
>
> > backend_qtagg.py seems to contain a proper (more or
>> less, see other postings of Ted Drain) implementation of double 
>> buffered drawing that avoids unnecessary rerendering of the bitmap.
>
> It still feels a bit kludgy to me -- a paint event should simply copy 
> the bitmap to the screen, any re-rendering should be triggered by 
> other events -- either a re-size, or explicitly by 
> figure.canvas.draw() or something. Anyway, given the current 
> structure, this looks like the way to go.
I agree, this is currently more a workaround  for some missing 
rererenderings. It seems to me, that rendering the figure is avoided as 
much as possible. Possibly this is due to the support for the vector 
graphic backends (postscript, pdf, svg)? I guess that with these 
backends rendering means actually creating the output file, but I didn't 
have a look at the source code.
>> self._need_rerender = True
>
> Where does this get set to True again? On a Figure.canvas.draw() call?
Actually nowhere else. In the QtAgg backend, in Figure.canvas.draw this 
is set to True, and then a repaint event is triggered, but no explicit 
rerendering. I didn't get this fact from the beginning. As stated above, 
this command is essentially a workaround for a missing initial 
rerendering after creating the FigureCanvas.
>
>> changed _onPaint(...) to following (note: removed evt.Skip() at end!)
>>def _onPaint(self, evt):
>
>>#repaint only damaged parts of window
>
> I don't know that this is needed, bitting the whole Window is 
> blazingly fast anyway -- but if it works, why not?
Actually, this code repaints the bounding box containing all damaged 
regions. I did it because the QtAgg backend also did it like this. If I 
quickly move another window in front of a matplotlib figure, than I can 
see I small difference.
>> By these change in onPaint a rerendering of the bitmap is done only if
>> needed (in fact, this is needed only once after the figure is shown
>> for the first time).
>
> Well, it's needed whenever the figure changes -- on each 
> figure.canvas.draw() call, I guess.
You are right. To express it more clearly: In my changed code a 
rererendering of the bitmap is done on each figure.canvas.draw() (as 
before). In the onPaint event callback no rerendering is done except the 
very first it's get callad after the figure has been created (changed 
behaviour).
>
> > I moved code from gui_repaint() into
>> _onPaint. Calls to gui_repaint() in other methods (e.g., draw) might 
>> now be
>> replaced by
>>
>> self.Refresh()
>> self.Update() #this is optional, leeds to an immediate repaint
>
> Maybe -- I've found (at least on OS-X) that using a ClientDC is still 
> required sometimes to get instant response. This is key if you're 
> doing anything like animation.
Initially I thought this is optional and might avoid some unnecessary 
repainting. Later I discovered that it is crucial for interactive 
panning. And for animation.
>
>>def draw(self, repaint=True):
>>"""
>>Render the figure using agg.
>>"""
>>DEBUG_MSG("draw()", 1, self)
>>  FigureCanvasAgg.draw(self)
>>self.bitmap = _convert_agg_to_wx_bitmap(self.get_renderer(), 
>> None)
>>if repaint:
>>self.Refresh(eraseBackground = False)
>>self.Update()
>
> I think maybe these should be calls to gui_repaint, which will get you 
> to a ClientDC instead of waiting for a paint event -- Update is not 
> always instant.
Didn't know this. The wxWidgets documentation states about Update(): 
"Calling this method immediately repaints the invalidated area of the 
window..."


>> I had to add some calls to figure.canvas.draw in my mpl-embedded-in-wx
>> application, e.g., after changing a colormap range, to give a
>> immediate change on screen. Before due to the frequent rerendering I
>> didn't notice that these statements were missing.
>
> I agree -- I think I'm going to need to add a few of those too. The 
> problem is that this is a change, and other folks' code is going to 
> break too.
At least for my case I would say that these changes to the wx backend 
didn't break my code, they revealed mistakes in my code (I used 
Refresh() instead of figure.canvas.draw() calls to get a rerendering of 
the matplotlib figure).

>> As Chris Barker noticed, Figure.draw() does not lead to a repainting
>> of the window on screen. This seems to be intended. Instead one should
>> use pylab.draw() or Figure.canvas.draw().
>
> I think you're right -- I should have looked at the pylab.draw code to 
> see what it did. Though I think Figure should have a method that does 
> do an instant update...DrawNow??
For GUI backends I would even expect that Figure.draw() should update 
the figure on screen. However, I don't know how this should be 
implemented for not breaking code which uses other backends.
>> What about the politics of 

Re: [matplotlib-devel] wx back-end bugs/issues

2008-05-06 Thread Gregor Thalhammer

Chris Barker schrieb:

Hi all,

I usually use MPL embedded in wx, so I haven't noticed these before 
but with the pylab window:


1) A couple icons seem to be missing. See screenshot enclosed.
I also discovered this behaviour. It seems to be a Windows only specific 
behaviour that only affects the bitmaps of the disabled (or grayed out) 
toolbar buttons. A solution I found is to use the png toolbar bitmaps 
instead of of the xpm ones. For this, replace in backend_wx.py, 
NavigationToolbar2Wx::_init_toolbar() 'home.xpm' by 'home.png', etc. In 
the same file, in _load_bitmap() replace wx.BITMAP_TYPE_XPM by 
wx.BITMAP_TYPE_PNG. This also gives a better visual impression since the 
png bitmaps have an alpha channel, see attached file. Furthermore, in my 
opinion, the floppy symbol is too small compared to the other icons. I 
also attached a magnified version.


Gregor
<><>-
This SF.net email is sponsored by the 2008 JavaOne(SM) Conference 
Don't miss this year's exciting event. There's still time to save $100. 
Use priority code J8TL2D2. 
http://ad.doubleclick.net/clk;198757673;13503038;p?http://java.sun.com/javaone___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] wx back-end bugs/issues

2008-05-07 Thread Gregor Thalhammer
John Hunter schrieb:
> On Tue, May 6, 2008 at 8:49 AM, Gregor Thalhammer
> <[EMAIL PROTECTED]> wrote:
>
>   
>>  I also discovered this behaviour. It seems to be a Windows only specific
>> behaviour that only affects the bitmaps of the disabled (or grayed out)
>> toolbar buttons. A solution I found is to use the png toolbar bitmaps
>> instead of of the xpm ones. For this, replace in backend_wx.py,
>> NavigationToolbar2Wx::_init_toolbar() 'home.xpm' by 'home.png', etc. In the
>> same file, in _load_bitmap() replace wx.BITMAP_TYPE_XPM by
>> wx.BITMAP_TYPE_PNG. This also gives a better visual impression since the png
>> bitmaps have an alpha channel, see attached file. Furthermore, in my
>> opinion, the floppy symbol is too small compared to the other icons. I also
>> attached a magnified version.
>> 
>
> Thankso Gregor -- I made these changes XPM->PNG for toolbar2 on the
> svn branch and trunk, but I don't have ready access to wx here, so if
> you or another wx svn user gets a chance to check, that would be
> great.  Else I can do it tonight from home.
>
>   
I checked the svn version (on Linux), works well. On Windows, applying 
these changes manually, I could see grayed out toolbox icons.

Gregor

-
This SF.net email is sponsored by the 2008 JavaOne(SM) Conference 
Don't miss this year's exciting event. There's still time to save $100. 
Use priority code J8TL2D2. 
http://ad.doubleclick.net/clk;198757673;13503038;p?http://java.sun.com/javaone
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


[matplotlib-devel] High quality downscaling of images

2008-06-09 Thread Gregor Thalhammer

Dear developers,

matplotlib offers high quality interpolation filters which give 
excellent results if you scale up an image. However, for downscaling an 
image the results are worse. Depending on the precise scaling fine 
details (e.g., thin horizontal lines, single pixel points) disappear and 
aliasing effects are visible. After studying the source and the docs for 
Agg I figured out how to improve this. Agg provides all possibilities, 
just use them.


I attached a patch against the current svn version that adds a 
'resample' argument to imshow. Additionally, this patch supports a 
'image.resample' entry in the rc file. Setting this to false (default), 
the behaviour is unchanged.
I also attached a simple test script (test_imshow.py) to show the 
difference between image display with and without resampling. To see the 
difference it might be necessary to zoom out.


Gregor Thalhammer
Index: src/_image.cpp
===
--- src/_image.cpp  (Revision 5430)
+++ src/_image.cpp  (Arbeitskopie)
@@ -426,11 +426,22 @@
   case HAMMING:  filter.calculate(agg::image_filter_hamming(), norm); 
break;
   case HERMITE:  filter.calculate(agg::image_filter_hermite(), norm); 
break;
 }
-   typedef agg::span_image_filter_rgba_2x2 span_gen_type;
-   typedef agg::renderer_scanline_aa renderer_type;
-   span_gen_type sg(ia, interpolator, filter);
-   renderer_type ri(rb, sa, sg);
-   agg::render_scanlines(ras, sl, ri);
+   if (resample)
+ {
+   typedef agg::span_image_resample_rgba_affine 
span_gen_type;
+   typedef agg::renderer_scanline_aa renderer_type;
+   span_gen_type sg(ia, interpolator, filter);
+   renderer_type ri(rb, sa, sg);
+   agg::render_scanlines(ras, sl, ri);
+ }
+   else
+ {
+   typedef agg::span_image_filter_rgba_2x2 span_gen_type;
+   typedef agg::renderer_scanline_aa renderer_type;
+   span_gen_type sg(ia, interpolator, filter);
+   renderer_type ri(rb, sa, sg);
+   agg::render_scanlines(ras, sl, ri);
+ }
   }
   break;
 case BILINEAR:
@@ -464,11 +475,22 @@
   case LANCZOS: filter.calculate(agg::image_filter_lanczos(radius), 
norm); break;
   case BLACKMAN: filter.calculate(agg::image_filter_blackman(radius), 
norm); break;
   }
-   typedef agg::span_image_filter_rgba span_gen_type;
-   typedef agg::renderer_scanline_aa renderer_type;
-   span_gen_type sg(ia, interpolator, filter);
-   renderer_type ri(rb, sa, sg);
-   agg::render_scanlines(ras, sl, ri);
+   if (resample)
+ {
+   typedef agg::span_image_resample_rgba_affine 
span_gen_type;
+   typedef agg::renderer_scanline_aa renderer_type;
+   span_gen_type sg(ia, interpolator, filter);
+   renderer_type ri(rb, sa, sg);
+   agg::render_scanlines(ras, sl, ri);
+ }
+   else
+ {
+   typedef agg::span_image_filter_rgba span_gen_type;
+   typedef agg::renderer_scanline_aa renderer_type;
+   span_gen_type sg(ia, interpolator, filter);
+   renderer_type ri(rb, sa, sg);
+   agg::render_scanlines(ras, sl, ri);
+ }
   }
   break;
 
@@ -530,6 +552,20 @@
 
 }
 
+char Image::get_resample__doc__[] =
+"get_resample()\n"
+"\n"
+"Get the resample flag."
+;
+
+Py::Object
+Image::get_resample(const Py::Tuple& args) {
+  _VERBOSE("Image::get_resample");
+
+  args.verify_length(0);
+  return Py::Int((int)resample);
+}
+
 char Image::get_size_out__doc__[] =
 "numrows, numcols = get_size()\n"
 "\n"
@@ -593,6 +629,21 @@
 
 }
 
+char Image::set_resample__doc__[] =
+"set_resample(boolean)\n"
+"\n"
+"Set the resample flag."
+;
+
+Py::Object
+Image::set_resample(const Py::Tuple& args) {
+  _VERBOSE("Image::set_resample");
+  args.verify_length(1);
+  int flag = Py::Int(args[0]);
+  resample = (bool)flag;
+  return Py::Object();
+}
+
 static void write_png_data(png_structp png_ptr, png_bytep data, png_size_t 
length) {
   PyObject* py_file_obj = (PyObject*)png_get_io_ptr(png_ptr);
   PyObject* write_method = PyObject_GetAttrString(py_file_obj, "write");
@@ -752,12 +803,14 @@
   add_varargs_method( "buffer_rgba", &Image::buffer_rgba, 
Image::buffer_rgba__doc__);
   add_varargs_method( "get_aspect", &Image::get_aspect, 
Image::get_aspect__doc__);
   add_varargs_method( "get_interpolation", &Image::get_interpolation, 
Image::get_interpolation__doc__);
+  add_varargs_method( "get_resample", &Image::get_resample, 
Image::get_resample__doc__);
   add_varargs_method( "get_size", &Image::get_size, Image::get_size__doc__);
   add_varargs_method( "get_size_out", &Im

Re: [matplotlib-devel] High quality downscaling of images

2008-06-09 Thread Gregor Thalhammer
John Hunter schrieb:
> On Mon, Jun 9, 2008 at 10:18 AM,
>
>   
>> I attached a patch against the current svn version that adds a 'resample'
>> argument to imshow. Additionally, this patch supports a 'image.resample'
>> entry in the rc file. Setting this to false (default), the behaviour is
>> unchanged.
>> 
>
> Hi Gregor -- thanks for sending this.  It's something I was aware of
> in agg but never got around to exposing.  I wonder if the
> resample=True|False is the right approach.  It might be nice for
> imshow to have an 'auto' mode to either resample or interpolate
> depending on the image dimensions w/ respect to the destination size.
> Ie, if we are displaying the full image into a small destination,
> 'auto' would default to resample.  If we zoom in sufficiently, the
> image might be best displayed with interpolation.  Is this something
> you think would be worthwhile and would you like to work on support
> for this?
>   
If I understood it correctly, Agg (i.e., span_image_resample_*) already 
exactly behaves like you proposed. It resamples the image if the scaling 
is less than 1, otherwise it interpolates.

> Also,l I notice the patch exposes span_image_resample_rgba_affine but not
> span_image_resample_rgba which takes an interpolator template
> argument.  I know very little about this area, but was this a
> conscious choice or one of expediency?  Can you explain the rational?
>
>   
I am not an Agg expert. The documentation of Agg is not very exhaustive. 
I took it from one of the demos. span_image_resample_rgba_affine seems 
to be faster than span_image_resample_rgba, but it supports affine but 
no perspective transformations. If I understood it correctly, matplotlib 
only uses image translation and scaling, not even rotation or shearing. 
All this is covered by span_image_resample_rgba_affine.

Gregor

-
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://sourceforge.net/services/buy/index.php
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel


Re: [matplotlib-devel] new legend interface and WXAgg interactive mode

2008-09-17 Thread Gregor Thalhammer
John Hunter schrieb:
>> Second, I am using interactive mode and WXAgg in windows. So my startup
>> script does this:
>> import matplotlib as _mpl
>> _mpl.use('WXAgg')
>> import pylab as _p
>> _p.ion()
>> Before, when I would then type
>> gca().plot([1,2,1])
>> 
>
> I would not expect a draw here, since draw only happens on pylab
> commands.  Eg _p.plot should trigger a draw, but not gca().plot
> because the latter is an axes method.  I don't really know why it
> would have worked before, if it did.  I would be pretty surprised if
> it did, actually.
>   
Older versions of the wx and wxagg backend indeed unnecessarily 
rerendered the figure (triggered a draw) very often - with every paint 
event.  This has been fixed.

Gregor

-
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
___
Matplotlib-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-devel