Skip to content

Commit 87782ba

Browse files
committed
🔒 down default axis range, 🔒 order of elements in gauges
1 parent 8e113eb commit 87782ba

File tree

11 files changed

+120
-56
lines changed

11 files changed

+120
-56
lines changed

src/traces/indicator/attributes.js

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -77,16 +77,17 @@ var rangeAttr = {
7777
],
7878
editType: 'plot',
7979
description: [
80-
'Sets the range of this axis.',
81-
'If the axis `type` is *log*, then you must take the log of your',
82-
'desired range (e.g. to set the range from 1 to 100,',
83-
'set the range from 0 to 2).',
84-
'If the axis `type` is *date*, it should be date strings,',
85-
'like date data, though Date objects and unix milliseconds',
86-
'will be accepted and converted to strings.',
87-
'If the axis `type` is *category*, it should be numbers,',
88-
'using the scale where each category is assigned a serial',
89-
'number from zero in the order it appears.'
80+
'Sets the range of this axis.'
81+
// TODO: add support for other axis type
82+
// 'If the axis `type` is *log*, then you must take the log of your',
83+
// 'desired range (e.g. to set the range from 1 to 100,',
84+
// 'set the range from 0 to 2).',
85+
// 'If the axis `type` is *date*, it should be date strings,',
86+
// 'like date data, though Date objects and unix milliseconds',
87+
// 'will be accepted and converted to strings.',
88+
// 'If the axis `type` is *category*, it should be numbers,',
89+
// 'using the scale where each category is assigned a serial',
90+
// 'number from zero in the order it appears.'
9091
].join(' ')
9192
};
9293

@@ -364,6 +365,7 @@ module.exports = {
364365
].join(' ')
365366
}),
366367
width: extendFlat({}, gaugeBarAttrs.line.width, {
368+
dflt: 1,
367369
description: [
368370
'Sets the width (in px) of the threshold line.'
369371
].join(' ')

src/traces/indicator/plot.js

Lines changed: 47 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -291,16 +291,16 @@ function drawBulletGauge(gd, plotGroup, cd, gaugeOpts) {
291291

292292
// Draw bullet background, steps
293293
var boxes = [gaugeBg].concat(trace.gauge.steps);
294-
var targetBullet = bullet.selectAll('g.target-bullet').data(boxes);
295-
targetBullet.enter().append('g').classed('target-bullet', true).append('rect');
296-
targetBullet.select('rect')
294+
var bgBullet = bullet.selectAll('g.bg-bullet').data(boxes);
295+
bgBullet.enter().append('g').classed('bg-bullet', true).append('rect');
296+
bgBullet.select('rect')
297297
.call(drawRect)
298298
.call(styleShape);
299-
targetBullet.exit().remove();
299+
bgBullet.exit().remove();
300300

301301
// Draw value bar with transitions
302-
var fgBullet = bullet.selectAll('g.fg-bullet').data([trace.gauge.bar]);
303-
fgBullet.enter().append('g').classed('fg-bullet', true).append('rect');
302+
var fgBullet = bullet.selectAll('g.value-bullet').data([trace.gauge.bar]);
303+
fgBullet.enter().append('g').classed('value-bullet', true).append('rect');
304304
fgBullet.select('rect')
305305
.attr('height', innerBulletHeight)
306306
.attr('y', (bulletHeight - innerBulletHeight) / 2)
@@ -320,8 +320,8 @@ function drawBulletGauge(gd, plotGroup, cd, gaugeOpts) {
320320
fgBullet.exit().remove();
321321

322322
var data = cd.filter(function() {return trace.gauge.threshold.value;});
323-
var threshold = bullet.selectAll('g.threshold').data(data);
324-
threshold.enter().append('g').classed('threshold', true).append('line');
323+
var threshold = bullet.selectAll('g.threshold-bullet').data(data);
324+
threshold.enter().append('g').classed('threshold-bullet', true).append('line');
325325
threshold.select('line')
326326
.attr('x1', ax.c2p(trace.gauge.threshold.value))
327327
.attr('x2', ax.c2p(trace.gauge.threshold.value))
@@ -331,8 +331,8 @@ function drawBulletGauge(gd, plotGroup, cd, gaugeOpts) {
331331
.style('stroke-width', trace.gauge.threshold.line.width);
332332
threshold.exit().remove();
333333

334-
var bulletOutline = bullet.selectAll('g.bullet-outline').data([gaugeOutline]);
335-
bulletOutline.enter().append('g').classed('bullet-outline', true).append('rect');
334+
var bulletOutline = bullet.selectAll('g.gauge-outline').data([gaugeOutline]);
335+
bulletOutline.enter().append('g').classed('gauge-outline', true).append('rect');
336336
bulletOutline.select('rect')
337337
.call(drawRect)
338338
.call(styleShape);
@@ -462,44 +462,53 @@ function drawAngularGauge(gd, plotGroup, cd, gaugeOpts) {
462462
});
463463
}
464464

465-
// Reexpress threshold for drawing
466-
var v = trace.gauge.threshold.value;
467-
var thresholdArc = {
468-
range: [v, v],
469-
color: trace.gauge.threshold.color,
470-
line: {
471-
color: trace.gauge.threshold.line.color,
472-
width: trace.gauge.threshold.line.width
473-
},
474-
thickness: trace.gauge.threshold.thickness
475-
};
476-
477465
// Draw background + steps
478466
var arcs = [gaugeBg].concat(trace.gauge.steps);
479-
if(v) arcs.push(thresholdArc);
480-
var targetArc = angularGauge.selectAll('g.target-arc').data(arcs);
481-
targetArc.enter().append('g').classed('target-arc', true).append('path');
482-
targetArc.select('path').call(drawArc).call(styleShape);
483-
targetArc.exit().remove();
467+
var bgArc = angularGauge.selectAll('g.bg-arc').data(arcs);
468+
bgArc.enter().append('g').classed('bg-arc', true).append('path');
469+
bgArc.select('path').call(drawArc).call(styleShape);
470+
bgArc.exit().remove();
471+
484472
// Draw foreground with transition
485-
var valueArcPath = arcPathGenerator(trace.gauge.bar.thickness);
486-
var fgArc = angularGauge.selectAll('g.fg-arc').data([trace.gauge.bar]);
487-
fgArc.enter().append('g').classed('fg-arc', true).append('path');
488-
var fgArcPath = fgArc.select('path');
473+
var valueArcPathGenerator = arcPathGenerator(trace.gauge.bar.thickness);
474+
var valueArc = angularGauge.selectAll('g.value-arc').data([trace.gauge.bar]);
475+
valueArc.enter().append('g').classed('value-arc', true).append('path');
476+
var valueArcPath = valueArc.select('path');
489477
if(hasTransition) {
490-
fgArcPath
478+
valueArcPath
491479
.transition()
492480
.duration(transitionOpts.duration)
493481
.ease(transitionOpts.easing)
494482
.each('end', function() { trace._lastValue = cd[0].y; onComplete && onComplete(); })
495483
.each('interrupt', function() { onComplete && onComplete(); })
496-
.attrTween('d', arcTween(valueArcPath, valueToAngle(cd[0].lastY), valueToAngle(cd[0].y)));
484+
.attrTween('d', arcTween(valueArcPathGenerator, valueToAngle(cd[0].lastY), valueToAngle(cd[0].y)));
497485
} else {
498-
fgArcPath
499-
.attr('d', valueArcPath.endAngle(valueToAngle(cd[0].y)));
486+
valueArcPath
487+
.attr('d', valueArcPathGenerator.endAngle(valueToAngle(cd[0].y)));
500488
}
501-
fgArcPath.call(styleShape);
502-
fgArc.exit().remove();
489+
valueArcPath.call(styleShape);
490+
valueArc.exit().remove();
491+
492+
// Draw threshold
493+
arcs = [];
494+
var v = trace.gauge.threshold.value;
495+
if(v) {
496+
arcs.push({
497+
range: [v, v],
498+
color: trace.gauge.threshold.color,
499+
line: {
500+
color: trace.gauge.threshold.line.color,
501+
width: trace.gauge.threshold.line.width
502+
},
503+
thickness: trace.gauge.threshold.thickness
504+
});
505+
}
506+
var thresholdArc = angularGauge.selectAll('g.threshold-arc').data(arcs);
507+
thresholdArc.enter().append('g').classed('threshold-arc', true).append('path');
508+
thresholdArc.select('path').call(drawArc).call(styleShape);
509+
thresholdArc.exit().remove();
510+
511+
// Draw border last
503512
var gaugeBorder = angularGauge.selectAll('g.gauge-outline').data([gaugeOutline]);
504513
gaugeBorder.enter().append('g').classed('gauge-outline', true).append('path');
505514
gaugeBorder.select('path').call(drawArc).call(styleShape);
@@ -616,7 +625,7 @@ function drawNumbers(gd, plotGroup, cd, opts) {
616625
var delta = numbers.select('tspan.delta');
617626
delta
618627
.call(Drawing.font, trace.delta.font)
619-
.each(function() { Color.fill(d3.select(this), deltaFill(cd[0]));})
628+
.call(Color.fill, deltaFill(cd[0]))
620629
.attr('x', deltaX)
621630
.attr('dy', deltaDy);
622631

350 Bytes
Loading
59 Bytes
Loading
-143 Bytes
Loading

test/image/mocks/indicator_bullet.json

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -76,10 +76,7 @@
7676
"color": "rgba(0, 0, 0, 1)"
7777
}
7878
},
79-
"value": 35,
80-
"number": {
81-
"valueformat": "0"
82-
}
79+
"value": 35
8380
}, {
8481
"domain": {
8582
"x": [0.25, 1],

test/image/mocks/indicator_gauge.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -171,7 +171,7 @@
171171
"width": 4
172172
},
173173
"thickness": 0.75,
174-
"value": 490
174+
"value": 410
175175
}
176176
}
177177
}],

test/image/mocks/indicator_scatter.json

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,9 @@
77
"title": {"text": "Users online"},
88
"type": "indicator",
99
"mode": "number+delta",
10-
"delta": {"reference": 512},
10+
"delta": {"reference": 512, "valueformat": ".0f"},
1111
"ticker": {
12-
"showticker": true,
13-
"showpercentage": true
12+
"showticker": true
1413
},
1514
"vmax": 500,
1615
"value": 492

test/jasmine/tests/indicator_test.js

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,17 @@ describe('Indicator defaults', function() {
5555
expect(out.delta.reference).toBe(1);
5656
});
5757

58+
it('defaults gauge.axis.range[0] to 0', function() {
59+
var out = _supply({type: 'indicator', mode: 'gauge', value: 1, gauge: {axis: {range: [null, 500]}}});
60+
expect(out.gauge.axis.range[0]).toBe(0);
61+
});
62+
63+
it('defaults gauge.axis.range[1] to 1.5 * value', function() {
64+
var out = _supply({type: 'indicator', mode: 'gauge', value: 100, gauge: {axis: {range: [50, null]}}});
65+
expect(out.gauge.axis.range[0]).toBe(50);
66+
expect(out.gauge.axis.range[1]).toBe(150);
67+
});
68+
5869
// text alignment
5970
['number'].forEach(function(mode) {
6071
it('aligns to center', function() {
@@ -324,6 +335,52 @@ describe('Indicator plot', function() {
324335
});
325336
});
326337

338+
describe('angular gauge', function() {
339+
it('properly order elements', function(done) {
340+
Plotly.newPlot(gd, {data: [{
341+
type: 'indicator',
342+
mode: 'gauge',
343+
gauge: {
344+
shape: 'angular',
345+
steps: [{
346+
range: [0, 250],
347+
}],
348+
threshold: {
349+
value: 410
350+
}
351+
}
352+
}]})
353+
.then(function() {
354+
customAssertions.assertMultiNodeOrder(['g.bg-arc', 'g.value-arc', 'g.threshold-arc', 'g.gauge-outline']);
355+
})
356+
.catch(failTest)
357+
.then(done);
358+
});
359+
});
360+
361+
describe('bullet gauge', function() {
362+
it('properly order elements', function(done) {
363+
Plotly.newPlot(gd, {data: [{
364+
type: 'indicator',
365+
mode: 'gauge',
366+
gauge: {
367+
shape: 'bullet',
368+
steps: [{
369+
range: [0, 250],
370+
}],
371+
threshold: {
372+
value: 410
373+
}
374+
}
375+
}]})
376+
.then(function() {
377+
customAssertions.assertMultiNodeOrder(['g.bg-bullet', 'g.value-bullet', 'g.threshold-bullet', 'g.gauge-outline']);
378+
})
379+
.catch(failTest)
380+
.then(done);
381+
});
382+
});
383+
327384
describe('title', function() {
328385
beforeEach(function() {
329386
// hide the div

0 commit comments

Comments
 (0)