Skip to content

Commit 9bb32f6

Browse files
jcfrancobenelan
authored andcommitted
fix(slider): ensure histograms with non-zero min are displayed correctly (#11587)
1 parent 546b8a6 commit 9bb32f6

File tree

3 files changed

+186
-99
lines changed

3 files changed

+186
-99
lines changed

packages/calcite-components/src/components/graph/graph.e2e.ts

+2-49
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import { newE2EPage, E2EPage } from "@arcgis/lumina-compiler/puppeteerTesting";
2-
import { describe, expect, it, beforeEach } from "vitest";
2+
import { describe, beforeEach } from "vitest";
33
import { accessible, defaults, hidden, renders, themed } from "../../tests/commonTests";
44
import { html } from "../../../support/formatting";
55
import type { Graph } from "./graph";
@@ -29,7 +29,7 @@ async function createGraphWithData(): Promise<E2EPage> {
2929

3030
describe("calcite-graph", () => {
3131
describe("renders", () => {
32-
renders(`<calcite-graph></calcite-graph>`, { display: "block" });
32+
renders(`calcite-graph`, { display: "block" });
3333
});
3434

3535
describe("honors hidden attribute", () => {
@@ -59,53 +59,6 @@ describe("calcite-graph", () => {
5959
]);
6060
});
6161

62-
it("draws an area graph", async () => {
63-
const page = await newE2EPage();
64-
await page.setContent(`<calcite-graph style="height:100px; width:300px;"></calcite-graph>`);
65-
await page.$eval("calcite-graph", (elm: any) => {
66-
elm.data = [
67-
[0, 4],
68-
[1, 7],
69-
[4, 6],
70-
[6, 2],
71-
];
72-
});
73-
await page.waitForChanges();
74-
const path = await page.find("calcite-graph >>> path");
75-
const d = path.getAttribute("d");
76-
expect(d).toBe(
77-
"M 0,60 L 0,20 L 0,20 C 16.666666666666664,-10.000000000000014 33.333333333333336,-40 50,-40 C 100,-40 150,-33.33333333333334 200,-20 C 233.33333333333334,-11.111111111111114 266.66666666666663,24.444444444444443 300,60 L 300,60 Z",
78-
);
79-
});
80-
81-
it("uses color-stops when provided", async () => {
82-
const page = await newE2EPage();
83-
await page.setContent(`<calcite-graph></calcite-graph>`);
84-
await page.$eval("calcite-graph", (elm: any) => {
85-
elm.data = [
86-
[0, 4],
87-
[1, 7],
88-
[4, 6],
89-
[6, 2],
90-
];
91-
elm.colorStops = [
92-
{ offset: 0, color: "red" },
93-
{ offset: 0.5, color: "green" },
94-
{ offset: 1, color: "blue" },
95-
];
96-
});
97-
98-
await page.waitForChanges();
99-
100-
const linearGradient = await page.find("calcite-graph >>> linearGradient");
101-
const linearGradientId = linearGradient.getAttribute("id");
102-
103-
const path = await page.find("calcite-graph >>> path");
104-
const fill = path.getAttribute("fill");
105-
106-
expect(fill).toBe(`url(#${linearGradientId})`);
107-
});
108-
10962
describe("theme", () => {
11063
themed(
11164
async () => {

packages/calcite-components/src/components/graph/util.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,7 @@ export function translate({ width, height, min, max }: TranslateOptions): Transl
7272
const rangeY = max[1] - min[1];
7373
return (point) => {
7474
const x = ((point[0] - min[0]) / rangeX) * width;
75-
const y = height - (point[1] / rangeY) * height;
75+
const y = height - ((point[1] - min[1]) / rangeY) * height;
7676
return [x, y];
7777
};
7878
}

packages/calcite-components/src/components/slider/slider.stories.ts

+183-49
Original file line numberDiff line numberDiff line change
@@ -231,65 +231,199 @@ rangeLabeledTicksEdgePositioningAtMin_TestOnly.parameters = {
231231
chromatic: { diffThreshold: 1 },
232232
};
233233

234-
export const Histogram = (): HTMLCalciteSliderElement["el"]["el"] => {
234+
function createHistogramSlider({
235+
range,
236+
values,
237+
histogram,
238+
}: {
239+
range: [number, number];
240+
values: [number, number];
241+
histogram: HTMLCalciteSliderElement["histogram"];
242+
}) {
235243
const slider = document.createElement("calcite-slider");
236-
slider.min = -100;
237-
slider.minValue = -33.32;
238-
slider.max = 100;
239-
slider.maxValue = 30.87;
240-
slider.histogram = [
241-
[-90, 0],
242-
[-60, 12],
243-
[-20, 25],
244-
[20, 55],
245-
[60, 10],
246-
[90, 0],
247-
] as any;
248-
slider.ticks = 10;
249-
slider.scale = "m";
244+
slider.min = range[0];
245+
slider.minValue = values[0];
246+
slider.max = range[1];
247+
slider.maxValue = values[1];
248+
slider.histogram = histogram;
250249
slider.style.minWidth = "60vw";
251250
return slider;
252-
};
251+
}
253252

254-
export const HistogramWithColors = (): HTMLCalciteSliderElement["el"]["el"] => {
255-
const slider = document.createElement("calcite-slider");
256-
slider.min = 0;
257-
slider.minValue = 35;
258-
slider.max = 100;
259-
slider.maxValue = 55;
260-
slider.histogram = [
261-
[0, 0],
262-
[20, 12],
263-
[40, 25],
264-
[60, 55],
265-
[80, 10],
266-
[100, 0],
267-
] as any;
268-
slider.style.minWidth = "60vw";
253+
export const Histogram = (): HTMLCalciteSliderElement["el"]["el"] => {
254+
function createTitle(title: string) {
255+
const titleElement = document.createElement("h1");
256+
titleElement.textContent = title;
257+
return titleElement;
258+
}
259+
260+
const sliderContainer = document.createElement("div");
261+
262+
const histogramSlider = createHistogramSlider({
263+
range: [-100, 100],
264+
values: [-33.32, 30.87],
265+
histogram: [
266+
[-90, 0],
267+
[-60, 12],
268+
[-20, 25],
269+
[20, 55],
270+
[60, 10],
271+
[90, 0],
272+
],
273+
});
274+
histogramSlider.ticks = 10;
275+
276+
sliderContainer.append(createTitle("Default"), histogramSlider);
277+
278+
const colorStopHistogramSlider = createHistogramSlider({
279+
range: [0, 100],
280+
values: [35, 55],
281+
histogram: [
282+
[0, 0],
283+
[20, 12],
284+
[40, 25],
285+
[60, 55],
286+
[80, 10],
287+
[100, 0],
288+
],
289+
});
269290
const colors = ["red", "green", "blue"];
270291
const offsets = colors.map((_, i) => `${(1 / (colors.length - 1)) * i}`);
271-
slider.histogramStops = colors.map((color, i) => ({ offset: parseFloat(offsets[i]), color }));
272-
slider.scale = "m";
273-
return slider;
292+
colorStopHistogramSlider.histogramStops = colors.map((color, i) => ({ offset: parseFloat(offsets[i]), color }));
293+
294+
sliderContainer.append(createTitle("Color Stops"), colorStopHistogramSlider);
295+
296+
const aboveZeroMinHistogramSlider = createHistogramSlider({
297+
range: [1925, 2024],
298+
values: [1925, 1935],
299+
histogram: [
300+
[1925, 2549],
301+
[1926, 3125],
302+
[1927, 2917],
303+
[1928, 2998],
304+
[1929, 2794],
305+
[1930, 2606],
306+
[1931, 2283],
307+
[1932, 3551],
308+
[1933, 3824],
309+
[1934, 3780],
310+
[1935, 3463],
311+
[1936, 3025],
312+
[1937, 2823],
313+
[1938, 3232],
314+
[1939, 3878],
315+
[1940, 3987],
316+
[1941, 3328],
317+
[1942, 2791],
318+
[1943, 3662],
319+
[1944, 3598],
320+
[1945, 3643],
321+
[1946, 3390],
322+
[1947, 3424],
323+
[1948, 3549],
324+
[1949, 4566],
325+
[1950, 5147],
326+
[1951, 5092],
327+
[1952, 4740],
328+
[1953, 4090],
329+
[1954, 4360],
330+
[1955, 5001],
331+
[1956, 5229],
332+
[1957, 4861],
333+
[1958, 5705],
334+
[1959, 5745],
335+
[1960, 5510],
336+
[1961, 6552],
337+
[1962, 5771],
338+
[1963, 6921],
339+
[1964, 6923],
340+
[1965, 6362],
341+
[1966, 7224],
342+
[1967, 7738],
343+
[1968, 7085],
344+
[1969, 5768],
345+
[1970, 7967],
346+
[1971, 8488],
347+
[1972, 8117],
348+
[1973, 7110],
349+
[1974, 6973],
350+
[1975, 6425],
351+
[1976, 7130],
352+
[1977, 5475],
353+
[1978, 7231],
354+
[1979, 6956],
355+
[1980, 6415],
356+
[1981, 6416],
357+
[1982, 6629],
358+
[1983, 5762],
359+
[1984, 7142],
360+
[1985, 7532],
361+
[1986, 6842],
362+
[1987, 6191],
363+
[1988, 5919],
364+
[1989, 7412],
365+
[1990, 7824],
366+
[1991, 6736],
367+
[1992, 8139],
368+
[1993, 6651],
369+
[1994, 8129],
370+
[1995, 6756],
371+
[1996, 9009],
372+
[1997, 8660],
373+
[1998, 6604],
374+
[1999, 5776],
375+
[2000, 6612],
376+
[2001, 5963],
377+
[2002, 5820],
378+
[2003, 6799],
379+
[2004, 6766],
380+
[2005, 6778],
381+
[2006, 5958],
382+
[2007, 5357],
383+
[2008, 5955],
384+
[2009, 5886],
385+
[2010, 4839],
386+
[2011, 5659],
387+
[2012, 6227],
388+
[2013, 5931],
389+
[2014, 6137],
390+
[2015, 7208],
391+
[2016, 5788],
392+
[2017, 5590],
393+
[2018, 7608],
394+
[2019, 6845],
395+
[2020, 6278],
396+
[2021, 6388],
397+
[2022, 5931],
398+
[2023, 6167],
399+
[2024, 4688],
400+
],
401+
});
402+
403+
aboveZeroMinHistogramSlider.histogramStops = [{ offset: 0, color: "#52aeb7" }];
404+
aboveZeroMinHistogramSlider.labelTicks = true;
405+
aboveZeroMinHistogramSlider.step = 10;
406+
aboveZeroMinHistogramSlider.ticks = 5;
407+
408+
sliderContainer.append(createTitle("Above Zero Min (e.g., Yearly Data)"), aboveZeroMinHistogramSlider);
409+
410+
return sliderContainer;
274411
};
275412

276413
export const darkModeHistogramRTL_TestOnly = (): HTMLCalciteSliderElement["el"]["el"] => {
277-
const slider = document.createElement("calcite-slider");
278-
slider.min = 0;
279-
slider.minValue = 25;
280-
slider.max = 100;
281-
slider.maxValue = 75;
282-
slider.histogram = [
283-
[0, 0],
284-
[20, 12],
285-
[40, 25],
286-
[60, 55],
287-
[80, 10],
288-
[100, 0],
289-
];
414+
const slider = createHistogramSlider({
415+
range: [0, 100],
416+
values: [25, 75],
417+
histogram: [
418+
[0, 0],
419+
[20, 12],
420+
[40, 25],
421+
[60, 55],
422+
[80, 10],
423+
[100, 0],
424+
],
425+
});
290426
slider.ticks = 10;
291-
slider.scale = "m";
292-
slider.style.minWidth = "60vw";
293427
slider.className = "calcite-mode-dark";
294428
return slider;
295429
};

0 commit comments

Comments
 (0)