Skip to content

Commit 097bc78

Browse files
committed
fix 4499 - do not display empty bars
1 parent 8122c21 commit 097bc78

File tree

4 files changed

+223
-5
lines changed

4 files changed

+223
-5
lines changed

src/traces/bar/plot.js

+9-5
Original file line numberDiff line numberDiff line change
@@ -147,6 +147,7 @@ function plot(gd, plotinfo, cdModule, traceLayer, opts, makeOnCompleteCallback)
147147
!isNumeric(y0) ||
148148
!isNumeric(y1)
149149
);
150+
150151
// display zeros if line.width > 0
151152
if(isBlank && shouldDisplayZeros && helpers.getLineWidth(trace, di) && (isHorizontal ? x1 - x0 === 0 : y1 - y0 === 0)) {
152153
isBlank = false;
@@ -190,7 +191,9 @@ function plot(gd, plotinfo, cdModule, traceLayer, opts, makeOnCompleteCallback)
190191
d3.round(Math.round(v) - offset, 2) : v;
191192
}
192193

193-
function expandToVisible(v, vc) {
194+
function expandToVisible(v, vc, hideZeroHeight) {
195+
if(hideZeroHeight && v === vc) return v;
196+
194197
// if it's not in danger of disappearing entirely,
195198
// round more precisely
196199
return Math.abs(v - vc) >= 2 ? roundWithLine(v) :
@@ -210,10 +213,11 @@ function plot(gd, plotinfo, cdModule, traceLayer, opts, makeOnCompleteCallback)
210213

211214
var op = Color.opacity(mc);
212215
var fixpx = (op < 1 || lw > 0.01) ? roundWithLine : expandToVisible;
213-
x0 = fixpx(x0, x1);
214-
x1 = fixpx(x1, x0);
215-
y0 = fixpx(y0, y1);
216-
y1 = fixpx(y1, y0);
216+
217+
x0 = fixpx(x0, x1, isHorizontal);
218+
x1 = fixpx(x1, x0, isHorizontal);
219+
y0 = fixpx(y0, y1, !isHorizontal);
220+
y1 = fixpx(y1, y0, !isHorizontal);
217221
}
218222

219223
var sel = transition(Lib.ensureSingle(bar, 'path'), fullLayout, opts, makeOnCompleteCallback);
33.9 KB
Loading

test/image/mocks/bar_hide_nulls.json

+180
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,180 @@
1+
{
2+
"data": [
3+
{
4+
"type": "bar",
5+
"x": [
6+
"A",
7+
"B",
8+
"C"
9+
],
10+
"y": [
11+
0,
12+
null,
13+
1
14+
],
15+
"text": [
16+
0,
17+
null,
18+
1
19+
],
20+
"textposition": "auto",
21+
"insidetextanchor": "middle",
22+
"cliponaxis": false
23+
},
24+
{
25+
"type": "bar",
26+
"x": [
27+
"A",
28+
"B",
29+
"C"
30+
],
31+
"y": [
32+
0,
33+
null,
34+
1
35+
],
36+
"text": [
37+
0,
38+
null,
39+
1
40+
],
41+
"textposition": "auto",
42+
"insidetextanchor": "middle",
43+
"cliponaxis": false,
44+
"xaxis": "x2",
45+
"yaxis": "y2"
46+
},
47+
{
48+
"type": "bar",
49+
"orientation": "h",
50+
"x": [
51+
0,
52+
null,
53+
1
54+
],
55+
"y": [
56+
"A",
57+
"B",
58+
"C"
59+
],
60+
"text": [
61+
0,
62+
null,
63+
1
64+
],
65+
"textposition": "auto",
66+
"insidetextanchor": "middle",
67+
"cliponaxis": false,
68+
"xaxis": "x3",
69+
"yaxis": "y3"
70+
},
71+
{
72+
"type": "bar",
73+
"orientation": "h",
74+
"x": [
75+
0,
76+
null,
77+
1
78+
],
79+
"y": [
80+
"A",
81+
"B",
82+
"C"
83+
],
84+
"text": [
85+
0,
86+
null,
87+
1
88+
],
89+
"textposition": "auto",
90+
"insidetextanchor": "middle",
91+
"cliponaxis": false,
92+
"xaxis": "x4",
93+
"yaxis": "y4"
94+
}
95+
],
96+
"layout": {
97+
"showlegend": true,
98+
"width": 800,
99+
"height": 800,
100+
"dragmode": "pan",
101+
"xaxis": {
102+
"domain": [
103+
0,
104+
0.48
105+
]
106+
},
107+
"xaxis2": {
108+
"autorange": "reversed",
109+
"anchor": "y2",
110+
"domain": [
111+
0.52,
112+
1
113+
]
114+
},
115+
"xaxis3": {
116+
"range": [
117+
-0.01,
118+
1
119+
],
120+
"zeroline": false,
121+
"anchor": "y3",
122+
"domain": [
123+
0,
124+
0.48
125+
]
126+
},
127+
"xaxis4": {
128+
"range": [
129+
-0.01,
130+
1
131+
],
132+
"zeroline": false,
133+
"autorange": "reversed",
134+
"anchor": "y4",
135+
"domain": [
136+
0.52,
137+
1
138+
]
139+
},
140+
"yaxis": {
141+
"range": [
142+
-0.01,
143+
1
144+
],
145+
"zeroline": false,
146+
"domain": [
147+
0,
148+
0.48
149+
]
150+
},
151+
"yaxis2": {
152+
"range": [
153+
-0.01,
154+
1
155+
],
156+
"zeroline": false,
157+
"autorange": "reversed",
158+
"anchor": "x2",
159+
"domain": [
160+
0.52,
161+
1
162+
]
163+
},
164+
"yaxis3": {
165+
"anchor": "x3",
166+
"domain": [
167+
0.52,
168+
1
169+
]
170+
},
171+
"yaxis4": {
172+
"autorange": "reversed",
173+
"anchor": "x4",
174+
"domain": [
175+
0,
176+
0.48
177+
]
178+
}
179+
}
180+
}

test/jasmine/tests/bar_test.js

+34
Original file line numberDiff line numberDiff line change
@@ -2025,6 +2025,40 @@ describe('A bar plot', function() {
20252025
.catch(failTest)
20262026
.then(done);
20272027
});
2028+
2029+
it('should not show up null and zero bars as thin bars', function(done) {
2030+
var mock = Lib.extendDeep({}, require('@mocks/bar_hide_nulls.json'));
2031+
2032+
function getArea(path) {
2033+
var pos = path
2034+
.substr(1, path.length - 2)
2035+
.replace('V', ',')
2036+
.replace('H', ',')
2037+
.replace('V', ',')
2038+
.split(',');
2039+
var dx = +pos[0];
2040+
var dy = +pos[1];
2041+
dy -= +pos[2];
2042+
dx -= +pos[3];
2043+
2044+
return dx * dy;
2045+
}
2046+
2047+
Plotly.plot(gd, mock)
2048+
.then(function() {
2049+
var nodes = gd.querySelectorAll('g.point > path');
2050+
expect(nodes.length).toBe(12, '# of bars');
2051+
2052+
[
2053+
0, 1, 3, 4, 6, 7, 9, 10
2054+
].forEach(function(i) {
2055+
var d = nodes[i].getAttribute('d');
2056+
expect(getArea(d)).toBe(0, 'item:' + i);
2057+
});
2058+
})
2059+
.catch(failTest)
2060+
.then(done);
2061+
});
20282062
});
20292063

20302064
describe('bar visibility toggling:', function() {

0 commit comments

Comments
 (0)