bootstrap-vue
Version:
BootstrapVue, with over 40 plugins and more than 75 custom components, provides one of the most comprehensive implementations of Bootstrap v4 components and grid system for Vue.js. With extensive and automated WAI-ARIA accessibility markup.
180 lines (162 loc) • 5.89 kB
JavaScript
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; }
import looseEqual from '../../../utils/loose-equal';
import { isArray, arrayIncludes } from '../../../utils/array';
import { getComponentConfig } from '../../../utils/config';
import sanitizeRow from './sanitize-row';
export default {
props: {
selectable: {
type: Boolean,
default: false
},
selectMode: {
type: String,
default: 'multi'
},
selectedVariant: {
type: String,
default: function _default() {
return getComponentConfig('BTable', 'selectedVariant');
}
}
},
data: function data() {
return {
selectedRows: [],
selectedLastRow: -1
};
},
computed: {
selectableTableClasses: function selectableTableClasses() {
var _ref;
var selectable = this.selectable;
var isSelecting = selectable && this.selectedRows && this.selectedRows.some(Boolean);
return _ref = {
'b-table-selectable': selectable
}, _defineProperty(_ref, "b-table-select-".concat(this.selectMode), selectable), _defineProperty(_ref, 'b-table-selecting', isSelecting), _ref;
},
selectableTableAttrs: function selectableTableAttrs() {
return {
'aria-multiselectable': this.selectableIsMultiSelect
};
},
selectableIsMultiSelect: function selectableIsMultiSelect() {
if (this.selectable) {
return arrayIncludes(['range', 'multi'], this.selectMode) ? 'true' : 'false';
} else {
return null;
}
}
},
watch: {
computedItems: function computedItems(newVal, oldVal) {
// Reset for selectable
// TODO: Should selectedLastClicked be reset here?
// As changes to _showDetails would trigger it to reset
this.selectedLastRow = -1;
var equal = false;
if (this.selectable && this.selectedRows.length > 0) {
// Quick check against array length
equal = isArray(newVal) && isArray(oldVal) && newVal.length === oldVal.length;
for (var i = 0; equal && i < newVal.length; i++) {
// Look for the first non-loosely equal row, after ignoring reserved fields
equal = looseEqual(sanitizeRow(newVal[i]), sanitizeRow(oldVal[i]));
}
}
if (!equal) {
this.clearSelected();
}
},
selectable: function selectable(newVal, oldVal) {
this.clearSelected();
this.setSelectionHandlers(newVal);
},
selectMode: function selectMode(newVal, oldVal) {
this.clearSelected();
},
selectedRows: function selectedRows(_selectedRows, oldVal) {
var _this = this;
if (this.selectable && !looseEqual(_selectedRows, oldVal)) {
var items = []; // forEach skips over non-existant indicies (on sparse arrays)
_selectedRows.forEach(function (v, idx) {
if (v) {
items.push(_this.computedItems[idx]);
}
});
this.$emit('row-selected', items);
}
}
},
beforeMount: function beforeMount() {
// Set up handlers
if (this.selectable) {
this.setSelectionHandlers(true);
}
},
methods: {
isRowSelected: function isRowSelected(idx) {
return Boolean(this.selectedRows[idx]);
},
selectableRowClasses: function selectableRowClasses(idx) {
var rowSelected = this.isRowSelected(idx);
var base = this.dark ? 'bg' : 'table';
var variant = this.selectedVariant;
return _defineProperty({
'b-table-row-selected': this.selectable && rowSelected
}, "".concat(base, "-").concat(variant), this.selectable && rowSelected && variant);
},
selectableRowAttrs: function selectableRowAttrs(idx) {
return {
'aria-selected': !this.selectable ? null : this.isRowSelected(idx) ? 'true' : 'false'
};
},
clearSelected: function clearSelected() {
var hasSelection = this.selectedRows.reduce(function (prev, v) {
return prev || v;
}, false);
if (hasSelection) {
this.selectedLastClicked = -1;
this.selectedRows = [];
}
},
setSelectionHandlers: function setSelectionHandlers(on) {
var method = on ? '$on' : '$off'; // Handle row-clicked event
this[method]('row-clicked', this.selectionHandler); // Clear selection on filter, pagination, and sort changes
this[method]('filtered', this.clearSelected);
this[method]('context-changed', this.clearSelected);
},
selectionHandler: function selectionHandler(item, index, evt) {
/* istanbul ignore if: should never happen */
if (!this.selectable) {
// Don't do anything if table is not in selectable mode
/* istanbul ignore next: should never happen */
this.clearSelected();
/* istanbul ignore next: should never happen */
return;
}
var selectedRows = this.selectedRows.slice();
var selected = !selectedRows[index];
var mode = this.selectMode; // Note 'multi' mode needs no special handling
if (mode === 'single') {
selectedRows = [];
} else if (mode === 'range') {
if (this.selectedLastRow > -1 && evt.shiftKey) {
// range
for (var idx = Math.min(this.selectedLastRow, index); idx <= Math.max(this.selectedLastRow, index); idx++) {
selectedRows[idx] = true;
}
selected = true;
} else {
if (!(evt.ctrlKey || evt.metaKey)) {
// clear range selection if any
selectedRows = [];
selected = true;
}
this.selectedLastRow = selected ? index : -1;
}
}
selectedRows[index] = selected;
this.selectedRows = selectedRows;
}
}
};