1
This commit is contained in:
+105
@@ -0,0 +1,105 @@
|
||||
"use client";
|
||||
|
||||
import React from 'react';
|
||||
import CloseOutlined from "@ant-design/icons/es/icons/CloseOutlined";
|
||||
import pickAttrs from "@rc-component/util/es/pickAttrs";
|
||||
import { useLocale } from '../../locale';
|
||||
import defaultLocale from '../../locale/en_US';
|
||||
import extendsObject from '../extendsObject';
|
||||
import { isNonNullable, isPlainObject } from '../is';
|
||||
export const pickClosable = context => {
|
||||
if (!context) {
|
||||
return undefined;
|
||||
}
|
||||
const {
|
||||
closable,
|
||||
closeIcon
|
||||
} = context;
|
||||
return {
|
||||
closable,
|
||||
closeIcon
|
||||
};
|
||||
};
|
||||
const EmptyFallbackCloseCollection = {};
|
||||
const computeClosableConfig = (closable, closeIcon) => {
|
||||
if (!closable && (closable === false || closeIcon === false || closeIcon === null)) {
|
||||
return false;
|
||||
}
|
||||
if (closable === undefined && closeIcon === undefined) {
|
||||
return null;
|
||||
}
|
||||
let closableConfig = {
|
||||
closeIcon: typeof closeIcon !== 'boolean' && closeIcon !== null ? closeIcon : undefined
|
||||
};
|
||||
if (isPlainObject(closable)) {
|
||||
closableConfig = {
|
||||
...closableConfig,
|
||||
...closable
|
||||
};
|
||||
}
|
||||
return closableConfig;
|
||||
};
|
||||
const mergeClosableConfigs = (propConfig, contextConfig, fallbackConfig) => {
|
||||
if (propConfig === false) {
|
||||
return false;
|
||||
}
|
||||
if (propConfig) {
|
||||
return extendsObject(fallbackConfig, contextConfig, propConfig);
|
||||
}
|
||||
if (contextConfig === false) {
|
||||
return false;
|
||||
}
|
||||
if (contextConfig) {
|
||||
return extendsObject(fallbackConfig, contextConfig);
|
||||
}
|
||||
return fallbackConfig.closable ? fallbackConfig : false;
|
||||
};
|
||||
const computeCloseIcon = (mergedConfig, fallbackCloseCollection, closeLabel) => {
|
||||
const {
|
||||
closeIconRender
|
||||
} = fallbackCloseCollection;
|
||||
const {
|
||||
closeIcon,
|
||||
...restConfig
|
||||
} = mergedConfig;
|
||||
let finalCloseIcon = closeIcon;
|
||||
const ariaOrDataProps = pickAttrs(restConfig, true);
|
||||
if (isNonNullable(finalCloseIcon)) {
|
||||
if (closeIconRender) {
|
||||
finalCloseIcon = closeIconRender(finalCloseIcon);
|
||||
}
|
||||
finalCloseIcon = /*#__PURE__*/React.isValidElement(finalCloseIcon) ? (/*#__PURE__*/React.cloneElement(finalCloseIcon, {
|
||||
'aria-label': closeLabel,
|
||||
...finalCloseIcon.props,
|
||||
...ariaOrDataProps
|
||||
})) : (/*#__PURE__*/React.createElement("span", {
|
||||
"aria-label": closeLabel,
|
||||
...ariaOrDataProps
|
||||
}, finalCloseIcon));
|
||||
}
|
||||
return [finalCloseIcon, ariaOrDataProps];
|
||||
};
|
||||
export const computeClosable = (propCloseCollection, contextCloseCollection, fallbackCloseCollection = EmptyFallbackCloseCollection, closeLabel = 'Close') => {
|
||||
const propConfig = computeClosableConfig(propCloseCollection?.closable, propCloseCollection?.closeIcon);
|
||||
const contextConfig = computeClosableConfig(contextCloseCollection?.closable, contextCloseCollection?.closeIcon);
|
||||
const mergedFallback = {
|
||||
closeIcon: /*#__PURE__*/React.createElement(CloseOutlined, null),
|
||||
...fallbackCloseCollection
|
||||
};
|
||||
const mergedConfig = mergeClosableConfigs(propConfig, contextConfig, mergedFallback);
|
||||
const closeBtnIsDisabled = typeof mergedConfig !== 'boolean' ? !!mergedConfig?.disabled : false;
|
||||
if (mergedConfig === false) {
|
||||
return [false, null, closeBtnIsDisabled, {}];
|
||||
}
|
||||
const [closeIcon, ariaProps] = computeCloseIcon(mergedConfig, mergedFallback, closeLabel);
|
||||
return [true, closeIcon, closeBtnIsDisabled, ariaProps];
|
||||
};
|
||||
export const useClosable = (propCloseCollection, contextCloseCollection, fallbackCloseCollection = EmptyFallbackCloseCollection) => {
|
||||
const [contextLocale] = useLocale('global', defaultLocale.global);
|
||||
return React.useMemo(() => {
|
||||
return computeClosable(propCloseCollection, contextCloseCollection, {
|
||||
closeIcon: /*#__PURE__*/React.createElement(CloseOutlined, null),
|
||||
...fallbackCloseCollection
|
||||
}, contextLocale.close);
|
||||
}, [propCloseCollection, contextCloseCollection, fallbackCloseCollection, contextLocale.close]);
|
||||
};
|
||||
Reference in New Issue
Block a user