@nutui/nutui-react
Version:
京东风格的轻量级移动端 React 组件库,支持一套代码生成 H5 和小程序
409 lines (408 loc) • 18.7 kB
JavaScript
Object.defineProperty(exports, "__esModule", {
value: true
});
Object.defineProperty(exports, "Cascader", {
enumerable: true,
get: function() {
return Cascader;
}
});
var _interop_require_default = require("@swc/helpers/_/_interop_require_default");
var _interop_require_wildcard = require("@swc/helpers/_/_interop_require_wildcard");
var _async_to_generator = require("@swc/helpers/_/_async_to_generator");
var _define_property = require("@swc/helpers/_/_define_property");
var _object_spread = require("@swc/helpers/_/_object_spread");
var _object_spread_props = require("@swc/helpers/_/_object_spread_props");
var _sliced_to_array = require("@swc/helpers/_/_sliced_to_array");
var _ts_generator = require("@swc/helpers/_/_ts_generator");
var _react = /*#__PURE__*/ _interop_require_wildcard._(require("react"));
var _iconsreact = require("@nutui/icons-react");
var _classnames = /*#__PURE__*/ _interop_require_default._(require("classnames"));
var _tabs = /*#__PURE__*/ _interop_require_default._(require("../tabs"));
var _popup = /*#__PURE__*/ _interop_require_default._(require("../popup"));
var _utils = require("./utils");
var _typings = require("../../utils/typings");
var _mergeprops = require("../../utils/merge-props");
var _usepropsvalue = require("../../hooks/use-props-value");
var _isempty = require("../../utils/is-empty");
var _userefstate = require("../../hooks/use-ref-state");
var _configprovider = require("../configprovider");
var defaultProps = (0, _object_spread_props._)((0, _object_spread._)({}, _typings.ComponentDefaults), {
activeColor: '',
activeIcon: 'checklist',
popup: true,
options: [],
optionKey: {},
format: {},
closeable: false,
closeIconPosition: 'top-right',
closeIcon: 'close',
lazy: false,
onClose: function onClose() {},
onChange: function onChange() {},
onPathChange: function onPathChange() {}
});
var Cascader = /*#__PURE__*/ (0, _react.forwardRef)(function(props, ref) {
var classPrefix = 'nut-cascader';
var classPane = "".concat(classPrefix, "-pane");
var _mergeProps = (0, _mergeprops.mergeProps)(defaultProps, props), activeColor = _mergeProps.activeColor, activeIcon = _mergeProps.activeIcon, popup = _mergeProps.popup, _mergeProps_popupProps = _mergeProps.popupProps, popupProps = _mergeProps_popupProps === void 0 ? {} : _mergeProps_popupProps, outerVisible = _mergeProps.visible, outerOptions = _mergeProps.options, outerValue = _mergeProps.value, outerDefaultValue = _mergeProps.defaultValue, optionKey = _mergeProps.optionKey, format = _mergeProps.format, closeable = _mergeProps.closeable, closeIconPosition = _mergeProps.closeIconPosition, closeIcon = _mergeProps.closeIcon, lazy = _mergeProps.lazy, onLoad = _mergeProps.onLoad;
var locale = (0, _configprovider.useConfig)().locale;
var _useState = (0, _sliced_to_array._)((0, _react.useState)(0), 2), tabActiveIndex = _useState[0], setTabActiveIndex = _useState[1];
var _useRefState = (0, _sliced_to_array._)((0, _userefstate.useRefState)(outerOptions), 2), optionsRef = _useRefState[0], setInnerOptions = _useRefState[1];
var innerOptions = (0, _userefstate.getRefValue)(optionsRef);
var _useState1 = (0, _sliced_to_array._)((0, _react.useState)({}), 2), loading = _useState1[0], setLoading = _useState1[1];
var _usePropsValue = (0, _sliced_to_array._)((0, _usepropsvalue.usePropsValue)({
value: outerValue,
defaultValue: outerDefaultValue,
finalValue: [],
onChange: function onChange(value) {
var _props_onChange, _props_onPathChange;
(_props_onChange = props.onChange) === null || _props_onChange === void 0 ? void 0 : _props_onChange.call(props, value, pathNodes.current);
(_props_onPathChange = props.onPathChange) === null || _props_onPathChange === void 0 ? void 0 : _props_onPathChange.call(props, value, pathNodes.current);
}
}), 2), value = _usePropsValue[0], setValue = _usePropsValue[1];
var _useState2 = (0, _sliced_to_array._)((0, _react.useState)(value), 2), innerValue = _useState2[0], setInnerValue = _useState2[1];
var options = (0, _react.useMemo)(function() {
if (!(0, _isempty.isEmpty)(format)) {
return (0, _utils.normalizeListOptions)(innerOptions, format);
}
if (!(0, _isempty.isEmpty)(optionKey)) {
return (0, _utils.normalizeOptions)(innerOptions, optionKey);
}
return innerOptions;
}, [
innerOptions,
optionKey,
format,
innerValue
]);
var pathNodes = (0, _react.useRef)([]);
var levels = (0, _react.useMemo)(function() {
var next = [];
var end = false;
var currentOptions = options;
var _iteratorNormalCompletion = true, _didIteratorError = false, _iteratorError = undefined;
try {
var _loop = function _loop() {
var _step_value = (0, _sliced_to_array._)(_step.value, 2), index = _step_value[0], val = _step_value[1];
var opt = currentOptions === null || currentOptions === void 0 ? void 0 : currentOptions.find(function(o) {
return o.value === val;
});
next.push({
selected: val,
pane: currentOptions
});
pathNodes.current[index] = opt;
if (opt === null || opt === void 0 ? void 0 : opt.children) {
currentOptions = opt.children;
} else {
end = true;
return "break";
}
};
for(var _iterator = innerValue.entries()[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true){
var _ret = _loop();
if (_ret === "break") break;
}
} catch (err) {
_didIteratorError = true;
_iteratorError = err;
} finally{
try {
if (!_iteratorNormalCompletion && _iterator.return != null) {
_iterator.return();
}
} finally{
if (_didIteratorError) {
throw _iteratorError;
}
}
}
if (!end) {
next.push({
selected: null,
pane: currentOptions
});
}
return next;
}, [
innerValue,
options,
innerOptions
]);
var _usePropsValue1 = (0, _sliced_to_array._)((0, _usepropsvalue.usePropsValue)({
value: outerVisible,
defaultValue: undefined,
onChange: function onChange(value) {
if (value === false) {
var _props_onClose;
(_props_onClose = props.onClose) === null || _props_onClose === void 0 ? void 0 : _props_onClose.call(props);
}
}
}), 2), visible = _usePropsValue1[0], setVisible = _usePropsValue1[1];
var actions = {
open: function open() {
setVisible(true);
},
close: function close() {
setVisible(false);
}
};
(0, _react.useImperativeHandle)(ref, function() {
return actions;
});
(0, _react.useEffect)(function() {
if (!visible) {
setInnerValue(value);
}
}, [
visible,
value
]);
(0, _react.useEffect)(function() {
setInnerOptions(outerOptions);
}, [
outerOptions
]);
(0, _react.useEffect)(function() {
setTabActiveIndex(levels.length - 1);
}, [
innerValue,
innerOptions,
outerOptions
]);
(0, _react.useEffect)(function() {
var max = levels.length - 1;
if (tabActiveIndex > max) {
setTabActiveIndex(max);
}
}, [
tabActiveIndex,
levels,
innerOptions,
outerOptions
]);
(0, _react.useEffect)(function() {
var load = /*#__PURE__*/ function() {
var _ref = (0, _async_to_generator._)(function() {
var parent, error;
return (0, _ts_generator._)(this, function(_state) {
switch(_state.label){
case 0:
parent = {
children: []
};
_state.label = 1;
case 1:
_state.trys.push([
1,
3,
,
4
]);
return [
4,
innerValue.reduce(/*#__PURE__*/ function() {
var _ref = (0, _async_to_generator._)(function(promise, val, key) {
var pane, parent, node;
return (0, _ts_generator._)(this, function(_state) {
switch(_state.label){
case 0:
return [
4,
onLoad({
value: val
}, key)
];
case 1:
pane = _state.sent();
return [
4,
promise
];
case 2:
parent = _state.sent();
parent.children = pane;
if (key === innerValue.length - 1) {
return [
2,
Promise.resolve(parent)
];
}
if (pane) {
node = pane.find(function(p) {
return p.value === val;
});
return [
2,
Promise.resolve(node)
];
}
return [
2
];
}
});
});
return function(promise, val, key) {
return _ref.apply(this, arguments);
};
}(), Promise.resolve(parent))
];
case 2:
_state.sent();
// 如果需要处理最终结果,可以在这里使用 last
setInnerOptions(parent.children);
return [
3,
4
];
case 3:
error = _state.sent();
console.error('Error loading data:', error);
return [
3,
4
];
case 4:
return [
2
];
}
});
});
return function load() {
return _ref.apply(this, arguments);
};
}();
if (lazy) load();
}, [
lazy
]);
var chooseItem = /*#__PURE__*/ function() {
var _ref = (0, _async_to_generator._)(function(pane, levelIndex) {
var nextValue, nextPathNodes, _props_onPathChange, asyncOptions;
return (0, _ts_generator._)(this, function(_state) {
switch(_state.label){
case 0:
if (pane.disabled) return [
2
];
nextValue = innerValue.slice(0, levelIndex);
nextPathNodes = pathNodes.current.slice(0, levelIndex);
if (pane.value) {
;
setLoading(!!onLoad && (0, _define_property._)({}, levelIndex, pane.value));
nextValue[levelIndex] = pane.value;
nextPathNodes[levelIndex] = pane;
pathNodes.current = nextPathNodes;
props === null || props === void 0 ? void 0 : (_props_onPathChange = props.onPathChange) === null || _props_onPathChange === void 0 ? void 0 : _props_onPathChange.call(props, nextValue, pathNodes.current);
}
if (!onLoad) return [
3,
3
];
if (!!pane.leaf) return [
3,
2
];
return [
4,
onLoad(pane, levelIndex)
];
case 1:
asyncOptions = _state.sent();
// 修改 options 触发渲染逻辑
if (asyncOptions) pane.children = asyncOptions;
return [
3,
3
];
case 2:
setVisible(false);
setValue(nextValue);
_state.label = 3;
case 3:
if (!pane.children && !onLoad) {
setVisible(false);
setValue(nextValue);
}
setInnerValue(nextValue);
setLoading({});
return [
2
];
}
});
});
return function chooseItem(pane, levelIndex) {
return _ref.apply(this, arguments);
};
}();
var renderCascaderItem = function renderCascaderItem(item, levelIndex) {
var _item_pane;
return (_item_pane = item.pane) === null || _item_pane === void 0 ? void 0 : _item_pane.map(function(pane, index) {
var active = item.selected === pane.value;
var classes = (0, _classnames.default)({
active: active,
disabled: pane.disabled
}, 'nut-cascader-item');
var showLoadingIcon = loading[levelIndex] === pane.value;
return /*#__PURE__*/ _react.default.createElement("div", {
className: classes,
style: {
color: active ? activeColor : ''
},
key: pane.value,
onClick: function onClick() {
chooseItem(pane, levelIndex);
}
}, /*#__PURE__*/ _react.default.createElement("div", {
className: "nut-cascader-item-title"
}, pane.text), showLoadingIcon && /*#__PURE__*/ _react.default.createElement(_iconsreact.Loading, {
color: "#969799",
className: "nut-cascader-item-icon-loading"
}), active && /*#__PURE__*/ /*#__PURE__*/ ((0, _react.isValidElement)(activeIcon) ? activeIcon : /*#__PURE__*/ _react.default.createElement(_iconsreact.Check, {
className: "".concat(classPrefix, "-icon-check")
})));
});
};
var renderTab = function renderTab() {
return /*#__PURE__*/ _react.default.createElement("div", {
className: (0, _classnames.default)(classPrefix, props.className),
style: props.style
}, /*#__PURE__*/ _react.default.createElement(_tabs.default, {
value: tabActiveIndex,
onChange: function onChange(index) {
var _props_onTabsChange;
(_props_onTabsChange = props.onTabsChange) === null || _props_onTabsChange === void 0 ? void 0 : _props_onTabsChange.call(props, Number(index));
setTabActiveIndex(Number(index));
}
}, levels.map(function(pane, index) {
return /*#__PURE__*/ _react.default.createElement(_tabs.default.TabPane, {
title: pane.selected || locale.select,
key: index
}, /*#__PURE__*/ _react.default.createElement("div", {
className: classPane
}, renderCascaderItem(pane, index)));
})));
};
return popup ? /*#__PURE__*/ _react.default.createElement(_popup.default, (0, _object_spread_props._)((0, _object_spread._)({}, popupProps), {
visible: visible,
position: "bottom",
round: true,
closeIcon: closeIcon,
closeable: closeable,
closeIconPosition: closeIconPosition,
title: props.title,
left: props.left,
onOverlayClick: function onOverlayClick() {
return setVisible(false);
},
onCloseIconClick: function onCloseIconClick() {
return setVisible(false);
}
}), renderTab()) : renderTab();
});
Cascader.displayName = 'NutCascader';
;