-
-
Notifications
You must be signed in to change notification settings - Fork 1.9k
Introducing transform plugins #499
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
- split per-trace defaults step from plots.supplyDataDefaults - call transform module supplyDefaults at end of trace-defaults routine, so that transform default logic can rely on trace defaults - add an applyTransforms step which generates 'expanded' data which themselves go through a trace-default step. - transform functions are expected to supply an array of traces
- the 'traces' array of trace index is now based off gd.data - make all transforms restyle calls go through doCalcdata which is the worse case scenario (i.e. we take no chance!)
EDITThis problem below is solved via 9a341c1 where we made the expanded full traces carry the index of their parent More on the first TODO item ⏫ : First, see example of group-by transform module here. In this module, transformed trace are expanded into as many traces as there are How to resolve this problem? Here are a few possibilities:
transforms: [{
type: 'groupby',
groups: ['a', 'b', 'a', 'b'],
groupsVisible: ['a']
}] would hide the |
else { | ||
dataOut.push(fullTrace); | ||
fill(modules, fullTrace._module); | ||
detect(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.
detect(fullTrace);
?
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.
in fact, this untransformed case needs i
linked in as well. Might as well make eg:
function addFinalTrace(finalTrace) {
finalTrace._input = trace;
finalTrace._inputIndex = i;
finalTrace._expandedIndex = cnt;
dataOut.push(finalTrace);
fill(modules, finalTrace);
detect(finalTrace);
cnt++;
}
since all of that needs to happen identically whichever way you added a trace to _fullData
.
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.
Good catch ⚾ . Thanks!
this looks awesome! with this architecture, my "visual" transforms will also need to have something like a "transform inverse".
my style panels will be built off of similar example with candlestick charts:
|
|
||
if(k.charAt(0) === '_') return; | ||
|
||
if(k === 'transforms') { |
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 think k === 'colorscales'
might need a special case too. I'm not using this plugin but adapted this approach for my own purposes, and I found that when coloring by a continuous variable you end up with errors unless colorscales are left alone. (And just by inspecting the docs, perhaps ticktext
and tickvals
might be special as well.)
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.
The ideal solution would use our Plotly.PlotSchema.crawl
utility to check for data_array
attributes in the incoming traces. Here, only data_array
attributes would have to be truncated.
} | ||
|
||
newTrace.name = groupName; | ||
newTrace.marker.color = opts.groupColors[groupName]; |
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.
We should probably set the color for each relevant trace mode, i.e.
for (var i = 0; i < modes.length; i++) {
newTrace[modes[i]].color = opts.groupColors[groupName];
}
looks like this pull is still alive and kicking. In terms of transforms, I think the vega vocabulary is fairly complete. I assume though that the supporting datalib is probably beyond the scope of I wonder how we might combine Also, one other thought is we might want to look at how |
I gotta say, this transform stuff is working quite well! Though there may be a bug, I'm still trying to figure it out: I'm not 100% sure why this happens, but for any transform you make, if you add a new trace during the transform, you can't hide the trace by clicking it in the legend :s I've only tried this by adding a new scatter trace with mode lines. |
Yep, that's a known bug. See #499 (comment) If you have any insight on what the desired behaviour should be, let me know. |
@armintaheri, the legend seems to get fixed when I merged in @rreusser's |
I doubt it. That would be some crazy magic fix from 🙏 if that's the case. |
Yeah @timelyportfolio the transforms included in this PR are meant for testing purposes only. Looking forward to seeing what you come up with 🍻 |
@bpostlethwaite please review commits (off a different branch): |
- remove error when array container are not of the same length - this is a temporary fix until #749 is addressed.
- move traceOut.index and traceOut._input assignments out of supplyTraceDefaults for clarity - 'index' ref -> index in user data (as before) - '_input' ref -> trace in user data (as before) - '_expandedIndex' ref -> index in fullData - '_expandedInput' ref -> full trace after transform, before 2nd trace dflts
- so that the 'same' expanded trace keep the same uid on update.
- module.transform must be a function - module.attributes and module.supplyDefaults are recommended but optional - log warning if transform module associated with transform type isn't found - extend traceIn if no supplyDefaults method is found.
@etpinard, should I be using |
@bpostlethwaite @chriddyp @timelyportfolio @rreusser @armintaheri this PR is now ready for review. |
…ing" This reverts commit a06441a.
assets/ is ambiguous as now test/images/assets/ exists
nice work! New age of hackerdackery for Plotly.js 💃 ! |
@timelyportfolio have you made any progress on your transform modules? |
@etpinard, yes, in multiple branches. Yesterday, I started new branch off I moved transforms to On In terms of a fuller discussion in case we want to really push it, I just set up this Wiki https://github.com/timelyportfolio/plotly.js/wiki/Discussion---Transforms. |
@timelyportfolio thanks for the info! |
@mdtusz @chriddyp @bpostlethwaite @alexcjohnson @jackparmer
This PR adds support for custom data transforms to be plugged into plotly.js via
Plotly.register
.In brief
Plotly.register
can now register transform modules 9ac6d0fgd._fullData
no longer have to be of the samelength
. 06f2e6dPlotly.restyle
can now handle transformed data 8ab9d0cExamples
A filter and group-by were added as examples in 2697975
Does it work?
See 56665f2
TODOs
transform
method.transforms
attributes into plot schema. (done, see b5ec01e)