@caribeng/ui 22.4.0 → 22.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +311 -313
- package/fesm2022/caribeng-ui-account-picker.mjs +533 -0
- package/fesm2022/caribeng-ui-aging.mjs +488 -0
- package/fesm2022/{caribeng-ui-caribe-alert.mjs → caribeng-ui-alert.mjs} +45 -45
- package/fesm2022/caribeng-ui-amount.mjs +249 -0
- package/fesm2022/caribeng-ui-anchor.mjs +2 -2
- package/fesm2022/{caribeng-ui-caribe-animation-lottie.mjs → caribeng-ui-animation-lottie.mjs} +41 -41
- package/fesm2022/caribeng-ui-audit-log.mjs +323 -0
- package/fesm2022/caribeng-ui-avatar.mjs +2 -2
- package/fesm2022/caribeng-ui-breadcrumb.mjs +13 -3
- package/fesm2022/{caribeng-ui-caribe-button-group.mjs → caribeng-ui-button-group.mjs} +15 -15
- package/fesm2022/caribeng-ui-button.mjs +2 -2
- package/fesm2022/{caribeng-ui-caribe-card-content.mjs → caribeng-ui-card-content.mjs} +39 -39
- package/fesm2022/{caribeng-ui-caribe-card-move.mjs → caribeng-ui-card-move.mjs} +65 -65
- package/fesm2022/{caribeng-ui-caribe-card-primary.mjs → caribeng-ui-card-primary.mjs} +31 -31
- package/fesm2022/{caribeng-ui-caribe-card-select.mjs → caribeng-ui-card-select.mjs} +67 -67
- package/fesm2022/caribeng-ui-carousel.mjs +2 -2
- package/fesm2022/caribeng-ui-cascadeselect.mjs +45 -9
- package/fesm2022/caribeng-ui-chat.mjs +2 -2
- package/fesm2022/{caribeng-ui-caribe-coachmark.mjs → caribeng-ui-coachmark.mjs} +85 -85
- package/fesm2022/caribeng-ui-command-palette.mjs +2 -2
- package/fesm2022/caribeng-ui-comments.mjs +864 -0
- package/fesm2022/caribeng-ui-datagrid.mjs +1635 -0
- package/fesm2022/caribeng-ui-dataview.mjs +2 -2
- package/fesm2022/caribeng-ui-datepicker.mjs +2 -2
- package/fesm2022/caribeng-ui-document.mjs +495 -0
- package/fesm2022/{caribeng-ui-caribe-dots-indicator.mjs → caribeng-ui-dots-indicator.mjs} +41 -41
- package/fesm2022/caribeng-ui-dynamic-form.mjs +1581 -0
- package/fesm2022/caribeng-ui-editor.mjs +2303 -1311
- package/fesm2022/{caribeng-ui-caribe-expansion-panel.mjs → caribeng-ui-expansion-panel.mjs} +39 -39
- package/fesm2022/{caribeng-ui-caribe-fab-menu.mjs → caribeng-ui-fab-menu.mjs} +75 -75
- package/fesm2022/caribeng-ui-file-card.mjs +2 -2
- package/fesm2022/{caribeng-ui-caribe-file-download.mjs → caribeng-ui-file-download.mjs} +63 -63
- package/fesm2022/caribeng-ui-financial-report.mjs +380 -0
- package/fesm2022/{caribeng-ui-caribe-float-menu.mjs → caribeng-ui-float-menu.mjs} +31 -31
- package/fesm2022/caribeng-ui-floatlabel.mjs +2 -2
- package/fesm2022/caribeng-ui-flow.mjs +1508 -0
- package/fesm2022/{caribeng-ui-caribe-footer.mjs → caribeng-ui-footer.mjs} +19 -19
- package/fesm2022/caribeng-ui-gantt.mjs +1094 -0
- package/fesm2022/{caribeng-ui-caribe-header.mjs → caribeng-ui-header.mjs} +49 -49
- package/fesm2022/{caribeng-ui-caribe-icon-button.mjs → caribeng-ui-icon-button.mjs} +23 -23
- package/fesm2022/caribeng-ui-image-cropper.mjs +671 -0
- package/fesm2022/caribeng-ui-import-wizard.mjs +746 -0
- package/fesm2022/caribeng-ui-infinite-scroll.mjs +226 -0
- package/fesm2022/caribeng-ui-input-number.mjs +22 -6
- package/fesm2022/{caribeng-ui-caribe-input-search.mjs → caribeng-ui-input-search.mjs} +65 -65
- package/fesm2022/{caribeng-ui-caribe-input-token.mjs → caribeng-ui-input-token.mjs} +59 -59
- package/fesm2022/caribeng-ui-inputotp.mjs +2 -2
- package/fesm2022/caribeng-ui-journal-entry.mjs +340 -0
- package/fesm2022/caribeng-ui-kanban.mjs +6 -6
- package/fesm2022/caribeng-ui-kpi.mjs +189 -0
- package/fesm2022/{caribeng-ui-caribe-link.mjs → caribeng-ui-link.mjs} +37 -37
- package/fesm2022/caribeng-ui-masonry.mjs +93 -0
- package/fesm2022/caribeng-ui-media-player.mjs +821 -0
- package/fesm2022/caribeng-ui-mentions.mjs +2 -2
- package/fesm2022/caribeng-ui-notification-center.mjs +636 -0
- package/fesm2022/{caribeng-ui-caribe-off-canvas.mjs → caribeng-ui-off-canvas.mjs} +55 -55
- package/fesm2022/{caribeng-ui-caribe-onboarding.mjs → caribeng-ui-onboarding.mjs} +105 -105
- package/fesm2022/caribeng-ui-orderlist.mjs +2 -2
- package/fesm2022/caribeng-ui-pdfviewer.mjs +1755 -25
- package/fesm2022/caribeng-ui-period-picker.mjs +637 -0
- package/fesm2022/caribeng-ui-phone-input.mjs +2 -2
- package/fesm2022/caribeng-ui-picklist.mjs +2 -2
- package/fesm2022/caribeng-ui-pivot.mjs +419 -0
- package/fesm2022/caribeng-ui-pricing.mjs +2 -2
- package/fesm2022/caribeng-ui-rating.mjs +14 -17
- package/fesm2022/caribeng-ui-reconciliation.mjs +386 -0
- package/fesm2022/caribeng-ui-scheduler.mjs +1027 -0
- package/fesm2022/caribeng-ui-select.mjs +2 -2
- package/fesm2022/{caribeng-ui-caribe-shortcut.mjs → caribeng-ui-shortcut.mjs} +29 -29
- package/fesm2022/caribeng-ui-sidebar.mjs +2 -2
- package/fesm2022/caribeng-ui-signature-pad.mjs +654 -0
- package/fesm2022/{caribeng-ui-caribe-status.mjs → caribeng-ui-status.mjs} +11 -11
- package/fesm2022/{caribeng-ui-caribe-step-indicator.mjs → caribeng-ui-step-indicator.mjs} +53 -53
- package/fesm2022/caribeng-ui-stepper.mjs +2 -2
- package/fesm2022/caribeng-ui-steps.mjs +2 -2
- package/fesm2022/caribeng-ui-table.mjs +323 -15
- package/fesm2022/caribeng-ui-tabmenu.mjs +2 -2
- package/fesm2022/caribeng-ui-tabs.mjs +2 -2
- package/fesm2022/{caribeng-ui-caribe-tag-button.mjs → caribeng-ui-tag-button.mjs} +25 -25
- package/fesm2022/caribeng-ui-tag.mjs +2 -2
- package/fesm2022/caribeng-ui-tieredmenu.mjs +6 -6
- package/fesm2022/{caribeng-ui-caribe-tracker.mjs → caribeng-ui-tracker.mjs} +29 -29
- package/fesm2022/{caribeng-ui-caribe-transaction-status.mjs → caribeng-ui-transaction-status.mjs} +11 -11
- package/fesm2022/caribeng-ui-treeselect.mjs +44 -9
- package/fesm2022/caribeng-ui-treetable.mjs +236 -17
- package/fesm2022/{caribeng-ui-caribe-voucher.mjs → caribeng-ui-voucher.mjs} +45 -45
- package/fesm2022/caribeng-ui-xlsx.mjs +486 -0
- package/fesm2022/caribeng-ui.mjs +1181 -1
- package/package.json +217 -177
- package/types/caribeng-ui-account-picker.d.ts +142 -0
- package/types/caribeng-ui-aging.d.ts +123 -0
- package/types/{caribeng-ui-caribe-alert.d.ts → caribeng-ui-alert.d.ts} +2 -2
- package/types/caribeng-ui-amount.d.ts +82 -0
- package/types/{caribeng-ui-caribe-animation-lottie.d.ts → caribeng-ui-animation-lottie.d.ts} +2 -2
- package/types/caribeng-ui-audit-log.d.ts +86 -0
- package/types/caribeng-ui-breadcrumb.d.ts +2 -2
- package/types/{caribeng-ui-caribe-button-group.d.ts → caribeng-ui-button-group.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-card-content.d.ts → caribeng-ui-card-content.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-card-move.d.ts → caribeng-ui-card-move.d.ts} +1 -1
- package/types/{caribeng-ui-caribe-card-primary.d.ts → caribeng-ui-card-primary.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-card-select.d.ts → caribeng-ui-card-select.d.ts} +2 -2
- package/types/caribeng-ui-cascadeselect.d.ts +6 -0
- package/types/{caribeng-ui-caribe-coachmark.d.ts → caribeng-ui-coachmark.d.ts} +2 -2
- package/types/caribeng-ui-comments.d.ts +214 -0
- package/types/caribeng-ui-datagrid.d.ts +269 -0
- package/types/caribeng-ui-document.d.ts +138 -0
- package/types/{caribeng-ui-caribe-dots-indicator.d.ts → caribeng-ui-dots-indicator.d.ts} +2 -2
- package/types/caribeng-ui-dynamic-form.d.ts +409 -0
- package/types/caribeng-ui-editor.d.ts +110 -12
- package/types/{caribeng-ui-caribe-expansion-panel.d.ts → caribeng-ui-expansion-panel.d.ts} +1 -1
- package/types/{caribeng-ui-caribe-fab-menu.d.ts → caribeng-ui-fab-menu.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-file-download.d.ts → caribeng-ui-file-download.d.ts} +1 -1
- package/types/caribeng-ui-financial-report.d.ts +102 -0
- package/types/{caribeng-ui-caribe-float-menu.d.ts → caribeng-ui-float-menu.d.ts} +2 -2
- package/types/caribeng-ui-flow.d.ts +228 -0
- package/types/{caribeng-ui-caribe-footer.d.ts → caribeng-ui-footer.d.ts} +2 -2
- package/types/caribeng-ui-gantt.d.ts +244 -0
- package/types/{caribeng-ui-caribe-header.d.ts → caribeng-ui-header.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-icon-button.d.ts → caribeng-ui-icon-button.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-illustration.d.ts → caribeng-ui-illustration.d.ts} +1 -1
- package/types/caribeng-ui-image-cropper.d.ts +169 -0
- package/types/caribeng-ui-import-wizard.d.ts +149 -0
- package/types/caribeng-ui-infinite-scroll.d.ts +75 -0
- package/types/caribeng-ui-input-number.d.ts +1 -1
- package/types/{caribeng-ui-caribe-input-search.d.ts → caribeng-ui-input-search.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-input-token.d.ts → caribeng-ui-input-token.d.ts} +2 -2
- package/types/caribeng-ui-journal-entry.d.ts +110 -0
- package/types/caribeng-ui-kpi.d.ts +64 -0
- package/types/{caribeng-ui-caribe-link.d.ts → caribeng-ui-link.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-logo.d.ts → caribeng-ui-logo.d.ts} +1 -1
- package/types/caribeng-ui-masonry.d.ts +32 -0
- package/types/caribeng-ui-media-player.d.ts +140 -0
- package/types/caribeng-ui-notification-center.d.ts +153 -0
- package/types/{caribeng-ui-caribe-off-canvas.d.ts → caribeng-ui-off-canvas.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-onboarding.d.ts → caribeng-ui-onboarding.d.ts} +2 -2
- package/types/caribeng-ui-pdfviewer.d.ts +245 -5
- package/types/caribeng-ui-period-picker.d.ts +148 -0
- package/types/caribeng-ui-pivot.d.ts +116 -0
- package/types/caribeng-ui-reconciliation.d.ts +109 -0
- package/types/caribeng-ui-scheduler.d.ts +188 -0
- package/types/{caribeng-ui-caribe-shortcut.d.ts → caribeng-ui-shortcut.d.ts} +2 -2
- package/types/caribeng-ui-signature-pad.d.ts +151 -0
- package/types/{caribeng-ui-caribe-status.d.ts → caribeng-ui-status.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-step-indicator.d.ts → caribeng-ui-step-indicator.d.ts} +2 -2
- package/types/caribeng-ui-table.d.ts +66 -2
- package/types/{caribeng-ui-caribe-tag-button.d.ts → caribeng-ui-tag-button.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-tracker.d.ts → caribeng-ui-tracker.d.ts} +2 -2
- package/types/{caribeng-ui-caribe-transaction-status.d.ts → caribeng-ui-transaction-status.d.ts} +2 -2
- package/types/caribeng-ui-treeselect.d.ts +6 -0
- package/types/caribeng-ui-treetable.d.ts +67 -2
- package/types/{caribeng-ui-caribe-voucher.d.ts → caribeng-ui-voucher.d.ts} +2 -2
- package/types/caribeng-ui-xlsx.d.ts +79 -0
- package/types/caribeng-ui.d.ts +711 -2
- package/fesm2022/caribeng-ui-caribe-calendar.mjs +0 -92
- package/fesm2022/caribeng-ui-caribe-circle-loading.mjs +0 -130
- package/fesm2022/caribeng-ui-caribe-data-table.mjs +0 -94
- package/fesm2022/caribeng-ui-caribe-file-select.mjs +0 -88
- package/fesm2022/caribeng-ui-caribe-inline-alert.mjs +0 -100
- package/fesm2022/caribeng-ui-caribe-input-date.mjs +0 -138
- package/fesm2022/caribeng-ui-caribe-input-select.mjs +0 -154
- package/fesm2022/caribeng-ui-caribe-loader.mjs +0 -48
- package/fesm2022/caribeng-ui-caribe-modal.mjs +0 -119
- package/fesm2022/caribeng-ui-caribe-pictogram.mjs +0 -52
- package/fesm2022/caribeng-ui-caribe-pop-over.mjs +0 -104
- package/fesm2022/caribeng-ui-caribe-preloader.mjs +0 -57
- package/fesm2022/caribeng-ui-caribe-progress-bar.mjs +0 -84
- package/fesm2022/caribeng-ui-caribe-stroke.mjs +0 -69
- package/fesm2022/caribeng-ui-caribe-switch.mjs +0 -182
- package/types/caribeng-ui-caribe-calendar.d.ts +0 -27
- package/types/caribeng-ui-caribe-circle-loading.d.ts +0 -28
- package/types/caribeng-ui-caribe-data-table.d.ts +0 -26
- package/types/caribeng-ui-caribe-file-select.d.ts +0 -31
- package/types/caribeng-ui-caribe-inline-alert.d.ts +0 -28
- package/types/caribeng-ui-caribe-input-date.d.ts +0 -40
- package/types/caribeng-ui-caribe-input-select.d.ts +0 -47
- package/types/caribeng-ui-caribe-loader.d.ts +0 -22
- package/types/caribeng-ui-caribe-modal.d.ts +0 -21
- package/types/caribeng-ui-caribe-pictogram.d.ts +0 -15
- package/types/caribeng-ui-caribe-pop-over.d.ts +0 -17
- package/types/caribeng-ui-caribe-preloader.d.ts +0 -24
- package/types/caribeng-ui-caribe-progress-bar.d.ts +0 -28
- package/types/caribeng-ui-caribe-stroke.d.ts +0 -17
- package/types/caribeng-ui-caribe-switch.d.ts +0 -55
- /package/fesm2022/{caribeng-ui-caribe-illustration.mjs → caribeng-ui-illustration.mjs} +0 -0
- /package/fesm2022/{caribeng-ui-caribe-logo.mjs → caribeng-ui-logo.mjs} +0 -0
|
@@ -0,0 +1,380 @@
|
|
|
1
|
+
import * as i0 from '@angular/core';
|
|
2
|
+
import { inject, viewChild, input, booleanAttribute, model, output, computed, afterRenderEffect, untracked, ViewEncapsulation, ChangeDetectionStrategy, Component } from '@angular/core';
|
|
3
|
+
import { injectCbTranslation, cbFormat, CB_CONFIG, cbSummarize, cbFormatAmount } from '@caribeng/ui';
|
|
4
|
+
import { resolveAccounts, accountLabel } from '@caribeng/ui/account-picker';
|
|
5
|
+
import { CbButton } from '@caribeng/ui/button';
|
|
6
|
+
import { CbIcon } from '@caribeng/ui/icon';
|
|
7
|
+
import { CbTreeTable } from '@caribeng/ui/treetable';
|
|
8
|
+
import { currencySymbol, cbDownloadXlsx } from '@caribeng/ui/xlsx';
|
|
9
|
+
|
|
10
|
+
let nextUid = 0;
|
|
11
|
+
/**
|
|
12
|
+
* Informe financiero jerárquico de CaribeNG: balance general, estado de resultados
|
|
13
|
+
* o balance de prueba a partir del plan de cuentas y los saldos de las cuentas de
|
|
14
|
+
* movimiento.
|
|
15
|
+
*
|
|
16
|
+
* - Cada cuenta mayor suma a sus auxiliares; los niveles se abren con los botones
|
|
17
|
+
* «Nivel 1…N» y se pueden ocultar las cuentas en cero.
|
|
18
|
+
* - Varios periodos en columnas y, con `comparative`, la variación y el % del
|
|
19
|
+
* primero frente al segundo.
|
|
20
|
+
* - Totales calculados (`totals`), saldos de naturaleza crédito en positivo
|
|
21
|
+
* (`signByNature`), exportación a Excel con niveles plegables e impresión.
|
|
22
|
+
* - Clic o Enter en una cuenta de movimiento emite `accountOpen` (ver sus movimientos).
|
|
23
|
+
*
|
|
24
|
+
* @example
|
|
25
|
+
* ```html
|
|
26
|
+
* <cb-financial-report title="Estado de resultados" [accounts]="puc" [balances]="saldos" [periods]="['2026', '2025']" comparative [classes]="['4', '5', '6']" [totals]="utilidad" />
|
|
27
|
+
* ```
|
|
28
|
+
*/
|
|
29
|
+
class CbFinancialReport {
|
|
30
|
+
/** Signo de cada cuenta según la naturaleza de su clase. */
|
|
31
|
+
signOf(acc) {
|
|
32
|
+
if (!this.signByNature())
|
|
33
|
+
return 1;
|
|
34
|
+
const nature = acc.nature ?? acc.ancestors.find((a) => a.nature)?.nature ?? (['2', '3', '4'].includes(acc.code[0]) ? 'credit' : 'debit');
|
|
35
|
+
return nature === 'credit' ? -1 : 1;
|
|
36
|
+
}
|
|
37
|
+
constructor() {
|
|
38
|
+
this.t = injectCbTranslation();
|
|
39
|
+
this.fmt = cbFormat;
|
|
40
|
+
this.config = inject(CB_CONFIG);
|
|
41
|
+
this.uid = `cb-financial-report-${++nextUid}`;
|
|
42
|
+
this.tree = viewChild.required(CbTreeTable);
|
|
43
|
+
this.title = input('', /* @ts-ignore */
|
|
44
|
+
...(ngDevMode ? [{ debugName: "title" }] : /* istanbul ignore next */ []));
|
|
45
|
+
/** Líneas bajo el título (empresa, NIT, periodo). */
|
|
46
|
+
this.subtitle = input([], /* @ts-ignore */
|
|
47
|
+
...(ngDevMode ? [{ debugName: "subtitle" }] : /* istanbul ignore next */ []));
|
|
48
|
+
/** Plan de cuentas. */
|
|
49
|
+
this.accounts = input([], /* @ts-ignore */
|
|
50
|
+
...(ngDevMode ? [{ debugName: "accounts" }] : /* istanbul ignore next */ []));
|
|
51
|
+
/** Saldos de las cuentas de movimiento, uno por periodo. */
|
|
52
|
+
this.balances = input({}, /* @ts-ignore */
|
|
53
|
+
...(ngDevMode ? [{ debugName: "balances" }] : /* istanbul ignore next */ []));
|
|
54
|
+
/** Nombres de los periodos (columnas). */
|
|
55
|
+
this.periods = input([], /* @ts-ignore */
|
|
56
|
+
...(ngDevMode ? [{ debugName: "periods" }] : /* istanbul ignore next */ []));
|
|
57
|
+
/** Columnas de variación y % del primer periodo frente al segundo. */
|
|
58
|
+
this.comparative = input(false, { ...(ngDevMode ? { debugName: "comparative" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
|
|
59
|
+
/**
|
|
60
|
+
* Clases (cuentas raíz) que se muestran: `['1', '2', '3']` para el balance. Todas
|
|
61
|
+
* por defecto. Los `totals` pueden usar cualquier cuenta, también de otras clases.
|
|
62
|
+
*/
|
|
63
|
+
this.classes = input(null, /* @ts-ignore */
|
|
64
|
+
...(ngDevMode ? [{ debugName: "classes" }] : /* istanbul ignore next */ []));
|
|
65
|
+
/** Muestra en positivo los saldos de naturaleza crédito (pasivo, patrimonio, ingresos). */
|
|
66
|
+
this.signByNature = input(true, { ...(ngDevMode ? { debugName: "signByNature" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
|
|
67
|
+
/** Filas de total al final. */
|
|
68
|
+
this.totals = input([], /* @ts-ignore */
|
|
69
|
+
...(ngDevMode ? [{ debugName: "totals" }] : /* istanbul ignore next */ []));
|
|
70
|
+
/** Niveles abiertos (1 = solo las clases). */
|
|
71
|
+
this.level = model(2, /* @ts-ignore */
|
|
72
|
+
...(ngDevMode ? [{ debugName: "level" }] : /* istanbul ignore next */ []));
|
|
73
|
+
/** Oculta las cuentas cuyos saldos son todos cero. */
|
|
74
|
+
this.hideZero = model(false, /* @ts-ignore */
|
|
75
|
+
...(ngDevMode ? [{ debugName: "hideZero" }] : /* istanbul ignore next */ []));
|
|
76
|
+
this.toolbar = input(true, { ...(ngDevMode ? { debugName: "toolbar" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
|
|
77
|
+
this.currency = input(undefined, /* @ts-ignore */
|
|
78
|
+
...(ngDevMode ? [{ debugName: "currency" }] : /* istanbul ignore next */ []));
|
|
79
|
+
this.negativeStyle = input('parens', /* @ts-ignore */
|
|
80
|
+
...(ngDevMode ? [{ debugName: "negativeStyle" }] : /* istanbul ignore next */ []));
|
|
81
|
+
/** Clic o Enter en una cuenta de movimiento. */
|
|
82
|
+
this.accountOpen = output();
|
|
83
|
+
this.resolved = computed(() => resolveAccounts(this.accounts()), /* @ts-ignore */
|
|
84
|
+
...(ngDevMode ? [{ debugName: "resolved" }] : /* istanbul ignore next */ []));
|
|
85
|
+
this.byCode = computed(() => new Map(this.resolved().map((a) => [a.code, a])), /* @ts-ignore */
|
|
86
|
+
...(ngDevMode ? [{ debugName: "byCode" }] : /* istanbul ignore next */ []));
|
|
87
|
+
/** Árbol de todo el plan de cuentas con los saldos (con signo) en las hojas. */
|
|
88
|
+
this.allNodes = computed(() => {
|
|
89
|
+
const periods = this.periods().length;
|
|
90
|
+
const balances = this.balances();
|
|
91
|
+
const all = this.resolved();
|
|
92
|
+
const childrenOf = new Map();
|
|
93
|
+
const roots = [];
|
|
94
|
+
const present = new Set(all.map((a) => a.code));
|
|
95
|
+
for (const a of all) {
|
|
96
|
+
const parent = [...a.ancestors].reverse().find((p) => present.has(p.code));
|
|
97
|
+
if (parent) {
|
|
98
|
+
if (!childrenOf.has(parent.code))
|
|
99
|
+
childrenOf.set(parent.code, []);
|
|
100
|
+
childrenOf.get(parent.code).push(a);
|
|
101
|
+
}
|
|
102
|
+
else
|
|
103
|
+
roots.push(a);
|
|
104
|
+
}
|
|
105
|
+
const build = (a) => {
|
|
106
|
+
const kids = childrenOf.get(a.code) ?? [];
|
|
107
|
+
const data = { cuenta: accountLabel(a), code: a.code };
|
|
108
|
+
if (!kids.length) {
|
|
109
|
+
const sign = this.signOf(a);
|
|
110
|
+
const values = balances[a.code] ?? [];
|
|
111
|
+
for (let i = 0; i < periods; i++)
|
|
112
|
+
data[`p${i}`] = values[i] == null ? 0 : sign * values[i];
|
|
113
|
+
if (this.comparative() && periods >= 2) {
|
|
114
|
+
data['var'] = data['p0'] - data['p1'];
|
|
115
|
+
data['pct'] = data['p1'] ? data['var'] / Math.abs(data['p1']) : null;
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
return { key: a.code, data, children: kids.length ? kids.map(build) : undefined };
|
|
119
|
+
};
|
|
120
|
+
return roots.map(build);
|
|
121
|
+
}, /* @ts-ignore */
|
|
122
|
+
...(ngDevMode ? [{ debugName: "allNodes" }] : /* istanbul ignore next */ []));
|
|
123
|
+
/** Árbol del informe: solo las clases pedidas (`classes`). */
|
|
124
|
+
this.baseNodes = computed(() => {
|
|
125
|
+
const allowed = this.classes();
|
|
126
|
+
return allowed ? this.allNodes().filter((n) => allowed.some((c) => n.key.startsWith(c))) : this.allNodes();
|
|
127
|
+
}, /* @ts-ignore */
|
|
128
|
+
...(ngDevMode ? [{ debugName: "baseNodes" }] : /* istanbul ignore next */ []));
|
|
129
|
+
/** Árbol mostrado: sin las cuentas en cero (si se pide) y con las filas de total. */
|
|
130
|
+
this.nodes = computed(() => {
|
|
131
|
+
const periods = this.periods().length;
|
|
132
|
+
const isZero = (n) => n.children?.length ? n.children.every(isZero) : Array.from({ length: periods }, (_, i) => n.data[`p${i}`]).every((v) => !v);
|
|
133
|
+
const prune = (nodes) => nodes.filter((n) => !isZero(n)).map((n) => (n.children?.length ? { ...n, children: prune(n.children) } : n));
|
|
134
|
+
const tree = this.hideZero() ? prune(this.baseNodes()) : this.baseNodes();
|
|
135
|
+
return [...tree, ...this.totalNodes()];
|
|
136
|
+
}, /* @ts-ignore */
|
|
137
|
+
...(ngDevMode ? [{ debugName: "nodes" }] : /* istanbul ignore next */ []));
|
|
138
|
+
/** Total (con signo) de una cuenta en cada periodo, sumando sus hojas. */
|
|
139
|
+
this.sums = computed(() => {
|
|
140
|
+
const periods = this.periods().length;
|
|
141
|
+
const out = new Map();
|
|
142
|
+
const walk = (n) => {
|
|
143
|
+
const v = n.children?.length
|
|
144
|
+
? n.children.map(walk).reduce((acc, x) => acc.map((a, i) => a + x[i]), new Array(periods).fill(0))
|
|
145
|
+
: Array.from({ length: periods }, (_, i) => n.data[`p${i}`] ?? 0);
|
|
146
|
+
out.set(n.key, v);
|
|
147
|
+
return v;
|
|
148
|
+
};
|
|
149
|
+
// Sobre todo el plan: un total puede usar cuentas fuera de las clases mostradas.
|
|
150
|
+
this.allNodes().forEach(walk);
|
|
151
|
+
return out;
|
|
152
|
+
}, /* @ts-ignore */
|
|
153
|
+
...(ngDevMode ? [{ debugName: "sums" }] : /* istanbul ignore next */ []));
|
|
154
|
+
this.totalNodes = computed(() => {
|
|
155
|
+
const periods = this.periods().length;
|
|
156
|
+
return this.totals().map((total, ti) => {
|
|
157
|
+
const values = new Array(periods).fill(0);
|
|
158
|
+
for (const term of total.terms) {
|
|
159
|
+
const v = this.sums().get(term.code) ?? new Array(periods).fill(0);
|
|
160
|
+
v.forEach((x, i) => (values[i] = Math.round((values[i] + (term.sign ?? 1) * x) * 100) / 100));
|
|
161
|
+
}
|
|
162
|
+
const data = { cuenta: total.label };
|
|
163
|
+
values.forEach((v, i) => (data[`p${i}`] = v));
|
|
164
|
+
if (this.comparative() && periods >= 2) {
|
|
165
|
+
data['var'] = values[0] - values[1];
|
|
166
|
+
data['pct'] = values[1] ? (values[0] - values[1]) / Math.abs(values[1]) : null;
|
|
167
|
+
}
|
|
168
|
+
return { key: `__total${ti}`, data };
|
|
169
|
+
});
|
|
170
|
+
}, /* @ts-ignore */
|
|
171
|
+
...(ngDevMode ? [{ debugName: "totalNodes" }] : /* istanbul ignore next */ []));
|
|
172
|
+
this.columns = computed(() => {
|
|
173
|
+
const t = this.t();
|
|
174
|
+
const cols = [{ field: 'cuenta', header: t.journalAccount }];
|
|
175
|
+
this.periods().forEach((p, i) => cols.push({ field: `p${i}`, header: p, type: 'currency', summary: 'sum' }));
|
|
176
|
+
if (this.comparative() && this.periods().length >= 2) {
|
|
177
|
+
cols.push({ field: 'var', header: t.reportVariation, type: 'currency', summary: (leaves) => (cbSummarize(leaves.map((d) => d['p0']), 'sum') ?? 0) - (cbSummarize(leaves.map((d) => d['p1']), 'sum') ?? 0) }, {
|
|
178
|
+
field: 'pct',
|
|
179
|
+
header: '%',
|
|
180
|
+
type: 'percent',
|
|
181
|
+
decimals: 1,
|
|
182
|
+
summary: (leaves) => {
|
|
183
|
+
const cur = cbSummarize(leaves.map((d) => d['p0']), 'sum') ?? 0;
|
|
184
|
+
const prev = cbSummarize(leaves.map((d) => d['p1']), 'sum') ?? 0;
|
|
185
|
+
return prev ? (cur - prev) / Math.abs(prev) : null;
|
|
186
|
+
},
|
|
187
|
+
});
|
|
188
|
+
}
|
|
189
|
+
return cols;
|
|
190
|
+
}, /* @ts-ignore */
|
|
191
|
+
...(ngDevMode ? [{ debugName: "columns" }] : /* istanbul ignore next */ []));
|
|
192
|
+
/** Niveles disponibles (hasta la profundidad del plan de cuentas). */
|
|
193
|
+
this.levels = computed(() => {
|
|
194
|
+
let depth = 1;
|
|
195
|
+
const walk = (nodes, d) => nodes.forEach((n) => {
|
|
196
|
+
depth = Math.max(depth, d);
|
|
197
|
+
if (n.children?.length)
|
|
198
|
+
walk(n.children, d + 1);
|
|
199
|
+
});
|
|
200
|
+
walk(this.baseNodes(), 1);
|
|
201
|
+
return Array.from({ length: depth }, (_, i) => i + 1);
|
|
202
|
+
}, /* @ts-ignore */
|
|
203
|
+
...(ngDevMode ? [{ debugName: "levels" }] : /* istanbul ignore next */ []));
|
|
204
|
+
this.rowClass = (node) => node.key.startsWith('__total') ? 'cb-fr__total' : this.byCode().get(node.key)?.level === 1 ? 'cb-fr__class' : null;
|
|
205
|
+
// Cada cambio de nivel (o del árbol) abre las filas hasta ese nivel.
|
|
206
|
+
afterRenderEffect(() => {
|
|
207
|
+
const level = this.level();
|
|
208
|
+
this.nodes();
|
|
209
|
+
untracked(() => this.tree().expandToLevel(level));
|
|
210
|
+
});
|
|
211
|
+
}
|
|
212
|
+
onActivate(node) {
|
|
213
|
+
const acc = this.byCode().get(node.key);
|
|
214
|
+
if (acc)
|
|
215
|
+
this.accountOpen.emit(acc);
|
|
216
|
+
}
|
|
217
|
+
/** Hoja de Excel del informe: todas las cuentas con sus niveles plegables, títulos y totales. */
|
|
218
|
+
toExcelSheet() {
|
|
219
|
+
const sheet = this.tree().toExcelSheet({ title: [this.title(), ...this.subtitle()].filter(Boolean), sheetName: this.title() || this.t().reportTitle });
|
|
220
|
+
// Las filas de total van en negrita y sin nivel.
|
|
221
|
+
const firstTotal = sheet.rows.length - this.totalNodes().length;
|
|
222
|
+
const rows = sheet.rows.map((r, i) => (i >= firstTotal ? { ...r, bold: true, level: 0, indent: 0 } : r));
|
|
223
|
+
const currency = this.currency() ?? this.config.currency;
|
|
224
|
+
return { ...sheet, rows, totals: undefined, columns: sheet.columns.map((c) => (c.type === 'currency' ? { ...c, negative: this.negativeStyle() ?? c.negative, symbol: currency ? currencySymbol(currency, this.config.numberLocale ?? this.t().intlLocale) : c.symbol } : c)) };
|
|
225
|
+
}
|
|
226
|
+
/** Descarga el informe en Excel. */
|
|
227
|
+
exportExcel(filename) {
|
|
228
|
+
cbDownloadXlsx(filename ?? (this.title() || this.t().reportTitle), this.toExcelSheet());
|
|
229
|
+
}
|
|
230
|
+
/** Imprime el informe (todas las cuentas hasta el nivel abierto) en una ventana de impresión limpia. */
|
|
231
|
+
print() {
|
|
232
|
+
const doc = document;
|
|
233
|
+
const frame = doc.createElement('iframe');
|
|
234
|
+
frame.setAttribute('aria-hidden', 'true');
|
|
235
|
+
frame.style.cssText = 'position:fixed;right:0;bottom:0;width:0;height:0;border:0';
|
|
236
|
+
doc.body.appendChild(frame);
|
|
237
|
+
const w = frame.contentWindow;
|
|
238
|
+
if (!w)
|
|
239
|
+
return;
|
|
240
|
+
const esc = (s) => String(s ?? '').replace(/[&<>]/g, (c) => ({ '&': '&', '<': '<', '>': '>' })[c]);
|
|
241
|
+
const cols = this.columns();
|
|
242
|
+
const locale = this.config.numberLocale ?? this.t().intlLocale;
|
|
243
|
+
const currency = this.currency() ?? this.config.currency ?? null;
|
|
244
|
+
const money = (v, c) => v == null || v === '' ? '' : c.type === 'percent' ? cbFormatAmount(v * 100, locale, { decimals: 1, negative: this.negativeStyle() }) + ' %' : cbFormatAmount(v, locale, { currency, negative: this.negativeStyle() });
|
|
245
|
+
const sheet = this.tree().toExcelSheet();
|
|
246
|
+
const visibleLevel = this.level();
|
|
247
|
+
const firstTotal = sheet.rows.length - this.totalNodes().length;
|
|
248
|
+
const body = sheet.rows
|
|
249
|
+
.map((r, i) => ({ r, isTotal: i >= firstTotal }))
|
|
250
|
+
.filter(({ r }) => (r.level ?? 0) < visibleLevel)
|
|
251
|
+
.map(({ r, isTotal }) => {
|
|
252
|
+
return `<tr class="${r.bold || isTotal ? 'b' : ''}${isTotal ? ' t' : ''}"><td style="padding-left:${0.4 + (r.indent ?? 0) * 1.1}rem">${esc(r.cells[0])}</td>${cols
|
|
253
|
+
.slice(1)
|
|
254
|
+
.map((c, ci) => `<td class="n">${esc(money(r.cells[ci + 1], c))}</td>`)
|
|
255
|
+
.join('')}</tr>`;
|
|
256
|
+
})
|
|
257
|
+
.join('');
|
|
258
|
+
w.document.open();
|
|
259
|
+
w.document.write(`<!doctype html><html lang="${esc(this.t().intlLocale)}"><head><meta charset="utf-8"><title>${esc(this.title() || this.t().reportTitle)}</title><style>` +
|
|
260
|
+
'body{font:12px system-ui,sans-serif;color:#111;margin:24px}h1{font-size:16px;margin:0 0 2px}p{margin:0;color:#555}table{width:100%;border-collapse:collapse;margin-top:14px}' +
|
|
261
|
+
'th,td{padding:4px 6px;border-bottom:1px solid #e5e7eb;text-align:left}th{font-size:11px;text-transform:uppercase;color:#555;border-bottom:1.5px solid #111}.n{text-align:right;font-variant-numeric:tabular-nums;white-space:nowrap}.b td{font-weight:600}.t td{border-top:1.5px solid #111}' +
|
|
262
|
+
`</style></head><body>${this.title() ? `<h1>${esc(this.title())}</h1>` : ''}${this.subtitle()
|
|
263
|
+
.map((s) => `<p>${esc(s)}</p>`)
|
|
264
|
+
.join('')}<table><thead><tr>${cols.map((c, i) => `<th${i ? ' class="n"' : ''}>${esc(c.header)}</th>`).join('')}</tr></thead><tbody>${body}</tbody></table></body></html>`);
|
|
265
|
+
w.document.close();
|
|
266
|
+
w.focus();
|
|
267
|
+
w.print();
|
|
268
|
+
setTimeout(() => frame.remove(), 1000);
|
|
269
|
+
}
|
|
270
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: CbFinancialReport, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
271
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.5", type: CbFinancialReport, isStandalone: true, selector: "cb-financial-report", inputs: { title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, subtitle: { classPropertyName: "subtitle", publicName: "subtitle", isSignal: true, isRequired: false, transformFunction: null }, accounts: { classPropertyName: "accounts", publicName: "accounts", isSignal: true, isRequired: false, transformFunction: null }, balances: { classPropertyName: "balances", publicName: "balances", isSignal: true, isRequired: false, transformFunction: null }, periods: { classPropertyName: "periods", publicName: "periods", isSignal: true, isRequired: false, transformFunction: null }, comparative: { classPropertyName: "comparative", publicName: "comparative", isSignal: true, isRequired: false, transformFunction: null }, classes: { classPropertyName: "classes", publicName: "classes", isSignal: true, isRequired: false, transformFunction: null }, signByNature: { classPropertyName: "signByNature", publicName: "signByNature", isSignal: true, isRequired: false, transformFunction: null }, totals: { classPropertyName: "totals", publicName: "totals", isSignal: true, isRequired: false, transformFunction: null }, level: { classPropertyName: "level", publicName: "level", isSignal: true, isRequired: false, transformFunction: null }, hideZero: { classPropertyName: "hideZero", publicName: "hideZero", isSignal: true, isRequired: false, transformFunction: null }, toolbar: { classPropertyName: "toolbar", publicName: "toolbar", isSignal: true, isRequired: false, transformFunction: null }, currency: { classPropertyName: "currency", publicName: "currency", isSignal: true, isRequired: false, transformFunction: null }, negativeStyle: { classPropertyName: "negativeStyle", publicName: "negativeStyle", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { level: "levelChange", hideZero: "hideZeroChange", accountOpen: "accountOpen" }, host: { classAttribute: "cb-financial-report" }, viewQueries: [{ propertyName: "tree", first: true, predicate: CbTreeTable, descendants: true, isSignal: true }], ngImport: i0, template: `
|
|
272
|
+
@if (title() || subtitle().length) {
|
|
273
|
+
<header class="cb-fr__head">
|
|
274
|
+
@if (title()) {
|
|
275
|
+
<h2 class="cb-fr__title" [id]="uid + '-title'">{{ title() }}</h2>
|
|
276
|
+
}
|
|
277
|
+
@for (line of subtitle(); track $index) {
|
|
278
|
+
<p class="cb-fr__subtitle">{{ line }}</p>
|
|
279
|
+
}
|
|
280
|
+
</header>
|
|
281
|
+
}
|
|
282
|
+
|
|
283
|
+
@if (toolbar()) {
|
|
284
|
+
<div class="cb-fr__toolbar" role="toolbar" [attr.aria-label]="t().reportToolbar">
|
|
285
|
+
<div class="cb-fr__levels" role="group" [attr.aria-label]="t().reportLevel">
|
|
286
|
+
@for (n of levels(); track n) {
|
|
287
|
+
<button type="button" class="cb-fr__level" [attr.aria-pressed]="level() === n" [attr.aria-label]="fmt(t().reportLevelN, n)" (click)="level.set(n)">{{ n }}</button>
|
|
288
|
+
}
|
|
289
|
+
</div>
|
|
290
|
+
<button type="button" class="cb-fr__toggle" [attr.aria-pressed]="hideZero()" (click)="hideZero.set(!hideZero())">
|
|
291
|
+
<cb-icon [name]="hideZero() ? 'eye-off' : 'eye'" [size]="15" aria-hidden="true" />
|
|
292
|
+
{{ t().reportHideZero }}
|
|
293
|
+
</button>
|
|
294
|
+
<span class="cb-fr__spacer"></span>
|
|
295
|
+
<cb-button size="sm" variant="outlined" (click)="exportExcel()">
|
|
296
|
+
<cb-icon name="download" [size]="15" aria-hidden="true" />
|
|
297
|
+
{{ t().reportExcel }}
|
|
298
|
+
</cb-button>
|
|
299
|
+
<cb-button size="sm" variant="text" (click)="print()">
|
|
300
|
+
<cb-icon name="file" [size]="15" aria-hidden="true" />
|
|
301
|
+
{{ t().reportPrint }}
|
|
302
|
+
</cb-button>
|
|
303
|
+
</div>
|
|
304
|
+
}
|
|
305
|
+
|
|
306
|
+
<cb-treetable
|
|
307
|
+
[value]="nodes()"
|
|
308
|
+
[columns]="columns()"
|
|
309
|
+
rollup
|
|
310
|
+
[showFooter]="false"
|
|
311
|
+
[currency]="currency()"
|
|
312
|
+
[negativeStyle]="negativeStyle()"
|
|
313
|
+
[rowClass]="rowClass"
|
|
314
|
+
[activateLeaves]="true"
|
|
315
|
+
[ariaLabel]="title() || t().reportTitle"
|
|
316
|
+
(nodeActivate)="onActivate($event)"
|
|
317
|
+
/>
|
|
318
|
+
`, isInline: true, styles: [":host{display:grid;gap:var(--cb-space-3, .75rem);width:100%;min-width:0;color:var(--cb-color-text);font-family:var(--cb-font-sans)}.cb-fr__head{display:grid;gap:.15rem}.cb-fr__title{margin:0;font-size:var(--cb-text-lg, 1.125rem);font-weight:var(--cb-font-weight-semibold, 600)}.cb-fr__subtitle{margin:0;color:var(--cb-color-text-muted);font-size:var(--cb-text-sm, .875rem)}.cb-fr__toolbar{display:flex;flex-wrap:wrap;align-items:center;gap:.5rem .75rem}.cb-fr__levels{display:inline-flex;padding:2px;border-radius:var(--cb-radius-md);background:var(--cb-color-surface-subtle)}.cb-fr__level,.cb-fr__toggle{border:0;background:transparent;color:inherit;font:inherit;font-size:var(--cb-text-sm, .875rem);cursor:pointer}.cb-fr__level{min-width:2rem;height:1.85rem;border-radius:var(--cb-radius-sm, 4px);color:var(--cb-color-text-muted);font-variant-numeric:tabular-nums}.cb-fr__level[aria-pressed=true]{background:var(--cb-color-bg);box-shadow:var(--cb-shadow-sm, 0 1px 2px rgb(0 0 0 / .08));color:var(--cb-color-text);font-weight:var(--cb-font-weight-semibold, 600)}.cb-fr__toggle{display:inline-flex;align-items:center;gap:.35rem;height:2rem;padding:0 .6rem;border-radius:var(--cb-radius-md);color:var(--cb-color-text-muted)}.cb-fr__toggle[aria-pressed=true]{background:color-mix(in srgb,var(--cb-color-primary-500) 12%,transparent);color:var(--cb-color-text)}:is(.cb-fr__level,.cb-fr__toggle):focus-visible{outline:2px solid var(--cb-color-focus-ring);outline-offset:1px}.cb-fr__spacer{flex:1}:host ::ng-deep .cb-fr__class>td{background:var(--cb-color-surface-subtle)}:host ::ng-deep .cb-fr__total>td{border-top:2px solid var(--cb-color-border-strong);background:var(--cb-color-surface-subtle);font-weight:var(--cb-font-weight-semibold, 600)}\n"], dependencies: [{ kind: "component", type: CbTreeTable, selector: "cb-treetable", inputs: ["value", "columns", "ariaLabel", "rollup", "currency", "showFooter", "rowClass", "activateLeaves", "negativeStyle"], outputs: ["nodeExpand", "nodeCollapse", "nodeActivate"] }, { kind: "component", type: CbButton, selector: "cb-button", inputs: ["severity", "variant", "size", "disabled", "loading", "fullWidth", "type", "ariaLabel", "ariaHaspopup", "ariaExpanded", "ariaControls"] }, { kind: "component", type: CbIcon, selector: "cb-icon", inputs: ["name", "size", "spin", "ariaLabel"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
319
|
+
}
|
|
320
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: CbFinancialReport, decorators: [{
|
|
321
|
+
type: Component,
|
|
322
|
+
args: [{ selector: 'cb-financial-report', changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.Emulated, imports: [CbTreeTable, CbButton, CbIcon], host: { class: 'cb-financial-report' }, template: `
|
|
323
|
+
@if (title() || subtitle().length) {
|
|
324
|
+
<header class="cb-fr__head">
|
|
325
|
+
@if (title()) {
|
|
326
|
+
<h2 class="cb-fr__title" [id]="uid + '-title'">{{ title() }}</h2>
|
|
327
|
+
}
|
|
328
|
+
@for (line of subtitle(); track $index) {
|
|
329
|
+
<p class="cb-fr__subtitle">{{ line }}</p>
|
|
330
|
+
}
|
|
331
|
+
</header>
|
|
332
|
+
}
|
|
333
|
+
|
|
334
|
+
@if (toolbar()) {
|
|
335
|
+
<div class="cb-fr__toolbar" role="toolbar" [attr.aria-label]="t().reportToolbar">
|
|
336
|
+
<div class="cb-fr__levels" role="group" [attr.aria-label]="t().reportLevel">
|
|
337
|
+
@for (n of levels(); track n) {
|
|
338
|
+
<button type="button" class="cb-fr__level" [attr.aria-pressed]="level() === n" [attr.aria-label]="fmt(t().reportLevelN, n)" (click)="level.set(n)">{{ n }}</button>
|
|
339
|
+
}
|
|
340
|
+
</div>
|
|
341
|
+
<button type="button" class="cb-fr__toggle" [attr.aria-pressed]="hideZero()" (click)="hideZero.set(!hideZero())">
|
|
342
|
+
<cb-icon [name]="hideZero() ? 'eye-off' : 'eye'" [size]="15" aria-hidden="true" />
|
|
343
|
+
{{ t().reportHideZero }}
|
|
344
|
+
</button>
|
|
345
|
+
<span class="cb-fr__spacer"></span>
|
|
346
|
+
<cb-button size="sm" variant="outlined" (click)="exportExcel()">
|
|
347
|
+
<cb-icon name="download" [size]="15" aria-hidden="true" />
|
|
348
|
+
{{ t().reportExcel }}
|
|
349
|
+
</cb-button>
|
|
350
|
+
<cb-button size="sm" variant="text" (click)="print()">
|
|
351
|
+
<cb-icon name="file" [size]="15" aria-hidden="true" />
|
|
352
|
+
{{ t().reportPrint }}
|
|
353
|
+
</cb-button>
|
|
354
|
+
</div>
|
|
355
|
+
}
|
|
356
|
+
|
|
357
|
+
<cb-treetable
|
|
358
|
+
[value]="nodes()"
|
|
359
|
+
[columns]="columns()"
|
|
360
|
+
rollup
|
|
361
|
+
[showFooter]="false"
|
|
362
|
+
[currency]="currency()"
|
|
363
|
+
[negativeStyle]="negativeStyle()"
|
|
364
|
+
[rowClass]="rowClass"
|
|
365
|
+
[activateLeaves]="true"
|
|
366
|
+
[ariaLabel]="title() || t().reportTitle"
|
|
367
|
+
(nodeActivate)="onActivate($event)"
|
|
368
|
+
/>
|
|
369
|
+
`, styles: [":host{display:grid;gap:var(--cb-space-3, .75rem);width:100%;min-width:0;color:var(--cb-color-text);font-family:var(--cb-font-sans)}.cb-fr__head{display:grid;gap:.15rem}.cb-fr__title{margin:0;font-size:var(--cb-text-lg, 1.125rem);font-weight:var(--cb-font-weight-semibold, 600)}.cb-fr__subtitle{margin:0;color:var(--cb-color-text-muted);font-size:var(--cb-text-sm, .875rem)}.cb-fr__toolbar{display:flex;flex-wrap:wrap;align-items:center;gap:.5rem .75rem}.cb-fr__levels{display:inline-flex;padding:2px;border-radius:var(--cb-radius-md);background:var(--cb-color-surface-subtle)}.cb-fr__level,.cb-fr__toggle{border:0;background:transparent;color:inherit;font:inherit;font-size:var(--cb-text-sm, .875rem);cursor:pointer}.cb-fr__level{min-width:2rem;height:1.85rem;border-radius:var(--cb-radius-sm, 4px);color:var(--cb-color-text-muted);font-variant-numeric:tabular-nums}.cb-fr__level[aria-pressed=true]{background:var(--cb-color-bg);box-shadow:var(--cb-shadow-sm, 0 1px 2px rgb(0 0 0 / .08));color:var(--cb-color-text);font-weight:var(--cb-font-weight-semibold, 600)}.cb-fr__toggle{display:inline-flex;align-items:center;gap:.35rem;height:2rem;padding:0 .6rem;border-radius:var(--cb-radius-md);color:var(--cb-color-text-muted)}.cb-fr__toggle[aria-pressed=true]{background:color-mix(in srgb,var(--cb-color-primary-500) 12%,transparent);color:var(--cb-color-text)}:is(.cb-fr__level,.cb-fr__toggle):focus-visible{outline:2px solid var(--cb-color-focus-ring);outline-offset:1px}.cb-fr__spacer{flex:1}:host ::ng-deep .cb-fr__class>td{background:var(--cb-color-surface-subtle)}:host ::ng-deep .cb-fr__total>td{border-top:2px solid var(--cb-color-border-strong);background:var(--cb-color-surface-subtle);font-weight:var(--cb-font-weight-semibold, 600)}\n"] }]
|
|
370
|
+
}], ctorParameters: () => [], propDecorators: { tree: [{ type: i0.ViewChild, args: [i0.forwardRef(() => CbTreeTable), { isSignal: true }] }], title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: false }] }], subtitle: [{ type: i0.Input, args: [{ isSignal: true, alias: "subtitle", required: false }] }], accounts: [{ type: i0.Input, args: [{ isSignal: true, alias: "accounts", required: false }] }], balances: [{ type: i0.Input, args: [{ isSignal: true, alias: "balances", required: false }] }], periods: [{ type: i0.Input, args: [{ isSignal: true, alias: "periods", required: false }] }], comparative: [{ type: i0.Input, args: [{ isSignal: true, alias: "comparative", required: false }] }], classes: [{ type: i0.Input, args: [{ isSignal: true, alias: "classes", required: false }] }], signByNature: [{ type: i0.Input, args: [{ isSignal: true, alias: "signByNature", required: false }] }], totals: [{ type: i0.Input, args: [{ isSignal: true, alias: "totals", required: false }] }], level: [{ type: i0.Input, args: [{ isSignal: true, alias: "level", required: false }] }, { type: i0.Output, args: ["levelChange"] }], hideZero: [{ type: i0.Input, args: [{ isSignal: true, alias: "hideZero", required: false }] }, { type: i0.Output, args: ["hideZeroChange"] }], toolbar: [{ type: i0.Input, args: [{ isSignal: true, alias: "toolbar", required: false }] }], currency: [{ type: i0.Input, args: [{ isSignal: true, alias: "currency", required: false }] }], negativeStyle: [{ type: i0.Input, args: [{ isSignal: true, alias: "negativeStyle", required: false }] }], accountOpen: [{ type: i0.Output, args: ["accountOpen"] }] } });
|
|
371
|
+
|
|
372
|
+
/*
|
|
373
|
+
* Public API Surface de @caribeng/ui/financial-report
|
|
374
|
+
*/
|
|
375
|
+
|
|
376
|
+
/**
|
|
377
|
+
* Generated bundle index. Do not edit.
|
|
378
|
+
*/
|
|
379
|
+
|
|
380
|
+
export { CbFinancialReport };
|
|
@@ -3,7 +3,7 @@ import { input, output, ViewEncapsulation, ChangeDetectionStrategy, Component }
|
|
|
3
3
|
import { injectCbTranslation } from '@caribeng/ui';
|
|
4
4
|
|
|
5
5
|
/**
|
|
6
|
-
* Float-menu
|
|
6
|
+
* Float-menu: menú flotante en forma de píldora con opciones
|
|
7
7
|
* seleccionables (segmentado horizontal).
|
|
8
8
|
*
|
|
9
9
|
* @example
|
|
@@ -28,39 +28,39 @@ class CbFloatMenu {
|
|
|
28
28
|
this.select = output();
|
|
29
29
|
}
|
|
30
30
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: CbFloatMenu, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
31
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.5", type: CbFloatMenu, isStandalone: true, selector: "cb-float-menu", inputs: { items: { classPropertyName: "items", publicName: "items", isSignal: true, isRequired: false, transformFunction: null }, activeId: { classPropertyName: "activeId", publicName: "activeId", isSignal: true, isRequired: false, transformFunction: null }, ariaLabel: { classPropertyName: "ariaLabel", publicName: "ariaLabel", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { select: "select" }, host: { classAttribute: "cb-float-menu-host" }, ngImport: i0, template: `
|
|
32
|
-
<nav class="cb-float-menu" [attr.aria-label]="(ariaLabel() ?? t().floatingMenu)">
|
|
33
|
-
@for (item of items(); track item.id) {
|
|
34
|
-
<button
|
|
35
|
-
type="button"
|
|
36
|
-
class="cb-float-menu__item"
|
|
37
|
-
[class.cb-float-menu__item--active]="activeId() === item.id"
|
|
38
|
-
[attr.aria-current]="activeId() === item.id || null"
|
|
39
|
-
(click)="select.emit(item)"
|
|
40
|
-
>
|
|
41
|
-
{{ item.label }}
|
|
42
|
-
</button>
|
|
43
|
-
}
|
|
44
|
-
</nav>
|
|
45
|
-
`, isInline: true, styles: [":host{display:inline-flex}.cb-float-menu{display:inline-flex;align-items:center;gap:var(--cb-space-1, .25rem);padding:var(--cb-space-1, .3rem);font-family:var(--cb-font-sans, inherit);background-color:var(--cb-color-surface-0, #ffffff);border:1px solid var(--cb-color-border, #e2e8f0);border-radius:var(--cb-radius-full, 999px);box-shadow:var(--cb-shadow-md, 0 6px 16px rgba(0, 0, 0, .12))}.cb-float-menu__item{padding:var(--cb-space-2, .4rem) var(--cb-space-4, .9rem);font:inherit;font-size:var(--cb-text-sm, .8125rem);font-weight:var(--cb-font-weight-medium, 500);color:var(--cb-color-text, #0f172a);background:transparent;border:none;border-radius:var(--cb-radius-full, 999px);cursor:pointer;white-space:nowrap;transition:background-color var(--cb-duration-fast, .12s) var(--cb-ease, ease),color var(--cb-duration-fast, .12s) var(--cb-ease, ease)}.cb-float-menu__item:hover:not(.cb-float-menu__item--active){background-color:var(--cb-color-surface-100, #f1f5f9)}.cb-float-menu__item--active{color
|
|
31
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.5", type: CbFloatMenu, isStandalone: true, selector: "cb-float-menu", inputs: { items: { classPropertyName: "items", publicName: "items", isSignal: true, isRequired: false, transformFunction: null }, activeId: { classPropertyName: "activeId", publicName: "activeId", isSignal: true, isRequired: false, transformFunction: null }, ariaLabel: { classPropertyName: "ariaLabel", publicName: "ariaLabel", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { select: "select" }, host: { classAttribute: "cb-float-menu-host" }, ngImport: i0, template: `
|
|
32
|
+
<nav class="cb-float-menu" [attr.aria-label]="(ariaLabel() ?? t().floatingMenu)">
|
|
33
|
+
@for (item of items(); track item.id) {
|
|
34
|
+
<button
|
|
35
|
+
type="button"
|
|
36
|
+
class="cb-float-menu__item"
|
|
37
|
+
[class.cb-float-menu__item--active]="activeId() === item.id"
|
|
38
|
+
[attr.aria-current]="activeId() === item.id || null"
|
|
39
|
+
(click)="select.emit(item)"
|
|
40
|
+
>
|
|
41
|
+
{{ item.label }}
|
|
42
|
+
</button>
|
|
43
|
+
}
|
|
44
|
+
</nav>
|
|
45
|
+
`, isInline: true, styles: [":host{display:inline-flex}.cb-float-menu{display:inline-flex;align-items:center;gap:var(--cb-space-1, .25rem);padding:var(--cb-space-1, .3rem);font-family:var(--cb-font-sans, inherit);background-color:var(--cb-color-surface-0, #ffffff);border:1px solid var(--cb-color-border, #e2e8f0);border-radius:var(--cb-radius-full, 999px);box-shadow:var(--cb-shadow-md, 0 6px 16px rgba(0, 0, 0, .12))}.cb-float-menu__item{padding:var(--cb-space-2, .4rem) var(--cb-space-4, .9rem);font:inherit;font-size:var(--cb-text-sm, .8125rem);font-weight:var(--cb-font-weight-medium, 500);color:var(--cb-color-text, #0f172a);background:transparent;border:none;border-radius:var(--cb-radius-full, 999px);cursor:pointer;white-space:nowrap;transition:background-color var(--cb-duration-fast, .12s) var(--cb-ease, ease),color var(--cb-duration-fast, .12s) var(--cb-ease, ease)}.cb-float-menu__item:hover:not(.cb-float-menu__item--active){background-color:var(--cb-color-surface-100, #f1f5f9)}.cb-float-menu__item--active{color:#fff;background-color:var(--cb-color-primary-700, #047857)}.cb-float-menu__item:focus-visible{outline:2px solid var(--cb-color-focus-ring, var(--cb-color-primary-500, #10b981));outline-offset:2px}:host-context([data-theme=\"dark\"]) .cb-float-menu{background-color:var(--cb-color-surface-800, #1e293b);border-color:var(--cb-color-surface-600, #475569)}:host-context([data-theme=\"dark\"]) .cb-float-menu__item{color:var(--cb-color-surface-0, #f8fafc)}:host-context([data-theme=\"dark\"]) .cb-float-menu__item:hover:not(.cb-float-menu__item--active){background-color:var(--cb-color-surface-700, #334155)}:host-context([data-theme=\"dark\"]) .cb-float-menu__item--active{background-color:var(--cb-color-primary-500, #10b981)}\n"], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
46
46
|
}
|
|
47
47
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: CbFloatMenu, decorators: [{
|
|
48
48
|
type: Component,
|
|
49
|
-
args: [{ selector: 'cb-float-menu', changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.Emulated, host: { class: 'cb-float-menu-host' }, template: `
|
|
50
|
-
<nav class="cb-float-menu" [attr.aria-label]="(ariaLabel() ?? t().floatingMenu)">
|
|
51
|
-
@for (item of items(); track item.id) {
|
|
52
|
-
<button
|
|
53
|
-
type="button"
|
|
54
|
-
class="cb-float-menu__item"
|
|
55
|
-
[class.cb-float-menu__item--active]="activeId() === item.id"
|
|
56
|
-
[attr.aria-current]="activeId() === item.id || null"
|
|
57
|
-
(click)="select.emit(item)"
|
|
58
|
-
>
|
|
59
|
-
{{ item.label }}
|
|
60
|
-
</button>
|
|
61
|
-
}
|
|
62
|
-
</nav>
|
|
63
|
-
`, styles: [":host{display:inline-flex}.cb-float-menu{display:inline-flex;align-items:center;gap:var(--cb-space-1, .25rem);padding:var(--cb-space-1, .3rem);font-family:var(--cb-font-sans, inherit);background-color:var(--cb-color-surface-0, #ffffff);border:1px solid var(--cb-color-border, #e2e8f0);border-radius:var(--cb-radius-full, 999px);box-shadow:var(--cb-shadow-md, 0 6px 16px rgba(0, 0, 0, .12))}.cb-float-menu__item{padding:var(--cb-space-2, .4rem) var(--cb-space-4, .9rem);font:inherit;font-size:var(--cb-text-sm, .8125rem);font-weight:var(--cb-font-weight-medium, 500);color:var(--cb-color-text, #0f172a);background:transparent;border:none;border-radius:var(--cb-radius-full, 999px);cursor:pointer;white-space:nowrap;transition:background-color var(--cb-duration-fast, .12s) var(--cb-ease, ease),color var(--cb-duration-fast, .12s) var(--cb-ease, ease)}.cb-float-menu__item:hover:not(.cb-float-menu__item--active){background-color:var(--cb-color-surface-100, #f1f5f9)}.cb-float-menu__item--active{color
|
|
49
|
+
args: [{ selector: 'cb-float-menu', changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.Emulated, host: { class: 'cb-float-menu-host' }, template: `
|
|
50
|
+
<nav class="cb-float-menu" [attr.aria-label]="(ariaLabel() ?? t().floatingMenu)">
|
|
51
|
+
@for (item of items(); track item.id) {
|
|
52
|
+
<button
|
|
53
|
+
type="button"
|
|
54
|
+
class="cb-float-menu__item"
|
|
55
|
+
[class.cb-float-menu__item--active]="activeId() === item.id"
|
|
56
|
+
[attr.aria-current]="activeId() === item.id || null"
|
|
57
|
+
(click)="select.emit(item)"
|
|
58
|
+
>
|
|
59
|
+
{{ item.label }}
|
|
60
|
+
</button>
|
|
61
|
+
}
|
|
62
|
+
</nav>
|
|
63
|
+
`, styles: [":host{display:inline-flex}.cb-float-menu{display:inline-flex;align-items:center;gap:var(--cb-space-1, .25rem);padding:var(--cb-space-1, .3rem);font-family:var(--cb-font-sans, inherit);background-color:var(--cb-color-surface-0, #ffffff);border:1px solid var(--cb-color-border, #e2e8f0);border-radius:var(--cb-radius-full, 999px);box-shadow:var(--cb-shadow-md, 0 6px 16px rgba(0, 0, 0, .12))}.cb-float-menu__item{padding:var(--cb-space-2, .4rem) var(--cb-space-4, .9rem);font:inherit;font-size:var(--cb-text-sm, .8125rem);font-weight:var(--cb-font-weight-medium, 500);color:var(--cb-color-text, #0f172a);background:transparent;border:none;border-radius:var(--cb-radius-full, 999px);cursor:pointer;white-space:nowrap;transition:background-color var(--cb-duration-fast, .12s) var(--cb-ease, ease),color var(--cb-duration-fast, .12s) var(--cb-ease, ease)}.cb-float-menu__item:hover:not(.cb-float-menu__item--active){background-color:var(--cb-color-surface-100, #f1f5f9)}.cb-float-menu__item--active{color:#fff;background-color:var(--cb-color-primary-700, #047857)}.cb-float-menu__item:focus-visible{outline:2px solid var(--cb-color-focus-ring, var(--cb-color-primary-500, #10b981));outline-offset:2px}:host-context([data-theme=\"dark\"]) .cb-float-menu{background-color:var(--cb-color-surface-800, #1e293b);border-color:var(--cb-color-surface-600, #475569)}:host-context([data-theme=\"dark\"]) .cb-float-menu__item{color:var(--cb-color-surface-0, #f8fafc)}:host-context([data-theme=\"dark\"]) .cb-float-menu__item:hover:not(.cb-float-menu__item--active){background-color:var(--cb-color-surface-700, #334155)}:host-context([data-theme=\"dark\"]) .cb-float-menu__item--active{background-color:var(--cb-color-primary-500, #10b981)}\n"] }]
|
|
64
64
|
}], propDecorators: { items: [{ type: i0.Input, args: [{ isSignal: true, alias: "items", required: false }] }], activeId: [{ type: i0.Input, args: [{ isSignal: true, alias: "activeId", required: false }] }], ariaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaLabel", required: false }] }], select: [{ type: i0.Output, args: ["select"] }] } });
|
|
65
65
|
|
|
66
66
|
/**
|
|
@@ -32,7 +32,7 @@ class CbFloatLabel {
|
|
|
32
32
|
this.filled.set(Boolean(inputEl && inputEl.value.trim().length > 0));
|
|
33
33
|
}
|
|
34
34
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: CbFloatLabel, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
35
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "22.0.5", type: CbFloatLabel, isStandalone: true, selector: "cb-float-label", inputs: { variant: { classPropertyName: "variant", publicName: "variant", isSignal: true, isRequired: false, transformFunction: null } }, host: { listeners: { "focusin": "onFocusIn()", "focusout": "onFocusOut()", "input": "checkFilled()", "change": "checkFilled()" }, properties: { "class.cb-float-label--over": "variant() === \"over\"", "class.cb-float-label--in": "variant() === \"in\"", "class.cb-float-label--on": "variant() === \"on\"", "class.cb-is-active": "focused() || filled()" }, classAttribute: "cb-float-label" }, ngImport: i0, template: `<ng-content />`, isInline: true, styles: [".cb-float-label{position:relative;display:inline-block;width:100%;font-family:var(--cb-font-sans)}.cb-float-label>label{position:absolute;left:var(--cb-space-3);top:50%;transform:translateY(-50%);padding:0 .25rem;background:var(--cb-color-surface);color:var(--cb-color-text-muted);font-size:var(--cb-text-sm);pointer-events:none;transition:top .14s ease,transform .14s ease,font-size .14s ease,color .14s ease}.cb-float-label.cb-is-active>label{top:0;transform:translateY(-50%);font-size:.75rem;color:var(--cb-color-primary-
|
|
35
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "22.0.5", type: CbFloatLabel, isStandalone: true, selector: "cb-float-label", inputs: { variant: { classPropertyName: "variant", publicName: "variant", isSignal: true, isRequired: false, transformFunction: null } }, host: { listeners: { "focusin": "onFocusIn()", "focusout": "onFocusOut()", "input": "checkFilled()", "change": "checkFilled()" }, properties: { "class.cb-float-label--over": "variant() === \"over\"", "class.cb-float-label--in": "variant() === \"in\"", "class.cb-float-label--on": "variant() === \"on\"", "class.cb-is-active": "focused() || filled()" }, classAttribute: "cb-float-label" }, ngImport: i0, template: `<ng-content />`, isInline: true, styles: [".cb-float-label{position:relative;display:inline-block;width:100%;font-family:var(--cb-font-sans)}.cb-float-label>label{position:absolute;left:var(--cb-space-3);top:50%;transform:translateY(-50%);padding:0 .25rem;background:var(--cb-color-surface);color:var(--cb-color-text-muted);font-size:var(--cb-text-sm);pointer-events:none;transition:top .14s ease,transform .14s ease,font-size .14s ease,color .14s ease}.cb-float-label.cb-is-active>label{top:0;transform:translateY(-50%);font-size:.75rem;color:var(--cb-color-primary-text)}.cb-float-label--over.cb-is-active>label{top:-.6rem;background:transparent}\n"], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
|
|
36
36
|
}
|
|
37
37
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: CbFloatLabel, decorators: [{
|
|
38
38
|
type: Component,
|
|
@@ -46,7 +46,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
|
|
|
46
46
|
'(focusout)': 'onFocusOut()',
|
|
47
47
|
'(input)': 'checkFilled()',
|
|
48
48
|
'(change)': 'checkFilled()',
|
|
49
|
-
}, template: `<ng-content />`, styles: [".cb-float-label{position:relative;display:inline-block;width:100%;font-family:var(--cb-font-sans)}.cb-float-label>label{position:absolute;left:var(--cb-space-3);top:50%;transform:translateY(-50%);padding:0 .25rem;background:var(--cb-color-surface);color:var(--cb-color-text-muted);font-size:var(--cb-text-sm);pointer-events:none;transition:top .14s ease,transform .14s ease,font-size .14s ease,color .14s ease}.cb-float-label.cb-is-active>label{top:0;transform:translateY(-50%);font-size:.75rem;color:var(--cb-color-primary-
|
|
49
|
+
}, template: `<ng-content />`, styles: [".cb-float-label{position:relative;display:inline-block;width:100%;font-family:var(--cb-font-sans)}.cb-float-label>label{position:absolute;left:var(--cb-space-3);top:50%;transform:translateY(-50%);padding:0 .25rem;background:var(--cb-color-surface);color:var(--cb-color-text-muted);font-size:var(--cb-text-sm);pointer-events:none;transition:top .14s ease,transform .14s ease,font-size .14s ease,color .14s ease}.cb-float-label.cb-is-active>label{top:0;transform:translateY(-50%);font-size:.75rem;color:var(--cb-color-primary-text)}.cb-float-label--over.cb-is-active>label{top:-.6rem;background:transparent}\n"] }]
|
|
50
50
|
}], ctorParameters: () => [], propDecorators: { variant: [{ type: i0.Input, args: [{ isSignal: true, alias: "variant", required: false }] }] } });
|
|
51
51
|
|
|
52
52
|
/**
|