pab-table.component.ts 38.63 KiB
import { Component, Input, Output, EventEmitter, OnInit } from "@angular/core";
import { MatDialog } from "@angular/material";
import {
    Pab,
    Session,
    Props,
    CalculatorType,
    Cloisons,
    Nub,
    Structure,
    ParallelStructure,
    LoiDebit
 } from "jalhyd";
 import { sprintf } from "sprintf-js";
import { I18nService } from "../../services/internationalisation/internationalisation.service";
import { FormulaireService } from "../../services/formulaire/formulaire.service";
import { ApplicationSetupService } from "../../services/app-setup/app-setup.service";
import { NotificationsService } from "../../services/notifications/notifications.service";
import { PabTable } from "../../formulaire/pab-table";
import { DialogEditPabComponent } from "../dialog-edit-pab/dialog-edit-pab.component";
/**
 * The big editable data grid for calculator type "Pab" (component)
@Component({
    selector: "pab-table",
    templateUrl: "./pab-table.component.html",
    styleUrls: [
        "./pab-table.component.scss"
export class PabTableComponent implements /* DoCheck, AfterViewInit, */ OnInit {
    @Input()
    private pabTable: PabTable;
    /** flag de validité des FieldSet enfants */
    private _isValid = false;
    /** événément de changement de validité */
    @Output()
    private validChange = new EventEmitter();
    /** événément de changement de valeur d'un input */
    @Output()
    private inputChange = new EventEmitter();
    /** underlying Pab, binded to the rows */
    private model: Pab;
    /** general headers above the columns */
    public headers: any[];
    /** columns headers description */
    public cols: any[];
    /** data binded to the table */
    public rows: any[];
    /** number of children to add when clicking "add" or "clone" button */
    public childrenToAdd = 1;
    /** items currently selected */
    private selectedItems: Nub[];
    /** used for shift+click implementation */
7172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140
private latestClickedCell: any; public constructor( private i18nService: I18nService, private formService: FormulaireService, private editPabDialog: MatDialog, private appSetupService: ApplicationSetupService, private notifService: NotificationsService ) { this.selectedItems = []; } public get title(): string { return this.i18nService.localizeText("INFO_PAB_TABLE"); } public get isValid() { return this._isValid; } /** returns true if the cell has an underlying model (ie. is editable) */ public hasModel(cell: any): boolean { return (cell !== undefined && cell.model !== undefined); } /** returns true if the cell is an editable number */ public isNumberInput(cell: any): boolean { return this.hasModel(cell) && ! this.isSelect(cell); } /** returns true if the cell is a select box @TODO rename */ public isSelect(cell: any): boolean { return this.hasModel(cell) && (cell.options !== undefined); } /** value to display in a cell, if it is not editable */ public cellValue(cell: any) { if (cell === undefined) { return ""; } else { if (this.hasModel(cell)) { return cell.model; } else { return cell.value; } } } public rowSpan(cell: any) { if (cell !== undefined && cell.rowspan) { return cell.rowspan; } return undefined; } public colSpan(cell: any) { if (cell !== undefined && cell.colspan) { return cell.colspan; } return undefined; } /** returns true if the cell / row has a selectable item */ public isSelectable(cellOrRow: any): boolean { return ( cellOrRow !== undefined && cellOrRow.selectable ); }
141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210
/** returns true if the cell / row has a selectableColumn item */ public isSelectableByColumn(cellOrRow: any): boolean { return ( cellOrRow !== undefined && cellOrRow.selectableColumn ); } /** * - checks if the cell / row has a selectable item, that is currently * selected * - if cell / row has a selectableColumn attribute, also checks if * this column is selected * * returns true if at least one criterion is met */ public isSelected(cellOrRow: any): boolean { let cellSelected = false; let columnSelected = false; // cell if (this.isSelectable(cellOrRow)) { cellSelected = true; if (Array.isArray(cellOrRow.selectable)) { for (const elt of cellOrRow.selectable) { cellSelected = cellSelected && this.selectedItems.includes(elt); } } else { cellSelected = this.selectedItems.includes(cellOrRow.selectable); } } // column if (this.isSelectableByColumn(cellOrRow)) { columnSelected = this.isDeviceColumnSelected(cellOrRow.selectableColumn); } // done return (cellSelected || columnSelected); } /** * returns true if every wall (including downwall) has its nth device * selected (or has no nth device) */ public isDeviceColumnSelected(n: number): boolean { let ok = true; for (const c of this.model.children) { const nthChild = c.getChildren()[n]; if (nthChild) { ok = ok && this.selectedItems.includes(nthChild); } } const nthChildDW = this.model.downWall.getChildren()[n]; if (nthChildDW) { ok = ok && this.selectedItems.includes(nthChildDW); } return ok; } /** * selects or unselects the clicked cell, depending on its current state * and the modifier key held if any */ public toggleSelection(cell: any, $event: any) { if ( this.isSelectable(cell) && ! this.hasModel(cell) // editable cells listen to the click event for edition only ) { if ($event.shiftKey && cell !== this.latestClickedCell) { // shift + click // @TODO interpopolate from this.latestClickedCell to this one console.log("shift + click");
211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280
} else if ( $event.ctrlKey // ctrl + click || ($event.shiftKey && cell === this.latestClickedCell) // shift on same cell => equiv. of ctrl ) { if (this.isSelected(cell)) { // unselect this cell / these cells if (Array.isArray(cell.selectable)) { this.selectedItems = this.selectedItems.filter(e => ! cell.selectable.includes(e)); } else { this.selectedItems = this.selectedItems.filter(e => e !== cell.selectable); } } else { // add this cell / these cells to selection if (Array.isArray(cell.selectable)) { this.selectedItems = this.selectedItems.concat(cell.selectable); this.selectedItems = this.selectedItems.filter( (item, index) => this.selectedItems.indexOf(item) === index // deduplicate ); } else { this.selectedItems.push(cell.selectable); } } } else { // just a click if (this.isSelected(cell)) { // select nothing this.selectedItems = []; } else { // select this cell / thses cells only if (Array.isArray(cell.selectable)) { this.selectedItems = cell.selectable.slice(); // array copy } else { this.selectedItems = [ cell.selectable ]; } } } this.latestClickedCell = cell; // clean list this.selectedItems = this.selectedItems.filter(e => e !== undefined); // @TODO useful ? $event.preventDefault(); $event.stopPropagation(); return false; } } // quick getter for 1st selected item public get selectedItem() { if (this.selectedItems.length === 0) { throw new Error("get selectedItem() : no item selected"); } return this.selectedItems[0]; } // prevents Firefox to display weird cell border when ctrl+clicking public preventCtrlClickBorder($event) { if ($event.ctrlKey) { $event.preventDefault(); } } public get addManyOptionsList() { return Array(20).fill(0).map((value, index) => index + 1); } // DEBUG private dumpParams(n: Nub) {
281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350
console.log(`---- PARAMETERS FOR NUB "${n.uid}" (${n.constructor.name}) ----`); for (const p of n.parameterIterator) { if (p.visible) { console.log(`> ${p.symbol} : ${p.singleValue}, ${p.currentValue}, ${p.v}`); } } } public zpouet() { console.log("!!!------------ zpoueeeeeeeeet ------------!!!"); for (const c of this.model.children) { this.dumpParams(c); } this.dumpParams(this.model.downWall); } // at this time @Input data is supposed to be already populated public ngOnInit() { this.model = this.pabTable.pab; this.refresh(); } /** * Builds the editable data grid from the Pab model */ private refresh() { const maxNbDevices = this.findMaxNumberOfDevices(); // 0. build spanned headers over real columns this.headers = []; // 1 header for basin let bs: any[] = this.model.children; bs = bs.concat(this.model.downWall); this.headers.push({ title: "Bassin", colspan: 6, selectable: bs }); // 1 header for each device of the wall having the most devices (including downwall) for (let i = 0; i < maxNbDevices; i++) { this.headers.push({ title: "Cloison : ouvrage n°" + (i + 1), colspan: 3, selectable: this.model.children.map(c => c.getChildren()[i]).concat(this.model.downWall.getChildren()[i]), selectableColumn: i }); } // A. build columns set this.cols = []; // 6 cols for basin this.cols.push({ title: "N° de bassin", selectable: bs }); this.cols.push({ title: "Longueur", selectable: bs }); this.cols.push({ title: "Largeur", selectable: bs }); this.cols.push({ title: "Débit d'attrait", selectable: bs }); this.cols.push({ title: "Cote radier mi-bassin", selectable: bs
351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420
}); this.cols.push({ title: "Cote radier amont paroi", selectable: bs }); // no col for wall type (defined by rowspan-2 header above) // 3 cols for each device of the wall having the most devices (including downwall) for (let i = 0; i < maxNbDevices; i++) { this.cols.push({ title: "Type", selectable: this.model.children.map(c => c.getChildren()[i]).concat(this.model.downWall.getChildren()[i]), selectableColumn: i }); this.cols.push({ title: "Paramètres", selectable: this.model.children.map(c => c.getChildren()[i]).concat(this.model.downWall.getChildren()[i]), selectableColumn: i }); this.cols.push({ title: "Valeurs", selectable: this.model.children.map(c => c.getChildren()[i]).concat(this.model.downWall.getChildren()[i]), selectableColumn: i }); } // B. Build rows set this.rows = []; // B.1 many rows for each wall let childIndex = 0; for (const cloison of this.model.children) { // admissible LoiDebit const loisCloisons = cloison.getLoisAdmissiblesArray().map(l => { // @TODO move up ? (same for all cloisons) return { label: LoiDebit[l], value: l }; }); // as much rows as the greatest number of parameters among its devices const maxNbParams = this.findMaxNumberOfDeviceParameters(cloison); // console.log(">>> max nb params: ", maxNbParams); for (let i = 0; i < maxNbParams; i++) { // build device params row const deviceParamRow = { selectable: cloison, cells: [] }; // basin number if (i === 0) { deviceParamRow.cells.push({ value: childIndex + 1, rowspan: maxNbParams + 1, class: "basin_number", selectable: cloison }); } // 5 empty cells if (i === 0) { deviceParamRow.cells.push({ colspan: 5, rowspan: maxNbParams, selectable: cloison }); } // device param cells : 3 cells for each device for (const ouvrage of cloison.structures) { const nvParam = ouvrage.getNthVisibleParam(i); // cell 1 : device type if (i === 0) { // 1st row deviceParamRow.cells.push({ model: ouvrage, modelValue: ouvrage.properties.getPropValue("loiDebit"), options: loisCloisons, selectable: ouvrage
421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490
}); } // fill space if (i === 1) { deviceParamRow.cells.push({ rowspan: (maxNbParams - 1), selectable: ouvrage }); } // cell 2 : param name if (nvParam) { deviceParamRow.cells.push({ value: nvParam.symbol, selectable: ouvrage }); } else { deviceParamRow.cells.push({ selectable: ouvrage }); } // cell 3 : param value if (nvParam) { deviceParamRow.cells.push({ model: nvParam, selectable: ouvrage }); } else { deviceParamRow.cells.push({ selectable: ouvrage }); } } // fill horizontal space const devDiff = (maxNbDevices - cloison.structures.length); if (i === 0) { for (let j = 0; j < devDiff; j++) { deviceParamRow.cells.push({ colspan: 3, rowspan: maxNbParams, selectable: cloison, selectableColumn: cloison.structures.length + j }); } } // done ! this.rows.push(deviceParamRow); } // 1 row for the basin after the wall const basinRow: { selectable: any, cells: any[] } = { selectable: cloison, cells: [ // no cell for basin number (defined by rowspan-n cell above) { model: cloison.prms.LB }, { model: cloison.prms.BB }, { model: cloison.prms.QA }, { model: cloison.prms.ZRMB }, { model: cloison.prms.ZRAM } ] }; // fill horizontal space
491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560
for (let i = 0; i < maxNbDevices; i++) { basinRow.cells.push({ colspan: 3 }); } // done ! this.rows.push(basinRow); childIndex ++; } // B.2 many rows for downwall // admissible LoiDebit const loisAval = this.model.downWall.getLoisAdmissiblesArray().map(l => { return { label: LoiDebit[l], value: l }; }); // as much rows as the greatest number of parameters among its devices const maxNbParamsDW = this.findMaxNumberOfDeviceParameters(this.model.downWall); for (let i = 0; i < maxNbParamsDW; i++) { // build device params row const deviceParamRowDW = { selectable: this.model.downWall, cells: [] }; // basin number if (i === 0) { deviceParamRowDW.cells.push({ value: "Aval", rowspan: maxNbParamsDW, class: "basin_number", selectable: this.model.downWall }); } // 5 empty cells if (i === 0) { deviceParamRowDW.cells.push({ colspan: 5, rowspan: maxNbParamsDW, selectable: this.model.downWall }); } // downwall device param cells : 3 cells for each device for (const ouvrage of this.model.downWall.structures) { const nvParam = ouvrage.getNthVisibleParam(i); // cell 1 : device type if (i === 0) { // 1st row deviceParamRowDW.cells.push({ model: ouvrage, modelValue: ouvrage.properties.getPropValue("loiDebit"), options: loisAval }); } // fill space if (i === 1) { deviceParamRowDW.cells.push({ rowspan: (maxNbParamsDW - 1), selectable: ouvrage }); } // cell 2 : param name if (nvParam) { deviceParamRowDW.cells.push({ value: nvParam.symbol, selectable: ouvrage }); } else { deviceParamRowDW.cells.push({ selectable: ouvrage }); } // cell 3 : param value
561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630
if (nvParam) { deviceParamRowDW.cells.push({ model: nvParam, selectable: ouvrage }); } else { deviceParamRowDW.cells.push({ selectable: ouvrage }); } } // fill horizontal space const devDiff = (maxNbDevices - this.model.downWall.structures.length); if (i === 0) { for (let j = 0; j < devDiff; j++) { deviceParamRowDW.cells.push({ colspan: 3, rowspan: maxNbParamsDW, selectable: this.model.downWall, selectableColumn: this.model.downWall.structures.length + j }); } } // done ! this.rows.push(deviceParamRowDW); } } private findMaxNumberOfDevices(): number { let maxNbDevices = 1; for (const w of this.model.children) { maxNbDevices = Math.max(maxNbDevices, w.getChildren().length); } maxNbDevices = Math.max(maxNbDevices, this.model.downWall.getChildren().length); return maxNbDevices; } private findMaxNumberOfDeviceParameters(struct: ParallelStructure): number { let maxNbParams = 1; for (const d of struct.getChildren()) { let nbParams = 0; for (const p of d.parameterIterator) { if (p.visible) { // console.log("(counting)", p.symbol); nbParams ++; } } // console.log(">>> child params: ", nbParams); maxNbParams = Math.max(maxNbParams, nbParams); } return maxNbParams; } /** returns true if exactly one device is selected, and nothing else */ public get selectionIsOneDevice() { return ( this.selectedItems.length === 1 && this.selectedItem instanceof Structure ); } /** * Returns true if there is at least one selected item, * and all selected items are devices */ private onlyDevicesAreSelected() { let ok = false; if (this.selectedItems.length > 0) { ok = true; for (const s of this.selectedItems) {
631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700
ok = ok && (s instanceof Structure); } } return ok; } /** * Returns true if there is at least one selected item, * and all selected items are walls */ private onlyWallsAreSelected(excludeDownwall: boolean = true) { let ok = false; if (this.selectedItems.length > 0) { ok = true; for (const s of this.selectedItems) { if (excludeDownwall) { ok = ok && (s instanceof Cloisons); } else { ok = ok && (s instanceof ParallelStructure); } } } return ok; } public get relatedEntityTitle() { let title = ""; if (this.onlyDevicesAreSelected()) { title = "Ouvrages"; } else if (this.onlyWallsAreSelected()) { title = "Cloisons"; } if (title !== "") { title += " :"; } return title; } public get enableAddButton() { return ( this.selectedItems.length === 1 && this.selectedItem.parent // exclude downwall ); } public get enableCopyButton() { return ( this.selectedItems.length === 1 && this.selectedItem.parent // exclude downwall ); } public get enableUpButton() { return ( this.selectedItems.length === 1 && this.selectedItem.parent && this.selectedItem.findPositionInParent() !== 0 ); } public get enableDownButton() { return ( this.selectedItems.length === 1 && this.selectedItem.parent && this.selectedItem.findPositionInParent() < (this.selectedItem.parent.getChildren().length - 1) ); } public get enableRemoveButton() { return (
701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770
this.selectedItems.length === 1 && this.selectedItem.parent && this.selectedItem.parent.getChildren().length > 1 ); } /** * returns true if at least one object is selected */ public get enableEditPabButton() { return this.selectedItems.length > 0; } public onAddClick() { // add default item for (let i = 0; i < this.childrenToAdd; i++) { if (this.selectedItem instanceof Structure) { // add new default device for wall parent const newDevice = Session.getInstance().createNub( new Props({ calcType: CalculatorType.Structure, loiDebit: (this.selectedItem.parent as ParallelStructure).getDefaultLoiDebit() }) ); this.selectedItem.parent.addChild(newDevice, this.selectedItem.findPositionInParent()); } else { // add new default wall for PAB parent const newWall = Session.getInstance().createNub( new Props({ calcType: CalculatorType.Cloisons }) ); // add new default device for new wall const newDevice = Session.getInstance().createNub( new Props({ calcType: CalculatorType.Structure, loiDebit: (newWall as ParallelStructure).getDefaultLoiDebit() }) ); newWall.addChild(newDevice); this.model.addChild(newWall, this.selectedItem.findPositionInParent()); } } this.refresh(); // notify const pos = this.selectedItem.findPositionInParent() + 1; let msg: string; if (this.childrenToAdd === 1) { if (this.selectedItem instanceof Structure) { msg = sprintf(this.i18nService.localizeText("INFO_DEVICE_ADDED"), pos); } else { msg = sprintf(this.i18nService.localizeText("INFO_WALL_ADDED"), pos); } } else { if (this.selectedItem instanceof Structure) { msg = sprintf(this.i18nService.localizeText("INFO_DEVICE_ADDED_N_TIMES"), this.childrenToAdd); } else { msg = sprintf(this.i18nService.localizeText("INFO_WALL_ADDED_N_TIMES"), this.childrenToAdd); } } this.notifService.notify(msg); this.childrenToAdd = 1; // reinit to avoid confusion } public onCopyClick() { // cloned selected item for (let i = 0; i < this.childrenToAdd; i++) {
771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840
const newChild = Session.getInstance().createNub( this.selectedItem.properties.clone(), this.selectedItem.parent ); // copy parameter values for (const p of this.selectedItem.prms) { newChild.getParameter(p.symbol).singleValue = p.singleValue; } // copy children if (this.selectedItem instanceof ParallelStructure) { for (const c of this.selectedItem.getChildren()) { const newGrandChild = Session.getInstance().createNub( c.properties.clone(), newChild ); // copy children parameters values for (const p of c.prms) { newGrandChild.getParameter(p.symbol).singleValue = p.singleValue; } // add to parent newChild.addChild( newGrandChild, c.findPositionInParent() ); } } // add to parent this.selectedItem.parent.addChild( newChild, this.selectedItem.findPositionInParent() ); } this.refresh(); // notify const pos = this.selectedItem.findPositionInParent() + 1; let msg: string; if (this.childrenToAdd === 1) { if (this.selectedItem instanceof Structure) { msg = sprintf(this.i18nService.localizeText("INFO_DEVICE_COPIED"), pos); } else { msg = sprintf(this.i18nService.localizeText("INFO_WALL_COPIED"), pos); } } else { if (this.selectedItem instanceof Structure) { msg = sprintf(this.i18nService.localizeText("INFO_DEVICE_COPIED_N_TIMES"), pos, this.childrenToAdd); } else { msg = sprintf(this.i18nService.localizeText("INFO_WALL_COPIED_N_TIMES"), pos, this.childrenToAdd); } } this.notifService.notify(msg); this.childrenToAdd = 1; // reinit to avoid confusion } public onMoveUpClick() { const pos = this.selectedItem.findPositionInParent() + 1; this.selectedItem.parent.moveChildUp(this.selectedItem); if (this.selectedItem instanceof Structure) { this.notifService.notify(sprintf(this.i18nService.localizeText("INFO_DEVICE_MOVED"), pos)); } else { this.notifService.notify(sprintf(this.i18nService.localizeText("INFO_WALL_MOVED"), pos)); } this.refresh(); } public onMoveDownClick() { const pos = this.selectedItem.findPositionInParent() + 1; this.selectedItem.parent.moveChildDown(this.selectedItem); if (this.selectedItem instanceof Structure) {
841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910
this.notifService.notify(sprintf(this.i18nService.localizeText("INFO_DEVICE_MOVED"), pos)); } else { this.notifService.notify(sprintf(this.i18nService.localizeText("INFO_WALL_MOVED"), pos)); } this.refresh(); } public onRemoveClick() { const pos = this.selectedItem.findPositionInParent() + 1; this.selectedItem.parent.deleteChild(this.selectedItem.findPositionInParent()); if (this.selectedItem instanceof Structure) { this.notifService.notify(sprintf(this.i18nService.localizeText("INFO_DEVICE_REMOVED"), pos)); } else { this.notifService.notify(sprintf(this.i18nService.localizeText("INFO_WALL_REMOVED"), pos)); } this.refresh(); } /** Replace device Nub when LoiDebit is changed */ public loiDebitSelected($event: any, cell: any) { const device = cell.model as Nub; const pos = device.findPositionInParent(); // create new child device const newDevice = Session.getInstance().createNub( new Props({ calcType: CalculatorType.Structure, loiDebit: $event.value }) ); // replace the current one device.parent.replaceChildInplace(device, newDevice); this.refresh(); } // show modal dialog for values edition public showEditPab() { if (this.selectedItems.length > 0) { // list variables eligible to modification const availableVariables: { label: string, value: string, occurrences: number, first: number, last: number }[] = []; for (const c of this.selectedItems) { for (const p of c.parameterIterator) { // deep one if ( p.visible && ! availableVariables.map(av => av.value).includes(p.symbol) ) { availableVariables.push({ label: this.formService.expandVariableNameAndUnit(CalculatorType.Pab, p.symbol), value: p.symbol, occurrences: 0, first: undefined, last: undefined }); } } } // find their min/max values (2nd pass) for (const av of availableVariables) { for (const c of this.selectedItems) { for (const p of c.parameterIterator) { if (p.visible && p.symbol === av.value) { av.occurrences ++; if (av.first === undefined) { av.first = p.singleValue; } av.last = p.singleValue; } } } }
911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980
// sum up selected items const walls: ParallelStructure[] = []; const wallsDevices: Structure[] = []; const devices: Structure[] = []; let vertical = true; // @TODO vertical AND consecutive ! let firstDevicePosition: number; // 1st pass for (const s of this.selectedItems) { if (s instanceof ParallelStructure) { walls.push(s); for (const c of s.structures) { if (firstDevicePosition === undefined) { firstDevicePosition = c.findPositionInParent(); } else { vertical = (vertical && (c.findPositionInParent() === firstDevicePosition)); } wallsDevices.push(c); } } } // 2nd pass for (const c of this.selectedItems) { if (c instanceof Structure) { if (! wallsDevices.includes(c)) { if (firstDevicePosition === undefined) { firstDevicePosition = c.findPositionInParent(); } else { vertical = (vertical && (c.findPositionInParent() === firstDevicePosition)); } devices.push(c); } } } // open dialog const dialogRef = this.editPabDialog.open( DialogEditPabComponent, { data: { availableVariables: availableVariables, selectedItemsAbstract: { walls: walls.length, wallsDevices: wallsDevices.length, devices: devices.length }, vertical: vertical // used to enable interpolation }, disableClose: true } ); // apply modifications dialogRef.afterClosed().subscribe(result => { if (result) { /* console.log("Apply values in parent !!", result.action, result.variable, result.value, result.delta, result.variableDetails); */ switch (result.action) { case "set-value": for (const s of this.selectedItems) { for (const p of s.parameterIterator) { // deep if (p.symbol === result.variable) { p.singleValue = result.value; } } } break; case "delta": for (const s of this.selectedItems) {
981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050
for (const p of s.parameterIterator) { // deep if (p.symbol === result.variable) { p.singleValue += result.delta; } } } break; case "interpolate": if (result.variableDetails.occurrences > 1) { const nDigits = this.appSetupService.displayDigits; // build values list const interpolatedValues: number[] = []; const step = ( (result.variableDetails.last - result.variableDetails.first) / (result.variableDetails.occurrences - 1) ); interpolatedValues.push(result.variableDetails.first); let currentValue: number = result.variableDetails.first; for (let i = 0; i < result.variableDetails.occurrences - 2; i++) { currentValue += step; interpolatedValues.push(Number(currentValue.toFixed(nDigits))); } interpolatedValues.push(result.variableDetails.last); // apply let idx = 0; for (const s of this.selectedItems) { for (const p of s.parameterIterator) { // deep if (p.symbol === result.variable) { p.singleValue = interpolatedValues[idx]; idx ++; } } } } else { throw new Error( `showEditPab() : cannot interpolate, too few occurrences (${result.variableDetails.occurrences})` ); } break; } } }); } } /* public ngAfterViewInit() { this.onFieldsetListChange(); this._fieldsetComponents.changes.subscribe(_ => this.onFieldsetListChange()); } public ngDoCheck() { this.updateValidity(); } */ /** * @TODO Calcul de la validité de la Pab */ private updateValidity() { this._isValid = false; /* if (this._fieldsetComponents !== undefined) { this._isValid = this._fieldsetComponents.reduce( // callback ( // accumulator (valeur précédente du résultat) acc, // currentValue (élément courant dans le tableau) fieldset, // currentIndex (indice courant dans le tableau)
10511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082
currIndex, // array (tableau parcouru) array ) => { return acc && fieldset.isValid; } // valeur initiale , this._fieldsetComponents.length > 0); } */ this.validChange.emit(); } /** * réception d'un événement de changement de valeur d'un input */ private onInputChange($event) { this.inputChange.emit($event); } /** * Renvoie l'événement au composant du dessus */ public onTabPressed(event) { console.log("tab pressed dans le tablo !"); } public get uitextEditPabTable() { return "Modifier les valeurs"; } }