Skip to content

PRF: only check some artists on mousemove #4878

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

Merged
merged 5 commits into from
Aug 16, 2015

Conversation

tacaswell
Copy link
Member

Instead of walking the full hitlist of the Axes, only check artists
that ask to be part of the mouseover events.

This is still missing logic to remove the artist from the mouseover_set
when removing the artist from the Axes.

This is an alternative to #4847

attn @blink1073

Instead of walking the full hitlist of the Axes, only check artists
that ask to be part of the mouseover events.

This is still missing logic to remove the artist from the mouseover_set
when removing the artist from the Axes.
@tacaswell tacaswell added this to the next point release milestone Aug 7, 2015
@blink1073
Copy link
Member

What would be wrong with checking a.mouseover directly and avoiding mouseover_set?

@tacaswell
Copy link
Member Author

I was trying to avoid walking the artist tree at all and avoid changing hit
list which i assume is used else where.

On the other hand, self.get_children would only do one layer, be only a bit
slower (I am guessing which I know is always a bad idea) and be a lot
simpler.

On Fri, Aug 7, 2015, 9:05 AM Steven Silvester notifications@github.com
wrote:

What would be wrong with checking a.mouseover directly and avoiding
mouseover_set?


Reply to this email directly or view it on GitHub
#4878 (comment)
.

@blink1073
Copy link
Member

You're right, it makes more sense the way it is now.

@fariza
Copy link
Member

fariza commented Aug 7, 2015

I prefer this approach to using the hitlist, it's cleaner and easier to follow what's being reported.

@tacaswell I think this would be a good place to also address #4284 making, a similar property in axes, to report or not.

@tacaswell
Copy link
Member Author

@fariza Possibly, but by the time we get to this code, the decision about what Axes to hand the event to to process has already been made, although it is probably simple to look up if there are any twin axes here.

I am inclined to punt on that to get the mouse-over code shippable ASAP.

@WeatherGod
Copy link
Member

Initially reported over in #4738 , I encountered a very troubling bug with NavigationToolbar2.mouse_over. When I display a very large image (haven't tried smaller images), and I pass the mouse over the figure window, memory usage increases by 100s of MBs every few seconds, and it doesn't seem to stop increasing. I eventually have to kill -9 the process when it gets up to around 5GB. This behavior is present even with this PR.

@tacaswell
Copy link
Member Author

Also close #4918

This is useful when removing artists from an `Axes`
 - disconnect the stale_callback (this assumes that matplotlib#4738 goes in)
 - remove the artist from the Axes.mousover_set
 - marks the parent axes/figure as stale
 - resets the artist's axes/figure to None
@tacaswell
Copy link
Member Author

@matplotlib/developers I think this is ready to go.

@tacaswell
Copy link
Member Author

Forgot this last thing from been when i was working on this/writing up the
current state last night.

On Wed, Aug 12, 2015, 2:54 PM Benjamin Root notifications@github.com
wrote:

Initially reported over in #4738
#4738 , I encountered a
very troubling bug with NavigationToolbar2.mouse_over. When I display a
very large image (haven't tried smaller images), and I pass the mouse over
the figure window, memory usage increases by 100s of MBs every few seconds,
and it doesn't seem to stop increasing. I eventually have to kill -9 the
process when it gets up to around 5GB. This behavior is present even with
this PR.


Reply to this email directly or view it on GitHub
#4878 (comment)
.

@tacaswell
Copy link
Member Author

Been should be Ben.

On Fri, Aug 14, 2015, 8:08 AM Thomas Caswell tcaswell@gmail.com wrote:

Forgot this last thing from been when i was working on this/writing up the
current state last night.

On Wed, Aug 12, 2015, 2:54 PM Benjamin Root notifications@github.com
wrote:

Initially reported over in #4738
#4738 , I encountered a
very troubling bug with NavigationToolbar2.mouse_over. When I display a
very large image (haven't tried smaller images), and I pass the mouse over
the figure window, memory usage increases by 100s of MBs every few seconds,
and it doesn't seem to stop increasing. I eventually have to kill -9 the
process when it gets up to around 5GB. This behavior is present even with
this PR.


Reply to this email directly or view it on GitHub
#4878 (comment)
.

@WeatherGod
Copy link
Member

I did a little bit more investigation on this. The data I was displaying
were masked arrays from netCDF4 objects. Meanwhile, if I simply create
large masked arrays with random data, I cannot reproduce the problem. So,
perhaps there is something about how we are interacting with views of data
that (I believe) is memmapped?

On Fri, Aug 14, 2015 at 8:09 AM, Thomas A Caswell notifications@github.com
wrote:

Been should be Ben.

On Fri, Aug 14, 2015, 8:08 AM Thomas Caswell tcaswell@gmail.com wrote:

Forgot this last thing from been when i was working on this/writing up
the
current state last night.

On Wed, Aug 12, 2015, 2:54 PM Benjamin Root notifications@github.com
wrote:

Initially reported over in #4738
#4738 , I encountered a
very troubling bug with NavigationToolbar2.mouse_over. When I display a
very large image (haven't tried smaller images), and I pass the mouse
over
the figure window, memory usage increases by 100s of MBs every few
seconds,
and it doesn't seem to stop increasing. I eventually have to kill -9 the
process when it gets up to around 5GB. This behavior is present even
with
this PR.


Reply to this email directly or view it on GitHub
<
https://github.com/matplotlib/matplotlib/pull/4878#issuecomment-130411057>
.


Reply to this email directly or view it on GitHub
#4878 (comment)
.

@jenshnielsen
Copy link
Member

The test error on python 2.6 looks real

ERROR: Failure: AttributeError ('module' object has no attribute 'test_artist')
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/home/travis/build/matplotlib/matplotlib/venv/lib/python2.6/site-packages/nose/loader.py", line 407, in loadTestsFromName
    module = resolve_name(addr.module)
  File "/home/travis/build/matplotlib/matplotlib/venv/lib/python2.6/site-packages/nose/util.py", line 322, in resolve_name
    obj = getattr(obj, part)
AttributeError: 'module' object has no attribute 'test_artist'

@tacaswell
Copy link
Member Author

The failure is due to import errors in test_artist in 2.6, hurray.

I really want to just drop 2.6, but I will get this sorted out.

@jenshnielsen
Copy link
Member

Im 👍 on dropping python 2.6 but I guess should keep it round for 1.5 and 2.0. Skipping the tests on Python 2.6 is IMHO an acceptable solution if the import error is in the test.

@OceanWolf
Copy link
Member

Drop 2.6??? Could we do that for 2.x? OrderedDicts here we come! 😄.

Apparently `assert_is`,  `assert_in`, and `assert_not_in` are
not in the 2.6 version of nose, but are in all others.
@tacaswell
Copy link
Member Author

The problem was that some of the fancier assert statements are not in 2.6, but are every where else (despite nose having the same version). I just switched to using assert_true which is easier than setting up conditional tests and local imports.

jenshnielsen added a commit that referenced this pull request Aug 16, 2015
PRF: only check some artists on mousemove
@jenshnielsen jenshnielsen merged commit be93150 into matplotlib:master Aug 16, 2015
@tacaswell tacaswell deleted the prf_mouse_move_event branch August 17, 2015 00:02
@@ -961,6 +980,21 @@ def format_cursor_data(self, data):
data = [data]
return ', '.join('{:0.3g}'.format(item) for item in data)

@property
def mouseover(self):
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just wondering, have you ever measured the performance of descriptor access vs attribute lookup. You might be quite shocked 😱

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have not, but I made this a property for the setter functionality.

@tacaswell
Copy link
Member Author

@pelson I agree this isn't great, but the hitlist solution was taking longer to run than the time between mouse events and the automatic mouse-over functionality is one people have been asking for for years.

Another option I see is to periodically walk the children and cache which of them have a message to add to the mouse over string, but that has a higher chance of going out of sync than this method does.

I have no problem renaming mouseover_set.

@@ -147,6 +147,23 @@ def remove(self):
# callback has one parameter, which is the child to be removed.
if self._remove_method is not None:
self._remove_method(self)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Surely the logic for removing from the axes should live in the remove method itself. Is there a reason we can't do that?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants