Thoughts about callbacks

As I blurted on -users, I'm thinking lately about callbacks in the
non-GUI portions of the libraries--mostly Artist and subclasses.
I'm curious if anybody else has been thinking about them?

Ideally, I'd like to see the following:

    All of the Artist subclasses, and anything else that might belong to
a Figure, would be updated to use/add cbook.CallbackRegistry callbacks
(weakref = good thing).

    In addition to emulating/replacing the simplistic 'pchanged' callback
with a signal of that same name, there would be a signal named after each
setter method, and said methods fire off their eponymous signal after they
modify the property.

    There should be some way to rate-limit or temporarily block individual
signals or callback connections.

    The various constructors, etc, would be modified to "subscribe" to
the 'pchanged' signal of all children, such that even if a particular
object in the "middle" of a figure heirarchy does nothing with the
signal, a sort of a global 'pchanged' signal propagates up to the top
object (FigureManager, Canvas, Figure, something).

My current Use Case for these features is in experimenting with different
Artist styles (Text styles/fonts, marker styles/sizes, etc), and I'm tired
of calling canvas.draw() all the time :slight_smile: But also, I'm working on a
GUI to do the same (traits UI), and want to tie both layers of the model
together with callbacks to speed up the experimenting.

I've spent a few hours this weekend doing some meta-monkey-patching--
using __getattribute__ to decorate the setters on-the-fly to invoke
callbacks.process(*args) after the changes. I have a few more quick
hacks to try before I'm ready to decide on a production-ready strategy.

So my question today is: is anyone interested in discussing these
ideas and how to implement them?

Thanks...

I'm interested. I was just noticing a need for the signals to simplify
some interactive stuff I was doing. I'm not wild about using the
current incarnation of the CallbackRegistry, since it doesn't allow
you to add signals after you create the object. Also, there are only
global signals, you can't connect to a specific object (unless you
were planning on each object having its own registry?). When I was
considering this yesterday, I was looking at these:

http://code.activestate.com/recipes/87056/
http://pydispatcher.sourceforge.net/

Also, had you given any thought to using decorators to note methods
that emit a certain signal, or to connect one method to a given
signal?

Ryan

···

On Sat, Oct 23, 2010 at 5:05 PM, David Carmean <dlc@...894...> wrote:

As I blurted on -users, I'm thinking lately about callbacks in the
non-GUI portions of the libraries--mostly Artist and subclasses.
I'm curious if anybody else has been thinking about them?

Ideally, I'd like to see the following:

All of the Artist subclasses, and anything else that might belong to
a Figure, would be updated to use/add cbook.CallbackRegistry callbacks
(weakref = good thing).

In addition to emulating/replacing the simplistic 'pchanged' callback
with a signal of that same name, there would be a signal named after each
setter method, and said methods fire off their eponymous signal after they
modify the property.

There should be some way to rate-limit or temporarily block individual
signals or callback connections.

The various constructors, etc, would be modified to "subscribe" to
the 'pchanged' signal of all children, such that even if a particular
object in the "middle" of a figure heirarchy does nothing with the
signal, a sort of a global 'pchanged' signal propagates up to the top
object (FigureManager, Canvas, Figure, something).

My current Use Case for these features is in experimenting with different
Artist styles (Text styles/fonts, marker styles/sizes, etc), and I'm tired
of calling canvas.draw() all the time :slight_smile: But also, I'm working on a
GUI to do the same (traits UI), and want to tie both layers of the model
together with callbacks to speed up the experimenting.

I've spent a few hours this weekend doing some meta-monkey-patching--
using __getattribute__ to decorate the setters on-the-fly to invoke
callbacks.process(*args) after the changes. I have a few more quick
hacks to try before I'm ready to decide on a production-ready strategy.

So my question today is: is anyone interested in discussing these
ideas and how to implement them?

--
Ryan May
Graduate Research Assistant
School of Meteorology
University of Oklahoma

It's great to see someone working on this. Similar ideas have been thrown around since at least as long as I "joined the party" in 2007 (search the e-mail archives for "Traits"). I like your approach because it should allow for a tighter integration of Traits, while at the same time not adding Traits as a dependency. It just might be the elusive middle ground that prevented us from really going forward way back when.

Mike

···

On 10/23/2010 06:05 PM, David Carmean wrote:

As I blurted on -users, I'm thinking lately about callbacks in the
non-GUI portions of the libraries--mostly Artist and subclasses.
I'm curious if anybody else has been thinking about them?

Ideally, I'd like to see the following:

     All of the Artist subclasses, and anything else that might belong to
a Figure, would be updated to use/add cbook.CallbackRegistry callbacks
(weakref = good thing).

     In addition to emulating/replacing the simplistic 'pchanged' callback
with a signal of that same name, there would be a signal named after each
setter method, and said methods fire off their eponymous signal after they
modify the property.

     There should be some way to rate-limit or temporarily block individual
signals or callback connections.

     The various constructors, etc, would be modified to "subscribe" to
the 'pchanged' signal of all children, such that even if a particular
object in the "middle" of a figure heirarchy does nothing with the
signal, a sort of a global 'pchanged' signal propagates up to the top
object (FigureManager, Canvas, Figure, something).

My current Use Case for these features is in experimenting with different
Artist styles (Text styles/fonts, marker styles/sizes, etc), and I'm tired
of calling canvas.draw() all the time :slight_smile: But also, I'm working on a
GUI to do the same (traits UI), and want to tie both layers of the model
together with callbacks to speed up the experimenting.

I've spent a few hours this weekend doing some meta-monkey-patching--
using __getattribute__ to decorate the setters on-the-fly to invoke
callbacks.process(*args) after the changes. I have a few more quick
hacks to try before I'm ready to decide on a production-ready strategy.

+1 on Mike's middle-ground idea.

In case you haven't seen it, decorators are presently used to allow
Aritist.draw to make a raster mode switch for a MixedModeRenderer.
It's really a generic per-artist before/after draw signal implemented
for that single purpose. This could potentially be refactored if
there's a new signaling system in place.

-Eric

···

On Mon, Oct 25, 2010 at 9:40 AM, Michael Droettboom <mdroe@...31...> wrote:

On 10/23/2010 06:05 PM, David Carmean wrote:

As I blurted on -users, I'm thinking lately about callbacks in the
non-GUI portions of the libraries--mostly Artist and subclasses.
I'm curious if anybody else has been thinking about them?

Ideally, I'd like to see the following:

 All of the Artist subclasses, and anything else that might belong to

a Figure, would be updated to use/add cbook.CallbackRegistry callbacks
(weakref = good thing).

 In addition to emulating/replacing the simplistic &#39;pchanged&#39; callback

with a signal of that same name, there would be a signal named after each
setter method, and said methods fire off their eponymous signal after they
modify the property.

 There should be some way to rate\-limit or temporarily block individual

signals or callback connections.

 The various constructors, etc, would be modified to &quot;subscribe&quot; to

the 'pchanged' signal of all children, such that even if a particular
object in the "middle" of a figure heirarchy does nothing with the
signal, a sort of a global 'pchanged' signal propagates up to the top
object (FigureManager, Canvas, Figure, something).

My current Use Case for these features is in experimenting with different
Artist styles (Text styles/fonts, marker styles/sizes, etc), and I'm tired
of calling canvas.draw() all the time :slight_smile: But also, I'm working on a
GUI to do the same (traits UI), and want to tie both layers of the model
together with callbacks to speed up the experimenting.

I've spent a few hours this weekend doing some meta-monkey-patching--
using __getattribute__ to decorate the setters on-the-fly to invoke
callbacks.process(*args) after the changes. I have a few more quick
hacks to try before I'm ready to decide on a production-ready strategy.

It's great to see someone working on this. Similar ideas have been
thrown around since at least as long as I "joined the party" in 2007
(search the e-mail archives for "Traits"). I like your approach because
it should allow for a tighter integration of Traits, while at the same
time not adding Traits as a dependency. It just might be the elusive
middle ground that prevented us from really going forward way back when.

Mike