@designbasekorea/ui 0.1.41 → 0.1.43
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.css +1 -1
- package/dist/index.css.map +1 -1
- package/dist/index.d.ts +8 -0
- package/dist/index.esm.css +1 -1
- package/dist/index.esm.css.map +1 -1
- package/dist/index.esm.js +127 -25
- package/dist/index.esm.js.map +1 -1
- package/dist/index.js +126 -24
- package/dist/index.js.map +1 -1
- package/dist/index.umd.css +1 -1
- package/dist/index.umd.css.map +1 -1
- package/dist/index.umd.js +126 -24
- package/dist/index.umd.js.map +1 -1
- package/package.json +1 -1
package/dist/index.umd.js
CHANGED
|
@@ -2266,49 +2266,49 @@
|
|
|
2266
2266
|
// 톤별 색상 팔레트
|
|
2267
2267
|
const colorPalettes = {
|
|
2268
2268
|
primary: {
|
|
2269
|
-
light: ['#
|
|
2269
|
+
light: ['#eff6ff', '#dbeafe', '#bfdbfe', '#93c5fd', '#60a5fa'], // blue-50 ~ blue-400 (더 밝게)
|
|
2270
2270
|
vivid: ['#3b82f6', '#2563eb', '#1d4ed8', '#1e40af', '#1e3a8a'], // blue-500 ~ blue-900
|
|
2271
|
-
dark: ['#
|
|
2271
|
+
dark: ['#0f172a', '#1e293b', '#334155', '#475569', '#64748b'], // slate-900 ~ slate-600 (더 어둡게)
|
|
2272
2272
|
},
|
|
2273
2273
|
secondary: {
|
|
2274
|
-
light: ['#
|
|
2274
|
+
light: ['#f8fafc', '#f1f5f9', '#e2e8f0', '#cbd5e1', '#94a3b8'], // slate-50 ~ slate-400 (더 밝게)
|
|
2275
2275
|
vivid: ['#6b7280', '#4b5563', '#374151', '#1f2937', '#111827'], // gray-500 ~ gray-900
|
|
2276
|
-
dark: ['#
|
|
2276
|
+
dark: ['#0f0f0f', '#1a1a1a', '#262626', '#404040', '#525252'], // neutral-950 ~ neutral-600 (더 어둡게)
|
|
2277
2277
|
},
|
|
2278
2278
|
success: {
|
|
2279
|
-
light: ['#
|
|
2279
|
+
light: ['#f0fdf4', '#dcfce7', '#bbf7d0', '#86efac', '#4ade80'], // green-50 ~ green-400 (더 밝게)
|
|
2280
2280
|
vivid: ['#22c55e', '#16a34a', '#15803d', '#166534', '#14532d'], // green-500 ~ green-900
|
|
2281
|
-
dark: ['#
|
|
2281
|
+
dark: ['#052e16', '#14532d', '#166534', '#15803d', '#16a34a'], // green-950 ~ green-600 (더 어둡게)
|
|
2282
2282
|
},
|
|
2283
2283
|
warning: {
|
|
2284
|
-
light: ['#
|
|
2285
|
-
vivid: ['#f59e0b', '#d97706', '#b45309', '#92400e', '#78350f'], //
|
|
2286
|
-
dark: ['#
|
|
2284
|
+
light: ['#fffbeb', '#fef3c7', '#fde68a', '#fcd34d', '#fbbf24'], // amber-50 ~ amber-400 (더 밝게)
|
|
2285
|
+
vivid: ['#f59e0b', '#d97706', '#b45309', '#92400e', '#78350f'], // amber-600 ~ amber-900
|
|
2286
|
+
dark: ['#451a03', '#78350f', '#92400e', '#b45309', '#d97706'], // amber-950 ~ amber-600 (더 어둡게)
|
|
2287
2287
|
},
|
|
2288
2288
|
error: {
|
|
2289
|
-
light: ['#
|
|
2289
|
+
light: ['#fef2f2', '#fecaca', '#fca5a5', '#f87171', '#f56565'], // red-50 ~ red-400 (더 밝게)
|
|
2290
2290
|
vivid: ['#ef4444', '#dc2626', '#b91c1c', '#991b1b', '#7f1d1d'], // red-500 ~ red-900
|
|
2291
|
-
dark: ['#
|
|
2291
|
+
dark: ['#450a0a', '#7f1d1d', '#991b1b', '#b91c1c', '#dc2626'], // red-950 ~ red-600 (더 어둡게)
|
|
2292
2292
|
},
|
|
2293
2293
|
info: {
|
|
2294
|
-
light: ['#
|
|
2294
|
+
light: ['#eff6ff', '#dbeafe', '#bfdbfe', '#93c5fd', '#60a5fa'], // blue-50 ~ blue-400 (더 밝게)
|
|
2295
2295
|
vivid: ['#3b82f6', '#2563eb', '#1d4ed8', '#1e40af', '#1e3a8a'], // blue-500 ~ blue-900
|
|
2296
|
-
dark: ['#
|
|
2296
|
+
dark: ['#0f172a', '#1e293b', '#334155', '#475569', '#64748b'], // slate-900 ~ slate-600 (더 어둡게)
|
|
2297
2297
|
},
|
|
2298
2298
|
purple: {
|
|
2299
|
-
light: ['#
|
|
2299
|
+
light: ['#faf5ff', '#f3e8ff', '#e9d5ff', '#d8b4fe', '#c084fc'], // purple-50 ~ purple-400 (더 밝게)
|
|
2300
2300
|
vivid: ['#a855f7', '#9333ea', '#7c3aed', '#6d28d9', '#5b21b6'], // purple-600 ~ purple-900
|
|
2301
|
-
dark: ['#
|
|
2301
|
+
dark: ['#3b0764', '#581c87', '#6b21a8', '#7c3aed', '#9333ea'], // purple-950 ~ purple-600 (더 어둡게)
|
|
2302
2302
|
},
|
|
2303
2303
|
ocean: {
|
|
2304
|
-
light: ['#
|
|
2304
|
+
light: ['#f0fdfa', '#ccfbf1', '#99f6e4', '#5eead4', '#2dd4bf'], // teal-50 ~ teal-400 (더 밝게)
|
|
2305
2305
|
vivid: ['#14b8a6', '#0d9488', '#0f766e', '#115e59', '#134e4a'], // teal-500 ~ teal-900
|
|
2306
|
-
dark: ['#
|
|
2306
|
+
dark: ['#042f2e', '#134e4a', '#115e59', '#0f766e', '#0d9488'], // teal-950 ~ teal-600 (더 어둡게)
|
|
2307
2307
|
},
|
|
2308
2308
|
sunset: {
|
|
2309
|
-
light: ['#
|
|
2309
|
+
light: ['#fff7ed', '#fed7aa', '#fdba74', '#fb923c', '#f97316'], // orange-50 ~ orange-500 (더 밝게)
|
|
2310
2310
|
vivid: ['#f97316', '#ea580c', '#c2410c', '#9a3412', '#7c2d12'], // orange-600 ~ orange-900
|
|
2311
|
-
dark: ['#
|
|
2311
|
+
dark: ['#431407', '#7c2d12', '#9a3412', '#c2410c', '#ea580c'], // orange-950 ~ orange-600 (더 어둡게)
|
|
2312
2312
|
},
|
|
2313
2313
|
};
|
|
2314
2314
|
const RandomGradient = ({ scheme = 'primary', tone = 'vivid', width = '100%', height = '600px', blur = 60, colorCount = 4, animated = false, animationDuration = 10, overlay = true, overlayOpacity = 0.2, children, className, }) => {
|
|
@@ -8145,10 +8145,48 @@
|
|
|
8145
8145
|
})), currentIndex: selectedImageIndex, isOpen: true, onOpenChange: handleLightboxClose, onImageChange: handleLightboxNavigate }))] }));
|
|
8146
8146
|
};
|
|
8147
8147
|
|
|
8148
|
-
const SearchBar = ({ value, defaultValue = '', placeholder = '검색...', size = 'm', variant = 'default', disabled = false, readOnly = false, fullWidth = false, searchIcon: SearchIconComponent = icons.SearchIcon, clearIcon: ClearIconComponent = icons.CloseIcon, onChange, onSearch, onFocus, onBlur, onKeyDown, className, ...props }) => {
|
|
8148
|
+
const SearchBar = ({ value, defaultValue = '', placeholder = '검색...', size = 'm', variant = 'default', disabled = false, readOnly = false, fullWidth = false, searchIcon: SearchIconComponent = icons.SearchIcon, clearIcon: ClearIconComponent = icons.CloseIcon, enableRecentSearches = false, recentSearchesKey = 'searchbar-recent-searches', suggestedSearches = [], suggestionRollingInterval = 5000, onChange, onSearch, onFocus, onBlur, onKeyDown, className, ...props }) => {
|
|
8149
8149
|
const [internalValue, setInternalValue] = React.useState(defaultValue);
|
|
8150
|
+
const [recentSearches, setRecentSearches] = React.useState([]);
|
|
8151
|
+
const [showRecentSearches, setShowRecentSearches] = React.useState(false);
|
|
8152
|
+
const [currentSuggestion, setCurrentSuggestion] = React.useState(0);
|
|
8153
|
+
const [isFocused, setIsFocused] = React.useState(false);
|
|
8150
8154
|
const inputRef = React.useRef(null);
|
|
8155
|
+
const suggestionIntervalRef = React.useRef(null);
|
|
8151
8156
|
const currentValue = value !== undefined ? value : internalValue;
|
|
8157
|
+
// 최근 검색어 로드
|
|
8158
|
+
React.useEffect(() => {
|
|
8159
|
+
if (enableRecentSearches) {
|
|
8160
|
+
try {
|
|
8161
|
+
const stored = localStorage.getItem(recentSearchesKey);
|
|
8162
|
+
if (stored) {
|
|
8163
|
+
setRecentSearches(JSON.parse(stored));
|
|
8164
|
+
}
|
|
8165
|
+
}
|
|
8166
|
+
catch (error) {
|
|
8167
|
+
console.warn('최근 검색어를 불러올 수 없습니다:', error);
|
|
8168
|
+
}
|
|
8169
|
+
}
|
|
8170
|
+
}, [enableRecentSearches, recentSearchesKey]);
|
|
8171
|
+
// 추천 검색어 롤링
|
|
8172
|
+
React.useEffect(() => {
|
|
8173
|
+
if (suggestedSearches.length > 0 && isFocused && !currentValue) {
|
|
8174
|
+
suggestionIntervalRef.current = setInterval(() => {
|
|
8175
|
+
setCurrentSuggestion(prev => (prev + 1) % suggestedSearches.length);
|
|
8176
|
+
}, suggestionRollingInterval);
|
|
8177
|
+
}
|
|
8178
|
+
else {
|
|
8179
|
+
if (suggestionIntervalRef.current) {
|
|
8180
|
+
clearInterval(suggestionIntervalRef.current);
|
|
8181
|
+
suggestionIntervalRef.current = null;
|
|
8182
|
+
}
|
|
8183
|
+
}
|
|
8184
|
+
return () => {
|
|
8185
|
+
if (suggestionIntervalRef.current) {
|
|
8186
|
+
clearInterval(suggestionIntervalRef.current);
|
|
8187
|
+
}
|
|
8188
|
+
};
|
|
8189
|
+
}, [suggestedSearches.length, isFocused, currentValue, suggestionRollingInterval]);
|
|
8152
8190
|
React.useEffect(() => {
|
|
8153
8191
|
if (value !== undefined) {
|
|
8154
8192
|
setInternalValue(value);
|
|
@@ -8164,9 +8202,24 @@
|
|
|
8164
8202
|
onChange?.('');
|
|
8165
8203
|
inputRef.current?.focus();
|
|
8166
8204
|
};
|
|
8167
|
-
const handleSearch = () => {
|
|
8168
|
-
|
|
8169
|
-
|
|
8205
|
+
const handleSearch = (searchValue) => {
|
|
8206
|
+
const searchTerm = searchValue || currentValue.trim();
|
|
8207
|
+
if (searchTerm) {
|
|
8208
|
+
onSearch?.(searchTerm);
|
|
8209
|
+
// 최근 검색어 저장
|
|
8210
|
+
if (enableRecentSearches) {
|
|
8211
|
+
const newRecentSearches = [
|
|
8212
|
+
searchTerm,
|
|
8213
|
+
...recentSearches.filter(item => item !== searchTerm)
|
|
8214
|
+
].slice(0, 10); // 최대 10개
|
|
8215
|
+
setRecentSearches(newRecentSearches);
|
|
8216
|
+
try {
|
|
8217
|
+
localStorage.setItem(recentSearchesKey, JSON.stringify(newRecentSearches));
|
|
8218
|
+
}
|
|
8219
|
+
catch (error) {
|
|
8220
|
+
console.warn('최근 검색어를 저장할 수 없습니다:', error);
|
|
8221
|
+
}
|
|
8222
|
+
}
|
|
8170
8223
|
}
|
|
8171
8224
|
};
|
|
8172
8225
|
const handleKeyDown = (e) => {
|
|
@@ -8175,6 +8228,49 @@
|
|
|
8175
8228
|
}
|
|
8176
8229
|
onKeyDown?.(e);
|
|
8177
8230
|
};
|
|
8231
|
+
const handleFocus = (e) => {
|
|
8232
|
+
setIsFocused(true);
|
|
8233
|
+
setShowRecentSearches(enableRecentSearches && recentSearches.length > 0);
|
|
8234
|
+
onFocus?.(e);
|
|
8235
|
+
};
|
|
8236
|
+
const handleBlur = (e) => {
|
|
8237
|
+
setIsFocused(false);
|
|
8238
|
+
// 약간의 지연을 두어 클릭 이벤트가 처리되도록 함
|
|
8239
|
+
setTimeout(() => {
|
|
8240
|
+
setShowRecentSearches(false);
|
|
8241
|
+
}, 200);
|
|
8242
|
+
onBlur?.(e);
|
|
8243
|
+
};
|
|
8244
|
+
const handleRecentSearchClick = (searchTerm) => {
|
|
8245
|
+
setInternalValue(searchTerm);
|
|
8246
|
+
onChange?.(searchTerm);
|
|
8247
|
+
setShowRecentSearches(false);
|
|
8248
|
+
handleSearch(searchTerm);
|
|
8249
|
+
};
|
|
8250
|
+
const handleRemoveRecentSearch = (searchTerm) => {
|
|
8251
|
+
const newRecentSearches = recentSearches.filter(item => item !== searchTerm);
|
|
8252
|
+
setRecentSearches(newRecentSearches);
|
|
8253
|
+
try {
|
|
8254
|
+
localStorage.setItem(recentSearchesKey, JSON.stringify(newRecentSearches));
|
|
8255
|
+
}
|
|
8256
|
+
catch (error) {
|
|
8257
|
+
console.warn('최근 검색어를 삭제할 수 없습니다:', error);
|
|
8258
|
+
}
|
|
8259
|
+
};
|
|
8260
|
+
const handleClearAllRecentSearches = () => {
|
|
8261
|
+
setRecentSearches([]);
|
|
8262
|
+
try {
|
|
8263
|
+
localStorage.removeItem(recentSearchesKey);
|
|
8264
|
+
}
|
|
8265
|
+
catch (error) {
|
|
8266
|
+
console.warn('최근 검색어를 모두 삭제할 수 없습니다:', error);
|
|
8267
|
+
}
|
|
8268
|
+
};
|
|
8269
|
+
const handleSuggestionClick = (suggestion) => {
|
|
8270
|
+
setInternalValue(suggestion);
|
|
8271
|
+
onChange?.(suggestion);
|
|
8272
|
+
handleSearch(suggestion);
|
|
8273
|
+
};
|
|
8178
8274
|
const classes = clsx('designbase-search-bar', `designbase-search-bar--${size}`, `designbase-search-bar--${variant}`, {
|
|
8179
8275
|
'designbase-search-bar--disabled': disabled,
|
|
8180
8276
|
'designbase-search-bar--readonly': readOnly,
|
|
@@ -8185,7 +8281,13 @@
|
|
|
8185
8281
|
'designbase-search-bar__input--disabled': disabled,
|
|
8186
8282
|
'designbase-search-bar__input--readonly': readOnly,
|
|
8187
8283
|
});
|
|
8188
|
-
|
|
8284
|
+
// 현재 플레이스홀더 (추천 검색어가 있으면 롤링)
|
|
8285
|
+
const currentPlaceholder = suggestedSearches.length > 0 && isFocused && !currentValue
|
|
8286
|
+
? suggestedSearches[currentSuggestion]
|
|
8287
|
+
: placeholder;
|
|
8288
|
+
return (jsxRuntime.jsxs("div", { className: classes, role: "search", children: [jsxRuntime.jsxs("div", { className: "designbase-search-bar__container", children: [jsxRuntime.jsx("div", { className: "designbase-search-bar__search-icon", children: jsxRuntime.jsx(SearchIconComponent, { size: size === 's' ? 16 : size === 'l' ? 24 : 20 }) }), jsxRuntime.jsx("input", { ref: inputRef, type: "text", className: inputClasses, value: currentValue, placeholder: currentPlaceholder, disabled: disabled, readOnly: readOnly, onChange: handleChange, onFocus: handleFocus, onBlur: handleBlur, onKeyDown: handleKeyDown, "aria-label": "\uAC80\uC0C9\uC5B4 \uC785\uB825", ...props }), currentValue && currentValue.length > 0 && !disabled && !readOnly && (jsxRuntime.jsx("button", { type: "button", className: "designbase-search-bar__clear-button", onClick: handleClear, "aria-label": "\uAC80\uC0C9\uC5B4 \uC9C0\uC6B0\uAE30", children: jsxRuntime.jsx(ClearIconComponent, { size: size === 's' ? 16 : size === 'l' ? 24 : 20 }) }))] }), showRecentSearches && recentSearches.length > 0 && (jsxRuntime.jsxs("div", { className: "designbase-search-bar__recent-searches", children: [jsxRuntime.jsxs("div", { className: "designbase-search-bar__recent-header", children: [jsxRuntime.jsx("span", { className: "designbase-search-bar__recent-title", children: "\uCD5C\uADFC \uAC80\uC0C9\uC5B4" }), jsxRuntime.jsx("button", { type: "button", className: "designbase-search-bar__clear-all-button", onClick: handleClearAllRecentSearches, "aria-label": "\uBAA8\uB4E0 \uCD5C\uADFC \uAC80\uC0C9\uC5B4 \uC0AD\uC81C", children: "\uC804\uCCB4 \uC0AD\uC81C" })] }), jsxRuntime.jsx("div", { className: "designbase-search-bar__recent-list", children: recentSearches.map((searchTerm, index) => (jsxRuntime.jsxs("div", { className: "designbase-search-bar__recent-item", children: [jsxRuntime.jsx("button", { type: "button", className: "designbase-search-bar__recent-search-button", onClick: () => handleRecentSearchClick(searchTerm), children: searchTerm }), jsxRuntime.jsx("button", { type: "button", className: "designbase-search-bar__recent-remove-button", onClick: () => handleRemoveRecentSearch(searchTerm), "aria-label": `${searchTerm} 삭제`, children: jsxRuntime.jsx(icons.XIcon, { size: 16 }) })] }, index))) })] })), suggestedSearches.length > 0 && isFocused && !currentValue && (jsxRuntime.jsxs("div", { className: "designbase-search-bar__suggestions", children: [jsxRuntime.jsx("div", { className: "designbase-search-bar__suggestions-header", children: jsxRuntime.jsx("span", { className: "designbase-search-bar__suggestions-title", children: "\uCD94\uCC9C \uAC80\uC0C9\uC5B4" }) }), jsxRuntime.jsx("div", { className: "designbase-search-bar__suggestions-list", children: suggestedSearches.map((suggestion, index) => (jsxRuntime.jsx("button", { type: "button", className: clsx('designbase-search-bar__suggestion-item', {
|
|
8289
|
+
'designbase-search-bar__suggestion-item--active': index === currentSuggestion
|
|
8290
|
+
}), onClick: () => handleSuggestionClick(suggestion), children: suggestion }, index))) })] }))] }));
|
|
8189
8291
|
};
|
|
8190
8292
|
SearchBar.displayName = 'SearchBar';
|
|
8191
8293
|
|