@xanui/ui 1.1.63 → 1.1.65

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/Alert/index.cjs CHANGED
@@ -12,7 +12,8 @@ var SuccessIcon = require('@xanui/icons/CheckCircle');
12
12
  var ErrorIcon = require('@xanui/icons/Cancel');
13
13
  var Close = require('@xanui/icons/Close');
14
14
  var index = require('../IconButton/index.cjs');
15
- var index$2 = require('../useAlert/index.cjs');
15
+ var index$2 = require('../Modal/index.cjs');
16
+ var index$3 = require('../Button/index.cjs');
16
17
 
17
18
  const Alert = (_a) => {
18
19
  var { children } = _a, rest = tslib.__rest(_a, ["children"]);
@@ -82,37 +83,99 @@ const Alert = (_a) => {
82
83
  font: "button",
83
84
  }, children: children })] })] })] })));
84
85
  };
85
- const ActionAlert = (props) => {
86
- var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k;
87
- const ref = React.useRef(null);
88
- const alert = index$2(Object.assign(Object.assign({}, props), { slotProps: Object.assign(Object.assign({}, props.slotProps), { modal: Object.assign(Object.assign({}, (_a = props.slotProps) === null || _a === void 0 ? void 0 : _a.modal), { slotProps: Object.assign(Object.assign({}, (_c = (_b = props.slotProps) === null || _b === void 0 ? void 0 : _b.modal) === null || _c === void 0 ? void 0 : _c.slotProps), { layer: Object.assign(Object.assign({}, (_f = (_e = (_d = props.slotProps) === null || _d === void 0 ? void 0 : _d.modal) === null || _e === void 0 ? void 0 : _e.slotProps) === null || _f === void 0 ? void 0 : _f.layer), { portal: Object.assign(Object.assign({}, (_k = (_j = (_h = (_g = props.slotProps) === null || _g === void 0 ? void 0 : _g.modal) === null || _h === void 0 ? void 0 : _h.slotProps) === null || _j === void 0 ? void 0 : _j.layer) === null || _k === void 0 ? void 0 : _k.portal), { container: ref.current || undefined }) }) }) }) }) }));
89
- React.useEffect(() => {
90
- if (props.open) {
91
- alert.open();
86
+ const ConfirmAlert = (props) => {
87
+ let { open, loading, content, size, color, direction, variant, closeButton, clickOutsideToClose, okButtonText, cancelButtonText, hideOkButton, hideCancelButton, buttonPlacement, onConfirm, onCancel, transition, blurMode, slotProps } = props, rest = tslib.__rest(props, ["open", "loading", "content", "size", "color", "direction", "variant", "closeButton", "clickOutsideToClose", "okButtonText", "cancelButtonText", "hideOkButton", "hideCancelButton", "buttonPlacement", "onConfirm", "onCancel", "transition", "blurMode", "slotProps"]);
88
+ hideOkButton !== null && hideOkButton !== void 0 ? hideOkButton : (hideOkButton = false);
89
+ hideCancelButton !== null && hideCancelButton !== void 0 ? hideCancelButton : (hideCancelButton = false);
90
+ size !== null && size !== void 0 ? size : (size = "small");
91
+ color !== null && color !== void 0 ? color : (color = 'default');
92
+ variant !== null && variant !== void 0 ? variant : (variant = "text");
93
+ direction !== null && direction !== void 0 ? direction : (direction = "column");
94
+ buttonPlacement !== null && buttonPlacement !== void 0 ? buttonPlacement : (buttonPlacement = "end");
95
+ let sx = {};
96
+ switch (buttonPlacement) {
97
+ case "start":
98
+ sx.justifyContent = 'flex-start';
99
+ break;
100
+ case "end":
101
+ sx.justifyContent = 'flex-end';
102
+ break;
103
+ case "between":
104
+ sx.justifyContent = 'space-between';
105
+ break;
106
+ case "full":
107
+ sx = {
108
+ "& button": {
109
+ flex: 1
110
+ }
111
+ };
112
+ break;
113
+ }
114
+ let sizes = {
115
+ small: 320,
116
+ medium: 400,
117
+ large: 600
118
+ };
119
+ let okcolor = color;
120
+ let closecolor = color;
121
+ if (color === 'default') {
122
+ okcolor = 'brand';
123
+ closecolor = 'default';
124
+ variant = 'text';
125
+ }
126
+ else {
127
+ if (variant === 'fill') {
128
+ okcolor = 'default';
129
+ closecolor = 'default';
92
130
  }
93
131
  else {
94
- alert.close();
132
+ okcolor = color;
133
+ closecolor = 'default';
95
134
  }
96
- }, [props.open]);
97
- return jsxRuntime.jsx(core.Tag, { ref: ref });
135
+ }
136
+ return (jsxRuntime.jsx(index$2, Object.assign({ open: open }, slotProps === null || slotProps === void 0 ? void 0 : slotProps.modal, { size: sizes[size] || size, blur: 40, blurMode: blurMode || "transparent", transition: transition || "zoom", onClickOutside: async () => {
137
+ if (clickOutsideToClose && !loading) {
138
+ onCancel && await onCancel();
139
+ }
140
+ }, children: jsxRuntime.jsxs(Alert, Object.assign({ direction: direction, sx: {
141
+ px: 2,
142
+ py: 1,
143
+ pt: direction === 'row' ? 1 : 2
144
+ }, color: color, variant: variant, onClose: closeButton ? close : undefined }, rest, { children: [content, jsxRuntime.jsxs(core.Tag, { sxr: Object.assign({ display: "flex", gap: 1, pt: 4, flexDirection: "row" }, sx), children: [!hideCancelButton && jsxRuntime.jsx(index$3, Object.assign({ disabled: loading, color: closecolor, variant: "fill" }, slotProps === null || slotProps === void 0 ? void 0 : slotProps.closeButton, { onClick: async () => {
145
+ onCancel && await onCancel();
146
+ }, children: cancelButtonText || "Close" })), jsxRuntime.jsx(index$3, Object.assign({ loading: loading, color: okcolor, variant: "fill" }, slotProps === null || slotProps === void 0 ? void 0 : slotProps.okButton, { onClick: async () => {
147
+ onConfirm && await onConfirm();
148
+ }, children: okButtonText || "OK" }))] })] })) })));
98
149
  };
99
- Alert.confirm = (props) => {
100
- var _a;
101
- const a = core.Renderar.render(ActionAlert, Object.assign(Object.assign({ open: true }, props), { slotProps: Object.assign(Object.assign({}, props.slotProps), { modal: Object.assign(Object.assign({}, (_a = props.slotProps) === null || _a === void 0 ? void 0 : _a.modal), { onClosed: () => {
150
+ Alert.confirm = (_a) => {
151
+ var _b;
152
+ var { onConfirm, onCancel } = _a, props = tslib.__rest(_a, ["onConfirm", "onCancel"]);
153
+ const confirm = core.Renderar.render(ConfirmAlert, Object.assign(Object.assign({}, props), { open: true, loading: false, onConfirm: async () => {
154
+ if (onConfirm) {
155
+ confirm.updateProps({ loading: true });
156
+ if (onConfirm)
157
+ await onConfirm();
158
+ confirm.updateProps({ open: false, loading: false });
159
+ }
160
+ else {
161
+ confirm.updateProps({ open: false });
162
+ }
163
+ }, onCancel: async () => {
164
+ if (onCancel) {
165
+ confirm.updateProps({ loading: true });
166
+ await onCancel();
167
+ confirm.updateProps({ open: false, loading: false });
168
+ }
169
+ else {
170
+ confirm.updateProps({ open: false });
171
+ }
172
+ }, slotProps: Object.assign(Object.assign({}, props.slotProps), { modal: Object.assign(Object.assign({}, (_b = props.slotProps) === null || _b === void 0 ? void 0 : _b.modal), { onClosed: () => {
102
173
  var _a, _b, _c, _d;
103
- a.unrender();
174
+ confirm.unrender();
104
175
  if ((_b = (_a = props === null || props === void 0 ? void 0 : props.slotProps) === null || _a === void 0 ? void 0 : _a.modal) === null || _b === void 0 ? void 0 : _b.onClosed) {
105
176
  (_d = (_c = props.slotProps) === null || _c === void 0 ? void 0 : _c.modal) === null || _d === void 0 ? void 0 : _d.onClosed();
106
177
  }
107
178
  } }) }) }));
108
- return {
109
- open: () => {
110
- a.updateProps({ open: true });
111
- },
112
- close: () => {
113
- a.updateProps({ open: false });
114
- },
115
- };
116
179
  };
117
180
 
118
181
  module.exports = Alert;
@@ -1 +1 @@
1
- {"version":3,"file":"index.cjs","sources":["../../src/Alert/index.tsx"],"sourcesContent":["\"use client\";\nimport { Tag, TagProps, useBreakpointProps, useColorTemplate, useInterface, useBreakpointPropsType, Renderar, UseColorTemplateType, UseColorTemplateColor } from \"@xanui/core\"\nimport React, { isValidElement, ReactElement, useEffect, useRef } from \"react\"\nimport Text from \"../Text\"\nimport InfoIcon from '@xanui/icons/Info';\nimport WarningIcon from '@xanui/icons/Warning';\nimport SuccessIcon from '@xanui/icons/CheckCircle';\nimport ErrorIcon from '@xanui/icons/Cancel';\nimport IconClose from '@xanui/icons/Close';\nimport IconButton from \"../IconButton\";\nimport useAlert, { UseAlerProps } from \"../useAlert\";\n\n\nexport type AlertProps = Omit<TagProps<\"div\">, \"content\" | \"title\" | \"direction\"> & {\n title?: useBreakpointPropsType<string | ReactElement>;\n direction?: useBreakpointPropsType<\"row\" | \"column\">;\n variant?: useBreakpointPropsType<UseColorTemplateType>;\n color?: useBreakpointPropsType<UseColorTemplateColor>;\n icon?: useBreakpointPropsType<\"info\" | \"warning\" | \"success\" | \"error\" | false | ReactElement>;\n onClose?: React.DOMAttributes<\"button\">['onClick'];\n}\n\nexport type AlertMesssageType = string | ReactElement | AlertProps\n\nconst Alert = ({ children, ...rest }: AlertProps) => {\n let [{\n title,\n variant,\n icon,\n color,\n direction,\n slotProps,\n onClose,\n ..._props\n }] = useInterface<any>(\"Alert\", rest, {\n variant: \"fill\"\n })\n color ??= \"default\"\n direction ??= \"row\"\n\n const _p: any = {}\n if (title) _p.title = title\n if (variant) _p.variant = variant\n if (icon) _p.icon = icon\n if (color) _p.color = color\n if (direction) _p.direction = direction\n\n const p: any = useBreakpointProps(_p)\n\n title = p.title\n variant = p.variant\n icon = p.icon\n color = p.color\n direction = p.direction\n\n let isRow = direction === 'row'\n\n\n const template = useColorTemplate(color, variant)\n\n let iconsx = {\n fontSize: isRow ? 22 : 40,\n color: color === 'default' ? \"text.primary\" : template.primary.color\n }\n\n const icons: any = {\n \"info\": <InfoIcon sx={iconsx} />,\n \"warning\": <WarningIcon sx={iconsx} />,\n \"success\": <SuccessIcon sx={iconsx} />,\n \"danger\": <ErrorIcon sx={iconsx} />\n }\n\n let _icon = icons[icon] || icons[color]\n\n return (\n <Tag\n {..._props}\n baseClass=\"alert\"\n sxr={{\n justifyContent: \"flex-start\",\n position: \"relative\",\n radius: 1,\n px: isRow ? (_icon ? .5 : 2) : 3,\n py: isRow ? .5 : 3,\n flexDirection: \"column\",\n display: 'flex',\n ..._props?.sx\n }}\n {...template.primary}\n >\n {\n onClose && <IconButton\n color={color}\n variant={variant === 'fill' ? \"fill\" : \"text\"}\n size={25}\n sx={{\n position: \"absolute\",\n top: 5,\n right: 5\n }}\n onClick={onClose}\n className=\"alert-close-button\"\n >\n <IconClose fontSize={18} />\n </IconButton>\n }\n <Tag\n sx={{\n display: \"flex\",\n gap: 1,\n flexDirection: direction,\n alignItems: isRow ? \"flex-start\" : \"center\"\n }}\n baseClass=\"alert-container\"\n >\n {\n _icon && <Tag\n baseClass=\"alert-icon\"\n sxr={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n p: isRow ? .5 : 0,\n \"& svg\": {\n color: template.primary.color\n }\n }}\n >\n {_icon}\n </Tag>\n }\n <Tag\n baseClass=\"alert-content\"\n sxr={{\n display: \"flex\",\n flexDirection: \"column\",\n flex: 1,\n color: template.primary.color,\n textAlign: isRow ? \"left\" : \"center\",\n gap: isRow ? 0 : 1\n }}\n >\n {title && <>\n {\n isValidElement(title) ? <Tag className=\"alert-title\">{title}</Tag> : <Text\n className=\"alert-titles\"\n variant=\"text\"\n sx={{\n fontWeight: 500,\n color: template.primary.color\n }}\n >{title}</Text>\n }\n </>}\n <Tag\n sxr={{\n font: \"button\",\n }}\n >\n {children}\n </Tag>\n </Tag>\n </Tag>\n </Tag>\n )\n}\n\nconst ActionAlert = (props: UseAlerProps) => {\n const ref = useRef<HTMLDivElement>(null);\n const alert = useAlert({\n ...props,\n slotProps: {\n ...props.slotProps,\n modal: {\n ...props.slotProps?.modal,\n slotProps: {\n ...props.slotProps?.modal?.slotProps,\n layer: {\n ...props.slotProps?.modal?.slotProps?.layer,\n portal: {\n ...props.slotProps?.modal?.slotProps?.layer?.portal,\n container: ref.current || undefined\n }\n }\n }\n }\n }\n })\n\n useEffect(() => {\n if (props.open) {\n alert.open()\n } else {\n alert.close()\n }\n }, [props.open])\n return <Tag ref={ref}></Tag>\n}\n\nAlert.confirm = (props: UseAlerProps) => {\n const a = Renderar.render(ActionAlert as any, {\n open: true,\n ...props,\n slotProps: {\n ...props.slotProps,\n modal: {\n ...props.slotProps?.modal,\n onClosed: () => {\n a.unrender()\n if (props?.slotProps?.modal?.onClosed) {\n props.slotProps?.modal?.onClosed()\n }\n },\n }\n },\n })\n\n return {\n open: () => {\n a.updateProps({ open: true })\n },\n close: () => {\n a.updateProps({ open: false })\n },\n }\n}\n\nexport default Alert"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAwBA;AAAe;AACX;AAUI;;;;;AAMJ;AAAW;AACX;AAAa;AACb;AAAU;AACV;AAAW;AACX;AAAe;AAEf;AAEA;AACA;AACA;AACA;AACA;AAEA;;AAKA;;AAEI;;AAGJ;AACI;AACA;AACA;AACA;;;;AA2BgB;AACA;AACA;;AAUJ;AACA;AACA;;AAEH;AAOW;AACA;AACA;;AAEA;AACI;AACH;;AASL;AACA;AACA;AACA;;;AAGH;AAQe;AACA;;AAOR;AACH;AAQzB;AAEA;;AACI;AACA;;AAqBI;;;;;;AAKJ;AACA;AACJ;AAEA;;AACI;;;AASgB;;;AAGJ;;;;;;;;;AAahB;;"}
1
+ {"version":3,"file":"index.cjs","sources":["../../src/Alert/index.tsx"],"sourcesContent":["\"use client\";\nimport { Tag, TagProps, useBreakpointProps, useColorTemplate, useInterface, useBreakpointPropsType, Renderar, UseColorTemplateType, UseColorTemplateColor, UseTransitionVariantTypes } from \"@xanui/core\"\nimport React, { isValidElement, ReactElement } from \"react\"\nimport Text from \"../Text\"\nimport InfoIcon from '@xanui/icons/Info';\nimport WarningIcon from '@xanui/icons/Warning';\nimport SuccessIcon from '@xanui/icons/CheckCircle';\nimport ErrorIcon from '@xanui/icons/Cancel';\nimport IconClose from '@xanui/icons/Close';\nimport IconButton from \"../IconButton\";\nimport Modal, { ModalProps } from \"../Modal\";\nimport Button, { ButtonProps } from \"../Button\";\n\nexport type AlertProps = Omit<TagProps<\"div\">, \"content\" | \"title\" | \"direction\"> & {\n title?: useBreakpointPropsType<string | ReactElement>;\n direction?: useBreakpointPropsType<\"row\" | \"column\">;\n variant?: useBreakpointPropsType<UseColorTemplateType>;\n color?: useBreakpointPropsType<UseColorTemplateColor>;\n icon?: useBreakpointPropsType<\"info\" | \"warning\" | \"success\" | \"error\" | false | ReactElement>;\n onClose?: React.DOMAttributes<\"button\">['onClick'];\n}\n\nexport type AlertMesssageType = string | ReactElement | AlertProps\n\nconst Alert = ({ children, ...rest }: AlertProps) => {\n let [{\n title,\n variant,\n icon,\n color,\n direction,\n slotProps,\n onClose,\n ..._props\n }] = useInterface<any>(\"Alert\", rest, {\n variant: \"fill\"\n })\n color ??= \"default\"\n direction ??= \"row\"\n\n const _p: any = {}\n if (title) _p.title = title\n if (variant) _p.variant = variant\n if (icon) _p.icon = icon\n if (color) _p.color = color\n if (direction) _p.direction = direction\n\n const p: any = useBreakpointProps(_p)\n\n title = p.title\n variant = p.variant\n icon = p.icon\n color = p.color\n direction = p.direction\n\n let isRow = direction === 'row'\n\n\n const template = useColorTemplate(color, variant)\n\n let iconsx = {\n fontSize: isRow ? 22 : 40,\n color: color === 'default' ? \"text.primary\" : template.primary.color\n }\n\n const icons: any = {\n \"info\": <InfoIcon sx={iconsx} />,\n \"warning\": <WarningIcon sx={iconsx} />,\n \"success\": <SuccessIcon sx={iconsx} />,\n \"danger\": <ErrorIcon sx={iconsx} />\n }\n\n let _icon = icons[icon] || icons[color]\n\n return (\n <Tag\n {..._props}\n baseClass=\"alert\"\n sxr={{\n justifyContent: \"flex-start\",\n position: \"relative\",\n radius: 1,\n px: isRow ? (_icon ? .5 : 2) : 3,\n py: isRow ? .5 : 3,\n flexDirection: \"column\",\n display: 'flex',\n ..._props?.sx\n }}\n {...template.primary}\n >\n {\n onClose && <IconButton\n color={color}\n variant={variant === 'fill' ? \"fill\" : \"text\"}\n size={25}\n sx={{\n position: \"absolute\",\n top: 5,\n right: 5\n }}\n onClick={onClose}\n className=\"alert-close-button\"\n >\n <IconClose fontSize={18} />\n </IconButton>\n }\n <Tag\n sx={{\n display: \"flex\",\n gap: 1,\n flexDirection: direction,\n alignItems: isRow ? \"flex-start\" : \"center\"\n }}\n baseClass=\"alert-container\"\n >\n {\n _icon && <Tag\n baseClass=\"alert-icon\"\n sxr={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n p: isRow ? .5 : 0,\n \"& svg\": {\n color: template.primary.color\n }\n }}\n >\n {_icon}\n </Tag>\n }\n <Tag\n baseClass=\"alert-content\"\n sxr={{\n display: \"flex\",\n flexDirection: \"column\",\n flex: 1,\n color: template.primary.color,\n textAlign: isRow ? \"left\" : \"center\",\n gap: isRow ? 0 : 1\n }}\n >\n {title && <>\n {\n isValidElement(title) ? <Tag className=\"alert-title\">{title}</Tag> : <Text\n className=\"alert-titles\"\n variant=\"text\"\n sx={{\n fontWeight: 500,\n color: template.primary.color\n }}\n >{title}</Text>\n }\n </>}\n <Tag\n sxr={{\n font: \"button\",\n }}\n >\n {children}\n </Tag>\n </Tag>\n </Tag>\n </Tag>\n )\n}\n\nexport type ConfirmAlertProps = Omit<AlertProps, 'children' | 'onClose' | 'variant' | \"size\"> & {\n open: boolean;\n loading: boolean;\n content: string | ReactElement,\n size?: \"small\" | \"medium\" | \"large\" | number;\n closeButton?: boolean;\n clickOutsideToClose?: boolean;\n okButtonText?: string;\n cancelButtonText?: string;\n hideOkButton?: boolean;\n hideCancelButton?: boolean;\n buttonPlacement?: \"start\" | \"end\" | \"between\" | \"full\";\n variant?: \"text\" | \"fill\"\n onConfirm?: () => Promise<void> | void;\n onCancel?: () => Promise<void> | void;\n transition?: UseTransitionVariantTypes;\n blurMode?: ModalProps['blurMode'];\n slotProps?: {\n modal?: Omit<ModalProps, 'open' | \"children\">;\n okButton?: Omit<ButtonProps, \"children\">;\n closeButton?: Omit<ButtonProps, \"children\">;\n }\n}\n\n\nconst ConfirmAlert = (props: ConfirmAlertProps) => {\n let {\n open,\n loading,\n content,\n size,\n color,\n direction,\n variant,\n closeButton,\n clickOutsideToClose,\n okButtonText,\n cancelButtonText,\n hideOkButton,\n hideCancelButton,\n buttonPlacement,\n onConfirm,\n onCancel,\n transition,\n blurMode,\n slotProps,\n ...rest\n } = props\n\n hideOkButton ??= false\n hideCancelButton ??= false\n\n size ??= \"small\"\n color ??= 'default'\n variant ??= \"text\"\n direction ??= \"column\"\n buttonPlacement ??= \"end\"\n let sx: any = {};\n\n switch (buttonPlacement) {\n case \"start\":\n sx.justifyContent = 'flex-start'\n break;\n case \"end\":\n sx.justifyContent = 'flex-end'\n break;\n case \"between\":\n sx.justifyContent = 'space-between'\n break;\n case \"full\":\n sx = {\n \"& button\": {\n flex: 1\n }\n }\n break;\n }\n\n let sizes: any = {\n small: 320,\n medium: 400,\n large: 600\n }\n\n let okcolor = color\n let closecolor = color\n if (color === 'default') {\n okcolor = 'brand'\n closecolor = 'default'\n variant = 'text'\n } else {\n if (variant === 'fill') {\n okcolor = 'default'\n closecolor = 'default'\n } else {\n okcolor = color\n closecolor = 'default'\n }\n }\n\n return (<Modal\n open={open}\n {...slotProps?.modal}\n size={sizes[size] || size}\n blur={40}\n blurMode={blurMode || \"transparent\"}\n transition={transition || \"zoom\"}\n onClickOutside={async () => {\n if (clickOutsideToClose && !loading) {\n onCancel && await onCancel()\n }\n }}\n >\n <Alert\n direction={direction}\n sx={{\n px: 2,\n py: 1,\n pt: direction === 'row' ? 1 : 2\n }}\n color={color}\n variant={variant}\n onClose={closeButton ? close : undefined}\n {...rest}\n >\n {content}\n <Tag\n sxr={{\n display: \"flex\",\n gap: 1,\n pt: 4,\n flexDirection: \"row\",\n ...sx,\n }}\n >\n {!hideCancelButton && <Button\n disabled={loading}\n color={closecolor}\n variant=\"fill\"\n {...slotProps?.closeButton}\n onClick={async () => {\n onCancel && await onCancel()\n }}\n >{cancelButtonText || \"Close\"}</Button>}\n <Button\n loading={loading}\n color={okcolor}\n variant=\"fill\"\n {...slotProps?.okButton}\n\n onClick={async () => {\n onConfirm && await onConfirm()\n }}\n >{okButtonText || \"OK\"}</Button>\n </Tag>\n </Alert>\n </Modal>)\n}\n\n\nAlert.confirm = ({ onConfirm, onCancel, ...props }: Omit<ConfirmAlertProps, \"open\" | \"loading\">) => {\n const confirm = Renderar.render(ConfirmAlert as any, {\n ...props,\n open: true,\n loading: false,\n onConfirm: async () => {\n if (onConfirm) {\n confirm.updateProps({ loading: true })\n if (onConfirm) await onConfirm()\n confirm.updateProps({ open: false, loading: false })\n } else {\n confirm.updateProps({ open: false })\n }\n },\n onCancel: async () => {\n if (onCancel) {\n confirm.updateProps({ loading: true })\n await onCancel()\n confirm.updateProps({ open: false, loading: false })\n } else {\n confirm.updateProps({ open: false })\n }\n },\n slotProps: {\n ...props.slotProps,\n modal: {\n ...props.slotProps?.modal,\n onClosed: () => {\n confirm.unrender()\n if (props?.slotProps?.modal?.onClosed) {\n props.slotProps?.modal?.onClosed()\n }\n },\n }\n },\n })\n}\n\nexport default Alert"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAwBA;AAAe;AACX;AAUI;;;;;AAMJ;AAAW;AACX;AAAa;AACb;AAAU;AACV;AAAW;AACX;AAAe;AAEf;AAEA;AACA;AACA;AACA;AACA;AAEA;;AAKA;;AAEI;;AAGJ;AACI;AACA;AACA;AACA;;;;AA2BgB;AACA;AACA;;AAUJ;AACA;AACA;;AAEH;AAOW;AACA;AACA;;AAEA;AACI;AACH;;AASL;AACA;AACA;AACA;;;AAGH;AAQe;AACA;;AAOR;AACH;AAQzB;AA2BA;;;;;;;;;;;AAmCQ;AACI;;AAEJ;AACI;;AAEJ;AACI;;AAEJ;AACI;AACI;AACI;AACH;;;;AAKb;AACI;AACA;AACA;;;;AAKJ;;;;;;AAKI;;;;;;;;;;AAiBI;AACI;;;AAOA;AACA;;AAEH;AAsBW;AACJ;AASI;;AAMxB;AAGA;;;;;;AAQgB;;AACA;;;;;AAIR;;;;AAKQ;;;;;AAIR;;;AAOY;;;AAGJ;AAIhB;;"}
package/Alert/index.d.ts CHANGED
@@ -1,7 +1,8 @@
1
1
  import * as react_jsx_runtime from 'react/jsx-runtime';
2
- import { TagProps, useBreakpointPropsType, UseColorTemplateType, UseColorTemplateColor } from '@xanui/core';
2
+ import { TagProps, useBreakpointPropsType, UseColorTemplateType, UseColorTemplateColor, UseTransitionVariantTypes } from '@xanui/core';
3
3
  import React, { ReactElement } from 'react';
4
- import { UseAlerProps } from '../useAlert/index.js';
4
+ import { ModalProps } from '../Modal/index.js';
5
+ import { ButtonProps } from '../Button/index.js';
5
6
 
6
7
  type AlertProps = Omit<TagProps<"div">, "content" | "title" | "direction"> & {
7
8
  title?: useBreakpointPropsType<string | ReactElement>;
@@ -13,11 +14,31 @@ type AlertProps = Omit<TagProps<"div">, "content" | "title" | "direction"> & {
13
14
  };
14
15
  declare const Alert: {
15
16
  ({ children, ...rest }: AlertProps): react_jsx_runtime.JSX.Element;
16
- confirm(props: UseAlerProps): {
17
- open: () => void;
18
- close: () => void;
17
+ confirm({ onConfirm, onCancel, ...props }: Omit<ConfirmAlertProps, "open" | "loading">): void;
18
+ };
19
+ type ConfirmAlertProps = Omit<AlertProps, 'children' | 'onClose' | 'variant' | "size"> & {
20
+ open: boolean;
21
+ loading: boolean;
22
+ content: string | ReactElement;
23
+ size?: "small" | "medium" | "large" | number;
24
+ closeButton?: boolean;
25
+ clickOutsideToClose?: boolean;
26
+ okButtonText?: string;
27
+ cancelButtonText?: string;
28
+ hideOkButton?: boolean;
29
+ hideCancelButton?: boolean;
30
+ buttonPlacement?: "start" | "end" | "between" | "full";
31
+ variant?: "text" | "fill";
32
+ onConfirm?: () => Promise<void> | void;
33
+ onCancel?: () => Promise<void> | void;
34
+ transition?: UseTransitionVariantTypes;
35
+ blurMode?: ModalProps['blurMode'];
36
+ slotProps?: {
37
+ modal?: Omit<ModalProps, 'open' | "children">;
38
+ okButton?: Omit<ButtonProps, "children">;
39
+ closeButton?: Omit<ButtonProps, "children">;
19
40
  };
20
41
  };
21
42
 
22
43
  export { Alert as default };
23
- export type { AlertProps };
44
+ export type { AlertProps, ConfirmAlertProps };
package/Alert/index.js CHANGED
@@ -2,7 +2,7 @@
2
2
  import { __rest } from 'tslib';
3
3
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
4
4
  import { useInterface, useBreakpointProps, useColorTemplate, Tag, Renderar } from '@xanui/core';
5
- import { isValidElement, useRef, useEffect } from 'react';
5
+ import { isValidElement } from 'react';
6
6
  import Text from '../Text/index.js';
7
7
  import InfoIcon from '@xanui/icons/Info';
8
8
  import WarningIcon from '@xanui/icons/Warning';
@@ -10,7 +10,8 @@ import SuccessIcon from '@xanui/icons/CheckCircle';
10
10
  import ErrorIcon from '@xanui/icons/Cancel';
11
11
  import Close from '@xanui/icons/Close';
12
12
  import IconButton from '../IconButton/index.js';
13
- import useAlert from '../useAlert/index.js';
13
+ import Modal from '../Modal/index.js';
14
+ import Button from '../Button/index.js';
14
15
 
15
16
  const Alert = (_a) => {
16
17
  var { children } = _a, rest = __rest(_a, ["children"]);
@@ -80,37 +81,99 @@ const Alert = (_a) => {
80
81
  font: "button",
81
82
  }, children: children })] })] })] })));
82
83
  };
83
- const ActionAlert = (props) => {
84
- var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k;
85
- const ref = useRef(null);
86
- const alert = useAlert(Object.assign(Object.assign({}, props), { slotProps: Object.assign(Object.assign({}, props.slotProps), { modal: Object.assign(Object.assign({}, (_a = props.slotProps) === null || _a === void 0 ? void 0 : _a.modal), { slotProps: Object.assign(Object.assign({}, (_c = (_b = props.slotProps) === null || _b === void 0 ? void 0 : _b.modal) === null || _c === void 0 ? void 0 : _c.slotProps), { layer: Object.assign(Object.assign({}, (_f = (_e = (_d = props.slotProps) === null || _d === void 0 ? void 0 : _d.modal) === null || _e === void 0 ? void 0 : _e.slotProps) === null || _f === void 0 ? void 0 : _f.layer), { portal: Object.assign(Object.assign({}, (_k = (_j = (_h = (_g = props.slotProps) === null || _g === void 0 ? void 0 : _g.modal) === null || _h === void 0 ? void 0 : _h.slotProps) === null || _j === void 0 ? void 0 : _j.layer) === null || _k === void 0 ? void 0 : _k.portal), { container: ref.current || undefined }) }) }) }) }) }));
87
- useEffect(() => {
88
- if (props.open) {
89
- alert.open();
84
+ const ConfirmAlert = (props) => {
85
+ let { open, loading, content, size, color, direction, variant, closeButton, clickOutsideToClose, okButtonText, cancelButtonText, hideOkButton, hideCancelButton, buttonPlacement, onConfirm, onCancel, transition, blurMode, slotProps } = props, rest = __rest(props, ["open", "loading", "content", "size", "color", "direction", "variant", "closeButton", "clickOutsideToClose", "okButtonText", "cancelButtonText", "hideOkButton", "hideCancelButton", "buttonPlacement", "onConfirm", "onCancel", "transition", "blurMode", "slotProps"]);
86
+ hideOkButton !== null && hideOkButton !== void 0 ? hideOkButton : (hideOkButton = false);
87
+ hideCancelButton !== null && hideCancelButton !== void 0 ? hideCancelButton : (hideCancelButton = false);
88
+ size !== null && size !== void 0 ? size : (size = "small");
89
+ color !== null && color !== void 0 ? color : (color = 'default');
90
+ variant !== null && variant !== void 0 ? variant : (variant = "text");
91
+ direction !== null && direction !== void 0 ? direction : (direction = "column");
92
+ buttonPlacement !== null && buttonPlacement !== void 0 ? buttonPlacement : (buttonPlacement = "end");
93
+ let sx = {};
94
+ switch (buttonPlacement) {
95
+ case "start":
96
+ sx.justifyContent = 'flex-start';
97
+ break;
98
+ case "end":
99
+ sx.justifyContent = 'flex-end';
100
+ break;
101
+ case "between":
102
+ sx.justifyContent = 'space-between';
103
+ break;
104
+ case "full":
105
+ sx = {
106
+ "& button": {
107
+ flex: 1
108
+ }
109
+ };
110
+ break;
111
+ }
112
+ let sizes = {
113
+ small: 320,
114
+ medium: 400,
115
+ large: 600
116
+ };
117
+ let okcolor = color;
118
+ let closecolor = color;
119
+ if (color === 'default') {
120
+ okcolor = 'brand';
121
+ closecolor = 'default';
122
+ variant = 'text';
123
+ }
124
+ else {
125
+ if (variant === 'fill') {
126
+ okcolor = 'default';
127
+ closecolor = 'default';
90
128
  }
91
129
  else {
92
- alert.close();
130
+ okcolor = color;
131
+ closecolor = 'default';
93
132
  }
94
- }, [props.open]);
95
- return jsx(Tag, { ref: ref });
133
+ }
134
+ return (jsx(Modal, Object.assign({ open: open }, slotProps === null || slotProps === void 0 ? void 0 : slotProps.modal, { size: sizes[size] || size, blur: 40, blurMode: blurMode || "transparent", transition: transition || "zoom", onClickOutside: async () => {
135
+ if (clickOutsideToClose && !loading) {
136
+ onCancel && await onCancel();
137
+ }
138
+ }, children: jsxs(Alert, Object.assign({ direction: direction, sx: {
139
+ px: 2,
140
+ py: 1,
141
+ pt: direction === 'row' ? 1 : 2
142
+ }, color: color, variant: variant, onClose: closeButton ? close : undefined }, rest, { children: [content, jsxs(Tag, { sxr: Object.assign({ display: "flex", gap: 1, pt: 4, flexDirection: "row" }, sx), children: [!hideCancelButton && jsx(Button, Object.assign({ disabled: loading, color: closecolor, variant: "fill" }, slotProps === null || slotProps === void 0 ? void 0 : slotProps.closeButton, { onClick: async () => {
143
+ onCancel && await onCancel();
144
+ }, children: cancelButtonText || "Close" })), jsx(Button, Object.assign({ loading: loading, color: okcolor, variant: "fill" }, slotProps === null || slotProps === void 0 ? void 0 : slotProps.okButton, { onClick: async () => {
145
+ onConfirm && await onConfirm();
146
+ }, children: okButtonText || "OK" }))] })] })) })));
96
147
  };
97
- Alert.confirm = (props) => {
98
- var _a;
99
- const a = Renderar.render(ActionAlert, Object.assign(Object.assign({ open: true }, props), { slotProps: Object.assign(Object.assign({}, props.slotProps), { modal: Object.assign(Object.assign({}, (_a = props.slotProps) === null || _a === void 0 ? void 0 : _a.modal), { onClosed: () => {
148
+ Alert.confirm = (_a) => {
149
+ var _b;
150
+ var { onConfirm, onCancel } = _a, props = __rest(_a, ["onConfirm", "onCancel"]);
151
+ const confirm = Renderar.render(ConfirmAlert, Object.assign(Object.assign({}, props), { open: true, loading: false, onConfirm: async () => {
152
+ if (onConfirm) {
153
+ confirm.updateProps({ loading: true });
154
+ if (onConfirm)
155
+ await onConfirm();
156
+ confirm.updateProps({ open: false, loading: false });
157
+ }
158
+ else {
159
+ confirm.updateProps({ open: false });
160
+ }
161
+ }, onCancel: async () => {
162
+ if (onCancel) {
163
+ confirm.updateProps({ loading: true });
164
+ await onCancel();
165
+ confirm.updateProps({ open: false, loading: false });
166
+ }
167
+ else {
168
+ confirm.updateProps({ open: false });
169
+ }
170
+ }, slotProps: Object.assign(Object.assign({}, props.slotProps), { modal: Object.assign(Object.assign({}, (_b = props.slotProps) === null || _b === void 0 ? void 0 : _b.modal), { onClosed: () => {
100
171
  var _a, _b, _c, _d;
101
- a.unrender();
172
+ confirm.unrender();
102
173
  if ((_b = (_a = props === null || props === void 0 ? void 0 : props.slotProps) === null || _a === void 0 ? void 0 : _a.modal) === null || _b === void 0 ? void 0 : _b.onClosed) {
103
174
  (_d = (_c = props.slotProps) === null || _c === void 0 ? void 0 : _c.modal) === null || _d === void 0 ? void 0 : _d.onClosed();
104
175
  }
105
176
  } }) }) }));
106
- return {
107
- open: () => {
108
- a.updateProps({ open: true });
109
- },
110
- close: () => {
111
- a.updateProps({ open: false });
112
- },
113
- };
114
177
  };
115
178
 
116
179
  export { Alert as default };
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["../../src/Alert/index.tsx"],"sourcesContent":["\"use client\";\nimport { Tag, TagProps, useBreakpointProps, useColorTemplate, useInterface, useBreakpointPropsType, Renderar, UseColorTemplateType, UseColorTemplateColor } from \"@xanui/core\"\nimport React, { isValidElement, ReactElement, useEffect, useRef } from \"react\"\nimport Text from \"../Text\"\nimport InfoIcon from '@xanui/icons/Info';\nimport WarningIcon from '@xanui/icons/Warning';\nimport SuccessIcon from '@xanui/icons/CheckCircle';\nimport ErrorIcon from '@xanui/icons/Cancel';\nimport IconClose from '@xanui/icons/Close';\nimport IconButton from \"../IconButton\";\nimport useAlert, { UseAlerProps } from \"../useAlert\";\n\n\nexport type AlertProps = Omit<TagProps<\"div\">, \"content\" | \"title\" | \"direction\"> & {\n title?: useBreakpointPropsType<string | ReactElement>;\n direction?: useBreakpointPropsType<\"row\" | \"column\">;\n variant?: useBreakpointPropsType<UseColorTemplateType>;\n color?: useBreakpointPropsType<UseColorTemplateColor>;\n icon?: useBreakpointPropsType<\"info\" | \"warning\" | \"success\" | \"error\" | false | ReactElement>;\n onClose?: React.DOMAttributes<\"button\">['onClick'];\n}\n\nexport type AlertMesssageType = string | ReactElement | AlertProps\n\nconst Alert = ({ children, ...rest }: AlertProps) => {\n let [{\n title,\n variant,\n icon,\n color,\n direction,\n slotProps,\n onClose,\n ..._props\n }] = useInterface<any>(\"Alert\", rest, {\n variant: \"fill\"\n })\n color ??= \"default\"\n direction ??= \"row\"\n\n const _p: any = {}\n if (title) _p.title = title\n if (variant) _p.variant = variant\n if (icon) _p.icon = icon\n if (color) _p.color = color\n if (direction) _p.direction = direction\n\n const p: any = useBreakpointProps(_p)\n\n title = p.title\n variant = p.variant\n icon = p.icon\n color = p.color\n direction = p.direction\n\n let isRow = direction === 'row'\n\n\n const template = useColorTemplate(color, variant)\n\n let iconsx = {\n fontSize: isRow ? 22 : 40,\n color: color === 'default' ? \"text.primary\" : template.primary.color\n }\n\n const icons: any = {\n \"info\": <InfoIcon sx={iconsx} />,\n \"warning\": <WarningIcon sx={iconsx} />,\n \"success\": <SuccessIcon sx={iconsx} />,\n \"danger\": <ErrorIcon sx={iconsx} />\n }\n\n let _icon = icons[icon] || icons[color]\n\n return (\n <Tag\n {..._props}\n baseClass=\"alert\"\n sxr={{\n justifyContent: \"flex-start\",\n position: \"relative\",\n radius: 1,\n px: isRow ? (_icon ? .5 : 2) : 3,\n py: isRow ? .5 : 3,\n flexDirection: \"column\",\n display: 'flex',\n ..._props?.sx\n }}\n {...template.primary}\n >\n {\n onClose && <IconButton\n color={color}\n variant={variant === 'fill' ? \"fill\" : \"text\"}\n size={25}\n sx={{\n position: \"absolute\",\n top: 5,\n right: 5\n }}\n onClick={onClose}\n className=\"alert-close-button\"\n >\n <IconClose fontSize={18} />\n </IconButton>\n }\n <Tag\n sx={{\n display: \"flex\",\n gap: 1,\n flexDirection: direction,\n alignItems: isRow ? \"flex-start\" : \"center\"\n }}\n baseClass=\"alert-container\"\n >\n {\n _icon && <Tag\n baseClass=\"alert-icon\"\n sxr={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n p: isRow ? .5 : 0,\n \"& svg\": {\n color: template.primary.color\n }\n }}\n >\n {_icon}\n </Tag>\n }\n <Tag\n baseClass=\"alert-content\"\n sxr={{\n display: \"flex\",\n flexDirection: \"column\",\n flex: 1,\n color: template.primary.color,\n textAlign: isRow ? \"left\" : \"center\",\n gap: isRow ? 0 : 1\n }}\n >\n {title && <>\n {\n isValidElement(title) ? <Tag className=\"alert-title\">{title}</Tag> : <Text\n className=\"alert-titles\"\n variant=\"text\"\n sx={{\n fontWeight: 500,\n color: template.primary.color\n }}\n >{title}</Text>\n }\n </>}\n <Tag\n sxr={{\n font: \"button\",\n }}\n >\n {children}\n </Tag>\n </Tag>\n </Tag>\n </Tag>\n )\n}\n\nconst ActionAlert = (props: UseAlerProps) => {\n const ref = useRef<HTMLDivElement>(null);\n const alert = useAlert({\n ...props,\n slotProps: {\n ...props.slotProps,\n modal: {\n ...props.slotProps?.modal,\n slotProps: {\n ...props.slotProps?.modal?.slotProps,\n layer: {\n ...props.slotProps?.modal?.slotProps?.layer,\n portal: {\n ...props.slotProps?.modal?.slotProps?.layer?.portal,\n container: ref.current || undefined\n }\n }\n }\n }\n }\n })\n\n useEffect(() => {\n if (props.open) {\n alert.open()\n } else {\n alert.close()\n }\n }, [props.open])\n return <Tag ref={ref}></Tag>\n}\n\nAlert.confirm = (props: UseAlerProps) => {\n const a = Renderar.render(ActionAlert as any, {\n open: true,\n ...props,\n slotProps: {\n ...props.slotProps,\n modal: {\n ...props.slotProps?.modal,\n onClosed: () => {\n a.unrender()\n if (props?.slotProps?.modal?.onClosed) {\n props.slotProps?.modal?.onClosed()\n }\n },\n }\n },\n })\n\n return {\n open: () => {\n a.updateProps({ open: true })\n },\n close: () => {\n a.updateProps({ open: false })\n },\n }\n}\n\nexport default Alert"],"names":[],"mappings":";;;;;;;;;;;;;;AAwBA;AAAe;AACX;AAUI;;;;;AAMJ;AAAW;AACX;AAAa;AACb;AAAU;AACV;AAAW;AACX;AAAe;AAEf;AAEA;AACA;AACA;AACA;AACA;AAEA;;AAKA;;AAEI;;AAGJ;AACI;AACA;AACA;AACA;;;;AA2BgB;AACA;AACA;;AAUJ;AACA;AACA;;AAEH;AAOW;AACA;AACA;;AAEA;AACI;AACH;;AASL;AACA;AACA;AACA;;;AAGH;AAQe;AACA;;AAOR;AACH;AAQzB;AAEA;;AACI;AACA;;AAqBI;;;;;;AAKJ;AACA;AACJ;AAEA;;AACI;;;AASgB;;;AAGJ;;;;;;;;;AAahB;;"}
1
+ {"version":3,"file":"index.js","sources":["../../src/Alert/index.tsx"],"sourcesContent":["\"use client\";\nimport { Tag, TagProps, useBreakpointProps, useColorTemplate, useInterface, useBreakpointPropsType, Renderar, UseColorTemplateType, UseColorTemplateColor, UseTransitionVariantTypes } from \"@xanui/core\"\nimport React, { isValidElement, ReactElement } from \"react\"\nimport Text from \"../Text\"\nimport InfoIcon from '@xanui/icons/Info';\nimport WarningIcon from '@xanui/icons/Warning';\nimport SuccessIcon from '@xanui/icons/CheckCircle';\nimport ErrorIcon from '@xanui/icons/Cancel';\nimport IconClose from '@xanui/icons/Close';\nimport IconButton from \"../IconButton\";\nimport Modal, { ModalProps } from \"../Modal\";\nimport Button, { ButtonProps } from \"../Button\";\n\nexport type AlertProps = Omit<TagProps<\"div\">, \"content\" | \"title\" | \"direction\"> & {\n title?: useBreakpointPropsType<string | ReactElement>;\n direction?: useBreakpointPropsType<\"row\" | \"column\">;\n variant?: useBreakpointPropsType<UseColorTemplateType>;\n color?: useBreakpointPropsType<UseColorTemplateColor>;\n icon?: useBreakpointPropsType<\"info\" | \"warning\" | \"success\" | \"error\" | false | ReactElement>;\n onClose?: React.DOMAttributes<\"button\">['onClick'];\n}\n\nexport type AlertMesssageType = string | ReactElement | AlertProps\n\nconst Alert = ({ children, ...rest }: AlertProps) => {\n let [{\n title,\n variant,\n icon,\n color,\n direction,\n slotProps,\n onClose,\n ..._props\n }] = useInterface<any>(\"Alert\", rest, {\n variant: \"fill\"\n })\n color ??= \"default\"\n direction ??= \"row\"\n\n const _p: any = {}\n if (title) _p.title = title\n if (variant) _p.variant = variant\n if (icon) _p.icon = icon\n if (color) _p.color = color\n if (direction) _p.direction = direction\n\n const p: any = useBreakpointProps(_p)\n\n title = p.title\n variant = p.variant\n icon = p.icon\n color = p.color\n direction = p.direction\n\n let isRow = direction === 'row'\n\n\n const template = useColorTemplate(color, variant)\n\n let iconsx = {\n fontSize: isRow ? 22 : 40,\n color: color === 'default' ? \"text.primary\" : template.primary.color\n }\n\n const icons: any = {\n \"info\": <InfoIcon sx={iconsx} />,\n \"warning\": <WarningIcon sx={iconsx} />,\n \"success\": <SuccessIcon sx={iconsx} />,\n \"danger\": <ErrorIcon sx={iconsx} />\n }\n\n let _icon = icons[icon] || icons[color]\n\n return (\n <Tag\n {..._props}\n baseClass=\"alert\"\n sxr={{\n justifyContent: \"flex-start\",\n position: \"relative\",\n radius: 1,\n px: isRow ? (_icon ? .5 : 2) : 3,\n py: isRow ? .5 : 3,\n flexDirection: \"column\",\n display: 'flex',\n ..._props?.sx\n }}\n {...template.primary}\n >\n {\n onClose && <IconButton\n color={color}\n variant={variant === 'fill' ? \"fill\" : \"text\"}\n size={25}\n sx={{\n position: \"absolute\",\n top: 5,\n right: 5\n }}\n onClick={onClose}\n className=\"alert-close-button\"\n >\n <IconClose fontSize={18} />\n </IconButton>\n }\n <Tag\n sx={{\n display: \"flex\",\n gap: 1,\n flexDirection: direction,\n alignItems: isRow ? \"flex-start\" : \"center\"\n }}\n baseClass=\"alert-container\"\n >\n {\n _icon && <Tag\n baseClass=\"alert-icon\"\n sxr={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n p: isRow ? .5 : 0,\n \"& svg\": {\n color: template.primary.color\n }\n }}\n >\n {_icon}\n </Tag>\n }\n <Tag\n baseClass=\"alert-content\"\n sxr={{\n display: \"flex\",\n flexDirection: \"column\",\n flex: 1,\n color: template.primary.color,\n textAlign: isRow ? \"left\" : \"center\",\n gap: isRow ? 0 : 1\n }}\n >\n {title && <>\n {\n isValidElement(title) ? <Tag className=\"alert-title\">{title}</Tag> : <Text\n className=\"alert-titles\"\n variant=\"text\"\n sx={{\n fontWeight: 500,\n color: template.primary.color\n }}\n >{title}</Text>\n }\n </>}\n <Tag\n sxr={{\n font: \"button\",\n }}\n >\n {children}\n </Tag>\n </Tag>\n </Tag>\n </Tag>\n )\n}\n\nexport type ConfirmAlertProps = Omit<AlertProps, 'children' | 'onClose' | 'variant' | \"size\"> & {\n open: boolean;\n loading: boolean;\n content: string | ReactElement,\n size?: \"small\" | \"medium\" | \"large\" | number;\n closeButton?: boolean;\n clickOutsideToClose?: boolean;\n okButtonText?: string;\n cancelButtonText?: string;\n hideOkButton?: boolean;\n hideCancelButton?: boolean;\n buttonPlacement?: \"start\" | \"end\" | \"between\" | \"full\";\n variant?: \"text\" | \"fill\"\n onConfirm?: () => Promise<void> | void;\n onCancel?: () => Promise<void> | void;\n transition?: UseTransitionVariantTypes;\n blurMode?: ModalProps['blurMode'];\n slotProps?: {\n modal?: Omit<ModalProps, 'open' | \"children\">;\n okButton?: Omit<ButtonProps, \"children\">;\n closeButton?: Omit<ButtonProps, \"children\">;\n }\n}\n\n\nconst ConfirmAlert = (props: ConfirmAlertProps) => {\n let {\n open,\n loading,\n content,\n size,\n color,\n direction,\n variant,\n closeButton,\n clickOutsideToClose,\n okButtonText,\n cancelButtonText,\n hideOkButton,\n hideCancelButton,\n buttonPlacement,\n onConfirm,\n onCancel,\n transition,\n blurMode,\n slotProps,\n ...rest\n } = props\n\n hideOkButton ??= false\n hideCancelButton ??= false\n\n size ??= \"small\"\n color ??= 'default'\n variant ??= \"text\"\n direction ??= \"column\"\n buttonPlacement ??= \"end\"\n let sx: any = {};\n\n switch (buttonPlacement) {\n case \"start\":\n sx.justifyContent = 'flex-start'\n break;\n case \"end\":\n sx.justifyContent = 'flex-end'\n break;\n case \"between\":\n sx.justifyContent = 'space-between'\n break;\n case \"full\":\n sx = {\n \"& button\": {\n flex: 1\n }\n }\n break;\n }\n\n let sizes: any = {\n small: 320,\n medium: 400,\n large: 600\n }\n\n let okcolor = color\n let closecolor = color\n if (color === 'default') {\n okcolor = 'brand'\n closecolor = 'default'\n variant = 'text'\n } else {\n if (variant === 'fill') {\n okcolor = 'default'\n closecolor = 'default'\n } else {\n okcolor = color\n closecolor = 'default'\n }\n }\n\n return (<Modal\n open={open}\n {...slotProps?.modal}\n size={sizes[size] || size}\n blur={40}\n blurMode={blurMode || \"transparent\"}\n transition={transition || \"zoom\"}\n onClickOutside={async () => {\n if (clickOutsideToClose && !loading) {\n onCancel && await onCancel()\n }\n }}\n >\n <Alert\n direction={direction}\n sx={{\n px: 2,\n py: 1,\n pt: direction === 'row' ? 1 : 2\n }}\n color={color}\n variant={variant}\n onClose={closeButton ? close : undefined}\n {...rest}\n >\n {content}\n <Tag\n sxr={{\n display: \"flex\",\n gap: 1,\n pt: 4,\n flexDirection: \"row\",\n ...sx,\n }}\n >\n {!hideCancelButton && <Button\n disabled={loading}\n color={closecolor}\n variant=\"fill\"\n {...slotProps?.closeButton}\n onClick={async () => {\n onCancel && await onCancel()\n }}\n >{cancelButtonText || \"Close\"}</Button>}\n <Button\n loading={loading}\n color={okcolor}\n variant=\"fill\"\n {...slotProps?.okButton}\n\n onClick={async () => {\n onConfirm && await onConfirm()\n }}\n >{okButtonText || \"OK\"}</Button>\n </Tag>\n </Alert>\n </Modal>)\n}\n\n\nAlert.confirm = ({ onConfirm, onCancel, ...props }: Omit<ConfirmAlertProps, \"open\" | \"loading\">) => {\n const confirm = Renderar.render(ConfirmAlert as any, {\n ...props,\n open: true,\n loading: false,\n onConfirm: async () => {\n if (onConfirm) {\n confirm.updateProps({ loading: true })\n if (onConfirm) await onConfirm()\n confirm.updateProps({ open: false, loading: false })\n } else {\n confirm.updateProps({ open: false })\n }\n },\n onCancel: async () => {\n if (onCancel) {\n confirm.updateProps({ loading: true })\n await onCancel()\n confirm.updateProps({ open: false, loading: false })\n } else {\n confirm.updateProps({ open: false })\n }\n },\n slotProps: {\n ...props.slotProps,\n modal: {\n ...props.slotProps?.modal,\n onClosed: () => {\n confirm.unrender()\n if (props?.slotProps?.modal?.onClosed) {\n props.slotProps?.modal?.onClosed()\n }\n },\n }\n },\n })\n}\n\nexport default Alert"],"names":[],"mappings":";;;;;;;;;;;;;;;AAwBA;AAAe;AACX;AAUI;;;;;AAMJ;AAAW;AACX;AAAa;AACb;AAAU;AACV;AAAW;AACX;AAAe;AAEf;AAEA;AACA;AACA;AACA;AACA;AAEA;;AAKA;;AAEI;;AAGJ;AACI;AACA;AACA;AACA;;;;AA2BgB;AACA;AACA;;AAUJ;AACA;AACA;;AAEH;AAOW;AACA;AACA;;AAEA;AACI;AACH;;AASL;AACA;AACA;AACA;;;AAGH;AAQe;AACA;;AAOR;AACH;AAQzB;AA2BA;;;;;;;;;;;AAmCQ;AACI;;AAEJ;AACI;;AAEJ;AACI;;AAEJ;AACI;AACI;AACI;AACH;;;;AAKb;AACI;AACA;AACA;;;;AAKJ;;;;;;AAKI;;;;;;;;;;AAiBI;AACI;;;AAOA;AACA;;AAEH;AAsBW;AACJ;AASI;;AAMxB;AAGA;;;;;;AAQgB;;AACA;;;;;AAIR;;;;AAKQ;;;;;AAIR;;;AAOY;;;AAGJ;AAIhB;;"}
@@ -1 +1 @@
1
- {"version":3,"file":"NumberFilter.cjs","sources":["../../../src/DataFilter/options/NumberFilter.tsx"],"sourcesContent":["\"use client\"\n\nimport { DataFilterSelect } from \"../types\";\nimport IconButton from \"../../IconButton\";\nimport Stack from \"../../Stack\";\nimport Text from \"../../Text\";\nimport Add from \"@xanui/icons/Add\";\nimport ClearAll from \"@xanui/icons/ClearAll\";\nimport InputNumber from \"../../InputNumber\";\n\ntype Props = {\n option: DataFilterSelect;\n value: number | null;\n onChange: (value: number | null) => void;\n}\n\nconst NumberFilter = ({ option, onChange, value }: Props) => {\n\n const isValue = value !== null && value !== undefined;\n\n return (\n <Stack\n width={\"100%\"}\n bgcolor=\"background.secondary\"\n p={1}\n radius={1}\n >\n <Stack\n direction=\"row\"\n alignItems=\"center\"\n justifyContent={\"space-between\"}\n gap={0.5}\n mb={isValue ? .5 : 0}\n >\n <Text>{option.label}</Text>\n <Stack\n direction=\"row\"\n gap={0.5}\n >\n <IconButton\n size=\"small\"\n variant=\"soft\"\n color={\"default\"}\n onClick={() => {\n onChange(0);\n }}\n >\n <Add />\n </IconButton>\n {\n isValue && <IconButton\n size=\"small\"\n variant=\"soft\"\n color={\"danger\"}\n onClick={() => {\n onChange(null);\n }}\n >\n <ClearAll />\n </IconButton>\n }\n </Stack>\n </Stack>\n <Stack\n direction=\"row\"\n gap={0.5}\n flexWrap=\"wrap\"\n >\n {\n isValue && <InputNumber\n variant={\"outline\"}\n value={value.toString()}\n onChange={(e: any) => {\n onChange(e.target.value);\n }}\n fullWidth\n />\n }\n </Stack>\n </Stack>\n )\n}\n\nexport default NumberFilter"],"names":[],"mappings":";;;;;;;;;;;AAgBA;;AAIG;;;;;AAqDkB;AACH;AAOlB;;"}
1
+ {"version":3,"file":"NumberFilter.cjs","sources":["../../../src/DataFilter/options/NumberFilter.tsx"],"sourcesContent":["\"use client\"\n\nimport { DataFilterSelect } from \"../types\";\nimport IconButton from \"../../IconButton\";\nimport Stack from \"../../Stack\";\nimport Text from \"../../Text\";\nimport Add from \"@xanui/icons/Add\";\nimport ClearAll from \"@xanui/icons/ClearAll\";\nimport InputNumber from \"../../InputNumber\";\n\ntype Props = {\n option: DataFilterSelect;\n value: number | null;\n onChange: (value: number | null) => void;\n}\n\nconst NumberFilter = ({ option, onChange, value }: Props) => {\n\n const isValue = value !== null && value !== undefined;\n\n return (\n <Stack\n width={\"100%\"}\n bgcolor=\"background.secondary\"\n p={1}\n radius={1}\n >\n <Stack\n direction=\"row\"\n alignItems=\"center\"\n justifyContent={\"space-between\"}\n gap={0.5}\n mb={isValue ? .5 : 0}\n >\n <Text>{option.label}</Text>\n <Stack\n direction=\"row\"\n gap={0.5}\n >\n <IconButton\n size=\"small\"\n variant=\"soft\"\n color={\"default\"}\n onClick={() => {\n onChange(0);\n }}\n >\n <Add />\n </IconButton>\n {\n isValue && <IconButton\n size=\"small\"\n variant=\"soft\"\n color={\"danger\"}\n onClick={() => {\n onChange(null);\n }}\n >\n <ClearAll />\n </IconButton>\n }\n </Stack>\n </Stack>\n <Stack\n direction=\"row\"\n gap={0.5}\n flexWrap=\"wrap\"\n >\n {\n isValue && <InputNumber\n variant={\"outline\"}\n value={value.toString() as any}\n onChange={(e: any) => {\n onChange(e.target.value);\n }}\n fullWidth\n />\n }\n </Stack>\n </Stack>\n )\n}\n\nexport default NumberFilter"],"names":[],"mappings":";;;;;;;;;;;AAgBA;;AAIG;;;;;AAqDkB;AACH;AAOlB;;"}
@@ -1 +1 @@
1
- {"version":3,"file":"NumberFilter.js","sources":["../../../src/DataFilter/options/NumberFilter.tsx"],"sourcesContent":["\"use client\"\n\nimport { DataFilterSelect } from \"../types\";\nimport IconButton from \"../../IconButton\";\nimport Stack from \"../../Stack\";\nimport Text from \"../../Text\";\nimport Add from \"@xanui/icons/Add\";\nimport ClearAll from \"@xanui/icons/ClearAll\";\nimport InputNumber from \"../../InputNumber\";\n\ntype Props = {\n option: DataFilterSelect;\n value: number | null;\n onChange: (value: number | null) => void;\n}\n\nconst NumberFilter = ({ option, onChange, value }: Props) => {\n\n const isValue = value !== null && value !== undefined;\n\n return (\n <Stack\n width={\"100%\"}\n bgcolor=\"background.secondary\"\n p={1}\n radius={1}\n >\n <Stack\n direction=\"row\"\n alignItems=\"center\"\n justifyContent={\"space-between\"}\n gap={0.5}\n mb={isValue ? .5 : 0}\n >\n <Text>{option.label}</Text>\n <Stack\n direction=\"row\"\n gap={0.5}\n >\n <IconButton\n size=\"small\"\n variant=\"soft\"\n color={\"default\"}\n onClick={() => {\n onChange(0);\n }}\n >\n <Add />\n </IconButton>\n {\n isValue && <IconButton\n size=\"small\"\n variant=\"soft\"\n color={\"danger\"}\n onClick={() => {\n onChange(null);\n }}\n >\n <ClearAll />\n </IconButton>\n }\n </Stack>\n </Stack>\n <Stack\n direction=\"row\"\n gap={0.5}\n flexWrap=\"wrap\"\n >\n {\n isValue && <InputNumber\n variant={\"outline\"}\n value={value.toString()}\n onChange={(e: any) => {\n onChange(e.target.value);\n }}\n fullWidth\n />\n }\n </Stack>\n </Stack>\n )\n}\n\nexport default NumberFilter"],"names":[],"mappings":";;;;;;;;;AAgBA;;AAIG;;;;;AAqDkB;AACH;AAOlB;;"}
1
+ {"version":3,"file":"NumberFilter.js","sources":["../../../src/DataFilter/options/NumberFilter.tsx"],"sourcesContent":["\"use client\"\n\nimport { DataFilterSelect } from \"../types\";\nimport IconButton from \"../../IconButton\";\nimport Stack from \"../../Stack\";\nimport Text from \"../../Text\";\nimport Add from \"@xanui/icons/Add\";\nimport ClearAll from \"@xanui/icons/ClearAll\";\nimport InputNumber from \"../../InputNumber\";\n\ntype Props = {\n option: DataFilterSelect;\n value: number | null;\n onChange: (value: number | null) => void;\n}\n\nconst NumberFilter = ({ option, onChange, value }: Props) => {\n\n const isValue = value !== null && value !== undefined;\n\n return (\n <Stack\n width={\"100%\"}\n bgcolor=\"background.secondary\"\n p={1}\n radius={1}\n >\n <Stack\n direction=\"row\"\n alignItems=\"center\"\n justifyContent={\"space-between\"}\n gap={0.5}\n mb={isValue ? .5 : 0}\n >\n <Text>{option.label}</Text>\n <Stack\n direction=\"row\"\n gap={0.5}\n >\n <IconButton\n size=\"small\"\n variant=\"soft\"\n color={\"default\"}\n onClick={() => {\n onChange(0);\n }}\n >\n <Add />\n </IconButton>\n {\n isValue && <IconButton\n size=\"small\"\n variant=\"soft\"\n color={\"danger\"}\n onClick={() => {\n onChange(null);\n }}\n >\n <ClearAll />\n </IconButton>\n }\n </Stack>\n </Stack>\n <Stack\n direction=\"row\"\n gap={0.5}\n flexWrap=\"wrap\"\n >\n {\n isValue && <InputNumber\n variant={\"outline\"}\n value={value.toString() as any}\n onChange={(e: any) => {\n onChange(e.target.value);\n }}\n fullWidth\n />\n }\n </Stack>\n </Stack>\n )\n}\n\nexport default NumberFilter"],"names":[],"mappings":";;;;;;;;;AAgBA;;AAIG;;;;;AAqDkB;AACH;AAOlB;;"}
@@ -9,41 +9,45 @@ var core = require('@xanui/core');
9
9
 
10
10
  const InputNumber = React.forwardRef((props, ref) => {
11
11
  var _a;
12
- const [_val, setVal] = React.useState((_a = props.value) !== null && _a !== void 0 ? _a : "");
13
12
  const inputRef = React.useRef(null);
14
13
  const mergeRef = core.useMergeRefs(inputRef, ref);
15
- React.useEffect(() => {
16
- if (inputRef.current && (props === null || props === void 0 ? void 0 : props.onChange)) {
17
- let valstr = String(_val);
18
- inputRef.current.value = valstr.includes(".") ? parseFloat(_val) : parseInt(_val);
19
- const syntheticEvent = {
20
- target: inputRef.current,
21
- currentTarget: inputRef.current,
22
- };
23
- props === null || props === void 0 ? void 0 : props.onChange(syntheticEvent);
24
- }
25
- }, [_val]);
26
- const isNumeric = _val === undefined || _val === '' || !isNaN(Number(_val));
14
+ const isNumeric = props.value === undefined || props.value === '' || !isNaN(Number(props.value));
27
15
  const errorProps = {};
28
16
  if (!isNumeric) {
29
17
  errorProps.error = true;
30
18
  errorProps.helperText = "Value must be numeric";
31
19
  }
32
- return (jsxRuntime.jsx(index, Object.assign({}, props, errorProps, { ref: mergeRef, endIcon: jsxRuntime.jsx(UnfoldMore, {}), value: _val !== null && _val !== void 0 ? _val : "", onKeyDown: (e) => {
20
+ return (jsxRuntime.jsx(index, Object.assign({}, props, errorProps, { ref: mergeRef, endIcon: jsxRuntime.jsx(UnfoldMore, {}), value: (_a = props.value) !== null && _a !== void 0 ? _a : "", onKeyDown: (e) => {
33
21
  var _a;
34
22
  (_a = props.onKeyDown) === null || _a === void 0 ? void 0 : _a.call(props, e);
35
23
  if (e.key !== 'ArrowUp' && e.key !== 'ArrowDown')
36
24
  return;
37
25
  e.preventDefault();
38
- const current = parseFloat(_val) || 0;
39
- setVal(e.key === 'ArrowUp' ? current + 1 : current - 1);
26
+ const current = parseFloat(props.value) || 0;
27
+ e.target.value = e.key === 'ArrowUp' ? current + 1 : current - 1;
28
+ (props === null || props === void 0 ? void 0 : props.onChange) && (props === null || props === void 0 ? void 0 : props.onChange(e));
29
+ }, onBlur: (e) => {
30
+ var _a;
31
+ const raw = e.target.value;
32
+ if (raw === "" || raw === ".")
33
+ return;
34
+ const num = parseFloat(raw);
35
+ if (!Number.isNaN(num)) {
36
+ (_a = props === null || props === void 0 ? void 0 : props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, Object.assign(Object.assign({}, e), { target: Object.assign(Object.assign({}, e.target), { value: num }) }));
37
+ }
40
38
  }, onChange: (e) => {
41
- let val = e.target.value.replace(/[^0-9.]/g, '');
42
- const parts = val.split('.');
43
- if (parts.length > 2) {
44
- val = parts[0] + '.' + parts.slice(1).join('');
39
+ var _a, _b;
40
+ let value = e.target.value;
41
+ if (value === "") {
42
+ (_a = props === null || props === void 0 ? void 0 : props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, e);
43
+ return;
45
44
  }
46
- setVal(val === "." ? `0.` : val);
45
+ if (!/^\d*\.?\d*$/.test(value))
46
+ return;
47
+ if (value === ".")
48
+ value = "0.";
49
+ const nextEvent = Object.assign(Object.assign({}, e), { target: Object.assign(Object.assign({}, e.target), { value }) });
50
+ (_b = props === null || props === void 0 ? void 0 : props.onChange) === null || _b === void 0 ? void 0 : _b.call(props, nextEvent);
47
51
  } })));
48
52
  });
49
53
 
@@ -1 +1 @@
1
- {"version":3,"file":"index.cjs","sources":["../../src/InputNumber/index.tsx"],"sourcesContent":["\"use client\"\nimport React, { useEffect, useRef, useState } from 'react'\nimport Input, { InputProps } from '../Input'\nimport UnfoldMore from '@xanui/icons/UnfoldMore'\nimport { useMergeRefs } from '@xanui/core'\n\nexport type InputNumberProps = Omit<InputProps, \"value\"> & {\n value?: number; // allow string so typing \".\" works\n}\n\nconst InputNumber = React.forwardRef<HTMLInputElement, InputNumberProps>((props, ref) => {\n const [_val, setVal] = useState<string>(props.value as any ?? \"\")\n const inputRef = useRef<any>(null)\n const mergeRef = useMergeRefs(inputRef, ref)\n useEffect(() => {\n if (inputRef.current && props?.onChange) {\n let valstr = String(_val)\n inputRef.current.value = valstr.includes(\".\") ? parseFloat(_val) : parseInt(_val)\n const syntheticEvent = {\n target: inputRef.current,\n currentTarget: inputRef.current,\n } as unknown as React.ChangeEvent<HTMLInputElement>;\n props?.onChange(syntheticEvent)\n }\n }, [_val])\n\n const isNumeric = _val === undefined || _val === '' || !isNaN(Number(_val));\n const errorProps: Partial<InputProps> = {};\n if (!isNumeric) {\n errorProps.error = true;\n errorProps.helperText = \"Value must be numeric\";\n }\n\n return (\n <Input\n {...props}\n {...errorProps}\n ref={mergeRef}\n endIcon={<UnfoldMore />}\n value={_val ?? \"\" as any}\n onKeyDown={(e: any) => {\n props.onKeyDown?.(e);\n\n if (e.key !== 'ArrowUp' && e.key !== 'ArrowDown') return;\n\n e.preventDefault();\n const current = parseFloat(_val as any) || 0;\n setVal(e.key === 'ArrowUp' ? current + 1 : current - 1 as any);\n }}\n onChange={(e) => {\n let val: any = e.target.value.replace(/[^0-9.]/g, '')\n const parts = val.split('.');\n if (parts.length > 2) {\n val = parts[0] + '.' + parts.slice(1).join('')\n }\n setVal(val === \".\" ? `0.` : val);\n }}\n />\n );\n});\n\nexport default InputNumber;\n"],"names":[],"mappings":";;;;;;;;;AAUA;;AACG;AACA;;;AAGG;AACG;;AAEA;;;;;;AAMN;AAEA;;;AAGG;AACA;;AAGH;;AAQS;;;;;AAMA;AACH;AAEG;;AAEA;AACG;;AAEH;;AAIZ;;"}
1
+ {"version":3,"file":"index.cjs","sources":["../../src/InputNumber/index.tsx"],"sourcesContent":["\"use client\"\nimport React, { useRef } from 'react'\nimport Input, { InputProps } from '../Input'\nimport UnfoldMore from '@xanui/icons/UnfoldMore'\nimport { useMergeRefs } from '@xanui/core'\n\nexport type InputNumberProps = Omit<InputProps, \"value\"> & {\n value?: number | \"\";\n}\n\nconst InputNumber = React.forwardRef<HTMLInputElement, InputNumberProps>((props, ref) => {\n const inputRef = useRef<any>(null)\n const mergeRef = useMergeRefs(inputRef, ref)\n const isNumeric = props.value === undefined || props.value === '' || !isNaN(Number(props.value));\n const errorProps: Partial<InputProps> = {};\n if (!isNumeric) {\n errorProps.error = true;\n errorProps.helperText = \"Value must be numeric\";\n }\n\n return (\n <Input\n {...props}\n {...errorProps}\n ref={mergeRef}\n endIcon={<UnfoldMore />}\n value={props.value ?? \"\" as any}\n onKeyDown={(e: any) => {\n props.onKeyDown?.(e);\n if (e.key !== 'ArrowUp' && e.key !== 'ArrowDown') return;\n e.preventDefault();\n const current = parseFloat(props.value as any) || 0;\n e.target.value = e.key === 'ArrowUp' ? current + 1 : current - 1 as any\n props?.onChange && props?.onChange(e)\n\n }}\n onBlur={(e) => {\n const raw = e.target.value\n if (raw === \"\" || raw === \".\") return\n const num = parseFloat(raw)\n if (!Number.isNaN(num)) {\n props?.onChange?.({\n ...e,\n target: { ...e.target, value: num },\n } as any)\n }\n }}\n\n onChange={(e) => {\n let value = e.target.value\n if (value === \"\") {\n props?.onChange?.(e)\n return\n }\n\n if (!/^\\d*\\.?\\d*$/.test(value)) return\n\n if (value === \".\") value = \"0.\"\n const nextEvent = {\n ...e,\n target: {\n ...e.target,\n value,\n },\n }\n\n props?.onChange?.(nextEvent as any)\n }}\n\n />\n );\n});\n\nexport default InputNumber;\n"],"names":[],"mappings":";;;;;;;;;AAUA;;AACG;;;;;AAKG;AACA;;AAGH;;AAQS;;;;;;AAKA;AAEH;;AAEG;AACA;;AACA;;;;AAOH;;AAGG;AACA;;;;AAKA;;;;AAGA;;;AAaZ;;"}
@@ -2,7 +2,7 @@ import React from 'react';
2
2
  import { InputProps } from '../Input/index.js';
3
3
 
4
4
  type InputNumberProps = Omit<InputProps, "value"> & {
5
- value?: number;
5
+ value?: number | "";
6
6
  };
7
7
  declare const InputNumber: React.ForwardRefExoticComponent<Omit<InputNumberProps, "ref"> & React.RefAttributes<HTMLInputElement>>;
8
8