zarm-web
Version:
基于 React 的桌面端UI库
471 lines (401 loc) • 20 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.default = void 0;
var _react = _interopRequireWildcard(require("react"));
var _classnames7 = _interopRequireDefault(require("classnames"));
var _Tab = _interopRequireDefault(require("./Tab"));
var _icon = _interopRequireDefault(require("../icon"));
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
function _getRequireWildcardCache() { if (typeof WeakMap !== "function") return null; var cache = new WeakMap(); _getRequireWildcardCache = function _getRequireWildcardCache() { return cache; }; return cache; }
function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } var cache = _getRequireWildcardCache(); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; if (obj != null) { var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
function _typeof(obj) { if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") { _typeof = function _typeof(obj) { return typeof obj; }; } else { _typeof = function _typeof(obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; }; } return _typeof(obj); }
function _extends() { _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; }; return _extends.apply(this, arguments); }
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (call && (_typeof(call) === "object" || typeof call === "function")) { return call; } return _assertThisInitialized(self); }
function _assertThisInitialized(self) { if (self === void 0) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return self; }
function _getPrototypeOf(o) { _getPrototypeOf = Object.setPrototypeOf ? Object.getPrototypeOf : function _getPrototypeOf(o) { return o.__proto__ || Object.getPrototypeOf(o); }; return _getPrototypeOf(o); }
function _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } }
function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); return Constructor; }
function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function"); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, writable: true, configurable: true } }); if (superClass) _setPrototypeOf(subClass, superClass); }
function _setPrototypeOf(o, p) { _setPrototypeOf = Object.setPrototypeOf || function _setPrototypeOf(o, p) { o.__proto__ = p; return o; }; return _setPrototypeOf(o, p); }
var Tabs =
/*#__PURE__*/
function (_Component) {
_inherits(Tabs, _Component);
_createClass(Tabs, null, [{
key: "getSelectIndex",
value: function getSelectIndex(children) {
var selectIndex;
_react.default.Children.forEach(children, function (item, $index) {
if (item.props && item.props.selected) {
selectIndex = $index;
}
});
return selectIndex;
}
}, {
key: "getDerivedStateFromProps",
value: function getDerivedStateFromProps(props) {
var newState = {
value: null
};
if ('value' in props) {
newState.value = props.value;
return newState;
}
return null;
}
}]);
function Tabs(props) {
var _this;
_classCallCheck(this, Tabs);
_this = _possibleConstructorReturn(this, _getPrototypeOf(Tabs).call(this, props));
_this.tabHeaderWrap = void 0;
_this.tabHeaderNav = void 0;
_this.activeTab = void 0;
_this.handleTabClick = function (e, index, disabled) {
var onChange = _this.props.onChange;
if (!disabled) {
_this.updateTabBar(e.target);
if (!('value' in _this.props)) {
_this.setState({
value: index
});
}
typeof onChange === 'function' && onChange(index);
}
};
_this.handleTabClose = function (e, index, disabled) {
e.stopPropagation();
var onTabClose = _this.props.onTabClose;
if (!disabled) {
typeof onTabClose === 'function' && onTabClose(index);
}
};
_this.scrollRightOrBottom = function (e) {
var _this$props = _this.props,
direction = _this$props.direction,
onNextClick = _this$props.onNextClick;
var _this$state = _this.state,
headerWidth = _this$state.headerWidth,
headerHeight = _this$state.headerHeight,
scrollWidth = _this$state.scrollWidth,
scrollHeight = _this$state.scrollHeight,
scrollOffset = _this$state.scrollOffset;
var scrollDimension = direction === 'horizontal' ? scrollWidth : scrollHeight;
var headerDimension = direction === 'horizontal' ? headerWidth : headerHeight;
var offset = scrollDimension - scrollOffset - headerDimension;
_this.setState({
scrollOffset: scrollOffset + (offset > headerDimension ? headerDimension : offset)
});
onNextClick && onNextClick(e);
};
_this.scrollLeftOrTop = function (e) {
var _this$props2 = _this.props,
direction = _this$props2.direction,
onPrevClick = _this$props2.onPrevClick;
var _this$state2 = _this.state,
headerWidth = _this$state2.headerWidth,
headerHeight = _this$state2.headerHeight,
scrollOffset = _this$state2.scrollOffset;
var headerDimension = direction === 'horizontal' ? headerWidth : headerHeight;
_this.setState({
scrollOffset: scrollOffset - (scrollOffset > headerDimension ? headerDimension : scrollOffset)
});
onPrevClick && onPrevClick(e);
};
_this.getActiveNode = function (node) {
if (node) {
if (_this.activeTab !== node) {
_this.activeTab = node;
_this.setActiveLineStyle();
}
}
};
_this.state = {
value: props.value || props.defaultValue || Tabs.getSelectIndex(props.children) || 0,
lineWidth: 0,
lineHeight: 0,
scrollOffset: 0,
headerWidth: 0,
headerHeight: 0,
scrollWidth: 0,
scrollHeight: 0,
isArrowShown: false
};
_this.tabHeaderWrap = _react.default.createRef();
_this.tabHeaderNav = _react.default.createRef();
return _this;
}
_createClass(Tabs, [{
key: "componentDidMount",
value: function componentDidMount() {
this.updateArrow();
this.setActiveLineStyle();
}
}, {
key: "componentDidUpdate",
value: function componentDidUpdate(prevProps, prevState) {
var prevSize = prevProps.size,
prevChildren = prevProps.children,
prevDirection = prevProps.direction;
var prevHeaderWidth = prevState.headerWidth,
prevHeaderHeight = prevState.headerHeight,
prevScrollWidth = prevState.scrollWidth;
var _ref = this.props || {},
currentSize = _ref.size,
_ref$children = _ref.children,
children = _ref$children === void 0 ? [] : _ref$children,
direction = _ref.direction;
var _this$state3 = this.state,
headerWidth = _this$state3.headerWidth,
headerHeight = _this$state3.headerHeight,
scrollWidth = _this$state3.scrollWidth,
scrollOffset = _this$state3.scrollOffset;
if (prevSize !== currentSize || prevDirection !== direction) {
this.setActiveLineStyle();
}
if (prevHeaderWidth !== headerWidth || prevHeaderHeight !== headerHeight || prevChildren !== children) {
this.updateArrow();
}
if (scrollWidth < prevScrollWidth) {
var result = scrollOffset - (prevScrollWidth - scrollWidth);
if (result > 0) {
this.updateScrollOffset(result);
}
}
}
}, {
key: "setActiveLineStyle",
value: function setActiveLineStyle() {
var _ref2 = this.activeTab && this.activeTab.getBoundingClientRect() || {},
_ref2$width = _ref2.width,
width = _ref2$width === void 0 ? 0 : _ref2$width,
_ref2$height = _ref2.height,
height = _ref2$height === void 0 ? 0 : _ref2$height;
this.setState({
lineWidth: width,
lineHeight: height
});
}
}, {
key: "getScrollOffset",
value: function getScrollOffset(target) {
var direction = this.props.direction;
var _this$state4 = this.state,
scrollOffset = _this$state4.scrollOffset,
headerWidth = _this$state4.headerWidth,
headerHeight = _this$state4.headerHeight;
var offsetLeft = target.offsetLeft,
offsetTop = target.offsetTop;
var _target$getBoundingCl = target.getBoundingClientRect(),
width = _target$getBoundingCl.width,
height = _target$getBoundingCl.height;
if (direction === 'horizontal') {
var _diff = scrollOffset + headerWidth < offsetLeft + width ? offsetLeft + width - headerWidth : scrollOffset;
return scrollOffset > offsetLeft ? offsetLeft : _diff;
}
var diff = scrollOffset + headerHeight < offsetTop + height ? offsetTop + height - headerHeight : scrollOffset;
return scrollOffset > offsetTop ? offsetTop : diff;
}
}, {
key: "getHeaderStyle",
value: function getHeaderStyle() {
var _ref3 = this.tabHeaderWrap && this.tabHeaderWrap.current && this.tabHeaderWrap.current.getBoundingClientRect() || {},
_ref3$width = _ref3.width,
headerWidth = _ref3$width === void 0 ? 0 : _ref3$width,
_ref3$height = _ref3.height,
headerHeight = _ref3$height === void 0 ? 0 : _ref3$height;
var _ref4 = this.tabHeaderNav && this.tabHeaderNav.current && this.tabHeaderNav.current.getBoundingClientRect() || {},
_ref4$width = _ref4.width,
scrollWidth = _ref4$width === void 0 ? 0 : _ref4$width,
_ref4$height = _ref4.height,
scrollHeight = _ref4$height === void 0 ? 0 : _ref4$height;
return {
headerWidth: headerWidth,
headerHeight: headerHeight,
scrollWidth: scrollWidth,
scrollHeight: scrollHeight
};
}
}, {
key: "updateScrollOffset",
value: function updateScrollOffset(scrollOffset) {
this.setState({
scrollOffset: scrollOffset
});
}
}, {
key: "updateArrow",
value: function updateArrow() {
var _this2 = this;
var direction = this.props.direction;
var _this$getHeaderStyle = this.getHeaderStyle(),
headerWidth = _this$getHeaderStyle.headerWidth,
headerHeight = _this$getHeaderStyle.headerHeight,
scrollWidth = _this$getHeaderStyle.scrollWidth,
scrollHeight = _this$getHeaderStyle.scrollHeight;
var isArrowShown = direction === 'horizontal' && scrollWidth > headerWidth || direction === 'vertical' && scrollHeight > headerHeight;
this.setState({
isArrowShown: isArrowShown
}, function () {
_this2.setState(_this2.getHeaderStyle());
_this2.updateTabBar(_this2.activeTab);
});
}
}, {
key: "updateTabBar",
value: function updateTabBar(target) {
var _this$state5 = this.state,
scrollOffset = _this$state5.scrollOffset,
isArrowShown = _this$state5.isArrowShown;
var offset = isArrowShown ? this.getScrollOffset(target) : scrollOffset;
this.updateScrollOffset(offset);
}
}, {
key: "renderHeaderLine",
value: function renderHeaderLine() {
var _this$props3 = this.props,
direction = _this$props3.direction,
prefixCls = _this$props3.prefixCls;
var _this$state6 = this.state,
lineWidth = _this$state6.lineWidth,
lineHeight = _this$state6.lineHeight;
var _ref5 = this.activeTab || {},
_ref5$offsetLeft = _ref5.offsetLeft,
offsetLeft = _ref5$offsetLeft === void 0 ? 0 : _ref5$offsetLeft,
_ref5$offsetTop = _ref5.offsetTop,
offsetTop = _ref5$offsetTop === void 0 ? 0 : _ref5$offsetTop;
var headerLineStyle = direction === 'horizontal' ? {
width: lineWidth,
height: 0,
transform: "translate3d(".concat(offsetLeft, "px,0,0)")
} : {
width: 0,
height: lineHeight,
transform: "translate3d(0,".concat(offsetTop, "px,0)")
};
return _react.default.createElement("div", {
className: "".concat(prefixCls, "__header__line"),
style: headerLineStyle
});
}
}, {
key: "render",
value: function render() {
var _classnames,
_classnames4,
_classnames5,
_this3 = this;
var _this$props4 = this.props,
className = _this$props4.className,
children = _this$props4.children,
style = _this$props4.style,
prefixCls = _this$props4.prefixCls,
type = _this$props4.type,
direction = _this$props4.direction,
size = _this$props4.size,
animated = _this$props4.animated;
var _this$state7 = this.state,
value = _this$state7.value,
isArrowShown = _this$state7.isArrowShown,
scrollOffset = _this$state7.scrollOffset,
headerWidth = _this$state7.headerWidth,
headerHeight = _this$state7.headerHeight,
scrollWidth = _this$state7.scrollWidth,
scrollHeight = _this$state7.scrollHeight;
var headerDimension = direction === 'horizontal' ? headerWidth : headerHeight;
var scrollDimension = direction === 'horizontal' ? scrollWidth : scrollHeight;
var arrowL = direction === 'horizontal' ? 'left' : 'top';
var arrowR = direction === 'horizontal' ? 'right' : 'bottom';
var isArrowLDisabled = scrollOffset === 0;
var isArrowRDisabled = Math.floor(Math.abs(scrollOffset + headerDimension - scrollDimension)) === 0;
var animateStyle = direction === 'horizontal' ? {
marginLeft: "-".concat(value * 100, "%")
} : {};
var headerNavStyle = direction === 'horizontal' ? {
transform: "translate3d(".concat(-scrollOffset, "px,0,0)")
} : {
transform: "translate3d(0,".concat(-scrollOffset, "px,0)")
};
var cls = (0, _classnames7.default)(prefixCls, className, (_classnames = {}, _defineProperty(_classnames, "".concat(prefixCls, "--").concat(direction), direction), _defineProperty(_classnames, "".concat(prefixCls, "--").concat(size), size), _defineProperty(_classnames, "".concat(prefixCls, "--").concat(type), direction === 'horizontal' && type), _classnames));
var headerCls = (0, _classnames7.default)("".concat(prefixCls, "__header"), _defineProperty({}, "".concat(prefixCls, "__header--arrow-mode"), isArrowShown));
var bodyCls = (0, _classnames7.default)("".concat(prefixCls, "__body"), _defineProperty({}, "".concat(prefixCls, "__body--animated"), animated));
var arrowLCls = (0, _classnames7.default)("".concat(prefixCls, "__header__arrow"), (_classnames4 = {}, _defineProperty(_classnames4, "".concat(prefixCls, "__header__arrow--").concat(arrowL), arrowL), _defineProperty(_classnames4, "".concat(prefixCls, "__header__arrow--disabled"), isArrowLDisabled), _classnames4));
var arrowRCls = (0, _classnames7.default)("".concat(prefixCls, "__header__arrow"), (_classnames5 = {}, _defineProperty(_classnames5, "".concat(prefixCls, "__header__arrow--").concat(arrowR), arrowR), _defineProperty(_classnames5, "".concat(prefixCls, "__header__arrow--disabled"), isArrowRDisabled), _classnames5));
var items = _react.default.Children.map(children, function (item, $index) {
var _classnames6;
var tabItemCls = (0, _classnames7.default)("".concat(prefixCls, "__header__item"), (_classnames6 = {}, _defineProperty(_classnames6, "".concat(prefixCls, "__header__item--disabled"), !!item.props.disabled), _defineProperty(_classnames6, "".concat(prefixCls, "__header__item--active"), $index === value), _classnames6));
var bindActiveRef = $index === value ? {
ref: _this3.getActiveNode
} : {};
return _react.default.createElement("div", _extends({
key: $index.toString(),
className: tabItemCls
}, bindActiveRef, {
onClick: function onClick(e) {
_this3.handleTabClick(e, $index, item.props.disabled);
}
}), item.props.title, direction === 'horizontal' && item.props.closable && _react.default.createElement(_icon.default, {
type: "wrong",
onClick: function onClick(e) {
_this3.handleTabClose(e, $index, item.props.disabled);
}
}));
});
var content = _react.default.Children.map(children, function (item, $index) {
return _react.default.createElement(_Tab.default, _extends({}, item.props, {
selected: value === $index
}), item.props.children);
});
return _react.default.createElement("div", {
className: cls,
style: style
}, _react.default.createElement("div", {
className: headerCls
}, _react.default.createElement("div", {
className: "".concat(prefixCls, "__header__scroll"),
ref: this.tabHeaderWrap
}, _react.default.createElement("div", {
className: "".concat(prefixCls, "__header__nav"),
ref: this.tabHeaderNav,
style: isArrowShown ? headerNavStyle : {}
}, items, type === 'line' && this.renderHeaderLine())), isArrowShown && _react.default.createElement(_react.default.Fragment, null, _react.default.createElement("span", {
className: arrowLCls,
onClick: function onClick(e) {
return !isArrowLDisabled && _this3.scrollLeftOrTop(e);
}
}, _react.default.createElement(_icon.default, {
type: "arrow-".concat(arrowL)
})), _react.default.createElement("span", {
className: arrowRCls,
onClick: function onClick(e) {
return !isArrowRDisabled && _this3.scrollRightOrBottom(e);
}
}, _react.default.createElement(_icon.default, {
type: "arrow-".concat(arrowR)
})))), _react.default.createElement("div", {
className: bodyCls,
style: animateStyle
}, content));
}
}]);
return Tabs;
}(_react.Component);
Tabs.displayName = 'Tabs';
Tabs.Tab = void 0;
Tabs.defaultProps = {
defaultValue: 0,
prefixCls: 'zw-tabs',
type: 'line',
direction: 'horizontal',
size: 'md',
onChange: function onChange() {},
onTabClose: function onTabClose() {},
animated: true
};
var _default = Tabs;
exports.default = _default;