@classic-homes/charts-core 0.3.1 → 0.3.2

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 CHANGED
@@ -1290,10 +1290,11 @@ function toSliceData(rows, options) {
1290
1290
  nullLabel = "Unknown",
1291
1291
  colors: colors3
1292
1292
  } = options;
1293
+ const effective = value === void 0 ? "count" : aggregate;
1293
1294
  const { categories, series } = fromRecords(rows, {
1294
1295
  category: name,
1295
1296
  value,
1296
- aggregate: value === void 0 ? "count" : aggregate,
1297
+ aggregate: effective,
1297
1298
  nullLabel
1298
1299
  });
1299
1300
  const values = series[0]?.data ?? [];
@@ -1307,7 +1308,12 @@ function toSliceData(rows, options) {
1307
1308
  const rest = slices.slice(topN);
1308
1309
  slices = slices.slice(0, topN);
1309
1310
  if (otherLabel !== void 0) {
1310
- slices.push({ name: otherLabel, value: rest.reduce((sum, slice) => sum + slice.value, 0) });
1311
+ const folded = new Set(rest.map((slice) => slice.name));
1312
+ const other = fromRecords(
1313
+ (rows ?? []).filter((row) => folded.has(toLabel(read(row, name), nullLabel))),
1314
+ { category: () => otherLabel, value, aggregate: effective }
1315
+ ).series[0]?.data[0];
1316
+ slices.push({ name: otherLabel, value: other ?? 0 });
1311
1317
  }
1312
1318
  }
1313
1319
  return slices.map(
@@ -1468,15 +1474,17 @@ function formatTableCell(table, cell, column, format) {
1468
1474
  return formatValue(cell, format);
1469
1475
  }
1470
1476
  }
1471
- function csvCell(cell) {
1477
+ var FORMULA_START = /^[=+\-@\t\r]/;
1478
+ function csvCell(cell, raw = cell) {
1472
1479
  if (cell == null) return "";
1473
- const text = String(cell);
1480
+ let text = String(cell);
1481
+ if (typeof raw === "string" && FORMULA_START.test(text)) text = `'${text}`;
1474
1482
  return /[",\r\n]/.test(text) ? `"${text.replace(/"/g, '""')}"` : text;
1475
1483
  }
1476
1484
  function tableToCsv(table, format) {
1477
1485
  const lines = [table.headers, ...table.rows].map(
1478
1486
  (row, rowIndex) => row.map(
1479
- (cell, column) => csvCell(rowIndex > 0 && format ? formatTableCell(table, cell, column, format) : cell)
1487
+ (cell, column) => csvCell(rowIndex > 0 && format ? formatTableCell(table, cell, column, format) : cell, cell)
1480
1488
  ).join(",")
1481
1489
  );
1482
1490
  return lines.join("\r\n");
package/dist/index.d.cts CHANGED
@@ -536,7 +536,11 @@ interface ToSliceDataOptions<T> {
536
536
  sort?: 'desc' | 'asc' | 'none';
537
537
  /** Keep only the largest N slices */
538
538
  topN?: number;
539
- /** Fold slices beyond `topN` into one with this label; omit to drop them */
539
+ /**
540
+ * Fold slices beyond `topN` into one with this label; omit to drop them.
541
+ * The folded slice aggregates the folded records, so with 'avg' it is their
542
+ * average rather than a sum of averages.
543
+ */
540
544
  otherLabel?: string;
541
545
  /** Label for a missing name (defaults to 'Unknown') */
542
546
  nullLabel?: string;
package/dist/index.d.ts CHANGED
@@ -536,7 +536,11 @@ interface ToSliceDataOptions<T> {
536
536
  sort?: 'desc' | 'asc' | 'none';
537
537
  /** Keep only the largest N slices */
538
538
  topN?: number;
539
- /** Fold slices beyond `topN` into one with this label; omit to drop them */
539
+ /**
540
+ * Fold slices beyond `topN` into one with this label; omit to drop them.
541
+ * The folded slice aggregates the folded records, so with 'avg' it is their
542
+ * average rather than a sum of averages.
543
+ */
540
544
  otherLabel?: string;
541
545
  /** Label for a missing name (defaults to 'Unknown') */
542
546
  nullLabel?: string;
package/dist/index.js CHANGED
@@ -969,10 +969,11 @@ function toSliceData(rows, options) {
969
969
  nullLabel = "Unknown",
970
970
  colors
971
971
  } = options;
972
+ const effective = value === void 0 ? "count" : aggregate;
972
973
  const { categories, series } = fromRecords(rows, {
973
974
  category: name,
974
975
  value,
975
- aggregate: value === void 0 ? "count" : aggregate,
976
+ aggregate: effective,
976
977
  nullLabel
977
978
  });
978
979
  const values = series[0]?.data ?? [];
@@ -986,7 +987,12 @@ function toSliceData(rows, options) {
986
987
  const rest = slices.slice(topN);
987
988
  slices = slices.slice(0, topN);
988
989
  if (otherLabel !== void 0) {
989
- slices.push({ name: otherLabel, value: rest.reduce((sum, slice) => sum + slice.value, 0) });
990
+ const folded = new Set(rest.map((slice) => slice.name));
991
+ const other = fromRecords(
992
+ (rows ?? []).filter((row) => folded.has(toLabel(read(row, name), nullLabel))),
993
+ { category: () => otherLabel, value, aggregate: effective }
994
+ ).series[0]?.data[0];
995
+ slices.push({ name: otherLabel, value: other ?? 0 });
990
996
  }
991
997
  }
992
998
  return slices.map(
@@ -1147,15 +1153,17 @@ function formatTableCell(table, cell, column, format) {
1147
1153
  return formatValue(cell, format);
1148
1154
  }
1149
1155
  }
1150
- function csvCell(cell) {
1156
+ var FORMULA_START = /^[=+\-@\t\r]/;
1157
+ function csvCell(cell, raw = cell) {
1151
1158
  if (cell == null) return "";
1152
- const text = String(cell);
1159
+ let text = String(cell);
1160
+ if (typeof raw === "string" && FORMULA_START.test(text)) text = `'${text}`;
1153
1161
  return /[",\r\n]/.test(text) ? `"${text.replace(/"/g, '""')}"` : text;
1154
1162
  }
1155
1163
  function tableToCsv(table, format) {
1156
1164
  const lines = [table.headers, ...table.rows].map(
1157
1165
  (row, rowIndex) => row.map(
1158
- (cell, column) => csvCell(rowIndex > 0 && format ? formatTableCell(table, cell, column, format) : cell)
1166
+ (cell, column) => csvCell(rowIndex > 0 && format ? formatTableCell(table, cell, column, format) : cell, cell)
1159
1167
  ).join(",")
1160
1168
  );
1161
1169
  return lines.join("\r\n");
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@classic-homes/charts-core",
3
- "version": "0.3.1",
3
+ "version": "0.3.2",
4
4
  "description": "Core utilities and theme for Classic Theme charts",
5
5
  "type": "module",
6
6
  "main": "dist/index.cjs",