Compare commits

...

10 Commits

Author SHA1 Message Date
julyp
e326621f44 优化树形表格 2020-05-06 11:08:37 +08:00
julyp
06fbfac3d8 忽略lock 2020-05-06 10:05:31 +08:00
julyp
838cd27a39 删除lock 2020-05-06 10:04:49 +08:00
julyp
c5c0da76a3 格式化文件 2020-05-06 10:02:34 +08:00
julyp
250b404fae 修复expand中多标签bug 2020-04-29 17:27:38 +08:00
Julyp
2f75abad78 更新changelog 2020-02-19 17:56:59 +08:00
Julyp
15fb982fd6 - 新增动态展开数据行 2020-02-19 17:54:47 +08:00
Julyp
ce247606b2 - 新增动态展开数据行 2020-02-19 17:15:39 +08:00
Julyp
481359a57c - 新增动态展开数据行 2020-02-19 14:56:29 +08:00
Julyp
de3c25e15c 添加travis 2020-02-17 12:39:59 +08:00
14 changed files with 480 additions and 8997 deletions

3
.gitignore vendored
View File

@@ -3,4 +3,5 @@ node_modules
*.log
RELEASE_NOTE*.md
.vscode
docs/
docs/
package-lock.json

View File

@@ -1,6 +1,20 @@
# Changelog
## [1.2.1](https://github.com/peng92055/smart-table/tree/1.2.1) (2020-02-08)
## [1.2.3](https://github.com/peng92055/smart-table/tree/1.2.3) (2020-05-06)
[Full Changelog](https://github.com/peng92055/smart-table/compare/1.2.2...1.2.3)
- 优化树形表格含有非法expand-parent
- 优化树形表格支持自定义高度控制
- 修复expand中多标签bug
## [1.2.2](https://github.com/peng92055/smart-table/tree/1.2.2) (2020-02-19)
[Full Changelog](https://github.com/peng92055/smart-table/compare/1.2.1...1.2.2)
- 增加动态开展行支持异步请求指定关键key
## [1.2.1](https://github.com/peng92055/smart-table/tree/1.2.1) (2020-02-11)
[Full Changelog](https://github.com/peng92055/smart-table/compare/1.2.0...1.2.1)

View File

@@ -1,6 +1,7 @@
# Smart Table 组件
![Badge](https://img.shields.io/badge/Hey!-Everybody-yellow)
![Version](https://img.shields.io/github/package-json/v/peng92055/smart-table)
![build](https://travis-ci.org/peng92055/smart-table.svg?branch=master)
![License](https://img.shields.io/github/license/peng92055/smart-table)
**专处理纯静态table固定头列及排序功能**
@@ -24,6 +25,7 @@
- 树形结构
- 单选
- 多选
- 开展动态行
## 体验
可直接访问https://peng92055.github.io/smart-table
@@ -68,8 +70,18 @@
height: 300,
align: 'left',
size: 'middle',
selection: 'checkbox',
selectionKey: 1,
expandCallback: function(slot, value) {
//模拟异步 可直接写同步代码
setTimeout(function() {
var content = "<span>我是展开内容第一次,当前展开的值为:" + value + "</span>"
slot.open(content, true) //第二个参数为是否需要parseDom 当传递的content为字符串时该值必须传递true
var content2 = document.createElement("span")
content2.innerText = "我是展开内容第二次,当前展开的值为:" + value
slot.open(content2)
})
}
})
```
@@ -99,8 +111,9 @@
| expand | boolean | no | 是否开启树形结构(树形结构会忽略排序及固定列) | false |
| defaultExpandAll | boolean | no | 是否默认展开所有树形结构 | false |
| selection | string | no | 单选或多选radio、checkbox)选中值会存储在根节点selected属性上 | false |
| selectionKey | string or number | no | 单选多选时选中取值对应的tbody中有效列的角标(角标从0开始) | 0 |
| selectionKey | string or number | no | 单选多选或展开时选中取值对应的tbody中有效列的角标(角标从0开始) | 0 |
| radioBgColor | string | no | 单选时body中选中行的背景色 | '#D1E7FF' |
| expandCallback | function | no | 动态展开行回调函数回传slot及value参数 | |

View File

@@ -10,7 +10,7 @@ module.exports = merge(common, {
inject: 'head'
})
],
devtool: 'inline-source-map',
devtool: 'cheap-module-eval-source-map',
devServer: {
contentBase: './examples'
}

View File

@@ -23,6 +23,7 @@ module.exports = merge(common, {
}
}],
},
devtool: 'cheap-module-source-map',
plugins: [
new CleanWebpackPlugin(),
new webpack.BannerPlugin(`smartTable v${pkg.version} | (c) pengyajun 2020 | Released under the MIT License.`),

View File

@@ -21,6 +21,7 @@ module.exports = merge(common, {
}
}],
},
devtool: 'cheap-module-source-map',
plugins: [
new CleanWebpackPlugin(),
new webpack.BannerPlugin(`smartTable v${pkg.version} | (c) pengyajun 2020 | Released under the MIT License.`)

File diff suppressed because one or more lines are too long

1
dist/smartTable.min.js.map vendored Normal file
View File

@@ -0,0 +1 @@
{"version":3,"file":"smartTable.min.js","sources":["webpack:///smartTable.min.js"],"mappings":"AACA","sourceRoot":""}

View File

@@ -82,6 +82,7 @@
<p> <a href="#smartTable2">&bull;&nbsp;固定列</a></p>
<p> <a href="#smartTable2">&bull;&nbsp;多选</a></p>
<p> <a href="#smartTable3">&bull;&nbsp;树形表</a></p>
<p> <a href="#smartTable4">&bull;&nbsp;展开动态行</a></p>
</div>
<div class="container">
<div id="smartTable1">
@@ -368,6 +369,99 @@
</tbody>
</table>
</div>
<div id="smartTable4">
<table stripe>
<thead>
<tr>
<th colspan="1" fixed sort>Id</th>
<th colspan="1" fixed sort>Logo</th>
<th colspan="1" width="200" fixed>日期</th>
<th colspan="1" width="100" sort>姓名</th>
<th colspan="1">省份(包含自治区)</th>
<th colspan="1" sort>市区</th>
<th colspan="1">地址</th>
<th colspan="1" width="95" fixed>邮编</th>
</tr>
</thead>
<tbody>
<tr>
<td>10</td>
<td><img src="./assets/js-table.png" /></td>
<td>2020-01-03</td>
<td>1王小虎</td>
<td>1上海</td>
<td>2长宁区</td>
<td>3上海市长宁区淞虹路888号</td>
<td>200331</td>
</tr>
<tr>
<td>13</td>
<td><img src="./assets/js-table.png" /></td>
<td>2020-02-03</td>
<td>2王小虎</td>
<td>3上海</td>
<td>4长宁区</td>
<td>2上海市长宁区淞虹路888号</td>
<td>200331</td>
</tr>
<tr>
<td>14</td>
<td><img src="./assets/js-table.png" /></td>
<td>2020-03-03</td>
<td>3王小虎</td>
<td>4上海</td>
<td>1长宁区</td>
<td>6上海市长宁区淞虹路888号</td>
<td>200331</td>
</tr>
<tr>
<td>15</td>
<td><img src="./assets/js-table.png" /></td>
<td>2020-02-03</td>
<td>2王小虎</td>
<td>3上海</td>
<td>4长宁区</td>
<td>2上海市长宁区淞虹路888号</td>
<td>200331</td>
</tr>
<tr>
<td>14</td>
<td><img src="./assets/js-table.png" /></td>
<td>2020-03-03</td>
<td>3王小虎</td>
<td>4上海</td>
<td>1长宁区</td>
<td>6上海市长宁区淞虹路888号</td>
<td>200331</td>
</tr>
<tr>
<td>13</td>
<td><img src="./assets/js-table.png" /></td>
<td>2020-02-03</td>
<td>2王小虎</td>
<td>3上海</td>
<td>4长宁区</td>
<td>2上海市长宁区淞虹路888号</td>
<td>200331</td>
</tr>
<tr>
<td>14</td>
<td><img src="./assets/js-table.png" /></td>
<td>2020-03-03</td>
<td>3王小虎</td>
<td>4上海</td>
<td>1长宁区</td>
<td>6上海市长宁区淞虹路888号</td>
<td>200331</td>
</tr>
<tr unsort>
<td colspan="6">合计</td>
<td>6上海市长宁区淞虹路888号</td>
<td>200331</td>
</tr>
</tbody>
</table>
</div>
</div>
<script>
@@ -391,6 +485,20 @@
expand: true,
defaultExpandAll: true
})
new SmartTable({
selector: '#smartTable4',
height: 320,
expandCallback: function(slot, value) {
setTimeout(function() {
var content = "<span>我是展开内容第一次,当前展开的值为:" + value + "</span>"
slot.open(content, true)
var content2 = document.createElement("span")
content2.innerText = "我是展开内容第二次,当前展开的值为:" + value
slot.open(content2)
}, 2000)
}
})
</script>
</body>

View File

@@ -21,6 +21,7 @@ import {
debounce,
getAttrNumber,
createCheckbox,
createExpandTrigger,
refactorCell,
replaceColGroup,
createTableWrapper,
@@ -29,7 +30,7 @@ import {
import scrollBarWidth from './scrollbar-width';
export default function initMixin(Table) {
Table.prototype._init = function(options = {}) {
Table.prototype._init = function (options = {}) {
if (!options.selector) {
return console.error("Smart Table init need a selector")
}
@@ -49,14 +50,18 @@ export default function initMixin(Table) {
hasAttribute(table, "stripe") && tbody.classList.add("stripe")
options.expand ? (querySelectorAll(thead, 'th[sort]').forEach(column => {
removeAttribute(column, "sort")
}), querySelectorAll(thead, 'th[fixed]').forEach(column => {
removeAttribute(column, "fixed")
})) : (querySelectorAll(tbody, 'tr[expand]').forEach(column => {
removeAttribute(column, "expand")
}), querySelectorAll(thead, 'tr[expand-parent]').forEach(column => {
removeAttribute(column, "expand-parent")
}))
removeAttribute(column, "sort")
}), querySelectorAll(thead, 'th[fixed]').forEach(column => {
removeAttribute(column, "fixed")
})) : (querySelectorAll(tbody, 'tr[expand]').forEach(column => {
removeAttribute(column, "expand")
}), querySelectorAll(thead, 'tr[expand-parent]').forEach(column => {
removeAttribute(column, "expand-parent")
}))
!!options.expandCallback && (querySelectorAll(thead, 'th[fixed]').forEach(column => {
removeAttribute(column, "fixed")
}))
const vm = this;
vm.$root = root
@@ -70,6 +75,9 @@ export default function initMixin(Table) {
}
vm.size = {}
vm.hasCheckbox = !options.expand && options.selection === 'checkbox'
vm.hasExpandCb = !!options.expandCallback
vm.hasExpandCb && appendExpandTrigger(vm)
vm.hasCheckbox && appendCheckbox(vm)
@@ -89,25 +97,48 @@ export default function initMixin(Table) {
bindEvents(vm)
const th = createElement("th");
styled(th, { display: 'none' })
styled(th, {
display: 'none'
})
setAttribute(th, "width", vm.gutterWidth);
setAttribute(th, "rowspan", vm.props.shapes.length);
appendChild(querySelector(vm.$thead, "tr"), th);
vm.$scrollTH = th;
if (vm.scrollY) {
styled(vm.$scrollTH, { display: 'table-cell' })
styled(vm.$scrollTH, {
display: 'table-cell'
})
resize(vm)
}
}
}
function appendCheckbox(vm) {
const { $thead, $tbody } = vm;
function appendExpandTrigger(vm) {
const {
$thead,
$tbody
} = vm;
let theadRow = querySelector($thead, "tr");
let th = theadRow.querySelector("th");
let selectionTh = createCheckbox("th", getAttrNumber(th, "rowspan", 1));
hasAttribute(th, "fixed") && setAttribute(selectionTh, "fixed")
insertBefore(theadRow, selectionTh, th)
let cell = createExpandTrigger("th", getAttrNumber(th, "rowspan", 1));
hasAttribute(th, "fixed") && setAttribute(cell, "fixed")
insertBefore(theadRow, cell, th)
querySelectorAll($tbody, "tr").forEach(row => {
let td = row.querySelector("td")
insertBefore(row, createExpandTrigger("td", getAttrNumber(td, "rowspan", 1)), td)
})
}
function appendCheckbox(vm) {
const {
$thead,
$tbody
} = vm;
let theadRow = querySelector($thead, "tr");
let th = theadRow.querySelector("th");
let cell = createCheckbox("th", getAttrNumber(th, "rowspan", 1));
hasAttribute(th, "fixed") && setAttribute(cell, "fixed")
insertBefore(theadRow, cell, th)
querySelectorAll($tbody, "tr").forEach(row => {
let td = row.querySelector("td")
insertBefore(row, createCheckbox("td", getAttrNumber(td, "rowspan", 1)), td)
@@ -115,8 +146,15 @@ function appendCheckbox(vm) {
}
function layout(vm, table) {
const { $root, $thead, $tbody, options } = vm;
const { height } = options;
const {
$root,
$thead,
$tbody,
options
} = vm;
const {
height
} = options;
querySelectorAll($thead, "th").forEach(cell => refactorCell(cell))
querySelectorAll($tbody, "td").forEach(cell => refactorCell(cell))
@@ -132,7 +170,10 @@ function layout(vm, table) {
const theadHeight = offsetHeight($thead);
const custHeight = (typeof height === 'function' ? height.call() : height) || offsetHeight($root);
const tbodyWrapperHeight = custHeight > theadHeight ? (custHeight - theadHeight - 1) : (theadHeight + 150)
styled(vm.$tbodyWrapper, { height: tbodyWrapperHeight + "px" })
styled(vm.$tbodyWrapper, {
height: tbodyWrapperHeight + "px"
})
vm.size.tbodyWrapperHeight = tbodyWrapperHeight;
@@ -144,7 +185,10 @@ function layout(vm, table) {
//根据表格中的tbody第一行 查出每列的宽度并记录
function initColgroupData(vm) {
const { $root, props } = vm;
const {
$root,
props
} = vm;
const rootWidth = offsetWidth($root) - 1;
const clientWidth = rootWidth - (vm.scrollY ? vm.gutterWidth : 0);
let arr = [];
@@ -171,8 +215,8 @@ function initColgroupData(vm) {
totalWidth = 0;
arr = arr.map((item, index) => {
if (item === 0) {
if (vm.hasCheckbox && index === 0) {
item = per > 55 ? per : 55;
if ((vm.hasCheckbox || vm.hasExpandCb) && index === 0) {
item = 55;
} else {
item = min;
}
@@ -203,13 +247,16 @@ function bindResizeEvents(vm) {
function bindEvents(vm) {
bindScrollEvents(vm);
bindRowEvents(vm);
vm.options.expand ? bindExpandEvents(vm) : bindSortEvents(vm);
vm.options.expand ? bindExpandTreeEvents(vm) : bindSortEvents(vm);
bindResizeEvents(vm);
}
function resize(vm) {
debounce(500, () => {
const { fixedLeft, fixedRight } = vm.props;
const {
fixedLeft,
fixedRight
} = vm.props;
initColgroupData(vm)
replaceColGroup(vm)
@@ -272,7 +319,7 @@ function syncPostion(vm) {
})()
}
function bindExpandEvents(vm) {
function bindExpandTreeEvents(vm) {
function seek(arr) {
arr.forEach(item => {
if (item.expand) {
@@ -286,7 +333,9 @@ function bindExpandEvents(vm) {
function expanding(item, expanded) {
expanded ? setAttribute(item.$el, "expanded") : removeAttribute(item.$el, "expanded");
item.children && (item.children.forEach(child => {
styled(child.$el, { display: expanded ? '' : 'none' })
styled(child.$el, {
display: expanded ? '' : 'none'
})
expanding(child, expanded)
}))
}
@@ -301,14 +350,19 @@ function bindScrollEvents(vm) {
}
function bindRowEvents(vm) {
const { selection, selectionKey } = vm.options;
let {
selection,
selectionKey
} = vm.options;
selectionKey = selectionKey || 0;
vm.hasExpandCb && (selectionKey++)
const totalCheckbox = querySelector(vm.$fixedLeft || vm.$thead, "th>.stb_cell>label.std-checkbox");
[].concat(vm.data, vm.unsortData).forEach(row => {
addHoverEvent(vm, row.$el, [row.$fixedLeftEl, row.$fixedRightEl])
row.$fixedLeftEl && addHoverEvent(vm, row.$fixedLeftEl, [row.$el, row.$fixedRightEl])
row.$fixedRightEl && addHoverEvent(vm, row.$fixedRightEl, [row.$el, row.$fixedLeftEl])
const value = row['field-' + selectionKey]
if (selection) {
let value = row['field-' + (selectionKey || 0)]
switch (selection) {
case 'radio':
addRadioEvent(vm, row.$el, [row.$fixedLeftEl, row.$fixedRightEl], value)
@@ -320,17 +374,55 @@ function bindRowEvents(vm) {
break
}
}
vm.hasExpandCb && addExpandTriggerEvent(vm, row.$fixedLeftEl || row.$el, row.$key, value)
})
if (vm.hasCheckbox) {
addTotalCheckboxEvent(vm, totalCheckbox)
}
}
function addExpandTriggerEvent(vm, row, key, value) {
const {
options
} = vm;
const trigger = querySelector(row, ".expand-cell>.stb_cell")
if (!trigger) return;
trigger.addEventListener('click', ($event) => {
if (trigger.hasAttribute("loading")) return;
if (trigger.hasAttribute("open")) {
removeAttribute(trigger, "open")
querySelectorAll(vm.$root, "tr.expand-" + key).forEach(expandRow => {
removeChild(expandRow.parentNode, expandRow)
})
} else {
setAttribute(trigger, "loading", true)
options.expandCallback.call(this, {
open: function (content, needParse) {
let cell = createElement("td")
setAttribute(cell, "colspan", vm.colgroup.length)
let wrapper = createElement("div", "std-dialog_content")
needParse ? (wrapper.innerHTML = content) : (appendChild(wrapper, content))
appendChild(cell, wrapper)
let expandRow = createElement("tr", `std-expand-row expand-${key}`)
appendChild(expandRow, cell)
insertBefore(row.parentNode, expandRow, row.nextSibling)
setAttribute(trigger, "open")
removeAttribute(trigger, "loading")
}
}, value)
}
$event.stopPropagation();
})
}
function addCheckboxEvent(vm, row, totalCheckbox, value) {
const trigger = querySelector(row, "label.std-checkbox")
if (!trigger || !totalCheckbox) return;
trigger.addEventListener('click', () => {
let { selected } = vm;
let {
selected
} = vm;
selected = selected || [];
const target = !hasAttribute(trigger, "checked");
target ? setAttribute(trigger, 'checked', true) : removeAttribute(trigger, 'checked')
@@ -344,14 +436,17 @@ function addCheckboxEvent(vm, row, totalCheckbox, value) {
}
vm.selected = selected;
})
}
function addTotalCheckboxEvent(vm, totalCheckbox) {
if (!totalCheckbox) return;
const { selectionKey } = vm.options;
const {
selectionKey
} = vm.options;
totalCheckbox.addEventListener('click', () => {
let { selected } = vm;
let {
selected
} = vm;
selected = [];
const target = !hasAttribute(totalCheckbox, "checked");
target ? setAttribute(totalCheckbox, 'checked', true) : removeAttribute(totalCheckbox, 'checked');
@@ -369,11 +464,15 @@ function addTotalCheckboxEvent(vm, totalCheckbox) {
function addRadioEvent(vm, trigger, relates, radioValue) {
if (!trigger) return;
trigger.addEventListener('click', () => {
let { selected } = vm;
let {
selected
} = vm;
let target = false;
if (selected === radioValue && !hasAttribute(trigger, "checked")) return;
if (selected !== radioValue) {
querySelectorAll(vm.$root, 'tr[checked]>td').forEach(item => styled(item, { background: '' }))
querySelectorAll(vm.$root, 'tr[checked]>td').forEach(item => styled(item, {
background: ''
}))
querySelectorAll(vm.$root, 'tr[checked]').forEach(item => removeAttribute(item, "checked"))
target = true;
} else {
@@ -384,13 +483,17 @@ function addRadioEvent(vm, trigger, relates, radioValue) {
selected = target ? radioValue : null;
target ? setAttribute(trigger, "checked", true) : removeAttribute(trigger, "checked");
trigger.querySelectorAll("td").forEach(column => {
styled(column, { background: target ? vm.style.radioBgColor : '' })
styled(column, {
background: target ? vm.style.radioBgColor : ''
})
})
relates.forEach(item => {
if (item) {
target ? setAttribute(item, "checked", true) : removeAttribute(item, "checked")
item.querySelectorAll("td").forEach(column => {
styled(column, { background: target ? vm.style.radioBgColor : '' })
styled(column, {
background: target ? vm.style.radioBgColor : ''
})
})
}
})
@@ -402,15 +505,23 @@ function addRadioEvent(vm, trigger, relates, radioValue) {
function addHoverEvent(vm, trigger, relates) {
if (!trigger) return;
trigger.addEventListener('mouseenter', () => {
styled(trigger, { background: vm.style.hoverBgColor })
styled(trigger, {
background: vm.style.hoverBgColor
})
relates.forEach(el => {
el && styled(el, { background: vm.style.hoverBgColor })
el && styled(el, {
background: vm.style.hoverBgColor
})
})
})
trigger.addEventListener('mouseleave', () => {
styled(trigger, { background: '' })
styled(trigger, {
background: ''
})
relates.forEach(el => {
el && styled(el, { background: '' })
el && styled(el, {
background: ''
})
})
})
}
@@ -437,6 +548,15 @@ function bindSortEvents(vm) {
}
return item
})
querySelectorAll(vm.$root, "tr.std-expand-row").forEach(row => {
removeChild(row.parentNode, row)
})
querySelectorAll(vm.$root, ".expand-cell>.stb_cell[open]").forEach(el => {
removeAttribute(el, "open")
})
querySelectorAll(vm.$root, ".expand-cell>.stb_cell[loading]").forEach(el => {
removeAttribute(el, "loading")
})
sort(vm, getAttribute(el, "sortkey"), sortType, sortOrder)
})
})
@@ -548,21 +668,28 @@ function initExpand(vm, tbody) {
const expandAll = vm.options.defaultExpandAll;
let data = [];
let parents = [];
let parentIds = [];
querySelectorAll(tbody, "tr").forEach(row => {
let paddingLength = parents.length;
let expand = hasAttribute(row, "expand");
let hasParent = hasAttribute(row, "expand-parent");
let node = { $el: row, id: getAttribute(row, "expand"), expand: expand };
if (expand) {
if (expandAll) {
setAttribute(row, 'expanded')
} else {
removeAttribute(row, 'expanded')
}
let expandParentId = getAttribute(row, "expand-parent");
if (parentIds.indexOf(expandParentId) === -1) {
hasParent = false;
}
let node = {
$el: row,
id: getAttribute(row, "expand"),
expand: expand
};
if (expand) {
expandAll ? setAttribute(row, 'expanded') : removeAttribute(row, 'expanded');
}
if (expand && !hasParent) {
node.children = [];
parents = [node];
parentIds.push(node.id)
data.push(node);
} else if (hasParent) {
let parentId = getAttribute(row, "expand-parent");
@@ -579,18 +706,28 @@ function initExpand(vm, tbody) {
parent && parent.children.push(node);
if (expand) {
parents.push(node)
parentIds.push(node.id)
node.children = [];
}
} else {
data.push(node)
}
if (hasParent) {
styled(querySelector(row, "td"), { paddingLeft: 32 * paddingLength + "px" })
styled(row, { display: expandAll ? '' : 'none' })
styled(querySelector(row, "td"), {
paddingLeft: 32 * paddingLength + "px"
})
styled(row, {
display: expandAll ? '' : 'none'
})
}
})
vm.expandData = data;
styled(vm.$tbodyWrapper, { height: '' })
styled(vm.$tbodyWrapper, {
height: ''
})
styled(vm.$tbodyWrapper, {
maxHeight: vm.size.tbodyWrapperHeight + 'px'
})
}
function initData(vm, tbody) {
@@ -603,7 +740,7 @@ function initData(vm, tbody) {
$el: row,
$fixedLeftEl: fixedLeftRows && fixedLeftRows[index],
$fixedRightEl: fixedRightRows && fixedRightRows[index],
$key: '$$rowkey' + index
$key: 'rowkey' + index
};
querySelectorAll(row, "td .stb_cell").forEach((cell, index) => {
rowData["field-" + index] = cell.innerHTML;

View File

@@ -1,5 +1,6 @@
import {
appendChild,
removeChild,
setAttribute,
getAttribute,
createElement,
@@ -20,14 +21,23 @@ export function refactorCell(cell) {
export function createCheckbox(parentTag, rowspan) {
if (!parentTag) return;
let td = createElement(parentTag)
setAttribute(td, "rowspan", rowspan)
let cell = createElement(parentTag)
setAttribute(cell, "rowspan", rowspan)
let wrapper = createElement("label", "std-checkbox");
let input = createElement("span", "std-checkbox_input");
appendChild(input, createElement("span", "std-checkbox_inner"))
appendChild(wrapper, input)
appendChild(td, wrapper)
return td
appendChild(cell, wrapper)
return cell
}
export function createExpandTrigger(parentTag, rowspan) {
if (!parentTag) return;
let cell = createElement(parentTag, parentTag === "td" ? "expand-cell" : "")
setAttribute(cell, "rowspan", rowspan)
let trigger = createElement("span", parentTag === "td" ? "expand-trigger" : "")
appendChild(cell, trigger)
return cell
}
export function createTableWrapper(className, vm, type, content) {

View File

@@ -9,6 +9,7 @@
border: 1px solid #ECF0F5;
border-right: none;
border-bottom: none;
&:after,
&:before {
content: "";
@@ -16,35 +17,43 @@
background-color: #ECF0F5;
z-index: 1;
}
&:before {
left: 0;
bottom: 0;
width: 100%;
height: 1px;
}
&:after {
top: 0;
right: 0;
width: 1px;
height: 100%;
}
table {
border-spacing: 0;
border: 0;
}
thead {
background: #F5F7FB;
font-size: 13px;
}
tr {
transition: background-color .25s ease;
}
tbody {
font-size: 12px;
tr[expand] {
td:first-child {
cursor: pointer;
:before {
&:before {
transition: 0.35s ease transform;
transform-origin: 25% 50%;
content: '';
@@ -57,16 +66,58 @@
margin: 5px 0 0 5px;
}
}
&[expanded]>td:first-child>:before {
transform: rotate(90deg);
&[expanded]>td:first-child {
&:before {
transform: rotate(90deg);
}
}
}
.expand-trigger {
display: inline-block;
transition: 0.35s ease transform;
transform-origin: 25% 50%;
width: 0;
height: 0;
border-width: 6px;
border-style: solid;
border-color: transparent transparent transparent #c0c4cc;
margin-left: 5px;
}
.expand-cell>.stb_cell {
cursor: pointer;
&[open] {
.expand-trigger {
transform: rotate(90deg);
}
}
&[loading] {
.expand-trigger {
margin-left: 0;
width: 1em;
height: 1em;
border-color: none;
transform-origin: center;
border: .2em solid transparent;
border-left-color: currentcolor;
border-right-color: currentcolor;
border-radius: 50%;
animation: 1s loading linear infinite;
}
}
}
&.stripe {
tr:nth-child(2n) {
background-color: #F9FBFF;
}
}
}
td,
th {
padding: 5px 0;
@@ -76,17 +127,21 @@
border-bottom: 1px solid #ECF0F5;
border-right: 1px solid #ECF0F5;
text-align: center;
&.is-hidden>* {
visibility: hidden;
}
}
th {
user-select: none;
overflow: hidden;
&[sort] {
&[sort]>.stb_cell {
cursor: pointer;
:before,
:after {
&:before,
&:after {
content: '';
float: right;
width: 0;
@@ -94,80 +149,99 @@
border-width: 5px;
border-style: solid;
}
:before {
&:before {
margin: 1px 0 0 -10px;
border-color: transparent transparent #c0c4cc transparent;
}
:after {
&:after {
margin: 12px 0 0 4px;
border-color: #c0c4cc transparent transparent transparent;
}
&.desc {
:after {
&:after {
border-top-color: #409eff;
}
}
&.asc {
:before {
&:before {
border-bottom-color: #409eff;
}
}
}
}
&.stb-cust-large {
thead {
font-size: 16px;
}
tbody {
font-size: 15px;
}
td,
th {
padding: 12px 0;
}
}
&.stb-cust-middle {
thead {
font-size: 15px;
}
tbody {
font-size: 14px;
}
td,
th {
padding: 10px 0;
}
}
&.stb-cust-left {
td,
th {
text-align: left;
}
}
&.stb-cust-right {
td,
th {
text-align: right;
}
}
th[align="left"],
td[align="left"] {
text-align: left;
}
th[align="center"],
td[align="center"] {
text-align: center;
}
th[align="right"],
td[align="right"] {
text-align: right;
}
th[nowrap],
td[nowrap] {
.stb_cell {
white-space: nowrap;
}
}
.std-checkbox_inner {
display: inline-block;
position: relative;
@@ -179,6 +253,7 @@
background-color: #fff;
z-index: 1;
transition: border-color .25s cubic-bezier(.71, -.46, .29, 1.46), background-color .25s cubic-bezier(.71, -.46, .29, 1.46);
&:after {
box-sizing: content-box;
content: "";
@@ -195,6 +270,7 @@
transform-origin: center;
}
}
.std-checkbox_input {
white-space: nowrap;
cursor: pointer;
@@ -204,6 +280,7 @@
position: relative;
vertical-align: middle;
}
.std-checkbox {
color: #606266;
font-weight: 500;
@@ -213,14 +290,17 @@
display: inline-block;
white-space: nowrap;
user-select: none;
&[checked]>.std-checkbox_input>.std-checkbox_inner {
background-color: #409eff;
border-color: #409eff;
&:after {
transform: rotate(45deg) scaleY(1);
}
}
}
.stb_cell {
overflow: hidden;
text-overflow: ellipsis;
@@ -229,11 +309,13 @@
padding: 0 4px;
line-height: 23px;
}
th>.stb_cell {
display: inline-block;
position: relative;
vertical-align: middle;
}
.stb_body,
.stb_footer,
.stb_header {
@@ -241,12 +323,15 @@
border-collapse: separate;
background: #fff;
}
.stb_header-wrapper {
overflow: hidden;
}
.stb_body-wrapper {
overflow: auto;
}
.stb_fixed,
.stb_fixed-right {
position: absolute;
@@ -256,11 +341,13 @@
overflow-y: hidden;
box-shadow: 0 -1px 8px rgba(0, 0, 0, .08);
}
.stb_fixed-right {
top: 0;
left: auto;
right: 0;
box-shadow: -1px 0 8px rgba(0, 0, 0, .08);
.stb_fixed-body-wrapper,
.stb_fixed-footer-wrapper,
.stb_fixed-header-wrapper {
@@ -268,18 +355,21 @@
right: 0;
}
}
.stb_fixed-right-patch {
position: absolute;
top: -1px;
right: 0;
background-color: #F5F7FB;
}
.stb_fixed-header-wrapper {
position: absolute;
left: 0;
top: 0;
z-index: 3;
}
.stb_fixed-body-wrapper {
position: absolute;
left: 0;
@@ -287,19 +377,47 @@
overflow: hidden;
z-index: 3;
}
::-webkit-scrollbar {
::-webkit-scrollbar {
width: 8px;
height: 8px;
background-color: #e9edf4;
}
::-webkit-scrollbar-thumb {
::-webkit-scrollbar-thumb {
background-color: #ccc;
border-radius: 2em;
}
::-webkit-scrollbar-thumb:hover {
::-webkit-scrollbar-thumb:hover {
background-color: #919191;
}
* {
box-sizing: border-box;
}
@-webkit-keyframes loading {
0% {
-webkit-transform: rotate(0deg);
transform: rotate(0deg);
}
100% {
-webkit-transform: rotate(360deg);
transform: rotate(360deg);
}
}
@keyframes loading {
0% {
-webkit-transform: rotate(0deg);
transform: rotate(0deg);
}
100% {
-webkit-transform: rotate(360deg);
transform: rotate(360deg);
}
}
}

8922
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@@ -1,6 +1,6 @@
{
"name": "smart-table",
"version": "1.2.1",
"version": "1.2.3",
"description": "smart table for static html",
"main": "index.js",
"scripts": {