From 87e00cfca74d99831753c2cbd5024f1e47f2d5eb Mon Sep 17 00:00:00 2001 From: "mathias.chouet" <mathias.chouet@irstea.fr> Date: Fri, 6 Sep 2019 12:13:36 +0200 Subject: [PATCH] Fix #281 use formattedValue (fv) instead of toFixed --- .../dialog-edit-param-values.component.ts | 3 +- .../fixedvar-results/results.component.ts | 3 +- .../pab-profile-graph.component.ts | 35 ++++++++++--------- .../pab-results-table.component.ts | 29 +++++++-------- .../pab-results/pab-results.component.ts | 5 --- ...pab-variable-results-selector.component.ts | 3 +- .../remous-results.component.ts | 9 ++--- .../results-graph/results-graph.component.ts | 17 ++++----- src/app/formulaire/ngparam.ts | 25 ++++++------- .../internationalisation.service.ts | 5 +-- src/app/util.ts | 34 ++++++++++++++++++ 11 files changed, 103 insertions(+), 65 deletions(-) diff --git a/src/app/components/dialog-edit-param-values/dialog-edit-param-values.component.ts b/src/app/components/dialog-edit-param-values/dialog-edit-param-values.component.ts index 9c5947efc..070a5422d 100644 --- a/src/app/components/dialog-edit-param-values/dialog-edit-param-values.component.ts +++ b/src/app/components/dialog-edit-param-values/dialog-edit-param-values.component.ts @@ -6,6 +6,7 @@ import { NgParameter } from "../../formulaire/ngparam"; import { ParamValueMode, ExtensionStrategy } from "jalhyd"; import { sprintf } from "sprintf-js"; import { ApplicationSetupService } from "../../services/app-setup/app-setup.service"; +import { fv } from "../../util"; @Component({ selector: "dialog-edit-param-values", @@ -125,7 +126,7 @@ export class DialogEditParamValuesComponent implements OnInit { tooltips: { callbacks: { label: function(tooltipItem) { - return Number(tooltipItem.yLabel).toFixed(nDigits); + return fv(Number(tooltipItem.yLabel)); } } } diff --git a/src/app/components/fixedvar-results/results.component.ts b/src/app/components/fixedvar-results/results.component.ts index 4f45d632e..db20c2ec5 100644 --- a/src/app/components/fixedvar-results/results.component.ts +++ b/src/app/components/fixedvar-results/results.component.ts @@ -3,6 +3,7 @@ import { Screenfull } from "screenfull"; // @see https://github.com/sindresorhus import { NgParameter } from "../../formulaire/ngparam"; import { ServiceFactory } from "../../services/service-factory"; +import { fv } from "../../util"; /** * Base class for results components, including common features @@ -82,7 +83,7 @@ export class ResultsComponent { if (originalValue < minRenderableNumber) { return String(Number(originalValue.toPrecision(nDigits))); // double casting avoids trailing zeroes } else { - return originalValue.toFixed(nDigits); + return fv(originalValue); } } } diff --git a/src/app/components/pab-profile-graph/pab-profile-graph.component.ts b/src/app/components/pab-profile-graph/pab-profile-graph.component.ts index 1fcbeb2d5..92a5b9979 100644 --- a/src/app/components/pab-profile-graph/pab-profile-graph.component.ts +++ b/src/app/components/pab-profile-graph/pab-profile-graph.component.ts @@ -9,6 +9,7 @@ import { PabResults } from "../../results/pab-results"; import { IYSeries } from "../../results/y-series"; import { CloisonAval, Cloisons } from "jalhyd"; +import { fv } from "../../util"; @Component({ selector: "pab-profile-graph", @@ -136,7 +137,7 @@ export class PabProfileGraphComponent extends ResultsComponent { const iter = v.getExtendedValuesIterator(this.size); while (iter.hasNext) { const nv = iter.next(); - vv.push(nv.value.toFixed(nDigits)); + vv.push(fv(nv.value)); } this.varValues.push(vv); } @@ -213,10 +214,10 @@ export class PabProfileGraphComponent extends ResultsComponent { // X is always wall abscissa for (const cr of this._results.cloisonsResults) { const x = cr.resultElement.getValue("x"); // any resultElement will do - data.push(x.toFixed(nDigits)); + data.push(fv(x)); } const xdw = this._results.cloisonAvalResults.resultElement.getValue("x"); - data.push(xdw.toFixed(nDigits)); + data.push(fv(xdw)); return data; } @@ -231,8 +232,8 @@ export class PabProfileGraphComponent extends ResultsComponent { const nDigits = this.appSetupService.displayDigits; // extend upstream dataF.push({ - x: (Number(xs[0]) - pabLength5Pct).toFixed(nDigits), - y: this._results.cloisonsResults[0].resultElement.getValue("ZRAM").toFixed(nDigits) + x: fv(Number(xs[0]) - pabLength5Pct), + y: fv(this._results.cloisonsResults[0].resultElement.getValue("ZRAM")) }); // regular walls for (let i = 0; i < this._results.cloisonsResults.length; i++) { @@ -243,11 +244,11 @@ export class PabProfileGraphComponent extends ResultsComponent { const halfLB = c.prms.LB.singleValue / 2; dataF.push({ x: xs[i], - y: ZRAM.toFixed(nDigits) + y: fv(ZRAM) }); dataF.push({ - x: (Number(xs[i]) + halfLB).toFixed(nDigits), - y: ZRMB.toFixed(nDigits) + x: fv(Number(xs[i]) + halfLB), + y: fv(ZRMB) }); } // downwall @@ -255,12 +256,12 @@ export class PabProfileGraphComponent extends ResultsComponent { const ZRAMdw = dw.prms.ZRAM.singleValue; dataF.push({ x: xs[ xs.length - 1 ], - y: ZRAMdw.toFixed(nDigits) + y: fv(ZRAMdw) }); // extend downstream dataF.push({ - x: (Number(xs[xs.length - 1]) + pabLength5Pct).toFixed(nDigits), - y: ZRAMdw.toFixed(nDigits) + x: fv(Number(xs[xs.length - 1]) + pabLength5Pct), + y: fv(ZRAMdw) }); // add series ret.push({ @@ -286,8 +287,8 @@ export class PabProfileGraphComponent extends ResultsComponent { // extend upstream dataN.push({ - x: (Number(xs[0]) - pabLength5Pct).toFixed(nDigits), - y: this._results.cloisonsResults[0].resultElements[n].vCalc.toFixed(nDigits) + x: fv(Number(xs[0]) - pabLength5Pct), + y: fv(this._results.cloisonsResults[0].resultElements[n].vCalc) }); // walls @@ -311,11 +312,11 @@ export class PabProfileGraphComponent extends ResultsComponent { // 2 points for each abscissa dataN.push({ x: x, - y: Z1.toFixed(nDigits) + y: fv(Z1) }); dataN.push({ x: x, - y: (nextZ1 !== undefined ? nextZ1.toFixed(nDigits) : "") + y: (nextZ1 !== undefined ? fv(nextZ1) : "") }); i++; @@ -323,8 +324,8 @@ export class PabProfileGraphComponent extends ResultsComponent { // extend downstream dataN.push({ - x: (Number(xs[xs.length - 1]) + pabLength5Pct).toFixed(nDigits), - y: (this._results.Z2[n] ? this._results.Z2[n].toFixed(nDigits) : "") + x: fv(Number(xs[xs.length - 1]) + pabLength5Pct), + y: (this._results.Z2[n] ? fv(this._results.Z2[n]) : "") }); ret.push({ diff --git a/src/app/components/pab-results/pab-results-table.component.ts b/src/app/components/pab-results/pab-results-table.component.ts index d685f4500..d17b83a56 100644 --- a/src/app/components/pab-results/pab-results-table.component.ts +++ b/src/app/components/pab-results/pab-results-table.component.ts @@ -8,6 +8,7 @@ import { PabResults } from "../../results/pab-results"; import { ApplicationSetupService } from "../../services/app-setup/app-setup.service"; import { I18nService } from "../../services/internationalisation/internationalisation.service"; import { ResultsComponent } from "../fixedvar-results/results.component"; +import { fv } from "../../util"; @Component({ selector: "pab-results-table", @@ -76,7 +77,7 @@ export class PabResultsTableComponent extends ResultsComponent { if (pr.cloisonsResults[0].resultElements[vi].vCalc) { // parfois le calcul des cloisons échoue this._dataSet.push([ this.intlService.localizeText("INFO_LIB_AMONT"), - pr.cloisonsResults[0].resultElements[vi] ? pr.cloisonsResults[0].resultElements[vi].vCalc.toFixed(nDigits) : "", + pr.cloisonsResults[0].resultElements[vi] ? fv(pr.cloisonsResults[0].resultElements[vi].vCalc) : "", "", "", "", "", "", "", "" ]); } @@ -96,14 +97,14 @@ export class PabResultsTableComponent extends ResultsComponent { this._dataSet.push([ i + 1, // n° cloison - Z1.toFixed(nDigits), // Z - r2n.ZRAM.toFixed(nDigits), - r2n.DH.toFixed(nDigits), - r2n.Q.toFixed(nDigits), - r2n.PV.toFixed(nDigits), - r2n.YMOY.toFixed(nDigits), - r2n.ZRMB.toFixed(nDigits), - r2n.QA, + fv(Z1), // Z + fv(r2n.ZRAM), + fv(r2n.DH), + fv(r2n.Q), + fv(r2n.PV), + fv(r2n.YMOY), + fv(r2n.ZRMB), + fv(r2n.QA), this.getJetTypes(pr.cloisonsResults[i], vi) ]); } @@ -115,10 +116,10 @@ export class PabResultsTableComponent extends ResultsComponent { const rln = pr.cloisonAvalResults.resultElements[vi].values; this._dataSet.push([ this.intlService.localizeText("INFO_LIB_AVAL"), - (pr.Z2[vi] !== undefined ? pr.Z2[vi].toFixed(nDigits) : ""), - cloisonAval.prms.ZRAM.singleValue.toFixed(nDigits), - rln.DH.toFixed(nDigits), - rln.Q.toFixed(nDigits), + (pr.Z2[vi] !== undefined ? fv(pr.Z2[vi]) : ""), + fv(cloisonAval.prms.ZRAM.singleValue), + fv(rln.DH), + fv(rln.Q), "", "", "", "", this.getJetTypes(pr.cloisonAvalResults, vi) ]); @@ -128,7 +129,7 @@ export class PabResultsTableComponent extends ResultsComponent { if (vanneZDV) { this._dataSet.push([ this.intlService.localizeText("INFO_LIB_COTE_VANNE_LEVANTE"), - vanneZDV.toFixed(nDigits), + fv(vanneZDV), "", "", "", "", "", "", "" ]); } diff --git a/src/app/components/pab-results/pab-results.component.ts b/src/app/components/pab-results/pab-results.component.ts index 510867ca6..4cd9b0dab 100644 --- a/src/app/components/pab-results/pab-results.component.ts +++ b/src/app/components/pab-results/pab-results.component.ts @@ -322,11 +322,6 @@ export class PabResultsComponent implements DoCheck { return CalculatorResults.paramLabel(p, false); } - public formattedValue(p: NgParameter): string { - const nDigits = this.appSetupService.displayDigits; - return p.getValue().toFixed(nDigits); - } - public get hasResults(): boolean { return this._pabResults && this._pabResults.hasResults; } diff --git a/src/app/components/pab-results/pab-variable-results-selector.component.ts b/src/app/components/pab-results/pab-variable-results-selector.component.ts index 4986bfbf8..799cc5267 100644 --- a/src/app/components/pab-results/pab-variable-results-selector.component.ts +++ b/src/app/components/pab-results/pab-variable-results-selector.component.ts @@ -3,6 +3,7 @@ import { Component, Output, EventEmitter } from "@angular/core"; import { PabResults } from "../../results/pab-results"; import { I18nService } from "../../services/internationalisation/internationalisation.service"; import { ApplicationSetupService } from "../../services/app-setup/app-setup.service"; +import { fv } from "../../util"; @Component({ selector: "pab-variable-results-selector", @@ -55,7 +56,7 @@ export class PabVariableResultsSelectorComponent { const iter = v.getExtendedValuesIterator(this.size); while (iter.hasNext) { const nv = iter.next(); - vv.push(nv.value.toFixed(nDigits)); + vv.push(fv(nv.value)); } this.varValues.push(vv); } diff --git a/src/app/components/remous-results/remous-results.component.ts b/src/app/components/remous-results/remous-results.component.ts index da77b6c0d..df5678887 100644 --- a/src/app/components/remous-results/remous-results.component.ts +++ b/src/app/components/remous-results/remous-results.component.ts @@ -10,6 +10,7 @@ import { VarResultsComponent } from "../fixedvar-results/var-results.component"; import { ApplicationSetupService } from "../../services/app-setup/app-setup.service"; import { FormulaireService } from "../../services/formulaire/formulaire.service"; import { ResultsComponent } from "../fixedvar-results/results.component"; +import { fv } from "../../util"; /** * données pour une ligne dans le graphe @@ -605,7 +606,7 @@ export class RemousResultsComponent extends ResultsComponent implements DoCheck ticks: { precision: nDigits, callback: function(value, index, values) { - return Number(value).toFixed(nDigits); + return fv(Number(value)); } }, scaleLabel: { @@ -617,7 +618,7 @@ export class RemousResultsComponent extends ResultsComponent implements DoCheck tooltips: { callbacks: { label: function(tooltipItem, data) { - return Number(tooltipItem.yLabel).toFixed(nDigits); + return fv(Number(tooltipItem.yLabel)); } } } @@ -645,7 +646,7 @@ export class RemousResultsComponent extends ResultsComponent implements DoCheck ticks: { precision: nDigits, callback: function(value, index, values) { - return Number(value).toFixed(nDigits); + return fv(Number(value)); } }, }] @@ -653,7 +654,7 @@ export class RemousResultsComponent extends ResultsComponent implements DoCheck tooltips: { callbacks: { label: function(tooltipItem, data) { - return Number(tooltipItem.yLabel).toFixed(nDigits); + return fv(Number(tooltipItem.yLabel)); } } } diff --git a/src/app/components/results-graph/results-graph.component.ts b/src/app/components/results-graph/results-graph.component.ts index 7c1ae074f..96c35127a 100644 --- a/src/app/components/results-graph/results-graph.component.ts +++ b/src/app/components/results-graph/results-graph.component.ts @@ -12,6 +12,7 @@ import { GraphType } from "../../results/graph-type"; import { ResultsComponent } from "../fixedvar-results/results.component"; import { IYSeries } from "../../results/y-series"; import { VarResults } from "../../results/var-results"; +import { fv } from "../../util"; @Component({ selector: "results-graph", @@ -240,7 +241,7 @@ export class ResultsGraphComponent extends ResultsComponent implements AfterCont ticks: { precision: nDigits, callback: function(value, index, values) { - return Number(value).toFixed(nDigits); + return fv(Number(value)); } }, scaleLabel: { @@ -261,14 +262,14 @@ export class ResultsGraphComponent extends ResultsComponent implements AfterCont displayColors: false, callbacks: { title: (tooltipItems, data) => { - return this.chartY + " = " + Number(tooltipItems[0].yLabel).toFixed(nDigits); + return this.chartY + " = " + fv(Number(tooltipItems[0].yLabel)); }, label: (tooltipItem, data) => { const lines: string[] = []; const nbLines = that._results.getVariatingParametersSymbols().length; for (const v of that._results.getVariatingParametersSymbols()) { const series = that._results.getValuesSeries[0](v); - const line = v + " = " + series[tooltipItem.index].toFixed(nDigits); + const line = v + " = " + fv(series[tooltipItem.index]); if (v === this.chartX) { if (nbLines > 1) { lines.unshift(""); @@ -357,14 +358,14 @@ export class ResultsGraphComponent extends ResultsComponent implements AfterCont displayColors: false, callbacks: { title: (tooltipItems, data) => { - return this.chartY + " = " + Number(tooltipItems[0].yLabel).toFixed(nDigits); + return this.chartY + " = " + fv(Number(tooltipItems[0].yLabel)); }, label: (tooltipItem, data) => { let lines: string[] = []; // 1. X if different from Y if (this.chartX !== this.chartY) { const xseries = that._results.getValuesSeries(this.chartX); - const xline = this.chartX + " = " + xseries[tooltipItem.index].toFixed(nDigits); + const xline = this.chartX + " = " + fv(xseries[tooltipItem.index]); lines.push(xline); } // 2. variated parameters other than X or Y @@ -372,7 +373,7 @@ export class ResultsGraphComponent extends ResultsComponent implements AfterCont for (const v of that._results.getVariatingParametersSymbols()) { if (v !== this.chartX && v !== this.chartY) { const series = that._results.getValuesSeries(v); - const line = v + " = " + series[tooltipItem.index].toFixed(nDigits); + const line = v + " = " + fv(series[tooltipItem.index]); varLines.push(line); } } @@ -417,8 +418,8 @@ export class ResultsGraphComponent extends ResultsComponent implements AfterCont // build fixed precision x/y coordinate pairs for (let j = 0; j < xSeries.length; j++) { dat.push({ - x: (xSeries[j] !== undefined) ? xSeries[j].toFixed(nDigits) : "", - y: (ySeries[j] !== undefined) ? ySeries[j].toFixed(nDigits) : "" + x: (xSeries[j] !== undefined) ? fv(xSeries[j]) : "", + y: (ySeries[j] !== undefined) ? fv(ySeries[j]) : "" }); } // add series diff --git a/src/app/formulaire/ngparam.ts b/src/app/formulaire/ngparam.ts index a76a934ff..a58d5ff42 100644 --- a/src/app/formulaire/ngparam.ts +++ b/src/app/formulaire/ngparam.ts @@ -6,6 +6,7 @@ import { sprintf } from "sprintf-js"; import { InputField } from "./input-field"; import { ServiceFactory } from "../services/service-factory"; import { FormulaireNode } from "./formulaire-node"; +import { fv } from "../util"; export enum ParamRadioConfig { /** pas de radio, paramètre modifiable à la main uniquement */ @@ -45,20 +46,20 @@ export class NgParameter extends InputField implements Observer { switch (p.valueMode) { case ParamValueMode.SINGLE: - valuePreview = String(p.getValue().toFixed(nDigits)); + valuePreview = fv(p.getValue()); break; case ParamValueMode.MINMAX: let min: any = p.min; let max: any = p.max; let step: any = p.step; if (min) { - min = min.toFixed(nDigits); + min = fv(min); } if (max) { - max = max.toFixed(nDigits); + max = fv(max); } if (step) { - step = step.toFixed(nDigits); + step = fv(step); } if (compact) { valuePreview = min + " … " + max; @@ -70,11 +71,11 @@ export class NgParameter extends InputField implements Observer { case ParamValueMode.LISTE: const vals = p.valueList || []; if (compact) { - valuePreview = vals[0].toFixed(nDigits) + " … " + vals[vals.length - 1].toFixed(nDigits); + valuePreview = fv(vals[0]) + " … " + fv(vals[vals.length - 1]); } else { valuePreview = i18n.localizeText("INFO_PARAMFIELD_PARAMVARIER_VALUES"); valuePreview += " " + vals.slice(0, 5).map((v) => { - return v.toFixed(nDigits); + return fv(v); }).join("; ") + "…"; } break; @@ -82,7 +83,7 @@ export class NgParameter extends InputField implements Observer { valuePreview = i18n.localizeText("INFO_PARAMFIELD_IN_CALCULATION"); if (p.calculability === ParamCalculability.DICHO) { valuePreview += " (" + i18n.localizeText("INFO_PARAMFIELD_IN_CALCULATION_INITIAL_VALUE") - + ": " + p.getValue().toFixed(nDigits) + ")"; + + ": " + fv(p.getValue()) + ")"; } break; case ParamValueMode.LINK: @@ -112,11 +113,11 @@ export class NgParameter extends InputField implements Observer { if (ref.hasMultipleValues()) { // compact representation const cVal = ref.nub.result.getCalculatedValues(); - valuePreview = cVal[0].toFixed(nDigits) + " … " + cVal[cVal.length - 1].toFixed(nDigits); + valuePreview = fv(cVal[0]) + " … " + fv(cVal[cVal.length - 1]); } else { const vCalc = ref.nub.result.vCalc; if (vCalc) { - valuePreview = String(vCalc.toFixed(nDigits)); + valuePreview = fv(vCalc); } else { // computation has been run but has failed valuePreview = i18n.localizeText("INFO_PARAMFIELD_CALCULATION_FAILED"); @@ -136,10 +137,10 @@ export class NgParameter extends InputField implements Observer { if (ref.hasMultipleValues()) { // compact representation const cVal = remoteValues.valueList; - valuePreview = cVal[0].toFixed(nDigits) + " … " + cVal[cVal.length - 1].toFixed(nDigits); + valuePreview = fv(cVal[0]) + " … " + fv(cVal[cVal.length - 1]); } else { // like SINGLE mode - valuePreview = String(remoteValues.currentValue.toFixed(nDigits)); + valuePreview = fv(remoteValues.currentValue); } } catch (e) { valuePreview = i18n.localizeText("INFO_PARAMFIELD_IN_CALCULATION"); @@ -205,7 +206,7 @@ export class NgParameter extends InputField implements Observer { this._paramDef.valueMode = m; this.notifyObservers({ "action": "valueModeChange", - "value": Number(this._paramDef.getValue().toFixed(nDigits)) + "value": Number(fv(this._paramDef.getValue())) }); } } diff --git a/src/app/services/internationalisation/internationalisation.service.ts b/src/app/services/internationalisation/internationalisation.service.ts index 65a77c278..063fd0a3a 100644 --- a/src/app/services/internationalisation/internationalisation.service.ts +++ b/src/app/services/internationalisation/internationalisation.service.ts @@ -5,6 +5,7 @@ import { Message, MessageCode, Observable, Observer, CalculatorType, LoiDebit } import { StringMap } from "../../stringmap"; import { ApplicationSetupService } from "../app-setup/app-setup.service"; import { HttpService } from "../http/http.service"; +import { fv } from "../../util"; @Injectable() export class I18nService extends Observable implements Observer { @@ -160,7 +161,7 @@ export class I18nService extends Observable implements Observer { const v: any = r.extraVar[k]; let s: string; if (typeof v === "number") { - s = v.toFixed(nDigits); + s = fv(v); } else { s = v; } @@ -197,7 +198,7 @@ export class I18nService extends Observable implements Observer { return this.localizeText(`INFO_${label.substring(match).toUpperCase()}_${value}`); } const nDigits = this.applicationSetupService.displayDigits; - return value.toFixed(nDigits); + return fv(value); } // interface Observer diff --git a/src/app/util.ts b/src/app/util.ts index b40e36cfe..9131ccba8 100644 --- a/src/app/util.ts +++ b/src/app/util.ts @@ -1,3 +1,6 @@ +import { NgParameter } from "./formulaire/ngparam"; +import { ServiceFactory } from "./services/service-factory"; + export function logObject(obj: {}, m?: string) { // évite le message "Value below was evaluated just now" dans le debugger de Chrome if (m === undefined) { @@ -10,3 +13,34 @@ export function logObject(obj: {}, m?: string) { export function isNumber(s: string): boolean { return Number(s) !== NaN; } + +/** + * fv (formatted value) + * Formats (rounds) the given number (or the value of the given parameter) with the + * number of decimals specified in app preferences; if given number is too low and + * more decimals would be needed, keep as much significative digits as the number of + * decimals specified in app preferences, except potential trailing zeroes + * + * ex. with 3 decimals: + * 1 => 1.000 + * 65431 => 65431.000 + * 0.002 => 0.002 + * 0.00004521684 => 0.0000452 + * 0.000001 => 0.000001 + */ +export function fv(p: NgParameter | number): string { + let originalValue: number; + if (p instanceof NgParameter) { + originalValue = p.getValue(); + } else if (typeof p === "number") { + originalValue = p; + } + const nDigits = ServiceFactory.instance.applicationSetupService.displayDigits; + const minRenderableNumber = Number("1E-" + nDigits); + // if required precision is too low, avoid rendering only zeroes + if (originalValue < minRenderableNumber) { + return String(Number(originalValue.toPrecision(nDigits))); // double casting avoids trailing zeroes + } else { + return originalValue.toFixed(nDigits); + } +} -- GitLab