element-plus
Version:
A Component Library for Vue3.0
1,368 lines (1,356 loc) • 134 kB
JavaScript
'use strict';
Object.defineProperty(exports, '__esModule', { value: true });
var vue = require('vue');
var util = require('../utils/util');
var dom = require('../utils/dom');
var core = require('@popperjs/core');
var PopupManager = require('../utils/popup-manager');
var debounce = require('lodash/debounce');
var locale = require('../locale');
var directives = require('../directives');
var scrollbarWidth = require('../utils/scrollbar-width');
var isServer = require('../utils/isServer');
var ElCheckbox = require('../el-checkbox');
var ElPopper = require('../el-popper');
var ElCheckboxGroup = require('../el-checkbox-group');
var ElScrollbar = require('../el-scrollbar');
var resizeEvent = require('../utils/resize-event');
var throttle = require('lodash/throttle');
function _interopDefaultLegacy (e) { return e && typeof e === 'object' && 'default' in e ? e : { 'default': e }; }
var PopupManager__default = /*#__PURE__*/_interopDefaultLegacy(PopupManager);
var debounce__default = /*#__PURE__*/_interopDefaultLegacy(debounce);
var scrollbarWidth__default = /*#__PURE__*/_interopDefaultLegacy(scrollbarWidth);
var isServer__default = /*#__PURE__*/_interopDefaultLegacy(isServer);
var ElCheckbox__default = /*#__PURE__*/_interopDefaultLegacy(ElCheckbox);
var ElPopper__default = /*#__PURE__*/_interopDefaultLegacy(ElPopper);
var ElCheckboxGroup__default = /*#__PURE__*/_interopDefaultLegacy(ElCheckboxGroup);
var ElScrollbar__default = /*#__PURE__*/_interopDefaultLegacy(ElScrollbar);
var throttle__default = /*#__PURE__*/_interopDefaultLegacy(throttle);
const getCell = function (event) {
let cell = event.target;
while (cell && cell.tagName.toUpperCase() !== 'HTML') {
if (cell.tagName.toUpperCase() === 'TD') {
return cell;
}
cell = cell.parentNode;
}
return null;
};
const isObject = function (obj) {
return obj !== null && typeof obj === 'object';
};
const orderBy = function (array, sortKey, reverse, sortMethod, sortBy) {
if (!sortKey &&
!sortMethod &&
(!sortBy || (Array.isArray(sortBy) && !sortBy.length))) {
return array;
}
if (typeof reverse === 'string') {
reverse = reverse === 'descending' ? -1 : 1;
}
else {
reverse = reverse && reverse < 0 ? -1 : 1;
}
const getKey = sortMethod
? null
: function (value, index) {
if (sortBy) {
if (!Array.isArray(sortBy)) {
sortBy = [sortBy];
}
return sortBy.map(function (by) {
if (typeof by === 'string') {
return util.getValueByPath(value, by);
}
else {
return by(value, index, array);
}
});
}
if (sortKey !== '$key') {
if (isObject(value) && '$value' in value)
value = value.$value;
}
return [isObject(value) ? util.getValueByPath(value, sortKey) : value];
};
const compare = function (a, b) {
if (sortMethod) {
return sortMethod(a.value, b.value);
}
for (let i = 0, len = a.key.length; i < len; i++) {
if (a.key[i] < b.key[i]) {
return -1;
}
if (a.key[i] > b.key[i]) {
return 1;
}
}
return 0;
};
return array
.map(function (value, index) {
return {
value: value,
index: index,
key: getKey ? getKey(value, index) : null,
};
})
.sort(function (a, b) {
let order = compare(a, b);
if (!order) {
order = a.index - b.index;
}
return order * reverse;
})
.map(item => item.value);
};
const getColumnById = function (table, columnId) {
let column = null;
table.columns.forEach(function (item) {
if (item.id === columnId) {
column = item;
}
});
return column;
};
const getColumnByKey = function (table, columnKey) {
let column = null;
for (let i = 0; i < table.columns.length; i++) {
const item = table.columns[i];
if (item.columnKey === columnKey) {
column = item;
break;
}
}
return column;
};
const getColumnByCell = function (table, cell) {
const matches = (cell.className || '').match(/el-table_[^\s]+/gm);
if (matches) {
return getColumnById(table, matches[0]);
}
return null;
};
const getRowIdentity = (row, rowKey) => {
if (!row)
throw new Error('row is required when get row identity');
if (typeof rowKey === 'string') {
if (rowKey.indexOf('.') < 0) {
return row[rowKey];
}
const key = rowKey.split('.');
let current = row;
for (let i = 0; i < key.length; i++) {
current = current[key[i]];
}
return current;
}
else if (typeof rowKey === 'function') {
return rowKey.call(null, row);
}
};
const getKeysMap = function (array, rowKey) {
const arrayMap = {};
(array || []).forEach((row, index) => {
arrayMap[getRowIdentity(row, rowKey)] = { row, index };
});
return arrayMap;
};
function parseHeight(height) {
if (typeof height === 'number') {
return height;
}
if (typeof height === 'string') {
if (/^\d+(?:px)?$/.test(height)) {
return parseInt(height, 10);
}
else {
return height;
}
}
return null;
}
function toggleRowStatus(statusArr, row, newVal) {
let changed = false;
const index = statusArr.indexOf(row);
const included = index !== -1;
const addRow = () => {
statusArr.push(row);
changed = true;
};
const removeRow = () => {
statusArr.splice(index, 1);
changed = true;
};
if (typeof newVal === 'boolean') {
if (newVal && !included) {
addRow();
}
else if (!newVal && included) {
removeRow();
}
}
else {
if (included) {
removeRow();
}
else {
addRow();
}
}
return changed;
}
function walkTreeNode(root, cb, childrenKey = 'children', lazyKey = 'hasChildren') {
const isNil = array => !(Array.isArray(array) && array.length);
function _walker(parent, children, level) {
cb(parent, children, level);
children.forEach(item => {
if (item[lazyKey]) {
cb(item, null, level + 1);
return;
}
const children = item[childrenKey];
if (!isNil(children)) {
_walker(item, children, level + 1);
}
});
}
root.forEach(item => {
if (item[lazyKey]) {
cb(item, null, 0);
return;
}
const children = item[childrenKey];
if (!isNil(children)) {
_walker(item, children, 0);
}
});
}
let removePopper;
function createTablePopper(trigger, popperContent, popperOptions) {
function renderContent() {
const content = document.createElement('div');
content.className = 'el-tooltip__popper is-dark';
content.innerHTML = popperContent;
content.style.zIndex = String(PopupManager__default['default'].nextZIndex());
document.body.appendChild(content);
return content;
}
function renderArrow() {
const arrow = document.createElement('div');
arrow.className = 'el-popper__arrow';
arrow.style.bottom = '-4px';
return arrow;
}
function showPopper() {
popperInstance && popperInstance.update();
}
removePopper = function removePopper() {
try {
popperInstance && popperInstance.destroy();
content && document.body.removeChild(content);
dom.off(trigger, 'mouseenter', showPopper);
}
catch (_a) { }
};
dom.off(trigger, 'mouseleave', removePopper);
let popperInstance = null;
const content = renderContent();
const arrow = renderArrow();
content.appendChild(arrow);
popperInstance = core.createPopper(trigger, content, Object.assign({ modifiers: [
{
name: 'offset',
options: {
offset: [0, 8],
},
},
{
name: 'arrow',
options: {
element: arrow,
padding: 10,
},
},
] }, popperOptions));
dom.on(trigger, 'mouseenter', showPopper);
dom.on(trigger, 'mouseleave', removePopper);
}
function useExpand(watcherData) {
const instance = vue.getCurrentInstance();
const defaultExpandAll = vue.ref(false);
const expandRows = vue.ref([]);
const updateExpandRows = () => {
const data = watcherData.data.value || [];
const rowKey = watcherData.rowKey.value;
if (defaultExpandAll.value) {
expandRows.value = data.slice();
}
else if (rowKey) {
const expandRowsMap = getKeysMap(expandRows.value, rowKey);
expandRows.value = data.reduce((prev, row) => {
const rowId = getRowIdentity(row, rowKey);
const rowInfo = expandRowsMap[rowId];
if (rowInfo) {
prev.push(row);
}
return prev;
}, []);
}
else {
expandRows.value = [];
}
};
const toggleRowExpansion = (row, expanded) => {
const changed = toggleRowStatus(expandRows.value, row, expanded);
if (changed) {
instance.emit('expand-change', row, expandRows.value.slice());
instance.store.scheduleLayout();
}
};
const setExpandRowKeys = (rowKeys) => {
instance.store.assertRowKey();
const data = watcherData.data.value || [];
const rowKey = watcherData.rowKey.value;
const keysMap = getKeysMap(data, rowKey);
expandRows.value = rowKeys.reduce((prev, cur) => {
const info = keysMap[cur];
if (info) {
prev.push(info.row);
}
return prev;
}, []);
};
const isRowExpanded = (row) => {
const rowKey = watcherData.rowKey.value;
if (rowKey) {
const expandMap = getKeysMap(expandRows.value, rowKey);
return !!expandMap[getRowIdentity(row, rowKey)];
}
return expandRows.value.indexOf(row) !== -1;
};
return {
updateExpandRows,
toggleRowExpansion,
setExpandRowKeys,
isRowExpanded,
states: {
expandRows,
defaultExpandAll,
},
};
}
function useCurrent(watcherData) {
const instance = vue.getCurrentInstance();
const _currentRowKey = vue.ref(null);
const currentRow = vue.ref(null);
const setCurrentRowKey = (key) => {
instance.store.assertRowKey();
_currentRowKey.value = key;
setCurrentRowByKey(key);
};
const restoreCurrentRowKey = () => {
_currentRowKey.value = null;
};
const setCurrentRowByKey = (key) => {
const { data = [], rowKey } = watcherData;
let _currentRow = null;
if (rowKey.value) {
_currentRow = util.arrayFind(vue.unref(data), item => getRowIdentity(item, rowKey.value) === key);
}
currentRow.value = _currentRow;
};
const updateCurrentRow = (_currentRow) => {
const oldCurrentRow = currentRow.value;
if (_currentRow && _currentRow !== oldCurrentRow) {
currentRow.value = _currentRow;
instance.emit('current-change', currentRow.value, oldCurrentRow);
return;
}
if (!_currentRow && oldCurrentRow) {
currentRow.value = null;
instance.emit('current-change', null, oldCurrentRow);
}
};
const updateCurrentRowData = () => {
const rowKey = watcherData.rowKey.value;
const data = watcherData.data.value || [];
const oldCurrentRow = currentRow.value;
if (data.indexOf(oldCurrentRow) === -1 && oldCurrentRow) {
if (rowKey) {
const currentRowKey = getRowIdentity(oldCurrentRow, rowKey);
setCurrentRowByKey(currentRowKey);
}
else {
currentRow.value = null;
}
if (currentRow.value === null) {
instance.emit('current-change', null, oldCurrentRow);
}
}
else if (_currentRowKey.value) {
setCurrentRowByKey(_currentRowKey.value);
restoreCurrentRowKey();
}
};
return {
setCurrentRowKey,
restoreCurrentRowKey,
setCurrentRowByKey,
updateCurrentRow,
updateCurrentRowData,
states: {
_currentRowKey,
currentRow,
},
};
}
function useTree(watcherData) {
const expandRowKeys = vue.ref([]);
const treeData = vue.ref({});
const indent = vue.ref(16);
const lazy = vue.ref(false);
const lazyTreeNodeMap = vue.ref({});
const lazyColumnIdentifier = vue.ref('hasChildren');
const childrenColumnName = vue.ref('children');
const instance = vue.getCurrentInstance();
const normalizedData = vue.computed(() => {
if (!watcherData.rowKey.value)
return {};
const data = watcherData.data.value || [];
return normalize(data);
});
const normalizedLazyNode = vue.computed(() => {
const rowKey = watcherData.rowKey.value;
const keys = Object.keys(lazyTreeNodeMap.value);
const res = {};
if (!keys.length)
return res;
keys.forEach(key => {
if (lazyTreeNodeMap.value[key].length) {
const item = { children: [] };
lazyTreeNodeMap.value[key].forEach(row => {
const currentRowKey = getRowIdentity(row, rowKey);
item.children.push(currentRowKey);
if (row[lazyColumnIdentifier.value] && !res[currentRowKey]) {
res[currentRowKey] = { children: [] };
}
});
res[key] = item;
}
});
return res;
});
const normalize = data => {
const rowKey = watcherData.rowKey.value;
const res = {};
walkTreeNode(data, (parent, children, level) => {
const parentId = getRowIdentity(parent, rowKey);
if (Array.isArray(children)) {
res[parentId] = {
children: children.map(row => getRowIdentity(row, rowKey)),
level,
};
}
else if (lazy.value) {
res[parentId] = {
children: [],
lazy: true,
level,
};
}
}, childrenColumnName.value, lazyColumnIdentifier.value);
return res;
};
const updateTreeData = () => {
var _a, _b;
const nested = normalizedData.value;
const normalizedLazyNode_ = normalizedLazyNode.value;
const keys = Object.keys(nested);
const newTreeData = {};
if (keys.length) {
const oldTreeData = vue.unref(treeData);
const defaultExpandAll = (_a = instance.store) === null || _a === void 0 ? void 0 : _a.states.defaultExpandAll.value;
const rootLazyRowKeys = [];
const getExpanded = (oldValue, key) => {
const included = defaultExpandAll ||
(expandRowKeys.value && expandRowKeys.value.indexOf(key) !== -1);
return !!((oldValue && oldValue.expanded) || included);
};
keys.forEach(key => {
const oldValue = oldTreeData[key];
const newValue = Object.assign({}, nested[key]);
newValue.expanded = getExpanded(oldValue, key);
if (newValue.lazy) {
const { loaded = false, loading = false } = oldValue || {};
newValue.loaded = !!loaded;
newValue.loading = !!loading;
rootLazyRowKeys.push(key);
}
newTreeData[key] = newValue;
});
const lazyKeys = Object.keys(normalizedLazyNode_);
if (lazy.value && lazyKeys.length && rootLazyRowKeys.length) {
lazyKeys.forEach(key => {
const oldValue = oldTreeData[key];
const lazyNodeChildren = normalizedLazyNode_[key].children;
if (rootLazyRowKeys.indexOf(key) !== -1) {
if (newTreeData[key].children.length !== 0) {
throw new Error('[ElTable]children must be an empty array.');
}
newTreeData[key].children = lazyNodeChildren;
}
else {
const { loaded = false, loading = false } = oldValue || {};
newTreeData[key] = {
lazy: true,
loaded: !!loaded,
loading: !!loading,
expanded: getExpanded(oldValue, key),
children: lazyNodeChildren,
level: '',
};
}
});
}
}
treeData.value = newTreeData;
(_b = instance.store) === null || _b === void 0 ? void 0 : _b.updateTableScrollY();
};
vue.watch(() => normalizedData.value, updateTreeData);
vue.watch(() => normalizedLazyNode.value, updateTreeData);
const updateTreeExpandKeys = value => {
expandRowKeys.value = value;
updateTreeData();
};
const toggleTreeExpansion = (row, expanded) => {
instance.store.assertRowKey();
const rowKey = watcherData.rowKey.value;
const id = getRowIdentity(row, rowKey);
const data = id && treeData.value[id];
if (id && data && 'expanded' in data) {
const oldExpanded = data.expanded;
expanded = typeof expanded === 'undefined' ? !data.expanded : expanded;
treeData.value[id].expanded = expanded;
if (oldExpanded !== expanded) {
instance.emit('expand-change', row, expanded);
}
instance.store.updateTableScrollY();
}
};
const loadOrToggle = row => {
instance.store.assertRowKey();
const rowKey = watcherData.rowKey.value;
const id = getRowIdentity(row, rowKey);
const data = treeData.value[id];
if (lazy.value && data && 'loaded' in data && !data.loaded) {
loadData(row, id, data);
}
else {
toggleTreeExpansion(row, undefined);
}
};
const loadData = (row, key, treeNode) => {
const { load } = instance.props;
if (load && !treeData.value[key].loaded) {
treeData.value[key].loading = true;
load(row, treeNode, data => {
if (!Array.isArray(data)) {
throw new Error('[ElTable] data must be an array');
}
treeData.value[key].loading = false;
treeData.value[key].loaded = true;
treeData.value[key].expanded = true;
if (data.length) {
lazyTreeNodeMap.value[key] = data;
}
instance.emit('expand-change', row, true);
});
}
};
return {
loadData,
loadOrToggle,
toggleTreeExpansion,
updateTreeExpandKeys,
updateTreeData,
normalize,
states: {
expandRowKeys,
treeData,
indent,
lazy,
lazyTreeNodeMap,
lazyColumnIdentifier,
childrenColumnName,
},
};
}
const sortData = (data, states) => {
const sortingColumn = states.sortingColumn;
if (!sortingColumn || typeof sortingColumn.sortable === 'string') {
return data;
}
return orderBy(data, states.sortProp, states.sortOrder, sortingColumn.sortMethod, sortingColumn.sortBy);
};
const doFlattenColumns = columns => {
const result = [];
columns.forEach(column => {
if (column.children) {
result.push.apply(result, doFlattenColumns(column.children));
}
else {
result.push(column);
}
});
return result;
};
function useWatcher() {
const instance = vue.getCurrentInstance();
const rowKey = vue.ref(null);
const data = vue.ref([]);
const _data = vue.ref([]);
const isComplex = vue.ref(false);
const _columns = vue.ref([]);
const originColumns = vue.ref([]);
const columns = vue.ref([]);
const fixedColumns = vue.ref([]);
const rightFixedColumns = vue.ref([]);
const leafColumns = vue.ref([]);
const fixedLeafColumns = vue.ref([]);
const rightFixedLeafColumns = vue.ref([]);
const leafColumnsLength = vue.ref(0);
const fixedLeafColumnsLength = vue.ref(0);
const rightFixedLeafColumnsLength = vue.ref(0);
const isAllSelected = vue.ref(false);
const selection = vue.ref([]);
const reserveSelection = vue.ref(false);
const selectOnIndeterminate = vue.ref(false);
const selectable = vue.ref(null);
const filters = vue.ref({});
const filteredData = vue.ref(null);
const sortingColumn = vue.ref(null);
const sortProp = vue.ref(null);
const sortOrder = vue.ref(null);
const hoverRow = vue.ref(null);
vue.watch(data, () => instance.state && scheduleLayout(false), {
deep: true,
});
const assertRowKey = () => {
if (!rowKey.value)
throw new Error('[ElTable] prop row-key is required');
};
const updateColumns = () => {
fixedColumns.value = _columns.value.filter(column => column.fixed === true || column.fixed === 'left');
rightFixedColumns.value = _columns.value.filter(column => column.fixed === 'right');
if (fixedColumns.value.length > 0 &&
_columns.value[0] &&
_columns.value[0].type === 'selection' &&
!_columns.value[0].fixed) {
_columns.value[0].fixed = true;
fixedColumns.value.unshift(_columns.value[0]);
}
const notFixedColumns = _columns.value.filter(column => !column.fixed);
originColumns.value = []
.concat(fixedColumns.value)
.concat(notFixedColumns)
.concat(rightFixedColumns.value);
const leafColumns = doFlattenColumns(notFixedColumns);
const fixedLeafColumns = doFlattenColumns(fixedColumns.value);
const rightFixedLeafColumns = doFlattenColumns(rightFixedColumns.value);
leafColumnsLength.value = leafColumns.length;
fixedLeafColumnsLength.value = fixedLeafColumns.length;
rightFixedLeafColumnsLength.value = rightFixedLeafColumns.length;
columns.value = []
.concat(fixedLeafColumns)
.concat(leafColumns)
.concat(rightFixedLeafColumns);
isComplex.value =
fixedColumns.value.length > 0 || rightFixedColumns.value.length > 0;
};
const scheduleLayout = (needUpdateColumns, immediate = false) => {
if (needUpdateColumns) {
updateColumns();
}
if (immediate) {
instance.state.doLayout();
}
else {
instance.state.debouncedUpdateLayout();
}
};
const isSelected = row => {
return selection.value.indexOf(row) > -1;
};
const clearSelection = () => {
isAllSelected.value = false;
const oldSelection = selection.value;
if (oldSelection.length) {
selection.value = [];
instance.emit('selection-change', []);
}
};
const cleanSelection = () => {
let deleted;
if (rowKey.value) {
deleted = [];
const selectedMap = getKeysMap(selection.value, rowKey.value);
const dataMap = getKeysMap(data.value, rowKey.value);
for (const key in selectedMap) {
if (selectedMap.hasOwnProperty(key) && !dataMap[key]) {
deleted.push(selectedMap[key].row);
}
}
}
else {
deleted = selection.value.filter(item => data.value.indexOf(item) === -1);
}
if (deleted.length) {
const newSelection = selection.value.filter(item => deleted.indexOf(item) === -1);
selection.value = newSelection;
instance.emit('selection-change', newSelection.slice());
}
};
const toggleRowSelection = (row, selected, emitChange = true) => {
const changed = toggleRowStatus(selection.value, row, selected);
if (changed) {
const newSelection = (selection.value || []).slice();
if (emitChange) {
instance.emit('select', newSelection, row);
}
instance.emit('selection-change', newSelection);
}
};
const _toggleAllSelection = () => {
const value = selectOnIndeterminate.value
? !isAllSelected.value
: !(isAllSelected.value || selection.value.length);
isAllSelected.value = value;
let selectionChanged = false;
data.value.forEach((row, index) => {
if (selectable.value) {
if (selectable.value.call(null, row, index) &&
toggleRowStatus(selection.value, row, value)) {
selectionChanged = true;
}
}
else {
if (toggleRowStatus(selection.value, row, value)) {
selectionChanged = true;
}
}
});
if (selectionChanged) {
instance.emit('selection-change', selection.value ? selection.value.slice() : []);
}
instance.emit('select-all', selection.value);
};
const updateSelectionByRowKey = () => {
const selectedMap = getKeysMap(selection.value, rowKey.value);
data.value.forEach(row => {
const rowId = getRowIdentity(row, rowKey.value);
const rowInfo = selectedMap[rowId];
if (rowInfo) {
selection.value[rowInfo.index] = row;
}
});
};
const updateAllSelected = () => {
var _a;
if (((_a = data.value) === null || _a === void 0 ? void 0 : _a.length) === 0) {
isAllSelected.value = false;
return;
}
let selectedMap;
if (rowKey.value) {
selectedMap = getKeysMap(selection.value, rowKey.value);
}
const isSelected = function (row) {
if (selectedMap) {
return !!selectedMap[getRowIdentity(row, rowKey.value)];
}
else {
return selection.value.indexOf(row) !== -1;
}
};
let isAllSelected_ = true;
let selectedCount = 0;
for (let i = 0, j = (data.value || []).length; i < j; i++) {
const item = data.value[i];
const isRowSelectable = selectable.value && selectable.value.call(null, item, i);
if (!isSelected(item)) {
if (!selectable.value || isRowSelectable) {
isAllSelected_ = false;
break;
}
}
else {
selectedCount++;
}
}
if (selectedCount === 0)
isAllSelected_ = false;
isAllSelected.value = isAllSelected_;
};
const updateFilters = (columns, values) => {
if (!Array.isArray(columns)) {
columns = [columns];
}
const filters_ = {};
columns.forEach(col => {
filters.value[col.id] = values;
filters_[col.columnKey || col.id] = values;
});
return filters_;
};
const updateSort = (column, prop, order) => {
if (sortingColumn.value && sortingColumn.value !== column) {
sortingColumn.value.order = null;
}
sortingColumn.value = column;
sortProp.value = prop;
sortOrder.value = order;
};
const execFilter = () => {
let sourceData = vue.unref(_data);
Object.keys(filters.value).forEach(columnId => {
const values = filters.value[columnId];
if (!values || values.length === 0)
return;
const column = getColumnById({
columns: columns.value,
}, columnId);
if (column && column.filterMethod) {
sourceData = sourceData.filter(row => {
return values.some(value => column.filterMethod.call(null, value, row, column));
});
}
});
filteredData.value = sourceData;
};
const execSort = () => {
data.value = sortData(filteredData.value, {
sortingColumn: sortingColumn.value,
sortProp: sortProp.value,
sortOrder: sortOrder.value,
});
};
const execQuery = ignore => {
if (!(ignore && ignore.filter)) {
execFilter();
}
execSort();
};
const clearFilter = columnKeys => {
const { tableHeader, fixedTableHeader, rightFixedTableHeader, } = instance.refs;
let panels = {};
if (tableHeader)
panels = Object.assign(panels, tableHeader.filterPanels);
if (fixedTableHeader)
panels = Object.assign(panels, fixedTableHeader.filterPanels);
if (rightFixedTableHeader)
panels = Object.assign(panels, rightFixedTableHeader.filterPanels);
const keys = Object.keys(panels);
if (!keys.length)
return;
if (typeof columnKeys === 'string') {
columnKeys = [columnKeys];
}
if (Array.isArray(columnKeys)) {
const columns_ = columnKeys.map(key => getColumnByKey({
columns: columns.value,
}, key));
keys.forEach(key => {
const column = columns_.find(col => col.id === key);
if (column) {
column.filteredValue = [];
}
});
instance.store.commit('filterChange', {
column: columns_,
values: [],
silent: true,
multi: true,
});
}
else {
keys.forEach(key => {
const column = columns.value.find(col => col.id === key);
if (column) {
column.filteredValue = [];
}
});
filters.value = {};
instance.store.commit('filterChange', {
column: {},
values: [],
silent: true,
});
}
};
const clearSort = () => {
if (!sortingColumn.value)
return;
updateSort(null, null, null);
instance.store.commit('changeSortCondition', {
silent: true,
});
};
const { setExpandRowKeys, toggleRowExpansion, updateExpandRows, states: expandStates, isRowExpanded, } = useExpand({
data,
rowKey,
});
const { updateTreeExpandKeys, toggleTreeExpansion, loadOrToggle, states: treeStates, } = useTree({
data,
rowKey,
});
const { updateCurrentRowData, updateCurrentRow, setCurrentRowKey, states: currentData, } = useCurrent({
data,
rowKey,
});
const setExpandRowKeysAdapter = val => {
setExpandRowKeys(val);
updateTreeExpandKeys(val);
};
const toggleRowExpansionAdapter = (row, expanded) => {
const hasExpandColumn = columns.value.some(({ type }) => type === 'expand');
if (hasExpandColumn) {
toggleRowExpansion(row, expanded);
}
else {
toggleTreeExpansion(row, expanded);
}
};
return {
assertRowKey,
updateColumns,
scheduleLayout,
isSelected,
clearSelection,
cleanSelection,
toggleRowSelection,
_toggleAllSelection,
updateSelectionByRowKey,
updateAllSelected,
updateFilters,
updateCurrentRow,
updateSort,
execFilter,
execSort,
execQuery,
clearFilter,
clearSort,
toggleRowExpansion,
setExpandRowKeysAdapter,
setCurrentRowKey,
toggleRowExpansionAdapter,
isRowExpanded,
updateExpandRows,
updateCurrentRowData,
loadOrToggle,
states: Object.assign(Object.assign(Object.assign({ rowKey,
data,
_data,
isComplex,
_columns,
originColumns,
columns,
fixedColumns,
rightFixedColumns,
leafColumns,
fixedLeafColumns,
rightFixedLeafColumns,
leafColumnsLength,
fixedLeafColumnsLength,
rightFixedLeafColumnsLength,
isAllSelected,
selection,
reserveSelection,
selectOnIndeterminate,
selectable,
filters,
filteredData,
sortingColumn,
sortProp,
sortOrder,
hoverRow }, expandStates), treeStates), currentData),
};
}
function replaceColumn(array, column) {
return array.map(item => {
var _a;
if (item.id === column.id) {
return column;
}
else if ((_a = item.children) === null || _a === void 0 ? void 0 : _a.length) {
item.children = replaceColumn(item.children, column);
}
return item;
});
}
function sortColumn(array) {
array.forEach(item => {
var _a, _b;
item.no = (_a = item.getColumnIndex) === null || _a === void 0 ? void 0 : _a.call(item);
if ((_b = item.children) === null || _b === void 0 ? void 0 : _b.length) {
sortColumn(item.children);
}
});
array.sort((cur, pre) => cur.no - pre.no);
}
function useStore() {
const instance = vue.getCurrentInstance();
const mutations = {
setData(states, data) {
const dataInstanceChanged = vue.unref(states.data) !== data;
states.data.value = data;
states._data.value = data;
instance.store.execQuery();
instance.store.updateCurrentRowData();
instance.store.updateExpandRows();
if (vue.unref(states.reserveSelection)) {
instance.store.assertRowKey();
instance.store.updateSelectionByRowKey();
}
else {
if (dataInstanceChanged) {
instance.store.clearSelection();
}
else {
instance.store.cleanSelection();
}
}
instance.store.updateAllSelected();
if (instance.$ready) {
instance.store.scheduleLayout();
}
},
insertColumn(states, column, parent) {
const array = vue.unref(states._columns);
let newColumns = [];
if (!parent) {
array.push(column);
newColumns = array;
}
else {
if (parent && !parent.children) {
parent.children = [];
}
parent.children.push(column);
newColumns = replaceColumn(array, parent);
}
sortColumn(newColumns);
states._columns.value = newColumns;
if (column.type === 'selection') {
states.selectable.value = column.selectable;
states.reserveSelection.value = column.reserveSelection;
}
if (instance.$ready) {
instance.store.updateColumns();
instance.store.scheduleLayout();
}
},
removeColumn(states, column, parent) {
const array = vue.unref(states._columns) || [];
if (parent) {
parent.children.splice(parent.children.findIndex(item => item.id === column.id), 1);
if (parent.children.length === 0) {
delete parent.children;
}
states._columns.value = replaceColumn(array, parent);
}
else {
const index = array.indexOf(column);
if (index > -1) {
array.splice(index, 1);
states._columns.value = array;
}
}
if (instance.$ready) {
instance.store.updateColumns();
instance.store.scheduleLayout();
}
},
sort(states, options) {
const { prop, order, init } = options;
if (prop) {
const column = util.arrayFind(vue.unref(states.columns), column => column.property === prop);
if (column) {
column.order = order;
instance.store.updateSort(column, prop, order);
instance.store.commit('changeSortCondition', { init });
}
}
},
changeSortCondition(states, options) {
const { sortingColumn: column, sortProp: prop, sortOrder: order } = states;
if (vue.unref(order) === null) {
states.sortingColumn.value = null;
states.sortProp.value = null;
}
const ingore = { filter: true };
instance.store.execQuery(ingore);
if (!options || !(options.silent || options.init)) {
instance.emit('sort-change', {
column: vue.unref(column),
prop: vue.unref(prop),
order: vue.unref(order),
});
}
instance.store.updateTableScrollY();
},
filterChange(states, options) {
const { column, values, silent } = options;
const newFilters = instance.store.updateFilters(column, values);
instance.store.execQuery();
if (!silent) {
instance.emit('filter-change', newFilters);
}
instance.store.updateTableScrollY();
},
toggleAllSelection() {
instance.store.toggleAllSelection();
},
rowSelectedChanged(states, row) {
instance.store.toggleRowSelection(row);
instance.store.updateAllSelected();
},
setHoverRow(states, row) {
states.hoverRow.value = row;
},
setCurrentRow(states, row) {
instance.store.updateCurrentRow(row);
},
};
const commit = function (name, ...args) {
const mutations = instance.store.mutations;
if (mutations[name]) {
mutations[name].apply(instance, [instance.store.states].concat(args));
}
else {
throw new Error(`Action not found: ${name}`);
}
};
const updateTableScrollY = function () {
vue.nextTick(() => instance.layout.updateScrollY.apply(instance.layout));
};
const watcher = useWatcher();
return Object.assign(Object.assign({}, watcher), { mutations,
commit,
updateTableScrollY });
}
function createStore(table, initialState = {}) {
if (!table) {
throw new Error('Table is required.');
}
const store = useStore();
store.toggleAllSelection = debounce__default['default'](store._toggleAllSelection, 10);
Object.keys(initialState).forEach(key => {
store.states[key].value = initialState[key];
});
return store;
}
class TableLayout {
constructor(options) {
this.observers = [];
this.table = null;
this.store = null;
this.columns = [];
this.fit = true;
this.showHeader = true;
this.height = vue.ref(null);
this.scrollX = vue.ref(false);
this.scrollY = vue.ref(false);
this.bodyWidth = vue.ref(null);
this.fixedWidth = vue.ref(null);
this.rightFixedWidth = vue.ref(null);
this.tableHeight = vue.ref(null);
this.headerHeight = vue.ref(44);
this.appendHeight = vue.ref(0);
this.footerHeight = vue.ref(44);
this.viewportHeight = vue.ref(null);
this.bodyHeight = vue.ref(null);
this.fixedBodyHeight = vue.ref(null);
this.gutterWidth = scrollbarWidth__default['default']();
for (const name in options) {
if (options.hasOwnProperty(name)) {
if (vue.isRef(this[name])) {
this[name].value = options[name];
}
else {
this[name] = options[name];
}
}
}
if (!this.table) {
throw new Error('table is required for Table Layout');
}
if (!this.store) {
throw new Error('store is required for Table Layout');
}
}
updateScrollY() {
const height = this.height.value;
if (height === null)
return false;
const bodyWrapper = this.table.refs.bodyWrapper;
if (this.table.vnode.el && bodyWrapper) {
const body = bodyWrapper.querySelector('.el-table__body');
const prevScrollY = this.scrollY.value;
const scrollY = body.offsetHeight > this.bodyHeight.value;
this.scrollY.value = scrollY;
return prevScrollY !== scrollY;
}
return false;
}
setHeight(value, prop = 'height') {
if (isServer__default['default'])
return;
const el = this.table.vnode.el;
value = parseHeight(value);
this.height.value = Number(value);
if (!el && (value || value === 0))
return vue.nextTick(() => this.setHeight(value, prop));
if (typeof value === 'number') {
el.style[prop] = value + 'px';
this.updateElsHeight();
}
else if (typeof value === 'string') {
el.style[prop] = value;
this.updateElsHeight();
}
}
setMaxHeight(value) {
this.setHeight(value, 'max-height');
}
getFlattenColumns() {
const flattenColumns = [];
const columns = this.table.store.states.columns.value;
columns.forEach(column => {
if (column.isColumnGroup) {
flattenColumns.push.apply(flattenColumns, column.columns);
}
else {
flattenColumns.push(column);
}
});
return flattenColumns;
}
updateElsHeight() {
if (!this.table.$ready)
return vue.nextTick(() => this.updateElsHeight());
const { headerWrapper: headerWrapper_, appendWrapper: appendWrapper_, footerWrapper: footerWrapper_, } = this.table.refs;
const appendWrapper = appendWrapper_;
const headerWrapper = headerWrapper_;
const footerWrapper = footerWrapper_;
this.appendHeight.value = appendWrapper ? appendWrapper.offsetHeight : 0;
if (this.showHeader && !headerWrapper)
return;
const headerTrElm = headerWrapper
? headerWrapper.querySelector('.el-table__header tr')
: null;
const noneHeader = this.headerDisplayNone(headerTrElm);
const headerHeight = (this.headerHeight.value = !this.showHeader
? 0
: headerWrapper.offsetHeight);
if (this.showHeader &&
!noneHeader &&
headerWrapper.offsetWidth > 0 &&
(this.table.store.states.columns.value || []).length > 0 &&
headerHeight < 2) {
return vue.nextTick(() => this.updateElsHeight());
}
const tableHeight = (this.tableHeight.value = this.table.vnode.el.clientHeight);
const footerHeight = (this.footerHeight.value = footerWrapper
? footerWrapper.offsetHeight
: 0);
if (this.height.value !== null) {
this.bodyHeight.value =
tableHeight - headerHeight - footerHeight + (footerWrapper ? 1 : 0);
}
this.fixedBodyHeight.value = this.scrollX.value
? this.bodyHeight.value - this.gutterWidth
: this.bodyHeight.value;
this.viewportHeight.value = this.scrollX.value
? tableHeight - this.gutterWidth
: tableHeight;
this.updateScrollY();
this.notifyObservers('scrollable');
}
headerDisplayNone(elm) {
if (!elm)
return true;
let headerChild = elm;
while (headerChild.tagName !== 'DIV') {
if (getComputedStyle(headerChild).display === 'none') {
return true;
}
headerChild = headerChild.parentElement;
}
return false;
}
updateColumnsWidth() {
if (isServer__default['default'])
return;
const fit = this.fit;
const bodyWidth = this.table.vnode.el.clientWidth;
let bodyMinWidth = 0;
const flattenColumns = this.getFlattenColumns();
const flexColumns = flattenColumns.filter(column => typeof column.width !== 'number');
flattenColumns.forEach(column => {
if (typeof column.width === 'number' && column.realWidth)
column.realWidth = null;
});
if (flexColumns.length > 0 && fit) {
flattenColumns.forEach(column => {
bodyMinWidth += column.width || column.minWidth || 80;
});
const scrollYWidth = this.scrollY.value ? this.gutterWidth : 0;
if (bodyMinWidth <= bodyWidth - scrollYWidth) {
this.scrollX.value = false;
const totalFlexWidth = bodyWidth - scrollYWidth - bodyMinWidth;
if (flexColumns.length === 1) {
flexColumns[0].realWidth =
(flexColumns[0].minWidth || 80) + totalFlexWidth;
}
else {
const allColumnsWidth = flexColumns.reduce((prev, column) => prev + (column.minWidth || 80), 0);
const flexWidthPerPixel = totalFlexWidth / allColumnsWidth;
let noneFirstWidth = 0;
flexColumns.forEach((column, index) => {
if (index === 0)
return;
const flexWidth = Math.floor((column.minWidth || 80) * flexWidthPerPixel);
noneFirstWidth += flexWidth;
column.realWidth = (column.minWidth || 80) + flexWidth;
});
flexColumns[0].realWidth =
(flexColumns[0].minWidth || 80) + totalFlexWidth - noneFirstWidth;
}
}
else {
this.scrollX.value = true;
flexColumns.forEach(function (column) {
column.realWidth = column.minWidth;
});
}
this.bodyWidth.value = Math.max(bodyMinWidth, bodyWidth);
this.table.state.resizeState.value.width = this.bodyWidth.value;
}
else {
flattenColumns.forEach(column => {
if (!column.width && !column.minWidth) {
column.realWidth = 80;
}
else {
column.realWidth = column.width || column.minWidth;
}
bodyMinWidth += column.realWidth;
});
this.scrollX.value = bodyMinWidth > bodyWidth;
this.bodyWidth.value = bodyMinWidth;
}
const fixedColumns = this.store.states.fixedColumns.value;
if (fixedColumns.length > 0) {
let fixedWidth = 0;
fixedColumns.forEach(function (column) {