Skip to content
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

Draw & adjust new shapes over image trace and cartesian subplots #4775

Merged
merged 71 commits into from
Apr 28, 2020

Conversation

archmoj
Copy link
Contributor

@archmoj archmoj commented Apr 20, 2020

Resolves #4374.

As illustrated in demo, this PR enables drawing and editing shapes over image trace (as well as cartesian subplots).

New layout attributes are

{
    `shape`: {
        `fillrule`: 'evenodd' | 'nonzero'
        `editable`: false | true
    },

    `newshape`: {
        `line`: {
            `width`:
            `dash`:
            `color`:
        },
        `fillcolor`:
        `fillrule`:  'evenodd' | 'nonzero'
        `opacity`:
        `layer`: 'above' | 'below'
        `drawdirection`: 'diagonal' | 'horizontal' | 'vertical' | 'ortho' 
    },

    `activeshape: {
        `fillcolor`:
        `opacity`:
    }
}

For more info regarding new attributes, please visit

newshape: {
line: {
color: {
valType: 'color',
editType: 'none',
role: 'info',
description: [
'Sets the line color.',
'By default uses either dark grey or white',
'to increase contrast with background color.'
].join(' ')
},
width: {
valType: 'number',
min: 0,
dflt: 4,
role: 'info',
editType: 'none',
description: 'Sets the line width (in px).'
},
dash: extendFlat({}, dash, {
dflt: 'solid',
editType: 'none'
}),
role: 'info',
editType: 'none'
},
fillcolor: {
valType: 'color',
dflt: 'rgba(0,0,0,0)',
role: 'info',
editType: 'none',
description: [
'Sets the color filling new shapes\' interior.',
'Please note that if using a fillcolor with alpha greater than half,',
'drag inside the active shape starts moving the shape underneath,',
'otherwise a new shape could be started over.'
].join(' ')
},
fillrule: {
valType: 'enumerated',
values: ['evenodd', 'nonzero'],
dflt: 'evenodd',
role: 'info',
editType: 'none',
description: [
'Determines the path\'s interior.',
'For more info please visit https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/fill-rule'
].join(' ')
},
opacity: {
valType: 'number',
min: 0,
max: 1,
dflt: 1,
role: 'info',
editType: 'none',
description: 'Sets the opacity of new shapes.'
},
layer: {
valType: 'enumerated',
values: ['below', 'above'],
dflt: 'above',
role: 'info',
editType: 'none',
description: 'Specifies whether new shapes are drawn below or above traces.'
},
drawdirection: {
valType: 'enumerated',
role: 'info',
values: ['ortho', 'horizontal', 'vertical', 'diagonal'],
dflt: 'diagonal',
editType: 'none',
description: [
'When `dragmode` is set to *drawrect*, *drawline* or *drawcircle*',
'this limits the drag to be horizontal, vertical or diagonal.',
'Using *diagonal* there is no limit e.g. in drawing lines in any direction.',
'*ortho* limits the draw to be either horizontal or vertical.',
'*horizontal* allows horizontal extend.',
'*vertical* allows vertical extend.'
].join(' ')
},
editType: 'none'
},
activeshape: {
fillcolor: {
valType: 'color',
dflt: 'rgb(255,0,255)',
role: 'style',
editType: 'none',
description: 'Sets the color filling the active shape\' interior.'
},
opacity: {
valType: 'number',
min: 0,
max: 1,
dflt: 0.5,
role: 'info',
editType: 'none',
description: 'Sets the opacity of the active shape.'
},
editType: 'none'
}

as well as
fillrule: {
valType: 'enumerated',
values: ['evenodd', 'nonzero'],
dflt: 'evenodd',
role: 'info',
editType: 'arraydraw',
description: [
'Determines which regions of complex paths constitute the interior.',
'For more info please visit https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/fill-rule'
].join(' ')
},
editable: {
valType: 'boolean',
role: 'info',
dflt: false,
editType: 'calc+arraydraw',
description: [
'Determines whether the shape could be activated for edit or not.',
'Has no effect when the older editable shapes mode is enabled via',
'`config.editable` or `config.edits.shapePosition`.'
].join(' ')
.

New modebar buttons could simply be added by passing strings (instead of objects) in config.
For example:

modeBarButtonsToAdd: [
  'drawline',
  'drawopenpath',
  'drawclosedpath',
  'drawcircle',
  'drawrect',
  'eraseshape'
]

@plotly/plotly_js
@emmanuelle

@archmoj archmoj added this to the v1.54.0 milestone Apr 20, 2020
@alexcjohnson
Copy link
Collaborator

New dragmode options are linedraw, rectdraw, ellipsedraw, closedfreedraw and openfreedraw.

Thoughts on naming? I might vote for:
drawline
drawrect
drawcircle (because even though it doesn't need to be 1:1, the shape you make is type: 'circle'),
drawfreeclosed, drawfreeopen (or maybe drawclosedpath and drawopenpath?)

@archmoj
Copy link
Contributor Author

archmoj commented Apr 20, 2020

New dragmode options are linedraw, rectdraw, ellipsedraw, closedfreedraw and openfreedraw.

Thoughts on naming? I might vote for:
drawline
drawrect
drawcircle (because even though it doesn't need to be 1:1, the shape you make is type: 'circle'),
drawfreeclosed, drawfreeopen (or maybe drawclosedpath and drawopenpath?)

Good call. Revised in a585394.

@archmoj
Copy link
Contributor Author

archmoj commented Apr 28, 2020

@alexcjohnson here is a demo with shapes on template.

Copy link
Collaborator

@alexcjohnson alexcjohnson left a comment

Choose a reason for hiding this comment

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

💃 👯 🕺

@jackparmer
Copy link
Contributor

Incredible work as always Mojtaba!!

@archmoj archmoj merged commit 891b6a1 into master Apr 28, 2020
@archmoj archmoj deleted the shape-drawing branch April 28, 2020 20:24
@emmanuelle
Copy link
Contributor

Hurray! 🎉 😍

@pfebrer
Copy link

pfebrer commented May 11, 2020

Just wanted to say that this is amazing :)

I hope you don't mind this quick question: Are these changes automatically available in react-plotly.js? I updated plotly.py and it works, but when I try it on react I just get a white canvas.

Thanks in advance and sorry if the question does not belong here.

@nicolaskruchten
Copy link
Contributor

Glad you like it!

In principle these should be available in react-plotly.js if you upgrade the version of plotly.js via npm install or yarn install, yes.

@pfebrer
Copy link

pfebrer commented May 11, 2020

Makes sense 😄

I somehow thought that plotly.js would get updated automatically when I reinstalled react-plotly.js. All good now, thanks!

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

Successfully merging this pull request may close these issues.

Shape drawing
6 participants