From 2653067439716a9dbae235b5d389f1d8135ca078 Mon Sep 17 00:00:00 2001 From: Eric Lavault <39483232+lvlte@users.noreply.github.com> Date: Sun, 20 Aug 2023 13:41:53 +0200 Subject: [PATCH 1/5] Allow to remove a scaleanchor constraint that is set by default --- src/plots/cartesian/constraints.js | 2 +- src/plots/cartesian/layout_attributes.js | 12 +++++++++--- 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/src/plots/cartesian/constraints.js b/src/plots/cartesian/constraints.js index 27596ff4eb9..d825cd92e3e 100644 --- a/src/plots/cartesian/constraints.js +++ b/src/plots/cartesian/constraints.js @@ -253,7 +253,7 @@ function handleOneAxDefaults(axIn, axOut, opts) { scaleanchor = Lib.coerce(axIn, axOut, { scaleanchor: { valType: 'enumerated', - values: linkableAxes + values: linkableAxes.concat([false]) } }, 'scaleanchor', scaleanchorDflt); } diff --git a/src/plots/cartesian/layout_attributes.js b/src/plots/cartesian/layout_attributes.js index 94cc77d9d9f..b3854603116 100644 --- a/src/plots/cartesian/layout_attributes.js +++ b/src/plots/cartesian/layout_attributes.js @@ -330,12 +330,13 @@ module.exports = { ].join(' ') }, // scaleanchor: not used directly, just put here for reference - // values are any opposite-letter axis id + // values are any opposite-letter axis id, or `false`. scaleanchor: { valType: 'enumerated', values: [ constants.idRegex.x.toString(), - constants.idRegex.y.toString() + constants.idRegex.y.toString(), + false ], editType: 'plot', description: [ @@ -353,7 +354,12 @@ module.exports = { 'and the last constraint encountered will be ignored to avoid possible', 'inconsistent constraints via `scaleratio`.', 'Note that setting axes simultaneously in both a `scaleanchor` and a `matches` constraint', - 'is currently forbidden.' + 'is currently forbidden.', + 'Setting `false` allows to remove a default constraint (occasionally,', + 'you may need to prevent a default `scaleanchor` constraint from', + 'being applied, eg. when having an image trace `yaxis: {scaleanchor: "x"}`', + 'is set automatically in order for pixels to be rendered as squares,', + 'setting `yaxis: {scaleanchor: false}` allows to remove the constraint).' ].join(' ') }, scaleratio: { From 7bde3b7229e79d2406eef059dd68420c7a1b9483 Mon Sep 17 00:00:00 2001 From: Eric Lavault <39483232+lvlte@users.noreply.github.com> Date: Sun, 20 Aug 2023 13:47:07 +0200 Subject: [PATCH 2/5] Add test case (image scaleanchor removal) --- test/jasmine/tests/image_test.js | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/test/jasmine/tests/image_test.js b/test/jasmine/tests/image_test.js index a5fe6fd4a77..81fa1d28105 100644 --- a/test/jasmine/tests/image_test.js +++ b/test/jasmine/tests/image_test.js @@ -209,6 +209,14 @@ describe('image smart layout defaults', function() { expect(gd._fullLayout.yaxis.scaleanchor).toBe('x'); }); + it('should NOT set scaleanchor if asked not to', function() { + gd = {}; + gd.data = [{type: 'image', z: [[[255, 0, 0]]]}]; + gd.layout = {yaxis: {scaleanchor: false}}; + supplyAllDefaults(gd); + expect(gd._fullLayout.yaxis.scaleanchor).toBe(false); + }); + it('should NOT reset scaleanchor if it\'s already defined', function() { gd.data = [{type: 'image', z: [[[255, 0, 0]]]}, {y: [5, 3, 2], xaxis: 'x3'}]; gd.layout = {yaxis: {scaleanchor: 'x3'}}; From e83dc48675f15205a6a9cebbf081c98bd3d6499b Mon Sep 17 00:00:00 2001 From: Eric Lavault <39483232+lvlte@users.noreply.github.com> Date: Sun, 20 Aug 2023 14:18:04 +0200 Subject: [PATCH 3/5] update plot-schema diff --- test/plot-schema.json | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/test/plot-schema.json b/test/plot-schema.json index 8e8dcb0356c..c155a45d912 100644 --- a/test/plot-schema.json +++ b/test/plot-schema.json @@ -11157,12 +11157,13 @@ }, "role": "object", "scaleanchor": { - "description": "If set to another axis id (e.g. `x2`, `y`), the range of this axis changes together with the range of the corresponding axis such that the scale of pixels per unit is in a constant ratio. Both axes are still zoomable, but when you zoom one, the other will zoom the same amount, keeping a fixed midpoint. `constrain` and `constraintoward` determine how we enforce the constraint. You can chain these, ie `yaxis: {scaleanchor: *x*}, xaxis2: {scaleanchor: *y*}` but you can only link axes of the same `type`. The linked axis can have the opposite letter (to constrain the aspect ratio) or the same letter (to match scales across subplots). Loops (`yaxis: {scaleanchor: *x*}, xaxis: {scaleanchor: *y*}` or longer) are redundant and the last constraint encountered will be ignored to avoid possible inconsistent constraints via `scaleratio`. Note that setting axes simultaneously in both a `scaleanchor` and a `matches` constraint is currently forbidden.", + "description": "If set to another axis id (e.g. `x2`, `y`), the range of this axis changes together with the range of the corresponding axis such that the scale of pixels per unit is in a constant ratio. Both axes are still zoomable, but when you zoom one, the other will zoom the same amount, keeping a fixed midpoint. `constrain` and `constraintoward` determine how we enforce the constraint. You can chain these, ie `yaxis: {scaleanchor: *x*}, xaxis2: {scaleanchor: *y*}` but you can only link axes of the same `type`. The linked axis can have the opposite letter (to constrain the aspect ratio) or the same letter (to match scales across subplots). Loops (`yaxis: {scaleanchor: *x*}, xaxis: {scaleanchor: *y*}` or longer) are redundant and the last constraint encountered will be ignored to avoid possible inconsistent constraints via `scaleratio`. Note that setting axes simultaneously in both a `scaleanchor` and a `matches` constraint is currently forbidden. Setting `false` allows to remove a default constraint (occasionally, you may need to prevent a default `scaleanchor` constraint from being applied, eg. when having an image trace `yaxis: {scaleanchor: \"x\"}` is set automatically in order for pixels to be rendered as squares, setting `yaxis: {scaleanchor: false}` allows to remove the constraint).", "editType": "plot", "valType": "enumerated", "values": [ "/^x([2-9]|[1-9][0-9]+)?( domain)?$/", - "/^y([2-9]|[1-9][0-9]+)?( domain)?$/" + "/^y([2-9]|[1-9][0-9]+)?( domain)?$/", + false ] }, "scaleratio": { @@ -12167,12 +12168,13 @@ }, "role": "object", "scaleanchor": { - "description": "If set to another axis id (e.g. `x2`, `y`), the range of this axis changes together with the range of the corresponding axis such that the scale of pixels per unit is in a constant ratio. Both axes are still zoomable, but when you zoom one, the other will zoom the same amount, keeping a fixed midpoint. `constrain` and `constraintoward` determine how we enforce the constraint. You can chain these, ie `yaxis: {scaleanchor: *x*}, xaxis2: {scaleanchor: *y*}` but you can only link axes of the same `type`. The linked axis can have the opposite letter (to constrain the aspect ratio) or the same letter (to match scales across subplots). Loops (`yaxis: {scaleanchor: *x*}, xaxis: {scaleanchor: *y*}` or longer) are redundant and the last constraint encountered will be ignored to avoid possible inconsistent constraints via `scaleratio`. Note that setting axes simultaneously in both a `scaleanchor` and a `matches` constraint is currently forbidden.", + "description": "If set to another axis id (e.g. `x2`, `y`), the range of this axis changes together with the range of the corresponding axis such that the scale of pixels per unit is in a constant ratio. Both axes are still zoomable, but when you zoom one, the other will zoom the same amount, keeping a fixed midpoint. `constrain` and `constraintoward` determine how we enforce the constraint. You can chain these, ie `yaxis: {scaleanchor: *x*}, xaxis2: {scaleanchor: *y*}` but you can only link axes of the same `type`. The linked axis can have the opposite letter (to constrain the aspect ratio) or the same letter (to match scales across subplots). Loops (`yaxis: {scaleanchor: *x*}, xaxis: {scaleanchor: *y*}` or longer) are redundant and the last constraint encountered will be ignored to avoid possible inconsistent constraints via `scaleratio`. Note that setting axes simultaneously in both a `scaleanchor` and a `matches` constraint is currently forbidden. Setting `false` allows to remove a default constraint (occasionally, you may need to prevent a default `scaleanchor` constraint from being applied, eg. when having an image trace `yaxis: {scaleanchor: \"x\"}` is set automatically in order for pixels to be rendered as squares, setting `yaxis: {scaleanchor: false}` allows to remove the constraint).", "editType": "plot", "valType": "enumerated", "values": [ "/^x([2-9]|[1-9][0-9]+)?( domain)?$/", - "/^y([2-9]|[1-9][0-9]+)?( domain)?$/" + "/^y([2-9]|[1-9][0-9]+)?( domain)?$/", + false ] }, "scaleratio": { @@ -75392,4 +75394,4 @@ } } } -} \ No newline at end of file +} From 735b9738a8f7f840c6edf1f0d250d1df8486d929 Mon Sep 17 00:00:00 2001 From: Eric Lavault <39483232+lvlte@users.noreply.github.com> Date: Sun, 20 Aug 2023 14:32:19 +0200 Subject: [PATCH 4/5] update plot-schema diff again --- test/plot-schema.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/plot-schema.json b/test/plot-schema.json index c155a45d912..6a1f962255c 100644 --- a/test/plot-schema.json +++ b/test/plot-schema.json @@ -75394,4 +75394,4 @@ } } } -} +} \ No newline at end of file From b55fd0618fc9b462ec412ba622331a1d88315d7c Mon Sep 17 00:00:00 2001 From: Eric Lavault <39483232+lvlte@users.noreply.github.com> Date: Mon, 21 Aug 2023 18:08:03 +0200 Subject: [PATCH 5/5] Add draftlog --- draftlogs/6712_add.md | 1 + 1 file changed, 1 insertion(+) create mode 100644 draftlogs/6712_add.md diff --git a/draftlogs/6712_add.md b/draftlogs/6712_add.md new file mode 100644 index 00000000000..ac47acf1823 --- /dev/null +++ b/draftlogs/6712_add.md @@ -0,0 +1 @@ +- Allow to remove a scaleanchor constraint that is set by default [[#6712](https://github.com/plotly/plotly.js/pull/6712)], with thanks to @lvlte for the contribution!