-
-
Notifications
You must be signed in to change notification settings - Fork 1.9k
SVG trace on selection perf #2583
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
Conversation
... that bypasses DOM style things selection doesn't affect. This speeds up on-selection perf and brings in back to a level comparably to before the persistent selection PR.
src/plots/cartesian/select.js
Outdated
@@ -404,18 +404,20 @@ function updateSelectedState(gd, searchTraces, eventData) { | |||
var len = items.length; | |||
var item0 = items[0]; | |||
var trace0 = item0.cd[0].trace; | |||
var _module = item0._module; | |||
var fn = _module.styleOnSelect || _module.style; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I like styleOnSelect
, very nice solution!
But please call it something more descriptive than fn
here - styleSelection
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
sure thing 😉
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done in 0e91c6e
src/traces/bar/style.js
Outdated
Drawing.selectedPointStyle(s.selectAll('path'), trace, gd); | ||
Drawing.selectedPointStyle(s.selectAll('text'), trace, gd); | ||
} else { | ||
stylePoints(s, trace, gd); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why do we need this else
? I don't see a corresponding case in the previous code...
BTW, I'm hesitant to suggest this after the .select().select()
data-mangling mess, but does it work to do Drawing.selectedPointStyle(s.selectAll('path,text'), trace, gd)
? Is that any faster?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah oops, this should be Drawing.selectedTextStyle(s.selectAll('text'), trace, gd)
. I'll add a test.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why do we need this else? I
To get back to the original state after double-click. Drawing.selectedPointStyle
and Drawing.selectedTextStyle
only handle selected
/ unselected
styling off a "base" state given by stylePoints
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll add a test.
added in 01df2d2
- make Drawing.pointStyle know how to apply [un]selected styles, so that we don't need to update DOM styles twice when we have set `selectedpoints`. - make Drawing.selected(Point|Text)Style no longer need a base state (coming from Drawing.pointStyle) to apply correct styles.
... as on-selection styling now goes a different pathway than restyle().
Commit 3776e8f is a little messy, so I'll explain it here: Previously (i.e. since the persistent selection PR #2135), [un]selected styles were applied to the DOM nodes assuming that the base style had been already applied to DOM nodes. Meaning that to get [un]selected style right, we needed to call Now post commit 3776e8f, Moreover, |
src/components/drawing/index.js
Outdated
}; | ||
|
||
drawing.singlePointStyle = function(d, sel, trace, markerScale, lineScale, gd) { | ||
drawing.makePointStyleFns = function(trace) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Define trace-wide per-pt functions w/o knowledge of d3 or DOM methods so that non-svg modules (e.g. scattermapbox
) can reuse them ♻️
src/components/drawing/index.js
Outdated
s.each(function(d) { | ||
for(var i = 0; i < seq.length; i++) { | ||
seq[i](d3.select(this), d); | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
interesting approach with seq
- it's not obvious to me that this is meaningfully different from 3 s.each
calls inside if(functionExists)
blocks, or 3 if(functionExists)
blocks inside one s.each
, did it make a big difference to do it this way?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
d3's each are a little slower than regular forEach and for-loops. Nothing worth losing sleep over, but we do gains a few ms using this sequence thing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
... by gain, I mean lose a few ms and gain performance. 😄
Looks great! Thanks for the help understanding 3776e8f 💃 |
resolves #2459
There's still plenty of room for improvements (for example via #2548), but this PR gets scatter selection perf back to a level comparable to before the persistent selection PR (in #2135). Unfortunately, this means adding yet another method on the trace module objects. I hope @alexcjohnson won't mind. In brief, the new
styleOnSelect
methods only update DOM styles corresponding theselected
andunselected
attributes and thus by-passes much of the regularstyle
DOM updates.In numbers from the start to end of the selecting throttle using this codepen from #2459, before this PR we had ~300-400ms: and after: ~40-60ms
In gifs:
before
after