-
-
Notifications
You must be signed in to change notification settings - Fork 1.9k
Enable & disable predefined modebar buttons via layout and template #5660
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
Changes from 7 commits
117e39c
154431f
dd842bd
3933b88
aeb1626
2056773
bf3416d
3daa2f3
096674c
5c17d6b
3293097
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,89 @@ | ||
| 'use strict'; | ||
|
|
||
| var modeBarButtons = require('./buttons'); | ||
| var buttonList = Object.keys(modeBarButtons); | ||
| var backButtons = [ | ||
| 'v1hovermode', | ||
| 'hoverclosest', | ||
| 'hovercompare', | ||
| 'togglehover', | ||
| 'togglespikelines', | ||
| 'drawclosedpath', | ||
| 'drawopenpath', | ||
| 'drawline', | ||
| 'drawrect', | ||
| 'drawcircle', | ||
| 'eraseshape', | ||
| ]; | ||
|
|
||
| var foreButtons = []; | ||
| var addToForeButtons = function(b) { | ||
| if(backButtons.indexOf(b._cat || b.name) !== -1) return; | ||
| // for convenience add lowercase shotname e.g. zoomin as well fullname zoomInGeo | ||
| var name = b.name; | ||
| var _cat = (b._cat || b.name).toLowerCase(); | ||
| if(foreButtons.indexOf(name) === -1) foreButtons.push(name); | ||
| if(foreButtons.indexOf(_cat) === -1) foreButtons.push(_cat); | ||
| }; | ||
| buttonList.forEach(function(k) { | ||
| addToForeButtons(modeBarButtons[k]); | ||
| }); | ||
| foreButtons.sort(); | ||
|
|
||
| module.exports = { | ||
| editType: 'modebar', | ||
|
|
||
| orientation: { | ||
| valType: 'enumerated', | ||
| values: ['v', 'h'], | ||
| dflt: 'h', | ||
| editType: 'modebar', | ||
| description: 'Sets the orientation of the modebar.' | ||
| }, | ||
| bgcolor: { | ||
| valType: 'color', | ||
| editType: 'modebar', | ||
| description: 'Sets the background color of the modebar.' | ||
| }, | ||
| color: { | ||
| valType: 'color', | ||
| editType: 'modebar', | ||
| description: 'Sets the color of the icons in the modebar.' | ||
| }, | ||
| activecolor: { | ||
| valType: 'color', | ||
| editType: 'modebar', | ||
| description: 'Sets the color of the active or hovered on icons in the modebar.' | ||
| }, | ||
| uirevision: { | ||
| valType: 'any', | ||
| editType: 'none', | ||
| description: [ | ||
| 'Controls persistence of user-driven changes related to the modebar,', | ||
| 'including `hovermode`, `dragmode`, and `showspikes` at both the', | ||
| 'root level and inside subplots. Defaults to `layout.uirevision`.' | ||
| ].join(' ') | ||
| }, | ||
| add: { | ||
| valType: 'flaglist', | ||
| flags: backButtons, | ||
| dflt: '', | ||
| editType: 'modebar', | ||
| description: [ | ||
| 'Determines which predefined modebar buttons to add.', | ||
| 'Please note that these buttons will only be shown if they are', | ||
| 'compatible with all trace types used in a graph.', | ||
| 'Similar to `config.modeBarButtonsToAdd` option' | ||
| ].join(' ') | ||
| }, | ||
| remove: { | ||
| valType: 'flaglist', | ||
| flags: foreButtons, | ||
| dflt: '', | ||
| editType: 'modebar', | ||
| description: [ | ||
| 'Determines which predefined modebar buttons to remove.', | ||
| 'Similar to `config.modeBarButtonsToRemove` option' | ||
| ].join(' ') | ||
| } | ||
| }; | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,24 @@ | ||
| 'use strict'; | ||
|
|
||
| var Lib = require('../../lib'); | ||
| var Color = require('../color'); | ||
| var Template = require('../../plot_api/plot_template'); | ||
| var attributes = require('./attributes'); | ||
|
|
||
| module.exports = function supplyLayoutDefaults(layoutIn, layoutOut) { | ||
| var containerIn = layoutIn.modebar || {}; | ||
| var containerOut = Template.newContainer(layoutOut, 'modebar'); | ||
|
|
||
| function coerce(attr, dflt) { | ||
| return Lib.coerce(containerIn, containerOut, attributes, attr, dflt); | ||
| } | ||
|
|
||
| coerce('orientation'); | ||
| coerce('bgcolor', Color.addOpacity(layoutOut.paper_bgcolor, 0.5)); | ||
| var defaultColor = Color.contrast(Color.rgb(layoutOut.modebar.bgcolor)); | ||
| coerce('color', Color.addOpacity(defaultColor, 0.3)); | ||
| coerce('activecolor', Color.addOpacity(defaultColor, 0.7)); | ||
| coerce('uirevision', layoutOut.uirevision); | ||
| coerce('add'); | ||
| coerce('remove'); | ||
| }; |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,3 +1,11 @@ | ||
| 'use strict'; | ||
|
|
||
| exports.manage = require('./manage'); | ||
| module.exports = { | ||
| moduleType: 'component', | ||
| name: 'modebar', | ||
|
|
||
| layoutAttributes: require('./attributes'), | ||
| supplyLayoutDefaults: require('./defaults'), | ||
|
|
||
| manage: require('./manage') | ||
| }; |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -72,8 +72,10 @@ function getButtonGroups(gd) { | |
| var fullLayout = gd._fullLayout; | ||
| var fullData = gd._fullData; | ||
| var context = gd._context; | ||
| var buttonsToRemove = context.modeBarButtonsToRemove; | ||
| var buttonsToAdd = context.modeBarButtonsToAdd; | ||
| var buttonsToAdd = context.modeBarButtonsToAdd | ||
| .concat(fullLayout.modebar.add.split('+')); | ||
| var buttonsToRemove = context.modeBarButtonsToRemove | ||
| .concat(fullLayout.modebar.remove.split('+')); | ||
|
||
|
|
||
| var hasCartesian = fullLayout._has('cartesian'); | ||
| var hasGL3D = fullLayout._has('gl3d'); | ||
|
|
@@ -96,9 +98,20 @@ function getButtonGroups(gd) { | |
| var out = []; | ||
|
|
||
| for(var i = 0; i < newGroup.length; i++) { | ||
| var button = newGroup[i]; | ||
| if(buttonsToRemove.indexOf(button) !== -1) continue; | ||
| out.push(modeBarButtons[button]); | ||
| var name = newGroup[i]; | ||
| var B = modeBarButtons[name]; | ||
| var v0 = B.name.toLowerCase(); | ||
| var v1 = (B._cat || B.name).toLowerCase(); | ||
| var found = false; | ||
| for(var q = 0; q < buttonsToRemove.length; q++) { | ||
| var t = buttonsToRemove[q].toLowerCase(); | ||
| if(t === v0 || t === v1) { | ||
| found = true; | ||
| break; | ||
| } | ||
| } | ||
| if(found) continue; | ||
| out.push(modeBarButtons[name]); | ||
| } | ||
|
|
||
| groups.push(out); | ||
|
|
||
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.
Using a flaglist here is convenient for validation, but it's different from the API we use for config, an array. Here we don't need to support the object form, which obviously wouldn't fit in a flaglist, I just wonder if ease of validation is sufficient reason to differ. @nicolaskruchten thoughts?
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 prefer an array, like in config
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.
Addressed in 5c17d6b and 3293097.