-
-
Notifications
You must be signed in to change notification settings - Fork 7.9k
Sliders unresponsive when created inside a function #3105
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
During the A quibble over language, I would say that the slider is 'non-responsive', not 'blocking' which is a term I associate with stopping execution of the whole program. |
OK, for "non-responsive", I updated the issue. Thanks. It would be good if the documentation mentioned how to manage Sliders (widgets?) created in functions that make plots (which can be quite common in programs that make multiple figures). I'm not sure if the method in the example I gave is a good idea (global reference kept), as I'm afraid that it may keep too many Matplotlib objects alive even when the figure is closed. On the other hand, adding an instance attribute to the canvas, that holds the slider, probably defeats the purpose of using of a weak reference in the first place for one of its instance methods… In any case, these questions show that documenting how to use sliders when creating plots in functions would be useful! |
I am planning to add a line to either the My suggestion on how to do this is to have the function return the figure, axes, and widget objects it creates:
|
Are you implying that users must keep references to these three objects in order to keep sliders responsive? the smaller the number of objects, the better… (more legible code, less memory consumed by figures that were closed but maintained in memory because of the references created by the caller, etc.). I like the idea of returning the objects that must be kept in memory, because the caller can handle them locally (no need for a global variable, in general) and release them when/if needed. |
The only obligatory reference to keep is the slider, there are referances to the figure in the pyplot state machine and to the axes from the figure (and vice-versa). However to use the figure/axes in the OO style requires having the other two so might as well return them (as if you are writing scripts you should be using the OO style anyway ;) ). |
I'm glad that only one reference (to the Slider) has to be kept. (Hopefully this does not lead to the figure being kept around if is closed, though, but that's a different issue.) I would suggest that you make explicit in the documentation that "the only obligatory reference to keep is the slider", so that the code is "lighter". (I rarely feel the need to use the OO style, mostly because each figure is created in a single function, or in a well defined part of the code, so there is no ambiguity about what the code is doing, and it is also slightly more legible thanks to the use of fewer variables.) Thank you for your help. :) |
I would argue that using pyplot (for anything but calling I strongly suggest you write functions like this
It is clear what is going on, the plotting logic is separate from the science/business logic, there is no ambiguity over which axes the artists will go to, and your
|
I see what you mean, and I agree that your example is clear. However, I never personally came across a case where plotting in the current axes was unsafe (as long as it is documented):
I agree that knowing in which axes the plotting function does its job generally requires one to check what the current axes are, and that in principle they can been changed as a side effect of some intervening functions. However, in many cases, the state-based approach is pretty clear, and the smaller number of variables arguably makes the code faster to read, and fewer variables need to be kept in working memory, so that's more legible, in my book. Again, though, I agree with you: there is a use for more a more explicit behavior. |
There is an entire genre of SO questions that are "how do I merge two figures" and "why are all of my plots going to the wrong axes?" which the answer boils down to "don't use the state machine". I think that we need to shift the way we introduce mpl to be OO first and then, by the way, the state-machine makes your life easy when working interactively. I am also going to fall back to pep-20 (http://legacy.python.org/dev/peps/pep-0020/): "explicit is better than implicit" |
I see. Then it makes sense to encourage Matplotlib users to use the more explicit approach. A personal note: I do prefer "explicit is better than implicit"; I somehow managed, over a few years now, to be sheltered from the problems you quote even though I've been using writing less explicit code. :) I guess that being fully aware of the concept of current axes and documenting that some functions plot in them helps. |
Added note to widget doc-strings that the user must maintain a reference to the widgets to keep them responsive (if they get gc'd the call backs go away). Some random conversion to numpyboc Closes matplotlib#3105
Thank you. I left a couple of comments on small typos. It would be useful to also add a sentence to the online documentation, in the introduction about widgets at http://matplotlib.org/api/widgets_api.html#gui-neutral-widgets. :) |
When a Slider is created inside a function, it is typically non-responsive (does not react to the mouse):
The problem appears to be fixed by keeping a reference to the slider. The closest thing I've found in the documentation is that a canvas only keeps weak references to its callbacks (http://matplotlib.org/users/event_handling.html). However, the connection with sliders is not so obvious—if there is any.
If I'm not mistaken, this behavior is not documented, so it would be nice to add it to the documentation, if it is normal.
The text was updated successfully, but these errors were encountered: