Skip to content

Commit 5c71495

Browse files
Fix percentage formatting
1 parent 654db94 commit 5c71495

3 files changed

Lines changed: 48 additions & 2 deletions

File tree

frontend/src/components/Simulation/Results.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ import { Panel, SimulationResults } from "@/dto/SimulationResults";
55
import ResultConcTable from "@/components/Simulation/ConcResultTable";
66
import Reactions from "../../pages/Reactions";
77
import { MassBalanceError } from "@/components/Simulation/MassBalanceError";
8-
import { extractPlotData } from "@/functions/Formatting";
8+
import { extractPlotData, formatPhaseFraction } from "@/functions/Formatting";
99
import BarChart from "@/components/BarChart";
1010
import GenericTable from "@/components/GenericTable";
1111

@@ -73,7 +73,7 @@ const Results: React.FC<ResultsProps> = ({ simulationResults }) => {
7373
const hasConcentrations = Object.keys(phase.concentrations).length > 0;
7474
if (!hasConcentrations) continue;
7575

76-
panelTabs.push(`${modelPrefix}${phase.kind} (${(phase.fraction * 100).toFixed(1)}%)`);
76+
panelTabs.push(`${modelPrefix}${phase.kind} (${formatPhaseFraction(phase.fraction)})`);
7777

7878
const initialConcentrations = simulationResults.input.concentrations;
7979

frontend/src/functions/Formatting.tsx

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,23 @@ import { SimulationResults, getCo2RichConcentrations } from "@/dto/SimulationRes
22
import { ChartDataSet, TabulatedResultRow } from "@/dto/ChartData";
33
import { ExperimentResult } from "@/dto/ExperimentResult";
44

5+
export const formatPhaseFraction = (fraction: number): string => {
6+
const percent = fraction * 100;
7+
8+
if (percent === 0 || percent === 100) return `${percent.toFixed(1)}%`;
9+
10+
if (percent < 0.1) {
11+
return `${percent.toExponential(2)} wt%`;
12+
}
13+
14+
if (percent > 99.9) {
15+
const decimals = Math.max(1, Math.ceil(-Math.log10(100 - percent)) + 1);
16+
return `${percent.toFixed(Math.min(decimals, 6))}%`;
17+
}
18+
19+
return `${percent.toFixed(1)}%`;
20+
};
21+
522
export const formatConcentration = (value: number | undefined | null): string => {
623
if (value === undefined || value === null) return "-";
724

frontend/tests/functions/Formatting.test.tsx

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import {
44
convertSimulationToChartData,
55
convertSimulationQueriesResultToTabulatedData,
66
convertExperimentResultsToTabulatedData,
7+
formatPhaseFraction,
78
} from "@/functions/Formatting";
89
import { SimulationResults } from "@/dto/SimulationResults";
910
import { ExperimentResult } from "@/dto/ExperimentResult";
@@ -33,6 +34,34 @@ describe("convertToSubscripts", () => {
3334
});
3435
});
3536

37+
describe("formatPhaseFraction", () => {
38+
it("should show normal percentage for mid-range values", () => {
39+
expect(formatPhaseFraction(0.5)).toBe("50.0%");
40+
expect(formatPhaseFraction(0.123)).toBe("12.3%");
41+
});
42+
43+
it("should show exact 0 and 100", () => {
44+
expect(formatPhaseFraction(0)).toBe("0.0%");
45+
expect(formatPhaseFraction(1)).toBe("100.0%");
46+
});
47+
48+
it("should show extra precision for values very close to 100%", () => {
49+
expect(formatPhaseFraction(0.999999)).toBe("99.99990%");
50+
expect(formatPhaseFraction(0.9999)).toBe("99.990%");
51+
expect(formatPhaseFraction(0.999)).toBe("99.9%");
52+
});
53+
54+
it("should show scientific notation wt% for very small values", () => {
55+
expect(formatPhaseFraction(0.000001)).toBe("1.00e-4 wt%");
56+
expect(formatPhaseFraction(0.0000001)).toBe("1.00e-5 wt%");
57+
});
58+
59+
it("should show normal percentage for small but not tiny values", () => {
60+
expect(formatPhaseFraction(0.05)).toBe("5.0%");
61+
expect(formatPhaseFraction(0.001)).toBe("0.1%");
62+
});
63+
});
64+
3665
describe("convertingSimulationToChartData", () => {
3766
const simulation: SimulationResults = {
3867
input: { concentrations: { CO: 0.5, H20: 0.7 }, models: [{ parameters: {}, modelId: "Narnia" }] },

0 commit comments

Comments
 (0)