@beweco/aurora-ui 0.6.61 → 0.6.63

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.esm.js CHANGED
@@ -342,7 +342,7 @@ var Input = function (_a) {
342
342
  } })));
343
343
  };
344
344
 
345
- var defaultTranslations$f = {
345
+ var defaultTranslations$g = {
346
346
  addHolidayTitle: "Add holiday",
347
347
  dayOption: "Day",
348
348
  dateRangeOption: "Date range",
@@ -366,7 +366,7 @@ var INITIAL_HOLIDAY_STATE = {
366
366
  */
367
367
  var AddHolidayForm = function (_a) {
368
368
  var onAddHoliday = _a.onAddHoliday, translations = _a.translations, className = _a.className, radioGroupProps = _a.radioGroupProps, dateRangePickerProps = _a.dateRangePickerProps, buttonProps = _a.buttonProps;
369
- var t = __assign(__assign({}, defaultTranslations$f), translations);
369
+ var t = __assign(__assign({}, defaultTranslations$g), translations);
370
370
  var _b = useState(INITIAL_HOLIDAY_STATE), newHoliday = _b[0], setNewHoliday = _b[1];
371
371
  /**
372
372
  * A boolean flag that determines if a date has been set.
@@ -436,7 +436,7 @@ var P = function (_a) {
436
436
  return (jsx("p", __assign({ className: cn("text-tiny text-default-500 font-normal", className) }, props, { children: children })));
437
437
  };
438
438
 
439
- var defaultTranslations$e = {
439
+ var defaultTranslations$f = {
440
440
  title: "Analytics",
441
441
  description: "Monthly growth of your metrics during the selected period",
442
442
  viewDetails: "View Details",
@@ -490,7 +490,7 @@ var formatMonth = function (month) {
490
490
  var AnalyticsCard = function (_a) {
491
491
  var _b, _c;
492
492
  var data = _a.data, _d = _a.showTimePeriods, showTimePeriods = _d === void 0 ? true : _d, _e = _a.showDropdownMenu, showDropdownMenu = _e === void 0 ? true : _e, _f = _a.showMetricCards, showMetricCards = _f === void 0 ? true : _f, onChartChange = _a.onChartChange, onMenuAction = _a.onMenuAction, onTimePeriodChange = _a.onTimePeriodChange, _g = _a.translations, translations = _g === void 0 ? {} : _g, props = __rest(_a, ["data", "showTimePeriods", "showDropdownMenu", "showMetricCards", "onChartChange", "onMenuAction", "onTimePeriodChange", "translations"]);
493
- var t = __assign(__assign({}, defaultTranslations$e), translations);
493
+ var t = __assign(__assign({}, defaultTranslations$f), translations);
494
494
  var _h = useState((_c = (_b = data[0]) === null || _b === void 0 ? void 0 : _b.key) !== null && _c !== void 0 ? _c : ""), activeChart = _h[0], setActiveChart = _h[1];
495
495
  var activeChartData = useMemo(function () {
496
496
  var _a;
@@ -653,7 +653,7 @@ var DEFAULT_PREDEFINED_COLORS = [
653
653
  /**
654
654
  * Default translations (Spanish)
655
655
  */
656
- var defaultTranslations$d = {
656
+ var defaultTranslations$e = {
657
657
  label: "Color",
658
658
  placeholder: "Ingresa código hex",
659
659
  customColorLabel: "Color personalizado",
@@ -718,7 +718,7 @@ var ColorPicker = forwardRef(function (_a, ref) {
718
718
  var value = _a.value, onChange = _a.onChange, label = _a.label, _b = _a.required, required = _b === void 0 ? false : _b, _c = _a.disabled, disabled = _c === void 0 ? false : _c, _d = _a.error, error = _d === void 0 ? false : _d, errorText = _a.errorText, _e = _a.predefinedColors, predefinedColors = _e === void 0 ? DEFAULT_PREDEFINED_COLORS : _e, _f = _a.enableRecentColors, enableRecentColors = _f === void 0 ? true : _f, _g = _a.maxRecentColors, maxRecentColors = _g === void 0 ? 6 : _g, _h = _a.recentColorsStorageKey, recentColorsStorageKey = _h === void 0 ? "aurora-ui-recent-colors" : _h, _j = _a.showPredefinedColors, showPredefinedColors = _j === void 0 ? true : _j, _k = _a.translations, translations = _k === void 0 ? {} : _k, _l = _a.className, className = _l === void 0 ? "" : _l, id = _a.id, name = _a.name;
719
719
  var generatedId = useId();
720
720
  var inputId = id || generatedId;
721
- var t = __assign(__assign({}, defaultTranslations$d), translations);
721
+ var t = __assign(__assign({}, defaultTranslations$e), translations);
722
722
  // Local state for text input — holds the hex digits WITHOUT the leading "#".
723
723
  // The "#" is rendered as a fixed startContent prefix.
724
724
  var _m = useState(stripHash(value)), textValue = _m[0], setTextValue = _m[1];
@@ -1849,7 +1849,7 @@ var countries = [
1849
1849
  ];
1850
1850
  var uniqueCountries = Array.from(new Map(countries.map(function (item) { return [item.code + item.name, item]; })).values());
1851
1851
  // Traducciones por defecto
1852
- var defaultTranslations$c = {
1852
+ var defaultTranslations$d = {
1853
1853
  label: "Teléfono",
1854
1854
  placeholder: "Número de teléfono",
1855
1855
  searchPlaceholder: "Buscar país...",
@@ -1933,7 +1933,7 @@ var defaultCurrencyOptions = (function () {
1933
1933
  euroOption
1934
1934
  ], false), base.slice(zaIdx + 1), true);
1935
1935
  })();
1936
- var defaultTranslations$b = {
1936
+ var defaultTranslations$c = {
1937
1937
  label: "Importe",
1938
1938
  placeholder: "0",
1939
1939
  searchPlaceholder: "Buscar país o moneda...",
@@ -2398,7 +2398,7 @@ var Currency = function (_a) {
2398
2398
  var portalDropdownRef = useRef(null);
2399
2399
  var _q = useState({}), dropdownPosition = _q[0], setDropdownPosition = _q[1];
2400
2400
  var _r = useState(options), filteredOptions = _r[0], setFilteredOptions = _r[1];
2401
- var t = __assign(__assign({}, defaultTranslations$b), translations);
2401
+ var t = __assign(__assign({}, defaultTranslations$c), translations);
2402
2402
  var getCountryName = function (opt) { var _a, _b; return (_b = (_a = t.countries) === null || _a === void 0 ? void 0 : _a[opt.country]) !== null && _b !== void 0 ? _b : opt.name; };
2403
2403
  var finalLabel = label !== null && label !== void 0 ? label : t.label;
2404
2404
  useEffect(function () {
@@ -2558,7 +2558,7 @@ function useBreakpoint() {
2558
2558
  }
2559
2559
 
2560
2560
  // Default translations in Spanish
2561
- var defaultTranslations$a = {
2561
+ var defaultTranslations$b = {
2562
2562
  emptyStateMessage: "No hay contenido disponible",
2563
2563
  emptyStateButtonText: "Agregar contenido",
2564
2564
  previousButtonLabel: "Anterior",
@@ -2584,7 +2584,7 @@ var defaultTranslations$a = {
2584
2584
  */
2585
2585
  var ContentCarousel = function (_a) {
2586
2586
  var items = _a.items, onItemClick = _a.onItemClick, _b = _a.className, className = _b === void 0 ? "" : _b, _c = _a.emptyStateRedirectPath, emptyStateRedirectPath = _c === void 0 ? "" : _c, _d = _a.translations, translations = _d === void 0 ? {} : _d, renderFooter = _a.renderFooter, renderHeader = _a.renderHeader, renderBody = _a.renderBody, _e = _a.haveChip, haveChip = _e === void 0 ? false : _e;
2587
- var t = __assign(__assign({}, defaultTranslations$a), translations);
2587
+ var t = __assign(__assign({}, defaultTranslations$b), translations);
2588
2588
  var breakpoint = useBreakpoint();
2589
2589
  var isMobile = breakpoint === "mobile";
2590
2590
  var isTablet = breakpoint === "tablet";
@@ -2789,7 +2789,7 @@ function CarouselItemComponent(_a) {
2789
2789
  }
2790
2790
 
2791
2791
  // Default translations in Spanish
2792
- var defaultTranslations$9 = {
2792
+ var defaultTranslations$a = {
2793
2793
  editButtonLabel: "Editar",
2794
2794
  deleteButtonLabel: "Eliminar",
2795
2795
  publishButtonLabel: "Publicar",
@@ -2816,7 +2816,7 @@ var defaultTranslations$9 = {
2816
2816
  */
2817
2817
  var SocialMediaBar = function (_a) {
2818
2818
  var platform = _a.platform, _b = _a.badgeOnly, badgeOnly = _b === void 0 ? false : _b, _c = _a.showPreview, showPreview = _c === void 0 ? false : _c, onEdit = _a.onEdit, onDelete = _a.onDelete, onPublish = _a.onPublish, onPreview = _a.onPreview, _d = _a.actionsAlwaysVisible, actionsAlwaysVisible = _d === void 0 ? false : _d, _e = _a.isHovered, isHovered = _e === void 0 ? false : _e, _f = _a.className, className = _f === void 0 ? "" : _f, _g = _a.translations, translations = _g === void 0 ? {} : _g, customBadge = _a.customBadge, customActions = _a.customActions;
2819
- var t = __assign(__assign({}, defaultTranslations$9), translations);
2819
+ var t = __assign(__assign({}, defaultTranslations$a), translations);
2820
2820
  // Determine visibility of actions
2821
2821
  var showActions = actionsAlwaysVisible || isHovered;
2822
2822
  return (jsxs("div", { className: "flex items-center justify-between ".concat(className), children: [jsxs("div", { className: "flex items-center gap-2", children: [customBadge || (jsxs("div", { className: "backdrop-blur-xl border border-white/30 rounded-full px-3 py-1.5 shadow-xl flex items-center gap-2", style: {
@@ -2892,7 +2892,7 @@ var SocialMediaCarousel = function (_a) {
2892
2892
  };
2893
2893
 
2894
2894
  // Traducciones por defecto en español
2895
- var defaultTranslations$8 = {
2895
+ var defaultTranslations$9 = {
2896
2896
  dayOption: "Día específico",
2897
2897
  dateRangeOption: "Rango de fechas",
2898
2898
  selectDateAriaLabel: "Seleccionar fecha",
@@ -2910,7 +2910,7 @@ var DateSelector = function (_a) {
2910
2910
  var _f = React.useState(initialDate || null), date = _f[0], setDate = _f[1];
2911
2911
  var _g = React.useState(initialDateRange || null), dateRange = _g[0], setDateRange = _g[1];
2912
2912
  // Combinar traducciones por defecto con las proporcionadas
2913
- var t = __assign(__assign({}, defaultTranslations$8), translations);
2913
+ var t = __assign(__assign({}, defaultTranslations$9), translations);
2914
2914
  var handleTypeChange = function (value) {
2915
2915
  var newType = value;
2916
2916
  setType(newType);
@@ -3222,7 +3222,7 @@ var KanbanComponent = function (_a) {
3222
3222
  var Kanban = memo(KanbanComponent);
3223
3223
  Kanban.displayName = "Kanban";
3224
3224
 
3225
- var defaultTranslations$7 = {
3225
+ var defaultTranslations$8 = {
3226
3226
  previewAlt: "Vista previa de imagen",
3227
3227
  removeButtonAriaLabel: "Eliminar imagen",
3228
3228
  emptyStateText: "No hay imágenes para mostrar",
@@ -3255,7 +3255,7 @@ var normalizeImages = function (images) {
3255
3255
  };
3256
3256
  var ImagePreview = function (_a) {
3257
3257
  var images = _a.images, _b = _a.size, size = _b === void 0 ? "small" : _b, onRemove = _a.onRemove, _c = _a.showRemoveButton, showRemoveButton = _c === void 0 ? true : _c, _d = _a.className, className = _d === void 0 ? "" : _d, _e = _a.translations, translations = _e === void 0 ? {} : _e, _f = _a.backgroundColor, backgroundColor = _f === void 0 ? "bg-white dark:bg-gray-800" : _f, _g = _a.radius, radius = _g === void 0 ? "lg" : _g, _h = _a.showBorder, showBorder = _h === void 0 ? true : _h, onImageClick = _a.onImageClick;
3258
- var t = __assign(__assign({}, defaultTranslations$7), translations);
3258
+ var t = __assign(__assign({}, defaultTranslations$8), translations);
3259
3259
  var normalizedImages = normalizeImages(images);
3260
3260
  var sizeClass = sizeClasses[size];
3261
3261
  var radiusClass = radiusClasses[radius];
@@ -3781,7 +3781,7 @@ var VALID_STEP_COLORS$1 = [
3781
3781
  "danger",
3782
3782
  "default",
3783
3783
  ];
3784
- var defaultTranslations$6 = {
3784
+ var defaultTranslations$7 = {
3785
3785
  checkIconTitle: "Check",
3786
3786
  };
3787
3787
  function getContainerCSSVars$1(color) {
@@ -3826,7 +3826,7 @@ function getCircleStyle$1(status) {
3826
3826
  var VerticalSteps = React.forwardRef(function (_a, ref) {
3827
3827
  var _b = _a.color, color = _b === void 0 ? "primary" : _b, _c = _a.steps, stepsProp = _c === void 0 ? [] : _c, _d = _a.defaultStep, defaultStep = _d === void 0 ? 0 : _d, onStepChange = _a.onStepChange, currentStepProp = _a.currentStep, _e = _a.hideProgressBars, hideProgressBars = _e === void 0 ? false : _e, _f = _a.hideInactiveDescriptions, hideInactiveDescriptions = _f === void 0 ? false : _f, stepClassName = _a.stepClassName, className = _a.className, translations = _a.translations, props = __rest(_a, ["color", "steps", "defaultStep", "onStepChange", "currentStep", "hideProgressBars", "hideInactiveDescriptions", "stepClassName", "className", "translations"]);
3828
3828
  var _g = $458b0a5536c1a7cf$export$40bfa8c7b0832715(currentStepProp, defaultStep, onStepChange), currentStep = _g[0], setCurrentStep = _g[1];
3829
- var t = __assign(__assign({}, defaultTranslations$6), translations);
3829
+ var t = __assign(__assign({}, defaultTranslations$7), translations);
3830
3830
  var steps = React.useMemo(function () {
3831
3831
  if (typeof stepsProp === "number") {
3832
3832
  return Array.from({ length: stepsProp }, function () { return ({}); });
@@ -3990,7 +3990,7 @@ var Phone = function (_a) {
3990
3990
  var portalDropdownRef = useRef(null);
3991
3991
  var _l = useState({}), dropdownPosition = _l[0], setDropdownPosition = _l[1];
3992
3992
  var _m = useState(uniqueCountries), filteredCountries = _m[0], setFilteredCountries = _m[1];
3993
- var t = __assign(__assign({}, defaultTranslations$c), translations);
3993
+ var t = __assign(__assign({}, defaultTranslations$d), translations);
3994
3994
  var getCountryName = function (country) { var _a, _b; return (_b = (_a = t.countries) === null || _a === void 0 ? void 0 : _a[country.country]) !== null && _b !== void 0 ? _b : country.name; };
3995
3995
  var finalLabel = label || t.label;
3996
3996
  useEffect(function () {
@@ -4089,7 +4089,7 @@ var Phone = function (_a) {
4089
4089
  : ""), onClick: function () { return handleCountrySelect(country); }, children: [jsx("span", { className: "mr-3", children: jsx(FlagIcon, { countryCode: country.country, size: "md" }) }), jsx("span", { className: "flex-1 text-left text-default-500", children: getCountryName(country) }), jsx("span", { className: "text-xs text-default-500", children: country.code })] }, "".concat(country.code, "-").concat(country.country))); })) : (jsx("div", { className: "px-4 py-2 text-sm text-default-500", children: t.noCountriesFound })) })] }), document.body)] }));
4090
4090
  };
4091
4091
 
4092
- var defaultTranslations$5 = {
4092
+ var defaultTranslations$6 = {
4093
4093
  message: "The Winter 2024 Release is here: new editor, analytics API, and so much more.",
4094
4094
  buttonText: "Explore",
4095
4095
  closeButtonLabel: "Close Banner",
@@ -4099,7 +4099,7 @@ var defaultTranslations$5 = {
4099
4099
  */
4100
4100
  var PromotionalBanner = function (_a) {
4101
4101
  var message = _a.message, buttonText = _a.buttonText, _b = _a.messageHref, messageHref = _b === void 0 ? "#" : _b, _c = _a.buttonHref, buttonHref = _c === void 0 ? "#" : _c, _d = _a.showCloseButton, showCloseButton = _d === void 0 ? true : _d, _e = _a.isVisible, isVisible = _e === void 0 ? true : _e, _f = _a.gradientColors, gradientColors = _f === void 0 ? ["default-100", "danger-100", "secondary-100"] : _f, _g = _a.buttonGradientColors, buttonGradientColors = _g === void 0 ? ["#F871A0", "#9353D3"] : _g, onClose = _a.onClose, onMessageClick = _a.onMessageClick, onButtonClick = _a.onButtonClick, _h = _a.messageLinkProps, messageLinkProps = _h === void 0 ? {} : _h, _j = _a.buttonProps, buttonProps = _j === void 0 ? {} : _j, _k = _a.translations, translations = _k === void 0 ? {} : _k;
4102
- var t = __assign(__assign({}, defaultTranslations$5), translations);
4102
+ var t = __assign(__assign({}, defaultTranslations$6), translations);
4103
4103
  var finalMessage = message || t.message;
4104
4104
  var finalButtonText = buttonText || t.buttonText;
4105
4105
  var handleClose = function () {
@@ -5016,7 +5016,7 @@ var TimeInput = function (_a) {
5016
5016
  * />
5017
5017
  * ```
5018
5018
  */
5019
- var defaultTranslations$4 = {
5019
+ var defaultTranslations$5 = {
5020
5020
  /** Label for the start time input field */
5021
5021
  from: "Desde",
5022
5022
  /** Label for the end time input field */
@@ -5074,7 +5074,7 @@ var defaultTranslations$4 = {
5074
5074
  */
5075
5075
  var ScheduleRow = function (_a) {
5076
5076
  var day = _a.day, daySchedule = _a.daySchedule, _b = _a.translations, translations = _b === void 0 ? {} : _b, _c = _a.showCopyToAll, showCopyToAll = _c === void 0 ? false : _c, onChange = _a.onChange, onCopyToAll = _a.onCopyToAll;
5077
- var t = __assign(__assign({}, defaultTranslations$4), translations);
5077
+ var t = __assign(__assign({}, defaultTranslations$5), translations);
5078
5078
  /**
5079
5079
  * @function validateTimeSlots
5080
5080
  * @description Validates all time slots to ensure the "from" time is not after the "to" time.
@@ -5227,7 +5227,7 @@ var Select = function (_a) {
5227
5227
  } })) }));
5228
5228
  };
5229
5229
 
5230
- var defaultTranslations$3 = {
5230
+ var defaultTranslations$4 = {
5231
5231
  username: "tu_negocio",
5232
5232
  sendMessage: "Enviar mensaje",
5233
5233
  viewMore: "ver más",
@@ -5252,7 +5252,7 @@ var defaultTranslations$3 = {
5252
5252
  */
5253
5253
  var SocialMediaPreview = function (_a) {
5254
5254
  var platform = _a.platform, imageUrl = _a.imageUrl, caption = _a.caption, _b = _a.variant, variant = _b === void 0 ? "full" : _b, _c = _a.postAspectRatio, postAspectRatio = _c === void 0 ? "square" : _c, _d = _a.showHeader, showHeader = _d === void 0 ? true : _d, _e = _a.maxCaptionLength, maxCaptionLength = _e === void 0 ? 125 : _e, onToggleCaption = _a.onToggleCaption, showFullCaption = _a.showFullCaption, username = _a.username, avatarUrl = _a.avatarUrl, _f = _a.translations, translations = _f === void 0 ? {} : _f, _g = _a.className, className = _g === void 0 ? "" : _g, _h = _a.imageProps, imageProps = _h === void 0 ? {} : _h, _j = _a.showEditButton, showEditButton = _j === void 0 ? false : _j, onEditClick = _a.onEditClick;
5255
- var t = __assign(__assign({}, defaultTranslations$3), translations);
5255
+ var t = __assign(__assign({}, defaultTranslations$4), translations);
5256
5256
  var displayUsername = username || t.username;
5257
5257
  var shouldTruncate = variant === "compact" && caption.length > maxCaptionLength;
5258
5258
  // Get aspect ratio based on postAspectRatio prop
@@ -5334,7 +5334,7 @@ var Textarea = function (_a) {
5334
5334
  };
5335
5335
 
5336
5336
  // Traducciones por defecto en español según las reglas de diseño
5337
- var defaultTranslations$2 = {
5337
+ var defaultTranslations$3 = {
5338
5338
  lightTheme: "Claro",
5339
5339
  darkTheme: "Oscuro",
5340
5340
  };
@@ -5350,7 +5350,7 @@ var defaultTranslations$2 = {
5350
5350
  var ThemePicker = function (_a) {
5351
5351
  var value = _a.value, onChange = _a.onChange, className = _a.className, _b = _a.translations, translations = _b === void 0 ? {} : _b;
5352
5352
  // Combinar traducciones por defecto con las proporcionadas
5353
- var t = __assign(__assign({}, defaultTranslations$2), translations);
5353
+ var t = __assign(__assign({}, defaultTranslations$3), translations);
5354
5354
  var themes = [
5355
5355
  {
5356
5356
  key: "light",
@@ -5779,7 +5779,7 @@ var TwoColumnLayoutAgent = function (_a) {
5779
5779
  };
5780
5780
 
5781
5781
  // Traducciones por defecto en español
5782
- var defaultTranslations$1 = {
5782
+ var defaultTranslations$2 = {
5783
5783
  uploadText: "Da clic y selecciona tus archivos",
5784
5784
  subText: "",
5785
5785
  dragText: "Suelta el archivo aquí",
@@ -6129,7 +6129,7 @@ var UploadFile = function (_a) {
6129
6129
  var _q = useState(""), selectedImageUrl = _q[0], setSelectedImageUrl = _q[1];
6130
6130
  var _r = useState(null); _r[0]; var setOriginalFile = _r[1];
6131
6131
  // Combinar traducciones por defecto con las proporcionadas
6132
- var t = useMemo(function () { return (__assign(__assign({}, defaultTranslations$1), translations)); }, [translations]);
6132
+ var t = useMemo(function () { return (__assign(__assign({}, defaultTranslations$2), translations)); }, [translations]);
6133
6133
  // Actualizar texto si se pasa como prop (retrocompatibilidad)
6134
6134
  var finalText = text || t.uploadText;
6135
6135
  var finalSubText = subText || t.subText;
@@ -6315,6 +6315,185 @@ var UploadFile = function (_a) {
6315
6315
  };
6316
6316
  UploadFile.displayName = "UploadFile";
6317
6317
 
6318
+ /**
6319
+ * Jitter pseudo-aleatorio determinista en [0,1), sembrado SOLO por el índice.
6320
+ * Misma constante Knuth (2654435761) que `computeStripJitter`/`computeBoxJitter`
6321
+ * de beweanalytics — nunca `Math.random()`.
6322
+ */
6323
+ function jitter(index) {
6324
+ return ((index * 2654435761) % 1000) / 1000;
6325
+ }
6326
+ /**
6327
+ * Cuartiles por interpolación lineal (R-7, el default de numpy/Excel).
6328
+ * Espeja `computeQuartiles` de beweanalytics para coherencia entre repos.
6329
+ */
6330
+ function computeQuartilesFromRaw(values) {
6331
+ if (values.length === 0) {
6332
+ return { min: 0, q1: 0, median: 0, q3: 0, max: 0 };
6333
+ }
6334
+ var sorted = __spreadArray([], values, true).sort(function (a, b) { return a - b; });
6335
+ var n = sorted.length;
6336
+ var first = sorted[0];
6337
+ var last = sorted[n - 1];
6338
+ var percentile = function (p) {
6339
+ if (n === 1) {
6340
+ return first;
6341
+ }
6342
+ var h = (n - 1) * p;
6343
+ var lo = Math.floor(h);
6344
+ var hi = Math.ceil(h);
6345
+ var loVal = sorted[lo];
6346
+ if (lo === hi) {
6347
+ return loVal;
6348
+ }
6349
+ var hiVal = sorted[hi];
6350
+ return loVal + (h - lo) * (hiVal - loVal);
6351
+ };
6352
+ return {
6353
+ min: first,
6354
+ q1: percentile(0.25),
6355
+ median: percentile(0.5),
6356
+ q3: percentile(0.75),
6357
+ max: last,
6358
+ };
6359
+ }
6360
+ /** Un grupo cae al fallback si tiene pocos datos o trae valores crudos. */
6361
+ function shouldFallback(group, minN) {
6362
+ var _a, _b;
6363
+ return group.n < minN || ((_b = (_a = group.rawValues) === null || _a === void 0 ? void 0 : _a.length) !== null && _b !== void 0 ? _b : 0) > 0;
6364
+ }
6365
+ var TO_SECONDS = {
6366
+ s: 1,
6367
+ min: 60,
6368
+ h: 3600,
6369
+ d: 86400,
6370
+ };
6371
+ /**
6372
+ * Elige la unidad de display (s/min/h/d) más legible para un valor de
6373
+ * referencia (típicamente la mediana) y devuelve el `factor` por el que
6374
+ * multiplicar los valores en `baseUnit` para obtener la unidad elegida.
6375
+ */
6376
+ function pickDisplayUnit(value, base) {
6377
+ if (base === "none") {
6378
+ return { unit: "", factor: 1 };
6379
+ }
6380
+ var seconds = Math.abs(value) * TO_SECONDS[base];
6381
+ var unit = "s";
6382
+ if (seconds >= TO_SECONDS.d) {
6383
+ unit = "d";
6384
+ }
6385
+ else if (seconds >= TO_SECONDS.h) {
6386
+ unit = "h";
6387
+ }
6388
+ else if (seconds >= TO_SECONDS.min) {
6389
+ unit = "min";
6390
+ }
6391
+ return { unit: unit, factor: TO_SECONDS[base] / TO_SECONDS[unit] };
6392
+ }
6393
+ /**
6394
+ * Path SVG del cuerpo del violin: polígono cerrado y espejado sobre `centerX`.
6395
+ * El ancho de cada bin es proporcional a su count (normalizado al bin máximo)
6396
+ * escalado a `halfWidth` px. `valueToY` mapea el valor medio del bin a la Y en px.
6397
+ */
6398
+ function buildDensityPath(bins, centerX, halfWidth, valueToY) {
6399
+ if (bins.length === 0) {
6400
+ return "";
6401
+ }
6402
+ var maxCount = Math.max.apply(Math, __spreadArray(__spreadArray([], bins.map(function (b) { return b.count; }), false), [1], false));
6403
+ var pts = bins.map(function (b) {
6404
+ var mid = (b.x0 + b.x1) / 2;
6405
+ return { y: valueToY(mid), w: (b.count / maxCount) * halfWidth };
6406
+ });
6407
+ var right = pts.map(function (p) { return "".concat(centerX + p.w, ",").concat(p.y); });
6408
+ var left = __spreadArray([], pts, true).reverse().map(function (p) { return "".concat(centerX - p.w, ",").concat(p.y); });
6409
+ return "M ".concat(right.join(" L "), " L ").concat(left.join(" L "), " Z");
6410
+ }
6411
+
6412
+ var COLOR_STROKE$1 = "#4338ca";
6413
+ var COLOR_MEDIAN$1 = "#1e3a8a";
6414
+ var COLOR_POINT = "#6366f1";
6415
+ var BOX_HALF = 10;
6416
+ var JITTER_SPAN = 22;
6417
+ /**
6418
+ * Fallback para grupos con n<20: caja (q1–q3) + mediana + puntos crudos con
6419
+ * jitter horizontal determinista. Un violin de 8 puntos miente; aquí se ve cada
6420
+ * punto real (caso Guru). Si faltan `rawValues`, cae a caja desde percentiles.
6421
+ */
6422
+ function ViolinFallback(_a) {
6423
+ var _b;
6424
+ var group = _a.group, centerX = _a.centerX, valueToY = _a.valueToY;
6425
+ var raw = (_b = group.rawValues) !== null && _b !== void 0 ? _b : [];
6426
+ var q = raw.length > 0
6427
+ ? computeQuartilesFromRaw(raw)
6428
+ : {
6429
+ min: group.p5,
6430
+ q1: group.p25,
6431
+ median: group.p50,
6432
+ q3: group.p75,
6433
+ max: group.p95,
6434
+ };
6435
+ return (jsxs("g", { children: [jsx("line", { x1: centerX, x2: centerX, y1: valueToY(q.min), y2: valueToY(q.max), stroke: COLOR_STROKE$1, strokeWidth: 1 }), jsx("rect", { x: centerX - BOX_HALF, y: valueToY(q.q3), width: BOX_HALF * 2, height: Math.max(0, valueToY(q.q1) - valueToY(q.q3)), fill: COLOR_STROKE$1, fillOpacity: 0.18, stroke: COLOR_STROKE$1 }), jsx("line", { x1: centerX - BOX_HALF, x2: centerX + BOX_HALF, y1: valueToY(q.median), y2: valueToY(q.median), stroke: COLOR_MEDIAN$1, strokeWidth: 2 }), raw.map(function (value, idx) { return (jsx("circle", { cx: centerX + (jitter(idx) - 0.5) * JITTER_SPAN, cy: valueToY(value), r: 2.5, fill: COLOR_POINT, fillOpacity: 0.8 }, "".concat(value, "-").concat(idx))); })] }));
6436
+ }
6437
+
6438
+ var MARGIN = { top: 24, right: 16, bottom: 40, left: 44 };
6439
+ var VIEW_WIDTH = 640;
6440
+ var VIOLIN_HALF_WIDTH = 46;
6441
+ var COLOR_BODY = "#c7d2fe";
6442
+ var COLOR_STROKE = "#4338ca";
6443
+ var COLOR_MEDIAN = "#1e3a8a";
6444
+ var COLOR_AXIS = "#6b7280";
6445
+ var defaultTranslations$1 = {
6446
+ emptyState: "Sin datos de distribución",
6447
+ sampleSizeLabel: "n",
6448
+ outliersLabel: "outliers",
6449
+ };
6450
+ function formatTick(value, factor, unit) {
6451
+ var scaled = value * factor;
6452
+ var rounded = Math.round(scaled * 10) / 10;
6453
+ return unit ? "".concat(rounded).concat(unit) : "".concat(rounded);
6454
+ }
6455
+ /**
6456
+ * ViolinPlot — distribución por grupo como densidad espejada (SVG puro), con
6457
+ * mediana/cuartiles superpuestos y `n=` visible. Cuando un grupo tiene n<20 (o
6458
+ * trae `rawValues`) degrada a box/strip (`ViolinFallback`): un violin de pocos
6459
+ * puntos miente. La estadística llega pre-calculada del SQL (payload chico).
6460
+ *
6461
+ * Sin `ResponsiveContainer` (no renderiza en happy-dom y complica el test):
6462
+ * `<svg viewBox>` + `width="100%"`. Autocontenido, sin HeroUI, para render
6463
+ * server-side directo en tests.
6464
+ */
6465
+ function ViolinPlot(_a) {
6466
+ var groups = _a.groups, valueLabel = _a.valueLabel, _b = _a.baseUnit, baseUnit = _b === void 0 ? "none" : _b, formatValue = _a.formatValue, _c = _a.height, height = _c === void 0 ? 320 : _c, _d = _a.minSampleForViolin, minSampleForViolin = _d === void 0 ? 20 : _d, _e = _a.translations, translations = _e === void 0 ? {} : _e;
6467
+ var t = __assign(__assign({}, defaultTranslations$1), translations);
6468
+ if (groups.length === 0) {
6469
+ return (jsx("svg", { viewBox: "0 0 ".concat(VIEW_WIDTH, " ").concat(height), width: "100%", role: "img", "aria-label": valueLabel, children: jsx("text", { x: VIEW_WIDTH / 2, y: height / 2, textAnchor: "middle", fill: COLOR_AXIS, children: t.emptyState }) }));
6470
+ }
6471
+ var plotTop = MARGIN.top;
6472
+ var plotBottom = height - MARGIN.bottom;
6473
+ var plotHeight = plotBottom - plotTop;
6474
+ // Escala Y común a todos los grupos (de 0 al p95 máximo, con margen).
6475
+ var maxValue = Math.max.apply(Math, __spreadArray(__spreadArray([], groups.map(function (g) { return g.p95; }), false), [1], false));
6476
+ var valueToY = function (v) {
6477
+ return plotBottom - (v / maxValue) * plotHeight;
6478
+ };
6479
+ var refMedian = groups.map(function (g) { return g.p50; }).sort(function (a, b) { return a - b; })[Math.floor(groups.length / 2)];
6480
+ var _f = pickDisplayUnit(refMedian, baseUnit), unit = _f.unit, factor = _f.factor;
6481
+ var fmt = formatValue !== null && formatValue !== void 0 ? formatValue : (function (v) { return formatTick(v, factor, unit); });
6482
+ var columnWidth = (VIEW_WIDTH - MARGIN.left - MARGIN.right) / groups.length;
6483
+ return (jsxs("svg", { viewBox: "0 0 ".concat(VIEW_WIDTH, " ").concat(height), width: "100%", role: "img", "aria-label": valueLabel, children: [[0, maxValue / 2, maxValue].map(function (v) { return (jsxs("g", { children: [jsx("line", { x1: MARGIN.left, x2: VIEW_WIDTH - MARGIN.right, y1: valueToY(v), y2: valueToY(v), stroke: "#e5e7eb", strokeDasharray: "3 3" }), jsx("text", { x: MARGIN.left - 6, y: valueToY(v) + 4, textAnchor: "end", fontSize: 11, fill: COLOR_AXIS, children: fmt(v) })] }, v)); }), groups.map(function (group, i) {
6484
+ var centerX = MARGIN.left + columnWidth * (i + 0.5);
6485
+ return (jsxs("g", { children: [shouldFallback(group, minSampleForViolin) ? (jsx(ViolinFallback, { group: group, centerX: centerX, valueToY: valueToY })) : (jsx(ViolinBody, { group: group, centerX: centerX, valueToY: valueToY })), jsx("text", { x: centerX, y: plotBottom + 16, textAnchor: "middle", fontSize: 12, fill: COLOR_AXIS, children: group.label }), jsxs("text", { x: centerX, y: plotBottom + 30, textAnchor: "middle", fontSize: 10, fill: COLOR_AXIS, children: [t.sampleSizeLabel, "=", group.n, group.nExcluded > 0
6486
+ ? " \u00B7 \u2212".concat(group.nExcluded, " ").concat(t.outliersLabel)
6487
+ : ""] })] }, group.label));
6488
+ })] }));
6489
+ }
6490
+ function ViolinBody(_a) {
6491
+ var group = _a.group, centerX = _a.centerX, valueToY = _a.valueToY;
6492
+ var path = buildDensityPath(group.bins, centerX, VIOLIN_HALF_WIDTH, valueToY);
6493
+ var boxHalf = 8;
6494
+ return (jsxs("g", { children: [jsx("path", { d: path, fill: COLOR_BODY, fillOpacity: 0.55, stroke: COLOR_STROKE, strokeWidth: 1 }), jsx("line", { x1: centerX, x2: centerX, y1: valueToY(group.p5), y2: valueToY(group.p95), stroke: COLOR_MEDIAN, strokeWidth: 1 }), jsx("rect", { x: centerX - boxHalf, y: valueToY(group.p75), width: boxHalf * 2, height: Math.max(0, valueToY(group.p25) - valueToY(group.p75)), fill: COLOR_STROKE, fillOpacity: 0.25, stroke: COLOR_STROKE }), jsx("line", { x1: centerX - boxHalf, x2: centerX + boxHalf, y1: valueToY(group.p50), y2: valueToY(group.p50), stroke: COLOR_MEDIAN, strokeWidth: 2 })] }));
6495
+ }
6496
+
6318
6497
  function resolvePreviewActions(previewAction, ctaType, ctaLabel, ctaValue) {
6319
6498
  var _a;
6320
6499
  var fromProp = (_a = previewAction === null || previewAction === void 0 ? void 0 : previewAction.filter(function (a) {
@@ -8159,11 +8338,13 @@ var SegmentationBuilder = forwardRef(function (_a, ref) {
8159
8338
  SegmentationBuilder.displayName = "SegmentationBuilder";
8160
8339
 
8161
8340
  var SENTINEL_KEY = "__tags-filter-sentinel__";
8341
+ var EMPTY_KEY = "__tags-filter-empty__";
8162
8342
  var DEFAULT_TRANSLATIONS = {
8163
8343
  placeholder: "Nombre de la etiqueta",
8164
8344
  labelSelect: "Selecciona etiqueta",
8165
8345
  labelSelected: "Etiquetas actuales",
8166
8346
  emptySelectedMessage: "No hay etiquetas seleccionadas",
8347
+ emptyAvailableMessage: "No hay etiquetas disponibles",
8167
8348
  errorLoadingPrefix: "Error al cargar etiquetas",
8168
8349
  loadingMoreLabel: "Cargando más etiquetas…",
8169
8350
  endOfListMessage: "",
@@ -8230,9 +8411,26 @@ function TagsFilter(_a) {
8230
8411
  });
8231
8412
  }, [items, inputValue, compareTags, onInputChange]);
8232
8413
  var filteredItems = getFilteredAvailable(selectedList);
8233
- var showSentinel = Boolean(onLoadMore) && (hasMore || Boolean(t.endOfListMessage));
8234
- var itemsWithSentinel = showSentinel
8235
- ? __spreadArray(__spreadArray([], filteredItems, true), [{ id: SENTINEL_KEY, value: "" }], false) : filteredItems;
8414
+ // El sentinel es quien monta el IntersectionObserver, así que tiene que
8415
+ // seguir en la colección mientras quede algo por traer o haya una carga en
8416
+ // curso: sin él, `onLoadMore` no se vuelve a disparar nunca.
8417
+ var showSentinel = Boolean(onLoadMore) &&
8418
+ (hasMore || isLoadingMore || Boolean(t.endOfListMessage));
8419
+ var isAvailableEmpty = filteredItems.length === 0;
8420
+ // Sin nada que ofrecer se inyecta un item de solo lectura con el mensaje de
8421
+ // vacío: así el desplegable explica por qué está vacío en vez de no abrirse
8422
+ // (o abrirse en blanco), y la colección nunca queda realmente vacía.
8423
+ //
8424
+ // Es el último recurso, no el primero: si aún hay páginas por cargar o una
8425
+ // petición en vuelo, gana el sentinel. De lo contrario bastaría con que la
8426
+ // página cargada no tuviera coincidencias (o con seleccionar todas sus
8427
+ // etiquetas) para anunciar "no hay etiquetas" y cortar la paginación.
8428
+ var canPaginate = Boolean(onLoadMore) && hasMore;
8429
+ var showEmptyItem = isAvailableEmpty && !canPaginate && !isLoadingMore;
8430
+ var itemsWithSentinel = showEmptyItem
8431
+ ? [{ id: EMPTY_KEY, value: "" }]
8432
+ : showSentinel
8433
+ ? __spreadArray(__spreadArray([], filteredItems, true), [{ id: SENTINEL_KEY, value: "" }], false) : filteredItems;
8236
8434
  var handleAutocompleteSelection = useCallback(function (key) {
8237
8435
  if (key == null) {
8238
8436
  return;
@@ -8251,9 +8449,16 @@ function TagsFilter(_a) {
8251
8449
  setInputValue(v);
8252
8450
  onInputChange === null || onInputChange === void 0 ? void 0 : onInputChange(v);
8253
8451
  }, selectedKey: null, items: itemsWithSentinel, onSelectionChange: handleAutocompleteSelection,
8254
- // "focus" keeps the menu tied to focus; prefer opening when typing.
8255
- menuTrigger: "input",
8256
- // When the filtered list is empty, avoid keeping an open overlay that blocks the modal.
8452
+ // El item de vacío no es seleccionable ni navegable con teclado:
8453
+ // es un mensaje, no una opción.
8454
+ disabledKeys: [EMPTY_KEY],
8455
+ // TECH-1640: el desplegable abre al enfocar/hacer clic, no solo al
8456
+ // escribir. Un selector de etiquetas debe enseñar lo que hay sin
8457
+ // exigir que el usuario recuerde el nombre.
8458
+ menuTrigger: "focus",
8459
+ // Salvo carga en curso, la colección siempre trae algo que mostrar
8460
+ // (ver `itemsWithSentinel`). Se mantiene el flag para que un hueco
8461
+ // transitorio no abra un overlay vacío sobre el modal padre.
8257
8462
  allowsEmptyCollection: false, shouldCloseOnBlur: true, popoverProps: {
8258
8463
  // isNonModal: false would render a full-screen invisible backdrop that
8259
8464
  // intercepts pointer events, blocking the parent modal's close button.
@@ -8264,6 +8469,9 @@ function TagsFilter(_a) {
8264
8469
  className: "max-h-[200px] overflow-y-auto",
8265
8470
  }, className: "w-full", children: function (item) {
8266
8471
  var candidate = item;
8472
+ if (candidate.id === EMPTY_KEY) {
8473
+ return (jsx(AutocompleteItem, { textValue: t.emptyAvailableMessage, isReadOnly: true, className: "opacity-100 cursor-default data-[hover=true]:bg-transparent", children: jsx("span", { className: "text-tiny text-default-500", children: t.emptyAvailableMessage }) }, EMPTY_KEY));
8474
+ }
8267
8475
  if (candidate.id === SENTINEL_KEY) {
8268
8476
  return (jsx(AutocompleteItem, { textValue: "", isReadOnly: true, className: "opacity-100 cursor-default data-[hover=true]:bg-transparent", children: jsx("div", { ref: function (node) {
8269
8477
  var _a;
@@ -9022,4 +9230,4 @@ var NavigationLoadingProvider = function (_a) {
9022
9230
  return (jsxs(NavigationLoadingContext.Provider, { value: value, children: [children, jsx(NavigationLoadingOverlay, { isVisible: isVisible })] }));
9023
9231
  };
9024
9232
 
9025
- export { ALL_THEMES, AURORA_THEME_FAMILIES, AURORA_THEME_REGISTRY, AccordionList, AddHolidayForm, AnalyticsCard, AreaLineChart, AuraAutocomplete, AuraTable, AuraToastProvider, BEWEOS_THEME_MODE_COOKIE_NAME, BreadcrumbsComponent, Button, Card, Chip, ColorPicker, ColorSelector, ContentCarousel, Currency, DEFAULT_PREDEFINED_COLORS, DatePicker, DateRangePicker, DateSelector, DrawerFilters, EmailPreview, EnumMenuNavListItem, GlobalToast, H1, H2, H3, H4, HeaderComponent, HolidayType, IconComponent, ImagePreview, Input, InputPassword, Kanban, KanbanCard, KanbanColumn, MenuComponent, Modal, ModalBody, ModalContent, ModalFooter, ModalHeader, MultiStepWizard, NavigationLoadingContext, NavigationLoadingOverlay, NavigationLoadingProvider, P, Pagination, Phone, PromotionalBanner, REGISTERED_THEME_COLORS, RangeFilter, RowSteps, DEFAULT_TRANSLATIONS$1 as SEGMENTATION_DEFAULT_TRANSLATIONS, ScheduleRow, SearchInput, SegmentationBuilder, Select, SimpleLineChart, SocialMediaBar, SocialMediaCarousel, SocialMediaPreview, StepIndicator, Switch as SwitchComponent, THEME_COLOR_HEX_MAP, TagsFilter, Textarea, ThemeContext, ThemePicker, ThemeProvider, TimeInput as TimeInputComponent, ToastContext, Tooltip, TwoColumnLayoutAgent, UploadFile, VerticalSteps, WhatsAppPreview, Wizard, WizardNavigation, WizardSidebar, applyCustomPrimaryColor, createCurrencyFormatter, uniqueCountries as defaultCountries, defaultCurrencyOptions, defaultTranslations$4 as defaultTranslations, forceLightOnlyThemeBeforeReact, formatAuroraThemeTooltip, generateThemeColorScale, getContrastForeground, getRegisteredThemeColorBases, getSelectedKeyFromPath, hexToThemeColor, hslToCssValue, isAuroraFullThemeId, isExactThemeColor, isGroupState, isHexColor, isSegmentationGroup, removeCustomPrimaryColor, sizeMap, themeColors, useAuraToast, useCloseOnAncestorScroll, useMediaQuery, useNavigationLoading, useThemeContext };
9233
+ export { ALL_THEMES, AURORA_THEME_FAMILIES, AURORA_THEME_REGISTRY, AccordionList, AddHolidayForm, AnalyticsCard, AreaLineChart, AuraAutocomplete, AuraTable, AuraToastProvider, BEWEOS_THEME_MODE_COOKIE_NAME, BreadcrumbsComponent, Button, Card, Chip, ColorPicker, ColorSelector, ContentCarousel, Currency, DEFAULT_PREDEFINED_COLORS, DatePicker, DateRangePicker, DateSelector, DrawerFilters, EmailPreview, EnumMenuNavListItem, GlobalToast, H1, H2, H3, H4, HeaderComponent, HolidayType, IconComponent, ImagePreview, Input, InputPassword, Kanban, KanbanCard, KanbanColumn, MenuComponent, Modal, ModalBody, ModalContent, ModalFooter, ModalHeader, MultiStepWizard, NavigationLoadingContext, NavigationLoadingOverlay, NavigationLoadingProvider, P, Pagination, Phone, PromotionalBanner, REGISTERED_THEME_COLORS, RangeFilter, RowSteps, DEFAULT_TRANSLATIONS$1 as SEGMENTATION_DEFAULT_TRANSLATIONS, ScheduleRow, SearchInput, SegmentationBuilder, Select, SimpleLineChart, SocialMediaBar, SocialMediaCarousel, SocialMediaPreview, StepIndicator, Switch as SwitchComponent, THEME_COLOR_HEX_MAP, TagsFilter, Textarea, ThemeContext, ThemePicker, ThemeProvider, TimeInput as TimeInputComponent, ToastContext, Tooltip, TwoColumnLayoutAgent, UploadFile, VerticalSteps, ViolinPlot, WhatsAppPreview, Wizard, WizardNavigation, WizardSidebar, applyCustomPrimaryColor, createCurrencyFormatter, uniqueCountries as defaultCountries, defaultCurrencyOptions, defaultTranslations$5 as defaultTranslations, forceLightOnlyThemeBeforeReact, formatAuroraThemeTooltip, generateThemeColorScale, getContrastForeground, getRegisteredThemeColorBases, getSelectedKeyFromPath, hexToThemeColor, hslToCssValue, isAuroraFullThemeId, isExactThemeColor, isGroupState, isHexColor, isSegmentationGroup, removeCustomPrimaryColor, sizeMap, themeColors, useAuraToast, useCloseOnAncestorScroll, useMediaQuery, useNavigationLoading, useThemeContext };
@@ -1 +1 @@
1
- {"version":3,"file":"TagsFilter.d.ts","sourceRoot":"","sources":["../../../../src/components/tags-filter/TagsFilter.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAM/B,OAAO,KAAK,EACX,eAAe,EAEf,MAAM,oBAAoB,CAAC;AAqC5B;;;;;GAKG;AACH,wBAAgB,UAAU,CAAC,CAAC,SAAS;IAAE,EAAE,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,EAAE,EACpE,KAAK,EACL,KAAK,EACL,QAAQ,EACR,YAAiB,EACjB,KAAK,EACL,SAAiB,EACjB,SAAc,EACd,YAAY,EAAE,SAAS,EACvB,QAAgB,EAChB,WAA2D,EAC3D,SAAkD,EAClD,aAAa,EACb,OAAe,EACf,aAAqB,EACrB,UAAU,EACV,kBAA0B,GAC1B,EAAE,eAAe,CAAC,CAAC,CAAC,GAAG,KAAK,CAAC,YAAY,CA0MzC;yBA3Ne,UAAU"}
1
+ {"version":3,"file":"TagsFilter.d.ts","sourceRoot":"","sources":["../../../../src/components/tags-filter/TagsFilter.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAM/B,OAAO,KAAK,EACX,eAAe,EAEf,MAAM,oBAAoB,CAAC;AAuC5B;;;;;GAKG;AACH,wBAAgB,UAAU,CAAC,CAAC,SAAS;IAAE,EAAE,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,EAAE,EACpE,KAAK,EACL,KAAK,EACL,QAAQ,EACR,YAAiB,EACjB,KAAK,EACL,SAAiB,EACjB,SAAc,EACd,YAAY,EAAE,SAAS,EACvB,QAAgB,EAChB,WAA2D,EAC3D,SAAkD,EAClD,aAAa,EACb,OAAe,EACf,aAAqB,EACrB,UAAU,EACV,kBAA0B,GAC1B,EAAE,eAAe,CAAC,CAAC,CAAC,GAAG,KAAK,CAAC,YAAY,CAiPzC;yBAlQe,UAAU"}
@@ -20,6 +20,12 @@ export type TagsFilterTranslations = {
20
20
  labelSelected?: string;
21
21
  /** Mensaje cuando no hay etiquetas seleccionadas */
22
22
  emptySelectedMessage?: string;
23
+ /**
24
+ * Mensaje dentro del desplegable cuando no queda ninguna etiqueta que
25
+ * ofrecer (el centro no tiene etiquetas, ya están todas asignadas o la
26
+ * búsqueda no encontró nada).
27
+ */
28
+ emptyAvailableMessage?: string;
23
29
  /** Prefijo del mensaje de error (ej. "Error al cargar etiquetas") */
24
30
  errorLoadingPrefix?: string;
25
31
  /** Texto sr-only del spinner inline mientras se cargan más páginas. */
@@ -1 +1 @@
1
- {"version":3,"file":"TagsFilter.types.d.ts","sourceRoot":"","sources":["../../../../src/components/tags-filter/TagsFilter.types.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,MAAM,WAAW,OAAO;IACvB,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,KAAK,EAAE,MAAM,CAAC;IACd,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACvB;AAED;;;GAGG;AACH,MAAM,MAAM,sBAAsB,GAAG;IACpC,kDAAkD;IAClD,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,iEAAiE;IACjE,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,wEAAwE;IACxE,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,oDAAoD;IACpD,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B,qEAAqE;IACrE,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,uEAAuE;IACvE,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,sFAAsF;IACtF,gBAAgB,CAAC,EAAE,MAAM,CAAC;CAC1B,CAAC;AAEF,MAAM,WAAW,eAAe,CAAC,CAAC,SAAS,OAAO,GAAG,OAAO;IAC3D,qDAAqD;IACrD,KAAK,EAAE,CAAC,EAAE,CAAC;IACX,0CAA0C;IAC1C,KAAK,EAAE,CAAC,EAAE,CAAC;IACX,2DAA2D;IAC3D,QAAQ,EAAE,CAAC,QAAQ,EAAE,CAAC,EAAE,KAAK,IAAI,CAAC;IAClC,uFAAuF;IACvF,YAAY,CAAC,EAAE,sBAAsB,CAAC;IACtC,sDAAsD;IACtD,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,+BAA+B;IAC/B,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,oCAAoC;IACpC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,kCAAkC;IAClC,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,2GAA2G;IAC3G,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,wEAAwE;IACxE,WAAW,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,KAAK,OAAO,CAAC;IACtC,kFAAkF;IAClF,SAAS,CAAC,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,MAAM,CAAC;IAC/B;;;;;;;;OAQG;IACH,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACxC,uEAAuE;IACvE,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,8EAA8E;IAC9E,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,mIAAmI;IACnI,UAAU,CAAC,EAAE,MAAM,IAAI,CAAC;IACxB,qEAAqE;IACrE,kBAAkB,CAAC,EAAE,MAAM,CAAC;CAC5B"}
1
+ {"version":3,"file":"TagsFilter.types.d.ts","sourceRoot":"","sources":["../../../../src/components/tags-filter/TagsFilter.types.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,MAAM,WAAW,OAAO;IACvB,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,KAAK,EAAE,MAAM,CAAC;IACd,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACvB;AAED;;;GAGG;AACH,MAAM,MAAM,sBAAsB,GAAG;IACpC,kDAAkD;IAClD,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,iEAAiE;IACjE,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,wEAAwE;IACxE,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,oDAAoD;IACpD,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B;;;;OAIG;IACH,qBAAqB,CAAC,EAAE,MAAM,CAAC;IAC/B,qEAAqE;IACrE,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,uEAAuE;IACvE,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,sFAAsF;IACtF,gBAAgB,CAAC,EAAE,MAAM,CAAC;CAC1B,CAAC;AAEF,MAAM,WAAW,eAAe,CAAC,CAAC,SAAS,OAAO,GAAG,OAAO;IAC3D,qDAAqD;IACrD,KAAK,EAAE,CAAC,EAAE,CAAC;IACX,0CAA0C;IAC1C,KAAK,EAAE,CAAC,EAAE,CAAC;IACX,2DAA2D;IAC3D,QAAQ,EAAE,CAAC,QAAQ,EAAE,CAAC,EAAE,KAAK,IAAI,CAAC;IAClC,uFAAuF;IACvF,YAAY,CAAC,EAAE,sBAAsB,CAAC;IACtC,sDAAsD;IACtD,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,+BAA+B;IAC/B,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,oCAAoC;IACpC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,kCAAkC;IAClC,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,2GAA2G;IAC3G,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,wEAAwE;IACxE,WAAW,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,KAAK,OAAO,CAAC;IACtC,kFAAkF;IAClF,SAAS,CAAC,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,MAAM,CAAC;IAC/B;;;;;;;;OAQG;IACH,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACxC,uEAAuE;IACvE,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,8EAA8E;IAC9E,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,mIAAmI;IACnI,UAAU,CAAC,EAAE,MAAM,IAAI,CAAC;IACxB,qEAAqE;IACrE,kBAAkB,CAAC,EAAE,MAAM,CAAC;CAC5B"}
@@ -0,0 +1,12 @@
1
+ import type { ViolinGroup } from "./ViolinPlot.types";
2
+ /**
3
+ * Fallback para grupos con n<20: caja (q1–q3) + mediana + puntos crudos con
4
+ * jitter horizontal determinista. Un violin de 8 puntos miente; aquí se ve cada
5
+ * punto real (caso Guru). Si faltan `rawValues`, cae a caja desde percentiles.
6
+ */
7
+ export declare function ViolinFallback({ group, centerX, valueToY, }: {
8
+ group: ViolinGroup;
9
+ centerX: number;
10
+ valueToY: (v: number) => number;
11
+ }): import("react/jsx-runtime").JSX.Element;
12
+ //# sourceMappingURL=ViolinFallback.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ViolinFallback.d.ts","sourceRoot":"","sources":["../../../../src/components/violin-plot/ViolinFallback.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAStD;;;;GAIG;AACH,wBAAgB,cAAc,CAAC,EAC9B,KAAK,EACL,OAAO,EACP,QAAQ,GACR,EAAE;IACF,KAAK,EAAE,WAAW,CAAC;IACnB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,CAAC,CAAC,EAAE,MAAM,KAAK,MAAM,CAAC;CAChC,2CAyDA"}
@@ -0,0 +1,14 @@
1
+ import type { ViolinPlotProps } from "./ViolinPlot.types";
2
+ /**
3
+ * ViolinPlot — distribución por grupo como densidad espejada (SVG puro), con
4
+ * mediana/cuartiles superpuestos y `n=` visible. Cuando un grupo tiene n<20 (o
5
+ * trae `rawValues`) degrada a box/strip (`ViolinFallback`): un violin de pocos
6
+ * puntos miente. La estadística llega pre-calculada del SQL (payload chico).
7
+ *
8
+ * Sin `ResponsiveContainer` (no renderiza en happy-dom y complica el test):
9
+ * `<svg viewBox>` + `width="100%"`. Autocontenido, sin HeroUI, para render
10
+ * server-side directo en tests.
11
+ */
12
+ export declare function ViolinPlot({ groups, valueLabel, baseUnit, formatValue, height, minSampleForViolin, translations, }: ViolinPlotProps): import("react/jsx-runtime").JSX.Element;
13
+ export default ViolinPlot;
14
+ //# sourceMappingURL=ViolinPlot.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ViolinPlot.d.ts","sourceRoot":"","sources":["../../../../src/components/violin-plot/ViolinPlot.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAEX,eAAe,EAEf,MAAM,oBAAoB,CAAC;AA2B5B;;;;;;;;;GASG;AACH,wBAAgB,UAAU,CAAC,EAC1B,MAAM,EACN,UAAU,EACV,QAAiB,EACjB,WAAW,EACX,MAAY,EACZ,kBAAuB,EACvB,YAAiB,GACjB,EAAE,eAAe,2CA4GjB;AA2DD,eAAe,UAAU,CAAC"}