ukelli-ui
Version:
[](https://travis-ci.org/ukelli/ukelli-ui) [](https://packagephobia.now.sh/result?p=ukelli-ui)
521 lines (430 loc) • 18.5 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.default = void 0;
var _react = _interopRequireWildcard(require("react"));
var _propTypes = _interopRequireDefault(require("prop-types"));
var _basicHelper = require("basic-helper");
var _mapperFilter = _interopRequireDefault(require("./mapper-filter"));
var _icon = require("../icon");
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { var desc = Object.defineProperty && Object.getOwnPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : {}; if (desc.get || desc.set) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } } newObj.default = obj; 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 _toConsumableArray(arr) { return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _nonIterableSpread(); }
function _nonIterableSpread() { throw new TypeError("Invalid attempt to spread non-iterable instance"); }
function _iterableToArray(iter) { if (Symbol.iterator in Object(iter) || Object.prototype.toString.call(iter) === "[object Arguments]") return Array.from(iter); }
function _arrayWithoutHoles(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } }
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
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 _possibleConstructorReturn(self, call) { if (call && (_typeof(call) === "object" || typeof call === "function")) { return call; } return _assertThisInitialized(self); }
function _getPrototypeOf(o) { _getPrototypeOf = Object.setPrototypeOf ? Object.getPrototypeOf : function _getPrototypeOf(o) { return o.__proto__ || Object.getPrototypeOf(o); }; return _getPrototypeOf(o); }
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); }
function _assertThisInitialized(self) { if (self === void 0) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return self; }
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; }
var isStringNumRegex = /\d+,?/;
/**
* 提供一个快速的表格数据渲染容器,不需要关注具体如何渲染,只需要传入对应的数据和过滤器
*
* @export
* @class TableBody
* @extends {MapperFilter}
*/
var TableBody =
/*#__PURE__*/
function (_MapperFilter) {
_inherits(TableBody, _MapperFilter);
function TableBody(props) {
var _this;
_classCallCheck(this, TableBody);
_this = _possibleConstructorReturn(this, _getPrototypeOf(TableBody).call(this, props));
_defineProperty(_assertThisInitialized(_assertThisInitialized(_this)), "excludeField", /action|checkbox/);
_defineProperty(_assertThisInitialized(_assertThisInitialized(_this)), "clearCheckeds", function () {
_this.toggleAllItems(false);
});
_defineProperty(_assertThisInitialized(_assertThisInitialized(_this)), "toggleSelectItem", function (item, idx) {
var nextCheckedItems = _this.state.checkedItems;
if (nextCheckedItems[idx]) {
delete nextCheckedItems[idx];
} else {
nextCheckedItems[idx] = item;
}
_this.selectItems(nextCheckedItems, idx);
});
_defineProperty(_assertThisInitialized(_assertThisInitialized(_this)), "getCheckbox", function (str, item, mapper, idx) {
var checkedItems = _this.state.checkedItems;
var checked = !!checkedItems[idx];
return _react.default.createElement("input", {
type: "checkbox",
checked: checked,
onChange: function onChange(e) {
return _this.toggleSelectItem(item, idx);
}
});
});
_defineProperty(_assertThisInitialized(_assertThisInitialized(_this)), "getKeyMapper", function () {
var _this$props = _this.props,
_this$props$keyMapper = _this$props.keyMapper,
keyMapper = _this$props$keyMapper === void 0 ? [] : _this$props$keyMapper,
needCheck = _this$props.needCheck;
var result = keyMapper;
if (needCheck) {
var checkExtend = {
key: 'checkbox',
w: 30,
filter: _this.getCheckbox
};
result = [checkExtend].concat(_toConsumableArray(keyMapper));
}
return result;
});
_defineProperty(_assertThisInitialized(_assertThisInitialized(_this)), "resizeCalcSize", function () {
var containerWidth = _this.state.containerWidth;
if (containerWidth != 'auto' && containerWidth < _this.tableRenderDOM.offsetWidth) {
_this.setState({
containerWidth: 'auto'
});
}
_this.calcSize();
});
_this.state = {
headerWidthMapper: [],
containerWidth: 'auto',
sortField: '',
isDesc: false,
checkedItems: {}
};
_this.firstTDDOMs = {};
_this.sameSortTime = 0;
return _this;
}
_createClass(TableBody, [{
key: "componentDidMount",
value: function componentDidMount() {
window.addEventListener('resize', this.resizeCalcSize);
this.calcSize();
}
}, {
key: "componentWillUnmount",
value: function componentWillUnmount() {
window.removeEventListener('resize', this.resizeCalcSize);
}
}, {
key: "componentDidUpdate",
value: function componentDidUpdate() {
this.calcSize();
}
/**
* 清除所有已选择的内容
*
* @memberof TableBody
* @public
*/
}, {
key: "toggleAllItems",
value: function toggleAllItems(allCheck) {
var nextCheckedItems = this.state.checkedItems;
if (!allCheck) {
nextCheckedItems = {};
} else {
this.props.records.forEach(function (item, idx) {
return nextCheckedItems[idx] = item;
});
}
this.selectItems(nextCheckedItems);
}
}, {
key: "selectItems",
value: function selectItems(nextState, idx) {
var onCheck = this.props.onCheck;
this.checkedItems = nextState;
this.setState({
checkedItems: nextState
});
(0, _basicHelper.Call)(onCheck, nextState, idx);
}
}, {
key: "calcSize",
value: function calcSize() {
var _this2 = this;
var nextHeaderWidthMapper = {};
var nextContainerWidth = 0;
Object.keys(this.firstTDDOMs).forEach(function (tdIdx) {
var currTDDOM = _this2.firstTDDOMs[tdIdx];
nextHeaderWidthMapper[tdIdx] = currTDDOM.offsetWidth;
nextContainerWidth += nextHeaderWidthMapper[tdIdx];
});
if (JSON.stringify(nextHeaderWidthMapper) !== JSON.stringify(this.state.headerWidthMapper)) {
var tableRenderWidth = this.tableRenderDOM.offsetWidth;
this.setState({
headerWidthMapper: nextHeaderWidthMapper,
containerWidth: nextContainerWidth > tableRenderWidth ? nextContainerWidth : 'auto'
});
}
}
}, {
key: "ignoreFilter",
value: function ignoreFilter(str) {
return this.props.sortIgnores.indexOf(str) !== -1;
}
}, {
key: "getMapperItemsDOM",
value: function getMapperItemsDOM(record, parentIdx, needCount) {
var _this3 = this;
var needAction = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : true;
if (!record) return;
var keyMapper = this.getKeyMapper();
var keyMapperLen = keyMapper.length;
var result = [];
var _loop = function _loop(_idx) {
var item = keyMapper[_idx];
if (!item) return "continue";
var key = item.key;
var currText = record[key];
var actionRes = !needAction && _this3.excludeField.test(key) ? '-' : _this3.mapperFilter(item, record, parentIdx);
if (needCount) {
var isNum = !isNaN(+currText) || isStringNumRegex.test(currText);
if (isNum) {
// 这里是处理累加的逻辑,如果为字符串的字段,则先把逗号去除
var isNumbTxt = +(currText + '').replace(',', '');
if (!isNaN(isNumbTxt) && typeof isNumbTxt === 'number') {
_this3.statistics[key] = (_this3.statistics[key] || 0) + isNumbTxt;
}
}
}
result.push(_react.default.createElement("td", {
ref: function ref(tdDOM) {
if (tdDOM && parentIdx == 0) {
_this3.firstTDDOMs[_idx] = tdDOM;
}
},
style: item.w ? {
width: item.w,
whiteSpace: 'pre-wrap'
} : null,
className: item.className || '',
key: parentIdx + '_' + _idx
}, actionRes));
};
for (var _idx = 0; _idx < keyMapperLen; _idx++) {
var _ret = _loop(_idx);
if (_ret === "continue") continue;
}
return result;
}
}, {
key: "getStatisticDOM",
value: function getStatisticDOM(record) {
if (this.props.needCount && Object.keys(record).length > 0) return this.getMapperItemsDOM(record, 'statistics', false, false);
}
}, {
key: "getHeaderWidth",
value: function getHeaderWidth() {
var headerWidthMapper = this.state.headerWidthMapper;
var result = 0;
var keyMapper = this.getKeyMapper();
keyMapper.forEach(function (item, idx) {
if (item) result += headerWidthMapper[idx];
});
return result;
}
}, {
key: "recordDescFilter",
value: function recordDescFilter() {
var _this$state = this.state,
sortField = _this$state.sortField,
isDesc = _this$state.isDesc;
var records = this.props.records;
if (!sortField) return records;
var result = _toConsumableArray(records);
result.sort(function (itemPrev, itemNext) {
var sortTargetPrev = itemPrev[sortField];
var sortTargetNext = itemNext[sortField];
var res;
switch (true) {
case typeof sortTargetPrev == 'string':
res = sortTargetPrev.localeCompare(sortTargetNext);
break;
case typeof sortTargetPrev == 'number':
res = sortTargetPrev - sortTargetNext;
break;
}
return isDesc ? res : res * -1;
});
return result;
}
}, {
key: "orderRecord",
value: function orderRecord(orderKey) {
var _this4 = this;
if (this.ignoreFilter(orderKey)) return;
this.setState(function (_ref) {
var isDesc = _ref.isDesc,
sortField = _ref.sortField;
var _isDesc = isDesc;
if (sortField == orderKey) {
_this4.sameSortTime += 1;
if (_this4.sameSortTime === 2) {
_isDesc = false;
orderKey = '';
_this4.sameSortTime = 0;
} else {
_isDesc = !_isDesc;
}
} else {
_this4.sameSortTime = 0;
_isDesc = false;
}
return {
sortField: orderKey,
isDesc: _isDesc
};
});
}
}, {
key: "render",
value: function render() {
var _this5 = this;
var _this$props2 = this.props,
needCount = _this$props2.needCount,
height = _this$props2.height,
whenCheckAction = _this$props2.whenCheckAction;
var _this$state2 = this.state,
headerWidthMapper = _this$state2.headerWidthMapper,
containerWidth = _this$state2.containerWidth,
sortField = _this$state2.sortField,
isDesc = _this$state2.isDesc,
checkedItems = _this$state2.checkedItems;
var records = this.recordDescFilter();
var hasRecord = records.length > 0;
var keyMapper = this.getKeyMapper();
var isAllCheck = Object.keys(checkedItems).length == records.length;
if (!Array.isArray(records)) {
console.error('records 必须为 []');
return _react.default.createElement("span", null);
}
/** 统计字段,每一次统计都是一个新对象 */
this.statistics = {};
var hasChecked = Object.keys(checkedItems).length != 0;
var tableHeader = _react.default.createElement("div", {
className: "table-body-scroll",
style: {
width: containerWidth
}
}, _react.default.createElement("table", {
className: "table nomargin table-header"
}, _react.default.createElement("thead", null, _react.default.createElement("tr", null, keyMapper.map(function (item, idx) {
if (!item) return;
var currHeaderWidth = item.w || headerWidthMapper[idx];
var title = item.title || window.$UKE.getKeyMap(item.key);
switch (true) {
case item.key === 'checkbox':
title = _react.default.createElement("input", {
type: "checkbox",
checked: isAllCheck,
onChange: function onChange(e) {
return _this5.toggleAllItems(e.target.checked);
}
});
break;
case (0, _basicHelper.IsFunc)(title):
title = title(item, idx);
break;
}
var isOrdering = sortField == item.key;
var sortTip = isOrdering ? _react.default.createElement("span", {
className: "caret",
style: {
transform: "rotate(".concat(!isDesc ? '180deg' : '0deg', ")")
}
}) : null;
return _react.default.createElement("th", {
className: "".concat(isOrdering ? '_order ' + (isDesc ? '_desc ' : '_asc ') : '', "_btn"),
key: item.key,
onClick: function onClick(e) {
return _this5.orderRecord(item.key);
},
style: {
width: currHeaderWidth
}
}, title, sortTip);
})))));
var tableBody = hasRecord ? _react.default.createElement("div", {
className: "table-body-scroll",
style: {
height: height,
width: containerWidth
}
}, _react.default.createElement("table", {
className: "table nomargin table-body"
}, _react.default.createElement("tbody", null, records.map(function (record, _idx) {
if (!record) return;
var _record$_highlight = record._highlight,
_highlight = _record$_highlight === void 0 ? '' : _record$_highlight;
var idx = _idx;
return _react.default.createElement("tr", {
key: idx,
className: _highlight
}, _this5.getMapperItemsDOM(record, idx, needCount));
}), this.props.needCount ? _react.default.createElement("tr", {
className: "theme"
}, this.getStatisticDOM(this.statistics)) : null))) : _react.default.createElement("span", {
className: "no-record-tip"
}, _react.default.createElement(_icon.Icon, {
n: "noData"
}), _react.default.createElement("span", {
className: "text"
}, "\u6682\u65E0\u8BB0\u5F55"));
return _react.default.createElement("div", {
className: "table-render" + (hasChecked ? ' has-checked' : ''),
ref: function ref(tableRenderDOM) {
if (tableRenderDOM) _this5.tableRenderDOM = tableRenderDOM;
}
}, hasChecked && !!whenCheckAction ? _react.default.createElement("div", {
className: "checked-actions"
}, whenCheckAction) : null, tableHeader, tableBody);
}
}]);
return TableBody;
}(_mapperFilter.default);
exports.default = TableBody;
_defineProperty(TableBody, "propTypes", {
/** 定义数据渲染的字段的映射配置 */
keyMapper: _propTypes.default.arrayOf(_propTypes.default.shape({
/** 字段的 key */
key: _propTypes.default.string.isRequired,
/** 该字段的过滤器函数,可以返回任意类型 */
filter: _propTypes.default.func,
/** 是否日期+时分秒 */
datetime: _propTypes.default.any,
/** 是否日期 */
date: _propTypes.default.any,
/** 是否格式化成金钱 */
money: _propTypes.default.any,
/** 单个格子的宽度 */
w: _propTypes.default.any,
/** 是否以绝对值格式化成金钱 */
abvMoney: _propTypes.default.any,
/** 该字段的值的映射 mapper */
namesMapper: _propTypes.default.shape({
key: _propTypes.default.string
})
})).isRequired,
/** 需要渲染的目标记录 */
records: _propTypes.default.arrayOf(_propTypes.default.object).isRequired,
/** 是否需要统计 */
needCount: _propTypes.default.bool,
/** 是否多选 */
needCheck: _propTypes.default.bool,
/** 无视的排序字段 */
sortIgnores: _propTypes.default.arrayOf(_propTypes.default.string),
/** 当选中时往表格顶部嵌入的内容 */
whenCheckAction: _propTypes.default.any
});
_defineProperty(TableBody, "defaultProps", {
sortIgnores: ['checkbox'],
needCheck: false,
needCount: false
});