I. Purpose of use:

Sometimes there are too many data items in our table, and scrolling is still troublesome to use the horizontal scroll bar. At this time, the requirement requires that the width of the head of our table can be automatically stretched, changed, and customized to display the data we need to see. At this time, we can consider using vue-Draggable – Resizable plug-in. Work with our table plug-in.

Ii. Applicable version

Suitable for us to use antdUI framework version 2.0 below, need to achieve table header can be customized width effect.

Three, the operation process

1. Use antD framework to draw basic table components

<a-table
  :columns="headers"
  :dataSource="dataSource"
  :pagination="false"
  rowKey="id"
  bordered
  :components="components"
  :scroll="{y: wrapHeight - 440, x: 1500}"
  onChange: onSelectChange"
></a-table>
Copy the code
  • For the specific use of A-table, please refer to relevant documents. Here, we need to pay attention to:
  1. Components parameter: This parameter is used to render the table interface through vue-Draggable -resizable plugin.
  2. Bordered parameter: This parameter is used to add box lines to the table because we need to drag and drop the border of the table header when stretching the table.
  3. Columns parameter: A-table determines whether two Columns are equal. One is based on the key. If the keys are equal, the Columns are equal. The other is to determine whether two COL entities are equal (the former precedes the latter). Since the width of col has changed after stretching, we need to use the first judgment method, so we need to set the key value of the sequence.

2. Set parameters of Components and specify table rendering rules

Because our tables usually have sorting functions, and table information can change at any time, our rendering rule components need to be placed in computed.

computed: { components () { return { header: { cell: (h, props, children) => { const {key, ... RestProps} = props // Because the drag event is over, the click event must be started, Const col = this.headers. Find (col => {const col = this.headers. Find (col => {const col = this.headers. Const k = col. DataIndex | | col. Key return k = = = key}) / / if there is no set col width, directly the same render back, don't add stretch form function if (! col || ! col.width) { return h('th', {... // If there is a width, set vue-draggable-resizable render parameter const dragProps = {key: col.dataIndex || col.key, class: 'table-draggable-handle', attrs: { w: 10, x: col.width, z: 1, axis: 'x', draggable: True, transform: 'None ', resizable: false}, draggable: true, resizable: false, on: {// Drag while setting isdrag parameter to true dragging: (x, y) => {isDrag = true col.width = math.max (x, 40)}, () => { isDrag = true // eslint-disable-next-line vue/no-async-in-computed-properties setTimeout(() => { isDrag = false }, 300)}} // Select select * from column click; If (restProps. On && restProps.on.click) {let clickFunc = restProps. On. => {if (isDrag) {return} clickFunc(event)}} // Render vue-draggable-resizable to column Const drag = h('vue-draggable-resizable', {... dragProps}) return h('th', {... restProps, class: 'resize-table-th'}, [...children, drag]) } } } } },Copy the code

Here we need to understand:

  1. The header’s cell function is specifically used for our header rendering
  2. The Cell passes in three arguments, H,props, and children. Where h is a rendering function, and h () in vue. Props refers to the data that the table passes to the table header cell. This includes the table primary key, and the entire table entity. The last children is a child component of the table.
  3. The isDrag parameter determines whether the current action is a click or drag. After the drag is complete, there is a setTimeout asynchronous function to prevent the click event from being triggered after the isDrag data is updated.

3. Set the sorter of the columns parameter and monitor the change of the sortOrder parameter through watch

Since we set components in computed, columns cannot achieve dynamic update, and sortOrder needs to change in time, so we use Watch alone to achieve dynamic update of columns.

watch: {
  sortedInfo () {
    this.columns.forEach(item => {
      if (item.sorter) item.sortOrder = this.sortedInfo && this.sortedInfo.columnKey === item.dataIndex && this.sortedInfo.order
    })
  }
},
Copy the code

4. Add the corresponding class

>>>.resize-table-th { position: relative; } >>> .table-draggable-handle { transform: none ! important; position: absolute; height: 100% ! important; bottom: 0; left: auto ! important; right: -5px; cursor: col-resize; touch-action: none; }Copy the code

Four, notes

  1. Note that the above method is applicable to vue2+ ANTd1 and does not apply to other versions.
  2. Be sure to set the width of columns that need to be stretched
  3. Stretching a table header may image other table header cells when the width is less than the screen width.
  4. After the table header is stretched, the length of the table may exceed the width of the table. Therefore, you need to set x for the Scroll attribute of the table to prevent inconsistency between the table header and data.