@neuctra/ui 0.2.3 → 0.2.5

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.
Files changed (38) hide show
  1. package/dist/components/basic/Alert.d.ts +0 -1
  2. package/dist/components/basic/Card.d.ts +1 -1
  3. package/dist/components/basic/{CheckRadioInput.d.ts → CheckboxGroup.d.ts} +4 -7
  4. package/dist/components/basic/DropDown.d.ts +24 -34
  5. package/dist/components/basic/Modal.d.ts +2 -9
  6. package/dist/components/basic/RadioGroup.d.ts +25 -0
  7. package/dist/components/basic/SwitchGroup.d.ts +25 -0
  8. package/dist/index.cjs.js +41 -52
  9. package/dist/index.cjs.js.map +1 -1
  10. package/dist/index.d.ts +3 -1
  11. package/dist/index.es.js +1920 -1893
  12. package/dist/index.es.js.map +1 -1
  13. package/dist/src/components/basic/Alert.js +45 -30
  14. package/dist/src/components/basic/Card.js +12 -10
  15. package/dist/src/components/basic/CheckboxGroup.js +40 -0
  16. package/dist/src/components/basic/DropDown.js +140 -294
  17. package/dist/src/components/basic/Modal.js +10 -12
  18. package/dist/src/components/basic/RadioGroup.js +37 -0
  19. package/dist/src/components/basic/SwitchGroup.js +50 -0
  20. package/dist/src/components/basic/Table.js +30 -11
  21. package/dist/src/index.js +4 -2
  22. package/dist/types/src/components/basic/Alert.d.ts +0 -1
  23. package/dist/types/src/components/basic/Card.d.ts +1 -1
  24. package/dist/types/src/components/basic/{CheckRadioInput.d.ts → CheckboxGroup.d.ts} +4 -7
  25. package/dist/types/src/components/basic/DropDown.d.ts +24 -34
  26. package/dist/types/src/components/basic/Modal.d.ts +2 -9
  27. package/dist/types/src/components/basic/RadioGroup.d.ts +25 -0
  28. package/dist/types/src/components/basic/SwitchGroup.d.ts +25 -0
  29. package/dist/types/src/index.d.ts +3 -1
  30. package/dist/ui.css +1 -1
  31. package/package.json +1 -1
  32. package/dist/components/avatar/AvatarGroup.d.ts +0 -9
  33. package/dist/components/avatar/AvatarWithStatus.d.ts +0 -10
  34. package/dist/src/components/avatar/AvatarGroup.js +0 -9
  35. package/dist/src/components/avatar/AvatarWithStatus.js +0 -18
  36. package/dist/src/components/basic/CheckRadioInput.js +0 -83
  37. package/dist/types/src/components/avatar/AvatarGroup.d.ts +0 -9
  38. package/dist/types/src/components/avatar/AvatarWithStatus.d.ts +0 -10
@@ -1,4 +1,4 @@
1
- import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
1
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
2
  import { useEffect, useState, useMemo } from "react";
3
3
  import { X, Info, CheckCircle, AlertCircle, AlertTriangle, } from "lucide-react";
4
4
  const typeStyles = {
@@ -27,7 +27,6 @@ const typeStyles = {
27
27
  Icon: _jsx(Info, { size: 20 }),
28
28
  },
29
29
  };
30
- /** 📍 Dynamic position styles */
31
30
  const getPositionStyle = (position) => {
32
31
  const base = {
33
32
  position: "fixed",
@@ -50,22 +49,24 @@ const getPositionStyle = (position) => {
50
49
  return { ...base, bottom: "1.25rem", right: "1.25rem" };
51
50
  }
52
51
  };
53
- /** 🎯 Production-grade Alert Component */
54
52
  export const Alert = ({ title, description, type = "info", dismissible = true, duration, onClose, icon, actionButton, position = "top-right", backgroundColor, borderColor, textColor = "#111827", borderRadius = "0.75rem", shadow = "0 4px 14px rgba(0,0,0,0.1)", padding = "1rem", fontSize = "0.95rem", fontWeight = 500, descriptionColor = "#374151", animationDuration = "300ms", maxWidth = "480px", className = "", style, }) => {
55
- const [visible, setVisible] = useState(true);
56
- /** Auto-dismiss after duration */
53
+ const [visible, setVisible] = useState(false);
54
+ const [exiting, setExiting] = useState(false);
57
55
  useEffect(() => {
56
+ setVisible(true);
58
57
  if (duration) {
59
58
  const timer = setTimeout(() => {
60
- setVisible(false);
61
- onClose?.();
59
+ setExiting(true);
60
+ setTimeout(() => {
61
+ setVisible(false);
62
+ onClose?.();
63
+ }, parseInt(animationDuration));
62
64
  }, duration);
63
65
  return () => clearTimeout(timer);
64
66
  }
65
- }, [duration, onClose]);
67
+ }, [duration, onClose, animationDuration]);
66
68
  const { bg, border, iconColor, Icon } = typeStyles[type];
67
69
  const positionStyle = getPositionStyle(position);
68
- /** Combine computed and custom styles */
69
70
  const containerStyle = useMemo(() => ({
70
71
  ...positionStyle,
71
72
  display: "flex",
@@ -79,18 +80,19 @@ export const Alert = ({ title, description, type = "info", dismissible = true, d
79
80
  padding,
80
81
  maxWidth,
81
82
  width: "calc(100% - 2.5rem)",
82
- opacity: visible ? 1 : 0,
83
- transform: visible
84
- ? position.includes("bottom")
85
- ? "translateY(0)"
86
- : "translateY(0)"
83
+ opacity: visible && !exiting ? 1 : 0,
84
+ transform: visible && !exiting
85
+ ? "translateY(0)"
87
86
  : position.includes("bottom")
88
87
  ? "translateY(20px)"
89
88
  : "translateY(-20px)",
90
89
  transition: `opacity ${animationDuration} ease, transform ${animationDuration} ease`,
90
+ fontWeight,
91
+ fontSize,
91
92
  ...style,
92
93
  }), [
93
94
  visible,
95
+ exiting,
94
96
  bg,
95
97
  border,
96
98
  borderColor,
@@ -103,24 +105,37 @@ export const Alert = ({ title, description, type = "info", dismissible = true, d
103
105
  backgroundColor,
104
106
  animationDuration,
105
107
  style,
108
+ fontSize,
109
+ fontWeight,
106
110
  ]);
107
111
  if (!visible)
108
112
  return null;
109
- return (_jsxs("div", { className: className, style: containerStyle, role: "alert", children: [_jsx("div", { style: { color: iconColor, marginTop: "2px" }, children: icon || Icon }), _jsxs("div", { style: { flex: 1, minWidth: 0 }, children: [title && (_jsx("div", { style: { fontWeight: 600, fontSize, marginBottom: "4px" }, children: title })), description && (_jsx("div", { style: {
110
- fontSize: "0.875rem",
111
- color: descriptionColor,
112
- lineHeight: 1.4,
113
- }, children: description })), actionButton && (_jsx("div", { style: { marginTop: "8px" }, children: actionButton }))] }), dismissible && (_jsx("button", { onClick: () => {
114
- setVisible(false);
115
- onClose?.();
116
- }, style: {
117
- background: "transparent",
118
- border: "none",
119
- color: "#6b7280",
120
- cursor: "pointer",
121
- marginLeft: "8px",
122
- padding: 0,
123
- lineHeight: 0,
124
- }, "aria-label": "Close alert", children: _jsx(X, { size: 16 }) }))] }));
113
+ return (_jsxs(_Fragment, { children: [_jsx("style", { children: `
114
+ @keyframes alert-slide-in-top {
115
+ from { opacity: 0; transform: translateY(-20px); }
116
+ to { opacity: 1; transform: translateY(0); }
117
+ }
118
+ @keyframes alert-slide-in-bottom {
119
+ from { opacity: 0; transform: translateY(20px); }
120
+ to { opacity: 1; transform: translateY(0); }
121
+ }
122
+ ` }), _jsxs("div", { className: className, style: {
123
+ ...containerStyle,
124
+ animation: `${position.includes("bottom") ? "alert-slide-in-bottom" : "alert-slide-in-top"} ${animationDuration} ease`,
125
+ }, role: "alert", children: [_jsx("div", { style: { color: iconColor, marginTop: "2px" }, children: icon || Icon }), _jsxs("div", { style: { flex: 1, minWidth: 0 }, children: [title && (_jsx("div", { style: { fontWeight: 600, fontSize, marginBottom: "4px" }, children: title })), description && (_jsx("div", { style: { fontSize: "0.875rem", color: descriptionColor, lineHeight: 1.4 }, children: description })), actionButton && _jsx("div", { style: { marginTop: "8px" }, children: actionButton })] }), dismissible && (_jsx("button", { onClick: () => {
126
+ setExiting(true);
127
+ setTimeout(() => {
128
+ setVisible(false);
129
+ onClose?.();
130
+ }, parseInt(animationDuration));
131
+ }, style: {
132
+ background: "transparent",
133
+ border: "none",
134
+ color: "#6b7280",
135
+ cursor: "pointer",
136
+ marginLeft: "8px",
137
+ padding: 0,
138
+ lineHeight: 0,
139
+ }, "aria-label": "Close alert", children: _jsx(X, { size: 16 }) }))] })] }));
125
140
  };
126
141
  Alert.displayName = "Alert";
@@ -2,7 +2,7 @@ import { jsx as _jsx } from "react/jsx-runtime";
2
2
  import { forwardRef, } from "react";
3
3
  const CardInner = ({ as, children, className = "", variant = "elevated", background = "#fff", textColor = "#000", borderRadius = 12, border, boxShadow, hoverShadow, padding = 16, margin, width, height, style = {}, hoverStyle = {}, onClick, ...rest }, ref) => {
4
4
  const Component = as || "div";
5
- // Default styling based on variant
5
+ // Default styling for known variants; unknown variants can be customized
6
6
  const baseVariantStyles = {
7
7
  elevated: {
8
8
  boxShadow: boxShadow || "0 4px 12px rgba(0,0,0,0.08)",
@@ -28,17 +28,19 @@ const CardInner = ({ as, children, className = "", variant = "elevated", backgro
28
28
  transition: "all 0.25s ease",
29
29
  cursor: onClick ? "pointer" : undefined,
30
30
  boxSizing: "border-box",
31
- ...baseVariantStyles[variant],
31
+ ...(baseVariantStyles[variant] || {}), // fallback if variant is custom
32
32
  ...style,
33
33
  };
34
- return (_jsx(Component, { ref: ref, className: `ui-card ${className}`, style: cardStyle, onClick: onClick, onMouseEnter: (e) => {
35
- Object.assign(e.currentTarget.style, hoverShadow ? { boxShadow: hoverShadow } : hoverStyle);
36
- }, onMouseLeave: (e) => {
37
- Object.assign(e.currentTarget.style, {
38
- ...baseVariantStyles[variant],
39
- ...style,
40
- });
41
- }, ...rest, children: children }));
34
+ const handleMouseEnter = (e) => {
35
+ Object.assign(e.currentTarget.style, hoverShadow ? { boxShadow: hoverShadow } : hoverStyle);
36
+ };
37
+ const handleMouseLeave = (e) => {
38
+ Object.assign(e.currentTarget.style, {
39
+ ...cardStyle,
40
+ ...(baseVariantStyles[variant] || {}),
41
+ });
42
+ };
43
+ return (_jsx(Component, { ref: ref, className: `ui-card ${className}`, style: cardStyle, onClick: onClick, onMouseEnter: handleMouseEnter, onMouseLeave: handleMouseLeave, ...rest, children: children }));
42
44
  };
43
45
  const ForwardedCard = forwardRef(CardInner);
44
46
  const Card = Object.assign(ForwardedCard, { displayName: "Card" });
@@ -0,0 +1,40 @@
1
+ "use client";
2
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
3
+ export const CheckboxGroup = ({ name, options, selectedValues = [], onChange, disabled = false, readOnly = false, required = false, error, className = "", customIcon, style, labelStyle, iconSize = 20, iconCheckedBgColor = "#2563eb", iconUncheckedBorderColor = "#9ca3af", textColor = "#374151", errorStyle, }) => {
4
+ const handleChange = (value) => {
5
+ if (!onChange)
6
+ return;
7
+ const updatedValues = selectedValues.includes(value)
8
+ ? selectedValues.filter((v) => v !== value)
9
+ : [...selectedValues, value];
10
+ onChange(updatedValues);
11
+ };
12
+ return (_jsxs("div", { className: className, style: { display: "flex", flexDirection: "column", gap: 8, ...style }, role: "group", "aria-disabled": disabled, children: [options.map((option) => {
13
+ const isChecked = selectedValues.includes(option.value);
14
+ return (_jsxs("label", { style: {
15
+ display: "flex",
16
+ alignItems: "center",
17
+ justifyContent: "space-between",
18
+ cursor: disabled ? "not-allowed" : "pointer",
19
+ opacity: disabled ? 0.6 : 1,
20
+ gap: 8,
21
+ userSelect: "none",
22
+ ...labelStyle,
23
+ }, children: [_jsx("span", { style: { color: textColor, fontSize: 14 }, children: option.label }), _jsx("input", { type: "checkbox", name: name, value: option.value, checked: isChecked, disabled: disabled || readOnly, required: required, onChange: () => handleChange(option.value), style: { display: "none" } }), customIcon ? (customIcon(isChecked)) : (_jsx("span", { style: {
24
+ display: "inline-flex",
25
+ justifyContent: "center",
26
+ alignItems: "center",
27
+ width: iconSize,
28
+ height: iconSize,
29
+ borderRadius: 4,
30
+ border: `2px solid ${isChecked ? iconCheckedBgColor : iconUncheckedBorderColor}`,
31
+ backgroundColor: isChecked ? iconCheckedBgColor : "transparent",
32
+ transition: "all 0.25s ease",
33
+ }, children: isChecked && (_jsx("svg", { viewBox: "0 0 24 24", fill: "none", stroke: "white", strokeWidth: 3, strokeLinecap: "round", strokeLinejoin: "round", style: { width: iconSize * 0.6, height: iconSize * 0.6 }, children: _jsx("polyline", { points: "20 6 9 17 4 12" }) })) }))] }, option.value));
34
+ }), error && (_jsx("p", { role: "alert", style: {
35
+ color: "#dc2626",
36
+ fontSize: 12,
37
+ marginTop: 4,
38
+ ...errorStyle,
39
+ }, children: error }))] }));
40
+ };