myio-js-library 0.1.557 → 0.1.558
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/dist/index.cjs +115 -5
- package/dist/index.d.cts +13 -1
- package/dist/index.d.ts +13 -1
- package/dist/index.js +115 -5
- package/dist/myio-js-library.umd.js +115 -5
- package/dist/myio-js-library.umd.min.js +1 -1
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -908,7 +908,7 @@ module.exports = __toCommonJS(src_exports);
|
|
|
908
908
|
// package.json
|
|
909
909
|
var package_default = {
|
|
910
910
|
name: "myio-js-library",
|
|
911
|
-
version: "0.1.
|
|
911
|
+
version: "0.1.558",
|
|
912
912
|
description: "A clean, standalone JS SDK for MYIO projects",
|
|
913
913
|
license: "MIT",
|
|
914
914
|
repository: "github:gh-myio/myio-js-library",
|
|
@@ -12855,6 +12855,26 @@ var CSS_STRING = `
|
|
|
12855
12855
|
margin-left: 4px;
|
|
12856
12856
|
}
|
|
12857
12857
|
|
|
12858
|
+
/* Consumo ainda carregando (spinner no lugar do valor) */
|
|
12859
|
+
.myio-ho-card__value.is-loading .num {
|
|
12860
|
+
display: inline-flex;
|
|
12861
|
+
align-items: center;
|
|
12862
|
+
gap: 8px;
|
|
12863
|
+
font-size: 14px;
|
|
12864
|
+
font-weight: 600;
|
|
12865
|
+
color: var(--myio-muted, #9ca3af);
|
|
12866
|
+
}
|
|
12867
|
+
.myio-ho-card__value-spinner {
|
|
12868
|
+
width: 14px;
|
|
12869
|
+
height: 14px;
|
|
12870
|
+
border: 2px solid rgba(124, 58, 237, 0.2);
|
|
12871
|
+
border-top-color: var(--myio-brand-700, #7c3aed);
|
|
12872
|
+
border-radius: 50%;
|
|
12873
|
+
animation: myio-consumption-spin 0.8s linear infinite;
|
|
12874
|
+
flex-shrink: 0;
|
|
12875
|
+
}
|
|
12876
|
+
@keyframes myio-consumption-spin { to { transform: rotate(360deg); } }
|
|
12877
|
+
|
|
12858
12878
|
/* Efficiency bar */
|
|
12859
12879
|
.myio-ho-card__eff {
|
|
12860
12880
|
display: flex;
|
|
@@ -16527,7 +16547,20 @@ function paint(root, state6) {
|
|
|
16527
16547
|
const primaryValue = formatValueByDomain(entityObject.val, entityObject.domain);
|
|
16528
16548
|
const numSpan = root.querySelector(".myio-ho-card__value .num");
|
|
16529
16549
|
const unitSpan = root.querySelector(".myio-ho-card__value .unit");
|
|
16530
|
-
|
|
16550
|
+
const valueBox = root.querySelector(".myio-ho-card__value");
|
|
16551
|
+
const dataLoading = !!entityObject.dataLoading && entityObject.domain !== "temperature";
|
|
16552
|
+
if (valueBox) {
|
|
16553
|
+
valueBox.classList.toggle("is-loading", dataLoading);
|
|
16554
|
+
if (dataLoading) valueBox.setAttribute("aria-busy", "true");
|
|
16555
|
+
else valueBox.removeAttribute("aria-busy");
|
|
16556
|
+
}
|
|
16557
|
+
if (dataLoading) {
|
|
16558
|
+
numSpan.innerHTML = '<span class="myio-ho-card__value-spinner" aria-hidden="true"></span>Carregando\u2026';
|
|
16559
|
+
numSpan.title = "Carregando consumo do per\xEDodo";
|
|
16560
|
+
} else {
|
|
16561
|
+
numSpan.textContent = primaryValue;
|
|
16562
|
+
numSpan.removeAttribute("title");
|
|
16563
|
+
}
|
|
16531
16564
|
const barContainer = root.querySelector(".bar");
|
|
16532
16565
|
const effContainer = root.querySelector(".myio-ho-card__eff");
|
|
16533
16566
|
if (state6.enableSelection) {
|
|
@@ -71709,6 +71742,25 @@ var HeaderView = class {
|
|
|
71709
71742
|
transition: color 0.2s ease;
|
|
71710
71743
|
}
|
|
71711
71744
|
|
|
71745
|
+
/* Consumo ainda carregando */
|
|
71746
|
+
.${HEADER_CSS_PREFIX}-kpi-loading {
|
|
71747
|
+
display: inline-flex;
|
|
71748
|
+
align-items: center;
|
|
71749
|
+
gap: 10px;
|
|
71750
|
+
font-size: 1rem;
|
|
71751
|
+
font-weight: 600;
|
|
71752
|
+
opacity: 0.85;
|
|
71753
|
+
}
|
|
71754
|
+
.${HEADER_CSS_PREFIX}-kpi-spinner {
|
|
71755
|
+
width: 18px;
|
|
71756
|
+
height: 18px;
|
|
71757
|
+
border: 2.5px solid rgba(255, 255, 255, 0.3);
|
|
71758
|
+
border-top-color: currentColor;
|
|
71759
|
+
border-radius: 50%;
|
|
71760
|
+
animation: myio-consumption-spin 0.8s linear infinite;
|
|
71761
|
+
}
|
|
71762
|
+
@keyframes myio-consumption-spin { to { transform: rotate(360deg); } }
|
|
71763
|
+
|
|
71712
71764
|
.${HEADER_CSS_PREFIX}-card__subrow {
|
|
71713
71765
|
display: flex;
|
|
71714
71766
|
align-items: center;
|
|
@@ -72147,7 +72199,28 @@ var HeaderView = class {
|
|
|
72147
72199
|
/**
|
|
72148
72200
|
* Update energy card
|
|
72149
72201
|
*/
|
|
72202
|
+
/** Spinner nos KPIs de consumo (energia e água) enquanto o período carrega */
|
|
72203
|
+
setConsumptionLoading(loading) {
|
|
72204
|
+
if (!loading) {
|
|
72205
|
+
[this.energyKpiEl, this.waterKpiEl].forEach((el2) => {
|
|
72206
|
+
if (el2?.querySelector(`.${HEADER_CSS_PREFIX}-kpi-loading`)) el2.textContent = "-";
|
|
72207
|
+
});
|
|
72208
|
+
return;
|
|
72209
|
+
}
|
|
72210
|
+
const html = `<span class="${HEADER_CSS_PREFIX}-kpi-loading" aria-busy="true"><span class="${HEADER_CSS_PREFIX}-kpi-spinner" aria-hidden="true"></span>Carregando\u2026</span>`;
|
|
72211
|
+
if (this.energyKpiEl) this.energyKpiEl.innerHTML = html;
|
|
72212
|
+
if (this.waterKpiEl) this.waterKpiEl.innerHTML = html;
|
|
72213
|
+
if (this.energyTrendEl) this.energyTrendEl.textContent = "";
|
|
72214
|
+
if (this.waterTrendEl) this.waterTrendEl.textContent = "";
|
|
72215
|
+
}
|
|
72150
72216
|
updateEnergyCard(data) {
|
|
72217
|
+
if (data.loading) {
|
|
72218
|
+
if (this.energyKpiEl) {
|
|
72219
|
+
this.energyKpiEl.innerHTML = `<span class="${HEADER_CSS_PREFIX}-kpi-loading" aria-busy="true"><span class="${HEADER_CSS_PREFIX}-kpi-spinner" aria-hidden="true"></span>Carregando\u2026</span>`;
|
|
72220
|
+
}
|
|
72221
|
+
if (this.energyTrendEl) this.energyTrendEl.textContent = "";
|
|
72222
|
+
return;
|
|
72223
|
+
}
|
|
72151
72224
|
if (this.energyKpiEl) {
|
|
72152
72225
|
if (data.isFiltered && data.unfilteredTotal > 0) {
|
|
72153
72226
|
const filteredFormatted = this.formatEnergy(data.customerTotal);
|
|
@@ -72196,6 +72269,13 @@ var HeaderView = class {
|
|
|
72196
72269
|
* Update water card
|
|
72197
72270
|
*/
|
|
72198
72271
|
updateWaterCard(data) {
|
|
72272
|
+
if (data.loading) {
|
|
72273
|
+
if (this.waterKpiEl) {
|
|
72274
|
+
this.waterKpiEl.innerHTML = `<span class="${HEADER_CSS_PREFIX}-kpi-loading" aria-busy="true"><span class="${HEADER_CSS_PREFIX}-kpi-spinner" aria-hidden="true"></span>Carregando\u2026</span>`;
|
|
72275
|
+
}
|
|
72276
|
+
if (this.waterTrendEl) this.waterTrendEl.textContent = "";
|
|
72277
|
+
return;
|
|
72278
|
+
}
|
|
72199
72279
|
if (this.waterKpiEl) {
|
|
72200
72280
|
if (data.isFiltered && data.unfilteredTotal > 0) {
|
|
72201
72281
|
const filteredFormatted = this.formatWater(data.filteredTotal);
|
|
@@ -73181,6 +73261,9 @@ function createHeaderComponent(params) {
|
|
|
73181
73261
|
tooltipData.temperature = data;
|
|
73182
73262
|
view.updateTemperatureCard(data);
|
|
73183
73263
|
}
|
|
73264
|
+
function setConsumptionLoading(loading) {
|
|
73265
|
+
view.setConsumptionLoading(loading);
|
|
73266
|
+
}
|
|
73184
73267
|
function updateWaterKPI(data) {
|
|
73185
73268
|
tooltipData.water = data;
|
|
73186
73269
|
view.updateWaterCard(data);
|
|
@@ -73236,6 +73319,7 @@ function createHeaderComponent(params) {
|
|
|
73236
73319
|
updateEnergyKPI,
|
|
73237
73320
|
updateTemperatureKPI,
|
|
73238
73321
|
updateWaterKPI,
|
|
73322
|
+
setConsumptionLoading,
|
|
73239
73323
|
updateTooltipData,
|
|
73240
73324
|
// Shopping/Filter
|
|
73241
73325
|
updateShoppings,
|
|
@@ -123722,6 +123806,20 @@ var HEADER_DEVICES_GRID_STYLES = `
|
|
|
123722
123806
|
body.light-mode .telemetry-grid-wrap.maximized .telemetry-grid-header {
|
|
123723
123807
|
background: #f8fafc;
|
|
123724
123808
|
}
|
|
123809
|
+
|
|
123810
|
+
/* Consumo ainda carregando */
|
|
123811
|
+
.hdg-value-spinner {
|
|
123812
|
+
display: inline-block;
|
|
123813
|
+
width: 13px;
|
|
123814
|
+
height: 13px;
|
|
123815
|
+
margin-right: 6px;
|
|
123816
|
+
vertical-align: -2px;
|
|
123817
|
+
border: 2px solid rgba(124, 58, 237, 0.2);
|
|
123818
|
+
border-top-color: var(--myio-brand-700, #7c3aed);
|
|
123819
|
+
border-radius: 50%;
|
|
123820
|
+
animation: myio-consumption-spin 0.8s linear infinite;
|
|
123821
|
+
}
|
|
123822
|
+
@keyframes myio-consumption-spin { to { transform: rotate(360deg); } }
|
|
123725
123823
|
`;
|
|
123726
123824
|
function injectHeaderDevicesGridStyles() {
|
|
123727
123825
|
const styleId = "hdg-styles";
|
|
@@ -123739,14 +123837,15 @@ var DOMAIN_CONFIG7 = {
|
|
|
123739
123837
|
consumptionLabel: "Consumo Total",
|
|
123740
123838
|
zeroLabel: "Sem Consumo",
|
|
123741
123839
|
unit: "kWh",
|
|
123742
|
-
|
|
123840
|
+
// 3 casas: mesmo padrão do dashboard de shopping (RFC-0108, measurementSettings default)
|
|
123841
|
+
formatValue: (value) => formatEnergy(value, void 0, 3)
|
|
123743
123842
|
},
|
|
123744
123843
|
water: {
|
|
123745
123844
|
totalLabel: "Total Hidr\xF4metros",
|
|
123746
123845
|
consumptionLabel: "Consumo Total",
|
|
123747
123846
|
zeroLabel: "Sem Consumo",
|
|
123748
123847
|
unit: "m\xB3",
|
|
123749
|
-
formatValue: (value) =>
|
|
123848
|
+
formatValue: (value) => `${(Number(value) || 0).toLocaleString("pt-BR", { minimumFractionDigits: 3, maximumFractionDigits: 3 })} m\xB3`
|
|
123750
123849
|
},
|
|
123751
123850
|
temperature: {
|
|
123752
123851
|
totalLabel: "Total Sensores",
|
|
@@ -123914,6 +124013,16 @@ var HeaderDevicesGridView = class {
|
|
|
123914
124013
|
const percentage = total > 0 ? (online / total * 100).toFixed(1) : "0.0";
|
|
123915
124014
|
connectivityEl.textContent = `${online}/${total} (${percentage}%)`;
|
|
123916
124015
|
totalEl.textContent = total.toString();
|
|
124016
|
+
if (stats.loading) {
|
|
124017
|
+
const spin = '<span class="hdg-value-spinner" aria-hidden="true"></span>';
|
|
124018
|
+
consumptionEl.innerHTML = `${spin}Carregando\u2026`;
|
|
124019
|
+
zeroEl.innerHTML = spin;
|
|
124020
|
+
consumptionEl.setAttribute("aria-busy", "true");
|
|
124021
|
+
zeroEl.setAttribute("aria-busy", "true");
|
|
124022
|
+
return;
|
|
124023
|
+
}
|
|
124024
|
+
consumptionEl.removeAttribute("aria-busy");
|
|
124025
|
+
zeroEl.removeAttribute("aria-busy");
|
|
123917
124026
|
consumptionEl.textContent = this.domainConfig.formatValue(consumption);
|
|
123918
124027
|
zeroEl.textContent = zeroCount.toString();
|
|
123919
124028
|
}
|
|
@@ -124020,7 +124129,8 @@ var HeaderDevicesGridController = class {
|
|
|
124020
124129
|
online,
|
|
124021
124130
|
total: devices.length,
|
|
124022
124131
|
consumption: displayValue,
|
|
124023
|
-
zeroCount
|
|
124132
|
+
zeroCount,
|
|
124133
|
+
loading: this.domain !== "temperature" && devices.some((d) => d.dataLoading)
|
|
124024
124134
|
});
|
|
124025
124135
|
}
|
|
124026
124136
|
setThemeMode(mode) {
|
package/dist/index.d.cts
CHANGED
|
@@ -7688,6 +7688,8 @@ interface ShoppingEnergy {
|
|
|
7688
7688
|
* Energy KPI data
|
|
7689
7689
|
*/
|
|
7690
7690
|
interface EnergyKPI {
|
|
7691
|
+
/** Consumo do período ainda carregando → spinner no KPI */
|
|
7692
|
+
loading?: boolean;
|
|
7691
7693
|
/** Total consumption for selected customers */
|
|
7692
7694
|
customerTotal: number;
|
|
7693
7695
|
/** Total consumption before filtering */
|
|
@@ -7758,6 +7760,8 @@ interface ShoppingWater {
|
|
|
7758
7760
|
* Water KPI data
|
|
7759
7761
|
*/
|
|
7760
7762
|
interface WaterKPI {
|
|
7763
|
+
/** Consumo do período ainda carregando → spinner no KPI */
|
|
7764
|
+
loading?: boolean;
|
|
7761
7765
|
/** Total consumption for selected customers */
|
|
7762
7766
|
filteredTotal: number;
|
|
7763
7767
|
/** Total consumption before filtering */
|
|
@@ -7939,6 +7943,8 @@ interface HeaderComponentInstance {
|
|
|
7939
7943
|
updateTemperatureKPI: (data: TemperatureKPI) => void;
|
|
7940
7944
|
/** Update water KPI */
|
|
7941
7945
|
updateWaterKPI: (data: WaterKPI) => void;
|
|
7946
|
+
/** Spinner nos KPIs de consumo (energia/água) enquanto o período carrega */
|
|
7947
|
+
setConsumptionLoading: (loading: boolean) => void;
|
|
7942
7948
|
/** Update tooltip data for a specific card */
|
|
7943
7949
|
updateTooltipData: (cardType: CardType, data: unknown) => void;
|
|
7944
7950
|
/** Update available shoppings */
|
|
@@ -8227,6 +8233,8 @@ declare class HeaderView {
|
|
|
8227
8233
|
/**
|
|
8228
8234
|
* Update energy card
|
|
8229
8235
|
*/
|
|
8236
|
+
/** Spinner nos KPIs de consumo (energia e água) enquanto o período carrega */
|
|
8237
|
+
setConsumptionLoading(loading: boolean): void;
|
|
8230
8238
|
updateEnergyCard(data: EnergyKPI): void;
|
|
8231
8239
|
/**
|
|
8232
8240
|
* Update temperature card
|
|
@@ -17475,6 +17483,8 @@ interface HeaderStats {
|
|
|
17475
17483
|
total: number;
|
|
17476
17484
|
consumption: number;
|
|
17477
17485
|
zeroCount: number;
|
|
17486
|
+
/** Consumo ainda carregando → spinner em Consumo Total / Sem Consumo */
|
|
17487
|
+
loading?: boolean;
|
|
17478
17488
|
}
|
|
17479
17489
|
interface HeaderLabels {
|
|
17480
17490
|
connectivity?: string;
|
|
@@ -17509,6 +17519,8 @@ interface HeaderDevicesGridInstance {
|
|
|
17509
17519
|
destroy: () => void;
|
|
17510
17520
|
}
|
|
17511
17521
|
interface HeaderDevice {
|
|
17522
|
+
/** Consumo do período ainda não chegou (HO: /summary em andamento) */
|
|
17523
|
+
dataLoading?: boolean;
|
|
17512
17524
|
entityId?: string;
|
|
17513
17525
|
ingestionId?: string;
|
|
17514
17526
|
deviceStatus?: string;
|
|
@@ -17586,7 +17598,7 @@ declare class HeaderDevicesGridController implements HeaderDevicesGridInstance {
|
|
|
17586
17598
|
* CSS-in-JS styles for the stats header
|
|
17587
17599
|
* FIEL ao showcase/telemetry-grid/index.html
|
|
17588
17600
|
*/
|
|
17589
|
-
declare const HEADER_DEVICES_GRID_STYLES = "\n /* RFC-0125: HeaderDevicesGrid Component - FIEL ao TELEMETRY widget */\n .hdg-header {\n display: flex !important;\n flex-direction: row !important;\n align-items: stretch;\n gap: 0;\n padding: 0;\n background: var(--card-bg, #1e293b);\n border-radius: 8px;\n margin-bottom: 12px;\n overflow: hidden;\n }\n\n .hdg-header .stat-item {\n display: flex !important;\n flex-direction: column !important;\n gap: 2px;\n flex: 1;\n min-width: 0;\n padding: 12px 16px;\n border-right: 1px solid var(--card-bd, #334155);\n }\n\n .hdg-header .stat-item:last-of-type {\n border-right: none;\n }\n\n .hdg-header .stat-label {\n font-size: 11px;\n color: var(--ink-2, #94a3b8);\n text-transform: uppercase;\n letter-spacing: 0.5px;\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n }\n\n .hdg-header .stat-value {\n font-size: 18px;\n font-weight: 700;\n color: var(--ink-1, #f1f5f9);\n }\n\n /* Highlight com background de destaque e barras em ambos os lados */\n .hdg-header .stat-item.highlight {\n background: linear-gradient(135deg, rgba(245, 158, 11, 0.15) 0%, rgba(245, 158, 11, 0.25) 100%);\n border-left: 3px solid var(--telemetry-primary, #f59e0b);\n border-right: 3px solid var(--telemetry-primary, #f59e0b);\n position: relative;\n }\n\n .hdg-header .stat-item.highlight .stat-value {\n color: var(--telemetry-primary, #f59e0b);\n font-size: 20px;\n }\n\n /* Ajuste para o item apos o highlight nao ter borda dupla */\n .hdg-header .stat-item.highlight + .stat-item {\n border-left: none;\n }\n\n .hdg-header .filter-actions {\n display: flex;\n align-items: center;\n gap: 8px;\n padding: 8px 12px;\n border-left: 1px solid var(--card-bd, #334155);\n }\n\n .hdg-header .search-wrap {\n display: none;\n overflow: hidden;\n transition: all 0.2s ease;\n }\n\n .hdg-header .search-wrap.active {\n display: block;\n }\n\n .hdg-header .search-wrap input {\n padding: 6px 12px;\n border: 1px solid var(--card-bd, #334155);\n border-radius: 6px;\n background: transparent;\n color: var(--ink-1, #f1f5f9);\n font-size: 13px;\n width: 180px;\n }\n\n .hdg-header .search-wrap input:focus {\n outline: none;\n border-color: var(--telemetry-primary, #f59e0b);\n }\n\n .hdg-header .icon-btn {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 36px;\n height: 36px;\n border: 1px solid var(--card-bd, #334155);\n border-radius: 6px;\n background: transparent;\n color: var(--ink-2, #94a3b8);\n cursor: pointer;\n transition: all 0.15s ease;\n }\n\n .hdg-header .icon-btn:hover {\n background: var(--telemetry-primary, #f59e0b);\n border-color: var(--telemetry-primary, #f59e0b);\n color: white;\n }\n\n .hdg-header .icon-btn svg {\n width: 18px;\n height: 18px;\n fill: currentColor;\n display: block;\n }\n\n .hdg-header .icon-btn .icon-minimize {\n display: none;\n }\n\n .hdg-header .icon-btn .icon-maximize {\n display: block;\n }\n\n /* Light mode */\n .hdg-header--light {\n background: #ffffff;\n border: 1px solid #e2e8f0;\n }\n\n .hdg-header--light .stat-item {\n border-color: #e2e8f0;\n }\n\n .hdg-header--light .stat-item.highlight {\n background: linear-gradient(135deg, rgba(245, 158, 11, 0.1) 0%, rgba(245, 158, 11, 0.2) 100%);\n border-left-color: var(--telemetry-primary, #f59e0b);\n border-right-color: var(--telemetry-primary, #f59e0b);\n }\n\n .hdg-header--light .stat-label {\n color: #64748b;\n }\n\n .hdg-header--light .stat-value {\n color: #1e293b;\n }\n\n .hdg-header--light .filter-actions {\n border-color: #e2e8f0;\n }\n\n .hdg-header--light .search-wrap input {\n background: #f1f5f9;\n border-color: #cbd5e1;\n color: #1e293b;\n }\n\n .hdg-header--light .icon-btn {\n border-color: #cbd5e1;\n color: #64748b;\n }\n\n /* Maximized state for parent container */\n .telemetry-grid-wrap.maximized {\n position: fixed !important;\n inset: 0 !important;\n z-index: 99999 !important;\n width: 100vw !important;\n height: 100vh !important;\n background: var(--card-bg, #0f172a) !important;\n border-radius: 0 !important;\n overflow: auto !important;\n padding: 16px !important;\n }\n\n .telemetry-grid-wrap.maximized .telemetry-grid-header {\n position: sticky;\n top: 0;\n z-index: 10;\n background: var(--card-bg, #0f172a);\n padding-bottom: 12px;\n }\n\n .telemetry-grid-wrap.maximized .telemetry-cards-grid {\n max-height: none !important;\n overflow: visible !important;\n }\n\n .telemetry-grid-wrap.maximized .hdg-header .icon-btn .icon-maximize {\n display: none;\n }\n\n .telemetry-grid-wrap.maximized .hdg-header .icon-btn .icon-minimize {\n display: block;\n }\n\n /* Light mode maximized */\n body.light-mode .telemetry-grid-wrap.maximized {\n background: #f8fafc !important;\n }\n\n body.light-mode .telemetry-grid-wrap.maximized .telemetry-grid-header {\n background: #f8fafc;\n }\n";
|
|
17601
|
+
declare const HEADER_DEVICES_GRID_STYLES = "\n /* RFC-0125: HeaderDevicesGrid Component - FIEL ao TELEMETRY widget */\n .hdg-header {\n display: flex !important;\n flex-direction: row !important;\n align-items: stretch;\n gap: 0;\n padding: 0;\n background: var(--card-bg, #1e293b);\n border-radius: 8px;\n margin-bottom: 12px;\n overflow: hidden;\n }\n\n .hdg-header .stat-item {\n display: flex !important;\n flex-direction: column !important;\n gap: 2px;\n flex: 1;\n min-width: 0;\n padding: 12px 16px;\n border-right: 1px solid var(--card-bd, #334155);\n }\n\n .hdg-header .stat-item:last-of-type {\n border-right: none;\n }\n\n .hdg-header .stat-label {\n font-size: 11px;\n color: var(--ink-2, #94a3b8);\n text-transform: uppercase;\n letter-spacing: 0.5px;\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n }\n\n .hdg-header .stat-value {\n font-size: 18px;\n font-weight: 700;\n color: var(--ink-1, #f1f5f9);\n }\n\n /* Highlight com background de destaque e barras em ambos os lados */\n .hdg-header .stat-item.highlight {\n background: linear-gradient(135deg, rgba(245, 158, 11, 0.15) 0%, rgba(245, 158, 11, 0.25) 100%);\n border-left: 3px solid var(--telemetry-primary, #f59e0b);\n border-right: 3px solid var(--telemetry-primary, #f59e0b);\n position: relative;\n }\n\n .hdg-header .stat-item.highlight .stat-value {\n color: var(--telemetry-primary, #f59e0b);\n font-size: 20px;\n }\n\n /* Ajuste para o item apos o highlight nao ter borda dupla */\n .hdg-header .stat-item.highlight + .stat-item {\n border-left: none;\n }\n\n .hdg-header .filter-actions {\n display: flex;\n align-items: center;\n gap: 8px;\n padding: 8px 12px;\n border-left: 1px solid var(--card-bd, #334155);\n }\n\n .hdg-header .search-wrap {\n display: none;\n overflow: hidden;\n transition: all 0.2s ease;\n }\n\n .hdg-header .search-wrap.active {\n display: block;\n }\n\n .hdg-header .search-wrap input {\n padding: 6px 12px;\n border: 1px solid var(--card-bd, #334155);\n border-radius: 6px;\n background: transparent;\n color: var(--ink-1, #f1f5f9);\n font-size: 13px;\n width: 180px;\n }\n\n .hdg-header .search-wrap input:focus {\n outline: none;\n border-color: var(--telemetry-primary, #f59e0b);\n }\n\n .hdg-header .icon-btn {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 36px;\n height: 36px;\n border: 1px solid var(--card-bd, #334155);\n border-radius: 6px;\n background: transparent;\n color: var(--ink-2, #94a3b8);\n cursor: pointer;\n transition: all 0.15s ease;\n }\n\n .hdg-header .icon-btn:hover {\n background: var(--telemetry-primary, #f59e0b);\n border-color: var(--telemetry-primary, #f59e0b);\n color: white;\n }\n\n .hdg-header .icon-btn svg {\n width: 18px;\n height: 18px;\n fill: currentColor;\n display: block;\n }\n\n .hdg-header .icon-btn .icon-minimize {\n display: none;\n }\n\n .hdg-header .icon-btn .icon-maximize {\n display: block;\n }\n\n /* Light mode */\n .hdg-header--light {\n background: #ffffff;\n border: 1px solid #e2e8f0;\n }\n\n .hdg-header--light .stat-item {\n border-color: #e2e8f0;\n }\n\n .hdg-header--light .stat-item.highlight {\n background: linear-gradient(135deg, rgba(245, 158, 11, 0.1) 0%, rgba(245, 158, 11, 0.2) 100%);\n border-left-color: var(--telemetry-primary, #f59e0b);\n border-right-color: var(--telemetry-primary, #f59e0b);\n }\n\n .hdg-header--light .stat-label {\n color: #64748b;\n }\n\n .hdg-header--light .stat-value {\n color: #1e293b;\n }\n\n .hdg-header--light .filter-actions {\n border-color: #e2e8f0;\n }\n\n .hdg-header--light .search-wrap input {\n background: #f1f5f9;\n border-color: #cbd5e1;\n color: #1e293b;\n }\n\n .hdg-header--light .icon-btn {\n border-color: #cbd5e1;\n color: #64748b;\n }\n\n /* Maximized state for parent container */\n .telemetry-grid-wrap.maximized {\n position: fixed !important;\n inset: 0 !important;\n z-index: 99999 !important;\n width: 100vw !important;\n height: 100vh !important;\n background: var(--card-bg, #0f172a) !important;\n border-radius: 0 !important;\n overflow: auto !important;\n padding: 16px !important;\n }\n\n .telemetry-grid-wrap.maximized .telemetry-grid-header {\n position: sticky;\n top: 0;\n z-index: 10;\n background: var(--card-bg, #0f172a);\n padding-bottom: 12px;\n }\n\n .telemetry-grid-wrap.maximized .telemetry-cards-grid {\n max-height: none !important;\n overflow: visible !important;\n }\n\n .telemetry-grid-wrap.maximized .hdg-header .icon-btn .icon-maximize {\n display: none;\n }\n\n .telemetry-grid-wrap.maximized .hdg-header .icon-btn .icon-minimize {\n display: block;\n }\n\n /* Light mode maximized */\n body.light-mode .telemetry-grid-wrap.maximized {\n background: #f8fafc !important;\n }\n\n body.light-mode .telemetry-grid-wrap.maximized .telemetry-grid-header {\n background: #f8fafc;\n }\n\n/* Consumo ainda carregando */\n.hdg-value-spinner {\n display: inline-block;\n width: 13px;\n height: 13px;\n margin-right: 6px;\n vertical-align: -2px;\n border: 2px solid rgba(124, 58, 237, 0.2);\n border-top-color: var(--myio-brand-700, #7c3aed);\n border-radius: 50%;\n animation: myio-consumption-spin 0.8s linear infinite;\n}\n@keyframes myio-consumption-spin { to { transform: rotate(360deg); } }\n";
|
|
17590
17602
|
declare function injectHeaderDevicesGridStyles(): void;
|
|
17591
17603
|
|
|
17592
17604
|
/**
|
package/dist/index.d.ts
CHANGED
|
@@ -7688,6 +7688,8 @@ interface ShoppingEnergy {
|
|
|
7688
7688
|
* Energy KPI data
|
|
7689
7689
|
*/
|
|
7690
7690
|
interface EnergyKPI {
|
|
7691
|
+
/** Consumo do período ainda carregando → spinner no KPI */
|
|
7692
|
+
loading?: boolean;
|
|
7691
7693
|
/** Total consumption for selected customers */
|
|
7692
7694
|
customerTotal: number;
|
|
7693
7695
|
/** Total consumption before filtering */
|
|
@@ -7758,6 +7760,8 @@ interface ShoppingWater {
|
|
|
7758
7760
|
* Water KPI data
|
|
7759
7761
|
*/
|
|
7760
7762
|
interface WaterKPI {
|
|
7763
|
+
/** Consumo do período ainda carregando → spinner no KPI */
|
|
7764
|
+
loading?: boolean;
|
|
7761
7765
|
/** Total consumption for selected customers */
|
|
7762
7766
|
filteredTotal: number;
|
|
7763
7767
|
/** Total consumption before filtering */
|
|
@@ -7939,6 +7943,8 @@ interface HeaderComponentInstance {
|
|
|
7939
7943
|
updateTemperatureKPI: (data: TemperatureKPI) => void;
|
|
7940
7944
|
/** Update water KPI */
|
|
7941
7945
|
updateWaterKPI: (data: WaterKPI) => void;
|
|
7946
|
+
/** Spinner nos KPIs de consumo (energia/água) enquanto o período carrega */
|
|
7947
|
+
setConsumptionLoading: (loading: boolean) => void;
|
|
7942
7948
|
/** Update tooltip data for a specific card */
|
|
7943
7949
|
updateTooltipData: (cardType: CardType, data: unknown) => void;
|
|
7944
7950
|
/** Update available shoppings */
|
|
@@ -8227,6 +8233,8 @@ declare class HeaderView {
|
|
|
8227
8233
|
/**
|
|
8228
8234
|
* Update energy card
|
|
8229
8235
|
*/
|
|
8236
|
+
/** Spinner nos KPIs de consumo (energia e água) enquanto o período carrega */
|
|
8237
|
+
setConsumptionLoading(loading: boolean): void;
|
|
8230
8238
|
updateEnergyCard(data: EnergyKPI): void;
|
|
8231
8239
|
/**
|
|
8232
8240
|
* Update temperature card
|
|
@@ -17475,6 +17483,8 @@ interface HeaderStats {
|
|
|
17475
17483
|
total: number;
|
|
17476
17484
|
consumption: number;
|
|
17477
17485
|
zeroCount: number;
|
|
17486
|
+
/** Consumo ainda carregando → spinner em Consumo Total / Sem Consumo */
|
|
17487
|
+
loading?: boolean;
|
|
17478
17488
|
}
|
|
17479
17489
|
interface HeaderLabels {
|
|
17480
17490
|
connectivity?: string;
|
|
@@ -17509,6 +17519,8 @@ interface HeaderDevicesGridInstance {
|
|
|
17509
17519
|
destroy: () => void;
|
|
17510
17520
|
}
|
|
17511
17521
|
interface HeaderDevice {
|
|
17522
|
+
/** Consumo do período ainda não chegou (HO: /summary em andamento) */
|
|
17523
|
+
dataLoading?: boolean;
|
|
17512
17524
|
entityId?: string;
|
|
17513
17525
|
ingestionId?: string;
|
|
17514
17526
|
deviceStatus?: string;
|
|
@@ -17586,7 +17598,7 @@ declare class HeaderDevicesGridController implements HeaderDevicesGridInstance {
|
|
|
17586
17598
|
* CSS-in-JS styles for the stats header
|
|
17587
17599
|
* FIEL ao showcase/telemetry-grid/index.html
|
|
17588
17600
|
*/
|
|
17589
|
-
declare const HEADER_DEVICES_GRID_STYLES = "\n /* RFC-0125: HeaderDevicesGrid Component - FIEL ao TELEMETRY widget */\n .hdg-header {\n display: flex !important;\n flex-direction: row !important;\n align-items: stretch;\n gap: 0;\n padding: 0;\n background: var(--card-bg, #1e293b);\n border-radius: 8px;\n margin-bottom: 12px;\n overflow: hidden;\n }\n\n .hdg-header .stat-item {\n display: flex !important;\n flex-direction: column !important;\n gap: 2px;\n flex: 1;\n min-width: 0;\n padding: 12px 16px;\n border-right: 1px solid var(--card-bd, #334155);\n }\n\n .hdg-header .stat-item:last-of-type {\n border-right: none;\n }\n\n .hdg-header .stat-label {\n font-size: 11px;\n color: var(--ink-2, #94a3b8);\n text-transform: uppercase;\n letter-spacing: 0.5px;\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n }\n\n .hdg-header .stat-value {\n font-size: 18px;\n font-weight: 700;\n color: var(--ink-1, #f1f5f9);\n }\n\n /* Highlight com background de destaque e barras em ambos os lados */\n .hdg-header .stat-item.highlight {\n background: linear-gradient(135deg, rgba(245, 158, 11, 0.15) 0%, rgba(245, 158, 11, 0.25) 100%);\n border-left: 3px solid var(--telemetry-primary, #f59e0b);\n border-right: 3px solid var(--telemetry-primary, #f59e0b);\n position: relative;\n }\n\n .hdg-header .stat-item.highlight .stat-value {\n color: var(--telemetry-primary, #f59e0b);\n font-size: 20px;\n }\n\n /* Ajuste para o item apos o highlight nao ter borda dupla */\n .hdg-header .stat-item.highlight + .stat-item {\n border-left: none;\n }\n\n .hdg-header .filter-actions {\n display: flex;\n align-items: center;\n gap: 8px;\n padding: 8px 12px;\n border-left: 1px solid var(--card-bd, #334155);\n }\n\n .hdg-header .search-wrap {\n display: none;\n overflow: hidden;\n transition: all 0.2s ease;\n }\n\n .hdg-header .search-wrap.active {\n display: block;\n }\n\n .hdg-header .search-wrap input {\n padding: 6px 12px;\n border: 1px solid var(--card-bd, #334155);\n border-radius: 6px;\n background: transparent;\n color: var(--ink-1, #f1f5f9);\n font-size: 13px;\n width: 180px;\n }\n\n .hdg-header .search-wrap input:focus {\n outline: none;\n border-color: var(--telemetry-primary, #f59e0b);\n }\n\n .hdg-header .icon-btn {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 36px;\n height: 36px;\n border: 1px solid var(--card-bd, #334155);\n border-radius: 6px;\n background: transparent;\n color: var(--ink-2, #94a3b8);\n cursor: pointer;\n transition: all 0.15s ease;\n }\n\n .hdg-header .icon-btn:hover {\n background: var(--telemetry-primary, #f59e0b);\n border-color: var(--telemetry-primary, #f59e0b);\n color: white;\n }\n\n .hdg-header .icon-btn svg {\n width: 18px;\n height: 18px;\n fill: currentColor;\n display: block;\n }\n\n .hdg-header .icon-btn .icon-minimize {\n display: none;\n }\n\n .hdg-header .icon-btn .icon-maximize {\n display: block;\n }\n\n /* Light mode */\n .hdg-header--light {\n background: #ffffff;\n border: 1px solid #e2e8f0;\n }\n\n .hdg-header--light .stat-item {\n border-color: #e2e8f0;\n }\n\n .hdg-header--light .stat-item.highlight {\n background: linear-gradient(135deg, rgba(245, 158, 11, 0.1) 0%, rgba(245, 158, 11, 0.2) 100%);\n border-left-color: var(--telemetry-primary, #f59e0b);\n border-right-color: var(--telemetry-primary, #f59e0b);\n }\n\n .hdg-header--light .stat-label {\n color: #64748b;\n }\n\n .hdg-header--light .stat-value {\n color: #1e293b;\n }\n\n .hdg-header--light .filter-actions {\n border-color: #e2e8f0;\n }\n\n .hdg-header--light .search-wrap input {\n background: #f1f5f9;\n border-color: #cbd5e1;\n color: #1e293b;\n }\n\n .hdg-header--light .icon-btn {\n border-color: #cbd5e1;\n color: #64748b;\n }\n\n /* Maximized state for parent container */\n .telemetry-grid-wrap.maximized {\n position: fixed !important;\n inset: 0 !important;\n z-index: 99999 !important;\n width: 100vw !important;\n height: 100vh !important;\n background: var(--card-bg, #0f172a) !important;\n border-radius: 0 !important;\n overflow: auto !important;\n padding: 16px !important;\n }\n\n .telemetry-grid-wrap.maximized .telemetry-grid-header {\n position: sticky;\n top: 0;\n z-index: 10;\n background: var(--card-bg, #0f172a);\n padding-bottom: 12px;\n }\n\n .telemetry-grid-wrap.maximized .telemetry-cards-grid {\n max-height: none !important;\n overflow: visible !important;\n }\n\n .telemetry-grid-wrap.maximized .hdg-header .icon-btn .icon-maximize {\n display: none;\n }\n\n .telemetry-grid-wrap.maximized .hdg-header .icon-btn .icon-minimize {\n display: block;\n }\n\n /* Light mode maximized */\n body.light-mode .telemetry-grid-wrap.maximized {\n background: #f8fafc !important;\n }\n\n body.light-mode .telemetry-grid-wrap.maximized .telemetry-grid-header {\n background: #f8fafc;\n }\n";
|
|
17601
|
+
declare const HEADER_DEVICES_GRID_STYLES = "\n /* RFC-0125: HeaderDevicesGrid Component - FIEL ao TELEMETRY widget */\n .hdg-header {\n display: flex !important;\n flex-direction: row !important;\n align-items: stretch;\n gap: 0;\n padding: 0;\n background: var(--card-bg, #1e293b);\n border-radius: 8px;\n margin-bottom: 12px;\n overflow: hidden;\n }\n\n .hdg-header .stat-item {\n display: flex !important;\n flex-direction: column !important;\n gap: 2px;\n flex: 1;\n min-width: 0;\n padding: 12px 16px;\n border-right: 1px solid var(--card-bd, #334155);\n }\n\n .hdg-header .stat-item:last-of-type {\n border-right: none;\n }\n\n .hdg-header .stat-label {\n font-size: 11px;\n color: var(--ink-2, #94a3b8);\n text-transform: uppercase;\n letter-spacing: 0.5px;\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n }\n\n .hdg-header .stat-value {\n font-size: 18px;\n font-weight: 700;\n color: var(--ink-1, #f1f5f9);\n }\n\n /* Highlight com background de destaque e barras em ambos os lados */\n .hdg-header .stat-item.highlight {\n background: linear-gradient(135deg, rgba(245, 158, 11, 0.15) 0%, rgba(245, 158, 11, 0.25) 100%);\n border-left: 3px solid var(--telemetry-primary, #f59e0b);\n border-right: 3px solid var(--telemetry-primary, #f59e0b);\n position: relative;\n }\n\n .hdg-header .stat-item.highlight .stat-value {\n color: var(--telemetry-primary, #f59e0b);\n font-size: 20px;\n }\n\n /* Ajuste para o item apos o highlight nao ter borda dupla */\n .hdg-header .stat-item.highlight + .stat-item {\n border-left: none;\n }\n\n .hdg-header .filter-actions {\n display: flex;\n align-items: center;\n gap: 8px;\n padding: 8px 12px;\n border-left: 1px solid var(--card-bd, #334155);\n }\n\n .hdg-header .search-wrap {\n display: none;\n overflow: hidden;\n transition: all 0.2s ease;\n }\n\n .hdg-header .search-wrap.active {\n display: block;\n }\n\n .hdg-header .search-wrap input {\n padding: 6px 12px;\n border: 1px solid var(--card-bd, #334155);\n border-radius: 6px;\n background: transparent;\n color: var(--ink-1, #f1f5f9);\n font-size: 13px;\n width: 180px;\n }\n\n .hdg-header .search-wrap input:focus {\n outline: none;\n border-color: var(--telemetry-primary, #f59e0b);\n }\n\n .hdg-header .icon-btn {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 36px;\n height: 36px;\n border: 1px solid var(--card-bd, #334155);\n border-radius: 6px;\n background: transparent;\n color: var(--ink-2, #94a3b8);\n cursor: pointer;\n transition: all 0.15s ease;\n }\n\n .hdg-header .icon-btn:hover {\n background: var(--telemetry-primary, #f59e0b);\n border-color: var(--telemetry-primary, #f59e0b);\n color: white;\n }\n\n .hdg-header .icon-btn svg {\n width: 18px;\n height: 18px;\n fill: currentColor;\n display: block;\n }\n\n .hdg-header .icon-btn .icon-minimize {\n display: none;\n }\n\n .hdg-header .icon-btn .icon-maximize {\n display: block;\n }\n\n /* Light mode */\n .hdg-header--light {\n background: #ffffff;\n border: 1px solid #e2e8f0;\n }\n\n .hdg-header--light .stat-item {\n border-color: #e2e8f0;\n }\n\n .hdg-header--light .stat-item.highlight {\n background: linear-gradient(135deg, rgba(245, 158, 11, 0.1) 0%, rgba(245, 158, 11, 0.2) 100%);\n border-left-color: var(--telemetry-primary, #f59e0b);\n border-right-color: var(--telemetry-primary, #f59e0b);\n }\n\n .hdg-header--light .stat-label {\n color: #64748b;\n }\n\n .hdg-header--light .stat-value {\n color: #1e293b;\n }\n\n .hdg-header--light .filter-actions {\n border-color: #e2e8f0;\n }\n\n .hdg-header--light .search-wrap input {\n background: #f1f5f9;\n border-color: #cbd5e1;\n color: #1e293b;\n }\n\n .hdg-header--light .icon-btn {\n border-color: #cbd5e1;\n color: #64748b;\n }\n\n /* Maximized state for parent container */\n .telemetry-grid-wrap.maximized {\n position: fixed !important;\n inset: 0 !important;\n z-index: 99999 !important;\n width: 100vw !important;\n height: 100vh !important;\n background: var(--card-bg, #0f172a) !important;\n border-radius: 0 !important;\n overflow: auto !important;\n padding: 16px !important;\n }\n\n .telemetry-grid-wrap.maximized .telemetry-grid-header {\n position: sticky;\n top: 0;\n z-index: 10;\n background: var(--card-bg, #0f172a);\n padding-bottom: 12px;\n }\n\n .telemetry-grid-wrap.maximized .telemetry-cards-grid {\n max-height: none !important;\n overflow: visible !important;\n }\n\n .telemetry-grid-wrap.maximized .hdg-header .icon-btn .icon-maximize {\n display: none;\n }\n\n .telemetry-grid-wrap.maximized .hdg-header .icon-btn .icon-minimize {\n display: block;\n }\n\n /* Light mode maximized */\n body.light-mode .telemetry-grid-wrap.maximized {\n background: #f8fafc !important;\n }\n\n body.light-mode .telemetry-grid-wrap.maximized .telemetry-grid-header {\n background: #f8fafc;\n }\n\n/* Consumo ainda carregando */\n.hdg-value-spinner {\n display: inline-block;\n width: 13px;\n height: 13px;\n margin-right: 6px;\n vertical-align: -2px;\n border: 2px solid rgba(124, 58, 237, 0.2);\n border-top-color: var(--myio-brand-700, #7c3aed);\n border-radius: 50%;\n animation: myio-consumption-spin 0.8s linear infinite;\n}\n@keyframes myio-consumption-spin { to { transform: rotate(360deg); } }\n";
|
|
17590
17602
|
declare function injectHeaderDevicesGridStyles(): void;
|
|
17591
17603
|
|
|
17592
17604
|
/**
|
package/dist/index.js
CHANGED
|
@@ -10,7 +10,7 @@ import {
|
|
|
10
10
|
// package.json
|
|
11
11
|
var package_default = {
|
|
12
12
|
name: "myio-js-library",
|
|
13
|
-
version: "0.1.
|
|
13
|
+
version: "0.1.558",
|
|
14
14
|
description: "A clean, standalone JS SDK for MYIO projects",
|
|
15
15
|
license: "MIT",
|
|
16
16
|
repository: "github:gh-myio/myio-js-library",
|
|
@@ -11242,6 +11242,26 @@ var CSS_STRING = `
|
|
|
11242
11242
|
margin-left: 4px;
|
|
11243
11243
|
}
|
|
11244
11244
|
|
|
11245
|
+
/* Consumo ainda carregando (spinner no lugar do valor) */
|
|
11246
|
+
.myio-ho-card__value.is-loading .num {
|
|
11247
|
+
display: inline-flex;
|
|
11248
|
+
align-items: center;
|
|
11249
|
+
gap: 8px;
|
|
11250
|
+
font-size: 14px;
|
|
11251
|
+
font-weight: 600;
|
|
11252
|
+
color: var(--myio-muted, #9ca3af);
|
|
11253
|
+
}
|
|
11254
|
+
.myio-ho-card__value-spinner {
|
|
11255
|
+
width: 14px;
|
|
11256
|
+
height: 14px;
|
|
11257
|
+
border: 2px solid rgba(124, 58, 237, 0.2);
|
|
11258
|
+
border-top-color: var(--myio-brand-700, #7c3aed);
|
|
11259
|
+
border-radius: 50%;
|
|
11260
|
+
animation: myio-consumption-spin 0.8s linear infinite;
|
|
11261
|
+
flex-shrink: 0;
|
|
11262
|
+
}
|
|
11263
|
+
@keyframes myio-consumption-spin { to { transform: rotate(360deg); } }
|
|
11264
|
+
|
|
11245
11265
|
/* Efficiency bar */
|
|
11246
11266
|
.myio-ho-card__eff {
|
|
11247
11267
|
display: flex;
|
|
@@ -14914,7 +14934,20 @@ function paint(root, state5) {
|
|
|
14914
14934
|
const primaryValue = formatValueByDomain(entityObject.val, entityObject.domain);
|
|
14915
14935
|
const numSpan = root.querySelector(".myio-ho-card__value .num");
|
|
14916
14936
|
const unitSpan = root.querySelector(".myio-ho-card__value .unit");
|
|
14917
|
-
|
|
14937
|
+
const valueBox = root.querySelector(".myio-ho-card__value");
|
|
14938
|
+
const dataLoading = !!entityObject.dataLoading && entityObject.domain !== "temperature";
|
|
14939
|
+
if (valueBox) {
|
|
14940
|
+
valueBox.classList.toggle("is-loading", dataLoading);
|
|
14941
|
+
if (dataLoading) valueBox.setAttribute("aria-busy", "true");
|
|
14942
|
+
else valueBox.removeAttribute("aria-busy");
|
|
14943
|
+
}
|
|
14944
|
+
if (dataLoading) {
|
|
14945
|
+
numSpan.innerHTML = '<span class="myio-ho-card__value-spinner" aria-hidden="true"></span>Carregando\u2026';
|
|
14946
|
+
numSpan.title = "Carregando consumo do per\xEDodo";
|
|
14947
|
+
} else {
|
|
14948
|
+
numSpan.textContent = primaryValue;
|
|
14949
|
+
numSpan.removeAttribute("title");
|
|
14950
|
+
}
|
|
14918
14951
|
const barContainer = root.querySelector(".bar");
|
|
14919
14952
|
const effContainer = root.querySelector(".myio-ho-card__eff");
|
|
14920
14953
|
if (state5.enableSelection) {
|
|
@@ -70086,6 +70119,25 @@ var HeaderView = class {
|
|
|
70086
70119
|
transition: color 0.2s ease;
|
|
70087
70120
|
}
|
|
70088
70121
|
|
|
70122
|
+
/* Consumo ainda carregando */
|
|
70123
|
+
.${HEADER_CSS_PREFIX}-kpi-loading {
|
|
70124
|
+
display: inline-flex;
|
|
70125
|
+
align-items: center;
|
|
70126
|
+
gap: 10px;
|
|
70127
|
+
font-size: 1rem;
|
|
70128
|
+
font-weight: 600;
|
|
70129
|
+
opacity: 0.85;
|
|
70130
|
+
}
|
|
70131
|
+
.${HEADER_CSS_PREFIX}-kpi-spinner {
|
|
70132
|
+
width: 18px;
|
|
70133
|
+
height: 18px;
|
|
70134
|
+
border: 2.5px solid rgba(255, 255, 255, 0.3);
|
|
70135
|
+
border-top-color: currentColor;
|
|
70136
|
+
border-radius: 50%;
|
|
70137
|
+
animation: myio-consumption-spin 0.8s linear infinite;
|
|
70138
|
+
}
|
|
70139
|
+
@keyframes myio-consumption-spin { to { transform: rotate(360deg); } }
|
|
70140
|
+
|
|
70089
70141
|
.${HEADER_CSS_PREFIX}-card__subrow {
|
|
70090
70142
|
display: flex;
|
|
70091
70143
|
align-items: center;
|
|
@@ -70524,7 +70576,28 @@ var HeaderView = class {
|
|
|
70524
70576
|
/**
|
|
70525
70577
|
* Update energy card
|
|
70526
70578
|
*/
|
|
70579
|
+
/** Spinner nos KPIs de consumo (energia e água) enquanto o período carrega */
|
|
70580
|
+
setConsumptionLoading(loading) {
|
|
70581
|
+
if (!loading) {
|
|
70582
|
+
[this.energyKpiEl, this.waterKpiEl].forEach((el2) => {
|
|
70583
|
+
if (el2?.querySelector(`.${HEADER_CSS_PREFIX}-kpi-loading`)) el2.textContent = "-";
|
|
70584
|
+
});
|
|
70585
|
+
return;
|
|
70586
|
+
}
|
|
70587
|
+
const html = `<span class="${HEADER_CSS_PREFIX}-kpi-loading" aria-busy="true"><span class="${HEADER_CSS_PREFIX}-kpi-spinner" aria-hidden="true"></span>Carregando\u2026</span>`;
|
|
70588
|
+
if (this.energyKpiEl) this.energyKpiEl.innerHTML = html;
|
|
70589
|
+
if (this.waterKpiEl) this.waterKpiEl.innerHTML = html;
|
|
70590
|
+
if (this.energyTrendEl) this.energyTrendEl.textContent = "";
|
|
70591
|
+
if (this.waterTrendEl) this.waterTrendEl.textContent = "";
|
|
70592
|
+
}
|
|
70527
70593
|
updateEnergyCard(data) {
|
|
70594
|
+
if (data.loading) {
|
|
70595
|
+
if (this.energyKpiEl) {
|
|
70596
|
+
this.energyKpiEl.innerHTML = `<span class="${HEADER_CSS_PREFIX}-kpi-loading" aria-busy="true"><span class="${HEADER_CSS_PREFIX}-kpi-spinner" aria-hidden="true"></span>Carregando\u2026</span>`;
|
|
70597
|
+
}
|
|
70598
|
+
if (this.energyTrendEl) this.energyTrendEl.textContent = "";
|
|
70599
|
+
return;
|
|
70600
|
+
}
|
|
70528
70601
|
if (this.energyKpiEl) {
|
|
70529
70602
|
if (data.isFiltered && data.unfilteredTotal > 0) {
|
|
70530
70603
|
const filteredFormatted = this.formatEnergy(data.customerTotal);
|
|
@@ -70573,6 +70646,13 @@ var HeaderView = class {
|
|
|
70573
70646
|
* Update water card
|
|
70574
70647
|
*/
|
|
70575
70648
|
updateWaterCard(data) {
|
|
70649
|
+
if (data.loading) {
|
|
70650
|
+
if (this.waterKpiEl) {
|
|
70651
|
+
this.waterKpiEl.innerHTML = `<span class="${HEADER_CSS_PREFIX}-kpi-loading" aria-busy="true"><span class="${HEADER_CSS_PREFIX}-kpi-spinner" aria-hidden="true"></span>Carregando\u2026</span>`;
|
|
70652
|
+
}
|
|
70653
|
+
if (this.waterTrendEl) this.waterTrendEl.textContent = "";
|
|
70654
|
+
return;
|
|
70655
|
+
}
|
|
70576
70656
|
if (this.waterKpiEl) {
|
|
70577
70657
|
if (data.isFiltered && data.unfilteredTotal > 0) {
|
|
70578
70658
|
const filteredFormatted = this.formatWater(data.filteredTotal);
|
|
@@ -71558,6 +71638,9 @@ function createHeaderComponent(params) {
|
|
|
71558
71638
|
tooltipData.temperature = data;
|
|
71559
71639
|
view.updateTemperatureCard(data);
|
|
71560
71640
|
}
|
|
71641
|
+
function setConsumptionLoading(loading) {
|
|
71642
|
+
view.setConsumptionLoading(loading);
|
|
71643
|
+
}
|
|
71561
71644
|
function updateWaterKPI(data) {
|
|
71562
71645
|
tooltipData.water = data;
|
|
71563
71646
|
view.updateWaterCard(data);
|
|
@@ -71613,6 +71696,7 @@ function createHeaderComponent(params) {
|
|
|
71613
71696
|
updateEnergyKPI,
|
|
71614
71697
|
updateTemperatureKPI,
|
|
71615
71698
|
updateWaterKPI,
|
|
71699
|
+
setConsumptionLoading,
|
|
71616
71700
|
updateTooltipData,
|
|
71617
71701
|
// Shopping/Filter
|
|
71618
71702
|
updateShoppings,
|
|
@@ -120831,6 +120915,20 @@ var HEADER_DEVICES_GRID_STYLES = `
|
|
|
120831
120915
|
body.light-mode .telemetry-grid-wrap.maximized .telemetry-grid-header {
|
|
120832
120916
|
background: #f8fafc;
|
|
120833
120917
|
}
|
|
120918
|
+
|
|
120919
|
+
/* Consumo ainda carregando */
|
|
120920
|
+
.hdg-value-spinner {
|
|
120921
|
+
display: inline-block;
|
|
120922
|
+
width: 13px;
|
|
120923
|
+
height: 13px;
|
|
120924
|
+
margin-right: 6px;
|
|
120925
|
+
vertical-align: -2px;
|
|
120926
|
+
border: 2px solid rgba(124, 58, 237, 0.2);
|
|
120927
|
+
border-top-color: var(--myio-brand-700, #7c3aed);
|
|
120928
|
+
border-radius: 50%;
|
|
120929
|
+
animation: myio-consumption-spin 0.8s linear infinite;
|
|
120930
|
+
}
|
|
120931
|
+
@keyframes myio-consumption-spin { to { transform: rotate(360deg); } }
|
|
120834
120932
|
`;
|
|
120835
120933
|
function injectHeaderDevicesGridStyles() {
|
|
120836
120934
|
const styleId = "hdg-styles";
|
|
@@ -120848,14 +120946,15 @@ var DOMAIN_CONFIG7 = {
|
|
|
120848
120946
|
consumptionLabel: "Consumo Total",
|
|
120849
120947
|
zeroLabel: "Sem Consumo",
|
|
120850
120948
|
unit: "kWh",
|
|
120851
|
-
|
|
120949
|
+
// 3 casas: mesmo padrão do dashboard de shopping (RFC-0108, measurementSettings default)
|
|
120950
|
+
formatValue: (value) => formatEnergy(value, void 0, 3)
|
|
120852
120951
|
},
|
|
120853
120952
|
water: {
|
|
120854
120953
|
totalLabel: "Total Hidr\xF4metros",
|
|
120855
120954
|
consumptionLabel: "Consumo Total",
|
|
120856
120955
|
zeroLabel: "Sem Consumo",
|
|
120857
120956
|
unit: "m\xB3",
|
|
120858
|
-
formatValue: (value) =>
|
|
120957
|
+
formatValue: (value) => `${(Number(value) || 0).toLocaleString("pt-BR", { minimumFractionDigits: 3, maximumFractionDigits: 3 })} m\xB3`
|
|
120859
120958
|
},
|
|
120860
120959
|
temperature: {
|
|
120861
120960
|
totalLabel: "Total Sensores",
|
|
@@ -121023,6 +121122,16 @@ var HeaderDevicesGridView = class {
|
|
|
121023
121122
|
const percentage = total > 0 ? (online / total * 100).toFixed(1) : "0.0";
|
|
121024
121123
|
connectivityEl.textContent = `${online}/${total} (${percentage}%)`;
|
|
121025
121124
|
totalEl.textContent = total.toString();
|
|
121125
|
+
if (stats.loading) {
|
|
121126
|
+
const spin = '<span class="hdg-value-spinner" aria-hidden="true"></span>';
|
|
121127
|
+
consumptionEl.innerHTML = `${spin}Carregando\u2026`;
|
|
121128
|
+
zeroEl.innerHTML = spin;
|
|
121129
|
+
consumptionEl.setAttribute("aria-busy", "true");
|
|
121130
|
+
zeroEl.setAttribute("aria-busy", "true");
|
|
121131
|
+
return;
|
|
121132
|
+
}
|
|
121133
|
+
consumptionEl.removeAttribute("aria-busy");
|
|
121134
|
+
zeroEl.removeAttribute("aria-busy");
|
|
121026
121135
|
consumptionEl.textContent = this.domainConfig.formatValue(consumption);
|
|
121027
121136
|
zeroEl.textContent = zeroCount.toString();
|
|
121028
121137
|
}
|
|
@@ -121129,7 +121238,8 @@ var HeaderDevicesGridController = class {
|
|
|
121129
121238
|
online,
|
|
121130
121239
|
total: devices.length,
|
|
121131
121240
|
consumption: displayValue,
|
|
121132
|
-
zeroCount
|
|
121241
|
+
zeroCount,
|
|
121242
|
+
loading: this.domain !== "temperature" && devices.some((d) => d.dataLoading)
|
|
121133
121243
|
});
|
|
121134
121244
|
}
|
|
121135
121245
|
setThemeMode(mode) {
|