The central bank now charts one point a day for a rolling ninety days, shipped rebased to 100, with alternating month columns named once along the bottom so no two dates collide; short games leave future days blank and the axis floor is pinned at 0 with the 100 baseline labelled. The market no longer clamps a price to 0.5-1.8x base: the day's supply and demand set an equilibrium (base * demand/supply) and the price eases toward it, so a sustained shortage lifts a good well past its old band while a glut cheapens it, and the price settles instead of compounding to infinity. The nation modal holds each scroll position across a snapshot rebuild so the foreign reserves below the fold stay put.
74 lines
2.7 KiB
JavaScript
74 lines
2.7 KiB
JavaScript
import { TestCase } from "./framework/test_case.js";
|
|
import { setupDom, teardownDom } from "./framework/dom.js";
|
|
import { lineChart } from "../client/js/ui/line_chart.js";
|
|
|
|
// The central bank sizes the chart to its panel and caps the height, so the
|
|
// chart must honour an explicit width/height instead of always drawing at its
|
|
// own default aspect ratio.
|
|
export class LineChartTest extends TestCase {
|
|
async test_chart_honours_the_requested_size() {
|
|
const env = await setupDom();
|
|
try {
|
|
const svg = lineChart(
|
|
[
|
|
{ label: "Energy", colour: "#ff0000", values: [100, 120] },
|
|
{ label: "Food", colour: "#00ff00", values: [100, 90] },
|
|
],
|
|
{ width: 800, height: 200, xLabel: (i) => `M${i}` }
|
|
);
|
|
this.assertEqual(svg.getAttribute("viewBox"), "0 0 800 200", "the viewBox uses the options");
|
|
this.assertEqual(svg.getAttribute("width"), "800", "the width attribute uses the options");
|
|
this.assertEqual(svg.getAttribute("height"), "200", "the height attribute uses the options");
|
|
this.assertSize(svg.querySelectorAll(".line-chart-line"), 2, "one line per series");
|
|
this.assertSize(
|
|
svg.querySelectorAll(".line-chart-baseline"), 1, "the baseline is drawn"
|
|
);
|
|
} finally {
|
|
teardownDom(env);
|
|
}
|
|
}
|
|
|
|
async test_chart_shades_and_names_month_bands() {
|
|
const env = await setupDom();
|
|
try {
|
|
const svg = lineChart(
|
|
[{ values: [100, 110] }],
|
|
{
|
|
width: 400,
|
|
height: 160,
|
|
window: 4,
|
|
min: 0,
|
|
xBands: [
|
|
{ start: 0, end: 1, label: "Jan" },
|
|
{ start: 2, end: 3, label: "Feb" },
|
|
],
|
|
}
|
|
);
|
|
this.assertSize(
|
|
svg.querySelectorAll(".line-chart-band-even, .line-chart-band-odd"),
|
|
2,
|
|
"one shaded column per month band"
|
|
);
|
|
const labels = svg.querySelectorAll(".line-chart-month");
|
|
this.assertSize(labels, 2, "each month is named once");
|
|
this.assertEqual(labels[0].textContent, "Jan");
|
|
this.assertEqual(labels[1].textContent, "Feb");
|
|
const axisLabels = [...svg.querySelectorAll(".line-chart-label")].map((el) => el.textContent);
|
|
this.assertTrue(axisLabels.includes("0"), "a pinned floor puts zero at the bottom");
|
|
this.assertTrue(axisLabels.includes("100"), "the baseline is labelled 100");
|
|
} finally {
|
|
teardownDom(env);
|
|
}
|
|
}
|
|
|
|
async test_chart_defaults_to_a_small_size() {
|
|
const env = await setupDom();
|
|
try {
|
|
const svg = lineChart([{ values: [100] }]);
|
|
this.assertEqual(svg.getAttribute("viewBox"), "0 0 320 150", "an unset size keeps the default");
|
|
} finally {
|
|
teardownDom(env);
|
|
}
|
|
}
|
|
}
|